@pikku/core 0.6.18 → 0.6.20

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/CHANGELOG.md CHANGED
@@ -1,5 +1,17 @@
1
1
  ## 0.6
2
2
 
3
+ ## 0.6.20
4
+
5
+ ### Patch Changes
6
+
7
+ - 1d43a9a: feat: adding context to allow middleware to set values (not typed)
8
+
9
+ ## 0.6.19
10
+
11
+ ### Patch Changes
12
+
13
+ - 9fb2b99: refactor: moving schemas to pikku state
14
+
3
15
  ## 0.6.18
4
16
 
5
17
  ### Patch Changes
@@ -16,7 +16,6 @@ export interface ErrorDetails {
16
16
  status: number;
17
17
  message: string;
18
18
  }
19
- export declare const getErrors: () => Map<PikkuError, ErrorDetails>;
20
19
  /**
21
20
  * Adds an error to the API errors map.
22
21
  * @param error - The error to add.
@@ -13,14 +13,13 @@ export class PikkuError extends Error {
13
13
  Object.setPrototypeOf(this, new.target.prototype);
14
14
  }
15
15
  }
16
- export const getErrors = () => pikkuState('errors', 'errors');
17
16
  /**
18
17
  * Adds an error to the API errors map.
19
18
  * @param error - The error to add.
20
19
  * @param details - The details of the error.
21
20
  */
22
21
  export const addError = (error, { status, message }) => {
23
- pikkuState('errors', 'errors').set(error, { status, message });
22
+ pikkuState('misc', 'errors').set(error, { status, message });
24
23
  };
25
24
  /**
26
25
  * Adds multiple errors to the API errors map.
@@ -37,10 +36,10 @@ export const addErrors = (errors) => {
37
36
  * @returns An object containing the status and message, or undefined if the error is not found.
38
37
  */
39
38
  export const getErrorResponse = (error) => {
40
- const errors = Array.from(pikkuState('errors', 'errors').entries());
39
+ const errors = Array.from(pikkuState('misc', 'errors').entries());
41
40
  const foundError = errors.find(([e]) => e.name === error.constructor.name);
42
41
  if (foundError) {
43
42
  return foundError[1];
44
43
  }
45
- return pikkuState('errors', 'errors').get(error);
44
+ return pikkuState('misc', 'errors').get(error);
46
45
  };
@@ -11,4 +11,4 @@ import { PikkuHTTP } from './http/http-routes.types.js';
11
11
  * @param {boolean} respondWith404 - Whether to respond with 404 for NotFoundError
12
12
  * @param {boolean} bubbleError - Whether to throw the error after handling
13
13
  */
14
- export declare const handleError: (e: any, http: PikkuHTTP | undefined, trackerId: string, logger: Logger, logWarningsForStatusCodes: number[], respondWith404: boolean, bubbleError: boolean) => void;
14
+ export declare const handleError: (e: any, http: PikkuHTTP | undefined, trackerId: string | undefined, logger: Logger, logWarningsForStatusCodes: number[], respondWith404: boolean, bubbleError: boolean) => void;
@@ -28,16 +28,20 @@ export const handleError = (e, http, trackerId, logger, logWarningsForStatusCode
28
28
  });
29
29
  // Log certain status codes as warnings
30
30
  if (logWarningsForStatusCodes.includes(errorResponse.status)) {
31
- logger.warn(`Warning id: ${trackerId}`);
31
+ if (trackerId) {
32
+ logger.warn(`Warning id: ${trackerId}`);
33
+ }
32
34
  logger.warn(e);
33
35
  }
34
36
  }
35
37
  else {
36
38
  // Handle unexpected errors
37
- logger.warn(`Error id: ${trackerId}`);
38
39
  logger.error(e);
39
40
  http?.response?.setStatus(500);
40
- http?.response?.setJson({ errorId: trackerId });
41
+ if (trackerId) {
42
+ logger.warn(`Error id: ${trackerId}`);
43
+ http?.response?.setJson({ errorId: trackerId });
44
+ }
41
45
  }
42
46
  // Handle 404 errors specifically
43
47
  if (e instanceof NotFoundError) {
@@ -3,7 +3,6 @@ import { match } from 'path-to-regexp';
3
3
  import { PikkuHTTPAbstractRequest } from './pikku-http-abstract-request.js';
4
4
  import { PikkuHTTPAbstractResponse } from './pikku-http-abstract-response.js';
5
5
  import { ForbiddenError, MissingSessionError, NotFoundError, } from '../errors/errors.js';
6
- import crypto from 'crypto';
7
6
  import { closeSessionServices } from '../utils.js';
8
7
  import { coerceQueryStringToArray, validateSchema } from '../schema.js';
9
8
  import { LocalUserSessionService } from '../services/user-session-service.js';
@@ -111,7 +110,7 @@ export const createHTTPInteraction = (request, response) => {
111
110
  */
112
111
  const executeRouteWithMiddleware = async (services, matchedRoute, http, options) => {
113
112
  const { matchedPath, params, route, middleware, schemaName } = matchedRoute;
114
- const { singletonServices, userSessionService, createSessionServices, skipUserSession, } = services;
113
+ const { singletonServices, userSessionService, context, createSessionServices, skipUserSession, } = services;
115
114
  const requiresSession = route.auth !== false;
116
115
  let sessionServices;
117
116
  let result;
@@ -132,8 +131,8 @@ const executeRouteWithMiddleware = async (services, matchedRoute, http, options)
132
131
  throw new MissingSessionError();
133
132
  }
134
133
  // Create session services
135
- sessionServices = await createSessionServices(singletonServices, { http }, session);
136
- const allServices = { ...singletonServices, ...sessionServices, http };
134
+ sessionServices = await createSessionServices({ ...singletonServices, context }, { http }, session);
135
+ const allServices = { ...singletonServices, ...sessionServices, context };
137
136
  const data = await http?.request?.getData();
138
137
  // Validate schema
139
138
  validateSchema(singletonServices.logger, singletonServices.schemaService, schemaName, data);
@@ -158,7 +157,7 @@ const executeRouteWithMiddleware = async (services, matchedRoute, http, options)
158
157
  http?.response?.end();
159
158
  return result;
160
159
  };
161
- await runMiddleware({ ...singletonServices, userSessionService }, { http }, middleware, runMain);
160
+ await runMiddleware({ ...singletonServices, context, userSessionService }, { http }, middleware, runMain);
162
161
  return sessionServices ? { result, sessionServices } : { result };
163
162
  };
164
163
  /**
@@ -169,7 +168,7 @@ const executeRouteWithMiddleware = async (services, matchedRoute, http, options)
169
168
  * @ignore
170
169
  */
171
170
  export const runHTTPRoute = async ({ singletonServices, request, response, createSessionServices, route: apiRoute, method: apiType, skipUserSession = false, respondWith404 = true, logWarningsForStatusCodes = [], coerceToArray = false, bubbleErrors = false, }) => {
172
- const trackerId = crypto.randomUUID().toString();
171
+ const context = new Map();
173
172
  const userSessionService = new LocalUserSessionService();
174
173
  let sessionServices;
175
174
  let result;
@@ -192,6 +191,7 @@ export const runHTTPRoute = async ({ singletonServices, request, response, creat
192
191
  ({ result, sessionServices } = await executeRouteWithMiddleware({
193
192
  singletonServices,
194
193
  userSessionService,
194
+ context,
195
195
  createSessionServices,
196
196
  skipUserSession,
197
197
  }, matchedRoute, http, { coerceToArray }));
@@ -199,7 +199,7 @@ export const runHTTPRoute = async ({ singletonServices, request, response, creat
199
199
  }
200
200
  catch (e) {
201
201
  // Handle and possibly bubble the error
202
- handleError(e, http, trackerId, singletonServices.logger, logWarningsForStatusCodes, respondWith404, bubbleErrors);
202
+ handleError(e, http, context.get('trackingId'), singletonServices.logger, logWarningsForStatusCodes, respondWith404, bubbleErrors);
203
203
  }
204
204
  finally {
205
205
  // Clean up session services
@@ -20,8 +20,9 @@ interface PikkuState {
20
20
  tasks: Map<string, CoreScheduledTask>;
21
21
  meta: ScheduledTasksMeta;
22
22
  };
23
- errors: {
23
+ misc: {
24
24
  errors: Map<PikkuError, ErrorDetails>;
25
+ schemas: Map<string, any>;
25
26
  };
26
27
  }
27
28
  export declare const resetPikkuState: () => void;
@@ -13,9 +13,9 @@ export const resetPikkuState = () => {
13
13
  tasks: new Map(),
14
14
  meta: [],
15
15
  },
16
- errors: {
17
- // We keep errors since they are registered globally
18
- errors: globalThis.pikkuState?.errors?.errors || new Map(),
16
+ misc: {
17
+ errors: globalThis.pikkuState?.misc?.errors || new Map(),
18
+ schemas: globalThis.pikkuState?.misc?.schema || new Map(),
19
19
  },
20
20
  };
21
21
  };
@@ -1,4 +1,3 @@
1
- import crypto from 'crypto';
2
1
  import { getErrorResponse } from '../errors/error-handler.js';
3
2
  import { closeSessionServices } from '../utils.js';
4
3
  import { pikkuState } from '../pikku-state.js';
@@ -16,7 +15,6 @@ class ScheduledTaskNotFoundError extends Error {
16
15
  }
17
16
  export async function runScheduledTask({ name, session, singletonServices, createSessionServices, }) {
18
17
  let sessionServices;
19
- const trackerId = crypto.randomUUID().toString();
20
18
  try {
21
19
  const task = pikkuState('scheduler', 'tasks').get(name);
22
20
  if (!task) {
@@ -33,7 +31,6 @@ export async function runScheduledTask({ name, session, singletonServices, creat
33
31
  catch (e) {
34
32
  const errorResponse = getErrorResponse(e);
35
33
  if (errorResponse != null) {
36
- singletonServices.logger.warn(`Error id: ${trackerId}`);
37
34
  singletonServices.logger.error(e);
38
35
  }
39
36
  throw e;
package/dist/schema.d.ts CHANGED
@@ -1,15 +1,5 @@
1
1
  import { Logger } from './services/logger.js';
2
2
  import { SchemaService } from './services/schema-service.js';
3
- /**
4
- * Retrieves the global schemas map.
5
- * @returns A map of schemas.
6
- */
7
- export declare const getSchemas: () => any;
8
- /**
9
- * Retrieves a schema from the schemas map.
10
- * @returns A schema.
11
- */
12
- export declare const getSchema: (schemaName: string) => any;
13
3
  /**
14
4
  * Adds a schema to the global schemas map.
15
5
  * @param name - The name of the schema.
package/dist/schema.js CHANGED
@@ -1,27 +1,5 @@
1
1
  import { UnprocessableContentError } from './errors/errors.js';
2
2
  import { pikkuState } from './pikku-state.js';
3
- /**
4
- * Retrieves the global schemas map.
5
- * @returns A map of schemas.
6
- */
7
- export const getSchemas = () => {
8
- if (!global.pikkuSchemas) {
9
- global.pikkuSchemas = new Map();
10
- }
11
- return global.pikkuSchemas;
12
- };
13
- /**
14
- * Retrieves a schema from the schemas map.
15
- * @returns A schema.
16
- */
17
- export const getSchema = (schemaName) => {
18
- const schemas = getSchemas();
19
- const schema = schemas.get(schemaName);
20
- if (!schema) {
21
- throw new Error(`Schema not found: ${schemaName}`);
22
- }
23
- return schema;
24
- };
25
3
  /**
26
4
  * Adds a schema to the global schemas map.
27
5
  * @param name - The name of the schema.
@@ -29,7 +7,7 @@ export const getSchema = (schemaName) => {
29
7
  * @ignore
30
8
  */
31
9
  export const addSchema = (name, value) => {
32
- getSchemas().set(name, value);
10
+ pikkuState('misc', 'schemas').set(name, value);
33
11
  };
34
12
  /**
35
13
  * Loads a schema and compiles it into a validator.
@@ -39,7 +17,8 @@ export const compileAllSchemas = (logger, schemaService) => {
39
17
  if (!schemaService) {
40
18
  throw new Error('SchemaService needs to be defined to load schemas');
41
19
  }
42
- for (const [name, schema] of getSchemas()) {
20
+ const schemas = pikkuState('misc', 'schemas');
21
+ for (const [name, schema] of schemas) {
43
22
  schemaService.compileSchema(name, schema);
44
23
  }
45
24
  validateAllSchemasLoaded(logger, schemaService);
@@ -64,7 +43,7 @@ const validateAllSchemasLoaded = (logger, schemaService) => {
64
43
  }
65
44
  };
66
45
  export const coerceQueryStringToArray = (schemaName, data) => {
67
- const schema = getSchema(schemaName);
46
+ const schema = pikkuState('misc', 'schemas').get(schemaName);
68
47
  for (const key in schema.properties) {
69
48
  const property = schema.properties[key];
70
49
  if (typeof property === 'boolean') {
@@ -90,7 +69,7 @@ export const validateSchema = async (logger, schemaService, schemaName, data) =>
90
69
  return;
91
70
  }
92
71
  }
93
- const schema = getSchema(schemaName);
72
+ const schema = pikkuState('misc', 'schemas').get(schemaName);
94
73
  await schemaService.compileSchema(schemaName, schema);
95
74
  await schemaService.validateSchema(schemaName, data);
96
75
  }