Skip to content
Draft
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
8 changes: 7 additions & 1 deletion .vscode/settings.json
Original file line number Diff line number Diff line change
Expand Up @@ -4,4 +4,10 @@
},
"editor.defaultFormatter": "esbenp.prettier-vscode",
"editor.formatOnSave": true,
}
"search.exclude": {
"**/node_modules/**": true,
"**/cdk.out/**": true,
"**/.next/**": true,
"**/pruned/**": true
}
}
62 changes: 62 additions & 0 deletions examples/cdk-pipelines/app.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,62 @@
import { Aspects, Stack, StackProps, Stage, StageProps } from "aws-cdk-lib";
import { Construct } from "constructs";
import { App } from "aws-cdk-lib";
import { AwsSolutionsChecks } from "cdk-nag";
import {
CodePipeline,
CodePipelineSource,
ShellStep,
} from "aws-cdk-lib/pipelines";
import { GlobalFunctionsStack } from "../global-functions/app";
import {
suppressCommonNags,
suppressGlobalNags,
suppressFunctionsNags,
} from "../shared/suppress-nags";

const app = new App();

const env = {
account: process.env["CDK_DEFAULT_ACCOUNT"],
region: process.env["CDK_DEFAULT_REGION"],
};

class MyStage extends Stage {
constructor(scope: Construct, id: string, props: StageProps) {
super(scope, id, props);
const stack = new GlobalFunctionsStack(this, "glbl-fns", {
env,
});
suppressCommonNags(stack);
suppressGlobalNags(stack);
suppressFunctionsNags(stack);
}
}

class CdkPipelinesStack extends Stack {
constructor(scope: Construct, id: string, props: StackProps) {
super(scope, id, props);
const pipeline = new CodePipeline(this, "Pipeline", {
synth: new ShellStep("ShellStep", {
installCommands: ["cd examples", "pnpm i"],
commands: ["cd examples/cdk-pipelines", "pnpm cdk synth"],
// NOTE: you must manually create this in AWS Console.
input: CodePipelineSource.connection("cdk-labs/cdk-nextjs", "main", {
connectionArn: this.formatArn({
service: "codestar-connections",
resource: "connection",
resourceName: process.env["CODESTAR_CONNECTION_ID"],
}),
}),
primaryOutputDirectory: "examples/cdk-pipelines/cdk.out",
}),
});
pipeline.addStage(new MyStage(this, "prod", { env }));
}
}

export const stack = new CdkPipelinesStack(app, "cdk-pplns", {
env,
});

Aspects.of(app).add(new AwsSolutionsChecks({ verbose: true }));
58 changes: 58 additions & 0 deletions examples/cdk-pipelines/cdk.json
Original file line number Diff line number Diff line change
@@ -0,0 +1,58 @@
{
"app": "pnpm tsx app.ts",
"watch": {
"include": ["src/**"],
"exclude": ["node_modules", "cdk.out"]
},
"context": {
"see": "https://github.com/aws/aws-cdk/blob/main/packages/%40aws-cdk/cx-api/FEATURE_FLAGS.md",
"@aws-cdk/aws-lambda:recognizeLayerVersion": true,
"@aws-cdk/core:checkSecretUsage": true,
"@aws-cdk/core:target-partitions": ["aws", "aws-cn"],
"@aws-cdk-containers/ecs-service-extensions:enableDefaultLogDriver": true,
"@aws-cdk/aws-ec2:uniqueImdsv2TemplateName": true,
"@aws-cdk/aws-ecs:arnFormatIncludesClusterName": true,
"@aws-cdk/aws-iam:minimizePolicies": true,
"@aws-cdk/core:validateSnapshotRemovalPolicy": true,
"@aws-cdk/aws-codepipeline:crossAccountKeyAliasStackSafeResourceName": true,
"@aws-cdk/aws-s3:createDefaultLoggingPolicy": true,
"@aws-cdk/aws-sns-subscriptions:restrictSqsDescryption": true,
"@aws-cdk/aws-apigateway:disableCloudWatchRole": true,
"@aws-cdk/core:enablePartitionLiterals": true,
"@aws-cdk/aws-events:eventsTargetQueueSameAccount": true,
"@aws-cdk/aws-ecs:disableExplicitDeploymentControllerForCircuitBreaker": true,
"@aws-cdk/aws-iam:importedRoleStackSafeDefaultPolicyName": true,
"@aws-cdk/aws-s3:serverAccessLogsUseBucketPolicy": true,
"@aws-cdk/aws-route53-patters:useCertificate": true,
"@aws-cdk/customresources:installLatestAwsSdkDefault": false,
"@aws-cdk/aws-rds:databaseProxyUniqueResourceName": true,
"@aws-cdk/aws-codedeploy:removeAlarmsFromDeploymentGroup": true,
"@aws-cdk/aws-apigateway:authorizerChangeDeploymentLogicalId": true,
"@aws-cdk/aws-ec2:launchTemplateDefaultUserData": true,
"@aws-cdk/aws-secretsmanager:useAttachedSecretResourcePolicyForSecretTargetAttachments": true,
"@aws-cdk/aws-redshift:columnId": true,
"@aws-cdk/aws-stepfunctions-tasks:enableEmrServicePolicyV2": true,
"@aws-cdk/aws-ec2:restrictDefaultSecurityGroup": true,
"@aws-cdk/aws-apigateway:requestValidatorUniqueId": true,
"@aws-cdk/aws-kms:aliasNameRef": true,
"@aws-cdk/aws-autoscaling:generateLaunchTemplateInsteadOfLaunchConfig": true,
"@aws-cdk/core:includePrefixInUniqueNameGeneration": true,
"@aws-cdk/aws-efs:denyAnonymousAccess": true,
"@aws-cdk/aws-opensearchservice:enableOpensearchMultiAzWithStandby": true,
"@aws-cdk/aws-lambda-nodejs:useLatestRuntimeVersion": true,
"@aws-cdk/aws-efs:mountTargetOrderInsensitiveLogicalId": true,
"@aws-cdk/aws-rds:auroraClusterChangeScopeOfInstanceParameterGroupWithEachParameters": true,
"@aws-cdk/aws-appsync:useArnForSourceApiAssociationIdentifier": true,
"@aws-cdk/aws-rds:preventRenderingDeprecatedCredentials": true,
"@aws-cdk/aws-codepipeline-actions:useNewDefaultBranchForCodeCommitSource": true,
"@aws-cdk/aws-cloudwatch-actions:changeLambdaPermissionLogicalIdForLambdaAction": true,
"@aws-cdk/aws-codepipeline:crossAccountKeysDefaultValueToFalse": true,
"@aws-cdk/aws-codepipeline:defaultPipelineTypeToV2": true,
"@aws-cdk/aws-kms:reduceCrossAccountRegionPolicyScope": true,
"@aws-cdk/aws-eks:nodegroupNameAttribute": true,
"@aws-cdk/aws-ec2:ebsDefaultGp3Volume": true,
"@aws-cdk/aws-ecs:removeDefaultDeploymentAlarm": true,
"@aws-cdk/custom-resources:logApiResponseDataPropertyTrueDefault": false,
"@aws-cdk/aws-stepfunctions-tasks:ecsReduceRunTaskPermissions": true
}
}
21 changes: 21 additions & 0 deletions examples/cdk-pipelines/package.json
Original file line number Diff line number Diff line change
@@ -0,0 +1,21 @@
{
"name": "cdk-pipelines",
"type": "module",
"private": true,
"scripts": {
"deploy:local": "dotenv -- cdk deploy --require-approval never",
"synth:local": "dotenv -- cdk synth",
"destroy:local": "dotenv -- cdk destroy --force",
"deploy": "cdk deploy --require-approval never"
},
"dependencies": {
"aws-cdk": "^2.1005.0",
"aws-cdk-lib": "2.186.0",
"cdk-nextjs": "link:../..",
"constructs": "10.0.5",
"tsx": "^4.19.3"
},
"devDependencies": {
"@types/node": "^22.13.13"
}
}
3 changes: 3 additions & 0 deletions examples/cdk-pipelines/tsconfig.json
Original file line number Diff line number Diff line change
@@ -0,0 +1,3 @@
{
"extends": ["../tsconfig.json"]
}
33 changes: 8 additions & 25 deletions examples/global-functions/app.ts
Original file line number Diff line number Diff line change
Expand Up @@ -7,14 +7,14 @@ import { AwsSolutionsChecks, NagSuppressions } from "cdk-nag";
import {
suppressCommonNags,
suppressGlobalNags,
suppressLambdaNags,
suppressFunctionsNags,
} from "../shared/suppress-nags";
import { FlowLogDestination } from "aws-cdk-lib/aws-ec2";
import { Bucket, ObjectOwnership } from "aws-cdk-lib/aws-s3";

const app = new App();

class GlobalFunctionsStack extends Stack {
export class GlobalFunctionsStack extends Stack {
constructor(scope: Construct, id: string, props: StackProps) {
super(scope, id, props);
const logsBucket = this.#getLogsBucket();
Expand Down Expand Up @@ -90,28 +90,11 @@ export const stack = new GlobalFunctionsStack(app, "glbl-fns", {
region: process.env["CDK_DEFAULT_REGION"],
},
});
suppressCommonNags(stack);
suppressGlobalNags(stack);
suppressLambdaNags(stack);
NagSuppressions.addResourceSuppressionsByPath(
stack,
`/${stack.stackName}/Nextjs/NextjsRevalidation/Queue/Resource`,
[
{
id: "AwsSolutions-SQS3",
reason: "DLQ not required for example app",
},
],
);
NagSuppressions.addResourceSuppressionsByPath(
stack,
`/${stack.stackName}/Nextjs/NextjsRevalidation/Fn/ServiceRole/Resource`,
[
{
id: "AwsSolutions-IAM4",
reason: "AWSLambdaBasicExecutionRole is not overly permissive",
},
],
);

export function suppressGlobalFunctionsStackNags() {
suppressCommonNags(stack);
suppressGlobalNags(stack);
suppressFunctionsNags(stack);
}

Aspects.of(app).add(new AwsSolutionsChecks({ verbose: true }));
2 changes: 1 addition & 1 deletion examples/package.json
Original file line number Diff line number Diff line change
Expand Up @@ -5,7 +5,7 @@
"scripts": {
"prune": "turbo prune app-playground --docker --out-dir pruned/app-playground"
},
"packageManager": "pnpm@9.1.4+sha256.30a1801ac4e723779efed13a21f4c39f9eb6c9fbb4ced101bce06b422593d7c9",
"packageManager": "pnpm@10.11.0",
"devDependencies": {
"@tsconfig/node20": "^20.1.5",
"@tsconfig/strictest": "^2.0.5",
Expand Down
22 changes: 21 additions & 1 deletion examples/shared/suppress-nags.ts
Original file line number Diff line number Diff line change
Expand Up @@ -26,7 +26,7 @@ export function suppressCommonNags(stack: Stack) {
);
}

export function suppressLambdaNags(stack: Stack) {
export function suppressFunctionsNags(stack: Stack) {
NagSuppressions.addResourceSuppressionsByPath(
stack,
`/${stack.stackName}/Nextjs/NextjsFunctions/Functions/ServiceRole/Resource`,
Expand All @@ -48,6 +48,26 @@ export function suppressLambdaNags(stack: Stack) {
},
],
);
NagSuppressions.addResourceSuppressionsByPath(
stack,
`/${stack.stackName}/Nextjs/NextjsRevalidation/Queue/Resource`,
[
{
id: "AwsSolutions-SQS3",
reason: "DLQ not required for example app",
},
],
);
NagSuppressions.addResourceSuppressionsByPath(
stack,
`/${stack.stackName}/Nextjs/NextjsRevalidation/Fn/ServiceRole/Resource`,
[
{
id: "AwsSolutions-IAM4",
reason: "AWSLambdaBasicExecutionRole is not overly permissive",
},
],
);
}

export function suppressContainerNags(stack: Stack) {
Expand Down