@platformatic/runtime 3.67.0 → 4.0.0-new-config.0

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.
package/lib/errors.js CHANGED
@@ -13,7 +13,11 @@ export const ERROR_PREFIX = 'PLT_RUNTIME'
13
13
 
14
14
  export const AddressInUseError = createError(
15
15
  `${ERROR_PREFIX}_EADDR_IN_USE`,
16
- 'The current port is in use by another application'
16
+ 'Port %d is already in use by applications "%s" and "%s"'
17
+ )
18
+ export const WorkerAddressInUseError = createError(
19
+ `${ERROR_PREFIX}_WORKER_EADDR_IN_USE`,
20
+ 'Port %d is already in use by another worker of the application "%s". Multiple workers can share a port only when the reusePort feature is available in your OS, otherwise set "server.portAssignment" to "perWorkerIncrement" in the application configuration or use a single worker.'
17
21
  )
18
22
  export const RuntimeExitedError = createError(
19
23
  `${ERROR_PREFIX}_RUNTIME_EXIT`,
@@ -98,14 +102,6 @@ export const NoConfigFileFoundError = createError(
98
102
  `${ERROR_PREFIX}_NO_CONFIG_FILE_FOUND`,
99
103
  "No config file found for application '%s'"
100
104
  )
101
- export const InvalidEntrypointError = createError(
102
- `${ERROR_PREFIX}_INVALID_ENTRYPOINT`,
103
- "Invalid entrypoint: '%s' does not exist"
104
- )
105
- export const MissingEntrypointError = createError(
106
- `${ERROR_PREFIX}_MISSING_ENTRYPOINT`,
107
- 'Missing application entrypoint.'
108
- )
109
105
  export const MissingDependencyError = createError(`${ERROR_PREFIX}_MISSING_DEPENDENCY`, 'Missing dependency: "%s"')
110
106
  export const InspectAndInspectBrkError = createError(
111
107
  `${ERROR_PREFIX}_INSPECT_AND_INSPECT_BRK`,
@@ -228,10 +224,6 @@ export const HealthSignalTypeMustBeStringError = createError(
228
224
  `${ERROR_PREFIX}_HEALTH_SIGNAL_TYPE_MUST_BE_STRING`,
229
225
  'Health signal type must be a string, received "%s"'
230
226
  )
231
- export const CannotRemoveEntrypointError = createError(
232
- `${ERROR_PREFIX}_CANNOT_REMOVE_ENTRYPOINT`,
233
- 'Cannot remove the entrypoint application.'
234
- )
235
227
  export const WorkerInterceptorNotReadyError = createError(
236
228
  `${ERROR_PREFIX}_WORKER_INTERCEPTOR_NOT_READY`,
237
229
  'The "%s" application worker interceptor is not ready'
package/lib/generator.js CHANGED
@@ -1,4 +1,3 @@
1
- import createError from '@fastify/error'
2
1
  import {
3
2
  createEnvFileTool,
4
3
  defaultPackageManager,
@@ -23,44 +22,20 @@ const engines = {
23
22
  node: '>=22.19.0'
24
23
  }
25
24
 
26
- export const ERROR_PREFIX = 'PLT_RUNTIME_GEN'
27
-
28
- const NoApplicationNamedError = createError(
29
- `${ERROR_PREFIX}_NO_APPLICATION_FOUND`,
30
- "No application named '%s' has been added to this runtime."
31
- )
32
- const NoEntryPointError = createError(`${ERROR_PREFIX}_NO_ENTRYPOINT`, 'No entrypoint had been defined.')
33
-
34
- function getRuntimeWrappableProperties (skipServer) {
35
- const wrappableProperties = {
25
+ function getRuntimeWrappableProperties () {
26
+ return {
36
27
  logger: {
37
28
  level: '{PLT_SERVER_LOGGER_LEVEL}'
38
29
  },
39
30
  managementApi: '{PLT_MANAGEMENT_API}'
40
31
  }
41
-
42
- if (!skipServer) {
43
- wrappableProperties.server = {
44
- hostname: '{PLT_SERVER_HOSTNAME}',
45
- port: '{PORT}'
46
- }
47
- }
48
-
49
- return wrappableProperties
50
32
  }
51
33
 
52
34
  function getRuntimeBaseEnvVars (config) {
53
- const env = {}
54
-
55
- if (!config.skipServer) {
56
- env.PLT_SERVER_HOSTNAME = '127.0.0.1'
57
- env.PORT = config.port || 3042
35
+ return {
36
+ PLT_SERVER_LOGGER_LEVEL: config.logLevel || 'info',
37
+ PLT_MANAGEMENT_API: true
58
38
  }
59
-
60
- env.PLT_SERVER_LOGGER_LEVEL = config.logLevel || 'info'
61
- env.PLT_MANAGEMENT_API = true
62
-
63
- return env
64
39
  }
65
40
 
66
41
  export class RuntimeGenerator extends BaseGenerator {
@@ -73,7 +48,6 @@ export class RuntimeGenerator extends BaseGenerator {
73
48
  this.applicationsFolder = opts.applicationsFolder ?? 'applications'
74
49
  this.applications = []
75
50
  this.existingApplications = []
76
- this.entryPoint = null
77
51
  this.packageManager = opts.packageManager ?? defaultPackageManager
78
52
  }
79
53
 
@@ -97,15 +71,6 @@ export class RuntimeGenerator extends BaseGenerator {
97
71
  application.setRuntime(this)
98
72
  }
99
73
 
100
- setEntryPoint (entryPoint) {
101
- const application =
102
- this.existingApplications.includes(entryPoint) || this.applications.find(svc => svc.name === entryPoint)
103
- if (!application) {
104
- throw new NoApplicationNamedError(entryPoint)
105
- }
106
- this.entryPoint = application
107
- }
108
-
109
74
  async generatePackageJson () {
110
75
  const template = {
111
76
  name: `${this.runtimeName}`,
@@ -165,8 +130,6 @@ export class RuntimeGenerator extends BaseGenerator {
165
130
 
166
131
  const { PLT_ROOT, ...existingEnvironment } = this.existingConfig[kMetadata].env
167
132
  this.config.env = existingEnvironment
168
- this.config.port = this.config.env.PORT
169
- this.entryPoint = this.existingConfig.applications.find(svc => svc.entrypoint)
170
133
  this.existingApplications = this.existingConfig.applications.map(s => s.id)
171
134
 
172
135
  this.updateRuntimeConfig(this.existingConfigRaw)
@@ -190,37 +153,42 @@ export class RuntimeGenerator extends BaseGenerator {
190
153
  }
191
154
 
192
155
  setApplicationsConfigValues () {
193
- this.applications.forEach(({ application }) => {
156
+ let newApplicationOrdinal = 0
157
+ this.applications.forEach(({ name, application }) => {
194
158
  if (!application.config) {
195
159
  // set default config
196
160
  application.setConfig()
197
161
  }
162
+ const existingOrdinal = this.existingApplications.indexOf(name)
163
+ const ordinal = existingOrdinal === -1 ? this.existingApplications.length + newApplicationOrdinal++ : existingOrdinal
164
+ this.setApplicationPort(application, ordinal)
198
165
  })
199
166
  }
200
167
 
168
+ setApplicationPort (application, ordinal) {
169
+ if (application.config.port === 3042) {
170
+ application.setConfig({ port: 3042 + ordinal })
171
+ }
172
+ }
173
+
201
174
  async _getConfigFileContents () {
202
175
  const config = {
203
176
  $schema: `https://schemas.platformatic.dev/wattpm/${this.platformaticVersion}.json`,
204
- entrypoint: this.entryPoint.name,
205
177
  watch: true,
206
178
  autoload: {
207
179
  path: this.config.autoload || this.applicationsFolder,
208
180
  exclude: ['docs']
209
181
  },
210
- ...getRuntimeWrappableProperties(this.config.skipServer)
182
+ ...getRuntimeWrappableProperties()
211
183
  }
212
184
 
213
185
  return config
214
186
  }
215
187
 
216
188
  async _afterPrepare () {
217
- if (!this.entryPoint) {
218
- throw new NoEntryPointError()
219
- }
220
189
  const applicationsEnv = await this.prepareApplicationFiles()
221
190
  this.addEnvVars({
222
191
  ...this.config.env,
223
- ...this.getRuntimeEnv(),
224
192
  ...applicationsEnv
225
193
  })
226
194
 
@@ -258,21 +226,6 @@ export class RuntimeGenerator extends BaseGenerator {
258
226
 
259
227
  async prepareQuestions () {
260
228
  await this.populateFromExistingConfig()
261
-
262
- if (this.existingConfig) {
263
- return
264
- }
265
-
266
- if (!this.config.skipServer) {
267
- // port
268
- this.questions.push({
269
- type: 'input',
270
- name: 'port',
271
- default: '3042',
272
- message: 'What port do you want to use?',
273
- filter: Number
274
- })
275
- }
276
229
  }
277
230
 
278
231
  setApplicationsDirectory () {
@@ -322,12 +275,6 @@ export class RuntimeGenerator extends BaseGenerator {
322
275
  // do nothing, makes no sense
323
276
  }
324
277
 
325
- getRuntimeEnv () {
326
- return {
327
- PORT: this.config.port
328
- }
329
- }
330
-
331
278
  async postInstallActions () {
332
279
  for (const { application } of this.applications) {
333
280
  await application.postInstallActions()
@@ -451,6 +398,7 @@ export class RuntimeGenerator extends BaseGenerator {
451
398
  })
452
399
  }
453
400
  applicationInstance.setConfig(baseConfig)
401
+ this.setApplicationPort(applicationInstance, allNewApplicationsNames.indexOf(newApplication.name))
454
402
  applicationInstance.setConfigFields(newApplication.fields)
455
403
 
456
404
  const applicationEnvPrefix = `PLT_${applicationInstance.config.envPrefix}`
@@ -494,18 +442,6 @@ export class RuntimeGenerator extends BaseGenerator {
494
442
  contents: JSON.stringify(currrentPackageJson, null, 2)
495
443
  })
496
444
 
497
- // set new entrypoint if specified
498
- const newEntrypoint = newConfig.entrypoint
499
- if (newEntrypoint) {
500
- // load platformatic.json runtime config
501
- const runtimePkgConfigFileData = JSON.parse(
502
- await readFile(join(this.targetDirectory, this.runtimeConfig), 'utf-8')
503
- )
504
-
505
- this.setEntryPoint(newEntrypoint)
506
- runtimePkgConfigFileData.entrypoint = newEntrypoint
507
- this.updateRuntimeConfig(runtimePkgConfigFileData)
508
- }
509
445
  await this.writeFiles()
510
446
  // save new env
511
447
  await envTool.save()
@@ -548,15 +484,6 @@ export class RuntimeGenerator extends BaseGenerator {
548
484
  tags: ['runtime-env']
549
485
  })
550
486
  }
551
-
552
- updateConfigEntryPoint (entrypoint) {
553
- // This can return null if the generator was not supposed to modify the config
554
- const configObject = this.getRuntimeConfigFileObject()
555
- const config = JSON.parse(configObject.contents)
556
- config.entrypoint = entrypoint
557
-
558
- this.updateRuntimeConfig(config)
559
- }
560
487
  }
561
488
 
562
489
  export class WrappedGenerator extends BaseGenerator {
@@ -626,7 +553,7 @@ export class WrappedGenerator extends BaseGenerator {
626
553
  async #createConfigFile () {
627
554
  const config = {
628
555
  $schema: `https://schemas.platformatic.dev/${this.module}/${this.platformaticVersion}.json`,
629
- runtime: getRuntimeWrappableProperties(this.config.skipServer)
556
+ runtime: getRuntimeWrappableProperties()
630
557
  }
631
558
 
632
559
  this.addFile({
@@ -14,7 +14,7 @@ import { platform, tmpdir } from 'node:os'
14
14
  import { dirname, join } from 'node:path'
15
15
  import { setTimeout as sleep } from 'node:timers/promises'
16
16
  import { createWebSocketStream } from 'ws'
17
- import { prepareApplication } from './config.js'
17
+ import { prepareAddedApplications } from './config.js'
18
18
 
19
19
  const PLATFORMATIC_TMP_DIR = join(tmpdir(), 'platformatic', 'runtimes')
20
20
 
@@ -169,11 +169,9 @@ export async function managementApiPlugin (app, opts) {
169
169
  }
170
170
  }
171
171
 
172
- for (let i = 0; i < applications.length; i++) {
173
- applications[i] = await prepareApplication(config, applications[i], config.workers)
174
- }
172
+ const prepared = await prepareAddedApplications(config, applications, runtime.getApplicationsIds())
175
173
 
176
- const created = await runtime.addApplications(applications, request.query.start !== 'false')
174
+ const created = await runtime.addApplications(prepared, request.query.start !== 'false')
177
175
  reply.code(201)
178
176
  return created
179
177
  })
@@ -3,7 +3,7 @@ import {
3
3
  kMetadata,
4
4
  validate
5
5
  } from '@platformatic/foundation'
6
- import { prepareApplication } from './config.js'
6
+ import { prepareAddedApplications } from './config.js'
7
7
 
8
8
  const allOperations = [
9
9
  'getRuntimeStatus',
@@ -138,11 +138,9 @@ export function createManagementHandlers (runtime, allowedOperations) {
138
138
 
139
139
  validate(applicationSchema, applications, {}, true, config[kMetadata].root)
140
140
 
141
- for (let i = 0; i < applications.length; i++) {
142
- applications[i] = await prepareApplication(config, applications[i], config.workers)
143
- }
141
+ const prepared = await prepareAddedApplications(config, applications, runtime.getApplicationsIds())
144
142
 
145
- return runtime.addApplications(applications, start)
143
+ return runtime.addApplications(prepared, start)
146
144
  })
147
145
 
148
146
  register('removeApplications', async ({ ids }) => {