@gasket/plugin-elastic-apm 7.3.0-canary.4 → 7.3.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.
- package/README.md +91 -46
- package/lib/actions.js +25 -0
- package/lib/cookies.js +6 -6
- package/lib/create.js +24 -0
- package/lib/index.d.ts +15 -20
- package/lib/index.js +12 -23
- package/package.json +43 -27
- package/lib/middleware.js +0 -40
- package/lib/preboot.js +0 -29
package/README.md
CHANGED
|
@@ -4,38 +4,32 @@ Adds Elastic APM instrumentation to your application
|
|
|
4
4
|
|
|
5
5
|
## Installation
|
|
6
6
|
|
|
7
|
-
#### New apps
|
|
8
|
-
|
|
9
7
|
```
|
|
10
|
-
|
|
8
|
+
npm i @gasket/plugin-elastic-apm
|
|
11
9
|
```
|
|
12
10
|
|
|
13
|
-
|
|
11
|
+
Update your `gasket` file plugin configuration:
|
|
14
12
|
|
|
15
|
-
```
|
|
16
|
-
|
|
17
|
-
```
|
|
13
|
+
```diff
|
|
14
|
+
// gasket.js
|
|
18
15
|
|
|
19
|
-
|
|
16
|
+
+ import pluginElasticApm from '@gasket/plugin-elastic-apm';
|
|
20
17
|
|
|
21
|
-
|
|
22
|
-
|
|
23
|
-
|
|
24
|
-
|
|
25
|
-
|
|
26
|
-
]
|
|
27
|
-
}
|
|
28
|
-
}
|
|
18
|
+
export default makeGasket({
|
|
19
|
+
plugins: [
|
|
20
|
+
+ pluginElasticApm
|
|
21
|
+
]
|
|
22
|
+
});
|
|
29
23
|
```
|
|
30
24
|
|
|
31
|
-
Add
|
|
25
|
+
Add `NODE_OPTIONS=--import=./setup.js` to the `package.json` start script:
|
|
32
26
|
|
|
33
27
|
```diff
|
|
34
28
|
"scripts": {
|
|
35
|
-
"build": "
|
|
36
|
-
- "start": "
|
|
37
|
-
+ "start": "
|
|
38
|
-
"local": "
|
|
29
|
+
"build": "next build",
|
|
30
|
+
- "start": "next start",
|
|
31
|
+
+ "start": "NODE_OPTIONS=--import=./setup.js next start",
|
|
32
|
+
"local": "next dev"
|
|
39
33
|
}
|
|
40
34
|
```
|
|
41
35
|
|
|
@@ -43,20 +37,22 @@ Add a `setup.js` script to the root of your app
|
|
|
43
37
|
|
|
44
38
|
```
|
|
45
39
|
// setup.js
|
|
46
|
-
|
|
40
|
+
import apm from 'elastic-apm-node';
|
|
47
41
|
|
|
48
|
-
|
|
42
|
+
// Elastic APM setup
|
|
43
|
+
apm.start({
|
|
49
44
|
serviceName: 'my-service-name',
|
|
45
|
+
captureHeaders: false,
|
|
50
46
|
secretToken: process.env.ELASTIC_APM_SECRET_TOKEN,
|
|
51
47
|
serverUrl: process.env.ELASTIC_APM_SERVER_URL
|
|
52
|
-
//
|
|
48
|
+
// additional configuration options
|
|
53
49
|
});
|
|
54
50
|
```
|
|
55
51
|
|
|
56
52
|
## Configuration
|
|
57
53
|
|
|
58
54
|
The [start recommendations] for the APM agent are to require it as early as
|
|
59
|
-
possible in your app. For Gasket apps, using
|
|
55
|
+
possible in your app. For Gasket apps, using `NODE_OPTIONS=--import=./setup.js`
|
|
60
56
|
will accomplish this. To configure the APM agent, set the environment variables
|
|
61
57
|
described in the [configuration options documentation].
|
|
62
58
|
|
|
@@ -64,11 +60,28 @@ In particular, the APM server URL (`ELASTIC_APM_SERVER_URL`) and secret token
|
|
|
64
60
|
(`ELASTIC_APM_SECRET_TOKEN`) are both required configuration. If either of these
|
|
65
61
|
are not present, the APM agent will be disabled.
|
|
66
62
|
|
|
63
|
+
### Dotenv
|
|
64
|
+
|
|
65
|
+
If you wish to use `dotenv`, be sure it is installed and imported in `setup.js`:
|
|
66
|
+
|
|
67
|
+
```
|
|
68
|
+
npm i dotenv
|
|
69
|
+
```
|
|
70
|
+
|
|
71
|
+
```diff
|
|
72
|
+
// setup.js
|
|
73
|
+
+ import 'dotenv/config';
|
|
74
|
+
import apm from 'elastic-apm-node';
|
|
75
|
+
|
|
76
|
+
// Elastic APM setup
|
|
77
|
+
apm.start({
|
|
78
|
+
...
|
|
79
|
+
```
|
|
67
80
|
|
|
68
81
|
### Plugin Configurations
|
|
69
82
|
|
|
70
83
|
The Gasket plugin provides some additional setup helpers. These can be
|
|
71
|
-
configured under `elasticAPM` in the `gasket.
|
|
84
|
+
configured under `elasticAPM` in the `gasket.js`.
|
|
72
85
|
|
|
73
86
|
- **`sensitiveCookies`** - (string[]) A list of sensitive cookies to filter
|
|
74
87
|
|
|
@@ -77,14 +90,14 @@ configured under `elasticAPM` in the `gasket.config.js`.
|
|
|
77
90
|
If your application’s users send session credentials or any other sensitive
|
|
78
91
|
information in their cookies, you may wish to filter them out before they are
|
|
79
92
|
stored in Elasticsearch. Specify a list of cookie names to redact in
|
|
80
|
-
`gasket.
|
|
93
|
+
`gasket.js`:
|
|
81
94
|
|
|
82
95
|
```js
|
|
83
|
-
|
|
96
|
+
export default makeGasket({
|
|
84
97
|
elasticAPM: {
|
|
85
98
|
sensitiveCookies: ['my_jwt', 'userFullName']
|
|
86
99
|
}
|
|
87
|
-
};
|
|
100
|
+
});
|
|
88
101
|
```
|
|
89
102
|
|
|
90
103
|
#### Custom Filtering Sensitive Fields
|
|
@@ -94,17 +107,18 @@ information in their cookies, you may wish to filter them out before they are
|
|
|
94
107
|
stored in Elasticsearch. Specify a list of cookie names to redact in
|
|
95
108
|
`setup.js` using the [sanitizeFieldNames] configuration option:
|
|
96
109
|
|
|
97
|
-
```
|
|
110
|
+
```diff
|
|
98
111
|
// setup.js
|
|
99
|
-
|
|
112
|
+
import apm from 'elastic-apm-node';
|
|
100
113
|
|
|
101
|
-
|
|
102
|
-
|
|
103
|
-
|
|
104
|
-
|
|
114
|
+
// Elastic APM setup
|
|
115
|
+
apm.start({
|
|
116
|
+
+ sanitizeFieldNames: ['foo', 'bar', '*token*']
|
|
117
|
+
...
|
|
105
118
|
```
|
|
106
119
|
|
|
107
120
|
The `sanitizeFieldNames` config option can be used for:
|
|
121
|
+
|
|
108
122
|
- request and response HTTP headers
|
|
109
123
|
- HTTP request cookies
|
|
110
124
|
- any form field captured during an `application/x-www-form-urlencoded` data request
|
|
@@ -114,9 +128,39 @@ To filter out other data, use the [APM Add Filter API].
|
|
|
114
128
|
### Custom Filters
|
|
115
129
|
|
|
116
130
|
According to the [Elastic APM docs], the _Elastic APM agent for Node.js is a
|
|
117
|
-
singleton_.
|
|
131
|
+
singleton_.
|
|
132
|
+
This means that you can import and configure the singleton in various
|
|
118
133
|
hooks of your Gasket app, such as with the [init] or [middleware] lifecycles.
|
|
119
134
|
|
|
135
|
+
## Actions
|
|
136
|
+
|
|
137
|
+
### getApmTransaction
|
|
138
|
+
|
|
139
|
+
Use the `getApmTransaction` action to access and decorate the current APM
|
|
140
|
+
transaction. This action is available in any lifecycle hook or server-side code.
|
|
141
|
+
|
|
142
|
+
```js
|
|
143
|
+
// example-plugin.js
|
|
144
|
+
|
|
145
|
+
export default {
|
|
146
|
+
name: 'example-plugin',
|
|
147
|
+
hooks: {
|
|
148
|
+
express(gasket, app) {
|
|
149
|
+
app.use(async (req, res, next) => {
|
|
150
|
+
const transaction = await gasket.actions.getApmTransaction(req);
|
|
151
|
+
const locale = await gasket.actions.getIntlLocale(req);
|
|
152
|
+
transaction.setLabel('locale', locale);
|
|
153
|
+
});
|
|
154
|
+
}
|
|
155
|
+
}
|
|
156
|
+
}
|
|
157
|
+
```
|
|
158
|
+
|
|
159
|
+
In the above example, we are hooking the express lifecycle to add middleware
|
|
160
|
+
to decorate the transaction.
|
|
161
|
+
Calling `getApmTransaction` will also allow other plugins to decorate the
|
|
162
|
+
transaction by hooking the `apmTransaction` lifecycle discussed next.
|
|
163
|
+
|
|
120
164
|
## Lifecycles
|
|
121
165
|
|
|
122
166
|
### apmTransaction
|
|
@@ -131,20 +175,22 @@ request details are as follows:
|
|
|
131
175
|
| `res` | The HTTP response or framework-specific wrapper around it |
|
|
132
176
|
|
|
133
177
|
```javascript
|
|
134
|
-
//
|
|
135
|
-
|
|
136
|
-
|
|
137
|
-
|
|
178
|
+
// example-plugin.js
|
|
179
|
+
|
|
180
|
+
export default {
|
|
181
|
+
name: 'example-plugin',
|
|
182
|
+
hooks: {
|
|
183
|
+
apmTransaction(gasket, transaction, { req, res }) => {
|
|
184
|
+
transaction.setLabel('language', req.headers['accept-language']);
|
|
185
|
+
}
|
|
186
|
+
}
|
|
138
187
|
}
|
|
139
188
|
```
|
|
140
189
|
|
|
141
190
|
## How it works
|
|
142
191
|
|
|
143
|
-
This plugin hooks the Gasket [
|
|
144
|
-
|
|
145
|
-
`preboot` hook finds that the APM agent has not yet been started using the
|
|
146
|
-
recommended `--require elastic-apm-node/start`, it will start it here. However,
|
|
147
|
-
you risk not bootstrapping necessary modules with a late start.
|
|
192
|
+
This plugin hooks the Gasket [configure] lifecycle to set additional filtering,
|
|
193
|
+
such as for sensitive cookies.
|
|
148
194
|
|
|
149
195
|
## License
|
|
150
196
|
|
|
@@ -152,7 +198,6 @@ you risk not bootstrapping necessary modules with a late start.
|
|
|
152
198
|
|
|
153
199
|
<!-- LINKS -->
|
|
154
200
|
|
|
155
|
-
[preboot]:/packages/gasket-plugin-start/README.md#preboot
|
|
156
201
|
[init]:packages/gasket-plugin-command/README.md#init
|
|
157
202
|
[middleware]:/packages/gasket-plugin-express/README.md#middleware
|
|
158
203
|
[configuration options documentation]:https://www.elastic.co/guide/en/apm/agent/nodejs/current/configuration.html
|
package/lib/actions.js
ADDED
|
@@ -0,0 +1,25 @@
|
|
|
1
|
+
const { withGasketRequest } = require('@gasket/request');
|
|
2
|
+
|
|
3
|
+
/** @type {import('@gasket/core').ActionHandler<'getApmTransaction'>} */
|
|
4
|
+
const getApmTransaction = withGasketRequest(
|
|
5
|
+
async function getApmTransaction(gasket, req) {
|
|
6
|
+
const apm = require('elastic-apm-node');
|
|
7
|
+
|
|
8
|
+
if (!apm?.isStarted()) {
|
|
9
|
+
return;
|
|
10
|
+
}
|
|
11
|
+
|
|
12
|
+
const transaction = apm.currentTransaction;
|
|
13
|
+
if (!transaction) {
|
|
14
|
+
return;
|
|
15
|
+
}
|
|
16
|
+
|
|
17
|
+
await gasket.exec('apmTransaction', transaction, { req });
|
|
18
|
+
|
|
19
|
+
return transaction;
|
|
20
|
+
}
|
|
21
|
+
);
|
|
22
|
+
|
|
23
|
+
module.exports = {
|
|
24
|
+
getApmTransaction
|
|
25
|
+
};
|
package/lib/cookies.js
CHANGED
|
@@ -17,7 +17,7 @@ const sensitiveCookies = (config) => {
|
|
|
17
17
|
|
|
18
18
|
/**
|
|
19
19
|
* Redacts the contents of user-specified sensitive cookies
|
|
20
|
-
* @type {import('
|
|
20
|
+
* @type {import('.').filterSensitiveCookies}
|
|
21
21
|
*/
|
|
22
22
|
const filterSensitiveCookies = function (config) {
|
|
23
23
|
return function (payload) {
|
|
@@ -25,9 +25,9 @@ const filterSensitiveCookies = function (config) {
|
|
|
25
25
|
|
|
26
26
|
if (
|
|
27
27
|
payload.context &&
|
|
28
|
-
|
|
29
|
-
|
|
30
|
-
|
|
28
|
+
payload.context.request &&
|
|
29
|
+
payload.context.request.headers &&
|
|
30
|
+
payload.context.request.headers.cookie
|
|
31
31
|
) {
|
|
32
32
|
let cookie = payload.context.request.headers.cookie;
|
|
33
33
|
cookiesToRedact.forEach((sc) => {
|
|
@@ -41,8 +41,8 @@ const filterSensitiveCookies = function (config) {
|
|
|
41
41
|
}
|
|
42
42
|
|
|
43
43
|
if (payload.context &&
|
|
44
|
-
|
|
45
|
-
|
|
44
|
+
payload.context.request &&
|
|
45
|
+
payload.context.request.cookies
|
|
46
46
|
) {
|
|
47
47
|
cookiesToRedact.forEach((sc) => {
|
|
48
48
|
if (sc in payload.context.request.cookies) {
|
package/lib/create.js
ADDED
|
@@ -0,0 +1,24 @@
|
|
|
1
|
+
const { name, version, devDependencies } = require('../package.json');
|
|
2
|
+
|
|
3
|
+
/** @type {import('@gasket/core').HookHandler<'create'>} */
|
|
4
|
+
module.exports = function create(gasket, { pkg, files, gasketConfig }) {
|
|
5
|
+
const generatorDir = `${__dirname}/../generator`;
|
|
6
|
+
|
|
7
|
+
gasketConfig.addPlugin('pluginElasticApm', name);
|
|
8
|
+
|
|
9
|
+
pkg.add('dependencies', {
|
|
10
|
+
[name]: `^${version}`,
|
|
11
|
+
'dotenv': devDependencies.dotenv,
|
|
12
|
+
'elastic-apm-node': devDependencies['elastic-apm-node']
|
|
13
|
+
});
|
|
14
|
+
|
|
15
|
+
pkg.extend((current) => {
|
|
16
|
+
return {
|
|
17
|
+
scripts: {
|
|
18
|
+
start: `NODE_OPTIONS=--import=./setup.js ${current.scripts.start}`
|
|
19
|
+
}
|
|
20
|
+
};
|
|
21
|
+
});
|
|
22
|
+
|
|
23
|
+
files.add(`${generatorDir}/*`);
|
|
24
|
+
};
|
package/lib/index.d.ts
CHANGED
|
@@ -1,9 +1,8 @@
|
|
|
1
|
-
import type {
|
|
2
|
-
import type {
|
|
3
|
-
import type {
|
|
4
|
-
import type { GasketData } from '@gasket/data';
|
|
1
|
+
import type { AgentConfigOptions, Transaction, Payload, Agent } from 'elastic-apm-node';
|
|
2
|
+
import type { GasketConfig, Plugin, MaybeAsync } from '@gasket/core';
|
|
3
|
+
import type { RequestLike, GasketRequest } from '@gasket/request';
|
|
5
4
|
|
|
6
|
-
export function filterSensitiveCookies(config: GasketConfig):
|
|
5
|
+
export function filterSensitiveCookies(config: GasketConfig): (Payload) => Payload;
|
|
7
6
|
|
|
8
7
|
export interface ExtendedAgentConfigOptions extends AgentConfigOptions {
|
|
9
8
|
sensitiveCookies?: Array<string>;
|
|
@@ -18,26 +17,22 @@ declare module '@gasket/core' {
|
|
|
18
17
|
apm?: Agent;
|
|
19
18
|
}
|
|
20
19
|
|
|
20
|
+
export interface GasketActions {
|
|
21
|
+
getApmTransaction(
|
|
22
|
+
req: RequestLike
|
|
23
|
+
): Promise<Transaction | void>
|
|
24
|
+
}
|
|
25
|
+
|
|
21
26
|
export interface HookExecTypes {
|
|
22
27
|
apmTransaction(
|
|
23
28
|
transaction: Transaction,
|
|
24
|
-
|
|
25
|
-
req:
|
|
26
|
-
res: ServerResponse & {
|
|
27
|
-
locals?: {
|
|
28
|
-
gasketData: GasketData & {
|
|
29
|
-
locale?: string;
|
|
30
|
-
};
|
|
31
|
-
};
|
|
32
|
-
};
|
|
29
|
+
context: {
|
|
30
|
+
req: GasketRequest;
|
|
33
31
|
}
|
|
34
32
|
): MaybeAsync<void>;
|
|
35
33
|
}
|
|
36
34
|
}
|
|
37
35
|
|
|
38
|
-
|
|
39
|
-
|
|
40
|
-
|
|
41
|
-
description: '',
|
|
42
|
-
hooks: {}
|
|
43
|
-
};
|
|
36
|
+
declare const plugin: Plugin;
|
|
37
|
+
|
|
38
|
+
export default plugin;
|
package/lib/index.js
CHANGED
|
@@ -1,14 +1,13 @@
|
|
|
1
1
|
/// <reference types="create-gasket-app" />
|
|
2
2
|
/// <reference types="@gasket/plugin-metadata" />
|
|
3
3
|
|
|
4
|
-
const
|
|
5
|
-
const
|
|
4
|
+
const actions = require('./actions');
|
|
5
|
+
const create = require('./create');
|
|
6
6
|
const configure = require('./configure');
|
|
7
7
|
const {
|
|
8
8
|
name,
|
|
9
9
|
version,
|
|
10
|
-
description
|
|
11
|
-
devDependencies
|
|
10
|
+
description
|
|
12
11
|
} = require('../package.json');
|
|
13
12
|
|
|
14
13
|
/** @type {import('@gasket/core').Plugin} */
|
|
@@ -16,30 +15,20 @@ const plugin = {
|
|
|
16
15
|
name,
|
|
17
16
|
version,
|
|
18
17
|
description,
|
|
18
|
+
actions,
|
|
19
19
|
hooks: {
|
|
20
20
|
configure,
|
|
21
|
-
|
|
22
|
-
create: {
|
|
23
|
-
timing: {
|
|
24
|
-
after: ['@gasket/plugin-start']
|
|
25
|
-
},
|
|
26
|
-
handler(gasket, { pkg, files }) {
|
|
27
|
-
const generatorDir = `${__dirname}/../generator`;
|
|
28
|
-
|
|
29
|
-
pkg.add('dependencies', {
|
|
30
|
-
'elastic-apm-node': devDependencies['elastic-apm-node']
|
|
31
|
-
});
|
|
32
|
-
pkg.add('scripts', {
|
|
33
|
-
start: 'gasket start --require ./setup.js'
|
|
34
|
-
});
|
|
35
|
-
|
|
36
|
-
files.add(`${generatorDir}/*`);
|
|
37
|
-
}
|
|
38
|
-
},
|
|
39
|
-
middleware,
|
|
21
|
+
create,
|
|
40
22
|
metadata(gasket, meta) {
|
|
41
23
|
return {
|
|
42
24
|
...meta,
|
|
25
|
+
actions: [
|
|
26
|
+
{
|
|
27
|
+
name: 'getApmTransaction',
|
|
28
|
+
description: 'Get the APM transaction data',
|
|
29
|
+
link: 'README.md#getApmTransaction'
|
|
30
|
+
}
|
|
31
|
+
],
|
|
43
32
|
configurations: [
|
|
44
33
|
{
|
|
45
34
|
name: 'elasticAPM',
|
package/package.json
CHANGED
|
@@ -1,24 +1,12 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@gasket/plugin-elastic-apm",
|
|
3
|
-
"version": "7.3.
|
|
3
|
+
"version": "7.3.1",
|
|
4
4
|
"description": "Adds Elastic APM instrumentation to your application",
|
|
5
5
|
"main": "lib/index.js",
|
|
6
6
|
"types": "lib/index.d.ts",
|
|
7
7
|
"files": [
|
|
8
8
|
"lib"
|
|
9
9
|
],
|
|
10
|
-
"scripts": {
|
|
11
|
-
"lint": "eslint .",
|
|
12
|
-
"lint:fix": "npm run lint -- --fix",
|
|
13
|
-
"test": "npm run test:runner",
|
|
14
|
-
"test:runner": "jest test/*.test.js",
|
|
15
|
-
"test:watch": "npm run test:runner -- --watch",
|
|
16
|
-
"test:coverage": "npm run test:runner -- --coverage --coverageReporters text",
|
|
17
|
-
"posttest": "npm run lint && npm run typecheck",
|
|
18
|
-
"report": "npm run test:runner -- --coverage --coverageReporters lcov",
|
|
19
|
-
"typecheck": "tsc",
|
|
20
|
-
"typecheck:watch": "tsc --watch"
|
|
21
|
-
},
|
|
22
10
|
"repository": {
|
|
23
11
|
"type": "git",
|
|
24
12
|
"url": "git+ssh://git@github.com/godaddy/gasket.git"
|
|
@@ -33,25 +21,31 @@
|
|
|
33
21
|
"plugin"
|
|
34
22
|
],
|
|
35
23
|
"author": "GoDaddy Operating Company, LLC",
|
|
36
|
-
"maintainers": [
|
|
37
|
-
"Keith Bartholomew <kbartholomew@godaddy.com>"
|
|
38
|
-
],
|
|
39
24
|
"license": "MIT",
|
|
40
25
|
"bugs": {
|
|
41
26
|
"url": "https://github.com/godaddy/gasket/issues"
|
|
42
27
|
},
|
|
43
28
|
"homepage": "https://github.com/godaddy/gasket/tree/main/packages/gasket-plugin-elastic-apm",
|
|
29
|
+
"dependencies": {
|
|
30
|
+
"@gasket/request": "^7.3.1"
|
|
31
|
+
},
|
|
44
32
|
"devDependencies": {
|
|
45
|
-
"@gasket/core": "^7.3.
|
|
46
|
-
"
|
|
47
|
-
"
|
|
48
|
-
"
|
|
49
|
-
"
|
|
50
|
-
"
|
|
51
|
-
"
|
|
33
|
+
"@gasket/core": "^7.3.1",
|
|
34
|
+
"@gasket/plugin-metadata": "^7.3.2",
|
|
35
|
+
"@types/jest": "^29.5.14",
|
|
36
|
+
"@types/node": "^20.17.19",
|
|
37
|
+
"create-gasket-app": "^7.3.2",
|
|
38
|
+
"cross-env": "^7.0.3",
|
|
39
|
+
"dotenv": "^16.4.7",
|
|
40
|
+
"elastic-apm-node": "^4.11.0",
|
|
41
|
+
"eslint": "^8.57.1",
|
|
42
|
+
"eslint-config-godaddy": "^7.1.1",
|
|
43
|
+
"eslint-config-godaddy-typescript": "^4.0.3",
|
|
44
|
+
"eslint-plugin-jest": "^28.11.0",
|
|
45
|
+
"eslint-plugin-unicorn": "^55.0.0",
|
|
52
46
|
"jest": "^29.7.0",
|
|
53
47
|
"nyc": "^15.1.0",
|
|
54
|
-
"typescript": "^5.
|
|
48
|
+
"typescript": "^5.7.3"
|
|
55
49
|
},
|
|
56
50
|
"eslintConfig": {
|
|
57
51
|
"extends": [
|
|
@@ -65,10 +59,32 @@
|
|
|
65
59
|
],
|
|
66
60
|
"rules": {
|
|
67
61
|
"unicorn/filename-case": "error"
|
|
68
|
-
}
|
|
62
|
+
},
|
|
63
|
+
"overrides": [
|
|
64
|
+
{
|
|
65
|
+
"files": [
|
|
66
|
+
"lib/*.ts"
|
|
67
|
+
],
|
|
68
|
+
"extends": [
|
|
69
|
+
"godaddy-typescript"
|
|
70
|
+
],
|
|
71
|
+
"rules": {
|
|
72
|
+
"jsdoc/*": "off"
|
|
73
|
+
}
|
|
74
|
+
}
|
|
75
|
+
]
|
|
69
76
|
},
|
|
70
77
|
"jest": {
|
|
71
78
|
"testEnvironment": "node"
|
|
72
79
|
},
|
|
73
|
-
"
|
|
74
|
-
|
|
80
|
+
"scripts": {
|
|
81
|
+
"lint": "eslint .",
|
|
82
|
+
"lint:fix": "pnpm run lint --fix",
|
|
83
|
+
"test": "cross-env NODE_OPTIONS='--unhandled-rejections=strict' jest",
|
|
84
|
+
"test:watch": "pnpm run test --watch",
|
|
85
|
+
"test:coverage": "pnpm run test --coverage",
|
|
86
|
+
"posttest": "pnpm run lint && pnpm run typecheck",
|
|
87
|
+
"typecheck": "tsc",
|
|
88
|
+
"typecheck:watch": "tsc --watch"
|
|
89
|
+
}
|
|
90
|
+
}
|
package/lib/middleware.js
DELETED
|
@@ -1,40 +0,0 @@
|
|
|
1
|
-
/// <reference types="@gasket/plugin-express" />
|
|
2
|
-
|
|
3
|
-
/**
|
|
4
|
-
* Middleware for customizing transactions
|
|
5
|
-
* @param {import('@gasket/core').Gasket} gasket - The Gasket engine
|
|
6
|
-
* @param {import('http').IncomingMessage} req - The HTTP request being handled
|
|
7
|
-
* @param {import('http').ServerResponse} res - The server response
|
|
8
|
-
*/
|
|
9
|
-
async function customizeTransaction(gasket, req, res) {
|
|
10
|
-
const apm = gasket.apm;
|
|
11
|
-
|
|
12
|
-
if (!apm?.isStarted()) {
|
|
13
|
-
return;
|
|
14
|
-
}
|
|
15
|
-
|
|
16
|
-
const transaction = apm.currentTransaction;
|
|
17
|
-
if (!transaction) {
|
|
18
|
-
return;
|
|
19
|
-
}
|
|
20
|
-
|
|
21
|
-
await gasket.exec('apmTransaction', transaction, { req, res });
|
|
22
|
-
}
|
|
23
|
-
|
|
24
|
-
/**
|
|
25
|
-
* Add middleware to gather config details
|
|
26
|
-
* @type {import('@gasket/core').HookHandler<'middleware'>}
|
|
27
|
-
*/
|
|
28
|
-
module.exports = function middleware(gasket) {
|
|
29
|
-
return (
|
|
30
|
-
gasket.apm &&
|
|
31
|
-
async function apmTransactionMiddleware(req, res, next) {
|
|
32
|
-
try {
|
|
33
|
-
customizeTransaction(gasket, req, res);
|
|
34
|
-
} catch (error) {
|
|
35
|
-
return next(error);
|
|
36
|
-
}
|
|
37
|
-
next();
|
|
38
|
-
}
|
|
39
|
-
);
|
|
40
|
-
};
|
package/lib/preboot.js
DELETED
|
@@ -1,29 +0,0 @@
|
|
|
1
|
-
/// <reference types="@gasket/plugin-start" />
|
|
2
|
-
/// <reference types="@gasket/plugin-logger" />
|
|
3
|
-
|
|
4
|
-
const { filterSensitiveCookies } = require('./cookies');
|
|
5
|
-
|
|
6
|
-
/** @type {import('@gasket/core').HookHandler<'preboot'>} */
|
|
7
|
-
module.exports = async function preboot(gasket) {
|
|
8
|
-
const { config, logger, command } = gasket;
|
|
9
|
-
|
|
10
|
-
if (command && command.id === 'local') return;
|
|
11
|
-
|
|
12
|
-
/**
|
|
13
|
-
* @type {import('elastic-apm-node')}
|
|
14
|
-
* Note: Prefer app-level dependency in case of duplicates
|
|
15
|
-
*/
|
|
16
|
-
const apm = require(require.resolve('elastic-apm-node', {
|
|
17
|
-
paths: [config.root, __dirname]
|
|
18
|
-
}));
|
|
19
|
-
|
|
20
|
-
if (!apm.isStarted()) {
|
|
21
|
-
logger.warn(
|
|
22
|
-
'Elastic APM agent is not started. Use `--require ./setup.js`'
|
|
23
|
-
);
|
|
24
|
-
}
|
|
25
|
-
|
|
26
|
-
apm.addFilter(filterSensitiveCookies(config));
|
|
27
|
-
|
|
28
|
-
gasket.apm = apm;
|
|
29
|
-
};
|