hapijs / hapijs/hapi

CORS Configuration Expectations and Assumptions

Open
#4,437 0 comments 0 reactions 0 assignees View on GitHub
documentation
Dominant language
JavaScript
Stars
14.8k
Forks
1.4k
Avg merge
22d 3h
Merged PRs (30d)
1

Description

#### Context

* *Node 14*:
* *Hapijs 21.3.0*:

#### What are you trying to achieve or the steps to reproduce ?

I am not sure if the documentation or my expectations are unclear or the intent is the hapijs project "it works as expected" But I think the CORS Documentation at the server level and route level could use some additional clarification in either case

Server Config with CORS enabled
```js
const server = hapi.server({
host: 'localhost',
listener,
port: 3000,
router: {
stripTrailingSlash: true,
},
routes: {
cors: {
origin: 'https://10.0.0.1',
headers: ['Accept', 'Content-Type'],
exposedHeaders: ['x-some custom-header'],
},
payload: {
allow: ['application/json', 'application/*+json'],
},
security: true,
},
tls: true,
});
```
The above configuration would enable CORS, at the server level, for ALL routes as per the documentation.

> server.options.routes
> Default value: none.
> A [route options](https://hapi.dev/api/?v=21.3.0#route-options) object used as the default configuration for every route.

I would expect that if I turned off the CORS at the route level (cors: false), that CORS should be disabled for that route e.g.

Route
```js
const healthcheck = {
method: 'GET',
path: '/healthcheck',
options: {
cors: false
handler: () => ({ status: 'Ok' }),
description: 'Test if the Service is up',
notes: [],
tags: ['api'], // ADD THIS TAG
},
};
```

> route.options.app
> Application-specific route configuration state. Should not be used by [plugins](https://hapi.dev/api/?v=21.3.0#plugins) which should use options.plugins[name] instead.

However, this is not the case. CORS is still enabled at the route regardless for the `cors: false` due to the original CORS specification at the server level. To "disable" CORS at the route level, you have to specify the `['*']` in the CORS origin field. The issue here is that CORS is still enabled for this route but you have to specify that anything/everything is allowed to access it which seems counter intuitive.

```js
const healthcheck = {
method: 'GET',
path: '/healthcheck',
options: {
cors: {
origin: ['*']
},
handler: () => ({ status: 'Ok' }),
description: 'Test if the Service is up',
notes: [],
tags: ['api'], // ADD THIS TAG
},
};
```

Maybe this is by design, in which case the documentation should call out that CORS configuration at the server level is an ALL or nothing kind of deal, whereas at the route level, CORS configuration will illicit finer control with some overhead.

If this is indeed a bug, then the expected behavior would be that adding `cors: false` at the route level would disable CORS

```js
const some = 'properly formatted code example';
```

Contributor guide

Open the contributing guide

Assessment

This issue has not been assessed yet.

Get new issues in your inbox

A short digest of beginner-friendly GitHub issues.