refactor(server): plugin modules (#5630)

- [x] separates modules into `fundamental`, `core`, `plugins`
- [x] optional modules with `@OptionalModule` decorator to install modules with requirements met(`requires`, `if`)
- [x] `module.contributesTo` defines optional features that will be enabled if module registered
- [x] `AFFiNE.plugins.use('payment', {})` to enable a optional/plugin module
- [x] `PaymentModule` is the first plugin module
- [x] GraphQLSchema will not be generated for non-included modules
- [x] Frontend can use `ServerConfigType` query to detect which features are enabled
- [x] override existing provider globally
This commit is contained in:
liuyi
2024-01-22 07:40:28 +00:00
parent ae8401b6f4
commit e516e0db23
130 changed files with 1297 additions and 974 deletions
@@ -10,13 +10,6 @@ declare global {
// eslint-disable-next-line no-var
var AFFiNE: AFFiNEConfig;
}
// eslint-disable-next-line @typescript-eslint/no-namespace
namespace NodeJS {
interface ProcessEnv {
SERVER_FLAVOR: ServerFlavor | '';
}
}
}
export enum ExternalAccount {
@@ -25,22 +18,28 @@ export enum ExternalAccount {
firebase = 'firebase',
}
export type ServerFlavor = 'allinone' | 'graphql' | 'sync' | 'selfhosted';
type ConfigPaths = LeafPaths<
export type ServerFlavor =
| 'allinone'
| 'main'
// @deprecated
| 'graphql'
| 'sync'
| 'selfhosted';
export type ConfigPaths = LeafPaths<
Omit<
AFFiNEConfig,
| 'ENV_MAP'
| 'version'
| 'baseUrl'
| 'origin'
| 'prod'
| 'dev'
| 'test'
| 'flavor'
| 'env'
| 'affine'
| 'deploy'
| 'node'
| 'baseUrl'
| 'origin'
>,
'',
'....'
'.....'
>;
/**
@@ -52,15 +51,28 @@ export interface AFFiNEConfig {
/**
* Server Identity
*/
readonly serverId: string;
serverId: string;
/**
* Name may show on the UI
*/
serverName: string;
/**
* System version
*/
readonly version: string;
/**
* Server flavor
*/
readonly flavor: ServerFlavor;
get flavor(): {
type: string;
main: boolean;
sync: boolean;
selfhosted: boolean;
};
/**
* Deployment environment
*/
@@ -172,38 +184,6 @@ export interface AFFiNEConfig {
limit: number;
};
/**
* Redis Config
*
* whether to use redis as Socket.IO adapter
*/
redis: {
/**
* if not enabled, use in-memory adapter by default
*/
enabled: boolean;
/**
* url of redis host
*/
host: string;
/**
* port of redis
*/
port: number;
username: string;
password: string;
/**
* redis database index
*
* Rate Limiter scope: database + 1
*
* Session scope: database + 2
*
* @default 0
*/
database: number;
};
/**
* authentication config
*/
@@ -341,15 +321,6 @@ export interface AFFiNEConfig {
metrics: {
enabled: boolean;
};
payment: {
stripe: {
keys: {
APIKey: string;
webhookKey: string;
};
} & import('stripe').Stripe.StripeConfig;
};
}
export * from './storage';