@platformatic/service 0.18.0 → 0.19.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 (29) hide show
  1. package/fixtures/hello/platformatic.service.json +3 -0
  2. package/fixtures/hello-client/hello/hello.cjs +21 -0
  3. package/fixtures/hello-client/hello/hello.d.ts +34 -0
  4. package/fixtures/hello-client/hello/hello.openapi.json +22 -0
  5. package/fixtures/hello-client/hello/package.json +5 -0
  6. package/fixtures/hello-client/platformatic.service.json +17 -0
  7. package/fixtures/hello-client/plugin.js +8 -0
  8. package/fixtures/hello-client-ts/dist/plugin.js +21 -0
  9. package/fixtures/hello-client-ts/dist/plugin.js.map +1 -0
  10. package/fixtures/hello-client-ts/hello/hello.cjs +21 -0
  11. package/fixtures/hello-client-ts/hello/hello.d.ts +34 -0
  12. package/fixtures/hello-client-ts/hello/hello.openapi.json +22 -0
  13. package/fixtures/hello-client-ts/hello/package.json +5 -0
  14. package/fixtures/hello-client-ts/platformatic.service.json +18 -0
  15. package/fixtures/hello-client-ts/plugin.ts +8 -0
  16. package/fixtures/hello-client-ts/tsconfig.json +22 -0
  17. package/index.d.ts +18 -0
  18. package/index.js +36 -1
  19. package/index.test-d.ts +27 -0
  20. package/lib/config.js +0 -22
  21. package/lib/schema.js +106 -3
  22. package/package.json +11 -5
  23. package/service.mjs +0 -0
  24. package/test/clients.test.js +59 -0
  25. package/test/fixtures/bad-typescript-plugin/dist/tsconfig.tsbuildinfo +1 -1
  26. package/test/https.test.js +58 -0
  27. package/test/tmp/typescript-plugin-clone-3/dist/tsconfig.tsbuildinfo +1 -1
  28. package/test/tmp/typescript-plugin-clone-4/dist/tsconfig.tsbuildinfo +1 -1
  29. package/test/tmp/typescript-plugin-clone-8/dist/tsconfig.tsbuildinfo +1 -1
@@ -9,5 +9,8 @@
9
9
  "plugins": {
10
10
  "paths": ["./plugin.js"]
11
11
  },
12
+ "service": {
13
+ "openapi": true
14
+ },
12
15
  "metrics": false
13
16
  }
@@ -0,0 +1,21 @@
1
+ 'use strict'
2
+
3
+ const pltClient = require('@platformatic/client')
4
+ const { join } = require('path')
5
+
6
+ async function generateHelloClientPlugin (app, opts) {
7
+ app.register(pltClient, {
8
+ type: 'openapi',
9
+ name: 'hello',
10
+ path: join(__dirname, 'hello.openapi.json'),
11
+ url: opts.url
12
+ })
13
+ }
14
+
15
+ generateHelloClientPlugin[Symbol.for('plugin-meta')] = {
16
+ name: 'hello OpenAPI Client'
17
+ }
18
+ generateHelloClientPlugin[Symbol.for('skip-override')] = true
19
+
20
+ module.exports = generateHelloClientPlugin
21
+ module.exports.default = generateHelloClientPlugin
@@ -0,0 +1,34 @@
1
+ import { FastifyPluginAsync } from 'fastify'
2
+
3
+ interface GetRequest {
4
+ }
5
+
6
+ interface GetResponse {
7
+ }
8
+
9
+ interface Hello {
10
+ get(req: GetRequest): Promise<GetResponse>;
11
+ }
12
+
13
+ type HelloPlugin = FastifyPluginAsync<NonNullable<hello.HelloOptions>>
14
+
15
+ declare module 'fastify' {
16
+ interface FastifyInstance {
17
+ 'hello': Hello;
18
+ }
19
+
20
+ interface FastifyRequest {
21
+ 'hello': Hello;
22
+ }
23
+ }
24
+
25
+ declare namespace hello {
26
+ export interface HelloOptions {
27
+ url: string
28
+ }
29
+ export const hello: HelloPlugin;
30
+ export { hello as default };
31
+ }
32
+
33
+ declare function hello(...params: Parameters<HelloPlugin>): ReturnType<HelloPlugin>;
34
+ export = hello;
@@ -0,0 +1,22 @@
1
+ {
2
+ "openapi": "3.0.3",
3
+ "info": {
4
+ "title": "Platformatic",
5
+ "description": "This is a service built on top of Platformatic",
6
+ "version": "1.0.0"
7
+ },
8
+ "components": {
9
+ "schemas": {}
10
+ },
11
+ "paths": {
12
+ "/": {
13
+ "get": {
14
+ "responses": {
15
+ "200": {
16
+ "description": "Default Response"
17
+ }
18
+ }
19
+ }
20
+ }
21
+ }
22
+ }
@@ -0,0 +1,5 @@
1
+ {
2
+ "name": "hello",
3
+ "main": "./hello.cjs",
4
+ "types": "./hello.d.ts"
5
+ }
@@ -0,0 +1,17 @@
1
+ {
2
+ "server": {
3
+ "hostname": "127.0.0.1",
4
+ "port": 0,
5
+ "logger": {
6
+ "level": "info"
7
+ }
8
+ },
9
+ "plugins": {
10
+ "paths": ["./plugin.js"]
11
+ },
12
+ "clients": [{
13
+ "path": "./hello",
14
+ "url": "{PLT_CLIENT_URL}"
15
+ }],
16
+ "metrics": false
17
+ }
@@ -0,0 +1,8 @@
1
+ 'use default'
2
+
3
+ /** @type {import('fastify').FastifyPluginAsync<{ optionA: boolean, optionB: string }>} */
4
+ module.exports = async function (app) {
5
+ app.get('/', async () => {
6
+ return app.hello.get()
7
+ })
8
+ }
@@ -0,0 +1,21 @@
1
+ "use strict";
2
+ var __awaiter = (this && this.__awaiter) || function (thisArg, _arguments, P, generator) {
3
+ function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
4
+ return new (P || (P = Promise))(function (resolve, reject) {
5
+ function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
6
+ function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
7
+ function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
8
+ step((generator = generator.apply(thisArg, _arguments || [])).next());
9
+ });
10
+ };
11
+ Object.defineProperty(exports, "__esModule", { value: true });
12
+ /// <reference path="./hello" />
13
+ function default_1(app) {
14
+ return __awaiter(this, void 0, void 0, function* () {
15
+ app.get('/', () => __awaiter(this, void 0, void 0, function* () {
16
+ return app.hello.get({});
17
+ }));
18
+ });
19
+ }
20
+ exports.default = default_1;
21
+ //# sourceMappingURL=plugin.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"plugin.js","sourceRoot":"","sources":["../plugin.ts"],"names":[],"mappings":";;;;;;;;;;;AACA,gCAAgC;AAEhC,mBAA+B,GAAoB;;QACjD,GAAG,CAAC,GAAG,CAAC,GAAG,EAAE,GAAS,EAAE;YACtB,OAAO,GAAG,CAAC,KAAK,CAAC,GAAG,CAAC,EAAE,CAAC,CAAA;QAC1B,CAAC,CAAA,CAAC,CAAA;IACJ,CAAC;CAAA;AAJD,4BAIC"}
@@ -0,0 +1,21 @@
1
+ 'use strict'
2
+
3
+ const pltClient = require('@platformatic/client')
4
+ const { join } = require('path')
5
+
6
+ async function generateHelloClientPlugin (app, opts) {
7
+ app.register(pltClient, {
8
+ type: 'openapi',
9
+ name: 'hello',
10
+ path: join(__dirname, 'hello.openapi.json'),
11
+ url: opts.url
12
+ })
13
+ }
14
+
15
+ generateHelloClientPlugin[Symbol.for('plugin-meta')] = {
16
+ name: 'hello OpenAPI Client'
17
+ }
18
+ generateHelloClientPlugin[Symbol.for('skip-override')] = true
19
+
20
+ module.exports = generateHelloClientPlugin
21
+ module.exports.default = generateHelloClientPlugin
@@ -0,0 +1,34 @@
1
+ import { FastifyPluginAsync } from 'fastify'
2
+
3
+ interface GetRequest {
4
+ }
5
+
6
+ interface GetResponse {
7
+ }
8
+
9
+ interface Hello {
10
+ get(req: GetRequest): Promise<GetResponse>;
11
+ }
12
+
13
+ type HelloPlugin = FastifyPluginAsync<NonNullable<hello.HelloOptions>>
14
+
15
+ declare module 'fastify' {
16
+ interface FastifyInstance {
17
+ 'hello': Hello;
18
+ }
19
+
20
+ interface FastifyRequest {
21
+ 'hello': Hello;
22
+ }
23
+ }
24
+
25
+ declare namespace hello {
26
+ export interface HelloOptions {
27
+ url: string
28
+ }
29
+ export const hello: HelloPlugin;
30
+ export { hello as default };
31
+ }
32
+
33
+ declare function hello(...params: Parameters<HelloPlugin>): ReturnType<HelloPlugin>;
34
+ export = hello;
@@ -0,0 +1,22 @@
1
+ {
2
+ "openapi": "3.0.3",
3
+ "info": {
4
+ "title": "Platformatic",
5
+ "description": "This is a service built on top of Platformatic",
6
+ "version": "1.0.0"
7
+ },
8
+ "components": {
9
+ "schemas": {}
10
+ },
11
+ "paths": {
12
+ "/": {
13
+ "get": {
14
+ "responses": {
15
+ "200": {
16
+ "description": "Default Response"
17
+ }
18
+ }
19
+ }
20
+ }
21
+ }
22
+ }
@@ -0,0 +1,5 @@
1
+ {
2
+ "name": "hello",
3
+ "main": "./hello.cjs",
4
+ "types": "./hello.d.ts"
5
+ }
@@ -0,0 +1,18 @@
1
+ {
2
+ "server": {
3
+ "hostname": "127.0.0.1",
4
+ "port": 0,
5
+ "logger": {
6
+ "level": "info"
7
+ }
8
+ },
9
+ "plugins": {
10
+ "paths": ["./plugin.ts"],
11
+ "typescript": true
12
+ },
13
+ "clients": [{
14
+ "path": "./hello",
15
+ "url": "{PLT_CLIENT_URL}"
16
+ }],
17
+ "metrics": false
18
+ }
@@ -0,0 +1,8 @@
1
+ import { FastifyInstance } from 'fastify'
2
+ /// <reference path="./hello" />
3
+
4
+ export default async function (app: FastifyInstance) {
5
+ app.get('/', async () => {
6
+ return app.hello.get({})
7
+ })
8
+ }
@@ -0,0 +1,22 @@
1
+ {
2
+ "compilerOptions": {
3
+ "module": "commonjs",
4
+ "esModuleInterop": true,
5
+ "target": "es6",
6
+ "moduleResolution": "node",
7
+ "sourceMap": true,
8
+ "pretty": true,
9
+ "noEmitOnError": true,
10
+ "outDir": "dist"
11
+ },
12
+ "watchOptions": {
13
+ "watchFile": "fixedPollingInterval",
14
+ "watchDirectory": "fixedPollingInterval",
15
+ "fallbackPolling": "dynamicPriority",
16
+ "synchronousWatchDirectory": true,
17
+ "excludeDirectories": [
18
+ "**/node_modules",
19
+ "dist"
20
+ ]
21
+ }
22
+ }
package/index.d.ts ADDED
@@ -0,0 +1,18 @@
1
+ import { FastifyInstance, InjectOptions, LightMyRequestResponse } from "fastify"
2
+
3
+ export type pltServiceHandlerBuildServer = {
4
+ app: FastifyInstance
5
+ address: string
6
+ port: number
7
+ restart: () => Promise<void>
8
+ listen: () => Promise<{
9
+ address: string
10
+ port: number
11
+ }>
12
+ stop: () => Promise<void>
13
+ inject: (opts: InjectOptions | string) => Promise<LightMyRequestResponse>
14
+ }
15
+
16
+ declare module '@platformatic/service' {
17
+ export function buildServer(opts: object, app?: object, ConfigManagerContructor?: object): Promise<pltServiceHandlerBuildServer>
18
+ }
package/index.js CHANGED
@@ -77,6 +77,12 @@ async function platformaticService (app, opts, toLoad = []) {
77
77
  }
78
78
  }
79
79
 
80
+ for (const plugin of (app.platformatic.config.clients || [])) {
81
+ app.register(require(plugin.path), {
82
+ url: plugin.url
83
+ })
84
+ }
85
+
80
86
  if (opts.plugins) {
81
87
  // if we don't have a fullPath, let's assume we are in a test and we can use the current working directory
82
88
  const configPath = app.platformatic.configManager.fullPath || join(process.cwd(), 'platformatic.db.json')
@@ -193,6 +199,24 @@ function adjustConfigAfterMerge (options, stash) {
193
199
  }
194
200
  }
195
201
 
202
+ async function adjustHttpsKeyAndCert (arg) {
203
+ if (typeof arg === 'string') {
204
+ return arg
205
+ }
206
+
207
+ if (!Array.isArray(arg)) {
208
+ // { path: pathToKeyOrCert }
209
+ return readFile(arg.path)
210
+ }
211
+
212
+ // Array of strings or objects.
213
+ for (let i = 0; i < arg.length; ++i) {
214
+ arg[i] = await adjustHttpsKeyAndCert(arg[i])
215
+ }
216
+
217
+ return arg
218
+ }
219
+
196
220
  async function buildServer (options, app, ConfigManagerContructor) {
197
221
  app = app || platformaticService
198
222
  ConfigManagerContructor = ConfigManagerContructor || ConfigManager
@@ -208,6 +232,16 @@ async function buildServer (options, app, ConfigManagerContructor) {
208
232
  options = deepmerge({}, options, cm.current)
209
233
  options.configManager = cm
210
234
  adjustConfigAfterMerge(options, stash)
235
+
236
+ if (options.server.https) {
237
+ options.server.https.key = await adjustHttpsKeyAndCert(options.server.https.key)
238
+ options.server.https.cert = await adjustHttpsKeyAndCert(options.server.https.cert)
239
+ options.server = { ...options.server, ...options.server.https }
240
+ delete options.server.https
241
+ options.server.protocol = 'https'
242
+ } else {
243
+ options.server.protocol = 'http'
244
+ }
211
245
  }
212
246
  const serverConfig = createServerConfig(options)
213
247
 
@@ -217,9 +251,10 @@ async function buildServer (options, app, ConfigManagerContructor) {
217
251
 
218
252
  Object.defineProperty(handler, 'url', {
219
253
  get () {
254
+ const protocol = serverConfig.protocol
220
255
  const address = handler.address
221
256
  const port = handler.port
222
- const url = `http://${address}:${port}`
257
+ const url = `${protocol}://${address}:${port}`
223
258
  return url
224
259
  }
225
260
  })
@@ -0,0 +1,27 @@
1
+ import { expectError, expectType } from 'tsd';
2
+ import {
3
+ FastifyInstance,
4
+ LightMyRequestResponse,
5
+ } from 'fastify';
6
+ import { pltServiceHandlerBuildServer } from '.';
7
+
8
+ const server: pltServiceHandlerBuildServer = {
9
+ app: {} as FastifyInstance,
10
+ address: 'localhost',
11
+ port: 3000,
12
+ restart: async () => {},
13
+ listen: async () => ({ address: 'localhost', port: 3000 }),
14
+ stop: async () => {},
15
+ inject: async () => ({} as LightMyRequestResponse),
16
+ };
17
+
18
+ expectType<pltServiceHandlerBuildServer>(server);
19
+ expectError<pltServiceHandlerBuildServer>({...server, app: 'WRONG' });
20
+ expectError<pltServiceHandlerBuildServer>({...server, address: 42 });
21
+ expectError<pltServiceHandlerBuildServer>({...server, port: 'WRONG' });
22
+ expectError<pltServiceHandlerBuildServer>({...server, restart: 'WRONG' });
23
+ expectError<pltServiceHandlerBuildServer>({...server, listen: 'WRONG' });
24
+ expectError<pltServiceHandlerBuildServer>({...server, listen: async () => ({ address: 42, port: 3000 }), });
25
+ expectError<pltServiceHandlerBuildServer>({...server, listen: async () => ({ address: 'localhost', port: 'WRONG' }), });
26
+ expectError<pltServiceHandlerBuildServer>({...server, stop: 'WRONG' });
27
+ expectError<pltServiceHandlerBuildServer>({...server, inject: 'WRONG' });
package/lib/config.js CHANGED
@@ -1,7 +1,6 @@
1
1
  'use strict'
2
2
 
3
3
  const ConfigManager = require('@platformatic/config')
4
- const { resolve } = require('path')
5
4
  const { schema } = require('./schema')
6
5
 
7
6
  class ServiceConfigManager extends ConfigManager {
@@ -19,27 +18,6 @@ class ServiceConfigManager extends ConfigManager {
19
18
  envWhitelist: ['PORT', ...(opts.envWhitelist || [])]
20
19
  })
21
20
  }
22
-
23
- _transformConfig () {
24
- const fixPluginPath = (plugin) => {
25
- // for some reasons c8 does not detect these
26
- /* c8 ignore next 3 */
27
- if (typeof plugin === 'string') {
28
- plugin = { path: plugin }
29
- }
30
- plugin.path = this._fixRelativePath(plugin.path)
31
- return plugin
32
- }
33
-
34
- // relative-to-absolute plugin path
35
- if (this.current.plugins?.paths) {
36
- this.current.plugins.paths = this.current.plugins.paths.map(fixPluginPath)
37
- }
38
- }
39
-
40
- _fixRelativePath (path) {
41
- return resolve(this.dirname, path)
42
- }
43
21
  }
44
22
 
45
23
  module.exports = ServiceConfigManager
package/lib/schema.js CHANGED
@@ -237,6 +237,87 @@ const server = {
237
237
  { type: 'integer' }
238
238
  ]
239
239
  },
240
+ https: {
241
+ type: 'object',
242
+ properties: {
243
+ key: {
244
+ anyOf: [
245
+ {
246
+ type: 'string'
247
+ },
248
+ {
249
+ type: 'object',
250
+ properties: {
251
+ path: {
252
+ type: 'string',
253
+ resolvePath: true
254
+ }
255
+ },
256
+ additionalProperties: false
257
+ },
258
+ {
259
+ type: 'array',
260
+ items: {
261
+ anyOf: [
262
+ {
263
+ type: 'string'
264
+ },
265
+ {
266
+ type: 'object',
267
+ properties: {
268
+ path: {
269
+ type: 'string',
270
+ resolvePath: true
271
+ }
272
+ },
273
+ additionalProperties: false
274
+ }
275
+ ]
276
+ }
277
+ }
278
+ ]
279
+ },
280
+ cert: {
281
+ anyOf: [
282
+ {
283
+ type: 'string'
284
+ },
285
+ {
286
+ type: 'object',
287
+ properties: {
288
+ path: {
289
+ type: 'string',
290
+ resolvePath: true
291
+ }
292
+ },
293
+ additionalProperties: false
294
+ },
295
+ {
296
+ type: 'array',
297
+ items: {
298
+ anyOf: [
299
+ {
300
+ type: 'string'
301
+ },
302
+ {
303
+ type: 'object',
304
+ properties: {
305
+ path: {
306
+ type: 'string',
307
+ resolvePath: true
308
+ }
309
+ },
310
+ additionalProperties: false
311
+ }
312
+ ]
313
+ }
314
+ }
315
+ ]
316
+ }
317
+ },
318
+ additionalProperties: false,
319
+ required: ['key', 'cert']
320
+ },
240
321
  cors
241
322
  },
242
323
  required: ['hostname', 'port']
@@ -274,12 +355,14 @@ const plugins = {
274
355
  type: 'array',
275
356
  items: {
276
357
  anyOf: [{
277
- type: 'string'
358
+ type: 'string',
359
+ resolvePath: true
278
360
  }, {
279
361
  type: 'object',
280
362
  properties: {
281
363
  path: {
282
- type: 'string'
364
+ type: 'string',
365
+ resolvePath: true
283
366
  },
284
367
  options: {
285
368
  type: 'object',
@@ -417,6 +500,24 @@ const service = {
417
500
  additionalProperties: false
418
501
  }
419
502
 
503
+ const clients = {
504
+ type: 'array',
505
+ items: {
506
+ type: 'object',
507
+ properties: {
508
+ path: {
509
+ type: 'string',
510
+ resolvePath: true
511
+ },
512
+ url: {
513
+ type: 'string'
514
+ }
515
+ },
516
+ additionalProperties: false,
517
+ required: ['path', 'url']
518
+ }
519
+ }
520
+
420
521
  const platformaticServiceSchema = {
421
522
  $id: `https://platformatic.dev/schemas/${version}/service`,
422
523
  type: 'object',
@@ -435,7 +536,8 @@ const platformaticServiceSchema = {
435
536
  $schema: {
436
537
  type: 'string'
437
538
  },
438
- service
539
+ service,
540
+ clients
439
541
  },
440
542
  additionalProperties: false,
441
543
  required: ['server'],
@@ -450,6 +552,7 @@ module.exports.plugins = plugins
450
552
  module.exports.watch = watch
451
553
  module.exports.openApiDefs = openApiDefs
452
554
  module.exports.openApiBase = openApiBase
555
+ module.exports.clients = clients
453
556
 
454
557
  if (require.main === module) {
455
558
  console.log(JSON.stringify(platformaticServiceSchema, null, 2))
package/package.json CHANGED
@@ -1,8 +1,11 @@
1
1
  {
2
2
  "name": "@platformatic/service",
3
- "version": "0.18.0",
3
+ "version": "0.19.1",
4
4
  "description": "",
5
5
  "main": "index.js",
6
+ "bin": {
7
+ "plt-service": "./service.mjs"
8
+ },
6
9
  "author": "Matteo Collina <hello@matteocollina.com>",
7
10
  "repository": {
8
11
  "type": "git",
@@ -17,12 +20,14 @@
17
20
  "@matteo.collina/worker": "^3.0.0",
18
21
  "bindings": "^1.5.0",
19
22
  "c8": "^7.13.0",
23
+ "self-cert": "^2.0.0",
20
24
  "snazzy": "^9.0.0",
21
25
  "split2": "^4.1.0",
22
26
  "standard": "^17.0.0",
23
27
  "strip-ansi": "^7.0.1",
24
28
  "tap": "^16.3.4",
25
- "typescript": "^4.9.5",
29
+ "typescript": "^5.0.0",
30
+ "tsd": "^0.28.0",
26
31
  "undici": "^5.20.0",
27
32
  "vscode-json-languageservice": "^5.3.0",
28
33
  "why-is-node-running": "^2.2.2",
@@ -58,8 +63,9 @@
58
63
  "pino-pretty": "^10.0.0",
59
64
  "rfdc": "^1.3.0",
60
65
  "ua-parser-js": "^1.0.33",
61
- "@platformatic/config": "0.18.0",
62
- "@platformatic/utils": "0.18.0"
66
+ "@platformatic/config": "0.19.1",
67
+ "@platformatic/client": "0.19.1",
68
+ "@platformatic/utils": "0.19.1"
63
69
  },
64
70
  "standard": {
65
71
  "ignore": [
@@ -67,7 +73,7 @@
67
73
  ]
68
74
  },
69
75
  "scripts": {
70
- "test": "standard | snazzy && c8 --100 tap test/*test.js test/*/*.test.mjs",
76
+ "test": "standard | snazzy && c8 --100 tap test/*test.js test/*/*.test.mjs && tsd",
71
77
  "lint": "standard | snazzy"
72
78
  }
73
79
  }
package/service.mjs CHANGED
File without changes