@contember/engine-server 0.12.0-beta.0 → 1.0.0-alpha.1

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (62) hide show
  1. package/alpine.dockerfile +2 -2
  2. package/debian.dockerfile +1 -1
  3. package/dist/src/MasterContainer.d.ts +4 -1
  4. package/dist/src/MasterContainer.d.ts.map +1 -1
  5. package/dist/src/MasterContainer.js +60 -31
  6. package/dist/src/MasterContainer.js.map +1 -1
  7. package/dist/src/bootstrap/Initializer.d.ts +4 -6
  8. package/dist/src/bootstrap/Initializer.d.ts.map +1 -1
  9. package/dist/src/bootstrap/Initializer.js +10 -11
  10. package/dist/src/bootstrap/Initializer.js.map +1 -1
  11. package/dist/src/config/config.d.ts +43 -22
  12. package/dist/src/config/config.d.ts.map +1 -1
  13. package/dist/src/config/config.js +135 -241
  14. package/dist/src/config/config.js.map +1 -1
  15. package/dist/src/http/ShowMetricsMiddleware.js +1 -1
  16. package/dist/src/http/ShowMetricsMiddleware.js.map +1 -1
  17. package/dist/src/http/index.d.ts +0 -1
  18. package/dist/src/http/index.d.ts.map +1 -1
  19. package/dist/src/http/index.js +0 -1
  20. package/dist/src/http/index.js.map +1 -1
  21. package/dist/src/project/ProjectContainer.d.ts +1 -1
  22. package/dist/src/project/ProjectContainer.d.ts.map +1 -1
  23. package/dist/src/project/ProjectContainerResolver.d.ts +13 -10
  24. package/dist/src/project/ProjectContainerResolver.d.ts.map +1 -1
  25. package/dist/src/project/ProjectContainerResolver.js +48 -33
  26. package/dist/src/project/ProjectContainerResolver.js.map +1 -1
  27. package/dist/src/project/ProjectGroupState.d.ts +18 -0
  28. package/dist/src/project/ProjectGroupState.d.ts.map +1 -0
  29. package/dist/src/project/ProjectGroupState.js +30 -0
  30. package/dist/src/project/ProjectGroupState.js.map +1 -0
  31. package/dist/src/project/ProjectInitializer.d.ts +4 -10
  32. package/dist/src/project/ProjectInitializer.d.ts.map +1 -1
  33. package/dist/src/project/ProjectInitializer.js +5 -19
  34. package/dist/src/project/ProjectInitializer.js.map +1 -1
  35. package/dist/src/project/ProjectSchemaResolver.d.ts +5 -5
  36. package/dist/src/project/ProjectSchemaResolver.d.ts.map +1 -1
  37. package/dist/src/project/ProjectSchemaResolver.js +4 -4
  38. package/dist/src/project/ProjectSchemaResolver.js.map +1 -1
  39. package/dist/src/start.js +22 -14
  40. package/dist/src/start.js.map +1 -1
  41. package/dist/src/tsconfig.tsbuildinfo +1 -1
  42. package/dist/src/utils/cluster.js +1 -1
  43. package/dist/src/utils/cluster.js.map +1 -1
  44. package/dist/tests/cases/http.js +12 -11
  45. package/dist/tests/cases/http.js.map +1 -1
  46. package/dist/tests/tsconfig.tsbuildinfo +1 -1
  47. package/package.json +21 -21
  48. package/src/MasterContainer.ts +106 -55
  49. package/src/bootstrap/Initializer.ts +10 -17
  50. package/src/config/config.ts +159 -289
  51. package/src/http/index.ts +0 -1
  52. package/src/project/ProjectContainerResolver.ts +58 -35
  53. package/src/project/ProjectGroupState.ts +33 -0
  54. package/src/project/ProjectInitializer.ts +9 -23
  55. package/src/project/ProjectSchemaResolver.ts +12 -7
  56. package/src/start.ts +13 -6
  57. package/tests/cases/http.ts +7 -2
  58. package/dist/src/http/RootMiddleware.d.ts +0 -9
  59. package/dist/src/http/RootMiddleware.d.ts.map +0 -1
  60. package/dist/src/http/RootMiddleware.js +0 -33
  61. package/dist/src/http/RootMiddleware.js.map +0 -1
  62. package/src/http/RootMiddleware.ts +0 -53
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@contember/engine-server",
3
- "version": "0.12.0-beta.0",
3
+ "version": "1.0.0-alpha.1",
4
4
  "license": "Apache-2.0",
5
5
  "main": "dist/src/index.js",
6
6
  "typings": "dist/src/index.d.ts",
@@ -8,24 +8,24 @@
8
8
  "test": "uvu dist/tests/cases/ \\.js$"
9
9
  },
10
10
  "dependencies": {
11
- "@contember/authorization": "^0.12.0-beta.0",
12
- "@contember/config-loader": "^0.12.0-beta.0",
13
- "@contember/database": "^0.12.0-beta.0",
14
- "@contember/database-migrations": "^0.12.0-beta.0",
15
- "@contember/dic": "^0.12.0-beta.0",
16
- "@contember/engine-common": "^0.12.0-beta.0",
17
- "@contember/engine-content-api": "^0.12.0-beta.0",
18
- "@contember/engine-http": "^0.12.0-beta.0",
19
- "@contember/engine-plugins": "^0.12.0-beta.0",
20
- "@contember/engine-s3-plugin": "^0.12.0-beta.0",
21
- "@contember/engine-system-api": "^0.12.0-beta.0",
22
- "@contember/engine-tenant-api": "^0.12.0-beta.0",
23
- "@contember/engine-vimeo-plugin": "^0.12.0-beta.0",
24
- "@contember/queryable": "^0.12.0-beta.0",
25
- "@contember/schema": "^0.12.0-beta.0",
26
- "@contember/schema-definition": "^0.12.0-beta.0",
27
- "@contember/schema-migrations": "^0.12.0-beta.0",
28
- "@contember/schema-utils": "^0.12.0-beta.0",
11
+ "@contember/authorization": "^1.0.0-alpha.1",
12
+ "@contember/config-loader": "^1.0.0-alpha.1",
13
+ "@contember/database": "^1.0.0-alpha.1",
14
+ "@contember/database-migrations": "^1.0.0-alpha.1",
15
+ "@contember/dic": "^1.0.0-alpha.1",
16
+ "@contember/engine-common": "^1.0.0-alpha.1",
17
+ "@contember/engine-content-api": "^1.0.0-alpha.1",
18
+ "@contember/engine-http": "^1.0.0-alpha.1",
19
+ "@contember/engine-plugins": "^1.0.0-alpha.1",
20
+ "@contember/engine-s3-plugin": "^1.0.0-alpha.1",
21
+ "@contember/engine-system-api": "^1.0.0-alpha.1",
22
+ "@contember/engine-tenant-api": "^1.0.0-alpha.1",
23
+ "@contember/engine-vimeo-plugin": "^1.0.0-alpha.1",
24
+ "@contember/queryable": "^1.0.0-alpha.1",
25
+ "@contember/schema": "^1.0.0-alpha.1",
26
+ "@contember/schema-definition": "^1.0.0-alpha.1",
27
+ "@contember/schema-migrations": "^1.0.0-alpha.1",
28
+ "@contember/schema-utils": "^1.0.0-alpha.1",
29
29
  "@sentry/node": "^6.8.0",
30
30
  "graphql": "^15.4.0",
31
31
  "koa-bodyparser": "^4.3.0",
@@ -35,9 +35,9 @@
35
35
  "uuid": "^8.3.1"
36
36
  },
37
37
  "devDependencies": {
38
- "@contember/engine-api-tester": "^0.12.0-beta.0",
38
+ "@contember/engine-api-tester": "^1.0.0-alpha.1",
39
39
  "@types/koa-compress": "^4.0.1",
40
- "@types/node": "^15.12.5",
40
+ "@types/node": "^17.0.5",
41
41
  "@types/supertest": "^2.0.8",
42
42
  "supertest": "^6.0.1",
43
43
  "uvu": "^0.5.1"
@@ -1,14 +1,11 @@
1
1
  import {
2
- ContentApplyDependenciesFactoryImpl,
3
- ContentEventApplier,
4
2
  createMapperContainer,
5
3
  EntitiesSelector,
6
4
  EntitiesSelectorMapperFactory,
7
5
  PermissionsByIdentityFactory,
8
6
  } from '@contember/engine-content-api'
9
7
  import { SystemContainerFactory } from '@contember/engine-system-api'
10
- import { TenantContainerFactory } from '@contember/engine-tenant-api'
11
- import getTenantMigrations from '@contember/engine-tenant-api/migrations'
8
+ import { ProjectInitializer as ProjectInitializerInterface, TenantContainerFactory } from '@contember/engine-tenant-api'
12
9
  import getSystemMigrations from '@contember/engine-system-api/migrations'
13
10
  import { Builder } from '@contember/dic'
14
11
  import { Config } from './config/config'
@@ -17,11 +14,27 @@ import { ModificationHandlerFactory } from '@contember/schema-migrations'
17
14
  import { Initializer } from './bootstrap'
18
15
  import { Plugin } from '@contember/engine-plugins'
19
16
  import { DatabaseCredentials, MigrationsRunner } from '@contember/database-migrations'
20
- import { createRootMiddleware, createShowMetricsMiddleware } from './http'
17
+ import { createColllectHttpMetricsMiddleware, createShowMetricsMiddleware } from './http'
21
18
  import {
19
+ ApiMiddlewareFactory,
20
+ AuthMiddlewareFactory,
21
+ compose,
22
+ ContentServerMiddlewareFactory,
23
+ createHomepageMiddleware,
24
+ createPlaygroundMiddleware,
25
+ createPoweredByHeaderMiddleware,
22
26
  createProviders,
27
+ createTimerMiddleware,
28
+ ErrorFactory,
23
29
  Koa,
30
+ NotModifiedMiddlewareFactory,
24
31
  ProjectConfigResolver,
32
+ ProjectGroupMiddlewareFactory,
33
+ ProjectMemberMiddlewareFactory,
34
+ ProjectResolveMiddlewareFactory,
35
+ Providers,
36
+ route,
37
+ StageResolveMiddlewareFactory,
25
38
  SystemGraphQLMiddlewareFactory,
26
39
  TenantGraphQLMiddlewareFactory,
27
40
  } from '@contember/engine-http'
@@ -36,12 +49,16 @@ import {
36
49
  } from './project'
37
50
  import { ClientBase } from 'pg'
38
51
  import { createSecretKey } from 'crypto'
52
+ import koaCompress from 'koa-compress'
53
+ import bodyParser from 'koa-bodyparser'
39
54
 
40
55
  export interface MasterContainer {
41
56
  initializer: Initializer
42
57
  koa: Koa
43
58
  monitoringKoa: Koa
44
59
  projectContainerResolver: ProjectContainerResolver
60
+ projectInitializer: ProjectInitializerInterface
61
+ providers: Providers
45
62
  }
46
63
 
47
64
  export interface MasterContainerArgs {
@@ -76,11 +93,11 @@ export class MasterContainerFactory {
76
93
  .addService('plugins', () =>
77
94
  plugins)
78
95
  .addService('tenantContainerFactory', ({ config }) =>
79
- new TenantContainerFactory(config.tenant.db, config.tenant.mailer))
96
+ new TenantContainerFactory(config.tenant.db, config.tenant.mailer, config.tenant.credentials))
80
97
  .addService('systemContainerFactory', () =>
81
98
  new SystemContainerFactory())
82
99
  .addService('providers', ({ config }) => {
83
- const encryptionKey = config.tenant.secrets
100
+ const encryptionKey = config.tenant.secrets.encryptionKey
84
101
  ? createSecretKey(Buffer.from(config.tenant.secrets.encryptionKey, 'hex'))
85
102
  : undefined
86
103
  return createProviders({ encryptionKey })
@@ -109,21 +126,16 @@ export class MasterContainerFactory {
109
126
  }).mapperFactory(db)
110
127
  return new EntitiesSelector(mapperFactory, permissionsByIdentityFactory)
111
128
  })
112
- .addService('identityFetcher', ({ tenantContainer }) =>
113
- tenantContainer.identityFetcher)
114
- .addService('eventApplier', () =>
115
- new ContentEventApplier(new ContentApplyDependenciesFactoryImpl()))
116
129
  .addService('systemDbMigrationsRunnerFactory', () =>
117
130
  (db: DatabaseCredentials, dbClient: ClientBase) =>
118
131
  new MigrationsRunner(db, 'system', getSystemMigrations, dbClient))
119
- .addService('systemContainer', ({ systemContainerFactory, entitiesSelector, eventApplier, identityFetcher, modificationHandlerFactory, providers, systemDbMigrationsRunnerFactory }) =>
132
+ .addService('systemContainer', ({ systemContainerFactory, entitiesSelector, modificationHandlerFactory, providers, systemDbMigrationsRunnerFactory, tenantContainer }) =>
120
133
  systemContainerFactory.create({
121
134
  entitiesSelector,
122
- eventApplier,
123
- identityFetcher,
124
135
  modificationHandlerFactory,
125
136
  providers,
126
137
  systemDbMigrationsRunnerFactory,
138
+ identityFetcher: tenantContainer.identityFetcher,
127
139
  }))
128
140
  .addService('schemaVersionBuilder', ({ systemContainer }) =>
129
141
  systemContainer.schemaVersionBuilder)
@@ -131,8 +143,8 @@ export class MasterContainerFactory {
131
143
  new ProjectContainerFactory(debugMode, plugins, schemaVersionBuilder, providers))
132
144
  .addService('tenantProjectManager', ({ tenantContainer }) =>
133
145
  tenantContainer.projectManager)
134
- .addService('projectContainerResolver', ({ tenantProjectManager, projectContainerFactory, projectConfigResolver }) =>
135
- new ProjectContainerResolver(projectContainerFactory, projectConfigResolver, tenantProjectManager))
146
+ .addService('projectContainerResolver', ({ tenantProjectManager, projectContainerFactory, projectConfigResolver, systemContainer }) =>
147
+ new ProjectContainerResolver(projectContainerFactory, projectConfigResolver, tenantProjectManager, systemContainer.projectInitializer))
136
148
  .addService('tenantGraphQlMiddlewareFactory', ({ tenantContainer }) =>
137
149
  new TenantGraphQLMiddlewareFactory(tenantContainer.resolvers, tenantContainer.resolverContextFactory, logSentryError))
138
150
  .addService('systemGraphQLMiddlewareFactory', ({ systemContainer, debugMode }) =>
@@ -156,35 +168,82 @@ export class MasterContainerFactory {
156
168
  )
157
169
  return register
158
170
  })
171
+ .addService('httpErrorFactory', ({ debugMode }) =>
172
+ new ErrorFactory(debugMode))
173
+ .addService('authMiddlewareFactory', ({ tenantContainer, httpErrorFactory }) =>
174
+ new AuthMiddlewareFactory(tenantContainer.apiKeyManager, httpErrorFactory))
175
+ .addService('projectGroupMiddlewareFactory', ({ tenantContainer, httpErrorFactory }) =>
176
+ new ProjectGroupMiddlewareFactory(config.server.projectGroup?.domainMapping, tenantContainer.projectGroupProvider, httpErrorFactory))
177
+ .addService('projectResolverMiddlewareFactory', ({ projectContainerResolver, httpErrorFactory }) =>
178
+ new ProjectResolveMiddlewareFactory(projectContainerResolver, httpErrorFactory))
179
+ .addService('apiMiddlewareFactory', ({ projectGroupMiddlewareFactory, authMiddlewareFactory }) =>
180
+ new ApiMiddlewareFactory(projectGroupMiddlewareFactory, authMiddlewareFactory))
181
+ .addService('stageResolveMiddlewareFactory', ({ httpErrorFactory }) =>
182
+ new StageResolveMiddlewareFactory(httpErrorFactory))
183
+ .addService('notModifiedMiddlewareFactory', () =>
184
+ new NotModifiedMiddlewareFactory())
185
+ .addService('projectMemberMiddlewareFactory', ({ debugMode, tenantContainer, httpErrorFactory }) =>
186
+ new ProjectMemberMiddlewareFactory(debugMode, tenantContainer.projectMemberManager, httpErrorFactory))
187
+ .addService('contentServerMiddlewareFactory', () =>
188
+ new ContentServerMiddlewareFactory())
159
189
  .addService(
160
190
  'koa',
161
191
  ({
162
- tenantGraphQlMiddlewareFactory,
163
- projectContainerResolver,
164
- tenantContainer,
165
- providers,
166
- systemGraphQLMiddlewareFactory,
167
- promRegistry,
168
- debugMode,
169
- version,
170
- config,
171
- }) => {
192
+ tenantGraphQlMiddlewareFactory,
193
+ systemGraphQLMiddlewareFactory,
194
+ apiMiddlewareFactory,
195
+ projectResolverMiddlewareFactory,
196
+ stageResolveMiddlewareFactory,
197
+ notModifiedMiddlewareFactory,
198
+ projectMemberMiddlewareFactory,
199
+ contentServerMiddlewareFactory,
200
+ promRegistry,
201
+ debugMode,
202
+ version,
203
+ config,
204
+ }) => {
172
205
  const app = new Koa()
173
206
  app.use(
174
- createRootMiddleware(
175
- debugMode,
176
- version ?? 'unknown',
177
- {
178
- tenantGraphQlMiddlewareFactory,
179
- projectContainerResolver: projectContainerResolver.getProjectContainer.bind(projectContainerResolver),
180
- apiKeyManager: tenantContainer.apiKeyManager,
181
- projectMemberManager: tenantContainer.projectMemberManager,
182
- providers,
183
- systemGraphQLMiddlewareFactory,
184
- },
185
- promRegistry,
186
- config.server.http,
187
- ),
207
+ compose([
208
+ koaCompress({
209
+ br: false,
210
+ }),
211
+ bodyParser({
212
+ jsonLimit: config.server.http.requestBodySize || '1mb',
213
+ }),
214
+ createPoweredByHeaderMiddleware(debugMode, version ?? 'unknown'),
215
+ createColllectHttpMetricsMiddleware(promRegistry),
216
+ createTimerMiddleware(),
217
+ route('/playground$', createPlaygroundMiddleware()),
218
+ createHomepageMiddleware(),
219
+ route(
220
+ '/content/:projectSlug/:stageSlug$',
221
+ compose([
222
+ apiMiddlewareFactory.create('content'),
223
+ projectResolverMiddlewareFactory.create(),
224
+ stageResolveMiddlewareFactory.create(),
225
+ notModifiedMiddlewareFactory.create(),
226
+ projectMemberMiddlewareFactory.create(),
227
+ contentServerMiddlewareFactory.create(),
228
+ ]),
229
+ ),
230
+ route(
231
+ '/tenant$',
232
+ compose([
233
+ apiMiddlewareFactory.create('tenant'),
234
+ tenantGraphQlMiddlewareFactory.create(),
235
+ ]),
236
+ ),
237
+ route(
238
+ '/system/:projectSlug$',
239
+ compose([
240
+ apiMiddlewareFactory.create('system'),
241
+ projectResolverMiddlewareFactory.create(),
242
+ projectMemberMiddlewareFactory.create(),
243
+ systemGraphQLMiddlewareFactory.create(),
244
+ ]),
245
+ ),
246
+ ]),
188
247
  )
189
248
 
190
249
  return app
@@ -196,33 +255,25 @@ export class MasterContainerFactory {
196
255
 
197
256
  return app
198
257
  })
199
- .addService('tenantMigrationsRunner', ({ config }) =>
200
- new MigrationsRunner(config.tenant.db, 'tenant', getTenantMigrations))
201
258
  .addService(
202
259
  'initializer',
203
- ({ tenantMigrationsRunner, tenantContainer, systemContainer, projectContainerResolver, config, providers }) =>
260
+ ({ tenantContainer, systemContainer, projectContainerResolver }) =>
204
261
  new Initializer(
205
- tenantMigrationsRunner,
262
+ tenantContainer.migrationsRunnerFactory,
206
263
  tenantContainer.projectManager,
207
264
  systemContainer.projectInitializer,
208
265
  projectContainerResolver,
209
- config.tenant.credentials,
210
- providers,
266
+ tenantContainer.projectGroupProvider,
211
267
  ),
212
268
  )
213
269
  .setupService('projectSchemaResolver', (it, { projectContainerResolver, schemaVersionBuilder }) => {
214
- it.setResolver(
215
- new ProjectSchemaResolver(
216
- projectContainerResolver.getProjectContainer.bind(projectContainerResolver),
217
- schemaVersionBuilder,
218
- ),
219
- )
270
+ it.setResolver(new ProjectSchemaResolver(projectContainerResolver, schemaVersionBuilder))
220
271
  })
221
- .setupService('projectInitializer', (it, { projectContainerResolver, systemContainer }) => {
222
- it.setInitializer(new ProjectInitializer(projectContainerResolver, systemContainer.projectInitializer))
272
+ .setupService('projectInitializer', (it, { projectContainerResolver }) => {
273
+ it.setInitializer(new ProjectInitializer(projectContainerResolver))
223
274
  })
224
275
  .build()
225
276
 
226
- return masterContainer.pick('initializer', 'koa', 'monitoringKoa', 'projectContainerResolver')
277
+ return masterContainer.pick('initializer', 'koa', 'monitoringKoa', 'projectContainerResolver', 'projectInitializer', 'providers')
227
278
  }
228
279
  }
@@ -1,10 +1,4 @@
1
- import {
2
- ProjectManager,
3
- Providers as TenantProviders,
4
- TenantCredentials,
5
- TenantMigrationArgs,
6
- } from '@contember/engine-tenant-api'
7
- import { MigrationsRunner } from '@contember/database-migrations'
1
+ import { MigrationsRunnerFactory, ProjectGroupProvider, ProjectManager } from '@contember/engine-tenant-api'
8
2
  import { ProjectInitializer } from '@contember/engine-system-api'
9
3
  import { Logger } from '@contember/engine-common'
10
4
  import { ProjectContainerResolver } from '../project'
@@ -13,26 +7,24 @@ import { Migration } from '@contember/schema-migrations'
13
7
 
14
8
  export class Initializer {
15
9
  constructor(
16
- private readonly tenantDbMigrationsRunner: MigrationsRunner,
10
+ private readonly tenantDbMigrationsRunnerFactory: MigrationsRunnerFactory,
17
11
  private readonly projectManager: ProjectManager,
18
12
  private readonly projectInitializer: ProjectInitializer,
19
13
  private readonly projectContainerResolver: ProjectContainerResolver,
20
- private readonly tenantCredentials: TenantCredentials,
21
- private readonly providers: TenantProviders,
14
+ private readonly projectGroupProvider: ProjectGroupProvider,
22
15
  ) {}
23
16
 
24
17
  public async initialize(): Promise<string[]> {
25
18
  // eslint-disable-next-line no-console
26
19
  const logger = new Logger(console.log)
27
20
  logger.group('\nInitializing tenant database')
28
- await this.tenantDbMigrationsRunner.migrate<TenantMigrationArgs>(logger.write.bind(logger), {
29
- credentials: this.tenantCredentials,
30
- providers: this.providers,
31
- })
21
+ // todo
22
+ await this.tenantDbMigrationsRunnerFactory.create('tenant').run(logger.write.bind(logger))
32
23
  logger.groupEnd()
33
24
 
34
25
  const projects: string[] = []
35
- for (const container of await this.projectContainerResolver.getAllProjectContainers()) {
26
+ const group = await this.projectGroupProvider.getGroup(undefined)
27
+ for (const container of await this.projectContainerResolver.getAllProjectContainers(group)) {
36
28
  const project = container.project
37
29
  projects.push(project.slug)
38
30
  logger.group(`\nUpdating project ${project.slug}`)
@@ -46,11 +38,12 @@ export class Initializer {
46
38
 
47
39
  public async createProject(project: ProjectConfig, migrations: Migration[]): Promise<void> {
48
40
  const { slug, name, ...config } = project
49
- const result = await this.projectManager.createProject({ slug, name, config, secrets: {} }, undefined)
41
+ const group = await this.projectGroupProvider.getGroup(undefined)
42
+ const result = await this.projectManager.createProject(group, { slug, name, config, secrets: {} }, undefined)
50
43
  if (!result) {
51
44
  throw new Error('Project already exists')
52
45
  }
53
- const container = await this.projectContainerResolver.getProjectContainer(project.slug)
46
+ const container = await this.projectContainerResolver.getProjectContainer(group, project.slug)
54
47
  if (!container) {
55
48
  throw new Error('Should not happen')
56
49
  }