@go-to-k/cdkd 0.300.1 → 0.301.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.
- package/dist/{asg-provider-BS5i71bK.js → asg-provider-CK2nZE6B.js} +3 -3
- package/dist/{asg-provider-BS5i71bK.js.map → asg-provider-CK2nZE6B.js.map} +1 -1
- package/dist/aws-failure-text-BEQfs6za.js.map +1 -1
- package/dist/cli.js +2 -2
- package/dist/{deploy-engine-BK4gG_5A.js → deploy-engine-DEvS2r2M.js} +1697 -1047
- package/dist/deploy-engine-DEvS2r2M.js.map +1 -0
- package/dist/{iam-policy-targets-DAs3w7QW.js → iam-policy-targets-DFk7zr0Q.js} +27 -2
- package/dist/iam-policy-targets-DFk7zr0Q.js.map +1 -0
- package/dist/{iam-role-provider-SmvPHPLC.js → iam-role-provider-s7oQ_V1d.js} +4 -10
- package/dist/iam-role-provider-s7oQ_V1d.js.map +1 -0
- package/dist/index.d.ts +25 -1
- package/dist/index.d.ts.map +1 -1
- package/dist/index.js +3 -3
- package/dist/{neptune-provider-CqZ1FaqT.js → neptune-provider-BWESr5fm.js} +3 -3
- package/dist/{neptune-provider-CqZ1FaqT.js.map → neptune-provider-BWESr5fm.js.map} +1 -1
- package/dist/{program-DVPHKsxv.js → program-C_kDHyxY.js} +111 -86
- package/dist/program-C_kDHyxY.js.map +1 -0
- package/dist/{provider-classes-CDzT2xg0.js → provider-classes-C1xbZd9k.js} +229 -110
- package/dist/provider-classes-C1xbZd9k.js.map +1 -0
- package/dist/{rds-provider-DraxDuQq.js → rds-provider-BfwQbYRR.js} +3 -3
- package/dist/{rds-provider-DraxDuQq.js.map → rds-provider-BfwQbYRR.js.map} +1 -1
- package/dist/{version-DTSDiQcV.js → version-BdWNHoO2.js} +2 -2
- package/dist/{version-DTSDiQcV.js.map → version-BdWNHoO2.js.map} +1 -1
- package/package.json +2 -2
- package/dist/deploy-engine-BK4gG_5A.js.map +0 -1
- package/dist/iam-policy-targets-DAs3w7QW.js.map +0 -1
- package/dist/iam-role-provider-SmvPHPLC.js.map +0 -1
- package/dist/program-DVPHKsxv.js.map +0 -1
- package/dist/provider-classes-CDzT2xg0.js.map +0 -1
|
@@ -1,13 +1,13 @@
|
|
|
1
1
|
import { r as getAwsClients } from "./aws-clients-B_CEQGE1.js";
|
|
2
2
|
import { B as safeMsg, F as displaySafe, I as displayStackName, L as isPasteableIdent, O as SECRET_REF_MAX_CODE_POINTS, P as displayIdent, a as getLogger, b as generateResourceNameWithFallback, n as isAwsAuthoredFailure, r as safeStringify, t as describeAwsFailure, y as generateResourceName, z as plainIdentOr } from "./aws-failure-text-BEQfs6za.js";
|
|
3
|
-
import { $ as protectedReplacementAdvice, $t as ambientCredentialConfig, A as isQuotableImportValue, B as isTerminalDeleteFailure, C as setBounded, D as VALUE_NOT_SHOWN, E as assertRegionMatch, F as resolveExplicitPhysicalId, Fn as isInertUnquoted, H as observeThenDisableProtection, Hn as withheldTargetClause, In as pasteableCommand, Kt as injectiveKey, L as ProtectionFlipRegistry, M as quotedRemedyLogicalId, Mt as markCreatedBeforeFailure, N as refusalTypeShown, Nn as commandHole, Nt as markSupersedesEarlierCreate, O as isPlainImportJson, P as remedyLogicalId, Pn as hasClauseBreak, Q as pasteableAwsCommand, Qn as markReplayMayCollide, Qt as ambientClientDefaults, Rn as plainOrDescribed, S as replayedSendWindow, St as withDerivedNameMasks, T as RESOURCE_NOT_FOUND, Tt as clearCreatedBeforeFailure, U as protectionFlipKey, V as logGroupProtectionSite, Vn as shellQuote, W as rdsFamilyProtectionSite, X as WITHHELD_AWS_COMMAND, Y as UNNAMEABLE_ID_CLAUSE, Z as isAwsCliLiteral, Zn as markNameCollision, Zt as withPasteableAwsProfile, _ as RecentIdSet, _t as createMaskedLogSinks, a as onlySecretDerived, at as startInterruptWatch, b as isInsideWindow, bn as ResourceUpdateNotSupportedError, bt as maskDeep, c as recordedPrincipalsRepair, cr as
|
|
3
|
+
import { $ as protectedReplacementAdvice, $n as explicitDenyPolicyKind, $t as ambientCredentialConfig, A as isQuotableImportValue, B as isTerminalDeleteFailure, C as setBounded, D as VALUE_NOT_SHOWN, E as assertRegionMatch, F as resolveExplicitPhysicalId, Fn as isInertUnquoted, H as observeThenDisableProtection, Hn as withheldTargetClause, In as pasteableCommand, Kt as injectiveKey, L as ProtectionFlipRegistry, M as quotedRemedyLogicalId, Mt as markCreatedBeforeFailure, N as refusalTypeShown, Nn as commandHole, Nt as markSupersedesEarlierCreate, O as isPlainImportJson, P as remedyLogicalId, Pn as hasClauseBreak, Q as pasteableAwsCommand, Qn as markReplayMayCollide, Qt as ambientClientDefaults, Rn as plainOrDescribed, S as replayedSendWindow, St as withDerivedNameMasks, T as RESOURCE_NOT_FOUND, Tt as clearCreatedBeforeFailure, U as protectionFlipKey, V as logGroupProtectionSite, Vn as shellQuote, W as rdsFamilyProtectionSite, X as WITHHELD_AWS_COMMAND, Y as UNNAMEABLE_ID_CLAUSE, Z as isAwsCliLiteral, Zn as markNameCollision, Zt as withPasteableAwsProfile, _ as RecentIdSet, _t as createMaskedLogSinks, a as onlySecretDerived, ar as isRetryableTransientError, at as startInterruptWatch, b as isInsideWindow, bn as ResourceUpdateNotSupportedError, bt as maskDeep, c as recordedPrincipalsRepair, cr as THROTTLING_ERROR_NAMES, ct as canonicalizeRoute53QueryName, dr as markNonRetryable, dt as compositeIdSkipResult, en as clientDefaultsFor, et as renderDisableCommand, fr as markRedactedCause, ft as logicalIdShown, g as AmbiguousCreateLatch, gt as stateOrphanRecordRemedy, h as AMBIGUOUS_LATCH_TTL_MS, ht as segmentAfterAnchor, i as holdsSecretDerivedEntry, in as CdkdError, it as isInterruptedWaitError, j as normalizeAwsTagsToCfn, jt as markAuxiliaryFailure, k as isPlainImportValue, lr as isMarkedNonRetryable, lt as compositeIdFormatMessage, nn as AccountIdUnavailableError, nr as isAmbiguousOutcomeError, o as readPrincipalLists, or as isTransientServerError, ot as ElapsedBudgetRegistry, p as withRemovalDefaults, pr as wrapMaskedAwsError, pt as packCompositeId, q as userPoolProtectionSite, qt as injectiveKeyPrefix, r as SECRET_DERIVED_READ_LIVE, rr as isExplicitDenyError, tn as credentialFingerprint, u as clearOnUpdateRemoval, ur as isThrottlingError, ut as compositeIdSeparatorRefusal, v as ambiguousAttemptLead, vn as ProvisioningError, vt as createMaskedRetryLogger, w as withoutServerErrorRetries, x as replayFollowedAmbiguousAttempt, xt as maskerOrIdentity, y as createAttemptKey, yt as isSecretDerivedValue, z as deleteWithProtectionCompensation } from "./iam-policy-targets-DFk7zr0Q.js";
|
|
4
4
|
import { s as ambientRegion } from "./aws-client-defaults-DBXBcg0J.js";
|
|
5
|
-
import { $ as S3_AUTO_DELETE_OBJECTS_TAG,
|
|
6
|
-
import { n as collectInlinePolicyNamesManagedBySiblings, r as IamCreateClientCache, t as IAMRoleProvider } from "./iam-role-provider-
|
|
7
|
-
import { a as resolveSecretDerivedPrincipals, i as isResolvableSecretPrincipalList, n as runDestroyForStack, o as canonicalizeIpProtocolValue, r as holdsUnprovenSecretPrincipalToken, s as resolvedResourceTimeoutMs, t as canonicalizeIpv4Cidr } from "./program-
|
|
8
|
-
import { RDSProvider } from "./rds-provider-
|
|
9
|
-
import { NeptuneProvider } from "./neptune-provider-
|
|
10
|
-
import { ASGProvider } from "./asg-provider-
|
|
5
|
+
import { $ as S3_AUTO_DELETE_OBJECTS_TAG, Bl as renderAssemblyPathEscape, Br as deleteSkipReason, C as withApiLimit, Co as configIntegerRefusal, Dl as canonicalizeRegion, Do as requireConfigArray, Ds as recoverMaskedOutput, Eo as replayWarn, Fo as lambdaFunctionNameForMask, Fr as unchangedBehindSecretReference, G as deleteBudgetKey, Gr as ec2InstanceProtectionSite, Gt as awaitInFlightSibling, H as DYNAMODB_DELETE_MIN_RESOURCE_TIMEOUT_MS, Hi as passedParameterClassesOf, Hr as isWaitAbandonedError, Ht as withNestedStackContext, Io as sameLambdaFunctionAddress, J as DELETE_INDEX_WAIT_PROCEED_NOTE, Jo as passedNoEchoParametersOf, Jr as reDisableInstanceApiTermination, K as resolveDynamoDbDeleteBudgetClock, Kr as isTerminationProtectionPropagationError, Lt as revertNestedChildFromJournal, Ms as carriesSecretMask, No as withRetry, Ol as derivePartitionAndUrlSuffix, Oo as requireConfigObject, Or as getCurrentResourceSecrets, Os as physicalNameCopiesOf, Po as canonicalLambdaFunctionName, Pr as slowCcOperationTimeoutMs, Pt as getNestedRevertRun, Q as ECR_AUTO_DELETE_IMAGES_TAG, Rl as describeFileReadFailure, S as lookupEachName, Sc as rewriteTemplateAssetReferences, So as configBooleanRefusal, To as readConfigString, U as beginDeleteWait, Ur as markWaitAbandoned, V as DynamoDBGlobalTableProvider, Vl as resolveAssemblyPath, Vr as withIndeterminateGuard, Vt as getCurrentNestedStackContext, W as compensateRemovedDeletionProtection, Wa as refuseMalformedResourcesForDestroy, X as deleteTableWithIndexBusyRetry, Xt as replacedDeleteFailureVerdict, Y as INDEX_SETTLE_POLL_INTERVAL_MS, Yi as accountArgs, Yr as reEnableInstanceApiTermination, Z as waitForIndexesSettled, _c as stringifyValue, _i as s3BucketArn, _o as isWarmThroughputDecrease, _r as tagPlanWarning, b as chunks, bi as s3BucketRegionalDomainName, bo as coerceCfnBoolean, c as isAbsoluteAssetPath, cr as acquireIdempotencyToken, dn as REDACTED_DELETE_ADDRESS_SKIP_REASON, dr as DBPROXY_TAGS_WHAT, et as hasCdkAutoDeleteTag, fi as isSettledInstanceState, fn as isRedactedRecordedValue, fr as DBPROXY_TAG_OPTIONS, go as coerceWarmThroughput$1, gr as tagMapAsList, gs as redactSecretsForState, ho as WARM_THROUGHPUT_MEMBERS, hr as refuseMalformedDesiredTags, hs as snapshotPassProvenance, io as findSilentDropProperties, ir as earliestDefined, ki as getAccountInfo, ko as requireConfigString, ks as recordAttributeIdCopy, l as listNestedTemplateRows, ln as getCurrentProducerRegions, lr as isRefusedByName, mi as outputReferenceProvenanceOf, mn as redactedDeleteAddressSkip, mr as readTagList, ms as recordReferenceProvenanceEntry, no as withheldAccountClause, nt as getPriorAttempts, oo as withoutSilentDropProperties, or as reserveStackCreateToken, pn as redactedDeleteAddressFields, pr as planTagDiff, ps as markSameGenerationBag, q as resolveDynamoDbDeleteBudgetMs, qr as observeThenDisableInstanceApiTermination, qt as getStackRecords, rt as markRefusedBeforeApplying, s as findNestedTemplateTreeDefect, t as DeployEngine, ts as hasMaskableValues, tt as isTruthyCfnBoolean, u as renderNestedTemplateTreeDefect, ur as markDeleteStarted, vi as s3BucketDomainName, vo as toCfnInteger, vr as definedAttributes, wa as refuseMalformedNestedChildOutputs, wl as decodeListingKey, wo as configStringRefusal, x as isAccessDeniedError, xi as s3BucketWebsiteUrl, xo as coerceCfnInteger, xs as dynamicReferenceTokens, yi as s3BucketDualStackDomainName, yo as toFiniteNumber, yr as stringifyIfAssigned, ys as withoutPhysicalNameCopies, zi as parseWebACLArn, zl as displayAssemblyPath } from "./deploy-engine-DEvS2r2M.js";
|
|
6
|
+
import { n as collectInlinePolicyNamesManagedBySiblings, r as IamCreateClientCache, t as IAMRoleProvider } from "./iam-role-provider-s7oQ_V1d.js";
|
|
7
|
+
import { a as resolveSecretDerivedPrincipals, i as isResolvableSecretPrincipalList, n as runDestroyForStack, o as canonicalizeIpProtocolValue, r as holdsUnprovenSecretPrincipalToken, s as resolvedResourceTimeoutMs, t as canonicalizeIpv4Cidr } from "./program-C_kDHyxY.js";
|
|
8
|
+
import { RDSProvider } from "./rds-provider-BfwQbYRR.js";
|
|
9
|
+
import { NeptuneProvider } from "./neptune-provider-BWESr5fm.js";
|
|
10
|
+
import { ASGProvider } from "./asg-provider-CK2nZE6B.js";
|
|
11
11
|
import { createHash, randomUUID } from "node:crypto";
|
|
12
12
|
import { CreateBucketCommand, DeleteBucketAnalyticsConfigurationCommand, DeleteBucketCommand, DeleteBucketCorsCommand, DeleteBucketEncryptionCommand, DeleteBucketIntelligentTieringConfigurationCommand, DeleteBucketInventoryConfigurationCommand, DeleteBucketLifecycleCommand, DeleteBucketMetricsConfigurationCommand, DeleteBucketOwnershipControlsCommand, DeleteBucketPolicyCommand, DeleteBucketReplicationCommand, DeleteBucketTaggingCommand, DeleteBucketWebsiteCommand, DeleteObjectsCommand, GetBucketAccelerateConfigurationCommand, GetBucketCorsCommand, GetBucketEncryptionCommand, GetBucketLifecycleConfigurationCommand, GetBucketLocationCommand, GetBucketLoggingCommand, GetBucketNotificationConfigurationCommand, GetBucketOwnershipControlsCommand, GetBucketPolicyCommand, GetBucketReplicationCommand, GetBucketTaggingCommand, GetBucketVersioningCommand, GetBucketWebsiteCommand, GetObjectCommand, GetObjectLockConfigurationCommand, GetPublicAccessBlockCommand, HeadBucketCommand, ListBucketAnalyticsConfigurationsCommand, ListBucketIntelligentTieringConfigurationsCommand, ListBucketInventoryConfigurationsCommand, ListBucketMetricsConfigurationsCommand, ListBucketsCommand, ListObjectVersionsCommand, ListObjectsV2Command, NoSuchBucket, PutBucketAccelerateConfigurationCommand, PutBucketAnalyticsConfigurationCommand, PutBucketCorsCommand, PutBucketEncryptionCommand, PutBucketIntelligentTieringConfigurationCommand, PutBucketInventoryConfigurationCommand, PutBucketLifecycleConfigurationCommand, PutBucketLoggingCommand, PutBucketMetricsConfigurationCommand, PutBucketNotificationConfigurationCommand, PutBucketOwnershipControlsCommand, PutBucketPolicyCommand, PutBucketReplicationCommand, PutBucketTaggingCommand, PutBucketVersioningCommand, PutBucketWebsiteCommand, PutObjectLockConfigurationCommand, PutPublicAccessBlockCommand, S3Client } from "@aws-sdk/client-s3";
|
|
13
13
|
import { AddRoleToInstanceProfileCommand, AddUserToGroupCommand, AttachGroupPolicyCommand, AttachRolePolicyCommand, AttachUserPolicyCommand, CreateAccessKeyCommand, CreateGroupCommand, CreateInstanceProfileCommand, CreateLoginProfileCommand, CreatePolicyCommand, CreatePolicyVersionCommand, CreateUserCommand, DeleteAccessKeyCommand, DeleteGroupCommand, DeleteGroupPolicyCommand, DeleteInstanceProfileCommand, DeleteLoginProfileCommand, DeletePolicyCommand, DeletePolicyVersionCommand, DeleteRolePolicyCommand, DeleteUserCommand, DeleteUserPermissionsBoundaryCommand, DeleteUserPolicyCommand, DetachGroupPolicyCommand, DetachRolePolicyCommand, DetachUserPolicyCommand, GetAccessKeyLastUsedCommand, GetGroupCommand, GetGroupPolicyCommand, GetInstanceProfileCommand, GetPolicyCommand, GetPolicyVersionCommand, GetRolePolicyCommand, GetUserCommand, GetUserPolicyCommand, IAMClient, ListAccessKeysCommand, ListAttachedGroupPoliciesCommand, ListAttachedUserPoliciesCommand, ListEntitiesForPolicyCommand, ListGroupPoliciesCommand, ListGroupsForUserCommand, ListPoliciesCommand, ListPolicyTagsCommand, ListPolicyVersionsCommand, ListUserPoliciesCommand, NoSuchEntityException, PutGroupPolicyCommand, PutRolePolicyCommand, PutUserPermissionsBoundaryCommand, PutUserPolicyCommand, RemoveRoleFromInstanceProfileCommand, RemoveUserFromGroupCommand, TagPolicyCommand, TagUserCommand, UntagPolicyCommand, UntagUserCommand, UpdateAccessKeyCommand, UpdateLoginProfileCommand } from "@aws-sdk/client-iam";
|
|
@@ -3259,6 +3259,8 @@ function isPlainBucketName(value) {
|
|
|
3259
3259
|
const BUCKET_LIST_IDENTITY_ATTEMPTS = 3;
|
|
3260
3260
|
const BUCKET_LIST_IDENTITY_DELAY_MS = 1500;
|
|
3261
3261
|
const BUCKET_LIST_IDENTITY_BUDGET_MS = 6e3;
|
|
3262
|
+
const OWN_WRITE_HEAD_ATTEMPTS = 5;
|
|
3263
|
+
const OWN_WRITE_HEAD_DELAY_MS = 500;
|
|
3262
3264
|
function isNoSuchBucketError(error) {
|
|
3263
3265
|
return error?.name === "NoSuchBucket";
|
|
3264
3266
|
}
|
|
@@ -3324,6 +3326,15 @@ function takeOwnLeftoverBucket(logicalId) {
|
|
|
3324
3326
|
ownLeftoverBuckets.delete(key);
|
|
3325
3327
|
return held !== void 0 && Date.now() - held.heldAtMs <= 18e5 ? held.identity : void 0;
|
|
3326
3328
|
}
|
|
3329
|
+
function isCreateTagResourceDenial(error) {
|
|
3330
|
+
return error instanceof Error && error.name === "AccessDenied" && describeAwsFailure(error).detail.includes("s3:TagResource");
|
|
3331
|
+
}
|
|
3332
|
+
function isCreateTagsShapeRefusal(error) {
|
|
3333
|
+
if (!(error instanceof Error)) return false;
|
|
3334
|
+
if (error.name === "MalformedXML" || error.name === "NotImplemented") return true;
|
|
3335
|
+
return (error.name === "InvalidArgument" || error.name === "InvalidRequest") && /\btags?\b/i.test(describeAwsFailure(error).detail);
|
|
3336
|
+
}
|
|
3337
|
+
const untaggedExplicitDeny = /* @__PURE__ */ new WeakMap();
|
|
3327
3338
|
var S3BucketProvider = class S3BucketProvider {
|
|
3328
3339
|
s3Client;
|
|
3329
3340
|
createClientHolder = {};
|
|
@@ -4603,6 +4614,11 @@ var S3BucketProvider = class S3BucketProvider {
|
|
|
4603
4614
|
const canonicalRegion = canonicalizeRegion(region);
|
|
4604
4615
|
if (canonicalRegion !== "us-east-1") createParams.CreateBucketConfiguration = { LocationConstraint: canonicalRegion };
|
|
4605
4616
|
if (declaresBucketObjectLock(properties)) createParams.ObjectLockEnabledForBucket = true;
|
|
4617
|
+
if (desiredTags.length > 0) createParams.CreateBucketConfiguration = {
|
|
4618
|
+
...createParams.CreateBucketConfiguration,
|
|
4619
|
+
Tags: desiredTags
|
|
4620
|
+
};
|
|
4621
|
+
let tagsAppliedOnCreate = false;
|
|
4606
4622
|
const preflight = canonicalizeRegion(region) === "us-east-1" ? await this.probeBucketRegion(bucketName) : { kind: "absent" };
|
|
4607
4623
|
let createdNewBucket = false;
|
|
4608
4624
|
const createClient = await this.getCreateClient();
|
|
@@ -4628,11 +4644,40 @@ var S3BucketProvider = class S3BucketProvider {
|
|
|
4628
4644
|
}
|
|
4629
4645
|
try {
|
|
4630
4646
|
const attemptStartMs = Date.now();
|
|
4631
|
-
if (!adoptedOwnLeftover)
|
|
4632
|
-
|
|
4633
|
-
|
|
4634
|
-
|
|
4635
|
-
|
|
4647
|
+
if (!adoptedOwnLeftover) {
|
|
4648
|
+
let tagsSent = createParams.CreateBucketConfiguration?.Tags !== void 0;
|
|
4649
|
+
try {
|
|
4650
|
+
try {
|
|
4651
|
+
await createClient.send(new CreateBucketCommand(createParams));
|
|
4652
|
+
} catch (taggedError) {
|
|
4653
|
+
const tagResourceDenied = isCreateTagResourceDenial(taggedError);
|
|
4654
|
+
if (!tagsSent || !(tagResourceDenied || isCreateTagsShapeRefusal(taggedError))) throw taggedError;
|
|
4655
|
+
this.logger.debug(safeMsg`CreateBucket with tags was ${tagResourceDenied ? "denied s3:TagResource" : "refused for its Tags member"} for ${displaySafe(logicalId)}; ` + `retrying without tags and applying them with PutBucketTagging`);
|
|
4656
|
+
const { Tags: _omitted, ...rest } = createParams.CreateBucketConfiguration ?? {};
|
|
4657
|
+
const untagged = { ...createParams };
|
|
4658
|
+
if (Object.keys(rest).length > 0) untagged.CreateBucketConfiguration = rest;
|
|
4659
|
+
else delete untagged.CreateBucketConfiguration;
|
|
4660
|
+
tagsSent = false;
|
|
4661
|
+
try {
|
|
4662
|
+
await createClient.send(new CreateBucketCommand(untagged));
|
|
4663
|
+
} catch (untaggedError) {
|
|
4664
|
+
if (tagResourceDenied && untaggedError instanceof Error && untaggedError.name === "AccessDenied") {
|
|
4665
|
+
this.logger.debug(safeMsg`CreateBucket without tags was denied too for ${displaySafe(logicalId)}; ` + `reporting the s3:TagResource denial`);
|
|
4666
|
+
const untaggedText = describeAwsFailure(untaggedError).detail;
|
|
4667
|
+
if (isExplicitDenyError(untaggedText) && taggedError instanceof Error) {
|
|
4668
|
+
untaggedExplicitDeny.set(taggedError, explicitDenyPolicyKind(untaggedText) ?? null);
|
|
4669
|
+
markNonRetryable(taggedError);
|
|
4670
|
+
}
|
|
4671
|
+
throw taggedError;
|
|
4672
|
+
}
|
|
4673
|
+
throw untaggedError;
|
|
4674
|
+
}
|
|
4675
|
+
}
|
|
4676
|
+
} catch (sendError) {
|
|
4677
|
+
createBucketLatch.noteFailure(logicalId, sendError, attemptStartMs, ambiguousWindow);
|
|
4678
|
+
throw sendError;
|
|
4679
|
+
}
|
|
4680
|
+
tagsAppliedOnCreate = tagsSent && preflight.kind === "absent";
|
|
4636
4681
|
}
|
|
4637
4682
|
createdNewBucket = adoptedOwnLeftover || preflight.kind === "absent";
|
|
4638
4683
|
bucketLeftBehind = createdNewBucket;
|
|
@@ -4658,7 +4703,7 @@ var S3BucketProvider = class S3BucketProvider {
|
|
|
4658
4703
|
try {
|
|
4659
4704
|
effectiveOverrides = await this.applyConfiguration(bucketName, properties, {
|
|
4660
4705
|
...context ? { context } : {},
|
|
4661
|
-
desiredTags
|
|
4706
|
+
...tagsAppliedOnCreate ? { skipTags: true } : { desiredTags }
|
|
4662
4707
|
});
|
|
4663
4708
|
for (const [key, value] of await this.applyAllSubConfigsForCreate(bucketName, properties, context)) effectiveOverrides.set(key, value);
|
|
4664
4709
|
} catch (innerError) {
|
|
@@ -4765,7 +4810,12 @@ var S3BucketProvider = class S3BucketProvider {
|
|
|
4765
4810
|
wrapOperationError(operation, logicalId, resourceType, physicalId, error) {
|
|
4766
4811
|
const failure = describeAwsFailure(error);
|
|
4767
4812
|
if (failure.redacted) this.logger.debug(`Failed to ${operation} S3 bucket ${displaySafe(logicalId)} (${this.shown(physicalId)}): ${this.maskRaw(failure.detail)}`);
|
|
4768
|
-
const
|
|
4813
|
+
const denyKind = failure.redacted ? explicitDenyPolicyKind(failure.detail) : void 0;
|
|
4814
|
+
const denyNote = failure.redacted && isExplicitDenyError(failure.detail) ? ` Refused by an explicit deny${denyKind !== void 0 ? ` (${denyKind})` : ""}, which retrying cannot clear.` : "";
|
|
4815
|
+
const tagResourceNote = failure.redacted && isCreateTagResourceDenial(error) ? " Creating a bucket with tags needs s3:TagResource." : "";
|
|
4816
|
+
const untaggedDenyKind = error instanceof Error ? untaggedExplicitDeny.get(error) : void 0;
|
|
4817
|
+
const untaggedDenyNote = untaggedDenyKind !== void 0 ? ` The untagged retry was refused by an explicit deny${untaggedDenyKind !== null ? ` (${untaggedDenyKind})` : ""}, which retrying cannot clear.` : "";
|
|
4818
|
+
const wrapped = new ProvisioningError(`Failed to ${operation} S3 bucket ${displaySafe(logicalId)}: ${this.maskRaw(failure.summary)}${denyNote}${tagResourceNote}${untaggedDenyNote}`, resourceType, logicalId, physicalId, error instanceof Error ? error : void 0);
|
|
4769
4819
|
return failure.redacted ? markRedactedCause(wrapped) : wrapped;
|
|
4770
4820
|
}
|
|
4771
4821
|
canonicalizeDesiredProperties(resourceType, properties) {
|
|
@@ -4777,12 +4827,21 @@ var S3BucketProvider = class S3BucketProvider {
|
|
|
4777
4827
|
out = canonicalizeBlock(out, "LifecycleConfiguration", effectiveLifecycleConfiguration);
|
|
4778
4828
|
return out;
|
|
4779
4829
|
}
|
|
4780
|
-
async readCurrentState(physicalId,
|
|
4781
|
-
|
|
4830
|
+
async readCurrentState(physicalId, logicalId, _resourceType, _properties, context) {
|
|
4831
|
+
const headAttempts = context?.afterOwnWrite === true ? OWN_WRITE_HEAD_ATTEMPTS : 1;
|
|
4832
|
+
for (let attempt = 1;; attempt++) try {
|
|
4782
4833
|
await this.s3Client.send(new HeadBucketCommand({ Bucket: physicalId }));
|
|
4834
|
+
break;
|
|
4783
4835
|
} catch (err) {
|
|
4784
4836
|
const e = err;
|
|
4785
|
-
if (err instanceof NoSuchBucket || e.name === "NotFound" || e.name === "NoSuchBucket" || e.$metadata?.httpStatusCode === 404)
|
|
4837
|
+
if (err instanceof NoSuchBucket || e.name === "NotFound" || e.name === "NoSuchBucket" || e.$metadata?.httpStatusCode === 404) {
|
|
4838
|
+
if (attempt < headAttempts) {
|
|
4839
|
+
await new Promise((r) => setTimeout(r, OWN_WRITE_HEAD_DELAY_MS));
|
|
4840
|
+
continue;
|
|
4841
|
+
}
|
|
4842
|
+
if (headAttempts > 1) this.logger.debug(safeMsg`HeadBucket still answered 404 after ${String(headAttempts)} attempts right after cdkd's own write; ` + safeMsg`no observed baseline is captured for ${displaySafe(logicalId)}`);
|
|
4843
|
+
return RESOURCE_NOT_FOUND;
|
|
4844
|
+
}
|
|
4786
4845
|
throw err;
|
|
4787
4846
|
}
|
|
4788
4847
|
const [versioning, encryption, ownership, pab, tags, lifecycle, cors, website, logging, notification, replication, objectLock, accelerate, metrics, analytics, intelligentTier, inventory] = await Promise.all([
|
|
@@ -14641,7 +14700,6 @@ var SSMParameterProvider = class SSMParameterProvider {
|
|
|
14641
14700
|
}
|
|
14642
14701
|
async create(logicalId, resourceType, properties, context) {
|
|
14643
14702
|
const mask = maskerOrIdentity(context?.maskSecrets);
|
|
14644
|
-
const warn = (message) => this.logger.warn(mask(message));
|
|
14645
14703
|
const ssmTags = SSMParameterProvider.desiredSsmTags(properties["Tags"], resourceType, logicalId);
|
|
14646
14704
|
const debug = (message) => this.logger.debug(mask(message));
|
|
14647
14705
|
debug(`Creating SSM parameter ${displaySafe(logicalId)}`);
|
|
@@ -14652,7 +14710,6 @@ var SSMParameterProvider = class SSMParameterProvider {
|
|
|
14652
14710
|
const type = properties["Type"] || "String";
|
|
14653
14711
|
const value = properties["Value"];
|
|
14654
14712
|
if (!value) throw new ProvisioningError(`Value is required for SSM parameter ${displaySafe(logicalId)}`, resourceType, logicalId);
|
|
14655
|
-
let leftBehind = false;
|
|
14656
14713
|
try {
|
|
14657
14714
|
const putParams = {
|
|
14658
14715
|
Name: name,
|
|
@@ -14666,30 +14723,8 @@ var SSMParameterProvider = class SSMParameterProvider {
|
|
|
14666
14723
|
const policies = ssmPoliciesParameter(properties["Policies"]);
|
|
14667
14724
|
if (policies !== void 0) putParams.Policies = policies;
|
|
14668
14725
|
if (properties["DataType"]) putParams.DataType = properties["DataType"];
|
|
14726
|
+
if (ssmTags.length > 0) putParams.Tags = ssmTags;
|
|
14669
14727
|
await (await this.getCreateClient()).send(new PutParameterCommand(putParams));
|
|
14670
|
-
leftBehind = true;
|
|
14671
|
-
try {
|
|
14672
|
-
if (ssmTags.length > 0) await this.ssmClient.send(new AddTagsToResourceCommand({
|
|
14673
|
-
ResourceType: "Parameter",
|
|
14674
|
-
ResourceId: name,
|
|
14675
|
-
Tags: ssmTags
|
|
14676
|
-
}));
|
|
14677
|
-
} catch (innerError) {
|
|
14678
|
-
try {
|
|
14679
|
-
await this.ssmClient.send(new DeleteParameterCommand({ Name: name }));
|
|
14680
|
-
leftBehind = false;
|
|
14681
|
-
debug(`Cleaned up partially-created SSM parameter ${displaySafe(logicalId)} (${displaySafe(mask(name))}) after wiring failure`);
|
|
14682
|
-
} catch (cleanupError) {
|
|
14683
|
-
const deleteCommand = renderDisableCommand({
|
|
14684
|
-
before: "aws ssm delete-parameter --name",
|
|
14685
|
-
identifier: name,
|
|
14686
|
-
maskSecrets: mask
|
|
14687
|
-
});
|
|
14688
|
-
const manualStep = deleteCommand ? `Outside a rollback's re-create, the failed deploy's rollback journal records it for \`cdkd rollback --revert-failed\`; otherwise delete it yourself before the next deploy: ${deleteCommand}` : "Outside a rollback's re-create, the failed deploy's rollback journal records it for `cdkd rollback --revert-failed`; otherwise delete it yourself before the next deploy, via the console: the parameter name cannot be reproduced safely on a command line: a command naming the sanitized form would delete a DIFFERENT parameter, and one naming a name that is not inert unquoted could run part of it as shell.";
|
|
14689
|
-
warn(`Failed to clean up partially-created SSM parameter ${displaySafe(logicalId)} (${displaySafe(mask(name))}): ${describeAwsFailure(cleanupError).detail}. ${manualStep}`);
|
|
14690
|
-
}
|
|
14691
|
-
throw markAuxiliaryFailure(innerError, logicalId);
|
|
14692
|
-
}
|
|
14693
14728
|
debug(`Successfully created SSM parameter ${displaySafe(logicalId)}: ${displaySafe(mask(name))}`);
|
|
14694
14729
|
const arn = await this.buildParameterArn(name, mask);
|
|
14695
14730
|
return {
|
|
@@ -14702,9 +14737,7 @@ var SSMParameterProvider = class SSMParameterProvider {
|
|
|
14702
14737
|
};
|
|
14703
14738
|
} catch (error) {
|
|
14704
14739
|
const cause = error instanceof Error ? error : void 0;
|
|
14705
|
-
|
|
14706
|
-
if (leftBehind) markCreatedBeforeFailure(thrown, logicalId, resourceType, name);
|
|
14707
|
-
throw thrown;
|
|
14740
|
+
throw this.wrapMaskedError(mask, error, (text) => new ProvisioningError(`Failed to create SSM parameter ${displaySafe(logicalId)}: ${text}`, resourceType, logicalId, void 0, cause));
|
|
14708
14741
|
}
|
|
14709
14742
|
}
|
|
14710
14743
|
async update(logicalId, physicalId, resourceType, properties, previousProperties, context) {
|
|
@@ -15689,7 +15722,15 @@ const createSubnetLatch = new AmbiguousCreateLatch("ec2:CreateSubnet");
|
|
|
15689
15722
|
const createInternetGatewayLatch = new AmbiguousCreateLatch("ec2:CreateInternetGateway");
|
|
15690
15723
|
const allocateAddressLatch = new AmbiguousCreateLatch("ec2:AllocateAddress");
|
|
15691
15724
|
const ec2IdsCreatedByThisProcess = new RecentIdSet();
|
|
15692
|
-
const
|
|
15725
|
+
const mayBeLostCreate = (tags, sent) => tags === void 0 || tags.length === 0 || sent.length > 0 && tagListsMatch(tags, sent);
|
|
15726
|
+
const lostCreateNoun = (what, sent, adjective) => sent.length === 0 ? `${adjective !== void 0 ? `${adjective}, ` : ""}untagged ${what}` : `${adjective !== void 0 ? `${adjective} ` : ""}${what} with no tags or exactly the template's tags`;
|
|
15727
|
+
function isCreateTagsDenial(error) {
|
|
15728
|
+
return isNamedError(error, CREATE_TAGS_DENIAL_NAMES) && describeAwsFailure(error).detail.includes("ec2:CreateTags");
|
|
15729
|
+
}
|
|
15730
|
+
const CREATE_TAGS_DENIAL_NAMES = /* @__PURE__ */ new Set(["UnauthorizedOperation"]);
|
|
15731
|
+
const IDEMPOTENT_MISMATCH_NAMES = /* @__PURE__ */ new Set(["IdempotentParameterMismatch"]);
|
|
15732
|
+
const OWN_WRITE_READ_ATTEMPTS = 5;
|
|
15733
|
+
const OWN_WRITE_READ_DELAY_MS = 500;
|
|
15693
15734
|
const ORPHAN_LIST_PAGE_SIZE$2 = 1e3;
|
|
15694
15735
|
var EC2Provider = class {
|
|
15695
15736
|
ec2Client;
|
|
@@ -15844,14 +15885,14 @@ var EC2Provider = class {
|
|
|
15844
15885
|
inspect: (id) => lookup.inspect(aws, id, regionArg)
|
|
15845
15886
|
});
|
|
15846
15887
|
}
|
|
15847
|
-
async reportPossibleOrphanVpcs(logicalId, cidrBlock, window, context) {
|
|
15888
|
+
async reportPossibleOrphanVpcs(logicalId, cidrBlock, sent, window, context) {
|
|
15848
15889
|
const log = createMaskedLogSinks(this.logger, context?.maskSecrets);
|
|
15849
15890
|
const wanted = canonicalizeIpv4Cidr(cidrBlock) ?? cidrBlock;
|
|
15850
15891
|
await this.reportPossibleEc2Orphans(logicalId, window, log, {
|
|
15851
15892
|
action: "CreateVpc",
|
|
15852
15893
|
listAction: "DescribeVpcs",
|
|
15853
15894
|
subject: `a VPC with CIDR ${log.value(cidrBlock)}`,
|
|
15854
|
-
noun: "
|
|
15895
|
+
noun: lostCreateNoun("VPC(s)", sent),
|
|
15855
15896
|
list: () => collectOrphanIds(async (token) => {
|
|
15856
15897
|
const page = await this.ec2Client.send(new DescribeVpcsCommand({
|
|
15857
15898
|
MaxResults: ORPHAN_LIST_PAGE_SIZE$2,
|
|
@@ -15861,18 +15902,18 @@ var EC2Provider = class {
|
|
|
15861
15902
|
items: page.Vpcs ?? [],
|
|
15862
15903
|
next: page.NextToken
|
|
15863
15904
|
};
|
|
15864
|
-
}, (vpc) => vpc.VpcId !== void 0 && vpc.IsDefault !== true &&
|
|
15905
|
+
}, (vpc) => vpc.VpcId !== void 0 && vpc.IsDefault !== true && mayBeLostCreate(vpc.Tags, sent) && vpc.CidrBlock !== void 0 && (canonicalizeIpv4Cidr(vpc.CidrBlock) ?? vpc.CidrBlock) === wanted && !ec2IdsCreatedByThisProcess.has(vpc.VpcId) ? vpc.VpcId : void 0),
|
|
15865
15906
|
inspect: (aws, id, regionArg) => aws`aws ec2 describe-vpcs --vpc-ids ${id}${regionArg}`.render()
|
|
15866
15907
|
});
|
|
15867
15908
|
}
|
|
15868
|
-
async reportPossibleOrphanSubnets(logicalId, vpcId, cidrBlock, window, context) {
|
|
15909
|
+
async reportPossibleOrphanSubnets(logicalId, vpcId, cidrBlock, sent, window, context) {
|
|
15869
15910
|
const log = createMaskedLogSinks(this.logger, context?.maskSecrets);
|
|
15870
15911
|
const wanted = canonicalizeIpv4Cidr(cidrBlock) ?? cidrBlock;
|
|
15871
15912
|
await this.reportPossibleEc2Orphans(logicalId, window, log, {
|
|
15872
15913
|
action: "CreateSubnet",
|
|
15873
15914
|
listAction: "DescribeSubnets",
|
|
15874
15915
|
subject: `a subnet with CIDR ${log.value(cidrBlock)} in VPC ${log.value(vpcId)}`,
|
|
15875
|
-
noun: "
|
|
15916
|
+
noun: lostCreateNoun("subnet(s)", sent),
|
|
15876
15917
|
afterward: "Creating it again, which fails with InvalidSubnet.Conflict while that subnet exists.",
|
|
15877
15918
|
list: () => collectOrphanIds(async (token) => {
|
|
15878
15919
|
const page = await this.ec2Client.send(new DescribeSubnetsCommand({
|
|
@@ -15887,17 +15928,17 @@ var EC2Provider = class {
|
|
|
15887
15928
|
items: page.Subnets ?? [],
|
|
15888
15929
|
next: page.NextToken
|
|
15889
15930
|
};
|
|
15890
|
-
}, (subnet) => subnet.SubnetId !== void 0 &&
|
|
15931
|
+
}, (subnet) => subnet.SubnetId !== void 0 && mayBeLostCreate(subnet.Tags, sent) && subnet.CidrBlock !== void 0 && (canonicalizeIpv4Cidr(subnet.CidrBlock) ?? subnet.CidrBlock) === wanted && !ec2IdsCreatedByThisProcess.has(subnet.SubnetId) ? subnet.SubnetId : void 0),
|
|
15891
15932
|
inspect: (aws, id, regionArg) => aws`aws ec2 describe-subnets --subnet-ids ${id}${regionArg}`.render()
|
|
15892
15933
|
});
|
|
15893
15934
|
}
|
|
15894
|
-
async reportPossibleOrphanInternetGateways(logicalId, window, context) {
|
|
15935
|
+
async reportPossibleOrphanInternetGateways(logicalId, sent, window, context) {
|
|
15895
15936
|
const log = createMaskedLogSinks(this.logger, context?.maskSecrets);
|
|
15896
15937
|
await this.reportPossibleEc2Orphans(logicalId, window, log, {
|
|
15897
15938
|
action: "CreateInternetGateway",
|
|
15898
15939
|
listAction: "DescribeInternetGateways",
|
|
15899
15940
|
subject: "an internet gateway",
|
|
15900
|
-
noun: "
|
|
15941
|
+
noun: lostCreateNoun("internet gateway(s)", sent, "detached"),
|
|
15901
15942
|
list: () => collectOrphanIds(async (token) => {
|
|
15902
15943
|
const page = await this.ec2Client.send(new DescribeInternetGatewaysCommand({
|
|
15903
15944
|
MaxResults: ORPHAN_LIST_PAGE_SIZE$2,
|
|
@@ -15907,23 +15948,23 @@ var EC2Provider = class {
|
|
|
15907
15948
|
items: page.InternetGateways ?? [],
|
|
15908
15949
|
next: page.NextToken
|
|
15909
15950
|
};
|
|
15910
|
-
}, (igw) => igw.InternetGatewayId !== void 0 && (igw.Attachments ?? []).length === 0 &&
|
|
15951
|
+
}, (igw) => igw.InternetGatewayId !== void 0 && (igw.Attachments ?? []).length === 0 && mayBeLostCreate(igw.Tags, sent) && !ec2IdsCreatedByThisProcess.has(igw.InternetGatewayId) ? igw.InternetGatewayId : void 0),
|
|
15911
15952
|
inspect: (aws, id, regionArg) => aws`aws ec2 describe-internet-gateways --internet-gateway-ids ${id}${regionArg}`.render()
|
|
15912
15953
|
});
|
|
15913
15954
|
}
|
|
15914
|
-
async reportPossibleOrphanAddresses(logicalId, input, window, context) {
|
|
15955
|
+
async reportPossibleOrphanAddresses(logicalId, input, sent, window, context) {
|
|
15915
15956
|
const log = createMaskedLogSinks(this.logger, context?.maskSecrets);
|
|
15916
15957
|
await this.reportPossibleEc2Orphans(logicalId, window, log, {
|
|
15917
15958
|
action: "AllocateAddress",
|
|
15918
15959
|
listAction: "DescribeAddresses",
|
|
15919
15960
|
subject: `an Elastic IP address (domain ${log.value(input.Domain ?? "vpc")})`,
|
|
15920
|
-
noun: "
|
|
15961
|
+
noun: lostCreateNoun("Elastic IP address(es)", sent, "unassociated"),
|
|
15921
15962
|
list: async () => {
|
|
15922
15963
|
const response = await this.ec2Client.send(new DescribeAddressesCommand({}));
|
|
15923
15964
|
const ids = [];
|
|
15924
15965
|
for (const address of response.Addresses ?? []) {
|
|
15925
15966
|
const id = address.AllocationId;
|
|
15926
|
-
if (id === void 0 || (address.Domain ?? "vpc") !== (input.Domain ?? "vpc") || address.AssociationId !== void 0 || !
|
|
15967
|
+
if (id === void 0 || (address.Domain ?? "vpc") !== (input.Domain ?? "vpc") || address.AssociationId !== void 0 || !mayBeLostCreate(address.Tags, sent) || input.NetworkBorderGroup !== void 0 && address.NetworkBorderGroup !== input.NetworkBorderGroup || input.PublicIpv4Pool !== void 0 && address.PublicIpv4Pool !== input.PublicIpv4Pool || ec2IdsCreatedByThisProcess.has(id)) continue;
|
|
15927
15968
|
ids.push(id);
|
|
15928
15969
|
}
|
|
15929
15970
|
return {
|
|
@@ -16139,14 +16180,16 @@ var EC2Provider = class {
|
|
|
16139
16180
|
try {
|
|
16140
16181
|
const createClient = await this.getCreateClient();
|
|
16141
16182
|
const orphanWindow = createVpcLatch.take(logicalId);
|
|
16142
|
-
if (orphanWindow !== void 0) await this.reportPossibleOrphanVpcs(logicalId, cidrBlock, orphanWindow, context);
|
|
16183
|
+
if (orphanWindow !== void 0) await this.reportPossibleOrphanVpcs(logicalId, cidrBlock, desiredTags, orphanWindow, context);
|
|
16143
16184
|
const attemptStartMs = Date.now();
|
|
16144
16185
|
let response;
|
|
16186
|
+
let tagsApplied;
|
|
16145
16187
|
try {
|
|
16146
|
-
response = await createClient.send(new CreateVpcCommand({
|
|
16188
|
+
({response, tagsApplied} = await this.sendTaggedCreate(logicalId, "vpc", desiredTags, (TagSpecifications) => createClient.send(new CreateVpcCommand({
|
|
16147
16189
|
CidrBlock: cidrBlock,
|
|
16148
|
-
InstanceTenancy: properties["InstanceTenancy"] ?? void 0
|
|
16149
|
-
|
|
16190
|
+
InstanceTenancy: properties["InstanceTenancy"] ?? void 0,
|
|
16191
|
+
...TagSpecifications && { TagSpecifications }
|
|
16192
|
+
}))));
|
|
16150
16193
|
} catch (error) {
|
|
16151
16194
|
createVpcLatch.noteFailure(logicalId, error, attemptStartMs, orphanWindow);
|
|
16152
16195
|
throw error;
|
|
@@ -16154,7 +16197,7 @@ var EC2Provider = class {
|
|
|
16154
16197
|
const vpcId = response.Vpc.VpcId;
|
|
16155
16198
|
ec2IdsCreatedByThisProcess.add(vpcId);
|
|
16156
16199
|
const vpcReplayWindow = replayedSendWindow(response, attemptStartMs);
|
|
16157
|
-
if (vpcReplayWindow !== void 0) await this.reportPossibleOrphanVpcs(logicalId, cidrBlock, vpcReplayWindow, context);
|
|
16200
|
+
if (vpcReplayWindow !== void 0) await this.reportPossibleOrphanVpcs(logicalId, cidrBlock, desiredTags, vpcReplayWindow, context);
|
|
16158
16201
|
let defaultSgId;
|
|
16159
16202
|
try {
|
|
16160
16203
|
if (properties["EnableDnsHostnames"] === true || properties["EnableDnsHostnames"] === "true") await this.ec2Client.send(new ModifyVpcAttributeCommand({
|
|
@@ -16165,7 +16208,7 @@ var EC2Provider = class {
|
|
|
16165
16208
|
VpcId: vpcId,
|
|
16166
16209
|
EnableDnsSupport: { Value: false }
|
|
16167
16210
|
}));
|
|
16168
|
-
await this.applyTags(vpcId, desiredTags, logicalId);
|
|
16211
|
+
if (!tagsApplied) await this.applyTags(vpcId, desiredTags, logicalId);
|
|
16169
16212
|
await this.ec2Client.send(new DescribeVpcsCommand({ VpcIds: [vpcId] }));
|
|
16170
16213
|
try {
|
|
16171
16214
|
defaultSgId = (await this.ec2Client.send(new DescribeSecurityGroupsCommand({ Filters: [{
|
|
@@ -16309,15 +16352,17 @@ var EC2Provider = class {
|
|
|
16309
16352
|
try {
|
|
16310
16353
|
const createClient = await this.getCreateClient();
|
|
16311
16354
|
const orphanWindow = createSubnetLatch.take(logicalId);
|
|
16312
|
-
if (orphanWindow !== void 0) await this.reportPossibleOrphanSubnets(logicalId, vpcId, cidrBlock, orphanWindow, context);
|
|
16355
|
+
if (orphanWindow !== void 0) await this.reportPossibleOrphanSubnets(logicalId, vpcId, cidrBlock, desiredTags, orphanWindow, context);
|
|
16313
16356
|
const attemptStartMs = Date.now();
|
|
16314
16357
|
let response;
|
|
16358
|
+
let tagsApplied;
|
|
16315
16359
|
try {
|
|
16316
|
-
response = await createClient.send(new CreateSubnetCommand({
|
|
16360
|
+
({response, tagsApplied} = await this.sendTaggedCreate(logicalId, "subnet", desiredTags, (TagSpecifications) => createClient.send(new CreateSubnetCommand({
|
|
16317
16361
|
VpcId: vpcId,
|
|
16318
16362
|
CidrBlock: cidrBlock,
|
|
16319
|
-
AvailabilityZone: properties["AvailabilityZone"] ?? void 0
|
|
16320
|
-
|
|
16363
|
+
AvailabilityZone: properties["AvailabilityZone"] ?? void 0,
|
|
16364
|
+
...TagSpecifications && { TagSpecifications }
|
|
16365
|
+
}))));
|
|
16321
16366
|
} catch (error) {
|
|
16322
16367
|
createSubnetLatch.noteFailure(logicalId, error, attemptStartMs, orphanWindow);
|
|
16323
16368
|
throw error;
|
|
@@ -16325,10 +16370,10 @@ var EC2Provider = class {
|
|
|
16325
16370
|
const subnetId = response.Subnet.SubnetId;
|
|
16326
16371
|
ec2IdsCreatedByThisProcess.add(subnetId);
|
|
16327
16372
|
const subnetReplayWindow = replayedSendWindow(response, attemptStartMs);
|
|
16328
|
-
if (subnetReplayWindow !== void 0) await this.reportPossibleOrphanSubnets(logicalId, vpcId, cidrBlock, subnetReplayWindow, context);
|
|
16373
|
+
if (subnetReplayWindow !== void 0) await this.reportPossibleOrphanSubnets(logicalId, vpcId, cidrBlock, desiredTags, subnetReplayWindow, context);
|
|
16329
16374
|
const availabilityZone = response.Subnet.AvailabilityZone;
|
|
16330
16375
|
try {
|
|
16331
|
-
await this.applyTags(subnetId, desiredTags, logicalId);
|
|
16376
|
+
if (!tagsApplied) await this.applyTags(subnetId, desiredTags, logicalId);
|
|
16332
16377
|
const mapPublicIp = properties["MapPublicIpOnLaunch"];
|
|
16333
16378
|
if (mapPublicIp === true || mapPublicIp === "true") {
|
|
16334
16379
|
await this.ec2Client.send(new ModifySubnetAttributeCommand({
|
|
@@ -16479,11 +16524,12 @@ var EC2Provider = class {
|
|
|
16479
16524
|
try {
|
|
16480
16525
|
const createClient = await this.getCreateClient();
|
|
16481
16526
|
const orphanWindow = createInternetGatewayLatch.take(logicalId);
|
|
16482
|
-
if (orphanWindow !== void 0) await this.reportPossibleOrphanInternetGateways(logicalId, orphanWindow, context);
|
|
16527
|
+
if (orphanWindow !== void 0) await this.reportPossibleOrphanInternetGateways(logicalId, desiredTags, orphanWindow, context);
|
|
16483
16528
|
const attemptStartMs = Date.now();
|
|
16484
16529
|
let response;
|
|
16530
|
+
let tagsApplied;
|
|
16485
16531
|
try {
|
|
16486
|
-
response = await createClient.send(new CreateInternetGatewayCommand({}));
|
|
16532
|
+
({response, tagsApplied} = await this.sendTaggedCreate(logicalId, "internet-gateway", desiredTags, (TagSpecifications) => createClient.send(new CreateInternetGatewayCommand(TagSpecifications ? { TagSpecifications } : {}))));
|
|
16487
16533
|
} catch (error) {
|
|
16488
16534
|
createInternetGatewayLatch.noteFailure(logicalId, error, attemptStartMs, orphanWindow);
|
|
16489
16535
|
throw error;
|
|
@@ -16491,8 +16537,8 @@ var EC2Provider = class {
|
|
|
16491
16537
|
const igwId = response.InternetGateway.InternetGatewayId;
|
|
16492
16538
|
ec2IdsCreatedByThisProcess.add(igwId);
|
|
16493
16539
|
const igwReplayWindow = replayedSendWindow(response, attemptStartMs);
|
|
16494
|
-
if (igwReplayWindow !== void 0) await this.reportPossibleOrphanInternetGateways(logicalId, igwReplayWindow, context);
|
|
16495
|
-
await this.applyTags(igwId, desiredTags, logicalId);
|
|
16540
|
+
if (igwReplayWindow !== void 0) await this.reportPossibleOrphanInternetGateways(logicalId, desiredTags, igwReplayWindow, context);
|
|
16541
|
+
if (!tagsApplied) await this.applyTags(igwId, desiredTags, logicalId);
|
|
16496
16542
|
this.logger.debug(`Successfully created InternetGateway ${logicalId}: ${igwId}`);
|
|
16497
16543
|
return {
|
|
16498
16544
|
physicalId: igwId,
|
|
@@ -16558,11 +16604,15 @@ var EC2Provider = class {
|
|
|
16558
16604
|
};
|
|
16559
16605
|
const createClient = await this.getCreateClient();
|
|
16560
16606
|
const orphanWindow = allocateAddressLatch.take(logicalId);
|
|
16561
|
-
if (orphanWindow !== void 0) await this.reportPossibleOrphanAddresses(logicalId, input, orphanWindow, context);
|
|
16607
|
+
if (orphanWindow !== void 0) await this.reportPossibleOrphanAddresses(logicalId, input, desiredTags, orphanWindow, context);
|
|
16562
16608
|
const attemptStartMs = Date.now();
|
|
16563
16609
|
let response;
|
|
16610
|
+
let tagsApplied;
|
|
16564
16611
|
try {
|
|
16565
|
-
response = await createClient.send(new AllocateAddressCommand(
|
|
16612
|
+
({response, tagsApplied} = await this.sendTaggedCreate(logicalId, "elastic-ip", desiredTags, (TagSpecifications) => createClient.send(new AllocateAddressCommand(TagSpecifications ? {
|
|
16613
|
+
...input,
|
|
16614
|
+
TagSpecifications
|
|
16615
|
+
} : input))));
|
|
16566
16616
|
} catch (error) {
|
|
16567
16617
|
allocateAddressLatch.noteFailure(logicalId, error, attemptStartMs, orphanWindow);
|
|
16568
16618
|
throw error;
|
|
@@ -16578,8 +16628,8 @@ var EC2Provider = class {
|
|
|
16578
16628
|
}
|
|
16579
16629
|
ec2IdsCreatedByThisProcess.add(allocationId);
|
|
16580
16630
|
const eipReplayWindow = replayedSendWindow(response, attemptStartMs);
|
|
16581
|
-
if (eipReplayWindow !== void 0) await this.reportPossibleOrphanAddresses(logicalId, input, eipReplayWindow, context);
|
|
16582
|
-
await this.applyTags(allocationId, desiredTags, logicalId);
|
|
16631
|
+
if (eipReplayWindow !== void 0) await this.reportPossibleOrphanAddresses(logicalId, input, desiredTags, eipReplayWindow, context);
|
|
16632
|
+
if (!tagsApplied) await this.applyTags(allocationId, desiredTags, logicalId);
|
|
16583
16633
|
const instanceId = properties["InstanceId"];
|
|
16584
16634
|
if (instanceId) {
|
|
16585
16635
|
if (process.env["CDKD_NO_WAIT"] === "true") this.logger.warn(`EIP ${logicalId} (${allocationId}) was NOT associated with ${displayIdent(instanceId)}: --no-wait skips the instance running-state wait, and AssociateAddress rejects an instance that is not yet running. Verify and associate once the instance is running: ${pasteableAwsCommand(context?.maskSecrets)`aws ec2 describe-instances --instance-ids ${instanceId} --query 'Reservations[].Instances[].State.Name' && aws ec2 associate-address --allocation-id ${allocationId} --instance-id ${instanceId}`.render()}`);
|
|
@@ -16767,7 +16817,8 @@ var EC2Provider = class {
|
|
|
16767
16817
|
});
|
|
16768
16818
|
let createdId;
|
|
16769
16819
|
try {
|
|
16770
|
-
const
|
|
16820
|
+
const { response, tagsApplied } = await this.sendTaggedCreate(logicalId, "natgateway", desiredTags, (TagSpecifications) => this.ec2Client.send(new CreateNatGatewayCommand({
|
|
16821
|
+
...TagSpecifications && { TagSpecifications },
|
|
16771
16822
|
ClientToken: natGatewayToken.value,
|
|
16772
16823
|
SubnetId: subnetId,
|
|
16773
16824
|
AllocationId: properties["AllocationId"],
|
|
@@ -16776,9 +16827,10 @@ var EC2Provider = class {
|
|
|
16776
16827
|
SecondaryAllocationIds: properties["SecondaryAllocationIds"],
|
|
16777
16828
|
SecondaryPrivateIpAddresses: properties["SecondaryPrivateIpAddresses"],
|
|
16778
16829
|
SecondaryPrivateIpAddressCount: properties["SecondaryPrivateIpAddressCount"]
|
|
16779
|
-
})))
|
|
16830
|
+
})));
|
|
16831
|
+
const natGatewayId = response.NatGateway.NatGatewayId;
|
|
16780
16832
|
createdId = natGatewayId;
|
|
16781
|
-
await this.applyTags(natGatewayId, desiredTags, logicalId);
|
|
16833
|
+
if (!tagsApplied) await this.applyTags(natGatewayId, desiredTags, logicalId);
|
|
16782
16834
|
if (process.env["CDKD_NO_WAIT"] !== "true") {
|
|
16783
16835
|
this.logger.debug(`Waiting for NatGateway ${natGatewayId} to reach available state...`);
|
|
16784
16836
|
await waitUntilNatGatewayAvailable({
|
|
@@ -16843,11 +16895,13 @@ var EC2Provider = class {
|
|
|
16843
16895
|
logicalId
|
|
16844
16896
|
});
|
|
16845
16897
|
try {
|
|
16846
|
-
const
|
|
16898
|
+
const { response, tagsApplied } = await this.sendTaggedCreate(logicalId, "route-table", desiredTags, (TagSpecifications) => this.ec2Client.send(new CreateRouteTableCommand({
|
|
16847
16899
|
VpcId: vpcId,
|
|
16848
|
-
ClientToken: routeTableToken.value
|
|
16849
|
-
|
|
16850
|
-
|
|
16900
|
+
ClientToken: routeTableToken.value,
|
|
16901
|
+
...TagSpecifications && { TagSpecifications }
|
|
16902
|
+
})));
|
|
16903
|
+
const routeTableId = response.RouteTable.RouteTableId;
|
|
16904
|
+
if (!tagsApplied) await this.applyTags(routeTableId, desiredTags, logicalId);
|
|
16851
16905
|
this.logger.debug(`Successfully created RouteTable ${logicalId}: ${routeTableId}`);
|
|
16852
16906
|
routeTableToken.release();
|
|
16853
16907
|
return {
|
|
@@ -17028,11 +17082,14 @@ var EC2Provider = class {
|
|
|
17028
17082
|
if (!groupDescription) throw new ProvisioningError(`GroupDescription is required for SecurityGroup ${logicalId}`, resourceType, logicalId);
|
|
17029
17083
|
let leftBehindId;
|
|
17030
17084
|
try {
|
|
17031
|
-
const
|
|
17085
|
+
const createClient = await this.getCreateClient();
|
|
17086
|
+
const { response, tagsApplied } = await this.sendTaggedCreate(logicalId, "security-group", desiredTags, (TagSpecifications) => createClient.send(new CreateSecurityGroupCommand({
|
|
17032
17087
|
GroupName: properties["GroupName"] ?? logicalId,
|
|
17033
17088
|
Description: groupDescription,
|
|
17034
|
-
VpcId: properties["VpcId"] ?? void 0
|
|
17035
|
-
|
|
17089
|
+
VpcId: properties["VpcId"] ?? void 0,
|
|
17090
|
+
...TagSpecifications && { TagSpecifications }
|
|
17091
|
+
})));
|
|
17092
|
+
const groupId = response.GroupId;
|
|
17036
17093
|
try {
|
|
17037
17094
|
const ingressRules = properties["SecurityGroupIngress"];
|
|
17038
17095
|
const egressRules = properties["SecurityGroupEgress"];
|
|
@@ -17041,7 +17098,7 @@ var EC2Provider = class {
|
|
|
17041
17098
|
firstRejection ??= { error };
|
|
17042
17099
|
});
|
|
17043
17100
|
await Promise.all([
|
|
17044
|
-
recordRejection(this.applyTags(groupId, desiredTags, logicalId)),
|
|
17101
|
+
recordRejection(this.applyTags(groupId, tagsApplied ? [] : desiredTags, logicalId)),
|
|
17045
17102
|
recordRejection(this.authorizeInlineIngress(groupId, ingressRules)),
|
|
17046
17103
|
recordRejection(this.applyInlineEgress(groupId, egressRules))
|
|
17047
17104
|
]);
|
|
@@ -17563,7 +17620,8 @@ var EC2Provider = class {
|
|
|
17563
17620
|
scope: "RunInstances",
|
|
17564
17621
|
logicalId
|
|
17565
17622
|
});
|
|
17566
|
-
const
|
|
17623
|
+
const { response, tagsApplied } = await this.sendTaggedCreate(logicalId, "instance", desiredTags, (TagSpecifications) => this.ec2Client.send(new RunInstancesCommand({
|
|
17624
|
+
...TagSpecifications && { TagSpecifications },
|
|
17567
17625
|
ClientToken: runInstancesToken.value,
|
|
17568
17626
|
ImageId: imageId,
|
|
17569
17627
|
InstanceType: instanceType,
|
|
@@ -17586,11 +17644,12 @@ var EC2Provider = class {
|
|
|
17586
17644
|
MetadataOptions: this.buildMetadataOptions(properties),
|
|
17587
17645
|
CreditSpecification: this.buildCreditSpecification(properties),
|
|
17588
17646
|
Placement: this.buildPlacement(properties)
|
|
17589
|
-
})))
|
|
17647
|
+
})));
|
|
17648
|
+
const instance = response.Instances?.[0];
|
|
17590
17649
|
if (!instance?.InstanceId) throw new Error("No instance ID returned from RunInstances");
|
|
17591
17650
|
const instanceId = instance.InstanceId;
|
|
17592
17651
|
try {
|
|
17593
|
-
await this.applyTags(instanceId, desiredTags, logicalId);
|
|
17652
|
+
if (!tagsApplied) await this.applyTags(instanceId, desiredTags, logicalId);
|
|
17594
17653
|
if (process.env["CDKD_NO_WAIT"] !== "true") {
|
|
17595
17654
|
this.logger.debug(`Waiting for instance ${instanceId} to be running...`);
|
|
17596
17655
|
await waitUntilInstanceRunning({
|
|
@@ -18021,11 +18080,13 @@ var EC2Provider = class {
|
|
|
18021
18080
|
logicalId
|
|
18022
18081
|
});
|
|
18023
18082
|
try {
|
|
18024
|
-
const
|
|
18083
|
+
const { response, tagsApplied } = await this.sendTaggedCreate(logicalId, "network-acl", desiredTags, (TagSpecifications) => this.ec2Client.send(new CreateNetworkAclCommand({
|
|
18025
18084
|
VpcId: vpcId,
|
|
18026
|
-
ClientToken: networkAclToken.value
|
|
18027
|
-
|
|
18028
|
-
|
|
18085
|
+
ClientToken: networkAclToken.value,
|
|
18086
|
+
...TagSpecifications && { TagSpecifications }
|
|
18087
|
+
})));
|
|
18088
|
+
const networkAclId = response.NetworkAcl.NetworkAclId;
|
|
18089
|
+
if (!tagsApplied) await this.applyTags(networkAclId, desiredTags, logicalId);
|
|
18029
18090
|
this.logger.debug(`Successfully created NetworkAcl ${logicalId}: ${networkAclId}`);
|
|
18030
18091
|
networkAclToken.release();
|
|
18031
18092
|
return {
|
|
@@ -18175,6 +18236,45 @@ var EC2Provider = class {
|
|
|
18175
18236
|
throw new ProvisioningError(`Failed to create SubnetNetworkAclAssociation ${logicalId}: ${error instanceof Error ? error.message : String(error)}`, resourceType, logicalId, void 0, cause);
|
|
18176
18237
|
}
|
|
18177
18238
|
}
|
|
18239
|
+
async sendTaggedCreate(logicalId, tagResourceType, tags, send) {
|
|
18240
|
+
if (tags.length === 0) return {
|
|
18241
|
+
response: await send(void 0),
|
|
18242
|
+
tagsApplied: false
|
|
18243
|
+
};
|
|
18244
|
+
const tagSpecifications = [{
|
|
18245
|
+
ResourceType: tagResourceType,
|
|
18246
|
+
Tags: tags.map((t) => ({
|
|
18247
|
+
Key: t.Key,
|
|
18248
|
+
Value: t.Value
|
|
18249
|
+
}))
|
|
18250
|
+
}];
|
|
18251
|
+
try {
|
|
18252
|
+
return {
|
|
18253
|
+
response: await send(tagSpecifications),
|
|
18254
|
+
tagsApplied: true
|
|
18255
|
+
};
|
|
18256
|
+
} catch (taggedError) {
|
|
18257
|
+
const tagsDenied = isCreateTagsDenial(taggedError);
|
|
18258
|
+
if (!tagsDenied && !isNamedError(taggedError, IDEMPOTENT_MISMATCH_NAMES)) throw taggedError;
|
|
18259
|
+
this.logger.debug(safeMsg`Create of ${logicalId} with tags was ${tagsDenied ? "denied ec2:CreateTags" : "refused for a client token an untagged create already used"}; ` + `retrying without tags and applying them with CreateTags`);
|
|
18260
|
+
try {
|
|
18261
|
+
return {
|
|
18262
|
+
response: await send(void 0),
|
|
18263
|
+
tagsApplied: false
|
|
18264
|
+
};
|
|
18265
|
+
} catch (untaggedError) {
|
|
18266
|
+
if (!tagsDenied || !(taggedError instanceof Error) || !isNamedError(untaggedError, CREATE_TAGS_DENIAL_NAMES)) throw untaggedError;
|
|
18267
|
+
this.logger.debug(safeMsg`Create of ${logicalId} without tags was denied too; reporting the ec2:CreateTags denial`);
|
|
18268
|
+
const untaggedDetail = describeAwsFailure(untaggedError).detail;
|
|
18269
|
+
this.logger.debug(safeMsg`Create of ${logicalId} without tags was refused: ${untaggedDetail}`);
|
|
18270
|
+
const explicit = isExplicitDenyError(untaggedDetail);
|
|
18271
|
+
const kind = explicit ? explicitDenyPolicyKind(untaggedDetail) : void 0;
|
|
18272
|
+
taggedError.message = `${taggedError.message} The create without tags was refused too (UnauthorizedOperation)${explicit ? `; explicit deny${kind !== void 0 ? ` (${kind})` : ""}` : ""}.`;
|
|
18273
|
+
if (explicit) markNonRetryable(taggedError);
|
|
18274
|
+
throw taggedError;
|
|
18275
|
+
}
|
|
18276
|
+
}
|
|
18277
|
+
}
|
|
18178
18278
|
async applyTags(resourceId, tags, logicalId) {
|
|
18179
18279
|
if (tags.length > 0) try {
|
|
18180
18280
|
await this.ec2Client.send(new CreateTagsCommand({
|
|
@@ -18267,6 +18367,14 @@ var EC2Provider = class {
|
|
|
18267
18367
|
return null;
|
|
18268
18368
|
}
|
|
18269
18369
|
async readCurrentState(physicalId, logicalId, resourceType, properties, context) {
|
|
18370
|
+
const attempts = context?.afterOwnWrite === true ? OWN_WRITE_READ_ATTEMPTS : 1;
|
|
18371
|
+
for (let attempt = 1;; attempt++) {
|
|
18372
|
+
const read = await this.readCurrentStateOnce(physicalId, logicalId, resourceType, properties, context);
|
|
18373
|
+
if (read !== RESOURCE_NOT_FOUND || attempt >= attempts) return read;
|
|
18374
|
+
await new Promise((r) => setTimeout(r, OWN_WRITE_READ_DELAY_MS));
|
|
18375
|
+
}
|
|
18376
|
+
}
|
|
18377
|
+
async readCurrentStateOnce(physicalId, logicalId, resourceType, properties, context) {
|
|
18270
18378
|
try {
|
|
18271
18379
|
switch (resourceType) {
|
|
18272
18380
|
case "AWS::EC2::VPC": return await this.readVpcCurrentState(physicalId);
|
|
@@ -29821,6 +29929,8 @@ function customAcrLevels(acr) {
|
|
|
29821
29929
|
}));
|
|
29822
29930
|
return Object.keys(custom).length > 0 ? custom : void 0;
|
|
29823
29931
|
}
|
|
29932
|
+
const EMAIL_RESET_CLAUSE = "reset to Cognito's default sender (EmailSendingAccount COGNITO_DEFAULT), dropping its SES SourceArn, and a redeploy will not restore it. Put the SES settings back with an UpdateUserPool that also carries the pool's other settings, since that call resets what it omits.";
|
|
29933
|
+
const EMAIL_RESET_BEFORE_DELETE_CLAUSE = "reset to Cognito's default sender (EmailSendingAccount COGNITO_DEFAULT), dropping its SES SourceArn, which stays that way if the delete fails.";
|
|
29824
29934
|
const sentWithoutEmail = /* @__PURE__ */ new WeakSet();
|
|
29825
29935
|
const createUserPoolLatch = new AmbiguousCreateLatch("CreateUserPool");
|
|
29826
29936
|
const userPoolsCreatedByThisProcess = new RecentIdSet();
|
|
@@ -30031,6 +30141,7 @@ var CognitoUserPoolProvider = class {
|
|
|
30031
30141
|
logger = getLogger().child("CognitoUserPoolProvider");
|
|
30032
30142
|
protectionFlips = new ProtectionFlipRegistry();
|
|
30033
30143
|
preFlipPools = /* @__PURE__ */ new WeakMap();
|
|
30144
|
+
emailOmittedFlips = /* @__PURE__ */ new WeakMap();
|
|
30034
30145
|
handledProperties = /* @__PURE__ */ new Map([["AWS::Cognito::UserPool", /* @__PURE__ */ new Set([
|
|
30035
30146
|
"UserPoolName",
|
|
30036
30147
|
"AutoVerifiedAttributes",
|
|
@@ -30487,10 +30598,12 @@ var CognitoUserPoolProvider = class {
|
|
|
30487
30598
|
if (bareFlip && pool.DeletionProtection !== "ACTIVE") bareFlip.ambiguous = false;
|
|
30488
30599
|
const resetConfirmed = bareFlip !== void 0 && !bareFlip.ambiguous;
|
|
30489
30600
|
if (bareFlip) this.reportSettingsResetByBareFlip(physicalId, bareFlip.pool, reportKind(bareFlip));
|
|
30601
|
+
if (flipRecord && this.emailOmittedFlips.has(flipRecord) && !echoesDeveloperEmail(pool) && !(bareFlip && echoesDeveloperEmail(bareFlip.pool))) this.logger.error(safeMsg`Cognito User Pool ${physicalId} is LIVE with its SES email configuration reset: ` + safeMsg`--remove-protection turned DeletionProtection off with an UpdateUserPool that left ` + safeMsg`out its DEVELOPER EmailConfiguration (sending it was refused), and the delete then ` + safeMsg`failed. The pool's email configuration was ${EMAIL_RESET_CLAUSE}`);
|
|
30490
30602
|
const bareLicensed = resetConfirmed && bareFlip.echoedSince !== true;
|
|
30491
30603
|
const readOn = pool.DeletionProtection === "ACTIVE";
|
|
30492
30604
|
try {
|
|
30493
|
-
|
|
30605
|
+
const emailAlreadyReset = flipRecord !== void 0 && this.emailOmittedFlips.get(flipRecord) === "definite";
|
|
30606
|
+
await this.sendEchoedDeletionProtection(physicalId, pool, "ACTIVE", { emailFallback: !readOn || emailAlreadyReset });
|
|
30494
30607
|
} catch (echoError) {
|
|
30495
30608
|
let failure = echoError;
|
|
30496
30609
|
if (bareLicensed && isRefusedEcho(echoError)) try {
|
|
@@ -30526,8 +30639,10 @@ var CognitoUserPoolProvider = class {
|
|
|
30526
30639
|
}
|
|
30527
30640
|
const mode = before.UserPoolAddOns?.AdvancedSecurityMode;
|
|
30528
30641
|
if (mode) held.push(`AdvancedSecurityMode=${mode}`);
|
|
30642
|
+
if (echoesDeveloperEmail(before)) held.push("EmailConfiguration.EmailSendingAccount=DEVELOPER (SES)");
|
|
30529
30643
|
const heldText = held.length > 0 ? held.join(", ") : "none of these settings";
|
|
30530
|
-
const
|
|
30644
|
+
const what = echoesDeveloperEmail(before) ? "self sign-up, Lambda triggers, advanced security and SES email configuration" : "self sign-up, Lambda triggers and advanced security";
|
|
30645
|
+
const state = kind === "unclear" ? safeMsg`is LIVE and its ${what} MAY have been reset: ` + safeMsg`--remove-protection sent UpdateUserPool with DeletionProtection alone (the pool's own ` + safeMsg`configuration was refused) and got no clear answer, and the delete then failed. Check it ` + safeMsg`with aws cognito-idp describe-user-pool.` : kind === "earlier" ? safeMsg`is LIVE; its ${what} were reset by an ` + safeMsg`earlier UpdateUserPool that --remove-protection sent with DeletionProtection alone (the ` + safeMsg`pool's own configuration was refused); they may have been restored since. Check it with ` + safeMsg`aws cognito-idp describe-user-pool.` : safeMsg`is LIVE with its ${what} reset: ` + safeMsg`--remove-protection had to turn DeletionProtection off with UpdateUserPool alone (the ` + safeMsg`pool's own configuration was refused), and the delete then failed.`;
|
|
30531
30646
|
this.logger.error(safeMsg`Cognito User Pool ${physicalId} ` + state + safeMsg` Before that write the pool held: ${heldText}. Put them back with ` + safeMsg`aws cognito-idp update-user-pool, sending the pool's complete configuration -- a ` + safeMsg`cdkd deploy will NOT restore them, because its recorded properties still match the template.`);
|
|
30532
30647
|
}
|
|
30533
30648
|
async deleteOnce(logicalId, physicalId, resourceType, context, flip) {
|
|
@@ -30592,31 +30707,38 @@ var CognitoUserPoolProvider = class {
|
|
|
30592
30707
|
throw new ProvisioningError(`Failed to delete Cognito User Pool ${logicalId}: ${error instanceof Error ? error.message : String(error)}`, resourceType, logicalId, physicalId, cause);
|
|
30593
30708
|
}
|
|
30594
30709
|
}
|
|
30595
|
-
async sendEchoedDeletionProtection(physicalId, pool, value) {
|
|
30710
|
+
async sendEchoedDeletionProtection(physicalId, pool, value, opts = {}) {
|
|
30596
30711
|
try {
|
|
30597
30712
|
await this.getClient().send(new UpdateUserPoolCommand(userPoolDeletionProtectionUpdate(physicalId, pool, value)));
|
|
30713
|
+
return "echoed";
|
|
30598
30714
|
} catch (echoError) {
|
|
30599
30715
|
if (!echoesDeveloperEmail(pool) || !isRefusedEcho(echoError)) throw echoError;
|
|
30716
|
+
if (opts.emailFallback === false) throw echoError;
|
|
30717
|
+
const resetClause = value === "ACTIVE" ? EMAIL_RESET_CLAUSE : EMAIL_RESET_BEFORE_DELETE_CLAUSE;
|
|
30600
30718
|
this.logger.debug(safeMsg`UpdateUserPool refused the SES EmailConfiguration of ${physicalId}: ${describeAwsFailure(echoError).summary}`);
|
|
30601
30719
|
try {
|
|
30602
30720
|
await this.getClient().send(new UpdateUserPoolCommand(userPoolDeletionProtectionUpdate(physicalId, pool, value, { withoutDeveloperEmail: true })));
|
|
30603
30721
|
} catch (resendError) {
|
|
30604
30722
|
if (typeof resendError === "object" && resendError !== null) sentWithoutEmail.add(resendError);
|
|
30723
|
+
if (isAmbiguousWriteFailure(resendError) && (value === "ACTIVE" || isTransientCognitoFailure(resendError))) this.logger.warn(safeMsg`Cognito User Pool ${physicalId}: UpdateUserPool refused the write carrying the ` + safeMsg`pool's SES EmailConfiguration (${describeAwsFailure(echoError).summary}), and the ` + safeMsg`write re-sent without it answered ${describeAwsFailure(resendError).summary}. If ` + safeMsg`that write landed, the pool's email configuration was ${resetClause}`);
|
|
30605
30724
|
throw resendError;
|
|
30606
30725
|
}
|
|
30607
|
-
this.logger.warn(safeMsg`Cognito User Pool ${physicalId}: UpdateUserPool refused the write (possibly the ` + safeMsg`pool's SES EmailConfiguration, ${describeAwsFailure(echoError).summary}), so ` + safeMsg`DeletionProtection was set to ${value} with the pool's other settings but without ` + safeMsg`that EmailConfiguration.
|
|
30726
|
+
this.logger.warn(safeMsg`Cognito User Pool ${physicalId}: UpdateUserPool refused the write (possibly the ` + safeMsg`pool's SES EmailConfiguration, ${describeAwsFailure(echoError).summary}), so ` + safeMsg`DeletionProtection was set to ${value} with the pool's other settings but without ` + safeMsg`that EmailConfiguration. The pool's email configuration was ${resetClause}`);
|
|
30727
|
+
return "without-email";
|
|
30608
30728
|
}
|
|
30609
30729
|
}
|
|
30610
30730
|
async disableUserPoolDeletionProtection(physicalId, pool, flip) {
|
|
30611
30731
|
if (this.preFlipPools.get(flip)?.ambiguous) this.preFlipPools.delete(flip);
|
|
30612
30732
|
const observedOn = pool.DeletionProtection === "ACTIVE";
|
|
30613
30733
|
try {
|
|
30614
|
-
await this.sendEchoedDeletionProtection(physicalId, pool, "INACTIVE");
|
|
30734
|
+
if (await this.sendEchoedDeletionProtection(physicalId, pool, "INACTIVE") === "without-email") this.emailOmittedFlips.set(flip, "definite");
|
|
30735
|
+
else if (echoesDeveloperEmail(pool)) this.emailOmittedFlips.delete(flip);
|
|
30615
30736
|
const earlier = this.preFlipPools.get(flip);
|
|
30616
30737
|
if (earlier) earlier.echoedSince = true;
|
|
30617
30738
|
return;
|
|
30618
30739
|
} catch (echoError) {
|
|
30619
30740
|
if (echoError instanceof ResourceNotFoundException$11) throw echoError;
|
|
30741
|
+
if (typeof echoError === "object" && echoError !== null && sentWithoutEmail.has(echoError) && isAmbiguousWriteFailure(echoError) && !this.emailOmittedFlips.has(flip)) this.emailOmittedFlips.set(flip, "ambiguous");
|
|
30620
30742
|
if (observedOn && isAmbiguousWriteFailure(echoError)) flip.flippedOffByThisRun = true;
|
|
30621
30743
|
if (isTransientCognitoFailure(echoError)) throw echoError;
|
|
30622
30744
|
if (!isRefusedEcho(echoError)) {
|
|
@@ -30663,7 +30785,7 @@ var CognitoUserPoolProvider = class {
|
|
|
30663
30785
|
const echoClause = echoError === void 0 ? "" : safeMsg`; the pool's own settings sent back were refused first (${describeAwsFailure(echoError).summary})`;
|
|
30664
30786
|
this.logger.debug(safeMsg`UpdateUserPool did not turn DeletionProtection off on ${physicalId}: ${describeAwsFailure(error).detail}`);
|
|
30665
30787
|
const refused = error instanceof Error && isAwsAuthoredFailure(error);
|
|
30666
|
-
this.logger.warn(refused ? safeMsg`Cognito User Pool ${physicalId}: DeletionProtection was left on, because UpdateUserPool ` + safeMsg`refused to turn it off (${describeAwsFailure(error).summary})` + echoClause + safeMsg`. The delete will be refused while it is on.${accessHint}` : safeMsg`Cognito User Pool ${physicalId}: UpdateUserPool failed without an answer from AWS ` + safeMsg`(${describeAwsFailure(error).summary})` + echoClause + (echoError === void 0 ? typeof error === "object" && error !== null && sentWithoutEmail.has(error) ? safeMsg`, so whether DeletionProtection was turned off is unknown. Its other settings were ` + safeMsg`not reset, except
|
|
30788
|
+
this.logger.warn(refused ? safeMsg`Cognito User Pool ${physicalId}: DeletionProtection was left on, because UpdateUserPool ` + safeMsg`refused to turn it off (${describeAwsFailure(error).summary})` + echoClause + safeMsg`. The delete will be refused while it is on.${accessHint}` : safeMsg`Cognito User Pool ${physicalId}: UpdateUserPool failed without an answer from AWS ` + safeMsg`(${describeAwsFailure(error).summary})` + echoClause + (echoError === void 0 ? typeof error === "object" && error !== null && sentWithoutEmail.has(error) ? safeMsg`, so whether DeletionProtection was turned off is unknown. Its other settings were ` + safeMsg`not reset, except the SES EmailConfiguration, which that write omitted: if it ` + safeMsg`landed, the pool's email configuration was ${EMAIL_RESET_BEFORE_DELETE_CLAUSE}` : safeMsg`, so whether DeletionProtection was turned off is unknown. Its other settings were ` + safeMsg`not reset.` : safeMsg`, so whether DeletionProtection was turned off ALONE is unknown; if it was, the ` + safeMsg`pool's self sign-up, Lambda triggers and advanced security were reset.`) + safeMsg` If the delete then fails, cdkd turns the guard back on. Check the pool with ` + safeMsg`aws cognito-idp describe-user-pool.`);
|
|
30667
30789
|
}
|
|
30668
30790
|
async readCurrentState(physicalId, _logicalId, resourceType) {
|
|
30669
30791
|
if (resourceType !== "AWS::Cognito::UserPool") return void 0;
|
|
@@ -37089,21 +37211,18 @@ var KinesisStreamProvider = class {
|
|
|
37089
37211
|
const streamMode = readConfigString(streamModeDetails, "StreamMode", "PROVISIONED", "AWS::Kinesis::Stream StreamModeDetails");
|
|
37090
37212
|
const shardCount = streamMode === "PROVISIONED" ? Number(properties["ShardCount"] ?? 1) : void 0;
|
|
37091
37213
|
const maxRecordSizeInKiB = maxRecordRead.kind === "usable" ? maxRecordRead.size : void 0;
|
|
37214
|
+
const tags = {};
|
|
37215
|
+
for (const tag of desiredTags) tags[tag.Key] = tag.Value;
|
|
37092
37216
|
await this.getCreateClient().send(new CreateStreamCommand({
|
|
37093
37217
|
StreamName: streamName,
|
|
37094
37218
|
...shardCount !== void 0 && { ShardCount: shardCount },
|
|
37095
37219
|
StreamModeDetails: { StreamMode: streamMode },
|
|
37096
|
-
...maxRecordSizeInKiB !== void 0 && { MaxRecordSizeInKiB: maxRecordSizeInKiB }
|
|
37220
|
+
...maxRecordSizeInKiB !== void 0 && { MaxRecordSizeInKiB: maxRecordSizeInKiB },
|
|
37221
|
+
...Object.keys(tags).length > 0 && { Tags: tags }
|
|
37097
37222
|
}));
|
|
37098
37223
|
streamCreated = true;
|
|
37099
37224
|
this.logger.debug(`CreateStream initiated for ${streamName}, waiting for ACTIVE status`);
|
|
37100
37225
|
const streamInfo = await this.waitForStreamActive(streamName);
|
|
37101
|
-
const tags = {};
|
|
37102
|
-
for (const tag of desiredTags) tags[tag.Key] = tag.Value;
|
|
37103
|
-
if (Object.keys(tags).length > 0) await this.getClient().send(new AddTagsToStreamCommand({
|
|
37104
|
-
StreamName: streamName,
|
|
37105
|
-
Tags: tags
|
|
37106
|
-
}));
|
|
37107
37226
|
const retentionPeriodHours = retentionRead.kind === "usable" ? retentionRead.hours : void 0;
|
|
37108
37227
|
if (retentionPeriodHours !== void 0 && retentionPeriodHours !== 24) {
|
|
37109
37228
|
this.logger.debug(`Setting retention period to ${retentionPeriodHours} hours for ${streamName}`);
|
|
@@ -46592,4 +46711,4 @@ var ACMCertificateProvider = class {
|
|
|
46592
46711
|
|
|
46593
46712
|
//#endregion
|
|
46594
46713
|
export { ACMCertificateProvider, ASGProvider, AgentCoreBrowserProvider, AgentCoreCodeInterpreterProvider, AgentCoreEvaluatorProvider, AgentCoreRuntimeProvider, ApiGatewayProvider, ApiGatewayV2Provider, AppSyncProvider, BudgetsBudgetProvider, CloudFrontDistributionProvider, CloudFrontOACProvider, CloudFrontOAIProvider, CloudTrailProvider, CloudWatchAlarmProvider, CloudWatchAnomalyDetectorProvider, CodeBuildProvider, CodeCommitRepositoryProvider, CognitoUserPoolProvider, DLMLifecyclePolicyProvider, DocDBProvider, DocDBSubnetGroupProvider, DynamoDBGlobalTableProvider, DynamoDBTableProvider, EC2Provider, ECRProvider, ECSProvider, EFSProvider, ELBv2Provider, EMRClusterProvider, EMRInstanceFleetConfigProvider, EMRInstanceGroupConfigProvider, ElastiCacheProvider, EventBridgeBusProvider, EventBridgeRuleProvider, FSxFileSystemProvider, FirehoseProvider, GlueConnectionProvider, GlueCrawlerProvider, GlueJobProvider, GlueProvider, GlueSecurityConfigurationProvider, GlueTriggerProvider, GlueWorkflowProvider, IAMAccessKeyProvider, IAMInstanceProfileProvider, IAMManagedPolicyProvider, IAMPolicyProvider, IAMRoleProvider, IAMUserGroupProvider, KMSProvider, KinesisStreamConsumerProvider, KinesisStreamProvider, LambdaEventInvokeConfigProvider, LambdaEventSourceMappingProvider, LambdaFunctionProvider, LambdaLayerVersionProvider, LambdaMicrovmImageProvider, LambdaNetworkConnectorProvider, LambdaPermissionProvider, LambdaUrlProvider, LambdaWebFunctionEndpointProvider, LambdaWebFunctionRevisionProvider, LogsLogGroupProvider, NeptuneProvider, NestedStackProvider, PipesPipeProvider, RDSDBProxyEndpointProvider, RDSDBProxyProvider, RDSDBProxyTargetGroupProvider, RDSProvider, Route53Provider, S3BucketPolicyProvider, S3BucketProvider, S3DirectoryBucketProvider, S3TablesProvider, S3VectorsProvider, SNSSubscriptionProvider, SNSTopicPolicyProvider, SNSTopicProvider, SQSQueuePolicyProvider, SQSQueueProvider, SSMParameterProvider, SchedulerScheduleProvider, SecretsManagerSecretProvider, ServiceDiscoveryProvider, StepFunctionsProvider, WAFv2WebACLProvider, WaitConditionHandleProvider };
|
|
46595
|
-
//# sourceMappingURL=provider-classes-
|
|
46714
|
+
//# sourceMappingURL=provider-classes-C1xbZd9k.js.map
|