0
Fork 0
mirror of https://github.com/logto-io/logto.git synced 2025-01-20 21:32:31 -05:00

feat(schemas): add email service guard and system key (#4079)

This commit is contained in:
Darcy Ye 2023-06-28 10:59:03 +08:00 committed by GitHub
parent ad6dde7f18
commit 4dc0930e09
No known key found for this signature in database
GPG key ID: 4AEE18F83AFDEB23
4 changed files with 78 additions and 6 deletions

View file

@ -1,9 +1,12 @@
import {
CloudflareKey,
EmailServiceProviderKey,
type HostnameProviderData,
type StorageProviderData,
type EmailServiceData,
hostnameProviderDataGuard,
storageProviderDataGuard,
emailServiceDataGuard,
StorageProviderKey,
type SystemKey,
} from '@logto/schemas';
@ -17,6 +20,7 @@ export default class SystemContext {
static shared = new SystemContext();
public storageProviderConfig?: StorageProviderData;
public hostnameProviderConfig?: HostnameProviderData;
public emailServiceProviderConfig?: EmailServiceData;
async loadProviderConfigs(pool: CommonQueryMethods) {
await Promise.all([
@ -34,6 +38,13 @@ export default class SystemContext {
hostnameProviderDataGuard
);
})(),
(async () => {
this.emailServiceProviderConfig = await this.loadConfig(
pool,
EmailServiceProviderKey.EmailServiceProvider,
emailServiceDataGuard
);
})(),
]);
}

View file

@ -19,6 +19,7 @@ export const connectorResponseGuard = Connectors.guard
z.object({
type: z.nativeEnum(ConnectorType),
isDemo: z.boolean().optional(),
extraInfo: z.record(z.unknown()).optional(),
})
);

View file

@ -1,3 +1,4 @@
import { verificationCodeTypeGuard } from '@logto/connector-kit';
import type { ZodType } from 'zod';
import { z } from 'zod';
@ -64,6 +65,54 @@ export const storageProviderGuard: Readonly<{
[StorageProviderKey.StorageProvider]: storageProviderDataGuard,
});
// Email service provider
export enum EmailServiceProvider {
SendGrid = 'SendGrid',
}
/**
* `General` is now used as a fallback scenario.
* This will be extended in the future since we will send different emails for
* different purposes (such as webhook that inform users of suspicious account activities).
*/
export enum OtherEmailTemplate {
General = 'General',
}
export const otherEmailTemplateGuard = z.nativeEnum(OtherEmailTemplate);
export const emailServiceDataGuard = z.discriminatedUnion('provider', [
z.object({
provider: z.literal(EmailServiceProvider.SendGrid),
appId: z.string(),
appSecret: z.string(),
fromEmail: z.string(),
templates: z.record(
verificationCodeTypeGuard.or(otherEmailTemplateGuard),
z.object({
subject: z.string(),
content: z.string(),
})
),
}),
]);
export type EmailServiceData = z.infer<typeof emailServiceDataGuard>;
export enum EmailServiceProviderKey {
EmailServiceProvider = 'EmailServiceProvider',
}
export type EmailServiceProviderType = {
[EmailServiceProviderKey.EmailServiceProvider]: EmailServiceData;
};
export const emailServiceProviderGuard: Readonly<{
[key in EmailServiceProviderKey]: ZodType<EmailServiceProviderType[key]>;
}> = Object.freeze({
[EmailServiceProviderKey.EmailServiceProvider]: emailServiceDataGuard,
});
// Demo social connectors
export enum DemoSocialProvider {
Google = 'google',
@ -120,22 +169,30 @@ export const cloudflareGuard: Readonly<{
});
// Summary
export type SystemKey = AlterationStateKey | StorageProviderKey | DemoSocialKey | CloudflareKey;
export type SystemKey =
| AlterationStateKey
| StorageProviderKey
| DemoSocialKey
| CloudflareKey
| EmailServiceProviderKey;
export type SystemType =
| AlterationStateType
| StorageProviderType
| DemoSocialType
| CloudflareType;
| CloudflareType
| EmailServiceProviderType;
export type SystemGuard = typeof alterationStateGuard &
typeof storageProviderGuard &
typeof demoSocialGuard &
typeof cloudflareGuard;
typeof cloudflareGuard &
typeof emailServiceProviderGuard;
export const systemKeys: readonly SystemKey[] = Object.freeze([
...Object.values(AlterationStateKey),
...Object.values(StorageProviderKey),
...Object.values(DemoSocialKey),
...Object.values(CloudflareKey),
...Object.values(EmailServiceProviderKey),
]);
export const systemGuards: SystemGuard = Object.freeze({
@ -143,4 +200,5 @@ export const systemGuards: SystemGuard = Object.freeze({
...storageProviderGuard,
...demoSocialGuard,
...cloudflareGuard,
...emailServiceProviderGuard,
});

View file

@ -229,9 +229,11 @@ export type EmailServiceBranding = z.infer<typeof emailServiceBrandingGuard>;
export const sendMessagePayloadGuard = z.object({
to: z.string(),
type: verificationCodeTypeGuard,
payload: z.object({
code: z.string(),
}),
payload: z
.object({
code: z.string(),
})
.merge(emailServiceBrandingGuard),
});
export type SendMessagePayload = z.infer<typeof sendMessagePayloadGuard>;