Skip to content

Commit

Permalink
feat(codebuild): support images with WINDOWS_SERVER_2019_CONTAINER en…
Browse files Browse the repository at this point in the history
…vironment type (#9526)

Windows Server 2019 based images should have environment type
WINDOWS_SERVER_2019_CONTAINER. WindowsBuildImage uses the
WINDOWS_CONTAINER environment type. This patch solves this by adding a
WindowsImageType enum to the options passed the WindowsBuildImage
constructor that is used to correctly populate the type field.

fixes #9484

----

*By submitting this pull request, I confirm that my contribution is made under the terms of the Apache-2.0 license*
  • Loading branch information
ermanno committed Aug 18, 2020
1 parent 8cf4086 commit d3813e7
Show file tree
Hide file tree
Showing 3 changed files with 97 additions and 14 deletions.
32 changes: 25 additions & 7 deletions packages/@aws-cdk/aws-codebuild/README.md
Expand Up @@ -213,18 +213,36 @@ The CodeBuild library supports both Linux and Windows images via the
`LinuxBuildImage` and `WindowsBuildImage` classes, respectively.

You can specify one of the predefined Windows/Linux images by using one
of the constants such as `WindowsBuildImage.WINDOWS_BASE_2_0` or
`LinuxBuildImage.STANDARD_2_0`.
of the constants such as `WindowsBuildImage.WIN_SERVER_CORE_2019_BASE`,
`WindowsBuildImage.WINDOWS_BASE_2_0` or `LinuxBuildImage.STANDARD_2_0`.

Alternatively, you can specify a custom image using one of the static methods on
`XxxBuildImage`:
`LinuxBuildImage`:

* Use `.fromDockerRegistry(image[, { secretsManagerCredentials }])` to reference an image in any public or private Docker registry.
* Use `.fromEcrRepository(repo[, tag])` to reference an image available in an
* `LinuxBuildImage.fromDockerRegistry(image[, { secretsManagerCredentials }])` to reference an image in any public or private Docker registry.
* `LinuxBuildImage.fromEcrRepository(repo[, tag])` to reference an image available in an
ECR repository.
* Use `.fromAsset(directory)` to use an image created from a
* `LinuxBuildImage.fromAsset(parent, id, props)` to use an image created from a
local asset.
* Use `.fromCodeBuildImageId(id)` to reference a pre-defined, CodeBuild-provided Docker image.
* `LinuxBuildImage.fromCodeBuildImageId(id)` to reference a pre-defined, CodeBuild-provided Docker image.

or one of the corresponding methods on `WindowsBuildImage`:

* `WindowsBuildImage.fromDockerRegistry(image[, { secretsManagerCredentials }, imageType])`
* `WindowsBuildImage.fromEcrRepository(repo[, tag, imageType])`
* `WindowsBuildImage.fromAsset(parent, id, props, [, imageType])`

Note that the `WindowsBuildImage` version of the static methods accepts an optional parameter of type `WindowsImageType`,
which can be either `WindowsImageType.STANDARD`, the default, or `WindowsImageType.SERVER_2019`:

```typescript
new codebuild.Project(this, 'Project', {
environment: {
buildImage: codebuild.WindowsBuildImage.fromEcrRepository(ecrRepository, 'v1.0', codebuild.WindowsImageType.SERVER_2019),
},
...
})
```

The following example shows how to define an image from a Docker asset:

Expand Down
57 changes: 50 additions & 7 deletions packages/@aws-cdk/aws-codebuild/lib/project.ts
Expand Up @@ -1442,6 +1442,21 @@ export class LinuxBuildImage implements IBuildImage {
}
}

/**
* Environment type for Windows Docker images
*/
export enum WindowsImageType {
/**
* The standard environment type, WINDOWS_CONTAINER
*/
STANDARD = 'WINDOWS_CONTAINER',

/**
* The WINDOWS_SERVER_2019_CONTAINER environment type
*/
SERVER_2019 = 'WINDOWS_SERVER_2019_CONTAINER'
}

/**
* Construction properties of {@link WindowsBuildImage}.
* Module-private, as the constructor of {@link WindowsBuildImage} is private.
Expand All @@ -1451,6 +1466,7 @@ interface WindowsBuildImageProps {
readonly imagePullPrincipalType?: ImagePullPrincipalType;
readonly secretsManagerCredentials?: secretsmanager.ISecret;
readonly repository?: ecr.IRepository;
readonly imageType?: WindowsImageType;
}

/**
Expand All @@ -1460,9 +1476,9 @@ interface WindowsBuildImageProps {
*
* You can also specify a custom image using one of the static methods:
*
* - WindowsBuildImage.fromDockerRegistry(image[, { secretsManagerCredentials }])
* - WindowsBuildImage.fromEcrRepository(repo[, tag])
* - WindowsBuildImage.fromAsset(parent, id, props)
* - WindowsBuildImage.fromDockerRegistry(image[, { secretsManagerCredentials }, imageType])
* - WindowsBuildImage.fromEcrRepository(repo[, tag, imageType])
* - WindowsBuildImage.fromAsset(parent, id, props, [, imageType])
*
* @see https://docs.aws.amazon.com/codebuild/latest/userguide/build-env-ref-available.html
*/
Expand All @@ -1486,14 +1502,29 @@ export class WindowsBuildImage implements IBuildImage {
imagePullPrincipalType: ImagePullPrincipalType.CODEBUILD,
});

/**
* The standard CodeBuild image `aws/codebuild/windows-base:2019-1.0`, which is
* based off Windows Server Core 2019.
*/
public static readonly WIN_SERVER_CORE_2019_BASE: IBuildImage = new WindowsBuildImage({
imageId: 'aws/codebuild/windows-base:2019-1.0',
imagePullPrincipalType: ImagePullPrincipalType.CODEBUILD,
imageType: WindowsImageType.SERVER_2019,
});

/**
* @returns a Windows build image from a Docker Hub image.
*/
public static fromDockerRegistry(name: string, options: DockerImageOptions): IBuildImage {
public static fromDockerRegistry(
name: string,
options: DockerImageOptions = {},
imageType: WindowsImageType = WindowsImageType.STANDARD): IBuildImage {

return new WindowsBuildImage({
...options,
imageId: name,
imagePullPrincipalType: ImagePullPrincipalType.SERVICE_ROLE,
imageType,
});
}

Expand All @@ -1508,34 +1539,46 @@ export class WindowsBuildImage implements IBuildImage {
* @param repository The ECR repository
* @param tag Image tag (default "latest")
*/
public static fromEcrRepository(repository: ecr.IRepository, tag: string = 'latest'): IBuildImage {
public static fromEcrRepository(
repository: ecr.IRepository,
tag: string = 'latest',
imageType: WindowsImageType = WindowsImageType.STANDARD): IBuildImage {

return new WindowsBuildImage({
imageId: repository.repositoryUriForTag(tag),
imagePullPrincipalType: ImagePullPrincipalType.SERVICE_ROLE,
imageType,
repository,
});
}

/**
* Uses an Docker image asset as a Windows build image.
*/
public static fromAsset(scope: Construct, id: string, props: DockerImageAssetProps): IBuildImage {
public static fromAsset(
scope: Construct,
id: string,
props: DockerImageAssetProps,
imageType: WindowsImageType = WindowsImageType.STANDARD): IBuildImage {

const asset = new DockerImageAsset(scope, id, props);
return new WindowsBuildImage({
imageId: asset.imageUri,
imagePullPrincipalType: ImagePullPrincipalType.SERVICE_ROLE,
imageType,
repository: asset.repository,
});
}

public readonly type = 'WINDOWS_CONTAINER';
public readonly type: string;
public readonly defaultComputeType = ComputeType.MEDIUM;
public readonly imageId: string;
public readonly imagePullPrincipalType?: ImagePullPrincipalType;
public readonly secretsManagerCredentials?: secretsmanager.ISecret;
public readonly repository?: ecr.IRepository;

private constructor(props: WindowsBuildImageProps) {
this.type = (props.imageType ?? WindowsImageType.STANDARD).toString();
this.imageId = props.imageId;
this.imagePullPrincipalType = props.imagePullPrincipalType;
this.secretsManagerCredentials = props.secretsManagerCredentials;
Expand Down
22 changes: 22 additions & 0 deletions packages/@aws-cdk/aws-codebuild/test/test.codebuild.ts
Expand Up @@ -1508,6 +1508,28 @@ export = {
test.done();
},

'Windows2019 image': {
'WIN_SERVER_CORE_2016_BASE': {
'has type WINDOWS_SERVER_2019_CONTAINER and default ComputeType MEDIUM'(test: Test) {
const stack = new cdk.Stack();
new codebuild.PipelineProject(stack, 'Project', {
environment: {
buildImage: codebuild.WindowsBuildImage.WIN_SERVER_CORE_2019_BASE,
},
});

expect(stack).to(haveResourceLike('AWS::CodeBuild::Project', {
'Environment': {
'Type': 'WINDOWS_SERVER_2019_CONTAINER',
'ComputeType': 'BUILD_GENERAL1_MEDIUM',
},
}));

test.done();
},
},
},

'ARM image': {
'AMAZON_LINUX_2_ARM': {
'has type ARM_CONTAINER and default ComputeType LARGE'(test: Test) {
Expand Down

0 comments on commit d3813e7

Please sign in to comment.