@trojs/openapi-server 1.13.0 → 1.14.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/package.json CHANGED
@@ -1,7 +1,7 @@
1
1
  {
2
2
  "name": "@trojs/openapi-server",
3
3
  "description": "OpenAPI Server",
4
- "version": "1.13.0",
4
+ "version": "1.14.0",
5
5
  "author": {
6
6
  "name": "Pieter Wigboldus",
7
7
  "url": "https://trojs.org/"
@@ -35,9 +35,10 @@
35
35
  "main": "src/server.js",
36
36
  "devDependencies": {
37
37
  "@eslint/js": "^9.15.0",
38
+ "@trojs/error": "^4.3.6",
38
39
  "@trojs/lint": "^0.3.4",
39
- "@types/node": "^22.0.0",
40
40
  "@types/express-serve-static-core": "^5.0.6",
41
+ "@types/node": "^22.0.0",
41
42
  "eslint": "^9.15.0",
42
43
  "globals": "^16.0.0",
43
44
  "jscpd": "^4.0.5",
package/src/api.js CHANGED
@@ -1,5 +1,6 @@
1
1
  import express from 'express'
2
2
  import swaggerUi from 'swagger-ui-express'
3
+ import crypto from 'node:crypto'
3
4
  import { setupRouter } from './router.js'
4
5
 
5
6
  /**
@@ -97,7 +98,7 @@ export class Api {
97
98
  if (this.apiDocs) {
98
99
  // Generate an ETag for the specification (simple hash or JSON string)
99
100
  const apiDocsString = JSON.stringify(this.specification)
100
- const etag = `"${Buffer.from(apiDocsString).toString('base64')}"`
101
+ const etag = `"${crypto.createHash('sha256').update(apiDocsString).digest('base64')}"`
101
102
 
102
103
  router.get('/api-docs', (request, response) => {
103
104
  // Check for If-None-Match header
@@ -1,3 +1,7 @@
1
+ /**
2
+ * @typedef {Error & { status?: number }} StatusError
3
+ */
4
+
1
5
  const errorCodesStatus = [
2
6
  {
3
7
  type: TypeError,
@@ -16,9 +20,10 @@ const errorCodesStatus = [
16
20
  /**
17
21
  * Get a http status when you send an error.
18
22
  * When it is a error, throw back the error.
19
- * @param {Error} error
23
+ * @param {StatusError} error
20
24
  * @returns {number}
21
25
  */
22
26
  export default (error) =>
23
- errorCodesStatus.find((errorCode) => error instanceof errorCode.type)
24
- .status
27
+ error.status
28
+ || errorCodesStatus.find((errorCode) => error instanceof errorCode.type)?.status
29
+ || 500
@@ -23,7 +23,7 @@ import { parseParams } from './params.js'
23
23
  * @returns {Function}
24
24
  */
25
25
  export const makeExpressCallback
26
- = ({ controller, specification, errorDetails, logger, meta, mock, preLog, postLog }) =>
26
+ = ({ controller, specification, errorDetails, logger, meta, mock, preLog, postLog }) =>
27
27
  /**
28
28
  * Handle controller
29
29
  * @async
@@ -32,76 +32,76 @@ export const makeExpressCallback
32
32
  * @param {Response} response
33
33
  * @returns {Promise<any>}
34
34
  */
35
- async (context, request, response) => {
36
- const startTime = hrtime()
37
- try {
38
- const allParameters = {
39
- ...(context.request?.params || {}),
40
- ...(context.request?.query || {})
41
- }
42
- const parameters = parseParams({
43
- query: allParameters,
44
- spec: context.operation.parameters,
45
- mock
46
- })
47
- const url = `${request.protocol}://${request.get('Host')}${request.originalUrl}`
48
- const feedback = {
49
- context,
50
- request,
51
- response,
52
- parameters,
53
- specification,
54
- post: request.body,
55
- url,
56
- logger,
57
- meta
58
- }
59
- if (preLog) {
60
- preLog(feedback)
61
- }
62
- const responseBody = await controller(feedback)
63
- const responseTime = hrtime(startTime)[1] / 1000000 // convert to milliseconds
64
- if (postLog) {
65
- postLog({ ...feedback, responseBody, responseTime })
66
- }
67
- logger.debug({
68
- url,
69
- parameters,
70
- post: request.body,
71
- response: responseBody
72
- })
73
-
74
- return responseBody
75
- } catch (error) {
76
- const errorCodeStatus = getStatusByError(error)
35
+ async (context, request, response) => {
36
+ const startTime = hrtime()
37
+ try {
38
+ const allParameters = {
39
+ ...(context.request?.params || {}),
40
+ ...(context.request?.query || {})
41
+ }
42
+ const parameters = parseParams({
43
+ query: allParameters,
44
+ spec: context.operation.parameters,
45
+ mock
46
+ })
47
+ const url = `${request.protocol}://${request.get('Host')}${request.originalUrl}`
48
+ const feedback = {
49
+ context,
50
+ request,
51
+ response,
52
+ parameters,
53
+ specification,
54
+ post: request.body,
55
+ url,
56
+ logger,
57
+ meta
58
+ }
59
+ if (preLog) {
60
+ preLog(feedback)
61
+ }
62
+ const responseBody = await controller(feedback)
63
+ const responseTime = hrtime(startTime)[1] / 1000000 // convert to milliseconds
64
+ if (postLog) {
65
+ postLog({ ...feedback, responseBody, responseTime })
66
+ }
67
+ logger.debug({
68
+ url,
69
+ parameters,
70
+ post: request.body,
71
+ response: responseBody
72
+ })
77
73
 
78
- if (errorCodeStatus >= 500) {
79
- logger.error(error)
80
- } else {
81
- logger.warn(error)
82
- }
74
+ return responseBody
75
+ } catch (error) {
76
+ const errorCodeStatus = getStatusByError(error)
83
77
 
84
- response.status(errorCodeStatus)
78
+ if (errorCodeStatus >= 500) {
79
+ logger.error(error)
80
+ } else {
81
+ logger.warn(error)
82
+ }
85
83
 
86
- if (errorDetails) {
87
- return {
88
- errors: [
89
- {
90
- message: error.message,
91
- value: error.valueOf(),
92
- type: error.constructor.name
93
- }
94
- ],
95
- status: errorCodeStatus,
96
- timestamp: new Date(),
97
- message: error.message
98
- }
99
- }
84
+ response.status(errorCodeStatus)
100
85
 
86
+ if (errorDetails) {
101
87
  return {
88
+ errors: [
89
+ {
90
+ message: error.message,
91
+ value: error.valueOf(),
92
+ type: error.constructor.name
93
+ }
94
+ ],
102
95
  status: errorCodeStatus,
103
96
  timestamp: new Date(),
104
97
  message: error.message
105
98
  }
106
99
  }
100
+
101
+ return {
102
+ status: errorCodeStatus,
103
+ timestamp: new Date(),
104
+ message: error.message
105
+ }
107
106
  }
107
+ }
package/src/router.js CHANGED
@@ -92,7 +92,7 @@ export const setupRouter = ({
92
92
 
93
93
  api.register('notImplemented', (context) => {
94
94
  const { mock: mockImplementation }
95
- = context.api.mockResponseForOperation(context.operation.operationId)
95
+ = context.api.mockResponseForOperation(context.operation.operationId)
96
96
  return mockImplementation
97
97
  })
98
98