Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

feat: add parameter helper functions on GuStack #92

Merged
merged 3 commits into from
Feb 17, 2021
Merged
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
38 changes: 0 additions & 38 deletions src/constructs/core/parameters.test.ts
Original file line number Diff line number Diff line change
@@ -1,22 +1,17 @@
import "@aws-cdk/assert/jest";
import { SynthUtils } from "@aws-cdk/assert/lib/synth-utils";
import { Stack } from "@aws-cdk/core";
import { simpleGuStackForTesting } from "../../../test/utils";
import type { SynthedStack } from "../../../test/utils";
import { Stage, Stages } from "../../constants";
import {
GuAmiParameter,
GuArnParameter,
GuInstanceTypeParameter,
GuParameter,
GuS3ObjectArnParameter,
GuStackParameter,
GuStageParameter,
GuStringParameter,
GuSubnetListParameter,
GuVpcParameter,
} from "./parameters";
import type { GuStack } from "./stack";

describe("The GuParameter class", () => {
it("sets the type as passed through by default", () => {
Expand Down Expand Up @@ -84,39 +79,6 @@ describe("The GuStringParameter class", () => {
});
});

describe("The GuStageParameter class", () => {
it("should set the values as required", () => {
const stack = new Stack() as GuStack;

new GuStageParameter(stack);

const json = SynthUtils.toCloudFormation(stack) as SynthedStack;

expect(json.Parameters.Stage).toEqual({
Type: "String",
Description: "Stage name",
AllowedValues: Stages,
Default: Stage.CODE,
});
});
});

describe("The GuStackParameter class", () => {
it("should set the values as required", () => {
const stack = new Stack() as GuStack;

new GuStackParameter(stack);

const json = SynthUtils.toCloudFormation(stack) as SynthedStack;

expect(json.Parameters.Stack).toEqual({
Type: "String",
Description: "Name of this stack",
Default: "deploy",
});
});
});

describe("The GuInstanceTypeParameter class", () => {
it("should combine default, override and prop values", () => {
const stack = simpleGuStackForTesting();
Expand Down
11 changes: 9 additions & 2 deletions src/constructs/core/parameters.ts
Original file line number Diff line number Diff line change
Expand Up @@ -10,11 +10,16 @@ export interface GuParameterProps extends CfnParameterProps {
export type GuNoTypeParameterProps = Omit<GuParameterProps, "type">;

export class GuParameter extends CfnParameter {
public readonly id: string;

constructor(scope: GuStack, id: string, props: GuParameterProps) {
super(scope, id, {
...props,
type: props.fromSSM ? `AWS::SSM::Parameter::Value<${props.type ?? "String"}>` : props.type,
});

this.id = id;
scope.setParam(this);
}
}

Expand All @@ -25,7 +30,8 @@ export class GuStringParameter extends GuParameter {
}

export class GuStageParameter extends GuParameter {
constructor(scope: GuStack, id: string = "Stage") {
public static readonly defaultId = "Stage";
constructor(scope: GuStack, id: string = GuStageParameter.defaultId) {
super(scope, id, {
type: "String",
description: "Stage name",
Expand All @@ -36,7 +42,8 @@ export class GuStageParameter extends GuParameter {
}

export class GuStackParameter extends GuParameter {
constructor(scope: GuStack, id: string = "Stack") {
public static readonly defaultId = "Stack";
constructor(scope: GuStack, id: string = GuStackParameter.defaultId) {
super(scope, id, {
type: "String",
description: "Name of this stack",
Expand Down
18 changes: 18 additions & 0 deletions src/constructs/core/stack.test.ts
Original file line number Diff line number Diff line change
Expand Up @@ -7,6 +7,7 @@ import { alphabeticalTags, simpleGuStackForTesting } from "../../../test/utils";
import type { SynthedStack } from "../../../test/utils";
import { Stage, Stages } from "../../constants";
import { TrackingTag } from "../../constants/library-info";
import { GuParameter } from "./parameters";
import { GuStack } from "./stack";

describe("The GuStack construct", () => {
Expand Down Expand Up @@ -63,4 +64,21 @@ describe("The GuStack construct", () => {

expect(stack.app).toBe("MyApp");
});

it("should return a parameter that exists", () => {
const stack = new GuStack(new App(), "Test", { app: "MyApp", stack: "test" });
const testParam = new GuParameter(stack, "MyTestParam", {});
stack.setParam(testParam);
akash1810 marked this conversation as resolved.
Show resolved Hide resolved

const actual = stack.getParam<GuParameter>("MyTestParam");
akash1810 marked this conversation as resolved.
Show resolved Hide resolved
expect(actual).toBe(testParam);
});

it("should throw on attempt to get a parameter that doesn't exist", () => {
const stack = new GuStack(new App(), "Test", { app: "MyApp", stack: "test" });

expect(() => stack.getParam<GuParameter>("i-do-not-exist")).toThrowError(
"Attempting to read parameter i-do-not-exist which does not exist"
);
});
});
22 changes: 19 additions & 3 deletions src/constructs/core/stack.ts
Original file line number Diff line number Diff line change
@@ -1,6 +1,7 @@
import type { App, StackProps } from "@aws-cdk/core";
import { Stack, Tags } from "@aws-cdk/core";
import { TrackingTag } from "../../constants/library-info";
import type { GuParameter } from "./parameters";
import { GuStageParameter } from "./parameters";

export interface GuStackProps extends StackProps {
Expand Down Expand Up @@ -39,14 +40,15 @@ export interface GuStackProps extends StackProps {
* ```
*/
export class GuStack extends Stack {
private readonly _stage: GuStageParameter;
private readonly _stack: string;
private readonly _app: string;

private params: Map<string, GuParameter>;

public readonly migratedFromCloudFormation: boolean;

get stage(): string {
return this._stage.valueAsString;
return this.getParam(GuStageParameter.defaultId).valueAsString;
}

get stack(): string {
Expand All @@ -73,13 +75,27 @@ export class GuStack extends Stack {
Tags.of(this).add(key, value, { applyToLaunchedInstances });
}

setParam(value: GuParameter): void {
this.params.set(value.id, value);
}

getParam<T extends GuParameter>(key: string): T {
if (!this.params.has(key)) {
throw new Error(`Attempting to read parameter ${key} which does not exist`);
}

return this.params.get(key) as T;
}

// eslint-disable-next-line custom-rules/valid-constructors -- GuStack is the exception as it must take an App
constructor(app: App, id: string, props: GuStackProps) {
super(app, id, props);

this.migratedFromCloudFormation = !!props.migratedFromCloudFormation;

this._stage = new GuStageParameter(this);
this.params = new Map<string, GuParameter>();
akash1810 marked this conversation as resolved.
Show resolved Hide resolved

new GuStageParameter(this);
this._stack = props.stack;
this._app = props.app;

Expand Down