cdk-nextjs 0.0.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.
Files changed (125) hide show
  1. package/.jsii +13811 -0
  2. package/.prettierrc +0 -0
  3. package/API.md +9694 -0
  4. package/LICENSE +202 -0
  5. package/README.md +137 -0
  6. package/THIRD-PARTY-LICENSES.md +31 -0
  7. package/assets/lambdas/assets-deployment/assets-deployment.lambda/assets-deployment.Dockerfile +18 -0
  8. package/assets/lambdas/assets-deployment/assets-deployment.lambda/index.js +8831 -0
  9. package/assets/lambdas/revalidate/revalidate.lambda/index.js +67 -0
  10. package/assets/lambdas/sign-fn-url/sign-fn-url.lambda/index.js +2002 -0
  11. package/examples/README.md +14 -0
  12. package/lib/common.d.ts +23 -0
  13. package/lib/common.js +28 -0
  14. package/lib/generated-structs/OptionalApplicationLoadBalancedTaskImageOptions.d.ts +106 -0
  15. package/lib/generated-structs/OptionalApplicationLoadBalancedTaskImageOptions.js +3 -0
  16. package/lib/generated-structs/OptionalCloudFrontFunctionProps.d.ts +43 -0
  17. package/lib/generated-structs/OptionalCloudFrontFunctionProps.js +3 -0
  18. package/lib/generated-structs/OptionalClusterProps.d.ts +49 -0
  19. package/lib/generated-structs/OptionalClusterProps.js +3 -0
  20. package/lib/generated-structs/OptionalDistributionProps.d.ts +155 -0
  21. package/lib/generated-structs/OptionalDistributionProps.js +3 -0
  22. package/lib/generated-structs/OptionalDockerImageAssetProps.d.ts +124 -0
  23. package/lib/generated-structs/OptionalDockerImageAssetProps.js +3 -0
  24. package/lib/generated-structs/OptionalDockerImageFunctionProps.d.ts +399 -0
  25. package/lib/generated-structs/OptionalDockerImageFunctionProps.js +3 -0
  26. package/lib/generated-structs/OptionalEdgeFunctionProps.d.ts +428 -0
  27. package/lib/generated-structs/OptionalEdgeFunctionProps.js +3 -0
  28. package/lib/generated-structs/OptionalFunctionProps.d.ts +422 -0
  29. package/lib/generated-structs/OptionalFunctionProps.js +3 -0
  30. package/lib/generated-structs/OptionalFunctionUrlProps.d.ts +30 -0
  31. package/lib/generated-structs/OptionalFunctionUrlProps.js +3 -0
  32. package/lib/generated-structs/OptionalNextjsAssetsDeploymentProps.d.ts +45 -0
  33. package/lib/generated-structs/OptionalNextjsAssetsDeploymentProps.js +3 -0
  34. package/lib/generated-structs/OptionalNextjsBuildProps.d.ts +30 -0
  35. package/lib/generated-structs/OptionalNextjsBuildProps.js +3 -0
  36. package/lib/generated-structs/OptionalNextjsContainersProps.d.ts +43 -0
  37. package/lib/generated-structs/OptionalNextjsContainersProps.js +3 -0
  38. package/lib/generated-structs/OptionalNextjsDistributionProps.d.ts +50 -0
  39. package/lib/generated-structs/OptionalNextjsDistributionProps.js +3 -0
  40. package/lib/generated-structs/OptionalNextjsFileSystemProps.d.ts +15 -0
  41. package/lib/generated-structs/OptionalNextjsFileSystemProps.js +3 -0
  42. package/lib/generated-structs/OptionalNextjsInvalidationProps.d.ts +17 -0
  43. package/lib/generated-structs/OptionalNextjsInvalidationProps.js +3 -0
  44. package/lib/generated-structs/OptionalNextjsVpcProps.d.ts +21 -0
  45. package/lib/generated-structs/OptionalNextjsVpcProps.js +3 -0
  46. package/lib/generated-structs/OptionalS3OriginProps.d.ts +64 -0
  47. package/lib/generated-structs/OptionalS3OriginProps.js +3 -0
  48. package/lib/generated-structs/OptionalVpcProps.d.ts +224 -0
  49. package/lib/generated-structs/OptionalVpcProps.js +3 -0
  50. package/lib/index.d.ts +35 -0
  51. package/lib/index.js +32 -0
  52. package/lib/lambdas/assets-deployment/assets-deployment-function.d.ts +13 -0
  53. package/lib/lambdas/assets-deployment/assets-deployment-function.js +23 -0
  54. package/lib/lambdas/assets-deployment/assets-deployment.lambda.d.ts +2 -0
  55. package/lib/lambdas/assets-deployment/assets-deployment.lambda.js +62 -0
  56. package/lib/lambdas/assets-deployment/common.d.ts +8 -0
  57. package/lib/lambdas/assets-deployment/common.js +32 -0
  58. package/lib/lambdas/assets-deployment/fs-to-fs.d.ts +2 -0
  59. package/lib/lambdas/assets-deployment/fs-to-fs.js +9 -0
  60. package/lib/lambdas/assets-deployment/fs-to-s3.d.ts +2 -0
  61. package/lib/lambdas/assets-deployment/fs-to-s3.js +45 -0
  62. package/lib/lambdas/assets-deployment/prune-s3.d.ts +15 -0
  63. package/lib/lambdas/assets-deployment/prune-s3.js +42 -0
  64. package/lib/lambdas/assets-deployment/s3.d.ts +2 -0
  65. package/lib/lambdas/assets-deployment/s3.js +7 -0
  66. package/lib/lambdas/assets-deployment/utils.d.ts +18 -0
  67. package/lib/lambdas/assets-deployment/utils.js +35 -0
  68. package/lib/lambdas/revalidate/revalidate-function.d.ts +13 -0
  69. package/lib/lambdas/revalidate/revalidate-function.js +23 -0
  70. package/lib/lambdas/revalidate/revalidate.lambda.d.ts +2 -0
  71. package/lib/lambdas/revalidate/revalidate.lambda.js +53 -0
  72. package/lib/lambdas/sign-fn-url/sign-fn-url-function.d.ts +13 -0
  73. package/lib/lambdas/sign-fn-url/sign-fn-url-function.js +23 -0
  74. package/lib/lambdas/sign-fn-url/sign-fn-url.lambda.d.ts +9 -0
  75. package/lib/lambdas/sign-fn-url/sign-fn-url.lambda.js +35 -0
  76. package/lib/lambdas/sign-fn-url/sign-request.d.ts +28 -0
  77. package/lib/lambdas/sign-fn-url/sign-request.js +119 -0
  78. package/lib/lambdas/sign-fn-url/sign-request.test.d.ts +1 -0
  79. package/lib/lambdas/sign-fn-url/sign-request.test.js +129 -0
  80. package/lib/nextjs-assets-deployment.d.ts +116 -0
  81. package/lib/nextjs-assets-deployment.js +93 -0
  82. package/lib/nextjs-build/add-cache-handler.d.ts +1 -0
  83. package/lib/nextjs-build/add-cache-handler.js +23 -0
  84. package/lib/nextjs-build/add-cache-handler.mjs +18 -0
  85. package/lib/nextjs-build/builder.Dockerfile +29 -0
  86. package/lib/nextjs-build/cache-handler.cjs +21513 -0
  87. package/lib/nextjs-build/cache-handler.d.ts +6 -0
  88. package/lib/nextjs-build/cache-handler.js +22 -0
  89. package/lib/nextjs-build/global-containers.Dockerfile +45 -0
  90. package/lib/nextjs-build/global-functions.Dockerfile +46 -0
  91. package/lib/nextjs-build/nextjs-build.d.ts +150 -0
  92. package/lib/nextjs-build/nextjs-build.js +220 -0
  93. package/lib/nextjs-build/regional-containers.Dockerfile +45 -0
  94. package/lib/nextjs-build/symlink-full-route-cache.d.ts +1 -0
  95. package/lib/nextjs-build/symlink-full-route-cache.js +37 -0
  96. package/lib/nextjs-build/symlink-full-route-cache.mjs +23 -0
  97. package/lib/nextjs-compute/nextjs-compute-base-props.d.ts +8 -0
  98. package/lib/nextjs-compute/nextjs-compute-base-props.js +3 -0
  99. package/lib/nextjs-compute/nextjs-containers.d.ts +43 -0
  100. package/lib/nextjs-compute/nextjs-containers.js +149 -0
  101. package/lib/nextjs-compute/nextjs-functions.d.ts +23 -0
  102. package/lib/nextjs-compute/nextjs-functions.js +57 -0
  103. package/lib/nextjs-distribution.d.ts +120 -0
  104. package/lib/nextjs-distribution.js +362 -0
  105. package/lib/nextjs-file-system.d.ts +42 -0
  106. package/lib/nextjs-file-system.js +74 -0
  107. package/lib/nextjs-invalidation.d.ts +19 -0
  108. package/lib/nextjs-invalidation.js +52 -0
  109. package/lib/nextjs-revalidation.d.ts +30 -0
  110. package/lib/nextjs-revalidation.js +65 -0
  111. package/lib/nextjs-static-assets.d.ts +21 -0
  112. package/lib/nextjs-static-assets.js +32 -0
  113. package/lib/nextjs-vpc.d.ts +42 -0
  114. package/lib/nextjs-vpc.js +64 -0
  115. package/lib/root-constructs/nextjs-base-overrides.d.ts +26 -0
  116. package/lib/root-constructs/nextjs-base-overrides.js +3 -0
  117. package/lib/root-constructs/nextjs-base-props.d.ts +56 -0
  118. package/lib/root-constructs/nextjs-base-props.js +3 -0
  119. package/lib/root-constructs/nextjs-global-containers.d.ts +74 -0
  120. package/lib/root-constructs/nextjs-global-containers.js +125 -0
  121. package/lib/root-constructs/nextjs-global-functions.d.ts +76 -0
  122. package/lib/root-constructs/nextjs-global-functions.js +131 -0
  123. package/lib/root-constructs/nextjs-regional-containers.d.ts +43 -0
  124. package/lib/root-constructs/nextjs-regional-containers.js +92 -0
  125. package/package.json +165 -0
@@ -0,0 +1,23 @@
1
+ // src/nextjs-build/symlink-full-route-cache.ts
2
+ import { mkdirSync, readdirSync, rmSync, symlinkSync } from "node:fs";
3
+ import { extname, join } from "node:path";
4
+ function createSymlinks(srcPath, destPath2) {
5
+ mkdirSync(destPath2, { recursive: true });
6
+ const entries = readdirSync(srcPath, { withFileTypes: true });
7
+ for (const entry of entries) {
8
+ const entryPath = join(srcPath, entry.name);
9
+ if (entry.isDirectory()) {
10
+ createSymlinks(entryPath, join(destPath2, entry.name));
11
+ } else if (entry.isFile()) {
12
+ const ext = extname(entryPath).slice(1);
13
+ if (["html", "rsc", "meta"].includes(ext)) {
14
+ const symlink = entryPath;
15
+ const target = join(destPath2, entry.name);
16
+ rmSync(symlink);
17
+ symlinkSync(target, symlink, "file");
18
+ }
19
+ }
20
+ }
21
+ }
22
+ var [sourcePath, destPath] = process.argv.slice(2);
23
+ createSymlinks(sourcePath, destPath);
@@ -0,0 +1,8 @@
1
+ import { IVpc } from "aws-cdk-lib/aws-ec2";
2
+ import { AccessPoint } from "aws-cdk-lib/aws-efs";
3
+ export interface NextjsComputeBaseProps {
4
+ readonly accessPoint: AccessPoint;
5
+ readonly containerMountPathForEfs: string;
6
+ readonly healthCheckPath: string;
7
+ readonly vpc: IVpc;
8
+ }
@@ -0,0 +1,3 @@
1
+ "use strict";
2
+ Object.defineProperty(exports, "__esModule", { value: true });
3
+ //# sourceMappingURL=data:application/json;base64,eyJ2ZXJzaW9uIjozLCJmaWxlIjoibmV4dGpzLWNvbXB1dGUtYmFzZS1wcm9wcy5qcyIsInNvdXJjZVJvb3QiOiIiLCJzb3VyY2VzIjpbIi4uLy4uL3NyYy9uZXh0anMtY29tcHV0ZS9uZXh0anMtY29tcHV0ZS1iYXNlLXByb3BzLnRzIl0sIm5hbWVzIjpbXSwibWFwcGluZ3MiOiIiLCJzb3VyY2VzQ29udGVudCI6WyJpbXBvcnQgeyBJVnBjIH0gZnJvbSBcImF3cy1jZGstbGliL2F3cy1lYzJcIjtcbmltcG9ydCB7IEFjY2Vzc1BvaW50IH0gZnJvbSBcImF3cy1jZGstbGliL2F3cy1lZnNcIjtcblxuZXhwb3J0IGludGVyZmFjZSBOZXh0anNDb21wdXRlQmFzZVByb3BzIHtcbiAgcmVhZG9ubHkgYWNjZXNzUG9pbnQ6IEFjY2Vzc1BvaW50O1xuICByZWFkb25seSBjb250YWluZXJNb3VudFBhdGhGb3JFZnM6IHN0cmluZztcbiAgcmVhZG9ubHkgaGVhbHRoQ2hlY2tQYXRoOiBzdHJpbmc7XG4gIHJlYWRvbmx5IHZwYzogSVZwYztcbn1cbiJdfQ==
@@ -0,0 +1,43 @@
1
+ import { DockerImageAsset } from "aws-cdk-lib/aws-ecr-assets";
2
+ import { Cluster } from "aws-cdk-lib/aws-ecs";
3
+ import { ApplicationLoadBalancedFargateService, ApplicationLoadBalancedFargateServiceProps } from "aws-cdk-lib/aws-ecs-patterns";
4
+ import { FileSystem } from "aws-cdk-lib/aws-efs";
5
+ import { Construct } from "constructs";
6
+ import { NextjsComputeBaseProps } from "./nextjs-compute-base-props";
7
+ import { NextjsType } from "../common";
8
+ import { OptionalApplicationLoadBalancedTaskImageOptions } from "../generated-structs/OptionalApplicationLoadBalancedTaskImageOptions";
9
+ import { OptionalClusterProps } from "../generated-structs/OptionalClusterProps";
10
+ export interface NextjsContainersOverrides {
11
+ readonly ecsClusterProps?: OptionalClusterProps;
12
+ readonly albFargateServiceProps?: ApplicationLoadBalancedFargateServiceProps;
13
+ readonly taskImageOptions?: OptionalApplicationLoadBalancedTaskImageOptions;
14
+ }
15
+ export interface NextjsContainersProps extends NextjsComputeBaseProps {
16
+ readonly dockerImageAsset: DockerImageAsset;
17
+ readonly fileSystem: FileSystem;
18
+ readonly nextjsType: NextjsType;
19
+ readonly overrides?: NextjsContainersOverrides;
20
+ readonly relativeEntrypointPath: string;
21
+ }
22
+ /**
23
+ * Next.js load balanced via Application Load Balancer with containers via AWS
24
+ * Fargate.
25
+ */
26
+ export declare class NextjsContainers extends Construct {
27
+ albFargateService: ApplicationLoadBalancedFargateService;
28
+ ecsCluster: Cluster;
29
+ url: string;
30
+ private props;
31
+ constructor(scope: Construct, id: string, props: NextjsContainersProps);
32
+ private createEcsCluster;
33
+ private createAlbFargateSevice;
34
+ /**
35
+ * Configure health checks for containers at ALB and ECS level. This ensures
36
+ * unhealthy containers are removed. Both of these health checks can be
37
+ * overwritten by user by accessing `albFargateService` property, so no need
38
+ * for `overrides`.
39
+ */
40
+ private configureHealthCheck;
41
+ private attachFileSystem;
42
+ private getUrl;
43
+ }
@@ -0,0 +1,149 @@
1
+ "use strict";
2
+ var _a;
3
+ Object.defineProperty(exports, "__esModule", { value: true });
4
+ exports.NextjsContainers = void 0;
5
+ const JSII_RTTI_SYMBOL_1 = Symbol.for("jsii.rtti");
6
+ const aws_cdk_lib_1 = require("aws-cdk-lib");
7
+ const aws_ecs_1 = require("aws-cdk-lib/aws-ecs");
8
+ const aws_ecs_patterns_1 = require("aws-cdk-lib/aws-ecs-patterns");
9
+ const aws_elasticloadbalancingv2_1 = require("aws-cdk-lib/aws-elasticloadbalancingv2");
10
+ const constructs_1 = require("constructs");
11
+ /**
12
+ * Next.js load balanced via Application Load Balancer with containers via AWS
13
+ * Fargate.
14
+ */
15
+ class NextjsContainers extends constructs_1.Construct {
16
+ constructor(scope, id, props) {
17
+ super(scope, id);
18
+ this.props = props;
19
+ this.ecsCluster = this.createEcsCluster();
20
+ this.albFargateService = this.createAlbFargateSevice();
21
+ this.configureHealthCheck();
22
+ this.attachFileSystem();
23
+ this.url = this.getUrl();
24
+ }
25
+ createEcsCluster() {
26
+ const cluster = new aws_ecs_1.Cluster(this, "EcsCluster", {
27
+ enableFargateCapacityProviders: true,
28
+ containerInsights: true,
29
+ vpc: this.props.vpc,
30
+ ...this.props.overrides?.ecsClusterProps,
31
+ });
32
+ return cluster;
33
+ }
34
+ createAlbFargateSevice() {
35
+ let cpuArchitecture = undefined;
36
+ if (process.arch === "x64") {
37
+ cpuArchitecture = aws_ecs_1.CpuArchitecture.X86_64;
38
+ }
39
+ else if (process.arch === "arm64") {
40
+ cpuArchitecture = aws_ecs_1.CpuArchitecture.ARM64;
41
+ }
42
+ const albFargateService = new aws_ecs_patterns_1.ApplicationLoadBalancedFargateService(this, "AlbFargateService", {
43
+ circuitBreaker: { rollback: true, enable: true },
44
+ cluster: this.ecsCluster,
45
+ cpu: 1024,
46
+ healthCheckGracePeriod: aws_cdk_lib_1.Duration.seconds(10),
47
+ maxHealthyPercent: 200,
48
+ memoryLimitMiB: 2048,
49
+ minHealthyPercent: 100, // maintain service availability during deployment
50
+ /*
51
+ This protocol version is for the target group (Fargate), not the ALB
52
+ Listener. From docs, "Application Load Balancers provide native support
53
+ for HTTP/2 with HTTPS listeners". See https://docs.aws.amazon.com/elasticloadbalancing/latest/application/load-balancer-listeners.html
54
+ Next.js default server does not support HTTP/2 as it's recommended
55
+ to proxy your Next.js server which we're doing with ALB.
56
+ Also note, CloudFront only supports HTTP/1.1 origins.
57
+ https://docs.aws.amazon.com/AmazonCloudFront/latest/DeveloperGuide/RequestAndResponseBehaviorCustomOrigin.html#RequestCustomHTTPVersion
58
+ */
59
+ protocolVersion: aws_elasticloadbalancingv2_1.ApplicationProtocolVersion.HTTP1,
60
+ runtimePlatform: {
61
+ cpuArchitecture,
62
+ },
63
+ taskImageOptions: {
64
+ command: ["node", this.props.relativeEntrypointPath],
65
+ containerName: "nextjs",
66
+ containerPort: 3000,
67
+ image: aws_ecs_1.ContainerImage.fromDockerImageAsset(this.props.dockerImageAsset),
68
+ logDriver: aws_ecs_1.LogDrivers.awsLogs({
69
+ streamPrefix: "nextjs",
70
+ mode: aws_ecs_1.AwsLogDriverMode.NON_BLOCKING,
71
+ }),
72
+ ...this.props.overrides?.taskImageOptions,
73
+ },
74
+ ...this.props.overrides?.albFargateServiceProps,
75
+ });
76
+ // required or health checks fail
77
+ albFargateService.taskDefinition.defaultContainer?.addEnvironment("HOSTNAME", "0.0.0.0");
78
+ // security best practice to enforce readonly for root filesystem
79
+ // hopefully https://github.com/aws/aws-cdk/issues/23935 will result in
80
+ // easier way to set this property
81
+ const cfnTaskDef = albFargateService.taskDefinition.node
82
+ .defaultChild;
83
+ cfnTaskDef.addPropertyOverride("ContainerDefinitions.0.ReadonlyRootFilesystem", true);
84
+ // speed up deployments by shortening deregistration delay
85
+ // https://docs.aws.amazon.com/AmazonECS/latest/bestpracticesguide/load-balancer-connection-draining.html
86
+ // TODO: document that this should be increased if long lived connections are expected
87
+ albFargateService.targetGroup.setAttribute("deregistration_delay.timeout_seconds", "30");
88
+ // best practice to enable cross zone load balancing
89
+ // @see https://docs.aws.amazon.com/elasticloadbalancing/latest/application/disable-cross-zone.html
90
+ albFargateService.loadBalancer.setAttribute("load_balancing.cross_zone.enabled", "true");
91
+ return albFargateService;
92
+ }
93
+ /**
94
+ * Configure health checks for containers at ALB and ECS level. This ensures
95
+ * unhealthy containers are removed. Both of these health checks can be
96
+ * overwritten by user by accessing `albFargateService` property, so no need
97
+ * for `overrides`.
98
+ */
99
+ configureHealthCheck() {
100
+ // speed up deployments by shortening health checks
101
+ // see https://docs.aws.amazon.com/AmazonECS/latest/bestpracticesguide/load-balancer-healthcheck.html
102
+ this.albFargateService.targetGroup.configureHealthCheck({
103
+ path: this.props.healthCheckPath,
104
+ healthyThresholdCount: 2,
105
+ interval: aws_cdk_lib_1.Duration.seconds(10), // too frequent? but enables faster rollback...
106
+ timeout: aws_cdk_lib_1.Duration.seconds(5), // must be less than interval
107
+ });
108
+ const healthCheck = {
109
+ command: [
110
+ "CMD-SHELL",
111
+ // curl isn't available in alpine linux
112
+ `wget --quiet --tries=1 --spider http://localhost:3000${this.props.healthCheckPath} || exit 1`,
113
+ ],
114
+ };
115
+ const defaultContainer = this.albFargateService.taskDefinition.defaultContainer;
116
+ if (defaultContainer) {
117
+ // @ts-expect-error must use internal "props" attribute b/c no other way to add health check
118
+ defaultContainer.props.healthCheck = healthCheck;
119
+ }
120
+ }
121
+ attachFileSystem() {
122
+ const container = this.albFargateService.taskDefinition.defaultContainer;
123
+ const volumeName = "cdk-nextjs-volume";
124
+ this.albFargateService.taskDefinition.addVolume({
125
+ name: volumeName,
126
+ efsVolumeConfiguration: {
127
+ fileSystemId: this.props.fileSystem.fileSystemId,
128
+ transitEncryption: "ENABLED",
129
+ authorizationConfig: {
130
+ accessPointId: this.props.accessPoint.accessPointId,
131
+ iam: "ENABLED",
132
+ },
133
+ },
134
+ });
135
+ container?.addMountPoints({
136
+ sourceVolume: volumeName,
137
+ containerPath: this.props.containerMountPathForEfs,
138
+ readOnly: false,
139
+ });
140
+ }
141
+ getUrl() {
142
+ const protocol = this.albFargateService.certificate ? "https" : "http";
143
+ return `${protocol}://${this.albFargateService.loadBalancer.loadBalancerDnsName}`;
144
+ }
145
+ }
146
+ exports.NextjsContainers = NextjsContainers;
147
+ _a = JSII_RTTI_SYMBOL_1;
148
+ NextjsContainers[_a] = { fqn: "cdk-nextjs.NextjsContainers", version: "0.0.0" };
149
+ //# sourceMappingURL=data:application/json;base64,eyJ2ZXJzaW9uIjozLCJmaWxlIjoibmV4dGpzLWNvbnRhaW5lcnMuanMiLCJzb3VyY2VSb290IjoiIiwic291cmNlcyI6WyIuLi8uLi9zcmMvbmV4dGpzLWNvbXB1dGUvbmV4dGpzLWNvbnRhaW5lcnMudHMiXSwibmFtZXMiOltdLCJtYXBwaW5ncyI6Ijs7Ozs7QUFBQSw2Q0FBdUM7QUFFdkMsaURBUTZCO0FBQzdCLG1FQUdzQztBQUV0Qyx1RkFBb0Y7QUFDcEYsMkNBQXVDO0FBb0J2Qzs7O0dBR0c7QUFDSCxNQUFhLGdCQUFpQixTQUFRLHNCQUFTO0lBTzdDLFlBQVksS0FBZ0IsRUFBRSxFQUFVLEVBQUUsS0FBNEI7UUFDcEUsS0FBSyxDQUFDLEtBQUssRUFBRSxFQUFFLENBQUMsQ0FBQztRQUNqQixJQUFJLENBQUMsS0FBSyxHQUFHLEtBQUssQ0FBQztRQUNuQixJQUFJLENBQUMsVUFBVSxHQUFHLElBQUksQ0FBQyxnQkFBZ0IsRUFBRSxDQUFDO1FBQzFDLElBQUksQ0FBQyxpQkFBaUIsR0FBRyxJQUFJLENBQUMsc0JBQXNCLEVBQUUsQ0FBQztRQUN2RCxJQUFJLENBQUMsb0JBQW9CLEVBQUUsQ0FBQztRQUM1QixJQUFJLENBQUMsZ0JBQWdCLEVBQUUsQ0FBQztRQUN4QixJQUFJLENBQUMsR0FBRyxHQUFHLElBQUksQ0FBQyxNQUFNLEVBQUUsQ0FBQztJQUMzQixDQUFDO0lBRU8sZ0JBQWdCO1FBQ3RCLE1BQU0sT0FBTyxHQUFHLElBQUksaUJBQU8sQ0FBQyxJQUFJLEVBQUUsWUFBWSxFQUFFO1lBQzlDLDhCQUE4QixFQUFFLElBQUk7WUFDcEMsaUJBQWlCLEVBQUUsSUFBSTtZQUN2QixHQUFHLEVBQUUsSUFBSSxDQUFDLEtBQUssQ0FBQyxHQUFHO1lBQ25CLEdBQUcsSUFBSSxDQUFDLEtBQUssQ0FBQyxTQUFTLEVBQUUsZUFBZTtTQUN6QyxDQUFDLENBQUM7UUFDSCxPQUFPLE9BQU8sQ0FBQztJQUNqQixDQUFDO0lBQ08sc0JBQXNCO1FBQzVCLElBQUksZUFBZSxHQUFnQyxTQUFTLENBQUM7UUFD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RSxPQUFPLEdBQUcsUUFBUSxNQUFNLElBQUksQ0FBQyxpQkFBaUIsQ0FBQyxZQUFZLENBQUMsbUJBQW1CLEVBQUUsQ0FBQztJQUNwRixDQUFDOztBQTFKSCw0Q0EySkMiLCJzb3VyY2VzQ29udGVudCI6WyJpbXBvcnQgeyBEdXJhdGlvbiB9IGZyb20gXCJhd3MtY2RrLWxpYlwiO1xuaW1wb3J0IHsgRG9ja2VySW1hZ2VBc3NldCB9IGZyb20gXCJhd3MtY2RrLWxpYi9hd3MtZWNyLWFzc2V0c1wiO1xuaW1wb3J0IHtcbiAgQXdzTG9nRHJpdmVyTW9kZSxcbiAgQ2ZuVGFza0RlZmluaXRpb24sXG4gIENsdXN0ZXIsXG4gIENvbnRhaW5lckltYWdlLFxuICBDcHVBcmNoaXRlY3R1cmUsXG4gIEhlYWx0aENoZWNrLFxuICBMb2dEcml2ZXJzLFxufSBmcm9tIFwiYXdzLWNkay1saWIvYXdzLWVjc1wiO1xuaW1wb3J0IHtcbiAgQXBwbGljYXRpb25Mb2FkQmFsYW5jZWRGYXJnYXRlU2VydmljZSxcbiAgQXBwbGljYXRpb25Mb2FkQmFsYW5jZWRGYXJnYXRlU2VydmljZVByb3BzLFxufSBmcm9tIFwiYXdzLWNkay1saWIvYXdzLWVjcy1wYXR0ZXJuc1wiO1xuaW1wb3J0IHsgRmlsZVN5c3RlbSB9IGZyb20gXCJhd3MtY2RrLWxpYi9hd3MtZWZzXCI7XG5pbXBvcnQgeyBBcHBsaWNhdGlvblByb3RvY29sVmVyc2lvbiB9IGZyb20gXCJhd3MtY2RrLWxpYi9hd3MtZWxhc3RpY2xvYWRiYWxhbmNpbmd2MlwiO1xuaW1wb3J0IHsgQ29uc3RydWN0IH0gZnJvbSBcImNvbnN0cnVjdHNcIjtcbmltcG9ydCB7IE5leHRqc0NvbXB1dGVCYXNlUHJvcHMgfSBmcm9tIFwiLi9uZXh0anMtY29tcHV0ZS1iYXNlLXByb3BzXCI7XG5pbXBvcnQgeyBOZXh0anNUeXBlIH0gZnJvbSBcIi4uL2NvbW1vblwiO1xuaW1wb3J0IHsgT3B0aW9uYWxBcHBsaWNhdGlvbkxvYWRCYWxhbmNlZFRhc2tJbWFnZU9wdGlvbnMgfSBmcm9tIFwiLi4vZ2VuZXJhdGVkLXN0cnVjdHMvT3B0aW9uYWxBcHBsaWNhdGlvbkxvYWRCYWxhbmNlZFRhc2tJbWFnZU9wdGlvbnNcIjtcbmltcG9ydCB7IE9wdGlvbmFsQ2x1c3RlclByb3BzIH0gZnJvbSBcIi4uL2dlbmVyYXRlZC1zdHJ1Y3RzL09wdGlvbmFsQ2x1c3RlclByb3BzXCI7XG5cbmV4cG9ydCBpbnRlcmZhY2UgTmV4dGpzQ29udGFpbmVyc092ZXJyaWRlcyB7XG4gIHJlYWRvbmx5IGVjc0NsdXN0ZXJQcm9wcz86IE9wdGlvbmFsQ2x1c3RlclByb3BzO1xuICByZWFkb25seSBhbGJGYXJnYXRlU2VydmljZVByb3BzPzogQXBwbGljYXRpb25Mb2FkQmFsYW5jZWRGYXJnYXRlU2VydmljZVByb3BzO1xuICByZWFkb25seSB0YXNrSW1hZ2VPcHRpb25zPzogT3B0aW9uYWxBcHBsaWNhdGlvbkxvYWRCYWxhbmNlZFRhc2tJbWFnZU9wdGlvbnM7XG59XG5cbmV4cG9ydCBpbnRlcmZhY2UgTmV4dGpzQ29udGFpbmVyc1Byb3BzIGV4dGVuZHMgTmV4dGpzQ29tcHV0ZUJhc2VQcm9wcyB7XG4gIHJlYWRvbmx5IGRvY2tlckltYWdlQXNzZXQ6IERvY2tlckltYWdlQXNzZXQ7XG4gIHJlYWRvbmx5IGZpbGVTeXN0ZW06IEZpbGVTeXN0ZW07XG4gIHJlYWRvbmx5IG5leHRqc1R5cGU6IE5leHRqc1R5cGU7XG4gIHJlYWRvbmx5IG92ZXJyaWRlcz86IE5leHRqc0NvbnRhaW5lcnNPdmVycmlkZXM7XG4gIHJlYWRvbmx5IHJlbGF0aXZlRW50cnlwb2ludFBhdGg6IHN0cmluZztcbn1cblxuLyoqXG4gKiBOZXh0LmpzIGxvYWQgYmFsYW5jZWQgdmlhIEFwcGxpY2F0aW9uIExvYWQgQmFsYW5jZXIgd2l0aCBjb250YWluZXJzIHZpYSBBV1NcbiAqIEZhcmdhdGUuXG4gKi9cbmV4cG9ydCBjbGFzcyBOZXh0anNDb250YWluZXJzIGV4dGVuZHMgQ29uc3RydWN0IHtcbiAgYWxiRmFyZ2F0ZVNlcnZpY2U6IEFwcGxpY2F0aW9uTG9hZEJhbGFuY2VkRmFyZ2F0ZVNlcnZpY2U7XG4gIGVjc0NsdXN0ZXI6IENsdXN0ZXI7XG4gIHVybDogc3RyaW5nO1xuXG4gIHByaXZhdGUgcHJvcHM6IE5leHRqc0NvbnRhaW5lcnNQcm9wcztcblxuICBjb25zdHJ1Y3RvcihzY29wZTogQ29uc3RydWN0LCBpZDogc3RyaW5nLCBwcm9wczogTmV4dGpzQ29udGFpbmVyc1Byb3BzKSB7XG4gICAgc3VwZXIoc2NvcGUsIGlkKTtcbiAgICB0aGlzLnByb3BzID0gcHJvcHM7XG4gICAgdGhpcy5lY3NDbHVzdGVyID0gdGhpcy5jcmVhdGVFY3NDbHVzdGVyKCk7XG4gICAgdGhpcy5hbGJGYXJnYXRlU2VydmljZSA9IHRoaXMuY3JlYXRlQWxiRmFyZ2F0ZVNldmljZSgpO1xuICAgIHRoaXMuY29uZmlndXJlSGVhbHRoQ2hlY2soKTtcbiAgICB0aGlzLmF0dGFjaEZpbGVTeXN0ZW0oKTtcbiAgICB0aGlzLnVybCA9IHRoaXMuZ2V0VXJsKCk7XG4gIH1cblxuICBwcml2YXRlIGNyZWF0ZUVjc0NsdXN0ZXIoKTogQ2x1c3RlciB7XG4gICAgY29uc3QgY2x1c3RlciA9IG5ldyBDbHVzdGVyKHRoaXMsIFwiRWNzQ2x1c3RlclwiLCB7XG4gICAgICBlbmFibGVGYXJnYXRlQ2FwYWNpdHlQcm92aWRlcnM6IHRydWUsXG4gICAgICBjb250YWluZXJJbnNpZ2h0czogdHJ1ZSxcbiAgICAgIHZwYzogdGhpcy5wcm9wcy52cGMsXG4gICAgICAuLi50aGlzLnByb3BzLm92ZXJyaWRlcz8uZWNzQ2x1c3RlclByb3BzLFxuICAgIH0pO1xuICAgIHJldHVybiBjbHVzdGVyO1xuICB9XG4gIHByaXZhdGUgY3JlYXRlQWxiRmFyZ2F0ZVNldmljZSgpOiBBcHBsaWNhdGlvbkxvYWRCYWxhbmNlZEZhcmdhdGVTZXJ2aWNlIHtcbiAgICBsZXQgY3B1QXJjaGl0ZWN0dXJlOiBDcHVBcmNoaXRlY3R1cmUgfCB1bmRlZmluZWQgPSB1bmRlZmluZWQ7XG4gICAgaWYgKHByb2Nlc3MuYXJjaCA9PT0gXCJ4NjRcIikge1xuICAgICAgY3B1QXJjaGl0ZWN0dXJlID0gQ3B1QXJjaGl0ZWN0dXJlLlg4Nl82NDtcbiAgICB9IGVsc2UgaWYgKHByb2Nlc3MuYXJjaCA9PT0gXCJhcm02NFwiKSB7XG4gICAgICBjcHVBcmNoaXRlY3R1cmUgPSBDcHVBcmNoaXRlY3R1cmUuQVJNNjQ7XG4gICAgfVxuICAgIGNvbnN0IGFsYkZhcmdhdGVTZXJ2aWNlID0gbmV3IEFwcGxpY2F0aW9uTG9hZEJhbGFuY2VkRmFyZ2F0ZVNlcnZpY2UoXG4gICAgICB0aGlzLFxuICAgICAgXCJBbGJGYXJnYXRlU2VydmljZVwiLFxuICAgICAge1xuICAgICAgICBjaXJjdWl0QnJlYWtlcjogeyByb2xsYmFjazogdHJ1ZSwgZW5hYmxlOiB0cnVlIH0sXG4gICAgICAgIGNsdXN0ZXI6IHRoaXMuZWNzQ2x1c3RlcixcbiAgICAgICAgY3B1OiAxMDI0LFxuICAgICAgICBoZWFsdGhDaGVja0dyYWNlUGVyaW9kOiBEdXJhdGlvbi5zZWNvbmRzKDEwKSxcbiAgICAgICAgbWF4SGVhbHRoeVBlcmNlbnQ6IDIwMCxcbiAgICAgICAgbWVtb3J5TGltaXRNaUI6IDIwNDgsXG4gICAgICAgIG1pbkhlYWx0aHlQZXJjZW50OiAxMDAsIC8vIG1haW50YWluIHNlcnZpY2UgYXZhaWxhYmlsaXR5IGR1cmluZyBkZXBsb3ltZW50XG4gICAgICAgIC8qXG4gICAgICAgICAgVGhpcyBwcm90b2NvbCB2ZXJzaW9uIGlzIGZvciB0aGUgdGFyZ2V0IGdyb3VwIChGYXJnYXRlKSwgbm90IHRoZSBBTEJcbiAgICAgICAgICBMaXN0ZW5lci4gRnJvbSBkb2NzLCBcIkFwcGxpY2F0aW9uIExvYWQgQmFsYW5jZXJzIHByb3ZpZGUgbmF0aXZlIHN1cHBvcnRcbiAgICAgICAgICBmb3IgSFRUUC8yIHdpdGggSFRUUFMgbGlzdGVuZXJzXCIuIFNlZSBodHRwczovL2RvY3MuYXdzLmFtYXpvbi5jb20vZWxhc3RpY2xvYWRiYWxhbmNpbmcvbGF0ZXN0L2FwcGxpY2F0aW9uL2xvYWQtYmFsYW5jZXItbGlzdGVuZXJzLmh0bWxcbiAgICAgICAgICBOZXh0LmpzIGRlZmF1bHQgc2VydmVyIGRvZXMgbm90IHN1cHBvcnQgSFRUUC8yIGFzIGl0J3MgcmVjb21tZW5kZWRcbiAgICAgICAgICB0byBwcm94eSB5b3VyIE5leHQuanMgc2VydmVyIHdoaWNoIHdlJ3JlIGRvaW5nIHdpdGggQUxCLlxuICAgICAgICAgIEFsc28gbm90ZSwgQ2xvdWRGcm9udCBvbmx5IHN1cHBvcnRzIEhUVFAvMS4xIG9yaWdpbnMuXG4gICAgICAgICAgaHR0cHM6Ly9kb2NzLmF3cy5hbWF6b24uY29tL0FtYXpvbkNsb3VkRnJvbnQvbGF0ZXN0L0RldmVsb3Blckd1aWRlL1JlcXVlc3RBbmRSZXNwb25zZUJlaGF2aW9yQ3VzdG9tT3JpZ2luLmh0bWwjUmVxdWVzdEN1c3RvbUhUVFBWZXJzaW9uXG4gICAgICAgICovXG4gICAgICAgIHByb3RvY29sVmVyc2lvbjogQXBwbGljYXRpb25Qcm90b2NvbFZlcnNpb24uSFRUUDEsXG4gICAgICAgIHJ1bnRpbWVQbGF0Zm9ybToge1xuICAgICAgICAgIGNwdUFyY2hpdGVjdHVyZSxcbiAgICAgICAgfSxcbiAgICAgICAgdGFza0ltYWdlT3B0aW9uczoge1xuICAgICAgICAgIGNvbW1hbmQ6IFtcIm5vZGVcIiwgdGhpcy5wcm9wcy5yZWxhdGl2ZUVudHJ5cG9pbnRQYXRoXSxcbiAgICAgICAgICBjb250YWluZXJOYW1lOiBcIm5leHRqc1wiLFxuICAgICAgICAgIGNvbnRhaW5lclBvcnQ6IDMwMDAsXG4gICAgICAgICAgaW1hZ2U6IENvbnRhaW5lckltYWdlLmZyb21Eb2NrZXJJbWFnZUFzc2V0KFxuICAgICAgICAgICAgdGhpcy5wcm9wcy5kb2NrZXJJbWFnZUFzc2V0LFxuICAgICAgICAgICksXG4gICAgICAgICAgbG9nRHJpdmVyOiBMb2dEcml2ZXJzLmF3c0xvZ3Moe1xuICAgICAgICAgICAgc3RyZWFtUHJlZml4OiBcIm5leHRqc1wiLFxuICAgICAgICAgICAgbW9kZTogQXdzTG9nRHJpdmVyTW9kZS5OT05fQkxPQ0tJTkcsXG4gICAgICAgICAgfSksXG4gICAgICAgICAgLi4udGhpcy5wcm9wcy5vdmVycmlkZXM/LnRhc2tJbWFnZU9wdGlvbnMsXG4gICAgICAgIH0sXG4gICAgICAgIC4uLnRoaXMucHJvcHMub3ZlcnJpZGVzPy5hbGJGYXJnYXRlU2VydmljZVByb3BzLFxuICAgICAgfSxcbiAgICApO1xuICAgIC8vIHJlcXVpcmVkIG9yIGhlYWx0aCBjaGVja3MgZmFpbFxuICAgIGFsYkZhcmdhdGVTZXJ2aWNlLnRhc2tEZWZpbml0aW9uLmRlZmF1bHRDb250YWluZXI/LmFkZEVudmlyb25tZW50KFxuICAgICAgXCJIT1NUTkFNRVwiLFxuICAgICAgXCIwLjAuMC4wXCIsXG4gICAgKTtcbiAgICAvLyBzZWN1cml0eSBiZXN0IHByYWN0aWNlIHRvIGVuZm9yY2UgcmVhZG9ubHkgZm9yIHJvb3QgZmlsZXN5c3RlbVxuICAgIC8vIGhvcGVmdWxseSBodHRwczovL2dpdGh1Yi5jb20vYXdzL2F3cy1jZGsvaXNzdWVzLzIzOTM1IHdpbGwgcmVzdWx0IGluXG4gICAgLy8gZWFzaWVyIHdheSB0byBzZXQgdGhpcyBwcm9wZXJ0eVxuICAgIGNvbnN0IGNmblRhc2tEZWYgPSBhbGJGYXJnYXRlU2VydmljZS50YXNrRGVmaW5pdGlvbi5ub2RlXG4gICAgICAuZGVmYXVsdENoaWxkIGFzIENmblRhc2tEZWZpbml0aW9uO1xuICAgIGNmblRhc2tEZWYuYWRkUHJvcGVydHlPdmVycmlkZShcbiAgICAgIFwiQ29udGFpbmVyRGVmaW5pdGlvbnMuMC5SZWFkb25seVJvb3RGaWxlc3lzdGVtXCIsXG4gICAgICB0cnVlLCAvLyBUT0RPOiBmaWd1cmUgd2h5IHN5bWxpbmsgbm90IGJlaW5nIGNyZWF0ZWQgYmV0d2VlbiBmdWxsIHJvdXRlIGNhY2hlXG4gICAgKTtcbiAgICAvLyBzcGVlZCB1cCBkZXBsb3ltZW50cyBieSBzaG9ydGVuaW5nIGRlcmVnaXN0cmF0aW9uIGRlbGF5XG4gICAgLy8gaHR0cHM6Ly9kb2NzLmF3cy5hbWF6b24uY29tL0FtYXpvbkVDUy9sYXRlc3QvYmVzdHByYWN0aWNlc2d1aWRlL2xvYWQtYmFsYW5jZXItY29ubmVjdGlvbi1kcmFpbmluZy5odG1sXG4gICAgLy8gVE9ETzogZG9jdW1lbnQgdGhhdCB0aGlzIHNob3VsZCBiZSBpbmNyZWFzZWQgaWYgbG9uZyBsaXZlZCBjb25uZWN0aW9ucyBhcmUgZXhwZWN0ZWRcbiAgICBhbGJGYXJnYXRlU2VydmljZS50YXJnZXRHcm91cC5zZXRBdHRyaWJ1dGUoXG4gICAgICBcImRlcmVnaXN0cmF0aW9uX2RlbGF5LnRpbWVvdXRfc2Vjb25kc1wiLFxuICAgICAgXCIzMFwiLFxuICAgICk7XG4gICAgLy8gYmVzdCBwcmFjdGljZSB0byBlbmFibGUgY3Jvc3Mgem9uZSBsb2FkIGJhbGFuY2luZ1xuICAgIC8vIEBzZWUgaHR0cHM6Ly9kb2NzLmF3cy5hbWF6b24uY29tL2VsYXN0aWNsb2FkYmFsYW5jaW5nL2xhdGVzdC9hcHBsaWNhdGlvbi9kaXNhYmxlLWNyb3NzLXpvbmUuaHRtbFxuICAgIGFsYkZhcmdhdGVTZXJ2aWNlLmxvYWRCYWxhbmNlci5zZXRBdHRyaWJ1dGUoXG4gICAgICBcImxvYWRfYmFsYW5jaW5nLmNyb3NzX3pvbmUuZW5hYmxlZFwiLFxuICAgICAgXCJ0cnVlXCIsXG4gICAgKTtcbiAgICByZXR1cm4gYWxiRmFyZ2F0ZVNlcnZpY2U7XG4gIH1cbiAgLyoqXG4gICAqIENvbmZpZ3VyZSBoZWFsdGggY2hlY2tzIGZvciBjb250YWluZXJzIGF0IEFMQiBhbmQgRUNTIGxldmVsLiBUaGlzIGVuc3VyZXNcbiAgICogdW5oZWFsdGh5IGNvbnRhaW5lcnMgYXJlIHJlbW92ZWQuIEJvdGggb2YgdGhlc2UgaGVhbHRoIGNoZWNrcyBjYW4gYmVcbiAgICogb3ZlcndyaXR0ZW4gYnkgdXNlciBieSBhY2Nlc3NpbmcgYGFsYkZhcmdhdGVTZXJ2aWNlYCBwcm9wZXJ0eSwgc28gbm8gbmVlZFxuICAgKiBmb3IgYG92ZXJyaWRlc2AuXG4gICAqL1xuICBwcml2YXRlIGNvbmZpZ3VyZUhlYWx0aENoZWNrKCkge1xuICAgIC8vIHNwZWVkIHVwIGRlcGxveW1lbnRzIGJ5IHNob3J0ZW5pbmcgaGVhbHRoIGNoZWNrc1xuICAgIC8vIHNlZSBodHRwczovL2RvY3MuYXdzLmFtYXpvbi5jb20vQW1hem9uRUNTL2xhdGVzdC9iZXN0cHJhY3RpY2VzZ3VpZGUvbG9hZC1iYWxhbmNlci1oZWFsdGhjaGVjay5odG1sXG4gICAgdGhpcy5hbGJGYXJnYXRlU2VydmljZS50YXJnZXRHcm91cC5jb25maWd1cmVIZWFsdGhDaGVjayh7XG4gICAgICBwYXRoOiB0aGlzLnByb3BzLmhlYWx0aENoZWNrUGF0aCxcbiAgICAgIGhlYWx0aHlUaHJlc2hvbGRDb3VudDogMixcbiAgICAgIGludGVydmFsOiBEdXJhdGlvbi5zZWNvbmRzKDEwKSwgLy8gdG9vIGZyZXF1ZW50PyBidXQgZW5hYmxlcyBmYXN0ZXIgcm9sbGJhY2suLi5cbiAgICAgIHRpbWVvdXQ6IER1cmF0aW9uLnNlY29uZHMoNSksIC8vIG11c3QgYmUgbGVzcyB0aGFuIGludGVydmFsXG4gICAgfSk7XG4gICAgY29uc3QgaGVhbHRoQ2hlY2s6IEhlYWx0aENoZWNrID0ge1xuICAgICAgY29tbWFuZDogW1xuICAgICAgICBcIkNNRC1TSEVMTFwiLFxuICAgICAgICAvLyBjdXJsIGlzbid0IGF2YWlsYWJsZSBpbiBhbHBpbmUgbGludXhcbiAgICAgICAgYHdnZXQgLS1xdWlldCAtLXRyaWVzPTEgLS1zcGlkZXIgaHR0cDovL2xvY2FsaG9zdDozMDAwJHt0aGlzLnByb3BzLmhlYWx0aENoZWNrUGF0aH0gfHwgZXhpdCAxYCxcbiAgICAgIF0sXG4gICAgfTtcbiAgICBjb25zdCBkZWZhdWx0Q29udGFpbmVyID1cbiAgICAgIHRoaXMuYWxiRmFyZ2F0ZVNlcnZpY2UudGFza0RlZmluaXRpb24uZGVmYXVsdENvbnRhaW5lcjtcbiAgICBpZiAoZGVmYXVsdENvbnRhaW5lcikge1xuICAgICAgLy8gQHRzLWV4cGVjdC1lcnJvciBtdXN0IHVzZSBpbnRlcm5hbCBcInByb3BzXCIgYXR0cmlidXRlIGIvYyBubyBvdGhlciB3YXkgdG8gYWRkIGhlYWx0aCBjaGVja1xuICAgICAgZGVmYXVsdENvbnRhaW5lci5wcm9wcy5oZWFsdGhDaGVjayA9IGhlYWx0aENoZWNrO1xuICAgIH1cbiAgfVxuICBwcml2YXRlIGF0dGFjaEZpbGVTeXN0ZW0oKSB7XG4gICAgY29uc3QgY29udGFpbmVyID0gdGhpcy5hbGJGYXJnYXRlU2VydmljZS50YXNrRGVmaW5pdGlvbi5kZWZhdWx0Q29udGFpbmVyO1xuICAgIGNvbnN0IHZvbHVtZU5hbWUgPSBcImNkay1uZXh0anMtdm9sdW1lXCI7XG4gICAgdGhpcy5hbGJGYXJnYXRlU2VydmljZS50YXNrRGVmaW5pdGlvbi5hZGRWb2x1bWUoe1xuICAgICAgbmFtZTogdm9sdW1lTmFtZSxcbiAgICAgIGVmc1ZvbHVtZUNvbmZpZ3VyYXRpb246IHtcbiAgICAgICAgZmlsZVN5c3RlbUlkOiB0aGlzLnByb3BzLmZpbGVTeXN0ZW0uZmlsZVN5c3RlbUlkLFxuICAgICAgICB0cmFuc2l0RW5jcnlwdGlvbjogXCJFTkFCTEVEXCIsXG4gICAgICAgIGF1dGhvcml6YXRpb25Db25maWc6IHtcbiAgICAgICAgICBhY2Nlc3NQb2ludElkOiB0aGlzLnByb3BzLmFjY2Vzc1BvaW50LmFjY2Vzc1BvaW50SWQsXG4gICAgICAgICAgaWFtOiBcIkVOQUJMRURcIixcbiAgICAgICAgfSxcbiAgICAgIH0sXG4gICAgfSk7XG4gICAgY29udGFpbmVyPy5hZGRNb3VudFBvaW50cyh7XG4gICAgICBzb3VyY2VWb2x1bWU6IHZvbHVtZU5hbWUsXG4gICAgICBjb250YWluZXJQYXRoOiB0aGlzLnByb3BzLmNvbnRhaW5lck1vdW50UGF0aEZvckVmcyxcbiAgICAgIHJlYWRPbmx5OiBmYWxzZSxcbiAgICB9KTtcbiAgfVxuICBwcml2YXRlIGdldFVybCgpOiBzdHJpbmcge1xuICAgIGNvbnN0IHByb3RvY29sID0gdGhpcy5hbGJGYXJnYXRlU2VydmljZS5jZXJ0aWZpY2F0ZSA/IFwiaHR0cHNcIiA6IFwiaHR0cFwiO1xuICAgIHJldHVybiBgJHtwcm90b2NvbH06Ly8ke3RoaXMuYWxiRmFyZ2F0ZVNlcnZpY2UubG9hZEJhbGFuY2VyLmxvYWRCYWxhbmNlckRuc05hbWV9YDtcbiAgfVxufVxuIl19
@@ -0,0 +1,23 @@
1
+ import { DockerImageCode, DockerImageFunction, FunctionUrl } from "aws-cdk-lib/aws-lambda";
2
+ import { Construct } from "constructs";
3
+ import { NextjsComputeBaseProps } from "./nextjs-compute-base-props";
4
+ import { OptionalDockerImageFunctionProps } from "../generated-structs/OptionalDockerImageFunctionProps";
5
+ import { OptionalFunctionUrlProps } from "../generated-structs/OptionalFunctionUrlProps";
6
+ export interface NextjsFunctionsOverrides {
7
+ readonly dockerImageFunctionProps?: OptionalDockerImageFunctionProps;
8
+ readonly functionUrlProps?: OptionalFunctionUrlProps;
9
+ }
10
+ export interface NextjsFunctionsProps extends NextjsComputeBaseProps {
11
+ readonly dockerImageCode: DockerImageCode;
12
+ readonly overrides?: NextjsFunctionsOverrides;
13
+ }
14
+ /**
15
+ * Run Next.js in functions on AWS with AWS Lambda.
16
+ */
17
+ export declare class NextjsFunctions extends Construct {
18
+ function: DockerImageFunction;
19
+ functionUrl: FunctionUrl;
20
+ private props;
21
+ constructor(scope: Construct, id: string, props: NextjsFunctionsProps);
22
+ private createFunction;
23
+ }
@@ -0,0 +1,57 @@
1
+ "use strict";
2
+ var _a;
3
+ Object.defineProperty(exports, "__esModule", { value: true });
4
+ exports.NextjsFunctions = void 0;
5
+ const JSII_RTTI_SYMBOL_1 = Symbol.for("jsii.rtti");
6
+ const aws_cdk_lib_1 = require("aws-cdk-lib");
7
+ const aws_lambda_1 = require("aws-cdk-lib/aws-lambda");
8
+ const constructs_1 = require("constructs");
9
+ /**
10
+ * Run Next.js in functions on AWS with AWS Lambda.
11
+ */
12
+ class NextjsFunctions extends constructs_1.Construct {
13
+ constructor(scope, id, props) {
14
+ super(scope, id);
15
+ this.props = props;
16
+ this.function = this.createFunction();
17
+ this.functionUrl = this.function.addFunctionUrl({
18
+ authType: aws_lambda_1.FunctionUrlAuthType.AWS_IAM,
19
+ invokeMode: aws_lambda_1.InvokeMode.RESPONSE_STREAM,
20
+ ...this.props.overrides?.functionUrlProps,
21
+ });
22
+ if (!this.function.role) {
23
+ throw new Error("Function role is undefined");
24
+ }
25
+ }
26
+ createFunction() {
27
+ let architecture = undefined;
28
+ if (process.arch === "x64") {
29
+ architecture = aws_lambda_1.Architecture.X86_64;
30
+ }
31
+ else if (process.arch === "arm64") {
32
+ architecture = aws_lambda_1.Architecture.ARM_64;
33
+ }
34
+ const fn = new aws_lambda_1.DockerImageFunction(this, "Functions", {
35
+ architecture,
36
+ code: this.props.dockerImageCode,
37
+ filesystem: aws_lambda_1.FileSystem.fromEfsAccessPoint(this.props.accessPoint, this.props.containerMountPathForEfs),
38
+ memorySize: 2048,
39
+ timeout: aws_cdk_lib_1.Duration.seconds(30),
40
+ vpc: this.props.vpc,
41
+ ...this.props.overrides?.dockerImageFunctionProps,
42
+ environment: {
43
+ AWS_LWA_ENABLE_COMPRESSION: "true",
44
+ AWS_LWA_INVOKE_MODE: "response_stream",
45
+ AWS_LWA_READINESS_CHECK_PATH: this.props.healthCheckPath,
46
+ AWS_LWA_READINESS_CHECK_PORT: "3000",
47
+ READINESS_CHECK_PATH: `http://127.0.0.1:3000${this.props.healthCheckPath}`,
48
+ ...this.props.overrides?.dockerImageFunctionProps?.environment,
49
+ },
50
+ });
51
+ return fn;
52
+ }
53
+ }
54
+ exports.NextjsFunctions = NextjsFunctions;
55
+ _a = JSII_RTTI_SYMBOL_1;
56
+ NextjsFunctions[_a] = { fqn: "cdk-nextjs.NextjsFunctions", version: "0.0.0" };
57
+ //# sourceMappingURL=data:application/json;base64,eyJ2ZXJzaW9uIjozLCJmaWxlIjoibmV4dGpzLWZ1bmN0aW9ucy5qcyIsInNvdXJjZVJvb3QiOiIiLCJzb3VyY2VzIjpbIi4uLy4uL3NyYy9uZXh0anMtY29tcHV0ZS9uZXh0anMtZnVuY3Rpb25zLnRzIl0sIm5hbWVzIjpbXSwibWFwcGluZ3MiOiI7Ozs7O0FBQUEsNkNBQXVDO0FBQ3ZDLHVEQVFnQztBQUNoQywyQ0FBdUM7QUFldkM7O0dBRUc7QUFDSCxNQUFhLGVBQWdCLFNBQVEsc0JBQVM7SUFNNUMsWUFBWSxLQUFnQixFQUFFLEVBQVUsRUFBRSxLQUEyQjtRQUNuRSxLQUFLLENBQUMsS0FBSyxFQUFFLEVBQUUsQ0FBQyxDQUFDO1FBQ2pCLElBQUksQ0FBQyxLQUFLLEdBQUcsS0FBSyxDQUFDO1FBQ25CLElBQUksQ0FBQyxRQUFRLEdBQUcsSUFBSSxDQUFDLGNBQWMsRUFBRSxDQUFDO1FBQ3RDLElBQUksQ0FBQyxXQUFXLEdBQUcsSUFBSSxDQUFDLFFBQVEsQ0FBQyxjQUFjLENBQUM7WUFDOUMsUUFBUSxFQUFFLGdDQUFtQixDQUFDLE9BQU87WUFDckMsVUFBVSxFQUFFLHVCQUFVLENBQUMsZUFBZTtZQUN0QyxHQUFHLElBQUksQ0FBQyxLQUFLLENBQUMsU0FBUyxFQUFFLGdCQUFnQjtTQUMxQyxDQUFDLENBQUM7UUFDSCxJQUFJLENBQUMsSUFBSSxDQUFDLFFBQVEsQ0FBQyxJQUFJLEVBQUUsQ0FBQztZQUN4QixNQUFNLElBQUksS0FBSyxDQUFDLDRCQUE0QixDQUFDLENBQUM7UUFDaEQsQ0FBQztJQUNILENBQUM7SUFFTyxjQUFjO1FBQ3BCLElBQUksWUFBWSxHQUE2QixTQUFTLENBQUM7UUFDdkQsSUFBSSxPQUFPLENBQUMsSUFBSSxLQUFLLEtBQUssRUFBRSxDQUFDO1lBQzNCLFlBQVksR0FBRyx5QkFBWSxDQUFDLE1BQU0sQ0FBQztRQUNyQyxDQUFDO2FBQU0sSUFBSSxPQUFPLENBQUMsSUFBSSxLQUFLLE9BQU8sRUFBRSxDQUFDO1lBQ3BDLFlBQVksR0FBRyx5QkFBWSxDQUFDLE1BQU0sQ0FBQztRQUNyQyxDQUFDO1FBQ0QsTUFBTSxFQUFFLEdBQUcsSUFBSSxnQ0FBbUIsQ0FBQyxJQUFJLEVBQUUsV0FBVyxFQUFFO1lBQ3BELFlBQVk7WUFDWixJQUFJLEVBQUUsSUFBSSxDQUFDLEtBQUssQ0FBQyxlQUFlO1lBQ2hDLFVBQVUsRUFBRSx1QkFBVSxDQUFDLGtCQUFrQixDQUN2QyxJQUFJLENBQUMsS0FBSyxDQUFDLFdBQVcsRUFDdEIsSUFBSSxDQUFDLEtBQUssQ0FBQyx3QkFBd0IsQ0FDcEM7WUFDRCxVQUFVLEVBQUUsSUFBSTtZQUNoQixPQUFPLEVBQUUsc0JBQVEsQ0FBQyxPQUFPLENBQUMsRUFBRSxDQUFDO1lBQzdCLEdBQUcsRUFBRSxJQUFJLENBQUMsS0FBSyxDQUFDLEdBQUc7WUFDbkIsR0FBRyxJQUFJLENBQUMsS0FBSyxDQUFDLFNBQVMsRUFBRSx3QkFBd0I7WUFDakQsV0FBVyxFQUFFO2dCQUNYLDBCQUEwQixFQUFFLE1BQU07Z0JBQ2xDLG1CQUFtQixFQUFFLGlCQUFpQjtnQkFDdEMsNEJBQTRCLEVBQUUsSUFBSSxDQUFDLEtBQUssQ0FBQyxlQUFlO2dCQUN4RCw0QkFBNEIsRUFBRSxNQUFNO2dCQUNwQyxvQkFBb0IsRUFBRSx3QkFBd0IsSUFBSSxDQUFDLEtBQUssQ0FBQyxlQUFlLEVBQUU7Z0JBQzFFLEdBQUcsSUFBSSxDQUFDLEtBQUssQ0FBQyxTQUFTLEVBQUUsd0JBQXdCLEVBQUUsV0FBVzthQUMvRDtTQUNGLENBQUMsQ0FBQztRQUNILE9BQU8sRUFBRSxDQUFDO0lBQ1osQ0FBQzs7QUFoREgsMENBaURDIiwic291cmNlc0NvbnRlbnQiOlsiaW1wb3J0IHsgRHVyYXRpb24gfSBmcm9tIFwiYXdzLWNkay1saWJcIjtcbmltcG9ydCB7XG4gIEFyY2hpdGVjdHVyZSxcbiAgRG9ja2VySW1hZ2VDb2RlLFxuICBEb2NrZXJJbWFnZUZ1bmN0aW9uLFxuICBGaWxlU3lzdGVtLFxuICBGdW5jdGlvblVybCxcbiAgRnVuY3Rpb25VcmxBdXRoVHlwZSxcbiAgSW52b2tlTW9kZSxcbn0gZnJvbSBcImF3cy1jZGstbGliL2F3cy1sYW1iZGFcIjtcbmltcG9ydCB7IENvbnN0cnVjdCB9IGZyb20gXCJjb25zdHJ1Y3RzXCI7XG5pbXBvcnQgeyBOZXh0anNDb21wdXRlQmFzZVByb3BzIH0gZnJvbSBcIi4vbmV4dGpzLWNvbXB1dGUtYmFzZS1wcm9wc1wiO1xuaW1wb3J0IHsgT3B0aW9uYWxEb2NrZXJJbWFnZUZ1bmN0aW9uUHJvcHMgfSBmcm9tIFwiLi4vZ2VuZXJhdGVkLXN0cnVjdHMvT3B0aW9uYWxEb2NrZXJJbWFnZUZ1bmN0aW9uUHJvcHNcIjtcbmltcG9ydCB7IE9wdGlvbmFsRnVuY3Rpb25VcmxQcm9wcyB9IGZyb20gXCIuLi9nZW5lcmF0ZWQtc3RydWN0cy9PcHRpb25hbEZ1bmN0aW9uVXJsUHJvcHNcIjtcblxuZXhwb3J0IGludGVyZmFjZSBOZXh0anNGdW5jdGlvbnNPdmVycmlkZXMge1xuICByZWFkb25seSBkb2NrZXJJbWFnZUZ1bmN0aW9uUHJvcHM/OiBPcHRpb25hbERvY2tlckltYWdlRnVuY3Rpb25Qcm9wcztcbiAgcmVhZG9ubHkgZnVuY3Rpb25VcmxQcm9wcz86IE9wdGlvbmFsRnVuY3Rpb25VcmxQcm9wcztcbn1cblxuZXhwb3J0IGludGVyZmFjZSBOZXh0anNGdW5jdGlvbnNQcm9wcyBleHRlbmRzIE5leHRqc0NvbXB1dGVCYXNlUHJvcHMge1xuICByZWFkb25seSBkb2NrZXJJbWFnZUNvZGU6IERvY2tlckltYWdlQ29kZTtcbiAgcmVhZG9ubHkgb3ZlcnJpZGVzPzogTmV4dGpzRnVuY3Rpb25zT3ZlcnJpZGVzO1xufVxuXG4vKipcbiAqIFJ1biBOZXh0LmpzIGluIGZ1bmN0aW9ucyBvbiBBV1Mgd2l0aCBBV1MgTGFtYmRhLlxuICovXG5leHBvcnQgY2xhc3MgTmV4dGpzRnVuY3Rpb25zIGV4dGVuZHMgQ29uc3RydWN0IHtcbiAgZnVuY3Rpb246IERvY2tlckltYWdlRnVuY3Rpb247XG4gIGZ1bmN0aW9uVXJsOiBGdW5jdGlvblVybDtcblxuICBwcml2YXRlIHByb3BzOiBOZXh0anNGdW5jdGlvbnNQcm9wcztcblxuICBjb25zdHJ1Y3RvcihzY29wZTogQ29uc3RydWN0LCBpZDogc3RyaW5nLCBwcm9wczogTmV4dGpzRnVuY3Rpb25zUHJvcHMpIHtcbiAgICBzdXBlcihzY29wZSwgaWQpO1xuICAgIHRoaXMucHJvcHMgPSBwcm9wcztcbiAgICB0aGlzLmZ1bmN0aW9uID0gdGhpcy5jcmVhdGVGdW5jdGlvbigpO1xuICAgIHRoaXMuZnVuY3Rpb25VcmwgPSB0aGlzLmZ1bmN0aW9uLmFkZEZ1bmN0aW9uVXJsKHtcbiAgICAgIGF1dGhUeXBlOiBGdW5jdGlvblVybEF1dGhUeXBlLkFXU19JQU0sXG4gICAgICBpbnZva2VNb2RlOiBJbnZva2VNb2RlLlJFU1BPTlNFX1NUUkVBTSxcbiAgICAgIC4uLnRoaXMucHJvcHMub3ZlcnJpZGVzPy5mdW5jdGlvblVybFByb3BzLFxuICAgIH0pO1xuICAgIGlmICghdGhpcy5mdW5jdGlvbi5yb2xlKSB7XG4gICAgICB0aHJvdyBuZXcgRXJyb3IoXCJGdW5jdGlvbiByb2xlIGlzIHVuZGVmaW5lZFwiKTtcbiAgICB9XG4gIH1cblxuICBwcml2YXRlIGNyZWF0ZUZ1bmN0aW9uKCkge1xuICAgIGxldCBhcmNoaXRlY3R1cmU6IEFyY2hpdGVjdHVyZSB8IHVuZGVmaW5lZCA9IHVuZGVmaW5lZDtcbiAgICBpZiAocHJvY2Vzcy5hcmNoID09PSBcIng2NFwiKSB7XG4gICAgICBhcmNoaXRlY3R1cmUgPSBBcmNoaXRlY3R1cmUuWDg2XzY0O1xuICAgIH0gZWxzZSBpZiAocHJvY2Vzcy5hcmNoID09PSBcImFybTY0XCIpIHtcbiAgICAgIGFyY2hpdGVjdHVyZSA9IEFyY2hpdGVjdHVyZS5BUk1fNjQ7XG4gICAgfVxuICAgIGNvbnN0IGZuID0gbmV3IERvY2tlckltYWdlRnVuY3Rpb24odGhpcywgXCJGdW5jdGlvbnNcIiwge1xuICAgICAgYXJjaGl0ZWN0dXJlLFxuICAgICAgY29kZTogdGhpcy5wcm9wcy5kb2NrZXJJbWFnZUNvZGUsXG4gICAgICBmaWxlc3lzdGVtOiBGaWxlU3lzdGVtLmZyb21FZnNBY2Nlc3NQb2ludChcbiAgICAgICAgdGhpcy5wcm9wcy5hY2Nlc3NQb2ludCxcbiAgICAgICAgdGhpcy5wcm9wcy5jb250YWluZXJNb3VudFBhdGhGb3JFZnMsXG4gICAgICApLFxuICAgICAgbWVtb3J5U2l6ZTogMjA0OCxcbiAgICAgIHRpbWVvdXQ6IER1cmF0aW9uLnNlY29uZHMoMzApLFxuICAgICAgdnBjOiB0aGlzLnByb3BzLnZwYyxcbiAgICAgIC4uLnRoaXMucHJvcHMub3ZlcnJpZGVzPy5kb2NrZXJJbWFnZUZ1bmN0aW9uUHJvcHMsXG4gICAgICBlbnZpcm9ubWVudDoge1xuICAgICAgICBBV1NfTFdBX0VOQUJMRV9DT01QUkVTU0lPTjogXCJ0cnVlXCIsXG4gICAgICAgIEFXU19MV0FfSU5WT0tFX01PREU6IFwicmVzcG9uc2Vfc3RyZWFtXCIsXG4gICAgICAgIEFXU19MV0FfUkVBRElORVNTX0NIRUNLX1BBVEg6IHRoaXMucHJvcHMuaGVhbHRoQ2hlY2tQYXRoLFxuICAgICAgICBBV1NfTFdBX1JFQURJTkVTU19DSEVDS19QT1JUOiBcIjMwMDBcIixcbiAgICAgICAgUkVBRElORVNTX0NIRUNLX1BBVEg6IGBodHRwOi8vMTI3LjAuMC4xOjMwMDAke3RoaXMucHJvcHMuaGVhbHRoQ2hlY2tQYXRofWAsXG4gICAgICAgIC4uLnRoaXMucHJvcHMub3ZlcnJpZGVzPy5kb2NrZXJJbWFnZUZ1bmN0aW9uUHJvcHM/LmVudmlyb25tZW50LFxuICAgICAgfSxcbiAgICB9KTtcbiAgICByZXR1cm4gZm47XG4gIH1cbn1cbiJdfQ==
@@ -0,0 +1,120 @@
1
+ import { ICertificate } from "aws-cdk-lib/aws-certificatemanager";
2
+ import { AddBehaviorOptions, CachePolicyProps, Distribution, ResponseHeadersPolicyProps } from "aws-cdk-lib/aws-cloudfront";
3
+ import { HttpOriginProps } from "aws-cdk-lib/aws-cloudfront-origins";
4
+ import { IBucket } from "aws-cdk-lib/aws-s3";
5
+ import { Construct } from "constructs";
6
+ import { NextjsType } from "./common";
7
+ import { OptionalDistributionProps } from "./generated-structs/OptionalDistributionProps";
8
+ import { OptionalFunctionProps } from "./generated-structs/OptionalFunctionProps";
9
+ import { OptionalS3OriginProps } from "./generated-structs/OptionalS3OriginProps";
10
+ import { PublicDirEntry } from "./nextjs-build/nextjs-build";
11
+ export interface NextjsDistributionOverrides {
12
+ readonly edgeFunctionProps?: OptionalFunctionProps;
13
+ readonly distributionProps?: OptionalDistributionProps;
14
+ readonly imageBehaviorOptions?: AddBehaviorOptions;
15
+ readonly imageCachePolicyProps?: CachePolicyProps;
16
+ readonly imageResponseHeadersPolicyProps?: ResponseHeadersPolicyProps;
17
+ readonly dynamicBehaviorOptions?: AddBehaviorOptions;
18
+ readonly dynamicCachePolicyProps?: CachePolicyProps;
19
+ readonly dynamicResponseHeadersPolicyProps?: ResponseHeadersPolicyProps;
20
+ readonly dynamicHttpOriginProps?: HttpOriginProps;
21
+ readonly staticBehaviorOptions?: AddBehaviorOptions;
22
+ readonly staticResponseHeadersPolicyProps?: ResponseHeadersPolicyProps;
23
+ readonly s3OriginProps?: OptionalS3OriginProps;
24
+ }
25
+ export interface NextjsDistributionProps {
26
+ /**
27
+ * Bucket containing static assets.
28
+ * Must be provided if you want to serve static files.
29
+ */
30
+ readonly assetsBucket: IBucket;
31
+ readonly basePath?: string;
32
+ /**
33
+ * Optional but only applicable for `NextjsType.GLOBAL_CONTAINERS`
34
+ */
35
+ readonly certificate?: ICertificate;
36
+ readonly distribution?: Distribution;
37
+ /**
38
+ * Dynamic (Next.js server) URL to add behavior to distribution
39
+ */
40
+ readonly dynamicUrl: string;
41
+ /**
42
+ * Required if `NextjsType.GLOBAL_FUNCTIONS`
43
+ */
44
+ readonly functionArn?: string;
45
+ readonly nextjsType: NextjsType;
46
+ /**
47
+ * Override props for every construct.
48
+ */
49
+ readonly overrides?: NextjsDistributionOverrides;
50
+ /**
51
+ * Path to directory of Next.js app's public directory. Used to add static
52
+ * behaviors to distribution.
53
+ */
54
+ readonly publicDirEntries: PublicDirEntry[];
55
+ }
56
+ export declare class NextjsDistribution extends Construct {
57
+ distribution: Distribution;
58
+ private props;
59
+ /**
60
+ * Common security headers applied by default to all origins
61
+ * @see https://docs.aws.amazon.com/AmazonCloudFront/latest/DeveloperGuide/using-managed-response-headers-policies.html#managed-response-headers-policies-security
62
+ */
63
+ private commonSecurityHeadersBehavior;
64
+ private staticOrigin;
65
+ private dynamicOrigin;
66
+ private dynamicOriginResponsePolicy;
67
+ private dynamicCloudFrontFunctionAssociations;
68
+ private edgeLambdas?;
69
+ private isFunctionCompute;
70
+ private staticBehaviorOptions;
71
+ private dynamicBehaviorOptions;
72
+ private imageBehaviorOptions;
73
+ /**
74
+ * Given stack id: "arn:aws:cloudformation:us-east-1:905418358903:stack/lh-stickb-idp/4bf74be0-e880-11ee-aea9-0affc6185b25",
75
+ * returns "4bf74be0"
76
+ */
77
+ private uniqueStackIdPart;
78
+ constructor(scope: Construct, id: string, props: NextjsDistributionProps);
79
+ private createStaticOrigin;
80
+ private createDynamicOrigin;
81
+ /**
82
+ * Lambda Function URLs "expect the `Host` header to contain the origin domain
83
+ * name, not the domain name of the CloudFront distribution."
84
+ * @see https://docs.aws.amazon.com/AmazonCloudFront/latest/DeveloperGuide/using-managed-origin-request-policies.html#managed-origin-request-policy-all-viewer-except-host-header
85
+ */
86
+ private createDynamicOriginRequestPolicy;
87
+ /**
88
+ * Ensures Next.js `request.url` will be correct domain instead of URL of
89
+ * compute option (App Runner, Fargate, or Lambda)
90
+ * @see https://open-next.js.org/advanced/workaround#workaround-set-x-forwarded-host-header-aws-specific
91
+ */
92
+ private createDynamicCloudFrontFunctionAssociations;
93
+ /**
94
+ * Required to sign requests so that we can use IAM_AUTH for Lambda Function URL
95
+ * to prevent public access. Once CloudFront Lambda OAC is released, we can
96
+ * use infra configuration for this instead of custom code.
97
+ */
98
+ private createEdgeLambdas;
99
+ private createStaticBehaviorOptions;
100
+ private createDynamicBehaviorOptions;
101
+ private createImageBehaviorOptions;
102
+ /**
103
+ * Creates or uses user specified CloudFront Distribution
104
+ */
105
+ private getDistribution;
106
+ private addDynamicBehaviors;
107
+ private addStaticBehaviors;
108
+ /**
109
+ * Optionally prepends base path to given path pattern.
110
+ */
111
+ private getPathPattern;
112
+ /**
113
+ * Add Origin Access Control (OAC) to CloudFront Distribution which is preferred
114
+ * way to secure access from Distribution to S3. Remove legacy OAI.
115
+ *
116
+ * When CDK releases L2 support for this, please remove this code.
117
+ * @see https://github.com/aws/aws-cdk/issues/21771#issuecomment-1567647338
118
+ */
119
+ private addS3OacAndRemoveOai;
120
+ }