@aligent/cdk-aspects 0.4.0 → 0.5.0
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 +6 -0
- package/index.d.ts +2 -0
- package/index.js +3 -1
- package/lib/defaults/dynamodb.d.ts +53 -0
- package/lib/defaults/dynamodb.js +114 -0
- package/lib/defaults/s3-bucket.d.ts +51 -0
- package/lib/defaults/s3-bucket.js +85 -0
- package/package.json +1 -1
package/CHANGELOG.md
CHANGED
|
@@ -1,5 +1,11 @@
|
|
|
1
1
|
# @aligent/cdk-aspects
|
|
2
2
|
|
|
3
|
+
## 0.5.0
|
|
4
|
+
|
|
5
|
+
### Minor Changes
|
|
6
|
+
|
|
7
|
+
- [#1630](https://github.com/aligent/cdk-constructs/pull/1630) [`91347d6`](https://github.com/aligent/cdk-constructs/commit/91347d62e048c23ae85f657e97c1dd357c1b2a70) Thanks [@kai-nguyen-aligent](https://github.com/kai-nguyen-aligent)! - Add default aspects for S3 and DynamoDB resources to enforce secure configuration defaults
|
|
8
|
+
|
|
3
9
|
## 0.4.0
|
|
4
10
|
|
|
5
11
|
### Minor Changes
|
package/index.d.ts
CHANGED
|
@@ -1,5 +1,7 @@
|
|
|
1
|
+
export * from "./lib/defaults/dynamodb";
|
|
1
2
|
export * from "./lib/defaults/log-group";
|
|
2
3
|
export * from "./lib/defaults/nodejs-function";
|
|
4
|
+
export * from "./lib/defaults/s3-bucket";
|
|
3
5
|
export * from "./lib/defaults/step-functions";
|
|
4
6
|
export * from "./lib/lambda-sfn-versioning";
|
|
5
7
|
export * from "./lib/microservice-checks";
|
package/index.js
CHANGED
|
@@ -14,10 +14,12 @@ var __exportStar = (this && this.__exportStar) || function(m, exports) {
|
|
|
14
14
|
for (var p in m) if (p !== "default" && !Object.prototype.hasOwnProperty.call(exports, p)) __createBinding(exports, m, p);
|
|
15
15
|
};
|
|
16
16
|
Object.defineProperty(exports, "__esModule", { value: true });
|
|
17
|
+
__exportStar(require("./lib/defaults/dynamodb"), exports);
|
|
17
18
|
__exportStar(require("./lib/defaults/log-group"), exports);
|
|
18
19
|
__exportStar(require("./lib/defaults/nodejs-function"), exports);
|
|
20
|
+
__exportStar(require("./lib/defaults/s3-bucket"), exports);
|
|
19
21
|
__exportStar(require("./lib/defaults/step-functions"), exports);
|
|
20
22
|
__exportStar(require("./lib/lambda-sfn-versioning"), exports);
|
|
21
23
|
__exportStar(require("./lib/microservice-checks"), exports);
|
|
22
24
|
__exportStar(require("./lib/resource-prefix"), exports);
|
|
23
|
-
//# sourceMappingURL=data:application/json;base64,
|
|
25
|
+
//# sourceMappingURL=data:application/json;base64,eyJ2ZXJzaW9uIjozLCJmaWxlIjoiaW5kZXguanMiLCJzb3VyY2VSb290IjoiIiwic291cmNlcyI6WyJpbmRleC50cyJdLCJuYW1lcyI6W10sIm1hcHBpbmdzIjoiOzs7Ozs7Ozs7Ozs7Ozs7O0FBQUEsMERBQXdDO0FBQ3hDLDJEQUF5QztBQUN6QyxpRUFBK0M7QUFDL0MsMkRBQXlDO0FBQ3pDLGdFQUE4QztBQUM5Qyw4REFBNEM7QUFDNUMsNERBQTBDO0FBQzFDLHdEQUFzQyIsInNvdXJjZXNDb250ZW50IjpbImV4cG9ydCAqIGZyb20gXCIuL2xpYi9kZWZhdWx0cy9keW5hbW9kYlwiO1xuZXhwb3J0ICogZnJvbSBcIi4vbGliL2RlZmF1bHRzL2xvZy1ncm91cFwiO1xuZXhwb3J0ICogZnJvbSBcIi4vbGliL2RlZmF1bHRzL25vZGVqcy1mdW5jdGlvblwiO1xuZXhwb3J0ICogZnJvbSBcIi4vbGliL2RlZmF1bHRzL3MzLWJ1Y2tldFwiO1xuZXhwb3J0ICogZnJvbSBcIi4vbGliL2RlZmF1bHRzL3N0ZXAtZnVuY3Rpb25zXCI7XG5leHBvcnQgKiBmcm9tIFwiLi9saWIvbGFtYmRhLXNmbi12ZXJzaW9uaW5nXCI7XG5leHBvcnQgKiBmcm9tIFwiLi9saWIvbWljcm9zZXJ2aWNlLWNoZWNrc1wiO1xuZXhwb3J0ICogZnJvbSBcIi4vbGliL3Jlc291cmNlLXByZWZpeFwiO1xuIl19
|
|
@@ -0,0 +1,53 @@
|
|
|
1
|
+
import { type IAspect } from "aws-cdk-lib";
|
|
2
|
+
import { IConstruct } from "constructs";
|
|
3
|
+
interface Config {
|
|
4
|
+
duration: "SHORT" | "MEDIUM" | "LONG";
|
|
5
|
+
}
|
|
6
|
+
/**
|
|
7
|
+
* Aspect that automatically applies configuration-aware defaults to DynamoDB Tables
|
|
8
|
+
*
|
|
9
|
+
* Visits all constructs in the scope and automatically applies configuration-specific
|
|
10
|
+
* removal policies and point-in-time recovery settings to DynamoDB tables.
|
|
11
|
+
* Different configurations balance between cost optimization and data retention needs.
|
|
12
|
+
*
|
|
13
|
+
* @example
|
|
14
|
+
* ```typescript
|
|
15
|
+
* // Apply configuration-specific defaults to all tables
|
|
16
|
+
* Aspects.of(app).add(new DynamoDbDefaultsAspect({ duration: 'SHORT' }));
|
|
17
|
+
*
|
|
18
|
+
* // Tables automatically inherit configuration defaults
|
|
19
|
+
* new Table(stack, 'MyTable', {
|
|
20
|
+
* // point-in-time recovery and removal policy applied automatically
|
|
21
|
+
* });
|
|
22
|
+
* ```
|
|
23
|
+
*
|
|
24
|
+
* @see https://docs.aws.amazon.com/cdk/api/v2/docs/aws-cdk-lib.aws_dynamodb.Table.html
|
|
25
|
+
*/
|
|
26
|
+
export declare class DynamoDbDefaultsAspect implements IAspect {
|
|
27
|
+
private readonly defaultProps;
|
|
28
|
+
/**
|
|
29
|
+
* Creates a new DynamoDbDefaultsAspect
|
|
30
|
+
*
|
|
31
|
+
* @param config - Configuration identifier used to select appropriate defaults.
|
|
32
|
+
*/
|
|
33
|
+
constructor(config: Config);
|
|
34
|
+
/**
|
|
35
|
+
* Get duration-specific DynamoDB table properties
|
|
36
|
+
*
|
|
37
|
+
* @param duration - The duration to get the table properties for
|
|
38
|
+
* @returns The table properties for the duration
|
|
39
|
+
*/
|
|
40
|
+
private retentionProperties;
|
|
41
|
+
private isProvisionedThroughputConfigured;
|
|
42
|
+
private isOnDemandThroughputConfigured;
|
|
43
|
+
/**
|
|
44
|
+
* Visits a construct and applies configuration-appropriate defaults
|
|
45
|
+
*
|
|
46
|
+
* Applies configuration-specific billing mode, throughput, point-in-time recovery,
|
|
47
|
+
* and removal policies to tables that don't already have these properties explicitly set.
|
|
48
|
+
*
|
|
49
|
+
* @param node - The construct to potentially modify
|
|
50
|
+
*/
|
|
51
|
+
visit(node: IConstruct): void;
|
|
52
|
+
}
|
|
53
|
+
export {};
|
|
@@ -0,0 +1,114 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
Object.defineProperty(exports, "__esModule", { value: true });
|
|
3
|
+
exports.DynamoDbDefaultsAspect = void 0;
|
|
4
|
+
const aws_cdk_lib_1 = require("aws-cdk-lib");
|
|
5
|
+
const aws_dynamodb_1 = require("aws-cdk-lib/aws-dynamodb");
|
|
6
|
+
/**
|
|
7
|
+
* Aspect that automatically applies configuration-aware defaults to DynamoDB Tables
|
|
8
|
+
*
|
|
9
|
+
* Visits all constructs in the scope and automatically applies configuration-specific
|
|
10
|
+
* removal policies and point-in-time recovery settings to DynamoDB tables.
|
|
11
|
+
* Different configurations balance between cost optimization and data retention needs.
|
|
12
|
+
*
|
|
13
|
+
* @example
|
|
14
|
+
* ```typescript
|
|
15
|
+
* // Apply configuration-specific defaults to all tables
|
|
16
|
+
* Aspects.of(app).add(new DynamoDbDefaultsAspect({ duration: 'SHORT' }));
|
|
17
|
+
*
|
|
18
|
+
* // Tables automatically inherit configuration defaults
|
|
19
|
+
* new Table(stack, 'MyTable', {
|
|
20
|
+
* // point-in-time recovery and removal policy applied automatically
|
|
21
|
+
* });
|
|
22
|
+
* ```
|
|
23
|
+
*
|
|
24
|
+
* @see https://docs.aws.amazon.com/cdk/api/v2/docs/aws-cdk-lib.aws_dynamodb.Table.html
|
|
25
|
+
*/
|
|
26
|
+
class DynamoDbDefaultsAspect {
|
|
27
|
+
/**
|
|
28
|
+
* Creates a new DynamoDbDefaultsAspect
|
|
29
|
+
*
|
|
30
|
+
* @param config - Configuration identifier used to select appropriate defaults.
|
|
31
|
+
*/
|
|
32
|
+
constructor(config) {
|
|
33
|
+
this.defaultProps = this.retentionProperties(config.duration);
|
|
34
|
+
}
|
|
35
|
+
/**
|
|
36
|
+
* Get duration-specific DynamoDB table properties
|
|
37
|
+
*
|
|
38
|
+
* @param duration - The duration to get the table properties for
|
|
39
|
+
* @returns The table properties for the duration
|
|
40
|
+
*/
|
|
41
|
+
retentionProperties(duration) {
|
|
42
|
+
switch (duration) {
|
|
43
|
+
case "SHORT":
|
|
44
|
+
return {
|
|
45
|
+
billingMode: aws_dynamodb_1.BillingMode.PROVISIONED,
|
|
46
|
+
readCapacity: 1,
|
|
47
|
+
writeCapacity: 1,
|
|
48
|
+
removalPolicy: aws_cdk_lib_1.RemovalPolicy.DESTROY,
|
|
49
|
+
};
|
|
50
|
+
case "MEDIUM":
|
|
51
|
+
return {
|
|
52
|
+
billingMode: aws_dynamodb_1.BillingMode.PAY_PER_REQUEST,
|
|
53
|
+
maxReadRequestUnits: 100,
|
|
54
|
+
maxWriteRequestUnits: 100,
|
|
55
|
+
removalPolicy: aws_cdk_lib_1.RemovalPolicy.DESTROY,
|
|
56
|
+
};
|
|
57
|
+
default:
|
|
58
|
+
return {
|
|
59
|
+
billingMode: aws_dynamodb_1.BillingMode.PAY_PER_REQUEST,
|
|
60
|
+
removalPolicy: aws_cdk_lib_1.RemovalPolicy.RETAIN,
|
|
61
|
+
};
|
|
62
|
+
}
|
|
63
|
+
}
|
|
64
|
+
isProvisionedThroughputConfigured() {
|
|
65
|
+
const { billingMode, readCapacity, writeCapacity } = this.defaultProps;
|
|
66
|
+
return (billingMode === aws_dynamodb_1.BillingMode.PROVISIONED &&
|
|
67
|
+
readCapacity !== undefined &&
|
|
68
|
+
writeCapacity !== undefined);
|
|
69
|
+
}
|
|
70
|
+
isOnDemandThroughputConfigured() {
|
|
71
|
+
const { billingMode, maxReadRequestUnits, maxWriteRequestUnits } = this.defaultProps;
|
|
72
|
+
return (billingMode === aws_dynamodb_1.BillingMode.PAY_PER_REQUEST &&
|
|
73
|
+
maxReadRequestUnits !== undefined &&
|
|
74
|
+
maxWriteRequestUnits !== undefined);
|
|
75
|
+
}
|
|
76
|
+
/**
|
|
77
|
+
* Visits a construct and applies configuration-appropriate defaults
|
|
78
|
+
*
|
|
79
|
+
* Applies configuration-specific billing mode, throughput, point-in-time recovery,
|
|
80
|
+
* and removal policies to tables that don't already have these properties explicitly set.
|
|
81
|
+
*
|
|
82
|
+
* @param node - The construct to potentially modify
|
|
83
|
+
*/
|
|
84
|
+
visit(node) {
|
|
85
|
+
if (node instanceof aws_dynamodb_1.Table) {
|
|
86
|
+
const { billingMode, readCapacity, writeCapacity, maxReadRequestUnits, maxWriteRequestUnits, removalPolicy, } = this.defaultProps;
|
|
87
|
+
if (removalPolicy) {
|
|
88
|
+
node.applyRemovalPolicy(removalPolicy);
|
|
89
|
+
}
|
|
90
|
+
const cfnTable = node.node.defaultChild;
|
|
91
|
+
if (!cfnTable)
|
|
92
|
+
return;
|
|
93
|
+
if (cfnTable.billingMode === undefined) {
|
|
94
|
+
cfnTable.billingMode = billingMode;
|
|
95
|
+
}
|
|
96
|
+
if (cfnTable.provisionedThroughput === undefined &&
|
|
97
|
+
this.isProvisionedThroughputConfigured()) {
|
|
98
|
+
cfnTable.provisionedThroughput = {
|
|
99
|
+
readCapacityUnits: readCapacity,
|
|
100
|
+
writeCapacityUnits: writeCapacity,
|
|
101
|
+
};
|
|
102
|
+
}
|
|
103
|
+
if (cfnTable.onDemandThroughput === undefined &&
|
|
104
|
+
this.isOnDemandThroughputConfigured()) {
|
|
105
|
+
cfnTable.onDemandThroughput = {
|
|
106
|
+
maxReadRequestUnits,
|
|
107
|
+
maxWriteRequestUnits,
|
|
108
|
+
};
|
|
109
|
+
}
|
|
110
|
+
}
|
|
111
|
+
}
|
|
112
|
+
}
|
|
113
|
+
exports.DynamoDbDefaultsAspect = DynamoDbDefaultsAspect;
|
|
114
|
+
//# sourceMappingURL=data:application/json;base64,eyJ2ZXJzaW9uIjozLCJmaWxlIjoiZHluYW1vZGIuanMiLCJzb3VyY2VSb290IjoiIiwic291cmNlcyI6WyJkeW5hbW9kYi50cyJdLCJuYW1lcyI6W10sIm1hcHBpbmdzIjoiOzs7QUFBQSw2Q0FBMEQ7QUFDMUQsMkRBS2tDO0FBT2xDOzs7Ozs7Ozs7Ozs7Ozs7Ozs7O0dBbUJHO0FBQ0gsTUFBYSxzQkFBc0I7SUFHakM7Ozs7T0FJRztJQUNILFlBQVksTUFBYztRQUN4QixJQUFJLENBQUMsWUFBWSxHQUFHLElBQUksQ0FBQyxtQkFBbUIsQ0FBQyxNQUFNLENBQUMsUUFBUSxDQUFDLENBQUM7SUFDaEUsQ0FBQztJQUVEOzs7OztPQUtHO0lBQ0ssbUJBQW1CLENBQ3pCLFFBQXFDO1FBRXJDLFFBQVEsUUFBUSxFQUFFLENBQUM7WUFDakIsS0FBSyxPQUFPO2dCQUNWLE9BQU87b0JBQ0wsV0FBVyxFQUFFLDBCQUFXLENBQUMsV0FBVztvQkFDcEMsWUFBWSxFQUFFLENBQUM7b0JBQ2YsYUFBYSxFQUFFLENBQUM7b0JBQ2hCLGFBQWEsRUFBRSwyQkFBYSxDQUFDLE9BQU87aUJBQ3JDLENBQUM7WUFDSixLQUFLLFFBQVE7Z0JBQ1gsT0FBTztvQkFDTCxXQUFXLEVBQUUsMEJBQVcsQ0FBQyxlQUFlO29CQUN4QyxtQkFBbUIsRUFBRSxHQUFHO29CQUN4QixvQkFBb0IsRUFBRSxHQUFHO29CQUN6QixhQUFhLEVBQUUsMkJBQWEsQ0FBQyxPQUFPO2lCQUNyQyxDQUFDO1lBQ0o7Z0JBQ0UsT0FBTztvQkFDTCxXQUFXLEVBQUUsMEJBQVcsQ0FBQyxlQUFlO29CQUN4QyxhQUFhLEVBQUUsMkJBQWEsQ0FBQyxNQUFNO2lCQUNwQyxDQUFDO1FBQ04sQ0FBQztJQUNILENBQUM7SUFFTyxpQ0FBaUM7UUFDdkMsTUFBTSxFQUFFLFdBQVcsRUFBRSxZQUFZLEVBQUUsYUFBYSxFQUFFLEdBQUcsSUFBSSxDQUFDLFlBQVksQ0FBQztRQUV2RSxPQUFPLENBQ0wsV0FBVyxLQUFLLDBCQUFXLENBQUMsV0FBVztZQUN2QyxZQUFZLEtBQUssU0FBUztZQUMxQixhQUFhLEtBQUssU0FBUyxDQUM1QixDQUFDO0lBQ0osQ0FBQztJQUVPLDhCQUE4QjtRQUNwQyxNQUFNLEVBQUUsV0FBVyxFQUFFLG1CQUFtQixFQUFFLG9CQUFvQixFQUFFLEdBQzlELElBQUksQ0FBQyxZQUFZLENBQUM7UUFFcEIsT0FBTyxDQUNMLFdBQVcsS0FBSywwQkFBVyxDQUFDLGVBQWU7WUFDM0MsbUJBQW1CLEtBQUssU0FBUztZQUNqQyxvQkFBb0IsS0FBSyxTQUFTLENBQ25DLENBQUM7SUFDSixDQUFDO0lBRUQ7Ozs7Ozs7T0FPRztJQUNILEtBQUssQ0FBQyxJQUFnQjtRQUNwQixJQUFJLElBQUksWUFBWSxvQkFBSyxFQUFFLENBQUM7WUFDMUIsTUFBTSxFQUNKLFdBQVcsRUFDWCxZQUFZLEVBQ1osYUFBYSxFQUNiLG1CQUFtQixFQUNuQixvQkFBb0IsRUFDcEIsYUFBYSxHQUNkLEdBQUcsSUFBSSxDQUFDLFlBQVksQ0FBQztZQUV0QixJQUFJLGFBQWEsRUFBRSxDQUFDO2dCQUNsQixJQUFJLENBQUMsa0JBQWtCLENBQUMsYUFBYSxDQUFDLENBQUM7WUFDekMsQ0FBQztZQUVELE1BQU0sUUFBUSxHQUFHLElBQUksQ0FBQyxJQUFJLENBQUMsWUFBd0IsQ0FBQztZQUNwRCxJQUFJLENBQUMsUUFBUTtnQkFBRSxPQUFPO1lBRXRCLElBQUksUUFBUSxDQUFDLFdBQVcsS0FBSyxTQUFTLEVBQUUsQ0FBQztnQkFDdkMsUUFBUSxDQUFDLFdBQVcsR0FBRyxXQUFXLENBQUM7WUFDckMsQ0FBQztZQUVELElBQ0UsUUFBUSxDQUFDLHFCQUFxQixLQUFLLFNBQVM7Z0JBQzVDLElBQUksQ0FBQyxpQ0FBaUMsRUFBRSxFQUN4QyxDQUFDO2dCQUNELFFBQVEsQ0FBQyxxQkFBcUIsR0FBRztvQkFDL0IsaUJBQWlCLEVBQUUsWUFBYTtvQkFDaEMsa0JBQWtCLEVBQUUsYUFBYztpQkFDbkMsQ0FBQztZQUNKLENBQUM7WUFFRCxJQUNFLFFBQVEsQ0FBQyxrQkFBa0IsS0FBSyxTQUFTO2dCQUN6QyxJQUFJLENBQUMsOEJBQThCLEVBQUUsRUFDckMsQ0FBQztnQkFDRCxRQUFRLENBQUMsa0JBQWtCLEdBQUc7b0JBQzVCLG1CQUFtQjtvQkFDbkIsb0JBQW9CO2lCQUNyQixDQUFDO1lBQ0osQ0FBQztRQUNILENBQUM7SUFDSCxDQUFDO0NBQ0Y7QUFwSEQsd0RBb0hDIiwic291cmNlc0NvbnRlbnQiOlsiaW1wb3J0IHsgUmVtb3ZhbFBvbGljeSwgdHlwZSBJQXNwZWN0IH0gZnJvbSBcImF3cy1jZGstbGliXCI7XG5pbXBvcnQge1xuICBCaWxsaW5nTW9kZSxcbiAgQ2ZuVGFibGUsXG4gIFRhYmxlLFxuICB0eXBlIFRhYmxlUHJvcHMsXG59IGZyb20gXCJhd3MtY2RrLWxpYi9hd3MtZHluYW1vZGJcIjtcbmltcG9ydCB7IElDb25zdHJ1Y3QgfSBmcm9tIFwiY29uc3RydWN0c1wiO1xuXG5pbnRlcmZhY2UgQ29uZmlnIHtcbiAgZHVyYXRpb246IFwiU0hPUlRcIiB8IFwiTUVESVVNXCIgfCBcIkxPTkdcIjtcbn1cblxuLyoqXG4gKiBBc3BlY3QgdGhhdCBhdXRvbWF0aWNhbGx5IGFwcGxpZXMgY29uZmlndXJhdGlvbi1hd2FyZSBkZWZhdWx0cyB0byBEeW5hbW9EQiBUYWJsZXNcbiAqXG4gKiBWaXNpdHMgYWxsIGNvbnN0cnVjdHMgaW4gdGhlIHNjb3BlIGFuZCBhdXRvbWF0aWNhbGx5IGFwcGxpZXMgY29uZmlndXJhdGlvbi1zcGVjaWZpY1xuICogcmVtb3ZhbCBwb2xpY2llcyBhbmQgcG9pbnQtaW4tdGltZSByZWNvdmVyeSBzZXR0aW5ncyB0byBEeW5hbW9EQiB0YWJsZXMuXG4gKiBEaWZmZXJlbnQgY29uZmlndXJhdGlvbnMgYmFsYW5jZSBiZXR3ZWVuIGNvc3Qgb3B0aW1pemF0aW9uIGFuZCBkYXRhIHJldGVudGlvbiBuZWVkcy5cbiAqXG4gKiBAZXhhbXBsZVxuICogYGBgdHlwZXNjcmlwdFxuICogLy8gQXBwbHkgY29uZmlndXJhdGlvbi1zcGVjaWZpYyBkZWZhdWx0cyB0byBhbGwgdGFibGVzXG4gKiBBc3BlY3RzLm9mKGFwcCkuYWRkKG5ldyBEeW5hbW9EYkRlZmF1bHRzQXNwZWN0KHsgZHVyYXRpb246ICdTSE9SVCcgfSkpO1xuICpcbiAqIC8vIFRhYmxlcyBhdXRvbWF0aWNhbGx5IGluaGVyaXQgY29uZmlndXJhdGlvbiBkZWZhdWx0c1xuICogbmV3IFRhYmxlKHN0YWNrLCAnTXlUYWJsZScsIHtcbiAqICAgLy8gcG9pbnQtaW4tdGltZSByZWNvdmVyeSBhbmQgcmVtb3ZhbCBwb2xpY3kgYXBwbGllZCBhdXRvbWF0aWNhbGx5XG4gKiB9KTtcbiAqIGBgYFxuICpcbiAqIEBzZWUgaHR0cHM6Ly9kb2NzLmF3cy5hbWF6b24uY29tL2Nkay9hcGkvdjIvZG9jcy9hd3MtY2RrLWxpYi5hd3NfZHluYW1vZGIuVGFibGUuaHRtbFxuICovXG5leHBvcnQgY2xhc3MgRHluYW1vRGJEZWZhdWx0c0FzcGVjdCBpbXBsZW1lbnRzIElBc3BlY3Qge1xuICBwcml2YXRlIHJlYWRvbmx5IGRlZmF1bHRQcm9wczogVGFibGVQcm9wcztcblxuICAvKipcbiAgICogQ3JlYXRlcyBhIG5ldyBEeW5hbW9EYkRlZmF1bHRzQXNwZWN0XG4gICAqXG4gICAqIEBwYXJhbSBjb25maWcgLSBDb25maWd1cmF0aW9uIGlkZW50aWZpZXIgdXNlZCB0byBzZWxlY3QgYXBwcm9wcmlhdGUgZGVmYXVsdHMuXG4gICAqL1xuICBjb25zdHJ1Y3Rvcihjb25maWc6IENvbmZpZykge1xuICAgIHRoaXMuZGVmYXVsdFByb3BzID0gdGhpcy5yZXRlbnRpb25Qcm9wZXJ0aWVzKGNvbmZpZy5kdXJhdGlvbik7XG4gIH1cblxuICAvKipcbiAgICogR2V0IGR1cmF0aW9uLXNwZWNpZmljIER5bmFtb0RCIHRhYmxlIHByb3BlcnRpZXNcbiAgICpcbiAgICogQHBhcmFtIGR1cmF0aW9uIC0gVGhlIGR1cmF0aW9uIHRvIGdldCB0aGUgdGFibGUgcHJvcGVydGllcyBmb3JcbiAgICogQHJldHVybnMgVGhlIHRhYmxlIHByb3BlcnRpZXMgZm9yIHRoZSBkdXJhdGlvblxuICAgKi9cbiAgcHJpdmF0ZSByZXRlbnRpb25Qcm9wZXJ0aWVzKFxuICAgIGR1cmF0aW9uOiBcIlNIT1JUXCIgfCBcIk1FRElVTVwiIHwgXCJMT05HXCJcbiAgKTogVGFibGVQcm9wcyB7XG4gICAgc3dpdGNoIChkdXJhdGlvbikge1xuICAgICAgY2FzZSBcIlNIT1JUXCI6XG4gICAgICAgIHJldHVybiB7XG4gICAgICAgICAgYmlsbGluZ01vZGU6IEJpbGxpbmdNb2RlLlBST1ZJU0lPTkVELFxuICAgICAgICAgIHJlYWRDYXBhY2l0eTogMSxcbiAgICAgICAgICB3cml0ZUNhcGFjaXR5OiAxLFxuICAgICAgICAgIHJlbW92YWxQb2xpY3k6IFJlbW92YWxQb2xpY3kuREVTVFJPWSxcbiAgICAgICAgfTtcbiAgICAgIGNhc2UgXCJNRURJVU1cIjpcbiAgICAgICAgcmV0dXJuIHtcbiAgICAgICAgICBiaWxsaW5nTW9kZTogQmlsbGluZ01vZGUuUEFZX1BFUl9SRVFVRVNULFxuICAgICAgICAgIG1heFJlYWRSZXF1ZXN0VW5pdHM6IDEwMCxcbiAgICAgICAgICBtYXhXcml0ZVJlcXVlc3RVbml0czogMTAwLFxuICAgICAgICAgIHJlbW92YWxQb2xpY3k6IFJlbW92YWxQb2xpY3kuREVTVFJPWSxcbiAgICAgICAgfTtcbiAgICAgIGRlZmF1bHQ6XG4gICAgICAgIHJldHVybiB7XG4gICAgICAgICAgYmlsbGluZ01vZGU6IEJpbGxpbmdNb2RlLlBBWV9QRVJfUkVRVUVTVCxcbiAgICAgICAgICByZW1vdmFsUG9saWN5OiBSZW1vdmFsUG9saWN5LlJFVEFJTixcbiAgICAgICAgfTtcbiAgICB9XG4gIH1cblxuICBwcml2YXRlIGlzUHJvdmlzaW9uZWRUaHJvdWdocHV0Q29uZmlndXJlZCgpIHtcbiAgICBjb25zdCB7IGJpbGxpbmdNb2RlLCByZWFkQ2FwYWNpdHksIHdyaXRlQ2FwYWNpdHkgfSA9IHRoaXMuZGVmYXVsdFByb3BzO1xuXG4gICAgcmV0dXJuIChcbiAgICAgIGJpbGxpbmdNb2RlID09PSBCaWxsaW5nTW9kZS5QUk9WSVNJT05FRCAmJlxuICAgICAgcmVhZENhcGFjaXR5ICE9PSB1bmRlZmluZWQgJiZcbiAgICAgIHdyaXRlQ2FwYWNpdHkgIT09IHVuZGVmaW5lZFxuICAgICk7XG4gIH1cblxuICBwcml2YXRlIGlzT25EZW1hbmRUaHJvdWdocHV0Q29uZmlndXJlZCgpIHtcbiAgICBjb25zdCB7IGJpbGxpbmdNb2RlLCBtYXhSZWFkUmVxdWVzdFVuaXRzLCBtYXhXcml0ZVJlcXVlc3RVbml0cyB9ID1cbiAgICAgIHRoaXMuZGVmYXVsdFByb3BzO1xuXG4gICAgcmV0dXJuIChcbiAgICAgIGJpbGxpbmdNb2RlID09PSBCaWxsaW5nTW9kZS5QQVlfUEVSX1JFUVVFU1QgJiZcbiAgICAgIG1heFJlYWRSZXF1ZXN0VW5pdHMgIT09IHVuZGVmaW5lZCAmJlxuICAgICAgbWF4V3JpdGVSZXF1ZXN0VW5pdHMgIT09IHVuZGVmaW5lZFxuICAgICk7XG4gIH1cblxuICAvKipcbiAgICogVmlzaXRzIGEgY29uc3RydWN0IGFuZCBhcHBsaWVzIGNvbmZpZ3VyYXRpb24tYXBwcm9wcmlhdGUgZGVmYXVsdHNcbiAgICpcbiAgICogQXBwbGllcyBjb25maWd1cmF0aW9uLXNwZWNpZmljIGJpbGxpbmcgbW9kZSwgdGhyb3VnaHB1dCwgcG9pbnQtaW4tdGltZSByZWNvdmVyeSxcbiAgICogYW5kIHJlbW92YWwgcG9saWNpZXMgdG8gdGFibGVzIHRoYXQgZG9uJ3QgYWxyZWFkeSBoYXZlIHRoZXNlIHByb3BlcnRpZXMgZXhwbGljaXRseSBzZXQuXG4gICAqXG4gICAqIEBwYXJhbSBub2RlIC0gVGhlIGNvbnN0cnVjdCB0byBwb3RlbnRpYWxseSBtb2RpZnlcbiAgICovXG4gIHZpc2l0KG5vZGU6IElDb25zdHJ1Y3QpOiB2b2lkIHtcbiAgICBpZiAobm9kZSBpbnN0YW5jZW9mIFRhYmxlKSB7XG4gICAgICBjb25zdCB7XG4gICAgICAgIGJpbGxpbmdNb2RlLFxuICAgICAgICByZWFkQ2FwYWNpdHksXG4gICAgICAgIHdyaXRlQ2FwYWNpdHksXG4gICAgICAgIG1heFJlYWRSZXF1ZXN0VW5pdHMsXG4gICAgICAgIG1heFdyaXRlUmVxdWVzdFVuaXRzLFxuICAgICAgICByZW1vdmFsUG9saWN5LFxuICAgICAgfSA9IHRoaXMuZGVmYXVsdFByb3BzO1xuXG4gICAgICBpZiAocmVtb3ZhbFBvbGljeSkge1xuICAgICAgICBub2RlLmFwcGx5UmVtb3ZhbFBvbGljeShyZW1vdmFsUG9saWN5KTtcbiAgICAgIH1cblxuICAgICAgY29uc3QgY2ZuVGFibGUgPSBub2RlLm5vZGUuZGVmYXVsdENoaWxkIGFzIENmblRhYmxlO1xuICAgICAgaWYgKCFjZm5UYWJsZSkgcmV0dXJuO1xuXG4gICAgICBpZiAoY2ZuVGFibGUuYmlsbGluZ01vZGUgPT09IHVuZGVmaW5lZCkge1xuICAgICAgICBjZm5UYWJsZS5iaWxsaW5nTW9kZSA9IGJpbGxpbmdNb2RlO1xuICAgICAgfVxuXG4gICAgICBpZiAoXG4gICAgICAgIGNmblRhYmxlLnByb3Zpc2lvbmVkVGhyb3VnaHB1dCA9PT0gdW5kZWZpbmVkICYmXG4gICAgICAgIHRoaXMuaXNQcm92aXNpb25lZFRocm91Z2hwdXRDb25maWd1cmVkKClcbiAgICAgICkge1xuICAgICAgICBjZm5UYWJsZS5wcm92aXNpb25lZFRocm91Z2hwdXQgPSB7XG4gICAgICAgICAgcmVhZENhcGFjaXR5VW5pdHM6IHJlYWRDYXBhY2l0eSEsXG4gICAgICAgICAgd3JpdGVDYXBhY2l0eVVuaXRzOiB3cml0ZUNhcGFjaXR5ISxcbiAgICAgICAgfTtcbiAgICAgIH1cblxuICAgICAgaWYgKFxuICAgICAgICBjZm5UYWJsZS5vbkRlbWFuZFRocm91Z2hwdXQgPT09IHVuZGVmaW5lZCAmJlxuICAgICAgICB0aGlzLmlzT25EZW1hbmRUaHJvdWdocHV0Q29uZmlndXJlZCgpXG4gICAgICApIHtcbiAgICAgICAgY2ZuVGFibGUub25EZW1hbmRUaHJvdWdocHV0ID0ge1xuICAgICAgICAgIG1heFJlYWRSZXF1ZXN0VW5pdHMsXG4gICAgICAgICAgbWF4V3JpdGVSZXF1ZXN0VW5pdHMsXG4gICAgICAgIH07XG4gICAgICB9XG4gICAgfVxuICB9XG59XG4iXX0=
|
|
@@ -0,0 +1,51 @@
|
|
|
1
|
+
import { type IAspect } from "aws-cdk-lib";
|
|
2
|
+
import { IConstruct } from "constructs";
|
|
3
|
+
interface Config {
|
|
4
|
+
duration: "SHORT" | "MEDIUM" | "LONG";
|
|
5
|
+
}
|
|
6
|
+
/**
|
|
7
|
+
* Aspect that automatically applies configuration-aware defaults to S3 Buckets
|
|
8
|
+
*
|
|
9
|
+
* Visits all constructs in the scope and automatically applies configuration-specific
|
|
10
|
+
* lifecycle and removal policies to S3 buckets. Different configurations balance
|
|
11
|
+
* between cost optimization and data retention needs.
|
|
12
|
+
*
|
|
13
|
+
* @example
|
|
14
|
+
* ```typescript
|
|
15
|
+
* // Apply configuration-specific defaults to all buckets
|
|
16
|
+
* Aspects.of(app).add(new S3DefaultsAspect({ autoDelete: true, duration: 'SHORT' }));
|
|
17
|
+
*
|
|
18
|
+
* // Buckets automatically inherit configuration defaults
|
|
19
|
+
* new Bucket(stack, 'MyBucket', {
|
|
20
|
+
* // lifecycle and removal policy applied automatically
|
|
21
|
+
* });
|
|
22
|
+
* ```
|
|
23
|
+
*
|
|
24
|
+
* @see https://docs.aws.amazon.com/cdk/api/v2/docs/aws-cdk-lib.aws_s3.Bucket.html
|
|
25
|
+
*/
|
|
26
|
+
export declare class S3DefaultsAspect implements IAspect {
|
|
27
|
+
private readonly defaultProps;
|
|
28
|
+
/**
|
|
29
|
+
* Creates a new S3DefaultsAspect
|
|
30
|
+
*
|
|
31
|
+
* @param config - Configuration identifier used to select appropriate defaults.
|
|
32
|
+
*/
|
|
33
|
+
constructor(config: Config);
|
|
34
|
+
/**
|
|
35
|
+
* Get duration-specific object expiration
|
|
36
|
+
*
|
|
37
|
+
* @param duration - The duration to get the expiration for
|
|
38
|
+
* @returns The expiration Duration, or undefined for LONG retention
|
|
39
|
+
*/
|
|
40
|
+
private retentionProperties;
|
|
41
|
+
/**
|
|
42
|
+
* Visits a construct and applies configuration-appropriate defaults
|
|
43
|
+
*
|
|
44
|
+
* Applies a removal policy and lifecycle rules to buckets that don't
|
|
45
|
+
* already have a lifecycle configuration explicitly set.
|
|
46
|
+
*
|
|
47
|
+
* @param node - The construct to potentially modify
|
|
48
|
+
*/
|
|
49
|
+
visit(node: IConstruct): void;
|
|
50
|
+
}
|
|
51
|
+
export {};
|
|
@@ -0,0 +1,85 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
Object.defineProperty(exports, "__esModule", { value: true });
|
|
3
|
+
exports.S3DefaultsAspect = void 0;
|
|
4
|
+
const aws_cdk_lib_1 = require("aws-cdk-lib");
|
|
5
|
+
const aws_s3_1 = require("aws-cdk-lib/aws-s3");
|
|
6
|
+
/**
|
|
7
|
+
* Aspect that automatically applies configuration-aware defaults to S3 Buckets
|
|
8
|
+
*
|
|
9
|
+
* Visits all constructs in the scope and automatically applies configuration-specific
|
|
10
|
+
* lifecycle and removal policies to S3 buckets. Different configurations balance
|
|
11
|
+
* between cost optimization and data retention needs.
|
|
12
|
+
*
|
|
13
|
+
* @example
|
|
14
|
+
* ```typescript
|
|
15
|
+
* // Apply configuration-specific defaults to all buckets
|
|
16
|
+
* Aspects.of(app).add(new S3DefaultsAspect({ autoDelete: true, duration: 'SHORT' }));
|
|
17
|
+
*
|
|
18
|
+
* // Buckets automatically inherit configuration defaults
|
|
19
|
+
* new Bucket(stack, 'MyBucket', {
|
|
20
|
+
* // lifecycle and removal policy applied automatically
|
|
21
|
+
* });
|
|
22
|
+
* ```
|
|
23
|
+
*
|
|
24
|
+
* @see https://docs.aws.amazon.com/cdk/api/v2/docs/aws-cdk-lib.aws_s3.Bucket.html
|
|
25
|
+
*/
|
|
26
|
+
class S3DefaultsAspect {
|
|
27
|
+
/**
|
|
28
|
+
* Creates a new S3DefaultsAspect
|
|
29
|
+
*
|
|
30
|
+
* @param config - Configuration identifier used to select appropriate defaults.
|
|
31
|
+
*/
|
|
32
|
+
constructor(config) {
|
|
33
|
+
const props = this.retentionProperties(config.duration);
|
|
34
|
+
this.defaultProps = { ...props };
|
|
35
|
+
}
|
|
36
|
+
/**
|
|
37
|
+
* Get duration-specific object expiration
|
|
38
|
+
*
|
|
39
|
+
* @param duration - The duration to get the expiration for
|
|
40
|
+
* @returns The expiration Duration, or undefined for LONG retention
|
|
41
|
+
*/
|
|
42
|
+
retentionProperties(duration) {
|
|
43
|
+
switch (duration) {
|
|
44
|
+
case "SHORT":
|
|
45
|
+
return {
|
|
46
|
+
lifecycleRules: [{ expiration: aws_cdk_lib_1.Duration.days(30) }],
|
|
47
|
+
removalPolicy: aws_cdk_lib_1.RemovalPolicy.DESTROY,
|
|
48
|
+
};
|
|
49
|
+
case "MEDIUM":
|
|
50
|
+
return {
|
|
51
|
+
lifecycleRules: [{ expiration: aws_cdk_lib_1.Duration.days(90) }],
|
|
52
|
+
removalPolicy: aws_cdk_lib_1.RemovalPolicy.DESTROY,
|
|
53
|
+
};
|
|
54
|
+
default:
|
|
55
|
+
return {
|
|
56
|
+
lifecycleRules: [],
|
|
57
|
+
removalPolicy: aws_cdk_lib_1.RemovalPolicy.RETAIN,
|
|
58
|
+
};
|
|
59
|
+
}
|
|
60
|
+
}
|
|
61
|
+
/**
|
|
62
|
+
* Visits a construct and applies configuration-appropriate defaults
|
|
63
|
+
*
|
|
64
|
+
* Applies a removal policy and lifecycle rules to buckets that don't
|
|
65
|
+
* already have a lifecycle configuration explicitly set.
|
|
66
|
+
*
|
|
67
|
+
* @param node - The construct to potentially modify
|
|
68
|
+
*/
|
|
69
|
+
visit(node) {
|
|
70
|
+
if (node instanceof aws_s3_1.Bucket) {
|
|
71
|
+
const { lifecycleRules, removalPolicy } = this.defaultProps;
|
|
72
|
+
if (removalPolicy) {
|
|
73
|
+
node.applyRemovalPolicy(removalPolicy);
|
|
74
|
+
}
|
|
75
|
+
if (lifecycleRules === null || lifecycleRules === void 0 ? void 0 : lifecycleRules.length) {
|
|
76
|
+
const cfnBucket = node.node.defaultChild;
|
|
77
|
+
if (cfnBucket && cfnBucket.lifecycleConfiguration === undefined) {
|
|
78
|
+
lifecycleRules.forEach(rule => node.addLifecycleRule(rule));
|
|
79
|
+
}
|
|
80
|
+
}
|
|
81
|
+
}
|
|
82
|
+
}
|
|
83
|
+
}
|
|
84
|
+
exports.S3DefaultsAspect = S3DefaultsAspect;
|
|
85
|
+
//# sourceMappingURL=data:application/json;base64,eyJ2ZXJzaW9uIjozLCJmaWxlIjoiczMtYnVja2V0LmpzIiwic291cmNlUm9vdCI6IiIsInNvdXJjZXMiOlsiczMtYnVja2V0LnRzIl0sIm5hbWVzIjpbXSwibWFwcGluZ3MiOiI7OztBQUFBLDZDQUFvRTtBQUNwRSwrQ0FBeUU7QUFPekU7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7R0FtQkc7QUFDSCxNQUFhLGdCQUFnQjtJQUczQjs7OztPQUlHO0lBQ0gsWUFBWSxNQUFjO1FBQ3hCLE1BQU0sS0FBSyxHQUFHLElBQUksQ0FBQyxtQkFBbUIsQ0FBQyxNQUFNLENBQUMsUUFBUSxDQUFDLENBQUM7UUFDeEQsSUFBSSxDQUFDLFlBQVksR0FBRyxFQUFFLEdBQUcsS0FBSyxFQUFFLENBQUM7SUFDbkMsQ0FBQztJQUVEOzs7OztPQUtHO0lBQ0ssbUJBQW1CLENBQUMsUUFBcUM7UUFDL0QsUUFBUSxRQUFRLEVBQUUsQ0FBQztZQUNqQixLQUFLLE9BQU87Z0JBQ1YsT0FBTztvQkFDTCxjQUFjLEVBQUUsQ0FBQyxFQUFFLFVBQVUsRUFBRSxzQkFBUSxDQUFDLElBQUksQ0FBQyxFQUFFLENBQUMsRUFBRSxDQUFDO29CQUNuRCxhQUFhLEVBQUUsMkJBQWEsQ0FBQyxPQUFPO2lCQUNyQyxDQUFDO1lBQ0osS0FBSyxRQUFRO2dCQUNYLE9BQU87b0JBQ0wsY0FBYyxFQUFFLENBQUMsRUFBRSxVQUFVLEVBQUUsc0JBQVEsQ0FBQyxJQUFJLENBQUMsRUFBRSxDQUFDLEVBQUUsQ0FBQztvQkFDbkQsYUFBYSxFQUFFLDJCQUFhLENBQUMsT0FBTztpQkFDckMsQ0FBQztZQUNKO2dCQUNFLE9BQU87b0JBQ0wsY0FBYyxFQUFFLEVBQUU7b0JBQ2xCLGFBQWEsRUFBRSwyQkFBYSxDQUFDLE1BQU07aUJBQ3BDLENBQUM7UUFDTixDQUFDO0lBQ0gsQ0FBQztJQUVEOzs7Ozs7O09BT0c7SUFDSCxLQUFLLENBQUMsSUFBZ0I7UUFDcEIsSUFBSSxJQUFJLFlBQVksZUFBTSxFQUFFLENBQUM7WUFDM0IsTUFBTSxFQUFFLGNBQWMsRUFBRSxhQUFhLEVBQUUsR0FBRyxJQUFJLENBQUMsWUFBWSxDQUFDO1lBQzVELElBQUksYUFBYSxFQUFFLENBQUM7Z0JBQ2xCLElBQUksQ0FBQyxrQkFBa0IsQ0FBQyxhQUFhLENBQUMsQ0FBQztZQUN6QyxDQUFDO1lBRUQsSUFBSSxjQUFjLGFBQWQsY0FBYyx1QkFBZCxjQUFjLENBQUUsTUFBTSxFQUFFLENBQUM7Z0JBQzNCLE1BQU0sU0FBUyxHQUFHLElBQUksQ0FBQyxJQUFJLENBQUMsWUFBeUIsQ0FBQztnQkFDdEQsSUFBSSxTQUFTLElBQUksU0FBUyxDQUFDLHNCQUFzQixLQUFLLFNBQVMsRUFBRSxDQUFDO29CQUNoRSxjQUFjLENBQUMsT0FBTyxDQUFDLElBQUksQ0FBQyxFQUFFLENBQUMsSUFBSSxDQUFDLGdCQUFnQixDQUFDLElBQUksQ0FBQyxDQUFDLENBQUM7Z0JBQzlELENBQUM7WUFDSCxDQUFDO1FBQ0gsQ0FBQztJQUNILENBQUM7Q0FDRjtBQTlERCw0Q0E4REMiLCJzb3VyY2VzQ29udGVudCI6WyJpbXBvcnQgeyBEdXJhdGlvbiwgUmVtb3ZhbFBvbGljeSwgdHlwZSBJQXNwZWN0IH0gZnJvbSBcImF3cy1jZGstbGliXCI7XG5pbXBvcnQgeyBCdWNrZXQsIENmbkJ1Y2tldCwgdHlwZSBCdWNrZXRQcm9wcyB9IGZyb20gXCJhd3MtY2RrLWxpYi9hd3MtczNcIjtcbmltcG9ydCB7IElDb25zdHJ1Y3QgfSBmcm9tIFwiY29uc3RydWN0c1wiO1xuXG5pbnRlcmZhY2UgQ29uZmlnIHtcbiAgZHVyYXRpb246IFwiU0hPUlRcIiB8IFwiTUVESVVNXCIgfCBcIkxPTkdcIjtcbn1cblxuLyoqXG4gKiBBc3BlY3QgdGhhdCBhdXRvbWF0aWNhbGx5IGFwcGxpZXMgY29uZmlndXJhdGlvbi1hd2FyZSBkZWZhdWx0cyB0byBTMyBCdWNrZXRzXG4gKlxuICogVmlzaXRzIGFsbCBjb25zdHJ1Y3RzIGluIHRoZSBzY29wZSBhbmQgYXV0b21hdGljYWxseSBhcHBsaWVzIGNvbmZpZ3VyYXRpb24tc3BlY2lmaWNcbiAqIGxpZmVjeWNsZSBhbmQgcmVtb3ZhbCBwb2xpY2llcyB0byBTMyBidWNrZXRzLiBEaWZmZXJlbnQgY29uZmlndXJhdGlvbnMgYmFsYW5jZVxuICogYmV0d2VlbiBjb3N0IG9wdGltaXphdGlvbiBhbmQgZGF0YSByZXRlbnRpb24gbmVlZHMuXG4gKlxuICogQGV4YW1wbGVcbiAqIGBgYHR5cGVzY3JpcHRcbiAqIC8vIEFwcGx5IGNvbmZpZ3VyYXRpb24tc3BlY2lmaWMgZGVmYXVsdHMgdG8gYWxsIGJ1Y2tldHNcbiAqIEFzcGVjdHMub2YoYXBwKS5hZGQobmV3IFMzRGVmYXVsdHNBc3BlY3QoeyBhdXRvRGVsZXRlOiB0cnVlLCBkdXJhdGlvbjogJ1NIT1JUJyB9KSk7XG4gKlxuICogLy8gQnVja2V0cyBhdXRvbWF0aWNhbGx5IGluaGVyaXQgY29uZmlndXJhdGlvbiBkZWZhdWx0c1xuICogbmV3IEJ1Y2tldChzdGFjaywgJ015QnVja2V0Jywge1xuICogICAvLyBsaWZlY3ljbGUgYW5kIHJlbW92YWwgcG9saWN5IGFwcGxpZWQgYXV0b21hdGljYWxseVxuICogfSk7XG4gKiBgYGBcbiAqXG4gKiBAc2VlIGh0dHBzOi8vZG9jcy5hd3MuYW1hem9uLmNvbS9jZGsvYXBpL3YyL2RvY3MvYXdzLWNkay1saWIuYXdzX3MzLkJ1Y2tldC5odG1sXG4gKi9cbmV4cG9ydCBjbGFzcyBTM0RlZmF1bHRzQXNwZWN0IGltcGxlbWVudHMgSUFzcGVjdCB7XG4gIHByaXZhdGUgcmVhZG9ubHkgZGVmYXVsdFByb3BzOiBCdWNrZXRQcm9wcztcblxuICAvKipcbiAgICogQ3JlYXRlcyBhIG5ldyBTM0RlZmF1bHRzQXNwZWN0XG4gICAqXG4gICAqIEBwYXJhbSBjb25maWcgLSBDb25maWd1cmF0aW9uIGlkZW50aWZpZXIgdXNlZCB0byBzZWxlY3QgYXBwcm9wcmlhdGUgZGVmYXVsdHMuXG4gICAqL1xuICBjb25zdHJ1Y3Rvcihjb25maWc6IENvbmZpZykge1xuICAgIGNvbnN0IHByb3BzID0gdGhpcy5yZXRlbnRpb25Qcm9wZXJ0aWVzKGNvbmZpZy5kdXJhdGlvbik7XG4gICAgdGhpcy5kZWZhdWx0UHJvcHMgPSB7IC4uLnByb3BzIH07XG4gIH1cblxuICAvKipcbiAgICogR2V0IGR1cmF0aW9uLXNwZWNpZmljIG9iamVjdCBleHBpcmF0aW9uXG4gICAqXG4gICAqIEBwYXJhbSBkdXJhdGlvbiAtIFRoZSBkdXJhdGlvbiB0byBnZXQgdGhlIGV4cGlyYXRpb24gZm9yXG4gICAqIEByZXR1cm5zIFRoZSBleHBpcmF0aW9uIER1cmF0aW9uLCBvciB1bmRlZmluZWQgZm9yIExPTkcgcmV0ZW50aW9uXG4gICAqL1xuICBwcml2YXRlIHJldGVudGlvblByb3BlcnRpZXMoZHVyYXRpb246IFwiU0hPUlRcIiB8IFwiTUVESVVNXCIgfCBcIkxPTkdcIikge1xuICAgIHN3aXRjaCAoZHVyYXRpb24pIHtcbiAgICAgIGNhc2UgXCJTSE9SVFwiOlxuICAgICAgICByZXR1cm4ge1xuICAgICAgICAgIGxpZmVjeWNsZVJ1bGVzOiBbeyBleHBpcmF0aW9uOiBEdXJhdGlvbi5kYXlzKDMwKSB9XSxcbiAgICAgICAgICByZW1vdmFsUG9saWN5OiBSZW1vdmFsUG9saWN5LkRFU1RST1ksXG4gICAgICAgIH07XG4gICAgICBjYXNlIFwiTUVESVVNXCI6XG4gICAgICAgIHJldHVybiB7XG4gICAgICAgICAgbGlmZWN5Y2xlUnVsZXM6IFt7IGV4cGlyYXRpb246IER1cmF0aW9uLmRheXMoOTApIH1dLFxuICAgICAgICAgIHJlbW92YWxQb2xpY3k6IFJlbW92YWxQb2xpY3kuREVTVFJPWSxcbiAgICAgICAgfTtcbiAgICAgIGRlZmF1bHQ6XG4gICAgICAgIHJldHVybiB7XG4gICAgICAgICAgbGlmZWN5Y2xlUnVsZXM6IFtdLFxuICAgICAgICAgIHJlbW92YWxQb2xpY3k6IFJlbW92YWxQb2xpY3kuUkVUQUlOLFxuICAgICAgICB9O1xuICAgIH1cbiAgfVxuXG4gIC8qKlxuICAgKiBWaXNpdHMgYSBjb25zdHJ1Y3QgYW5kIGFwcGxpZXMgY29uZmlndXJhdGlvbi1hcHByb3ByaWF0ZSBkZWZhdWx0c1xuICAgKlxuICAgKiBBcHBsaWVzIGEgcmVtb3ZhbCBwb2xpY3kgYW5kIGxpZmVjeWNsZSBydWxlcyB0byBidWNrZXRzIHRoYXQgZG9uJ3RcbiAgICogYWxyZWFkeSBoYXZlIGEgbGlmZWN5Y2xlIGNvbmZpZ3VyYXRpb24gZXhwbGljaXRseSBzZXQuXG4gICAqXG4gICAqIEBwYXJhbSBub2RlIC0gVGhlIGNvbnN0cnVjdCB0byBwb3RlbnRpYWxseSBtb2RpZnlcbiAgICovXG4gIHZpc2l0KG5vZGU6IElDb25zdHJ1Y3QpOiB2b2lkIHtcbiAgICBpZiAobm9kZSBpbnN0YW5jZW9mIEJ1Y2tldCkge1xuICAgICAgY29uc3QgeyBsaWZlY3ljbGVSdWxlcywgcmVtb3ZhbFBvbGljeSB9ID0gdGhpcy5kZWZhdWx0UHJvcHM7XG4gICAgICBpZiAocmVtb3ZhbFBvbGljeSkge1xuICAgICAgICBub2RlLmFwcGx5UmVtb3ZhbFBvbGljeShyZW1vdmFsUG9saWN5KTtcbiAgICAgIH1cblxuICAgICAgaWYgKGxpZmVjeWNsZVJ1bGVzPy5sZW5ndGgpIHtcbiAgICAgICAgY29uc3QgY2ZuQnVja2V0ID0gbm9kZS5ub2RlLmRlZmF1bHRDaGlsZCBhcyBDZm5CdWNrZXQ7XG4gICAgICAgIGlmIChjZm5CdWNrZXQgJiYgY2ZuQnVja2V0LmxpZmVjeWNsZUNvbmZpZ3VyYXRpb24gPT09IHVuZGVmaW5lZCkge1xuICAgICAgICAgIGxpZmVjeWNsZVJ1bGVzLmZvckVhY2gocnVsZSA9PiBub2RlLmFkZExpZmVjeWNsZVJ1bGUocnVsZSkpO1xuICAgICAgICB9XG4gICAgICB9XG4gICAgfVxuICB9XG59XG4iXX0=
|