@whook/cors
TypeScript icon, indicating that this package has built-in type declarations

16.1.0 • Public • Published

@whook/cors

A wrapper to provide CORS support to a Whook server

GitHub license

This Whook wrapper provides CORS support by adding it to your OpenAPI file and creating the handlers that runs the OPTIONS method when you cannot do it at the proxy/gateway level.

Usage

To use this plugin, simply install it:

npm i @whook/cors;

Declare it in the src/index.ts file of your project:

  // ...

  $.register(
    constant('HANDLERS_WRAPPERS', [
+      'wrapHandlerWithCORS',
      'wrapHandlerWithAuthorization',
    ]),
  );

  // ...

  $.register(
    constant('WHOOK_PLUGINS', [
      ...WHOOK_DEFAULT_PLUGINS,
+      '@whook/cors',
      '@whook/authorization',
    ]),
  );

  // ...

Declare types in your src/whook.d.ts definition:

+ import type {
+   CORSConfig,
+   WhookAPIOperationCORSConfig,
+ } from '@whook/cors';

declare module 'application-services' {

  // ...

  export interface AppConfig
-    extends WhookBaseConfigs {}
+    extends WhookBaseConfigs, CORSConfig {}

  // ...
}

// ...

declare module '@whook/whook' {
  export interface WhookAPIHandlerDefinition<
    T extends Record<string, unknown> = Record<string, unknown>,
    U extends {
      [K in keyof U]: K extends `x-${string}` ? Record<string, unknown> : never;
    } = unknown,
    V extends Record<string, unknown> = Record<string, unknown>,
  > extends WhookBaseAPIHandlerDefinition<T, U> {
    operation: U & WhookAPIOperation<
        T &
      WhookAPIOperationSwaggerConfig & WhookAPIOperationCORSConfig
    >;
  }
}

And add the CORS config (usually in src/config/common/config.js):

// ...
import type { AppConfig } from 'application-services';

const CONFIG: AppConfig = {
  // ...
+   CORS: {
+     'Access-Control-Allow-Origin': '*',
+     'Access-Control-Allow-Methods': 'GET,POST,PUT,DELETE,OPTIONS',
+     'Access-Control-Allow-Headers': [
+       'Accept',
+       'Accept-Encoding',
+       'Accept-Language',
+       'Referrer',
+       'Content-Type',
+       'Content-Encoding',
+       'Authorization',
+       'Keep-Alive',
+       'User-Agent',
+     ].join(','),
+   },
};

export default CONFIG;

You should also use the wrapped error handler:

+ import { initErrorHandlerWithCORS } from '@whook/cors';

// ...

export async function prepareEnvironment<T extends Knifecycle<Dependencies>>(
    $: T = new Knifecycle() as T,
  ): Promise<T> {

//...

+  // Add the CORS wrapped error handler
+  $.register(initErrorHandlerWithCORS);

  return $;
}

According to the kind of build you use, you may also declare it in your src/build.ts file:

  $.register(
    constant('INITIALIZER_PATH_MAP', {
      ...DEFAULT_BUILD_INITIALIZER_PATH_MAP,
      // MY_SERVICE: '@my/service_module_name',
      jwtToken: 'jwt-service/dist/index.js',
+      errorHandler: '@whook/cors/dist/services/errorHandler.js',
    }),
  );

Finally, you must adapt the API service to handle CORS options:

+ import { augmentAPIWithCORS } from '@whook/cors';

// (...)

export default name('API', autoService(initAPI));

// The API service is where you put your handlers
// altogether to form the final API
async function initAPI({
// (..)
) {

  // (..)

  // You can apply transformations to your API like
  // here for CORS support (OPTIONS method handling)
-  return augmentAPIWithFakeAuth({ ENV }, API);
+  return augmentAPIWithCORS(await augmentAPIWithFakeAuth({ ENV }, API));
}

To see a real example have a look at the @whook/example.

Note that you can define individual CORS values on the handler definitions usins the x-whook property.

API

Functions

augmentAPIWithCORS(API)Promise.<Object>

Augment an OpenAPI to also serve OPTIONS methods with the CORS added.

wrapErrorHandlerForCORS(services)Promise.<Object>

Wrap the error handler service as a last chance to add CORS

initWrapHandlerWithCORS(services)Promise.<Object>

Wrap an handler to append CORS to response.

augmentAPIWithCORS(API) ⇒ Promise.<Object>

Augment an OpenAPI to also serve OPTIONS methods with the CORS added.

Kind: global function
Returns: Promise.<Object> - The augmented OpenAPI object

Param Type Description
API Object The OpenAPI object

wrapErrorHandlerForCORS(services) ⇒ Promise.<Object>

Wrap the error handler service as a last chance to add CORS

Kind: global function
Returns: Promise.<Object> - A promise of an object containing the reshaped env vars.

Param Type Default Description
services Object The services depended on
services.CORS Object A CORS object to be added to errors responses
[services.log] Object noop An optional logging service

initWrapHandlerWithCORS(services) ⇒ Promise.<Object>

Wrap an handler to append CORS to response.

Kind: global function
Returns: Promise.<Object> - A promise of an object containing the reshaped env vars.

Param Type Default Description
services Object The services ENV depends on
services.CORS Object A CORS object to be added to errors responses
[services.log] Object noop An optional logging service

Authors

License

MIT

Package Sidebar

Install

npm i @whook/cors

Weekly Downloads

231

Version

16.1.0

License

MIT

Unpacked Size

69 kB

Total Files

24

Last publish

Collaborators

  • nfroidure