@digitraffic/common 2022.11.23-2 → 2022.11.23-test-2
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/dist/aws/infra/api/integration.d.ts +1 -1
- package/dist/aws/infra/api/integration.js +4 -8
- package/dist/aws/infra/api/response.d.ts +3 -9
- package/dist/aws/infra/api/response.js +18 -49
- package/dist/aws/infra/api/responses.d.ts +0 -8
- package/dist/aws/infra/api/responses.js +0 -8
- package/dist/aws/infra/api/static-integration.js +6 -12
- package/dist/aws/infra/canaries/canary-parameters.d.ts +2 -2
- package/dist/aws/infra/canaries/url-checker.d.ts +2 -2
- package/dist/aws/infra/stack/lambda-configs.d.ts +3 -3
- package/dist/aws/infra/stack/monitoredfunction.d.ts +2 -2
- package/dist/aws/infra/stack/monitoredfunction.js +31 -31
- package/dist/aws/runtime/secrets/dbsecret.d.ts +9 -8
- package/dist/aws/runtime/secrets/dbsecret.js +4 -4
- package/dist/aws/runtime/secrets/secret-holder.d.ts +3 -2
- package/dist/aws/runtime/secrets/secret.d.ts +1 -1
- package/dist/aws/types/proxytypes.d.ts +2 -2
- package/dist/database/database.d.ts +2 -2
- package/dist/marine/rtz.d.ts +10 -10
- package/dist/types/either.d.ts +3 -3
- package/package.json +33 -22
- package/src/aws/infra/api/integration.ts +14 -30
- package/src/aws/infra/api/response.ts +26 -107
- package/src/aws/infra/api/responses.ts +0 -8
- package/src/aws/infra/api/static-integration.ts +14 -48
- package/src/aws/runtime/secrets/dbsecret.ts +54 -23
- package/src/aws/runtime/secrets/secret-holder.ts +3 -6
- package/src/database/database.ts +1 -1
- package/dist/aws/infra/api/integration.js.map +0 -1
- package/dist/aws/infra/api/response.js.map +0 -1
- package/dist/aws/infra/api/responses.js.map +0 -1
- package/dist/aws/infra/api/static-integration.js.map +0 -1
- package/dist/aws/infra/canaries/canary-alarm.js.map +0 -1
- package/dist/aws/infra/canaries/canary-keys.js.map +0 -1
- package/dist/aws/infra/canaries/canary-parameters.js.map +0 -1
- package/dist/aws/infra/canaries/canary-role.js.map +0 -1
- package/dist/aws/infra/canaries/canary.js.map +0 -1
- package/dist/aws/infra/canaries/database-canary.js.map +0 -1
- package/dist/aws/infra/canaries/database-checker.js.map +0 -1
- package/dist/aws/infra/canaries/url-canary.js.map +0 -1
- package/dist/aws/infra/canaries/url-checker.js.map +0 -1
- package/dist/aws/infra/documentation.js.map +0 -1
- package/dist/aws/infra/import-util.js.map +0 -1
- package/dist/aws/infra/scheduler.js.map +0 -1
- package/dist/aws/infra/security-rule.js.map +0 -1
- package/dist/aws/infra/sqs-integration.js.map +0 -1
- package/dist/aws/infra/sqs-queue.js.map +0 -1
- package/dist/aws/infra/stack/lambda-configs.js.map +0 -1
- package/dist/aws/infra/stack/monitoredfunction.js.map +0 -1
- package/dist/aws/infra/stack/rest_apis.js.map +0 -1
- package/dist/aws/infra/stack/stack-checking-aspect.js.map +0 -1
- package/dist/aws/infra/stack/stack.js.map +0 -1
- package/dist/aws/infra/stack/subscription.js.map +0 -1
- package/dist/aws/infra/stacks/db-dns-stack.js.map +0 -1
- package/dist/aws/infra/stacks/db-proxy-stack.js.map +0 -1
- package/dist/aws/infra/stacks/db-stack.js.map +0 -1
- package/dist/aws/infra/stacks/intra-stack-configuration.js.map +0 -1
- package/dist/aws/infra/stacks/network-stack.js.map +0 -1
- package/dist/aws/infra/usage-plans.js.map +0 -1
- package/dist/aws/runtime/apikey.js.map +0 -1
- package/dist/aws/runtime/digitraffic-integration-response.js.map +0 -1
- package/dist/aws/runtime/environment.js.map +0 -1
- package/dist/aws/runtime/messaging.js.map +0 -1
- package/dist/aws/runtime/s3.js.map +0 -1
- package/dist/aws/runtime/secrets/dbsecret.js.map +0 -1
- package/dist/aws/runtime/secrets/proxy-holder.js.map +0 -1
- package/dist/aws/runtime/secrets/rds-holder.js.map +0 -1
- package/dist/aws/runtime/secrets/secret-holder.js.map +0 -1
- package/dist/aws/runtime/secrets/secret.js.map +0 -1
- package/dist/aws/types/errors.js.map +0 -1
- package/dist/aws/types/lambda-response.js.map +0 -1
- package/dist/aws/types/mediatypes.js.map +0 -1
- package/dist/aws/types/model-with-reference.js.map +0 -1
- package/dist/aws/types/proxytypes.js.map +0 -1
- package/dist/aws/types/tags.js.map +0 -1
- package/dist/database/cached.js.map +0 -1
- package/dist/database/database.js.map +0 -1
- package/dist/database/last-updated.js.map +0 -1
- package/dist/database/models.js.map +0 -1
- package/dist/marine/id_utils.js.map +0 -1
- package/dist/marine/rtz.js.map +0 -1
- package/dist/test/asserter.js.map +0 -1
- package/dist/test/db-testutils.js.map +0 -1
- package/dist/test/httpserver.js.map +0 -1
- package/dist/test/secret.js.map +0 -1
- package/dist/test/secrets-manager.js.map +0 -1
- package/dist/test/testutils.js.map +0 -1
- package/dist/types/either.js.map +0 -1
- package/dist/types/input-error.js.map +0 -1
- package/dist/types/language.js.map +0 -1
- package/dist/types/traffictype.js.map +0 -1
- package/dist/types/validator.js.map +0 -1
- package/dist/utils/api-model.js.map +0 -1
- package/dist/utils/base64.js.map +0 -1
- package/dist/utils/date-utils.js.map +0 -1
- package/dist/utils/geojson-types.js.map +0 -1
- package/dist/utils/geometry.js.map +0 -1
- package/dist/utils/retry.js.map +0 -1
- package/dist/utils/slack.js.map +0 -1
- package/dist/utils/utils.js.map +0 -1
package/package.json
CHANGED
@@ -1,6 +1,6 @@
|
|
1
1
|
{
|
2
2
|
"name": "@digitraffic/common",
|
3
|
-
"version": "2022.11.23-2",
|
3
|
+
"version": "2022.11.23-test-2",
|
4
4
|
"description": "",
|
5
5
|
"repository": {
|
6
6
|
"type": "git",
|
@@ -10,36 +10,41 @@
|
|
10
10
|
"node": ">=14 <17",
|
11
11
|
"yarn": ">1.2 <2"
|
12
12
|
},
|
13
|
-
"scripts": {
|
14
|
-
"build": "tsc",
|
15
|
-
"lint": "eslint --cache .",
|
16
|
-
"eslint-report": "eslint . --format html",
|
17
|
-
"clean": "rimraf dist output",
|
18
|
-
"test": "jest --detectOpenHandles --forceExit --coverage --coverageDirectory=output/coverage/jest",
|
19
|
-
"prepare": "husky install",
|
20
|
-
"prepublishOnly": "yarn clean && yarn build && yarn test"
|
21
|
-
},
|
22
13
|
"license": "EUPL-1.2",
|
23
14
|
"private": false,
|
24
15
|
"files": [
|
25
16
|
"dist/**/*.js",
|
17
|
+
"dist/**/*.d.ts",
|
26
18
|
"src/**/*.ts"
|
27
19
|
],
|
28
|
-
"
|
29
|
-
"
|
20
|
+
"peerDependencies": {
|
21
|
+
"pg-promise": "^10.12.0",
|
22
|
+
"spex": "^3.0.0",
|
23
|
+
"constructs": "^10.1.131",
|
24
|
+
"@aws-cdk/aws-synthetics-alpha": "^2.50.0-alpha.0",
|
30
25
|
"@types/geojson": "^7946.0.10",
|
31
|
-
"aws-cdk-lib": "2.
|
32
|
-
"aws-sdk": "2.1241.0",
|
26
|
+
"aws-cdk-lib": "^2.50.0",
|
27
|
+
"aws-sdk": "^2.1241.0",
|
33
28
|
"axios": "^0.21.1",
|
34
|
-
"change-case": "4.1.2",
|
35
|
-
"constructs": "10.1.131",
|
29
|
+
"change-case": "^4.1.2",
|
36
30
|
"geojson-validation": "^1.0.2",
|
37
31
|
"moment": "^2.29.4",
|
38
32
|
"node-ttl": "^0.2.0",
|
39
|
-
"pg-native": "^3.0.1"
|
40
|
-
"pg-promise": "^10.12.0"
|
33
|
+
"pg-native": "^3.0.1"
|
41
34
|
},
|
42
35
|
"devDependencies": {
|
36
|
+
"@aws-cdk/aws-synthetics-alpha": "2.50.0-alpha.0",
|
37
|
+
"@types/geojson": "^7946.0.10",
|
38
|
+
"aws-cdk-lib": "^2.50.0",
|
39
|
+
"aws-sdk": "^2.1241.0",
|
40
|
+
"axios": "^0.21.1",
|
41
|
+
"change-case": "^4.1.2",
|
42
|
+
"constructs": "^10.1.131",
|
43
|
+
"geojson-validation": "^1.0.2",
|
44
|
+
"moment": "^2.29.4",
|
45
|
+
"node-ttl": "^0.2.0",
|
46
|
+
"pg-native": "^3.0.1",
|
47
|
+
"pg-promise": "^10.12.0",
|
43
48
|
"@types/aws-lambda": "^8.10.106",
|
44
49
|
"@types/jest": "^29.0.3",
|
45
50
|
"@types/node": "^18.7.23",
|
@@ -49,7 +54,6 @@
|
|
49
54
|
"@typescript-eslint/parser": "^5.39.0",
|
50
55
|
"eslint": "^8.24.0",
|
51
56
|
"eslint-config-prettier": "^8.5.0",
|
52
|
-
"eslint-plugin-deprecation": "1.3.3",
|
53
57
|
"husky": ">=6",
|
54
58
|
"jest": "^29.1.1",
|
55
59
|
"jest-junit": "^14.0.1",
|
@@ -58,8 +62,8 @@
|
|
58
62
|
"ramda": "^0.28.0",
|
59
63
|
"rimraf": "^3.0.2",
|
60
64
|
"sinon": "^14.0.0",
|
61
|
-
"ts-jest": "^29.0.
|
62
|
-
"typescript": "^4.
|
65
|
+
"ts-jest": "^29.0.2",
|
66
|
+
"typescript": "^4.7.4"
|
63
67
|
},
|
64
68
|
"externals": [
|
65
69
|
"aws-sdk",
|
@@ -67,5 +71,12 @@
|
|
67
71
|
],
|
68
72
|
"lint-staged": {
|
69
73
|
"*.{js,ts,css,md,yml,yaml,json}": "prettier --write"
|
74
|
+
},
|
75
|
+
"scripts": {
|
76
|
+
"build": "tsc",
|
77
|
+
"lint": "eslint --cache .",
|
78
|
+
"eslint-report": "eslint . --format html",
|
79
|
+
"clean": "rimraf dist output",
|
80
|
+
"test": "jest --detectOpenHandles --forceExit --coverage --coverageDirectory=output/coverage/jest"
|
70
81
|
}
|
71
|
-
}
|
82
|
+
}
|
@@ -1,17 +1,13 @@
|
|
1
|
-
import {
|
2
|
-
|
3
|
-
|
4
|
-
|
5
|
-
} from "aws-cdk-lib/aws-apigateway";
|
6
|
-
import { IFunction } from "aws-cdk-lib/aws-lambda";
|
7
|
-
import { MediaType } from "../../types/mediatypes";
|
8
|
-
import { DigitrafficIntegrationResponse } from "../../runtime/digitraffic-integration-response";
|
1
|
+
import {IntegrationResponse, LambdaIntegration, PassthroughBehavior} from "aws-cdk-lib/aws-apigateway";
|
2
|
+
import {IFunction} from "aws-cdk-lib/aws-lambda";
|
3
|
+
import {MediaType} from "../../types/mediatypes";
|
4
|
+
import {DigitrafficIntegrationResponse} from "../../runtime/digitraffic-integration-response";
|
9
5
|
|
10
|
-
type ParameterType =
|
6
|
+
type ParameterType = 'path' | 'querystring';
|
11
7
|
|
12
8
|
interface ApiParameter {
|
13
|
-
type: ParameterType
|
14
|
-
name: string
|
9
|
+
type: ParameterType
|
10
|
+
name: string
|
15
11
|
}
|
16
12
|
|
17
13
|
export class DigitrafficIntegration {
|
@@ -26,15 +22,13 @@ export class DigitrafficIntegration {
|
|
26
22
|
}
|
27
23
|
|
28
24
|
addPathParameter(...names: string[]): DigitrafficIntegration {
|
29
|
-
names.forEach(
|
25
|
+
names.forEach(name => this.parameters.push({type: 'path', name}));
|
30
26
|
|
31
27
|
return this;
|
32
28
|
}
|
33
29
|
|
34
30
|
addQueryParameter(...names: string[]): DigitrafficIntegration {
|
35
|
-
names.forEach((name)
|
36
|
-
this.parameters.push({ type: "querystring", name })
|
37
|
-
);
|
31
|
+
names.forEach(name => this.parameters.push({type: 'querystring', name}));
|
38
32
|
|
39
33
|
return this;
|
40
34
|
}
|
@@ -45,14 +39,8 @@ export class DigitrafficIntegration {
|
|
45
39
|
return new LambdaIntegration(this.lambda, {
|
46
40
|
proxy: false,
|
47
41
|
integrationResponses,
|
48
|
-
requestParameters:
|
49
|
-
|
50
|
-
? undefined
|
51
|
-
: this.createRequestParameters(),
|
52
|
-
requestTemplates:
|
53
|
-
this.parameters.length == 0
|
54
|
-
? undefined
|
55
|
-
: this.createRequestTemplates(),
|
42
|
+
requestParameters: this.parameters.length == 0 ? undefined : this.createRequestParameters(),
|
43
|
+
requestTemplates: this.parameters.length == 0 ? undefined : this.createRequestTemplates(),
|
56
44
|
passthroughBehavior: PassthroughBehavior.WHEN_NO_MATCH,
|
57
45
|
});
|
58
46
|
}
|
@@ -61,9 +49,7 @@ export class DigitrafficIntegration {
|
|
61
49
|
const requestParameters: Record<string, string> = {};
|
62
50
|
|
63
51
|
this.parameters.forEach((parameter: ApiParameter) => {
|
64
|
-
requestParameters[
|
65
|
-
`integration.request.${parameter.type}.${parameter.name}`
|
66
|
-
] = `method.request.${parameter.type}.${parameter.name}`;
|
52
|
+
requestParameters[`integration.request.${parameter.type}.${parameter.name}`] = `method.request.${parameter.type}.${parameter.name}`;
|
67
53
|
});
|
68
54
|
|
69
55
|
return requestParameters;
|
@@ -73,9 +59,7 @@ export class DigitrafficIntegration {
|
|
73
59
|
const requestJson: Record<string, string> = {};
|
74
60
|
|
75
61
|
this.parameters.forEach((parameter: ApiParameter) => {
|
76
|
-
requestJson[
|
77
|
-
parameter.name
|
78
|
-
] = `$util.escapeJavaScript($input.params('${parameter.name}'))`;
|
62
|
+
requestJson[parameter.name] = `$util.escapeJavaScript($input.params('${parameter.name}'))`;
|
79
63
|
});
|
80
64
|
|
81
65
|
return {
|
@@ -86,4 +70,4 @@ export class DigitrafficIntegration {
|
|
86
70
|
createResponses(): IntegrationResponse[] {
|
87
71
|
return [DigitrafficIntegrationResponse.ok(this.mediaType)];
|
88
72
|
}
|
89
|
-
}
|
73
|
+
}
|
@@ -1,12 +1,5 @@
|
|
1
|
-
import
|
2
|
-
import {
|
3
|
-
JsonSchemaType,
|
4
|
-
JsonSchemaVersion,
|
5
|
-
JsonSchema,
|
6
|
-
MethodResponse,
|
7
|
-
Model,
|
8
|
-
} from "aws-cdk-lib/aws-apigateway";
|
9
|
-
import { IModel } from "aws-cdk-lib/aws-apigateway/lib/model";
|
1
|
+
import apigateway = require('aws-cdk-lib/aws-apigateway');
|
2
|
+
import {MediaType} from "../../types/mediatypes";
|
10
3
|
|
11
4
|
/**
|
12
5
|
* This is velocity-script, that assumes the response to be LambdaResponse(status and body).
|
@@ -30,119 +23,45 @@ $inputRoot.body
|
|
30
23
|
|
31
24
|
const BODY_FROM_INPUT_PATH = "$input.path('$').body";
|
32
25
|
|
33
|
-
|
34
|
-
const messageSchema: JsonSchema = {
|
35
|
-
schema: JsonSchemaVersion.DRAFT4,
|
36
|
-
type: JsonSchemaType.OBJECT,
|
37
|
-
description:
|
26
|
+
// DEPRECATED
|
27
|
+
const messageSchema: apigateway.JsonSchema = {
|
28
|
+
schema: apigateway.JsonSchemaVersion.DRAFT4,
|
29
|
+
type: apigateway.JsonSchemaType.OBJECT,
|
30
|
+
description: 'Response with message',
|
38
31
|
properties: {
|
39
32
|
message: {
|
40
|
-
type: JsonSchemaType.STRING,
|
41
|
-
description:
|
33
|
+
type: apigateway.JsonSchemaType.STRING,
|
34
|
+
description: 'Response message',
|
42
35
|
},
|
43
36
|
},
|
44
37
|
};
|
45
38
|
|
46
|
-
|
39
|
+
// DEPRECATED
|
47
40
|
export const MessageModel = {
|
48
41
|
contentType: MediaType.APPLICATION_JSON,
|
49
|
-
modelName:
|
42
|
+
modelName: 'MessageResponseModel',
|
50
43
|
schema: messageSchema,
|
51
44
|
};
|
52
45
|
|
53
|
-
const NotFoundMessage =
|
54
|
-
export const NotFoundResponse = JSON.stringify({
|
46
|
+
const NotFoundMessage = 'Not found';
|
47
|
+
export const NotFoundResponse = JSON.stringify({message: NotFoundMessage});
|
55
48
|
|
56
|
-
const InternalServerErrorMessage =
|
57
|
-
const InternalServerErrorResponse = JSON.stringify({
|
58
|
-
message: InternalServerErrorMessage,
|
59
|
-
});
|
49
|
+
const InternalServerErrorMessage = 'Error';
|
50
|
+
const InternalServerErrorResponse = JSON.stringify({message: InternalServerErrorMessage});
|
60
51
|
|
61
|
-
const BadRequestMessage =
|
62
|
-
const BadRequestResponse = JSON.stringify({
|
52
|
+
const BadRequestMessage = 'Bad request';
|
53
|
+
const BadRequestResponse = JSON.stringify({message: BadRequestMessage});
|
63
54
|
|
64
|
-
|
65
|
-
export const
|
66
|
-
|
67
|
-
|
68
|
-
);
|
69
|
-
/// @deprecated
|
70
|
-
export const NotFoundResponseTemplate = createResponses(
|
71
|
-
MediaType.APPLICATION_JSON,
|
72
|
-
NotFoundResponse
|
73
|
-
);
|
74
|
-
/// @deprecated
|
75
|
-
export const XmlResponseTemplate = createResponses(
|
76
|
-
MediaType.APPLICATION_XML,
|
77
|
-
BODY_FROM_INPUT_PATH
|
78
|
-
);
|
79
|
-
/// @deprecated
|
80
|
-
export const InternalServerErrorResponseTemplate = createResponses(
|
81
|
-
MediaType.APPLICATION_JSON,
|
82
|
-
InternalServerErrorResponse
|
83
|
-
);
|
55
|
+
export const BadRequestResponseTemplate = createResponses(MediaType.APPLICATION_JSON, BadRequestResponse);
|
56
|
+
export const NotFoundResponseTemplate = createResponses(MediaType.APPLICATION_JSON, NotFoundResponse);
|
57
|
+
export const XmlResponseTemplate = createResponses(MediaType.APPLICATION_XML, BODY_FROM_INPUT_PATH);
|
58
|
+
export const SvgResponseTemplate = createResponses(MediaType.IMAGE_SVG, BODY_FROM_INPUT_PATH);
|
59
|
+
export const InternalServerErrorResponseTemplate = createResponses(MediaType.APPLICATION_JSON, InternalServerErrorResponse);
|
84
60
|
|
85
|
-
|
86
|
-
|
87
|
-
key: MediaType,
|
88
|
-
value: T
|
89
|
-
): Record<string, T> {
|
90
|
-
return {
|
91
|
-
[key]: value,
|
92
|
-
};
|
93
|
-
}
|
94
|
-
|
95
|
-
export class DigitrafficMethodResponse {
|
96
|
-
static response(
|
97
|
-
statusCode: string,
|
98
|
-
model: IModel,
|
99
|
-
mediaType: MediaType,
|
100
|
-
disableCors = false
|
101
|
-
): MethodResponse {
|
102
|
-
return {
|
103
|
-
statusCode,
|
104
|
-
responseModels: {
|
105
|
-
[mediaType]: model,
|
106
|
-
},
|
107
|
-
responseParameters: disableCors
|
108
|
-
? {}
|
109
|
-
: {
|
110
|
-
"method.response.header.Access-Control-Allow-Origin":
|
111
|
-
true,
|
112
|
-
},
|
113
|
-
};
|
114
|
-
}
|
115
|
-
|
116
|
-
static response200(model: IModel, mediaType = MediaType.APPLICATION_JSON) {
|
117
|
-
return DigitrafficMethodResponse.response(
|
118
|
-
"200",
|
119
|
-
model,
|
120
|
-
mediaType,
|
121
|
-
false
|
122
|
-
);
|
123
|
-
}
|
61
|
+
export function createResponses<T>(key: MediaType, value: T): Record<string, T> {
|
62
|
+
const map: Record<string, T> = {};
|
124
63
|
|
125
|
-
|
126
|
-
model = Model.EMPTY_MODEL,
|
127
|
-
mediaType = MediaType.APPLICATION_JSON
|
128
|
-
) {
|
129
|
-
return DigitrafficMethodResponse.response(
|
130
|
-
"500",
|
131
|
-
model,
|
132
|
-
mediaType,
|
133
|
-
false
|
134
|
-
);
|
135
|
-
}
|
64
|
+
map[key] = value;
|
136
65
|
|
137
|
-
|
138
|
-
model = Model.EMPTY_MODEL,
|
139
|
-
mediaType = MediaType.APPLICATION_JSON
|
140
|
-
) {
|
141
|
-
return DigitrafficMethodResponse.response(
|
142
|
-
"400",
|
143
|
-
model,
|
144
|
-
mediaType,
|
145
|
-
false
|
146
|
-
);
|
147
|
-
}
|
66
|
+
return map;
|
148
67
|
}
|
@@ -52,9 +52,6 @@ export const RESPONSE_404_NOT_FOUND = {
|
|
52
52
|
responseTemplates: NotFoundResponseTemplate,
|
53
53
|
};
|
54
54
|
|
55
|
-
/**
|
56
|
-
* @deprecated Use DigitrafficMethodResponse
|
57
|
-
*/
|
58
55
|
export function methodResponse(
|
59
56
|
status: string,
|
60
57
|
contentType: MediaType,
|
@@ -68,9 +65,6 @@ export function methodResponse(
|
|
68
65
|
};
|
69
66
|
}
|
70
67
|
|
71
|
-
/**
|
72
|
-
* @deprecated Use DigitrafficMethodResponse
|
73
|
-
*/
|
74
68
|
export function corsMethod(response: MethodResponse): MethodResponse {
|
75
69
|
return {
|
76
70
|
...response,
|
@@ -95,8 +89,6 @@ interface IntegrationOptions {
|
|
95
89
|
* Creates a default Lambda integration for a REST API resource _root_
|
96
90
|
* @param lambdaFunction The Lambda function
|
97
91
|
* @param options Options
|
98
|
-
*
|
99
|
-
* @deprecated Use DigitrafficIntegration
|
100
92
|
*/
|
101
93
|
export function defaultIntegration(
|
102
94
|
lambdaFunction: AWSFunction,
|
@@ -1,17 +1,13 @@
|
|
1
|
-
import {
|
2
|
-
|
3
|
-
|
4
|
-
Resource,
|
5
|
-
} from "aws-cdk-lib/aws-apigateway";
|
6
|
-
import { MediaType } from "../../types/mediatypes";
|
7
|
-
import { corsMethod, RESPONSE_CORS_INTEGRATION } from "./responses";
|
1
|
+
import {MockIntegration, PassthroughBehavior, Resource} from "aws-cdk-lib/aws-apigateway";
|
2
|
+
import {MediaType} from "../../types/mediatypes";
|
3
|
+
import {corsMethod, RESPONSE_CORS_INTEGRATION} from "./responses";
|
8
4
|
|
9
5
|
const INTEGRATION_RESPONSE_200 = `{
|
10
6
|
"statusCode": 200
|
11
7
|
}`;
|
12
8
|
|
13
9
|
const METHOD_RESPONSE_200 = {
|
14
|
-
statusCode:
|
10
|
+
statusCode: '200',
|
15
11
|
};
|
16
12
|
|
17
13
|
/**
|
@@ -23,18 +19,9 @@ const METHOD_RESPONSE_200 = {
|
|
23
19
|
*/
|
24
20
|
export class DigitrafficStaticIntegration extends MockIntegration {
|
25
21
|
constructor(
|
26
|
-
resource: Resource,
|
27
|
-
mediaType: MediaType,
|
28
|
-
response: string,
|
29
|
-
enableCors = true,
|
30
|
-
apiKeyRequired = true
|
22
|
+
resource: Resource, mediaType: MediaType, response: string, enableCors = true, apiKeyRequired = true,
|
31
23
|
) {
|
32
|
-
const integrationResponse =
|
33
|
-
DigitrafficStaticIntegration.createIntegrationResponse(
|
34
|
-
response,
|
35
|
-
mediaType,
|
36
|
-
enableCors
|
37
|
-
);
|
24
|
+
const integrationResponse = DigitrafficStaticIntegration.createIntegrationResponse(response, mediaType, enableCors);
|
38
25
|
|
39
26
|
super({
|
40
27
|
passthroughBehavior: PassthroughBehavior.WHEN_NO_TEMPLATES,
|
@@ -44,53 +31,32 @@ export class DigitrafficStaticIntegration extends MockIntegration {
|
|
44
31
|
integrationResponses: [integrationResponse],
|
45
32
|
});
|
46
33
|
|
47
|
-
[
|
34
|
+
['GET', 'HEAD'].forEach((httpMethod) => {
|
48
35
|
resource.addMethod(httpMethod, this, {
|
49
36
|
apiKeyRequired,
|
50
|
-
methodResponses: [
|
51
|
-
DigitrafficStaticIntegration.createMethodResponse(
|
52
|
-
enableCors
|
53
|
-
),
|
54
|
-
],
|
37
|
+
methodResponses: [DigitrafficStaticIntegration.createMethodResponse(enableCors)],
|
55
38
|
});
|
56
39
|
});
|
57
40
|
}
|
58
41
|
|
59
|
-
static json<K>(
|
60
|
-
resource: Resource,
|
61
|
-
response: K,
|
62
|
-
enableCors = true,
|
63
|
-
apiKeyRequired = true
|
64
|
-
) {
|
42
|
+
static json<K>(resource: Resource, response: K, enableCors = true, apiKeyRequired = true) {
|
65
43
|
return new DigitrafficStaticIntegration(
|
66
|
-
resource,
|
67
|
-
MediaType.APPLICATION_JSON,
|
68
|
-
JSON.stringify(response),
|
69
|
-
enableCors,
|
70
|
-
apiKeyRequired
|
44
|
+
resource, MediaType.APPLICATION_JSON, JSON.stringify(response), enableCors, apiKeyRequired,
|
71
45
|
);
|
72
46
|
}
|
73
47
|
|
74
|
-
private static createIntegrationResponse(
|
75
|
-
response: string,
|
76
|
-
mediaType: MediaType,
|
77
|
-
enableCors: boolean
|
78
|
-
) {
|
48
|
+
private static createIntegrationResponse(response: string, mediaType: MediaType, enableCors: boolean) {
|
79
49
|
const integrationResponse = {
|
80
|
-
statusCode:
|
50
|
+
statusCode: '200',
|
81
51
|
responseTemplates: {
|
82
52
|
[mediaType]: response,
|
83
53
|
},
|
84
54
|
};
|
85
55
|
|
86
|
-
return enableCors
|
87
|
-
? { ...integrationResponse, ...RESPONSE_CORS_INTEGRATION }
|
88
|
-
: integrationResponse;
|
56
|
+
return enableCors ? {...integrationResponse, ...RESPONSE_CORS_INTEGRATION} : integrationResponse;
|
89
57
|
}
|
90
58
|
|
91
59
|
private static createMethodResponse(enableCors: boolean) {
|
92
|
-
return enableCors
|
93
|
-
? corsMethod(METHOD_RESPONSE_200)
|
94
|
-
: METHOD_RESPONSE_200;
|
60
|
+
return enableCors ? corsMethod(METHOD_RESPONSE_200) : METHOD_RESPONSE_200;
|
95
61
|
}
|
96
62
|
}
|
@@ -1,18 +1,24 @@
|
|
1
|
-
import {withSecret, withSecretAndPrefix} from "./secret";
|
1
|
+
import { GenericSecret, withSecret, withSecretAndPrefix } from "./secret";
|
2
2
|
|
3
3
|
export type DbSecret = {
|
4
|
-
readonly username: string
|
5
|
-
readonly password: string
|
6
|
-
readonly host: string
|
7
|
-
readonly ro_host: string
|
4
|
+
readonly username: string;
|
5
|
+
readonly password: string;
|
6
|
+
readonly host: string;
|
7
|
+
readonly ro_host: string;
|
8
8
|
};
|
9
9
|
|
10
10
|
export enum RdsProxySecretKey {
|
11
|
-
username = "username",
|
11
|
+
username = "username",
|
12
|
+
password = "password",
|
13
|
+
proxy_host = "proxy_host",
|
14
|
+
proxy_ro_host = "proxy_ro_host",
|
12
15
|
}
|
13
16
|
|
14
17
|
export enum RdsSecretKey {
|
15
|
-
username = "username",
|
18
|
+
username = "username",
|
19
|
+
password = "password",
|
20
|
+
host = "host",
|
21
|
+
ro_host = "ro_host",
|
16
22
|
}
|
17
23
|
|
18
24
|
export type RdsProxySecret = Record<RdsProxySecretKey, string>;
|
@@ -37,7 +43,7 @@ function setDbSecret(secret: DbSecret) {
|
|
37
43
|
// eslint-disable-next-line @typescript-eslint/no-explicit-any
|
38
44
|
let cachedSecret: any;
|
39
45
|
|
40
|
-
const missingSecretErrorText =
|
46
|
+
const missingSecretErrorText = "Missing or empty secretId";
|
41
47
|
|
42
48
|
/**
|
43
49
|
* You can give the following options for retrieving a secret:
|
@@ -48,13 +54,22 @@ const missingSecretErrorText = 'Missing or empty secretId';
|
|
48
54
|
|
49
55
|
*/
|
50
56
|
export type SecretOptions = {
|
51
|
-
readonly expectedKeys?: string[]
|
52
|
-
readonly prefix?: string
|
53
|
-
}
|
57
|
+
readonly expectedKeys?: string[];
|
58
|
+
readonly prefix?: string;
|
59
|
+
};
|
54
60
|
|
55
|
-
export type SecretToPromiseFunction<Secret, Response = void> = (
|
56
|
-
|
57
|
-
|
61
|
+
export type SecretToPromiseFunction<Secret, Response = void> = (
|
62
|
+
secret: Secret
|
63
|
+
) => Promise<Response> | void;
|
64
|
+
export type SecretFunction<Secret, Response = void> = (
|
65
|
+
secretId: string,
|
66
|
+
fn: SecretToPromiseFunction<Secret, Response>,
|
67
|
+
options?: SecretOptions
|
68
|
+
) => Promise<Response | void>;
|
69
|
+
export type EmptySecretFunction<Response = void> = SecretFunction<
|
70
|
+
DbSecret,
|
71
|
+
Response
|
72
|
+
>;
|
58
73
|
|
59
74
|
/**
|
60
75
|
* Run the given function with secret retrieved from Secrets Manager. Also injects database-credentials into environment.
|
@@ -66,7 +81,11 @@ export type EmptySecretFunction<Response = void> = SecretFunction<DbSecret, Resp
|
|
66
81
|
* @param {function} fn
|
67
82
|
* @param {SecretOptions} options
|
68
83
|
*/
|
69
|
-
export async function withDbSecret<Secret, Response>(
|
84
|
+
export async function withDbSecret<Secret, Response>(
|
85
|
+
secretId: string,
|
86
|
+
fn: SecretToPromiseFunction<Secret, Response>,
|
87
|
+
options?: SecretOptions
|
88
|
+
): Promise<Response | void> {
|
70
89
|
if (!secretId) {
|
71
90
|
console.error(missingSecretErrorText);
|
72
91
|
return Promise.reject(missingSecretErrorText);
|
@@ -81,9 +100,13 @@ export async function withDbSecret<Secret, Response>(secretId: string, fn: Secre
|
|
81
100
|
});
|
82
101
|
|
83
102
|
// then actual secret
|
84
|
-
await withSecretAndPrefix(
|
85
|
-
|
86
|
-
|
103
|
+
await withSecretAndPrefix(
|
104
|
+
secretId,
|
105
|
+
options.prefix,
|
106
|
+
(fetchedSecret: Secret) => {
|
107
|
+
cachedSecret = fetchedSecret;
|
108
|
+
}
|
109
|
+
);
|
87
110
|
} else {
|
88
111
|
await withSecret(secretId, (fetchedSecret: DbSecret) => {
|
89
112
|
setDbSecret(fetchedSecret);
|
@@ -97,7 +120,10 @@ export async function withDbSecret<Secret, Response>(secretId: string, fn: Secre
|
|
97
120
|
}
|
98
121
|
return fn(cachedSecret);
|
99
122
|
} catch (error) {
|
100
|
-
console.error(
|
123
|
+
console.error(
|
124
|
+
"method=withDbSecret Caught an error, refreshing secret",
|
125
|
+
error
|
126
|
+
);
|
101
127
|
// try to refetch secret in case it has changed
|
102
128
|
await withSecret(secretId, (fetchedSecret: DbSecret) => {
|
103
129
|
setDbSecret(fetchedSecret);
|
@@ -107,10 +133,15 @@ export async function withDbSecret<Secret, Response>(secretId: string, fn: Secre
|
|
107
133
|
}
|
108
134
|
}
|
109
135
|
|
110
|
-
export function checkExpectedSecretKeys<Secret>(
|
111
|
-
|
136
|
+
export function checkExpectedSecretKeys<Secret extends GenericSecret>(
|
137
|
+
keys: string[],
|
138
|
+
secret: Secret
|
139
|
+
) {
|
140
|
+
const missingKeys = keys.filter((key) => !(key in secret));
|
112
141
|
if (missingKeys.length) {
|
113
|
-
console.error(
|
114
|
-
|
142
|
+
console.error(
|
143
|
+
`method=checkExpectedSecretKeys secret didn't contain the key(s) ${missingKeys}`
|
144
|
+
);
|
145
|
+
throw new Error("Expected keys were not found");
|
115
146
|
}
|
116
147
|
}
|
@@ -23,7 +23,7 @@ const DEFAULT_CONFIGURATION = {
|
|
23
23
|
*
|
24
24
|
* Supports setting the database environment paramaters from the secret too.
|
25
25
|
*/
|
26
|
-
export class SecretHolder<Secret> {
|
26
|
+
export class SecretHolder<Secret extends GenericSecret> {
|
27
27
|
private readonly secretId: string;
|
28
28
|
private readonly prefix: string;
|
29
29
|
private readonly expectedKeys: string[];
|
@@ -51,7 +51,7 @@ export class SecretHolder<Secret> {
|
|
51
51
|
this.secretCache.push(DEFAULT_SECRET_KEY, secretValue);
|
52
52
|
}
|
53
53
|
|
54
|
-
public static create<S>(
|
54
|
+
public static create<S extends GenericSecret>(
|
55
55
|
prefix = DEFAULT_PREFIX,
|
56
56
|
expectedKeys: string[] = []
|
57
57
|
) {
|
@@ -67,10 +67,7 @@ export class SecretHolder<Secret> {
|
|
67
67
|
const parsedSecret =
|
68
68
|
this.prefix === DEFAULT_PREFIX
|
69
69
|
? secret
|
70
|
-
: this.parseSecret(
|
71
|
-
secret as unknown as GenericSecret,
|
72
|
-
`${this.prefix}.`
|
73
|
-
);
|
70
|
+
: this.parseSecret(secret, `${this.prefix}.`);
|
74
71
|
|
75
72
|
if (this.expectedKeys.length > 0) {
|
76
73
|
checkExpectedSecretKeys(this.expectedKeys, parsedSecret);
|
package/src/database/database.ts
CHANGED
@@ -1,6 +1,6 @@
|
|
1
1
|
import { IDatabase, ITask } from "pg-promise";
|
2
2
|
import { DatabaseEnvironmentKeys } from "../aws/runtime/secrets/dbsecret";
|
3
|
-
import { getEnvVariable } from "../utils/utils";
|
3
|
+
import { getEnvVariable, getEnvVariableSafe } from "../utils/utils";
|
4
4
|
import { envValue } from "../aws/runtime/environment";
|
5
5
|
|
6
6
|
// eslint-disable-next-line @typescript-eslint/no-var-requires
|
@@ -1 +0,0 @@
|
|
1
|
-
{"version":3,"file":"integration.js","sourceRoot":"","sources":["../../../../src/aws/infra/api/integration.ts"],"names":[],"mappings":";;;AAAA,+DAIoC;AAEpC,uDAAmD;AACnD,qGAAgG;AAShG,MAAa,sBAAsB;IAM/B,YAAY,MAAiB,EAAE,SAAS,GAAG,sBAAS,CAAC,UAAU;QAFtD,eAAU,GAAmB,EAAE,CAAC;QAGrC,IAAI,CAAC,MAAM,GAAG,MAAM,CAAC;QACrB,IAAI,CAAC,SAAS,GAAG,SAAS,CAAC;IAC/B,CAAC;IAED,gBAAgB,CAAC,GAAG,KAAe;QAC/B,KAAK,CAAC,OAAO,CAAC,CAAC,IAAI,EAAE,EAAE,CAAC,IAAI,CAAC,UAAU,CAAC,IAAI,CAAC,EAAE,IAAI,EAAE,MAAM,EAAE,IAAI,EAAE,CAAC,CAAC,CAAC;QAEtE,OAAO,IAAI,CAAC;IAChB,CAAC;IAED,iBAAiB,CAAC,GAAG,KAAe;QAChC,KAAK,CAAC,OAAO,CAAC,CAAC,IAAI,EAAE,EAAE,CACnB,IAAI,CAAC,UAAU,CAAC,IAAI,CAAC,EAAE,IAAI,EAAE,aAAa,EAAE,IAAI,EAAE,CAAC,CACtD,CAAC;QAEF,OAAO,IAAI,CAAC;IAChB,CAAC;IAED,KAAK;QACD,MAAM,oBAAoB,GAAG,IAAI,CAAC,eAAe,EAAE,CAAC;QAEpD,OAAO,IAAI,kCAAiB,CAAC,IAAI,CAAC,MAAM,EAAE;YACtC,KAAK,EAAE,KAAK;YACZ,oBAAoB;YACpB,iBAAiB,EACb,IAAI,CAAC,UAAU,CAAC,MAAM,IAAI,CAAC;gBACvB,CAAC,CAAC,SAAS;gBACX,CAAC,CAAC,IAAI,CAAC,uBAAuB,EAAE;YACxC,gBAAgB,EACZ,IAAI,CAAC,UAAU,CAAC,MAAM,IAAI,CAAC;gBACvB,CAAC,CAAC,SAAS;gBACX,CAAC,CAAC,IAAI,CAAC,sBAAsB,EAAE;YACvC,mBAAmB,EAAE,oCAAmB,CAAC,aAAa;SACzD,CAAC,CAAC;IACP,CAAC;IAED,uBAAuB;QACnB,MAAM,iBAAiB,GAA2B,EAAE,CAAC;QAErD,IAAI,CAAC,UAAU,CAAC,OAAO,CAAC,CAAC,SAAuB,EAAE,EAAE;YAChD,iBAAiB,CACb,uBAAuB,SAAS,CAAC,IAAI,IAAI,SAAS,CAAC,IAAI,EAAE,CAC5D,GAAG,kBAAkB,SAAS,CAAC,IAAI,IAAI,SAAS,CAAC,IAAI,EAAE,CAAC;QAC7D,CAAC,CAAC,CAAC;QAEH,OAAO,iBAAiB,CAAC;IAC7B,CAAC;IAED,sBAAsB;QAClB,MAAM,WAAW,GAA2B,EAAE,CAAC;QAE/C,IAAI,CAAC,UAAU,CAAC,OAAO,CAAC,CAAC,SAAuB,EAAE,EAAE;YAChD,WAAW,CACP,SAAS,CAAC,IAAI,CACjB,GAAG,yCAAyC,SAAS,CAAC,IAAI,KAAK,CAAC;QACrE,CAAC,CAAC,CAAC;QAEH,OAAO;YACH,CAAC,sBAAS,CAAC,gBAAgB,CAAC,EAAE,IAAI,CAAC,SAAS,CAAC,WAAW,CAAC;SAC5D,CAAC;IACN,CAAC;IAED,eAAe;QACX,OAAO,CAAC,iEAA8B,CAAC,EAAE,CAAC,IAAI,CAAC,SAAS,CAAC,CAAC,CAAC;IAC/D,CAAC;CACJ;AAxED,wDAwEC"}
|
@@ -1 +0,0 @@
|
|
1
|
-
{"version":3,"file":"response.js","sourceRoot":"","sources":["../../../../src/aws/infra/api/response.ts"],"names":[],"mappings":"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"}
|
@@ -1 +0,0 @@
|
|
1
|
-
{"version":3,"file":"responses.js","sourceRoot":"","sources":["../../../../src/aws/infra/api/responses.ts"],"names":[],"mappings":";;;AAAA,yCAMoB;AACpB,+DAKoC;AAGpC,+CAI4B;AAGf,QAAA,eAAe,GAAwB;IAChD,UAAU,EAAE,KAAK;CACpB,CAAC;AAEW,QAAA,wBAAwB,GAAwB;IACzD,UAAU,EAAE,KAAK;IACjB,gBAAgB,EAAE,4BAAmB;IACrC,iBAAiB,EAAE,qCAA0B;CAChD,CAAC;AAEW,QAAA,yBAAyB,GAAwB;IAC1D,UAAU,EAAE,KAAK;IACjB,gBAAgB,EAAE,sBAAa;IAC/B,iBAAiB,EAAE,8CAAmC;CACzD,CAAC;AAEF,MAAM,YAAY,GAAG;IACjB,iBAAiB,EAAE,8BAAmB;CACzC,CAAC;AAEW,QAAA,yBAAyB,GAAG;IACrC,kBAAkB,EAAE;QAChB,oDAAoD,EAAE,KAAK;KAC9D;CACJ,CAAC;AAEW,QAAA,sBAAsB,GAAG;IAClC,UAAU,EAAE,KAAK;IACjB,gBAAgB,EAAE,0BAAiB;IACnC,iBAAiB,EAAE,mCAAwB;CAC9C,CAAC;AAEF;;GAEG;AACH,SAAgB,cAAc,CAC1B,MAAc,EACd,WAAsB,EACtB,KAAa,EACb,UAAoC;IAEpC,OAAO;QACH,UAAU,EAAE,MAAM;QAClB,cAAc,EAAE,IAAA,0BAAe,EAAC,WAAW,EAAE,KAAK,CAAC;QACnD,kBAAkB,EAAE,UAAU,IAAI,EAAE;KACvC,CAAC;AACN,CAAC;AAXD,wCAWC;AAED;;GAEG;AACH,SAAgB,UAAU,CAAC,QAAwB;IAC/C,OAAO;QACH,GAAG,QAAQ;QACX,GAAG;YACC,kBAAkB,EAAE;gBAChB,oDAAoD,EAAE,IAAI;aAC7D;SACJ;KACJ,CAAC;AACN,CAAC;AATD,gCASC;AAWD;;;;;;GAMG;AACH,SAAgB,kBAAkB,CAC9B,cAA2B,EAC3B,OAA4B;IAE5B,OAAO,IAAI,kCAAiB,CAAC,cAAc,EAAE;QACzC,KAAK,EAAE,KAAK;QACZ,oBAAoB,EAAE,OAAO,EAAE,SAAS,IAAI;YACxC,WAAW,CAAC,uBAAe,EAAE,OAAO,CAAC;YACrC,WAAW,CAAC,gCAAwB,EAAE,OAAO,CAAC;YAC9C,WAAW,CAAC,8BAAsB,EAAE,OAAO,CAAC;YAC5C,WAAW,CAAC,iCAAyB,EAAE,OAAO,CAAC;SAClD;QACD,iBAAiB,EAAE,OAAO,EAAE,iBAAiB,IAAI,EAAE;QACnD,gBAAgB,EAAE,OAAO,EAAE,gBAAgB,IAAI,EAAE;QACjD,mBAAmB,EACf,OAAO,EAAE,mBAAmB,IAAI,oCAAmB,CAAC,aAAa;KACxE,CAAC,CAAC;AACP,CAAC;AAjBD,gDAiBC;AAED,SAAgB,WAAW,CACvB,QAA6B,EAC7B,OAA4B;IAE5B,IAAI,OAAO,EAAE,GAAG,EAAE;QACd,QAAQ,GAAG,EAAE,GAAG,QAAQ,EAAE,GAAG,YAAY,EAAE,CAAC;KAC/C;IACD,IAAI,CAAC,OAAO,EAAE,WAAW,EAAE;QACvB,QAAQ,GAAG,EAAE,GAAG,QAAQ,EAAE,GAAG,iCAAyB,EAAE,CAAC;KAC5D;IAED,OAAO,QAAQ,CAAC;AACpB,CAAC;AAZD,kCAYC"}
|