From 5cd9609058d4da0bd71aa82b43e31e190af66299 Mon Sep 17 00:00:00 2001 From: Elad Ben-Israel Date: Thu, 13 Jun 2019 22:17:29 +0300 Subject: [PATCH] feat(s3): add missing storage classes and API cleanups (#2834) Fixes #2708 BREAKING CHANGE: `s3.StorageClass` is now an enum-like class instead of a regular enum. This means that you need to call `.value` in order to obtain it's value. * **s3:** `s3.Coordinates` renamed to `s3.Location` * **codepipeline:** `Artifact.s3Coordinates` renamed to `Artifact.s3Location`. --- ...ambda-deployed-through-codepipeline.lit.ts | 2 +- .../@aws-cdk/aws-codepipeline/lib/artifact.ts | 4 +- packages/@aws-cdk/aws-lambda/lib/code.ts | 12 ++--- packages/@aws-cdk/aws-s3/lib/bucket.ts | 21 +++++++-- packages/@aws-cdk/aws-s3/lib/index.ts | 2 +- .../lib/{coordinates.ts => location.ts} | 4 +- packages/@aws-cdk/aws-s3/lib/rule.ts | 46 ++++++++++++++++--- 7 files changed, 70 insertions(+), 21 deletions(-) rename packages/@aws-cdk/aws-s3/lib/{coordinates.ts => location.ts} (64%) diff --git a/packages/@aws-cdk/aws-codepipeline-actions/test/integ.lambda-deployed-through-codepipeline.lit.ts b/packages/@aws-cdk/aws-codepipeline-actions/test/integ.lambda-deployed-through-codepipeline.lit.ts index 9477b4406e120..752bad003e2c1 100644 --- a/packages/@aws-cdk/aws-codepipeline-actions/test/integ.lambda-deployed-through-codepipeline.lit.ts +++ b/packages/@aws-cdk/aws-codepipeline-actions/test/integ.lambda-deployed-through-codepipeline.lit.ts @@ -121,7 +121,7 @@ pipeline.addStage({ stackName: 'LambdaStackDeployedName', adminPermissions: true, parameterOverrides: { - ...lambdaCode.assign(lambdaBuildOutput.s3Coordinates), + ...lambdaCode.assign(lambdaBuildOutput.s3Location), }, extraInputs: [ lambdaBuildOutput, diff --git a/packages/@aws-cdk/aws-codepipeline/lib/artifact.ts b/packages/@aws-cdk/aws-codepipeline/lib/artifact.ts index c0cd163e9f4b6..917cb979b8d66 100644 --- a/packages/@aws-cdk/aws-codepipeline/lib/artifact.ts +++ b/packages/@aws-cdk/aws-codepipeline/lib/artifact.ts @@ -70,10 +70,10 @@ export class Artifact { } /** - * Returns the coordinates of the .zip file in S3 that this Artifact represents. + * Returns the location of the .zip file in S3 that this Artifact represents. * Used by Lambda's `CfnParametersCode` when being deployed in a CodePipeline. */ - public get s3Coordinates(): s3.Coordinates { + public get s3Location(): s3.Location { return { bucketName: this.bucketName, objectKey: this.objectKey, diff --git a/packages/@aws-cdk/aws-lambda/lib/code.ts b/packages/@aws-cdk/aws-lambda/lib/code.ts index eafd8a2c5f97c..5f097cddbdffa 100644 --- a/packages/@aws-cdk/aws-lambda/lib/code.ts +++ b/packages/@aws-cdk/aws-lambda/lib/code.ts @@ -262,18 +262,18 @@ export class CfnParametersCode extends Code { * Create a parameters map from this instance's CloudFormation parameters. * * It returns a map with 2 keys that correspond to the names of the parameters defined in this Lambda code, - * and as values it contains the appropriate expressions pointing at the provided S3 coordinates - * (most likely, obtained from a CodePipeline Artifact by calling the `artifact.s3Coordinates` method). + * and as values it contains the appropriate expressions pointing at the provided S3 location + * (most likely, obtained from a CodePipeline Artifact by calling the `artifact.s3Location` method). * The result should be provided to the CloudFormation Action * that is deploying the Stack that the Lambda with this code is part of, * in the `parameterOverrides` property. * - * @param coordinates the coordinates of the object in S3 that represents the Lambda code + * @param location the location of the object in S3 that represents the Lambda code */ - public assign(coordinates: s3.Coordinates): { [name: string]: any } { + public assign(location: s3.Location): { [name: string]: any } { const ret: { [name: string]: any } = {}; - ret[this.bucketNameParam] = coordinates.bucketName; - ret[this.objectKeyParam] = coordinates.objectKey; + ret[this.bucketNameParam] = location.bucketName; + ret[this.objectKeyParam] = location.objectKey; return ret; } diff --git a/packages/@aws-cdk/aws-s3/lib/bucket.ts b/packages/@aws-cdk/aws-s3/lib/bucket.ts index 78aaf22b4839b..2187a7bdee972 100644 --- a/packages/@aws-cdk/aws-s3/lib/bucket.ts +++ b/packages/@aws-cdk/aws-s3/lib/bucket.ts @@ -1060,17 +1060,24 @@ export class Bucket extends BucketBase { function parseLifecycleRule(rule: LifecycleRule): CfnBucket.RuleProperty { const enabled = rule.enabled !== undefined ? rule.enabled : true; - const x = { + const x: CfnBucket.RuleProperty = { // tslint:disable-next-line:max-line-length abortIncompleteMultipartUpload: rule.abortIncompleteMultipartUploadAfterDays !== undefined ? { daysAfterInitiation: rule.abortIncompleteMultipartUploadAfterDays } : undefined, expirationDate: rule.expirationDate, expirationInDays: rule.expirationInDays, id: rule.id, noncurrentVersionExpirationInDays: rule.noncurrentVersionExpirationInDays, - noncurrentVersionTransitions: rule.noncurrentVersionTransitions, + noncurrentVersionTransitions: mapOrUndefined(rule.noncurrentVersionTransitions, t => ({ + storageClass: t.storageClass.value, + transitionInDays: t.transitionInDays + })), prefix: rule.prefix, status: enabled ? 'Enabled' : 'Disabled', - transitions: rule.transitions, + transitions: mapOrUndefined(rule.transitions, t => ({ + storageClass: t.storageClass.value, + transitionDate: t.transitionDate, + transitionInDays: t.transitionInDays + })), tagFilters: self.parseTagFilters(rule.tagFilters) }; @@ -1280,3 +1287,11 @@ export interface OnCloudTrailBucketEventOptions extends events.OnEventOptions { */ readonly paths?: string[]; } + +function mapOrUndefined(list: T[] | undefined, callback: (element: T) => U): U[] | undefined { + if (!list || list.length === 0) { + return undefined; + } + + return list.map(callback); +} \ No newline at end of file diff --git a/packages/@aws-cdk/aws-s3/lib/index.ts b/packages/@aws-cdk/aws-s3/lib/index.ts index f3877cd18f485..1dc376d335420 100644 --- a/packages/@aws-cdk/aws-s3/lib/index.ts +++ b/packages/@aws-cdk/aws-s3/lib/index.ts @@ -1,7 +1,7 @@ export * from './bucket'; export * from './bucket-policy'; export * from './destination'; -export * from './coordinates'; +export * from './location'; export * from './rule'; // AWS::S3 CloudFormation Resources: diff --git a/packages/@aws-cdk/aws-s3/lib/coordinates.ts b/packages/@aws-cdk/aws-s3/lib/location.ts similarity index 64% rename from packages/@aws-cdk/aws-s3/lib/coordinates.ts rename to packages/@aws-cdk/aws-s3/lib/location.ts index 6b096762fd573..c081ef343d227 100644 --- a/packages/@aws-cdk/aws-s3/lib/coordinates.ts +++ b/packages/@aws-cdk/aws-s3/lib/location.ts @@ -1,7 +1,7 @@ /** - * An interface that represents the coordinates of a specific object in an S3 Bucket. + * An interface that represents the location of a specific object in an S3 Bucket. */ -export interface Coordinates { +export interface Location { /** * The name of the S3 Bucket the object is in. */ diff --git a/packages/@aws-cdk/aws-s3/lib/rule.ts b/packages/@aws-cdk/aws-s3/lib/rule.ts index 186469dd0048a..ea20482e63ee9 100644 --- a/packages/@aws-cdk/aws-s3/lib/rule.ts +++ b/packages/@aws-cdk/aws-s3/lib/rule.ts @@ -146,23 +146,57 @@ export interface NoncurrentVersionTransition { /** * Storage class to move an object to */ -export enum StorageClass { +export class StorageClass { /** - * Storage class for data that is accessed less frequently, but requires rapid access when needed. + * Storage class for data that is accessed less frequently, but requires rapid + * access when needed. * * Has lower availability than Standard storage. */ - InfrequentAccess = 'STANDARD_IA', + public static readonly InfrequentAccess = new StorageClass('STANDARD_IA'); /** * Infrequent Access that's only stored in one availability zone. * * Has lower availability than standard InfrequentAccess. */ - OneZoneInfrequentAccess = 'ONEZONE_IA', + public static readonly OneZoneInfrequentAccess = new StorageClass('ONEZONE_IA'); /** - * Storage class for long-term archival that can take between minutes and hours to access. + * Storage class for long-term archival that can take between minutes and + * hours to access. + * + * Use for archives where portions of the data might need to be retrieved in + * minutes. Data stored in the GLACIER storage class has a minimum storage + * duration period of 90 days and can be accessed in as little as 1-5 minutes + * using expedited retrieval. If you delete an object before the 90-day + * minimum, you are charged for 90 days. */ - Glacier = 'GLACIER' + public static readonly Glacier = new StorageClass('GLACIER'); + + /** + * Use for archiving data that rarely needs to be accessed. Data stored in the + * DEEP_ARCHIVE storage class has a minimum storage duration period of 180 + * days and a default retrieval time of 12 hours. If you delete an object + * before the 180-day minimum, you are charged for 180 days. For pricing + * information, see Amazon S3 Pricing. + */ + public static readonly DeepArchive = new StorageClass('DEEP_ARCHIVE'); + + /** + * The INTELLIGENT_TIERING storage class is designed to optimize storage costs + * by automatically moving data to the most cost-effective storage access + * tier, without performance impact or operational overhead. + * INTELLIGENT_TIERING delivers automatic cost savings by moving data on a + * granular object level between two access tiers, a frequent access tier and + * a lower-cost infrequent access tier, when access patterns change. The + * INTELLIGENT_TIERING storage class is ideal if you want to optimize storage + * costs automatically for long-lived data when access patterns are unknown or + * unpredictable. + */ + public static readonly IntelligentTiering = new StorageClass('INTELLIGENT_TIERING'); + + constructor(public readonly value: string) { } + + public toString() { return this.value; } }