@go-to-k/cdkd 0.295.0 → 0.296.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-DuAHOXvT.js → asg-provider-AVCcoXnQ.js} +8 -6
- package/dist/asg-provider-AVCcoXnQ.js.map +1 -0
- package/dist/cli.js +2 -2
- package/dist/{deploy-engine-CuI_h_Ml.js → deploy-engine-D7204v7Z.js} +986 -183
- package/dist/deploy-engine-D7204v7Z.js.map +1 -0
- package/dist/{iam-policy-targets-CMSQGQnm.js → iam-policy-targets-DSDSdxXz.js} +145 -4
- package/dist/iam-policy-targets-DSDSdxXz.js.map +1 -0
- package/dist/{iam-role-provider-CyM-wxAp.js → iam-role-provider-CCPaZ3U4.js} +11 -5
- package/dist/iam-role-provider-CCPaZ3U4.js.map +1 -0
- package/dist/index.d.ts +37 -3
- package/dist/index.d.ts.map +1 -1
- package/dist/index.js +4 -4
- package/dist/{logger-B46YMG0h.js → logger-Dvc7ddKe.js} +19 -3
- package/dist/{logger-B46YMG0h.js.map → logger-Dvc7ddKe.js.map} +1 -1
- package/dist/{neptune-provider-BGVccWhg.js → neptune-provider-D1t9NgT-.js} +20 -14
- package/dist/neptune-provider-D1t9NgT-.js.map +1 -0
- package/dist/{program-Cbxe8TgI.js → program-B0sp_SHG.js} +6219 -5942
- package/dist/program-B0sp_SHG.js.map +1 -0
- package/dist/{provider-classes-DiWFkAOH.js → provider-classes-DMOnX5s-.js} +989 -238
- package/dist/provider-classes-DMOnX5s-.js.map +1 -0
- package/dist/{rds-provider-D6_Rcnub.js → rds-provider-DltlcDiQ.js} +22 -15
- package/dist/rds-provider-DltlcDiQ.js.map +1 -0
- package/dist/{version-CMMITJVg.js → version-DUHDmEhz.js} +2 -2
- package/dist/{version-CMMITJVg.js.map → version-DUHDmEhz.js.map} +1 -1
- package/package.json +4 -4
- package/dist/asg-provider-DuAHOXvT.js.map +0 -1
- package/dist/deploy-engine-CuI_h_Ml.js.map +0 -1
- package/dist/iam-policy-targets-CMSQGQnm.js.map +0 -1
- package/dist/iam-role-provider-CyM-wxAp.js.map +0 -1
- package/dist/neptune-provider-BGVccWhg.js.map +0 -1
- package/dist/program-Cbxe8TgI.js.map +0 -1
- package/dist/provider-classes-DiWFkAOH.js.map +0 -1
- package/dist/rds-provider-D6_Rcnub.js.map +0 -1
|
@@ -1,8 +1,8 @@
|
|
|
1
1
|
import { r as getAwsClients, s as __exportAll } from "./aws-clients-CnmtbrxD.js";
|
|
2
|
-
import { A as displaySafe, E as UNRENDERABLE, F as safeMsg, L as truncateCodePoints, M as isPasteableIdent, O as displayAwsMessage, P as plainIdentOr, S as withoutGeneratedFallbackName, T as STACK_REF_MAX_CODE_POINTS, _ as getCurrentSkipPrefix, b as withSkipPrefix, c as getLiveRenderer, f as applyDefaultNameForFallback, g as generateResourceNameWithFallback, h as generateResourceName, j as displayStackName, k as displayIdent, m as explicitNamePropertyFor, n as getLogger, r as isStdoutReservedForPayload, s as installLogLineMaskerSource, v as getCurrentStackName, w as SECRET_REF_MAX_CODE_POINTS, x as withStackName, y as looksLikeCdkdGeneratedName } from "./logger-
|
|
3
|
-
import { $
|
|
2
|
+
import { A as displaySafe, E as UNRENDERABLE, F as safeMsg, L as truncateCodePoints, M as isPasteableIdent, O as displayAwsMessage, P as plainIdentOr, S as withoutGeneratedFallbackName, T as STACK_REF_MAX_CODE_POINTS, _ as getCurrentSkipPrefix, b as withSkipPrefix, c as getLiveRenderer, f as applyDefaultNameForFallback, g as generateResourceNameWithFallback, h as generateResourceName, j as displayStackName, k as displayIdent, m as explicitNamePropertyFor, n as getLogger, r as isStdoutReservedForPayload, s as installLogLineMaskerSource, v as getCurrentStackName, w as SECRET_REF_MAX_CODE_POINTS, x as withStackName, y as looksLikeCdkdGeneratedName } from "./logger-Dvc7ddKe.js";
|
|
3
|
+
import { $n as markRedactedCause, $t as LockError, A as isTerminalDeleteFailure, At as CUSTOM_RESOURCE_RESPONSE_PREFIX, Bn as isAmbiguousCcHandlerErrorCode, Bt as clientDefaultsFor, C as refusalTypeShown, Cn as physicalIdShownBesideCommand, Ct as buildForceUnlockCommand, D as ProtectionFlipRegistry, Dn as shellQuote, Dt as formatLockOperation, En as shellBoundedDisplay, Et as formatLockExpiry, Fn as isRecreateRetryableError, Ft as producerRecordKey, Gn as retryClassificationText, H as pasteableAwsCommand, Hn as isIamPropagationError, Ht as AccountIdUnavailableError, In as isReplayedNameCollisionFrom, J as isInterruptedWaitError, Jn as safeStringify$1, Kn as describeAwsFailure, Kt as CrossAccountSecretRefusalError, Lt as withPasteableAwsProfile, M as observeThenDisableProtection, Mn as hasReplayMayCollide, Mt as injectiveKey, N as protectionFlipKey, Nn as isNameCollisionErrorFrom, O as compensateProtectionFlip, On as withheldTargetClause, Ot as formatLockOwner, Pn as isNameCooldownError, Q as canonicalizeRoute53QueryName, Qn as markNonRetryable, R as DELETION_PROTECTION_DOC_POINTER, Rn as markReplayMayCollide, Rt as ambientClientDefaults, S as quotedRemedyLogicalId, Sn as pasteableCommand, St as UNREPRODUCIBLE_LOCK_CLAUSE, T as resolveExplicitPhysicalId, Tn as quotedOrDescribed, U as protectedReplacementAdvice, Un as isRetryableTransientError, Ut as AssetError, Vn as isAmbiguousOutcomeError, Vt as credentialFingerprint, Wn as isTransientServerError, Wt as CdkdError, X as ElapsedBudgetRegistry, Xn as isMarkedNonRetryable, Xt as IntrinsicResolutionRefusalError, Y as startInterruptWatch, Yt as DynamicReferenceRegionAmbiguousError, Z as monotonicNowMs, Zn as isThrottlingError, _n as SHELL_ACTIVE_WHY, _t as hasCreatedBeforeFailure, an as ResourceTimeoutError, at as segmentAfterAnchor, b as isQuotableImportValue, bt as markAuxiliaryFailure, ct as createMaskedRetryLogger, d as prepareRemovalForUpdate, dt as maskerOrIdentity, en as MacroExpansionError, er as wrapMaskedAwsError, et as compositeIdSeparatorRefusal, f as removalWarning, ft as withDerivedNameMasks, g as assertRegionMatch, gn as SHELL_ACTIVE, gt as createdBeforeFailure, h as RESOURCE_NOT_FOUND, i as holdsSecretDerivedEntry, in as ProvisioningError, it as resourceTypeShown, jn as isUpdateUnsupportedError, jt as DEFAULT_STATE_PREFIX, k as deleteWithProtectionCompensation, kt as sanitizeRecoveryValue, l as withUnchangedSecretPrincipalLists, ln as StateError, lt as isSecretDerivedValue, m as withoutInjectedRemovals, mt as carryCreatedBeforeFailure, nt as logicalIdShown, on as ResourceUpdateNotSupportedError, ot as stateOrphanRecordRemedy, pn as normalizeAwsError, pt as RETRY_AUXILIARY_OWNER, qt as DependencyError, st as createMaskedLogSinks, tn as MalformedProducerRecordRefusalError, un as SynthesisError, ut as maskDeep, vn as UNSHOWABLE_VALUE, vt as isAuxiliaryFailure, wn as plainOrDescribed, x as normalizeAwsTagsToCfn, xn as isInertUnquoted, xt as markCreatedBeforeFailure, yn as commandHole, yt as isAuxiliaryMarkOf, zn as formatRetryClassificationSignals, zt as ambientCredentialConfig } from "./iam-policy-targets-DSDSdxXz.js";
|
|
4
4
|
import { a as setAssumedRoleCredentials, i as getPreAssumeEnvCredentials, n as awsClientDefaults, o as setPreAssumeEnvCredentials, r as getAssumedRoleCredentials, s as ambientRegion, t as SECOND_ROLE_PUBLISH_REFUSAL } from "./aws-client-defaults-D0q0z4dG.js";
|
|
5
|
-
import { t as getCdkdVersion } from "./version-
|
|
5
|
+
import { t as getCdkdVersion } from "./version-DUHDmEhz.js";
|
|
6
6
|
import { createHash, randomUUID } from "node:crypto";
|
|
7
7
|
import { AsyncLocalStorage } from "node:async_hooks";
|
|
8
8
|
import { CreateBucketCommand, DeleteObjectCommand, DeleteObjectsCommand, GetBucketLocationCommand, GetBucketReplicationCommand, GetObjectCommand, HeadBucketCommand, HeadObjectCommand, ListObjectVersionsCommand, ListObjectsV2Command, NoSuchKey, PutBucketEncryptionCommand, PutBucketPolicyCommand, PutObjectCommand, PutPublicAccessBlockCommand, S3Client, S3ServiceException } from "@aws-sdk/client-s3";
|
|
@@ -2705,7 +2705,7 @@ var FileAssetPublisher = class {
|
|
|
2705
2705
|
|
|
2706
2706
|
//#endregion
|
|
2707
2707
|
//#region src/utils/regexp.ts
|
|
2708
|
-
function escapeRegExp$
|
|
2708
|
+
function escapeRegExp$3(value) {
|
|
2709
2709
|
return value.replace(/[.*+?^${}()|[\]\\]/g, "\\$&");
|
|
2710
2710
|
}
|
|
2711
2711
|
function stripControlChars(value) {
|
|
@@ -3123,7 +3123,7 @@ function trailingShortFlagOfCluster(arg) {
|
|
|
3123
3123
|
for (const flag of ARGV_VALUE_BEARING_FLAGS) if (flag.length === 2 && flag.startsWith("-") && flag[1] !== "-" && flag[1] === last) return flag;
|
|
3124
3124
|
}
|
|
3125
3125
|
const ARGV_VALUE_TOKEN_RE = (() => {
|
|
3126
|
-
const alternation = [...ARGV_VALUE_BEARING_FLAGS].sort((a, b) => b.length - a.length || a.localeCompare(b)).map(escapeRegExp$
|
|
3126
|
+
const alternation = [...ARGV_VALUE_BEARING_FLAGS].sort((a, b) => b.length - a.length || a.localeCompare(b)).map(escapeRegExp$3).join("|");
|
|
3127
3127
|
if (alternation.length === 0 || [...ARGV_VALUE_BEARING_FLAGS].some((f) => f.trim() === "")) throw new Error("ARGV_VALUE_BEARING_FLAGS is empty or holds an empty flag: the token scan would match every k=v");
|
|
3128
3128
|
return new RegExp(`(^|\\s)(${alternation})(\\s+|=)([^\\s=]*)=\\S*`, "g");
|
|
3129
3129
|
})();
|
|
@@ -4133,10 +4133,10 @@ function flattenAssetPlaceholders(value, accountId, region, partition = "aws") {
|
|
|
4133
4133
|
return value.replace(/\$\{AWS::AccountId\}/g, accountId).replace(/\$\{AWS::Region\}/g, region).replace(/\$\{AWS::Partition\}/g, partition);
|
|
4134
4134
|
}
|
|
4135
4135
|
function isDefaultBootstrapBucketName(name, accountId, region) {
|
|
4136
|
-
return new RegExp(`^cdk-[a-z0-9]+-assets-${accountId}-${escapeRegExp$
|
|
4136
|
+
return new RegExp(`^cdk-[a-z0-9]+-assets-${accountId}-${escapeRegExp$3(region)}$`).test(name);
|
|
4137
4137
|
}
|
|
4138
4138
|
function isDefaultBootstrapRepoName(name, accountId, region) {
|
|
4139
|
-
return new RegExp(`^cdk-[a-z0-9]+-container-assets-${accountId}-${escapeRegExp$
|
|
4139
|
+
return new RegExp(`^cdk-[a-z0-9]+-container-assets-${accountId}-${escapeRegExp$3(region)}$`).test(name);
|
|
4140
4140
|
}
|
|
4141
4141
|
function buildAssetRedirectMap(manifest, marker, accountId, region, partition = "aws") {
|
|
4142
4142
|
const buckets = /* @__PURE__ */ new Map();
|
|
@@ -4145,7 +4145,7 @@ function buildAssetRedirectMap(manifest, marker, accountId, region, partition =
|
|
|
4145
4145
|
const addForms = (rawName, flattened, target) => {
|
|
4146
4146
|
sources.set(flattened, target);
|
|
4147
4147
|
if (rawName !== flattened) sources.set(rawName, target);
|
|
4148
|
-
const suffixRe = new RegExp(`-${accountId}-${escapeRegExp$
|
|
4148
|
+
const suffixRe = new RegExp(`-${accountId}-${escapeRegExp$3(region)}$`);
|
|
4149
4149
|
for (const suffix of [
|
|
4150
4150
|
"-${AWS::AccountId}-${AWS::Region}",
|
|
4151
4151
|
`-\${AWS::AccountId}-${region}`,
|
|
@@ -4186,7 +4186,7 @@ function buildAssetRedirectMap(manifest, marker, accountId, region, partition =
|
|
|
4186
4186
|
};
|
|
4187
4187
|
}
|
|
4188
4188
|
function buildBoundaryRegex(source) {
|
|
4189
|
-
return new RegExp(`(?<![A-Za-z0-9_.-])${escapeRegExp$
|
|
4189
|
+
return new RegExp(`(?<![A-Za-z0-9_.-])${escapeRegExp$3(source)}(?![A-Za-z0-9_-])`, "g");
|
|
4190
4190
|
}
|
|
4191
4191
|
function rewriteString(value, map, counter) {
|
|
4192
4192
|
let result = value;
|
|
@@ -4803,6 +4803,14 @@ function refuseMalformedOperation(shownStack, where, op) {
|
|
|
4803
4803
|
const attempted = o["attemptedProperties"];
|
|
4804
4804
|
if (attempted !== void 0 && (typeof attempted !== "object" || attempted === null || Array.isArray(attempted))) fail("attemptedProperties", attempted, "an object when present");
|
|
4805
4805
|
if (o["oldResourceRetained"] !== void 0 && typeof o["oldResourceRetained"] !== "boolean") fail("oldResourceRetained", o["oldResourceRetained"], "a boolean when present");
|
|
4806
|
+
if (o["physicalIdRecoveredFromError"] !== void 0 && typeof o["physicalIdRecoveredFromError"] !== "boolean") fail("physicalIdRecoveredFromError", o["physicalIdRecoveredFromError"], "a boolean when present");
|
|
4807
|
+
if (o["physicalIdRecoveredFromError"] !== void 0 && o["changeType"] !== "CREATE") refuseMalformed(shownStack, `${where}.physicalIdRecoveredFromError is only valid on a CREATE (got changeType ${kind(o["changeType"])}).`);
|
|
4808
|
+
if (o["deletionPolicy"] !== void 0 && ![
|
|
4809
|
+
"Delete",
|
|
4810
|
+
"Retain",
|
|
4811
|
+
"Snapshot",
|
|
4812
|
+
"RetainExceptOnCreate"
|
|
4813
|
+
].includes(o["deletionPolicy"])) fail("deletionPolicy", o["deletionPolicy"], "one of Delete, Retain, Snapshot, RetainExceptOnCreate when present");
|
|
4806
4814
|
if (o["previousResourceType"] !== void 0 && typeof o["previousResourceType"] !== "string") fail("previousResourceType", o["previousResourceType"], "a string when present");
|
|
4807
4815
|
}
|
|
4808
4816
|
function kind(v) {
|
|
@@ -4968,7 +4976,7 @@ async function rebuildClientForBucketRegion(client, bucket, opts = {}) {
|
|
|
4968
4976
|
|
|
4969
4977
|
//#endregion
|
|
4970
4978
|
//#region src/state/s3-state-backend.ts
|
|
4971
|
-
function errorDetail$
|
|
4979
|
+
function errorDetail$2(error) {
|
|
4972
4980
|
return displaySafe(error instanceof Error ? error.message : error, { asciiOnly: true }) || "<unrenderable>";
|
|
4973
4981
|
}
|
|
4974
4982
|
const LEGACY_KEY_DEPTH = 2;
|
|
@@ -5088,7 +5096,7 @@ var S3StateBackend = class {
|
|
|
5088
5096
|
} catch (error) {
|
|
5089
5097
|
if (!isNoSuchKey(error)) {
|
|
5090
5098
|
if (error instanceof StateError) throw error;
|
|
5091
|
-
throw new StateError(`Failed to get state for stack ${shownStackName} (${shownRegionName}): ${errorDetail$
|
|
5099
|
+
throw new StateError(`Failed to get state for stack ${shownStackName} (${shownRegionName}): ${errorDetail$2(error)}`, error instanceof Error ? error : void 0);
|
|
5092
5100
|
}
|
|
5093
5101
|
this.logger.debug(`No state at new key for stack: ${shownStackName} (${shownRegionName})`);
|
|
5094
5102
|
}
|
|
@@ -5135,7 +5143,7 @@ var S3StateBackend = class {
|
|
|
5135
5143
|
}));
|
|
5136
5144
|
this.logger.info(`Migrated state for stack ${this.displayName(stackName)} to region-scoped layout (${displayIdent(region)})`);
|
|
5137
5145
|
} catch (deleteError) {
|
|
5138
|
-
this.logger.warn(`Migrated stack ${this.displayName(stackName)} to new key, but failed to delete legacy key: ${errorDetail$
|
|
5146
|
+
this.logger.warn(`Migrated stack ${this.displayName(stackName)} to new key, but failed to delete legacy key: ${errorDetail$2(deleteError)}`);
|
|
5139
5147
|
}
|
|
5140
5148
|
await notifyStateSaved(stackName, region);
|
|
5141
5149
|
return response.ETag;
|
|
@@ -5145,7 +5153,7 @@ var S3StateBackend = class {
|
|
|
5145
5153
|
bucket: this.config.bucket,
|
|
5146
5154
|
operation: "PutObject"
|
|
5147
5155
|
});
|
|
5148
|
-
throw new StateError(`Failed to save state for stack ${this.stackRef(stackName, region)}: ${errorDetail$
|
|
5156
|
+
throw new StateError(`Failed to save state for stack ${this.stackRef(stackName, region)}: ${errorDetail$2(normalized)}`, normalized);
|
|
5149
5157
|
}
|
|
5150
5158
|
}
|
|
5151
5159
|
async deleteState(stackName, region) {
|
|
@@ -5177,7 +5185,7 @@ var S3StateBackend = class {
|
|
|
5177
5185
|
bucket: this.config.bucket,
|
|
5178
5186
|
operation: "DeleteObject"
|
|
5179
5187
|
});
|
|
5180
|
-
throw new StateError(`Failed to delete state for stack ${this.stackRef(stackName, region)}: ${errorDetail$
|
|
5188
|
+
throw new StateError(`Failed to delete state for stack ${this.stackRef(stackName, region)}: ${errorDetail$2(normalized)}`, normalized);
|
|
5181
5189
|
} finally {
|
|
5182
5190
|
await this.deleteRollbackJournal(stackName, region);
|
|
5183
5191
|
}
|
|
@@ -5199,7 +5207,7 @@ var S3StateBackend = class {
|
|
|
5199
5207
|
bucket: this.config.bucket,
|
|
5200
5208
|
operation: "DeleteObject"
|
|
5201
5209
|
});
|
|
5202
|
-
throw new StateError(`Failed to delete legacy state for stack ${displayStackName(stackName)}: ${errorDetail$
|
|
5210
|
+
throw new StateError(`Failed to delete legacy state for stack ${displayStackName(stackName)}: ${errorDetail$2(normalized)}`, normalized);
|
|
5203
5211
|
}
|
|
5204
5212
|
}
|
|
5205
5213
|
async listStacks() {
|
|
@@ -5370,7 +5378,7 @@ var S3StateBackend = class {
|
|
|
5370
5378
|
});
|
|
5371
5379
|
} catch (error) {
|
|
5372
5380
|
const describing = options.objectDescription ? ` (${options.objectDescription})` : "";
|
|
5373
|
-
this.logger.warn(`Could not purge noncurrent versions of ${keys.length} key(s) in bucket '${this.config.bucket}': the purge could not be started. Their previous versions survive and remain readable via GetObject with a VersionId${describing}. Grant s3:ListBucketVersions and s3:DeleteObjectVersion on the state bucket, or purge the key(s) by hand. Underlying error: ${errorDetail$
|
|
5381
|
+
this.logger.warn(`Could not purge noncurrent versions of ${keys.length} key(s) in bucket '${this.config.bucket}': the purge could not be started. Their previous versions survive and remain readable via GetObject with a VersionId${describing}. Grant s3:ListBucketVersions and s3:DeleteObjectVersion on the state bucket, or purge the key(s) by hand. Underlying error: ${errorDetail$2(error)}`);
|
|
5374
5382
|
}
|
|
5375
5383
|
}
|
|
5376
5384
|
async purgeNoncurrentVersionsUnderPrefix(keyPrefix, options = {}) {
|
|
@@ -5384,7 +5392,7 @@ var S3StateBackend = class {
|
|
|
5384
5392
|
} catch (error) {
|
|
5385
5393
|
const prefixShown = displayIdent(keyPrefix, { maxCodePoints: STACK_REF_MAX_CODE_POINTS });
|
|
5386
5394
|
const describing = options.objectDescription ? ` (${options.objectDescription})` : "";
|
|
5387
|
-
this.logger.warn(safeMsg`Could not purge noncurrent versions under the prefix ${prefixShown} in bucket ${this.config.bucket}: the purge could not be started. Their previous versions survive and remain readable via GetObject with a VersionId${describing}. Grant s3:ListBucketVersions and s3:DeleteObjectVersion on the state bucket, or purge the prefix by hand. Underlying error: ${errorDetail$
|
|
5395
|
+
this.logger.warn(safeMsg`Could not purge noncurrent versions under the prefix ${prefixShown} in bucket ${this.config.bucket}: the purge could not be started. Their previous versions survive and remain readable via GetObject with a VersionId${describing}. Grant s3:ListBucketVersions and s3:DeleteObjectVersion on the state bucket, or purge the prefix by hand. Underlying error: ${errorDetail$2(error)}`);
|
|
5388
5396
|
return {
|
|
5389
5397
|
deletedBodies: 0,
|
|
5390
5398
|
complete: false
|
|
@@ -5410,7 +5418,7 @@ var S3StateBackend = class {
|
|
|
5410
5418
|
await this.saveCreateTokenLedger(stackName, region, ledger);
|
|
5411
5419
|
} catch (error) {
|
|
5412
5420
|
const normalized = normalizeAwsError(error, { bucket: this.config.bucket });
|
|
5413
|
-
throw new StateError(`Failed to renew the create-token ledger of stack ${this.stackRef(stackName, region)}: ${errorDetail$
|
|
5421
|
+
throw new StateError(`Failed to renew the create-token ledger of stack ${this.stackRef(stackName, region)}: ${errorDetail$2(normalized)}. The state record was left in place; re-run once the ledger can be written.`, normalized);
|
|
5414
5422
|
}
|
|
5415
5423
|
}
|
|
5416
5424
|
async deleteCreateTokenLedger(stackName, region) {
|
|
@@ -5427,7 +5435,7 @@ var S3StateBackend = class {
|
|
|
5427
5435
|
bucket: this.config.bucket,
|
|
5428
5436
|
operation: "DeleteObject"
|
|
5429
5437
|
});
|
|
5430
|
-
throw new StateError(`Failed to delete the create-token ledger for stack ${this.stackRef(stackName, region)}: ${errorDetail$
|
|
5438
|
+
throw new StateError(`Failed to delete the create-token ledger for stack ${this.stackRef(stackName, region)}: ${errorDetail$2(normalized)}. The state record was left in place; re-run once the ledger can be deleted.`, normalized);
|
|
5431
5439
|
}
|
|
5432
5440
|
}
|
|
5433
5441
|
async loadRollbackJournal(stackName, region) {
|
|
@@ -5453,6 +5461,58 @@ var S3StateBackend = class {
|
|
|
5453
5461
|
else newest.failedOperations = remaining;
|
|
5454
5462
|
await this.putRawObject(this.getRollbackJournalKey(stackName, region), JSON.stringify(journal, null, 2));
|
|
5455
5463
|
}
|
|
5464
|
+
async dropRollbackJournalFailedOperations(stackName, region, drop) {
|
|
5465
|
+
const journal = await this.loadRollbackJournal(stackName, region);
|
|
5466
|
+
if (!journal) return 0;
|
|
5467
|
+
let removed = 0;
|
|
5468
|
+
for (const segment of journal.segments) {
|
|
5469
|
+
if (!segment.failedOperations) continue;
|
|
5470
|
+
const kept = segment.failedOperations.filter((op) => !drop(op, segment));
|
|
5471
|
+
removed += segment.failedOperations.length - kept.length;
|
|
5472
|
+
if (kept.length === 0) delete segment.failedOperations;
|
|
5473
|
+
else segment.failedOperations = kept;
|
|
5474
|
+
}
|
|
5475
|
+
if (removed === 0) return 0;
|
|
5476
|
+
await this.putRawObject(this.getRollbackJournalKey(stackName, region), JSON.stringify(journal, null, 2));
|
|
5477
|
+
return removed;
|
|
5478
|
+
}
|
|
5479
|
+
async reduceRollbackJournalToFailedOperations(stackName, region, keep, supersededLogicalIds = [], demote = () => false) {
|
|
5480
|
+
const journal = await this.loadRollbackJournal(stackName, region);
|
|
5481
|
+
if (!journal) return 0;
|
|
5482
|
+
const carried = new Set(supersededLogicalIds);
|
|
5483
|
+
const kept = [];
|
|
5484
|
+
let count = 0;
|
|
5485
|
+
const keptBySegment = journal.segments.map((segment) => (segment.failedOperations ?? []).filter((op) => keep(op, segment)).map((op) => op.physicalIdRecoveredFromError === true && demote(op, segment) ? {
|
|
5486
|
+
...op,
|
|
5487
|
+
physicalIdRecoveredFromError: false
|
|
5488
|
+
} : op));
|
|
5489
|
+
const keptIds = new Set(keptBySegment.flat().map((op) => op.logicalId));
|
|
5490
|
+
for (let s = journal.segments.length - 1; s >= 0; s--) {
|
|
5491
|
+
const segment = journal.segments[s];
|
|
5492
|
+
for (const op of segment.operations) carried.add(op.logicalId);
|
|
5493
|
+
for (const id of segment.supersededLogicalIds ?? []) carried.add(id);
|
|
5494
|
+
const failed = keptBySegment[s];
|
|
5495
|
+
if (failed.length === 0) continue;
|
|
5496
|
+
const reduced = {
|
|
5497
|
+
...segment,
|
|
5498
|
+
initialDeploy: false,
|
|
5499
|
+
operations: [],
|
|
5500
|
+
failedOperations: failed
|
|
5501
|
+
};
|
|
5502
|
+
delete reduced.previousOutputs;
|
|
5503
|
+
delete reduced.previousCrossStackReads;
|
|
5504
|
+
addSupersededIds(reduced, [...carried].filter((id) => !keptIds.has(id) || segment.supersededLogicalIds?.includes(id)));
|
|
5505
|
+
kept.unshift(reduced);
|
|
5506
|
+
count += failed.length;
|
|
5507
|
+
}
|
|
5508
|
+
if (kept.length === 0) {
|
|
5509
|
+
await this.deleteRollbackJournal(stackName, region);
|
|
5510
|
+
return 0;
|
|
5511
|
+
}
|
|
5512
|
+
journal.segments = kept;
|
|
5513
|
+
await this.putRawObject(this.getRollbackJournalKey(stackName, region), JSON.stringify(journal, null, 2));
|
|
5514
|
+
return count;
|
|
5515
|
+
}
|
|
5456
5516
|
async popRollbackJournalSegment(stackName, region) {
|
|
5457
5517
|
const journal = await this.loadRollbackJournal(stackName, region);
|
|
5458
5518
|
if (!journal || journal.segments.length === 0) {
|
|
@@ -5521,7 +5581,7 @@ var S3StateBackend = class {
|
|
|
5521
5581
|
} catch (error) {
|
|
5522
5582
|
if (!isNoSuchKey(error) && error.name !== "NotFound") {
|
|
5523
5583
|
gone = false;
|
|
5524
|
-
this.logger.warn(`Failed to delete rollback journal for ${this.stackRef(stackName, region)}: ${errorDetail$
|
|
5584
|
+
this.logger.warn(`Failed to delete rollback journal for ${this.stackRef(stackName, region)}: ${errorDetail$2(error)}`);
|
|
5525
5585
|
}
|
|
5526
5586
|
}
|
|
5527
5587
|
await this.purgeNoncurrentVersions([key], { objectDescription: "the rollback journal, whose `failedOperations[].attemptedProperties` records the properties of the failed write verbatim" });
|
|
@@ -5639,7 +5699,7 @@ var S3StateBackend = class {
|
|
|
5639
5699
|
};
|
|
5640
5700
|
} catch (error) {
|
|
5641
5701
|
if (isNoSuchKey(error)) return null;
|
|
5642
|
-
throw new StateError(`Failed to get legacy state for stack ${this.displayName(stackName)}: ${errorDetail$
|
|
5702
|
+
throw new StateError(`Failed to get legacy state for stack ${this.displayName(stackName)}: ${errorDetail$2(error)}`, error instanceof Error ? error : void 0);
|
|
5643
5703
|
}
|
|
5644
5704
|
}
|
|
5645
5705
|
parseStateBody(bodyString, stackName) {
|
|
@@ -5691,7 +5751,7 @@ function safeSegment(value) {
|
|
|
5691
5751
|
function stackRef(stackName, region) {
|
|
5692
5752
|
return region === void 0 ? safeSegment(stackName) : `${safeSegment(stackName)} (${safeSegment(region)})`;
|
|
5693
5753
|
}
|
|
5694
|
-
function errorDetail(error) {
|
|
5754
|
+
function errorDetail$1(error) {
|
|
5695
5755
|
return displaySafe(error instanceof Error ? error.message : error, { asciiOnly: true }) || "<unrenderable>";
|
|
5696
5756
|
}
|
|
5697
5757
|
function isLockInfoExpired(lockInfo) {
|
|
@@ -5827,7 +5887,7 @@ var LockManager = class {
|
|
|
5827
5887
|
}
|
|
5828
5888
|
return false;
|
|
5829
5889
|
}
|
|
5830
|
-
throw new LockError(`Failed to acquire lock for stack ${safeSegment(stackName)} (${safeSegment(region)}): ` + errorDetail(error), error instanceof Error ? error : void 0);
|
|
5890
|
+
throw new LockError(`Failed to acquire lock for stack ${safeSegment(stackName)} (${safeSegment(region)}): ` + errorDetail$1(error), error instanceof Error ? error : void 0);
|
|
5831
5891
|
}
|
|
5832
5892
|
}
|
|
5833
5893
|
async putLockObject(key, lockInfo, condition = { IfNoneMatch: "*" }) {
|
|
@@ -5882,7 +5942,7 @@ var LockManager = class {
|
|
|
5882
5942
|
return null;
|
|
5883
5943
|
}
|
|
5884
5944
|
if (error instanceof LockError) throw error;
|
|
5885
|
-
throw new LockError(`Failed to get lock info for stack ${shownStack}: ${errorDetail(error)}`, error instanceof Error ? error : void 0);
|
|
5945
|
+
throw new LockError(`Failed to get lock info for stack ${shownStack}: ${errorDetail$1(error)}`, error instanceof Error ? error : void 0);
|
|
5886
5946
|
}
|
|
5887
5947
|
}
|
|
5888
5948
|
async isLocked(stackName, region) {
|
|
@@ -5930,16 +5990,16 @@ var LockManager = class {
|
|
|
5930
5990
|
this.logger.warn(`Not releasing the lock for stack ${stackRef(stackName, region)}: the conditional delete could not be evaluated here, and this process could not confirm the lock is still its own. Leaving it in place rather than risk deleting another process's lock. It expires on its own, or clear it with cdkd force-unlock. If this repeats, grant s3:GetObject on the lock key -- a delete conditioned on an ETag requires it.`);
|
|
5931
5991
|
return;
|
|
5932
5992
|
}
|
|
5933
|
-
this.logger.debug(`Conditional lock release for stack ${stackRef(stackName, region)} is not supported here (${errorDetail(error)}); retrying unconditionally`);
|
|
5993
|
+
this.logger.debug(`Conditional lock release for stack ${stackRef(stackName, region)} is not supported here (${errorDetail$1(error)}); retrying unconditionally`);
|
|
5934
5994
|
try {
|
|
5935
5995
|
await this.deleteLock(stackName, region);
|
|
5936
5996
|
this.logger.debug(`Lock released for stack: ${stackRef(stackName, region)}`);
|
|
5937
5997
|
return;
|
|
5938
5998
|
} catch (fallbackError) {
|
|
5939
|
-
throw new LockError(`Failed to release lock for stack ${stackRef(stackName, region)}: ${errorDetail(fallbackError)}`, fallbackError instanceof Error ? fallbackError : void 0);
|
|
5999
|
+
throw new LockError(`Failed to release lock for stack ${stackRef(stackName, region)}: ${errorDetail$1(fallbackError)}`, fallbackError instanceof Error ? fallbackError : void 0);
|
|
5940
6000
|
}
|
|
5941
6001
|
}
|
|
5942
|
-
throw new LockError(`Failed to release lock for stack ${stackRef(stackName, region)}: ${errorDetail(error)}`, error instanceof Error ? error : void 0);
|
|
6002
|
+
throw new LockError(`Failed to release lock for stack ${stackRef(stackName, region)}: ${errorDetail$1(error)}`, error instanceof Error ? error : void 0);
|
|
5943
6003
|
} finally {
|
|
5944
6004
|
await this.purgeLockVersions(this.getLockKey(stackName, region), "release");
|
|
5945
6005
|
}
|
|
@@ -5998,7 +6058,7 @@ var LockManager = class {
|
|
|
5998
6058
|
objectDescription: LOCK_OBJECT_DESCRIPTION
|
|
5999
6059
|
});
|
|
6000
6060
|
} catch (error) {
|
|
6001
|
-
report(`Could not purge noncurrent versions of the lock key ${displayIdent(key, { maxCodePoints: STACK_REF_MAX_CODE_POINTS })} in bucket '${this.config.bucket}': the purge could not be started. Their previous versions survive and remain readable via GetObject with a VersionId (${LOCK_OBJECT_DESCRIPTION}). Grant s3:ListBucketVersions and s3:DeleteObjectVersion on the state bucket, or purge the key by hand. Underlying error: ${errorDetail(error)}`);
|
|
6061
|
+
report(`Could not purge noncurrent versions of the lock key ${displayIdent(key, { maxCodePoints: STACK_REF_MAX_CODE_POINTS })} in bucket '${this.config.bucket}': the purge could not be started. Their previous versions survive and remain readable via GetObject with a VersionId (${LOCK_OBJECT_DESCRIPTION}). Grant s3:ListBucketVersions and s3:DeleteObjectVersion on the state bucket, or purge the key by hand. Underlying error: ${errorDetail$1(error)}`);
|
|
6002
6062
|
}
|
|
6003
6063
|
}
|
|
6004
6064
|
trackHeldLock(args) {
|
|
@@ -6078,7 +6138,7 @@ var LockManager = class {
|
|
|
6078
6138
|
this.logger.warn(`Lost the lock for stack ${stackRef(held.stackName, held.region)} while the operation was still running: the lock object has been replaced or removed. Another cdkd process may now be writing to this stack concurrently. This process will not delete the current lock when it finishes.`);
|
|
6079
6139
|
return;
|
|
6080
6140
|
}
|
|
6081
|
-
this.logger.debug(`Lock renewal for stack ${stackRef(held.stackName, held.region)} failed, will retry: ${errorDetail(error)}`);
|
|
6141
|
+
this.logger.debug(`Lock renewal for stack ${stackRef(held.stackName, held.region)} failed, will retry: ${errorDetail$1(error)}`);
|
|
6082
6142
|
if (!held.warnedPastExpiry && Date.now() >= held.info.expiresAt) {
|
|
6083
6143
|
held.warnedPastExpiry = true;
|
|
6084
6144
|
this.logger.warn(`Lock renewal for stack ${stackRef(held.stackName, held.region)} has been failing long enough that the lock expired at ${new Date(held.info.expiresAt).toISOString()}. Another cdkd process can now take it while this operation is still running. Renewal keeps retrying.`);
|
|
@@ -6151,13 +6211,13 @@ function nanIfUncoercible(value) {
|
|
|
6151
6211
|
//#endregion
|
|
6152
6212
|
//#region src/deployment/secret-redaction/rules.ts
|
|
6153
6213
|
const MIN_NEEDLE_LENGTH = 4;
|
|
6154
|
-
function escapeRegExp$
|
|
6214
|
+
function escapeRegExp$2(value) {
|
|
6155
6215
|
return value.replace(/[.*+?^${}()|[\]\\]/g, "\\$&");
|
|
6156
6216
|
}
|
|
6157
6217
|
function buildNeedleRegex(values) {
|
|
6158
6218
|
const needles = Array.from(new Set(values)).filter((v) => v.length >= 4).sort((a, b) => b.length - a.length);
|
|
6159
6219
|
if (needles.length === 0) return void 0;
|
|
6160
|
-
return new RegExp(needles.map(escapeRegExp$
|
|
6220
|
+
return new RegExp(needles.map(escapeRegExp$2).join("|"), "g");
|
|
6161
6221
|
}
|
|
6162
6222
|
const TEMPLATE_DERIVED_RULES = {
|
|
6163
6223
|
descendArrays: true,
|
|
@@ -7323,7 +7383,7 @@ function intrinsicSkeletonPattern(source) {
|
|
|
7323
7383
|
return anchoredSkeletonPattern(segments);
|
|
7324
7384
|
}
|
|
7325
7385
|
function anchoredSkeletonPattern(segments) {
|
|
7326
|
-
const body = joinSkeletonSegments(segments.map((segment) => segment === UNKNOWN_PART ? SKELETON_WILDCARD : escapeRegExp$
|
|
7386
|
+
const body = joinSkeletonSegments(segments.map((segment) => segment === UNKNOWN_PART ? SKELETON_WILDCARD : escapeRegExp$2(segment)));
|
|
7327
7387
|
return body === void 0 ? void 0 : new RegExp(`^${body}$`);
|
|
7328
7388
|
}
|
|
7329
7389
|
const UNKNOWN_PART = Symbol("unknown intrinsic part");
|
|
@@ -9099,58 +9159,6 @@ var ReplacementRulesRegistry = class {
|
|
|
9099
9159
|
}
|
|
9100
9160
|
};
|
|
9101
9161
|
|
|
9102
|
-
//#endregion
|
|
9103
|
-
//#region src/provisioning/auxiliary-failure.ts
|
|
9104
|
-
const AUXILIARY_LOGICAL_ID_SUFFIX = "/auxiliary";
|
|
9105
|
-
const MAX_DEPTH = 5;
|
|
9106
|
-
function auxiliaryLogicalId(ownerLogicalId) {
|
|
9107
|
-
return `${ownerLogicalId}${AUXILIARY_LOGICAL_ID_SUFFIX}`;
|
|
9108
|
-
}
|
|
9109
|
-
const RETRY_AUXILIARY_OWNER = "withRetry";
|
|
9110
|
-
function isAuxiliaryMarkOf(link, ownerLogicalId) {
|
|
9111
|
-
try {
|
|
9112
|
-
if (typeof link !== "object" && typeof link !== "function" || link === null) return false;
|
|
9113
|
-
const own = Object.getOwnPropertyDescriptor(link, "logicalId");
|
|
9114
|
-
return isAuxiliaryMark(own) && own?.value === auxiliaryLogicalId(ownerLogicalId);
|
|
9115
|
-
} catch {
|
|
9116
|
-
return false;
|
|
9117
|
-
}
|
|
9118
|
-
}
|
|
9119
|
-
function isAuxiliaryMark(descriptor) {
|
|
9120
|
-
return descriptor !== void 0 && descriptor.enumerable === false && descriptor.writable === false && typeof descriptor.value === "string" && descriptor.value.endsWith(AUXILIARY_LOGICAL_ID_SUFFIX);
|
|
9121
|
-
}
|
|
9122
|
-
function isAuxiliaryFailure(error) {
|
|
9123
|
-
try {
|
|
9124
|
-
let current = error;
|
|
9125
|
-
for (let depth = 0; depth < MAX_DEPTH && typeof current === "object" && current !== null; depth++) {
|
|
9126
|
-
if (isAuxiliaryMark(Object.getOwnPropertyDescriptor(current, "logicalId"))) return true;
|
|
9127
|
-
current = current.cause;
|
|
9128
|
-
}
|
|
9129
|
-
} catch {}
|
|
9130
|
-
return false;
|
|
9131
|
-
}
|
|
9132
|
-
function markAuxiliaryFailure(error, ownerLogicalId) {
|
|
9133
|
-
try {
|
|
9134
|
-
let current = error;
|
|
9135
|
-
for (let depth = 0; depth < MAX_DEPTH && typeof current === "object" && current !== null; depth++) {
|
|
9136
|
-
const own = Object.getOwnPropertyDescriptor(current, "logicalId");
|
|
9137
|
-
if (typeof own?.value === "string") {
|
|
9138
|
-
if (isAuxiliaryMark(own)) return error;
|
|
9139
|
-
} else {
|
|
9140
|
-
if (Object.isExtensible(current) && own?.configurable !== false) Object.defineProperty(current, "logicalId", {
|
|
9141
|
-
value: auxiliaryLogicalId(ownerLogicalId),
|
|
9142
|
-
enumerable: false,
|
|
9143
|
-
writable: false,
|
|
9144
|
-
configurable: true
|
|
9145
|
-
});
|
|
9146
|
-
return error;
|
|
9147
|
-
}
|
|
9148
|
-
current = current.cause;
|
|
9149
|
-
}
|
|
9150
|
-
} catch {}
|
|
9151
|
-
return error;
|
|
9152
|
-
}
|
|
9153
|
-
|
|
9154
9162
|
//#endregion
|
|
9155
9163
|
//#region src/deployment/retry.ts
|
|
9156
9164
|
const IAM_PROPAGATION_INITIAL_DELAY_MS = 250;
|
|
@@ -9175,11 +9183,14 @@ async function withRetry(operation, logicalId, opts = {}) {
|
|
|
9175
9183
|
let nameCooldownSleptMs = 0;
|
|
9176
9184
|
let serverErrorRetries = 0;
|
|
9177
9185
|
let replayMayCollide = false;
|
|
9186
|
+
let previousError;
|
|
9178
9187
|
const settle = (error) => replayMayCollide ? markReplayMayCollide(markAuxiliaryFailure(error, RETRY_AUXILIARY_OWNER)) : error;
|
|
9179
9188
|
for (let attempt = 0; attempt <= attemptCeiling; attempt++) try {
|
|
9180
9189
|
return await operation();
|
|
9181
9190
|
} catch (error) {
|
|
9182
9191
|
lastError = error;
|
|
9192
|
+
const carried = carryCreatedBeforeFailure(previousError, error);
|
|
9193
|
+
if (hasCreatedBeforeFailure(carried) || !hasCreatedBeforeFailure(previousError)) previousError = carried;
|
|
9183
9194
|
if (isAuxiliaryFailure(error) || hasReplayMayCollide(error) || isAmbiguousOutcomeError(error)) replayMayCollide = true;
|
|
9184
9195
|
const message = describeAwsFailure(error).detail;
|
|
9185
9196
|
const classifyText = retryClassificationText(error);
|
|
@@ -15209,10 +15220,10 @@ function refuseMalformedResourcesForDestroy(state, stackName, region, recovery)
|
|
|
15209
15220
|
throw markNonRetryable(new CdkdError(malformedDestroyResourcesRefusalMessage(stackName, region, recovery), STATE_RESOURCES_MALFORMED));
|
|
15210
15221
|
}
|
|
15211
15222
|
const STATE_REGION_DIVERGED = "STATE_REGION_DIVERGED";
|
|
15212
|
-
function divergentRecordRegionRefusalMessage(stackName, keyRegion, divergentBodyRegion, resourceCount, recovery) {
|
|
15223
|
+
function divergentRecordRegionRefusalMessage(stackName, keyRegion, divergentBodyRegion, resourceCount, recovery, provenOrphans = 0) {
|
|
15213
15224
|
const cap = STACK_REF_MAX_CODE_POINTS;
|
|
15214
15225
|
const exact = rendersExactly(stackName, cap) && rendersExactly(keyRegion, cap) && isPasteableIdent(stackName) && isPasteableIdent(keyRegion);
|
|
15215
|
-
const lists = resourceCount === void 0 ? "its resources map cannot be read" : `it still lists ${resourceCount} resource${resourceCount === 1 ? "" : "s"}`;
|
|
15226
|
+
const lists = resourceCount === void 0 ? "its resources map cannot be read" : resourceCount === 0 && provenOrphans > 0 ? `its rollback journal holds ${provenOrphans} failed create${provenOrphans === 1 ? "" : "s"} whose resource the destroy would delete` : `it still lists ${resourceCount} resource${resourceCount === 1 ? "" : "s"}`;
|
|
15216
15227
|
const kind = describeRegionValueKind(divergentBodyRegion);
|
|
15217
15228
|
const opening = exact ? `cdkd will not destroy stack ${shellQuote(safeIdentifier(stackName, cap))} (${shellQuote(safeIdentifier(keyRegion, cap))}): the state record read from that region's key carries a 'region' of its own (${kind}) that is not the key's, and ${lists}` : `cdkd will not destroy the state record this command loaded: it carries a 'region' of its own (${kind}) that is not the region of the key it was read from, and ${lists}`;
|
|
15218
15229
|
const listing = withheldListingPointer(recovery);
|
|
@@ -15220,11 +15231,11 @@ function divergentRecordRegionRefusalMessage(stackName, keyRegion, divergentBody
|
|
|
15220
15231
|
const remedy = exact ? "Re-run with --verbose to see what the record's region field holds, then either destroy against the region the resources are really in, or repair that field to match the key it is stored under and re-run. " + withheldAccountClause(withheldAccounts, "the command at the end of this message prints") + "To drop the record and leave the live resources standing, spelled out rather than pasteable because that command DELETES a record: " + dropRecordTemplate(recovery) : "This record's stack name or region does NOT render exactly — what any surrounding output shows is a sanitized form, and another record may render identically — so this message names no target and offers no command against one. List the records with " + (listing.line === void 0 ? `${WITHHELD_LISTING_POINTER}. Inspect it with: ${inspectCommand(void 0, void 0)}` : `${listing.pointer}.` + destroyAccountClause(recovery) + `\n${listing.line}\nInspect it with: ${inspectCommand(void 0, void 0, recovery)}`);
|
|
15221
15232
|
return `${opening} ${resourceCount === void 0 ? `— so cdkd can neither count what it would delete nor tell which region it is in` : `— so cdkd cannot tell which region those resources are in`}. cdkd stamps the key's region into every record it writes, so this record was not written by cdkd. Destroying against the key's region would issue every delete there; if the record's own region is the honest half, each delete comes back not-found, which this command reads as ALREADY DELETED — it would report success, remove the record, and leave every resource standing in the other region with nothing naming it. ${remedy}`;
|
|
15222
15233
|
}
|
|
15223
|
-
function refuseDivergentRecordRegionForDestroy(state, stackName, keyRegion, divergentBodyRegion, recovery) {
|
|
15234
|
+
function refuseDivergentRecordRegionForDestroy(state, stackName, keyRegion, divergentBodyRegion, recovery, provenOrphans = 0) {
|
|
15224
15235
|
if (divergentBodyRegion === void 0) return;
|
|
15225
15236
|
const resourceCount = isReadableBag(state.resources) ? Object.keys(state.resources).length : void 0;
|
|
15226
|
-
if (resourceCount === 0) return;
|
|
15227
|
-
throw markNonRetryable(new CdkdError(divergentRecordRegionRefusalMessage(stackName, keyRegion, divergentBodyRegion, resourceCount, recovery), STATE_REGION_DIVERGED));
|
|
15237
|
+
if (resourceCount === 0 && provenOrphans === 0) return;
|
|
15238
|
+
throw markNonRetryable(new CdkdError(divergentRecordRegionRefusalMessage(stackName, keyRegion, divergentBodyRegion, resourceCount, recovery, provenOrphans), STATE_REGION_DIVERGED));
|
|
15228
15239
|
}
|
|
15229
15240
|
function malformedDeployResourcesRefusalMessage(rawStackName, rawRegion) {
|
|
15230
15241
|
const stackName = absentIfEmpty(rawStackName);
|
|
@@ -15663,6 +15674,16 @@ function malformedDestroyResourceEntriesRefusalMessage(rawStackName, rawRegion,
|
|
|
15663
15674
|
const region = absentIfEmpty(rawRegion);
|
|
15664
15675
|
return `${namedEntriesClause(stackName, region, logicalIds)} 'cdkd destroy' DELETES what this map names, so it refuses rather than continuing: a null row stops the run on a bare TypeError in the listing above the prompt; a false, 0 or empty-string row is SKIPPED as 'not found in state' and the record removed with its resource still live in AWS; and any other row it cannot read, unless its own deletion policy retains it, is routed to a provider on whatever its type field holds — nothing, or a non-string — with a physical id nothing checked, so its delete either fails on a type-lookup error that names the row but not what is wrong with its record, after every readable row not retained was deleted, or is counted done, the record removed and success reported with its resource still live. Nothing was deleted or written FOR THIS STACK. Repair the row first; 'cdkd state orphan' drops the whole record with every resource left standing, which is more than this row asks for. ${inspectClause(stackName, region, recovery)}Inspect the record with: ` + inspectCommand(stackName, region, recovery);
|
|
15665
15676
|
}
|
|
15677
|
+
function refuseMalformedResourcePropertiesForDestroy(state, stackName, region, recovery) {
|
|
15678
|
+
const unreadable = unreadableResourcePropertyBags(state);
|
|
15679
|
+
if (unreadable.length === 0) return;
|
|
15680
|
+
throw markNonRetryable(new CdkdError(malformedDestroyResourcePropertiesRefusalMessage(stackName, region, unreadable, recovery), STATE_RESOURCES_MALFORMED));
|
|
15681
|
+
}
|
|
15682
|
+
function malformedDestroyResourcePropertiesRefusalMessage(rawStackName, rawRegion, logicalIds, recovery) {
|
|
15683
|
+
const stackName = absentIfEmpty(rawStackName);
|
|
15684
|
+
const region = absentIfEmpty(rawRegion);
|
|
15685
|
+
return `${namedPropertyBagsDiagnosis(stackName, region, logicalIds)} 'cdkd destroy' hands that map to the resource's delete, which reads keys off it — whether an RDS DB instance takes a final snapshot, whether an ECR repository is emptied first — so it refuses rather than continuing: the provider would get the torn value as it stands, and reading the map as EMPTY answers each of those keys as absent, a delete that fails or takes the wrong branch after every resource ordered before it was deleted. Nothing was deleted or written FOR THIS STACK. Repair the map first; 'cdkd state orphan' drops the whole record with every resource left standing, which is more than this asks for. ${inspectClause(stackName, region, recovery)}Inspect the record with: ` + inspectCommand(stackName, region, recovery);
|
|
15686
|
+
}
|
|
15666
15687
|
function refuseMalformedResourceEntriesForImport(state, reimportedLogicalIds, stackName, region, recovery) {
|
|
15667
15688
|
const reimported = new Set(reimportedLogicalIds);
|
|
15668
15689
|
const unreadable = unreadableResourceEntries(state).filter((id) => !reimported.has(id));
|
|
@@ -15902,7 +15923,7 @@ function isPlainObject$2(value) {
|
|
|
15902
15923
|
return value !== null && typeof value === "object" && !Array.isArray(value);
|
|
15903
15924
|
}
|
|
15904
15925
|
const DYNAMIC_REFERENCE_OPEN = "{{resolve:";
|
|
15905
|
-
const NESTED_STACK_TYPE$
|
|
15926
|
+
const NESTED_STACK_TYPE$3 = "AWS::CloudFormation::Stack";
|
|
15906
15927
|
const NESTED_OUTPUT_PREFIX = "Outputs.";
|
|
15907
15928
|
function carriesSecretValue(value, corpora) {
|
|
15908
15929
|
if (carriesSecretMask(value)) return true;
|
|
@@ -15977,7 +15998,7 @@ function intrinsicKey(value) {
|
|
|
15977
15998
|
const key = keys[0];
|
|
15978
15999
|
return key === "Ref" || key.startsWith("Fn::") ? key : void 0;
|
|
15979
16000
|
}
|
|
15980
|
-
const OPAQUE_ATTRIBUTE_TYPES = /* @__PURE__ */ new Set(["AWS::CloudFormation::CustomResource", NESTED_STACK_TYPE$
|
|
16001
|
+
const OPAQUE_ATTRIBUTE_TYPES = /* @__PURE__ */ new Set(["AWS::CloudFormation::CustomResource", NESTED_STACK_TYPE$3]);
|
|
15981
16002
|
function hasOpaqueAttributes(logicalId, walk) {
|
|
15982
16003
|
const definition = walk.resources[logicalId];
|
|
15983
16004
|
const type = isPlainObject$2(definition) ? definition["Type"] : void 0;
|
|
@@ -16334,7 +16355,7 @@ function passedKey(passed) {
|
|
|
16334
16355
|
function isNestedStackRow(logicalId, walk) {
|
|
16335
16356
|
if (!Object.hasOwn(walk.resources, logicalId)) return false;
|
|
16336
16357
|
const definition = walk.resources[logicalId];
|
|
16337
|
-
return isPlainObject$2(definition) && definition["Type"] === NESTED_STACK_TYPE$
|
|
16358
|
+
return isPlainObject$2(definition) && definition["Type"] === NESTED_STACK_TYPE$3;
|
|
16338
16359
|
}
|
|
16339
16360
|
function getAttAttribute(operand, target) {
|
|
16340
16361
|
if (Array.isArray(operand)) return operand.length === 2 && typeof operand[1] === "string" ? operand[1] : void 0;
|
|
@@ -21381,13 +21402,13 @@ function resolvesReference(desired, previous, mask) {
|
|
|
21381
21402
|
rest = rest.slice(at + token.length);
|
|
21382
21403
|
}
|
|
21383
21404
|
literals.push(rest);
|
|
21384
|
-
const pattern = literals.map(escapeRegExp).join("[\\s\\S]*");
|
|
21405
|
+
const pattern = literals.map(escapeRegExp$1).join("[\\s\\S]*");
|
|
21385
21406
|
return new RegExp(`^${pattern}$`).test(desired);
|
|
21386
21407
|
}
|
|
21387
21408
|
function isPlainObject$1(value) {
|
|
21388
21409
|
return typeof value === "object" && value !== null && !Array.isArray(value);
|
|
21389
21410
|
}
|
|
21390
|
-
function escapeRegExp(text) {
|
|
21411
|
+
function escapeRegExp$1(text) {
|
|
21391
21412
|
return text.replace(/[.*+?^${}()|[\]\\]/g, "\\$&");
|
|
21392
21413
|
}
|
|
21393
21414
|
|
|
@@ -21795,7 +21816,10 @@ function isCcConflict(error) {
|
|
|
21795
21816
|
}
|
|
21796
21817
|
var CloudControlProvider = class {
|
|
21797
21818
|
cloudControlClient;
|
|
21798
|
-
|
|
21819
|
+
baseLogger = getLogger().child("CloudControlProvider");
|
|
21820
|
+
get logger() {
|
|
21821
|
+
return idLogScope.getStore() ?? this.baseLogger;
|
|
21822
|
+
}
|
|
21799
21823
|
patchGenerator = new JsonPatchGenerator();
|
|
21800
21824
|
warnedUnresolvableSchemaTypes = /* @__PURE__ */ new Set();
|
|
21801
21825
|
protectionFlips = new ProtectionFlipRegistry();
|
|
@@ -21810,7 +21834,12 @@ var CloudControlProvider = class {
|
|
|
21810
21834
|
const awsClients = getAwsClients();
|
|
21811
21835
|
this.cloudControlClient = awsClients.cloudControl;
|
|
21812
21836
|
}
|
|
21813
|
-
async create(logicalId, resourceType, properties) {
|
|
21837
|
+
async create(logicalId, resourceType, properties, context) {
|
|
21838
|
+
const mask = maskerOrIdentity(context?.maskSecrets);
|
|
21839
|
+
const idLog = new IdScrubLog(this.logger, mask, holdsSecretDerivedLeaf(properties, mask));
|
|
21840
|
+
return inIdLogScope(idLog, () => this.createInIdLogScope(logicalId, resourceType, properties, idLog));
|
|
21841
|
+
}
|
|
21842
|
+
async createInIdLogScope(logicalId, resourceType, properties, idLog) {
|
|
21814
21843
|
this.logger.debug(`Creating resource ${logicalId} (${resourceType})`);
|
|
21815
21844
|
try {
|
|
21816
21845
|
const ccProperties = stringifyJsonProperties(resourceType, stripNullValues(properties));
|
|
@@ -21824,6 +21853,7 @@ var CloudControlProvider = class {
|
|
|
21824
21853
|
this.logger.debug(`Create request submitted for ${logicalId}, token: ${createResponse.ProgressEvent.RequestToken}`);
|
|
21825
21854
|
const progressEvent = await this.waitForOperation(createResponse.ProgressEvent.RequestToken, logicalId, "CREATE", resourceType);
|
|
21826
21855
|
if (!progressEvent.Identifier) throw new ProvisioningError(`Failed to create resource ${logicalId}: No physical ID returned`, resourceType, logicalId);
|
|
21856
|
+
idLog.addId(progressEvent.Identifier);
|
|
21827
21857
|
this.logger.debug(`Created resource ${logicalId}, physical ID: ${progressEvent.Identifier}`);
|
|
21828
21858
|
const result = { physicalId: progressEvent.Identifier };
|
|
21829
21859
|
if (progressEvent.ResourceModel) result.attributes = this.parseResourceModel(progressEvent.ResourceModel);
|
|
@@ -21831,6 +21861,7 @@ var CloudControlProvider = class {
|
|
|
21831
21861
|
result.attributes = await this.enrichResourceAttributes(resourceType, progressEvent.Identifier, result.attributes);
|
|
21832
21862
|
return result;
|
|
21833
21863
|
} catch (error) {
|
|
21864
|
+
idLog.addId(identifierCarriedBy(error));
|
|
21834
21865
|
await this.cleanupFailedCreateRemnant(error, resourceType, logicalId);
|
|
21835
21866
|
this.handleError(error, "CREATE", resourceType, logicalId);
|
|
21836
21867
|
}
|
|
@@ -21851,7 +21882,10 @@ var CloudControlProvider = class {
|
|
|
21851
21882
|
} catch (cleanupError) {
|
|
21852
21883
|
const message = cleanupError instanceof Error ? cleanupError.message : String(cleanupError);
|
|
21853
21884
|
if (isWaitAbandonedError(cleanupError)) {
|
|
21854
|
-
|
|
21885
|
+
const line = `Could not confirm whether the remnant ${error.physicalId} left by the failed CREATE of ${logicalId} was removed (a retry may fail with AlreadyExists until it is removed manually): ${displaySafe(message)}`;
|
|
21886
|
+
const log = this.logger;
|
|
21887
|
+
if (log instanceof IdScrubLog) log.warnKeepingResume(line, abandonedRequestTokens(cleanupError));
|
|
21888
|
+
else log.warn(line);
|
|
21855
21889
|
return;
|
|
21856
21890
|
}
|
|
21857
21891
|
if (isNotFoundMessage(message)) {
|
|
@@ -21862,7 +21896,12 @@ var CloudControlProvider = class {
|
|
|
21862
21896
|
}
|
|
21863
21897
|
}
|
|
21864
21898
|
async update(logicalId, physicalId, resourceType, properties, previousProperties, context) {
|
|
21865
|
-
const
|
|
21899
|
+
const mask = maskerOrIdentity(context?.maskSecrets);
|
|
21900
|
+
const idLog = new IdScrubLog(this.logger, mask, holdsSecretDerivedLeaf(properties, mask) || holdsSecretDerivedLeaf(previousProperties, mask));
|
|
21901
|
+
idLog.addId(physicalId);
|
|
21902
|
+
return inIdLogScope(idLog, () => this.updateInIdLogScope(logicalId, physicalId, resourceType, properties, previousProperties, context, idLog));
|
|
21903
|
+
}
|
|
21904
|
+
async updateInIdLogScope(logicalId, physicalId, resourceType, properties, previousProperties, context, idLog) {
|
|
21866
21905
|
idLog.debug(`Updating resource ${logicalId} (${resourceType}), physical ID: ${physicalId}`);
|
|
21867
21906
|
await this.assertRecordedRegionAgainstClient("pre-update", context?.expectedRegion, resourceType, logicalId, physicalId);
|
|
21868
21907
|
try {
|
|
@@ -21936,26 +21975,41 @@ var CloudControlProvider = class {
|
|
|
21936
21975
|
this.handleError(error, "UPDATE", resourceType, logicalId, physicalId);
|
|
21937
21976
|
}
|
|
21938
21977
|
}
|
|
21939
|
-
async delete(logicalId, physicalId, resourceType,
|
|
21978
|
+
async delete(logicalId, physicalId, resourceType, properties, context) {
|
|
21979
|
+
const mask = maskerOrIdentity(void 0);
|
|
21980
|
+
const idLog = new IdScrubLog(this.logger, mask, holdsSecretDerivedLeaf(properties, mask));
|
|
21981
|
+
idLog.addId(physicalId);
|
|
21982
|
+
const result = await inIdLogScope(idLog, () => this.deleteInIdLogScope(logicalId, physicalId, resourceType, properties, context));
|
|
21983
|
+
if (!idLog.withheld || !result) return result;
|
|
21984
|
+
return {
|
|
21985
|
+
...result,
|
|
21986
|
+
...result.outcome === "skipped" && { reason: idLog.scrub(result.reason) },
|
|
21987
|
+
...Array.isArray(result.indeterminateGuards) && { indeterminateGuards: result.indeterminateGuards.map((guard) => ({
|
|
21988
|
+
...guard,
|
|
21989
|
+
reason: idLog.scrub(guard.reason)
|
|
21990
|
+
})) }
|
|
21991
|
+
};
|
|
21992
|
+
}
|
|
21993
|
+
async deleteInIdLogScope(logicalId, physicalId, resourceType, properties, context) {
|
|
21940
21994
|
this.logger.debug(`Deleting resource ${logicalId} (${resourceType}), physical ID: ${physicalId}`);
|
|
21941
21995
|
if (context?.finalSnapshotIdentifier !== void 0) throw new ProvisioningError(`${logicalId} (${resourceType}) requires a final snapshot (DeletionPolicy: Snapshot), but the Cloud Control API delete route has no final-snapshot parameter. Re-run with --skip-final-snapshot after snapshotting manually, or retain the resource.`, resourceType, logicalId, physicalId);
|
|
21942
21996
|
await this.assertRecordedRegionAgainstClient("pre-delete", context?.expectedRegion, resourceType, logicalId, physicalId);
|
|
21943
21997
|
const indeterminateGuard = await this.confirmDeleteTargetIdentity(logicalId, resourceType, physicalId, context);
|
|
21944
21998
|
if (context?.removeProtection === true && resourceType === "AWS::AutoScaling::AutoScalingGroup") {
|
|
21945
21999
|
this.logger.debug(`Delegating protected AutoScalingGroup ${logicalId} delete to the SDK ASGProvider (Cloud Control cannot force-delete a protected ASG)`);
|
|
21946
|
-
const { ASGProvider } = await import("./asg-provider-
|
|
22000
|
+
const { ASGProvider } = await import("./asg-provider-AVCcoXnQ.js");
|
|
21947
22001
|
const delegateRegion = ambientRegion();
|
|
21948
22002
|
let asgProvider = this.asgDeleteDelegates.get(delegateRegion);
|
|
21949
22003
|
if (asgProvider === void 0) {
|
|
21950
22004
|
asgProvider = new ASGProvider();
|
|
21951
22005
|
this.asgDeleteDelegates.set(delegateRegion, asgProvider);
|
|
21952
22006
|
}
|
|
21953
|
-
return withIndeterminateGuard(await asgProvider.delete(logicalId, physicalId, resourceType,
|
|
22007
|
+
return withIndeterminateGuard(await asgProvider.delete(logicalId, physicalId, resourceType, properties, context), indeterminateGuard);
|
|
21954
22008
|
}
|
|
21955
22009
|
if ((context?.deletionPolicy === "Delete" || context?.skipFinalSnapshot === true) && SDK_DELETE_FAMILIES.has(resourceType)) {
|
|
21956
|
-
if (deletesThroughSdkProvider(resourceType,
|
|
22010
|
+
if (deletesThroughSdkProvider(resourceType, properties)) {
|
|
21957
22011
|
const delegate = await this.sdkDeleteDelegateInCcRegion(resourceType, logicalId, physicalId);
|
|
21958
|
-
return withIndeterminateGuard(await delegate.delete(logicalId, physicalId, resourceType,
|
|
22012
|
+
return withIndeterminateGuard(await delegate.delete(logicalId, physicalId, resourceType, properties, context), indeterminateGuard);
|
|
21959
22013
|
}
|
|
21960
22014
|
this.logger.warn(safeMsg`${logicalId} (${resourceType}) records a GlobalClusterIdentifier cdkd cannot detach it from, so it is deleted through ` + `Cloud Control, which handles the global-cluster membership. Its handler ` + safeMsg`can take a manual final snapshot of ${physicalId}, which cdkd does not record; ` + `delete it yourself if you do not want it.`);
|
|
21961
22015
|
}
|
|
@@ -22049,7 +22103,7 @@ var CloudControlProvider = class {
|
|
|
22049
22103
|
const family = SDK_DELETE_FAMILIES.get(resourceType);
|
|
22050
22104
|
const cached = this.sdkDeleteDelegates.get(family);
|
|
22051
22105
|
if (cached !== void 0 && cached.region === ccRegion) return cached.provider;
|
|
22052
|
-
const provider = family === "rds" ? new (await (import("./rds-provider-
|
|
22106
|
+
const provider = family === "rds" ? new (await (import("./rds-provider-DltlcDiQ.js"))).RDSProvider({ region: ccRegion }) : new (await (import("./neptune-provider-D1t9NgT-.js"))).NeptuneProvider({ region: ccRegion });
|
|
22053
22107
|
this.sdkDeleteDelegates.set(family, {
|
|
22054
22108
|
region: ccRegion,
|
|
22055
22109
|
provider
|
|
@@ -22752,20 +22806,94 @@ var CloudControlProvider = class {
|
|
|
22752
22806
|
return masked;
|
|
22753
22807
|
}
|
|
22754
22808
|
};
|
|
22755
|
-
|
|
22756
|
-
|
|
22757
|
-
|
|
22758
|
-
|
|
22759
|
-
|
|
22760
|
-
|
|
22761
|
-
|
|
22762
|
-
|
|
22763
|
-
|
|
22764
|
-
|
|
22765
|
-
|
|
22809
|
+
var IdScrubLog = class {
|
|
22810
|
+
needles = [];
|
|
22811
|
+
base;
|
|
22812
|
+
mask;
|
|
22813
|
+
evidence;
|
|
22814
|
+
constructor(base, mask, evidence) {
|
|
22815
|
+
this.base = base;
|
|
22816
|
+
this.mask = mask;
|
|
22817
|
+
this.evidence = evidence;
|
|
22818
|
+
}
|
|
22819
|
+
get withheld() {
|
|
22820
|
+
return this.needles.length > 0;
|
|
22821
|
+
}
|
|
22822
|
+
addId(id) {
|
|
22823
|
+
if (!this.evidence || id === void 0 || id === "") return;
|
|
22824
|
+
const parts = [id, ...id.split("|")].filter((needle) => needle !== "");
|
|
22825
|
+
const raw = [...new Set(parts.flatMap((part) => [
|
|
22826
|
+
part,
|
|
22827
|
+
displaySafe(part),
|
|
22828
|
+
displaySafe(part, { asciiOnly: true })
|
|
22829
|
+
]))].filter((needle) => needle !== "" && needle !== "***");
|
|
22830
|
+
const masked = raw.map((needle) => this.mask(needle));
|
|
22831
|
+
this.needles = [.../* @__PURE__ */ new Set([
|
|
22832
|
+
...this.needles,
|
|
22833
|
+
...raw,
|
|
22834
|
+
...masked.filter((m, i) => m !== "" && m !== raw[i] && m !== "***")
|
|
22835
|
+
])].sort((a, b) => b.length - a.length);
|
|
22836
|
+
}
|
|
22837
|
+
scrub = (text) => this.needles.reduce((out, needle) => out.split(needle).join("***"), this.mask(text));
|
|
22838
|
+
scrubKeepingResume(text, requestTokens) {
|
|
22839
|
+
const tokens = requestTokens.filter((token) => token !== "");
|
|
22840
|
+
if (tokens.length === 0) return this.scrub(text);
|
|
22841
|
+
const keep = new RegExp(`(${[RESUME_COMMAND.source, ...tokens.map(escapeRegExp)].join("|")})`);
|
|
22842
|
+
return text.split(keep).map((segment, i) => i % 2 === 1 ? this.mask(segment) : this.scrub(segment)).join("");
|
|
22843
|
+
}
|
|
22844
|
+
scrubError(error) {
|
|
22845
|
+
if (this.needles.length === 0 || !(error instanceof Error)) return error;
|
|
22846
|
+
const original = errorCauseChain(error);
|
|
22847
|
+
const tokens = abandonedRequestTokens(error);
|
|
22848
|
+
const scrubbed = maskSecretsInError(error, /* @__PURE__ */ new Map(), (text) => this.scrubKeepingResume(text, tokens));
|
|
22849
|
+
const clones = errorCauseChain(scrubbed);
|
|
22850
|
+
original.forEach((link, i) => {
|
|
22851
|
+
const clone = clones[i];
|
|
22852
|
+
if (clone === void 0 || clone === link) return;
|
|
22853
|
+
for (const key of VERBATIM_ERROR_FIELDS) {
|
|
22854
|
+
const descriptor = Object.getOwnPropertyDescriptor(link, key);
|
|
22855
|
+
if (descriptor === void 0 || typeof descriptor.value !== "string") continue;
|
|
22856
|
+
try {
|
|
22857
|
+
Object.defineProperty(clone, key, descriptor);
|
|
22858
|
+
} catch {}
|
|
22859
|
+
}
|
|
22860
|
+
});
|
|
22861
|
+
return scrubbed;
|
|
22862
|
+
}
|
|
22863
|
+
warnKeepingResume(message, requestTokens) {
|
|
22864
|
+
this.base.warn(this.scrubKeepingResume(message, requestTokens));
|
|
22865
|
+
}
|
|
22866
|
+
debug(message) {
|
|
22867
|
+
this.base.debug(this.scrub(message));
|
|
22868
|
+
}
|
|
22869
|
+
info(message) {
|
|
22870
|
+
this.base.info(this.scrub(message));
|
|
22871
|
+
}
|
|
22872
|
+
warn(message) {
|
|
22873
|
+
this.base.warn(this.scrub(message));
|
|
22874
|
+
}
|
|
22875
|
+
error(message) {
|
|
22876
|
+
this.base.error(this.scrub(message));
|
|
22877
|
+
}
|
|
22878
|
+
};
|
|
22879
|
+
const VERBATIM_ERROR_FIELDS = ["logicalId", "resourceType"];
|
|
22880
|
+
function escapeRegExp(text) {
|
|
22881
|
+
return text.replace(/[.*+?^${}()|[\]\\]/g, "\\$&");
|
|
22882
|
+
}
|
|
22883
|
+
const RESUME_COMMAND = /aws(?: --profile (?:'(?:[^'\n]|'\\'')*'|\S+))? cloudcontrol get-resource-request-status --request-token \S+(?: --region \S+)?/;
|
|
22884
|
+
function abandonedRequestTokens(error) {
|
|
22885
|
+
return error instanceof Error ? errorCauseChain(error).flatMap((link) => link instanceof CloudControlWaitAbandonedError ? [link.requestToken] : []) : [];
|
|
22886
|
+
}
|
|
22887
|
+
const idLogScope = new AsyncLocalStorage();
|
|
22888
|
+
async function inIdLogScope(idLog, fn) {
|
|
22889
|
+
try {
|
|
22890
|
+
return await idLogScope.run(idLog, fn);
|
|
22891
|
+
} catch (error) {
|
|
22892
|
+
throw idLog.scrubError(error);
|
|
22893
|
+
}
|
|
22766
22894
|
}
|
|
22767
|
-
function
|
|
22768
|
-
return
|
|
22895
|
+
function identifierCarriedBy(error) {
|
|
22896
|
+
return error instanceof ProvisioningError ? error.physicalId : void 0;
|
|
22769
22897
|
}
|
|
22770
22898
|
function holdsSecretDerivedLeaf(value, mask, depth = 0) {
|
|
22771
22899
|
if (typeof value === "string") return isSecretDerivedValue(value, mask);
|
|
@@ -22874,8 +23002,34 @@ const CR_MASKED_SERVICE_TOKEN_SKIP_REASON = "masked ServiceToken in state — De
|
|
|
22874
23002
|
const CR_REFERENCE_SERVICE_TOKEN_SKIP_REASON = "dynamic reference as ServiceToken in state — handler not invoked";
|
|
22875
23003
|
const CR_DELETE_INVOKE_FAILED_SKIP_REASON = "Delete request to the handler did not complete — resource unproven";
|
|
22876
23004
|
const CR_DELETE_HANDLER_FAILED_SKIP_REASON = "Delete handler reported FAILED — resource unproven";
|
|
22877
|
-
const
|
|
23005
|
+
const CR_BACKING_LAMBDA_GONE_SKIP_REASON = "backing Lambda function is gone — Delete handler not invoked";
|
|
23006
|
+
function crSkipNotARetryCaveat(context, logicalId) {
|
|
23007
|
+
return `NOTE this record is a POINTER, not a retry: the same destroy run deletes the backing Lambda, so the next 'cdkd destroy' cannot reach the handler either: it skips this resource again and keeps the record (issue 2115). Tear the resource down by hand, then drop the record with ${stateOrphanRecordRemedy(context, logicalId)}.`;
|
|
23008
|
+
}
|
|
22878
23009
|
const DEPLOY_SKIP_CAVEAT = "NOTE this arm is ALSO reached from cdkd deploy. Since issue 1762 the DELETE of a resource removed from the template behaves like destroy — the record is KEPT and the next deploy re-attempts it — but a REPLACEMENT / rollback delete FAILS the resource instead (https://github.com/go-to-k/cdkd/issues/1762), leaving the old one untracked; there, tear the resource down by hand.";
|
|
23010
|
+
function crDeployNoStateOrphan(logicalId) {
|
|
23011
|
+
return `For a resource removed from the template, to give up on the delete and stop tracking it, drop the record with ${stateOrphanRecordRemedy(void 0, logicalId)}.`;
|
|
23012
|
+
}
|
|
23013
|
+
function crDeploySkipTail(logicalId) {
|
|
23014
|
+
return "Meanwhile 'cdkd deploy --allow-unaddressed' exits 0 (a deploy-only flag; 'cdkd rollback' has none); the record stays and each deploy re-attempts the delete. A delete-first REPLACEMENT or a rollback delete usually FAILS the resource and keeps the record (https://github.com/go-to-k/cdkd/issues/1762). Where the other copy already exists (a replacement that created the new resource first, or a rollback that re-created the old one first), the skip only warns and the surviving copy is no longer tracked, so tear it down by hand. " + crDeployNoStateOrphan(logicalId);
|
|
23015
|
+
}
|
|
23016
|
+
const CR_DEPLOY_HANDLER_SKIP_HEAD = "This delete is not part of a stack destroy (a 'cdkd deploy' template removal, replacement or rollback, or a 'cdkd rollback'). For a resource removed from the template the record is KEPT and the next 'cdkd deploy' re-sends the Delete: fix what made it fail (the handler's Delete logic, or what stopped the invoke) and re-deploy. That reaches the handler only while its function exists: if this deploy also deleted the backing Lambda, the next deploy finds it gone and DROPS the record with a warning, so tear down what the handler manages by hand. ";
|
|
23017
|
+
const CR_DEPLOY_UNADDRESSABLE_HEAD = "This delete is not part of a stack destroy (a 'cdkd deploy' template removal, replacement or rollback, or a 'cdkd rollback'). For a resource removed from the template the record is KEPT and every 'cdkd deploy' skips it again until ServiceToken is restored: put the provider's Lambda function or SNS topic ARN back in state.json and re-deploy, which sends the Delete while that handler exists. If its Lambda function is gone, that deploy DROPS the record with a warning instead, so tear down what the handler manages by hand. ";
|
|
23018
|
+
function crDestroyUnaddressableRemedy(context, logicalId) {
|
|
23019
|
+
return `Tear the resource down by hand, then drop the record with ${stateOrphanRecordRemedy(context, logicalId)}. Restoring ServiceToken (the provider's Lambda function or SNS topic ARN) in state.json and re-running helps only while that handler still exists: a destroy goes on to delete its backing Lambda.`;
|
|
23020
|
+
}
|
|
23021
|
+
function handlerSkipRemedy(context, logicalId) {
|
|
23022
|
+
return context?.stackDestroy === true ? ` — cdkd is KEEPING the state record and the run exits non-zero. ${crSkipNotARetryCaveat(context, logicalId)}` : `. ${CR_DEPLOY_HANDLER_SKIP_HEAD}${crDeploySkipTail(logicalId)}`;
|
|
23023
|
+
}
|
|
23024
|
+
function crUnresolvedTokenUpdateRemedy() {
|
|
23025
|
+
return "This indicates an unresolved value in the template, or, on a rollback, in the resource's recorded state. Check that the template resolves ServiceToken to the provider's Lambda function or SNS topic ARN and re-deploy; a rollback replays the recorded value, so restore the template and re-deploy instead. Do not drop this record with 'cdkd state orphan', with or without --resource: the template still declares the resource, so the next deploy would send the handler a fresh Create and leave what it already manages untracked.";
|
|
23026
|
+
}
|
|
23027
|
+
function unresolvedTokenDeleteRemedy(context, logicalId) {
|
|
23028
|
+
return context?.stackDestroy === true ? `re-run 'cdkd import', or drop the record with ${stateOrphanRecordRemedy(context, logicalId)}, to recover.` : `put the provider's Lambda function or SNS topic ARN back as ServiceToken in state.json and re-run to recover. ${crDeployNoStateOrphan(logicalId)}`;
|
|
23029
|
+
}
|
|
23030
|
+
function unaddressableServiceTokenRemedy(context, logicalId) {
|
|
23031
|
+
return context?.stackDestroy === true ? crDestroyUnaddressableRemedy(context, logicalId) : `${CR_DEPLOY_UNADDRESSABLE_HEAD}${crDeploySkipTail(logicalId)}`;
|
|
23032
|
+
}
|
|
22879
23033
|
function isCustomResourceResponsePayload(value) {
|
|
22880
23034
|
if (typeof value !== "object" || value === null) return false;
|
|
22881
23035
|
const payload = value;
|
|
@@ -23218,7 +23372,7 @@ var CustomResourceProvider = class CustomResourceProvider {
|
|
|
23218
23372
|
this.logger.debug(`Creating custom resource ${logicalId} (${resourceType})`);
|
|
23219
23373
|
const serviceToken = properties["ServiceToken"];
|
|
23220
23374
|
if (!serviceToken) throw new ProvisioningError(`ServiceToken is required for custom resource ${logicalId}`, resourceType, logicalId);
|
|
23221
|
-
if (typeof serviceToken !== "string") throw new ProvisioningError(`Custom Resource ${logicalId}: ServiceToken is not a resolved string ARN (got ${typeof serviceToken}). This
|
|
23375
|
+
if (typeof serviceToken !== "string") throw new ProvisioningError(`Custom Resource ${logicalId}: ServiceToken is not a resolved string ARN (got ${typeof serviceToken}). This indicates an unresolved value in the template, or, on a rollback, in the resource's recorded state. Check that the template resolves ServiceToken to the provider's Lambda function or SNS topic ARN; a rollback replays the recorded value, so restore the template and re-deploy instead.`, resourceType, logicalId);
|
|
23222
23376
|
this.refuseResolvedSecret(logicalId, resourceType, properties);
|
|
23223
23377
|
try {
|
|
23224
23378
|
const cfnResponse = await this.invokeCustomResourceWithRetry(serviceToken, logicalId, "Create", (invocation) => ({
|
|
@@ -23249,7 +23403,7 @@ var CustomResourceProvider = class CustomResourceProvider {
|
|
|
23249
23403
|
this.logger.debug(`Updating custom resource ${logicalId}: ${physicalId} (${resourceType})`);
|
|
23250
23404
|
const serviceToken = properties["ServiceToken"];
|
|
23251
23405
|
if (!serviceToken) throw new ProvisioningError(`ServiceToken is required for custom resource ${logicalId}`, resourceType, logicalId, physicalId);
|
|
23252
|
-
if (typeof serviceToken !== "string") throw new ProvisioningError(`Custom Resource ${logicalId}: ServiceToken is not a resolved string ARN (got ${typeof serviceToken}).
|
|
23406
|
+
if (typeof serviceToken !== "string") throw new ProvisioningError(`Custom Resource ${logicalId}: ServiceToken is not a resolved string ARN (got ${typeof serviceToken}). ` + crUnresolvedTokenUpdateRemedy(), resourceType, logicalId, physicalId);
|
|
23253
23407
|
this.refuseResolvedSecret(logicalId, resourceType, properties, physicalId, previousProperties);
|
|
23254
23408
|
try {
|
|
23255
23409
|
const cfnResponse = await this.invokeCustomResourceWithRetry(serviceToken, logicalId, "Update", (invocation) => ({
|
|
@@ -23279,7 +23433,7 @@ var CustomResourceProvider = class CustomResourceProvider {
|
|
|
23279
23433
|
throw new ProvisioningError(`Failed to update custom resource ${logicalId}: ${error instanceof Error ? error.message : String(error)}`, resourceType, logicalId, physicalId, cause);
|
|
23280
23434
|
}
|
|
23281
23435
|
}
|
|
23282
|
-
async delete(logicalId, physicalId, resourceType, properties,
|
|
23436
|
+
async delete(logicalId, physicalId, resourceType, properties, context) {
|
|
23283
23437
|
this.logger.debug(`Deleting custom resource ${logicalId}: ${physicalId} (${resourceType})`);
|
|
23284
23438
|
if (!properties) {
|
|
23285
23439
|
this.logger.warn(`No properties available for custom resource ${logicalId}, skipping deletion — the handler is never invoked, so anything this custom resource manages is LEFT IN PLACE. Restore the record's properties in state.json and re-run, or tear the resource down by hand. ${DEPLOY_SKIP_CAVEAT}`);
|
|
@@ -23296,23 +23450,30 @@ var CustomResourceProvider = class CustomResourceProvider {
|
|
|
23296
23450
|
reason: CR_NO_SERVICE_TOKEN_SKIP_REASON
|
|
23297
23451
|
};
|
|
23298
23452
|
}
|
|
23299
|
-
if (typeof serviceToken !== "string") throw new ProvisioningError(`Custom Resource ${logicalId}: ServiceToken is not a resolved string ARN (got ${typeof serviceToken}). This usually indicates state was written by a pre-fix cdkd import;
|
|
23453
|
+
if (typeof serviceToken !== "string") throw new ProvisioningError(`Custom Resource ${logicalId}: ServiceToken is not a resolved string ARN (got ${typeof serviceToken}). This usually indicates state was written by a pre-fix cdkd import; ` + unresolvedTokenDeleteRemedy(context, logicalId), resourceType, logicalId, physicalId);
|
|
23300
23454
|
if (carriesSecretMask(serviceToken)) {
|
|
23301
|
-
this.logger.warn(safeMsg`ServiceToken for custom resource ${logicalId} is recorded in state as the redaction ` + safeMsg`mask '${"***"}' (a NoEcho value this resource reads equals, or is contained ` + "in, its ServiceToken), so cdkd cannot address the handler; skipping deletion — anything this custom resource manages is LEFT IN PLACE. Re-deploying does not repair the record while that attribute still carries the value.
|
|
23455
|
+
this.logger.warn(safeMsg`ServiceToken for custom resource ${logicalId} is recorded in state as the redaction ` + safeMsg`mask '${"***"}' (a NoEcho value this resource reads equals, or is contained ` + "in, its ServiceToken), so cdkd cannot address the handler; skipping deletion — anything this custom resource manages is LEFT IN PLACE. Re-deploying does not repair the record while that attribute still carries the value. " + safeMsg`${unaddressableServiceTokenRemedy(context, logicalId)}`);
|
|
23302
23456
|
return {
|
|
23303
23457
|
outcome: "skipped",
|
|
23304
23458
|
reason: CR_MASKED_SERVICE_TOKEN_SKIP_REASON
|
|
23305
23459
|
};
|
|
23306
23460
|
}
|
|
23307
23461
|
if (dynamicReferenceTokens(serviceToken).length > 0) {
|
|
23308
|
-
this.logger.warn(safeMsg`ServiceToken for custom resource ${logicalId} is recorded in state as a ` + "'{{resolve:...}}' dynamic reference, which cdkd does not resolve on delete, so it cannot address the handler; skipping deletion — anything this custom resource manages is LEFT IN PLACE. CloudFormation does not support secure (secretsmanager / ssm-secure) dynamic references in custom resources, and cdkd now refuses such a template at deploy time.
|
|
23462
|
+
this.logger.warn(safeMsg`ServiceToken for custom resource ${logicalId} is recorded in state as a ` + "'{{resolve:...}}' dynamic reference, which cdkd does not resolve on delete, so it cannot address the handler; skipping deletion — anything this custom resource manages is LEFT IN PLACE. CloudFormation does not support secure (secretsmanager / ssm-secure) dynamic references in custom resources, and cdkd now refuses such a template at deploy time. " + safeMsg`${unaddressableServiceTokenRemedy(context, logicalId)}`);
|
|
23309
23463
|
return {
|
|
23310
23464
|
outcome: "skipped",
|
|
23311
23465
|
reason: CR_REFERENCE_SERVICE_TOKEN_SKIP_REASON
|
|
23312
23466
|
};
|
|
23313
23467
|
}
|
|
23314
23468
|
if (!this.isSnsServiceToken(serviceToken) && await this.isBackingLambdaGone(serviceToken)) {
|
|
23315
|
-
|
|
23469
|
+
if (context?.stackDestroy === true) {
|
|
23470
|
+
this.logger.warn(safeMsg`Backing Lambda for custom resource ${logicalId} no longer exists (${serviceToken}), so ` + "its Delete handler cannot be invoked and cdkd cannot confirm the resource was deleted; skipping deletion — anything this custom resource manages may still be LIVE. cdkd is KEEPING the state record and the run exits non-zero, as CloudFormation leaves such a stack DELETE_FAILED. A re-run skips it again unless a function with that exact ARN exists again (e.g. a shared provider stack destroyed before this one, then redeployed). Otherwise confirm by hand that whatever it manages is gone (or tear it down), then drop the record with " + safeMsg`${stateOrphanRecordRemedy(context, logicalId)}.`);
|
|
23471
|
+
return {
|
|
23472
|
+
outcome: "skipped",
|
|
23473
|
+
reason: CR_BACKING_LAMBDA_GONE_SKIP_REASON
|
|
23474
|
+
};
|
|
23475
|
+
}
|
|
23476
|
+
this.logger.warn(safeMsg`Backing Lambda for custom resource ${logicalId} no longer exists (${serviceToken}); ` + "treating the custom resource as already deleted and DROPPING its state record, as CloudFormation ignores a delete failure in an update's cleanup phase. The handler can never run again, so if its teardown was never PROVEN, whatever it manages may still be LIVE and is now untracked by cdkd. Check for leftovers by hand.");
|
|
23316
23477
|
return;
|
|
23317
23478
|
}
|
|
23318
23479
|
try {
|
|
@@ -23327,7 +23488,7 @@ var CustomResourceProvider = class CustomResourceProvider {
|
|
|
23327
23488
|
ResourceProperties: this.stringifyProperties(properties)
|
|
23328
23489
|
}), DELETE_PATH_UNMASKED);
|
|
23329
23490
|
if (cfnResponse.Status === "FAILED") {
|
|
23330
|
-
this.logger.warn(`Custom resource delete handler returned FAILED for ${logicalId}: ${cfnResponse.Reason || "Unknown reason"}. The handler reported that it did NOT delete, so anything this custom resource manages is LEFT IN PLACE
|
|
23491
|
+
this.logger.warn(`Custom resource delete handler returned FAILED for ${logicalId}: ${cfnResponse.Reason || "Unknown reason"}. The handler reported that it did NOT delete, so anything this custom resource manages is LEFT IN PLACE${handlerSkipRemedy(context, logicalId)}`);
|
|
23331
23492
|
return {
|
|
23332
23493
|
outcome: "skipped",
|
|
23333
23494
|
reason: CR_DELETE_HANDLER_FAILED_SKIP_REASON
|
|
@@ -23335,7 +23496,7 @@ var CustomResourceProvider = class CustomResourceProvider {
|
|
|
23335
23496
|
}
|
|
23336
23497
|
this.logger.debug(`Successfully deleted custom resource ${logicalId}`);
|
|
23337
23498
|
} catch (error) {
|
|
23338
|
-
this.logger.warn(`Failed to delete custom resource ${logicalId}, but continuing: ${describeAwsFailure(error).detail}. The Delete handler did not complete, so anything this custom resource manages may still be LIVE
|
|
23499
|
+
this.logger.warn(`Failed to delete custom resource ${logicalId}, but continuing: ${describeAwsFailure(error).detail}. The Delete handler did not complete, so anything this custom resource manages may still be LIVE${handlerSkipRemedy(context, logicalId)}`);
|
|
23339
23500
|
return {
|
|
23340
23501
|
outcome: "skipped",
|
|
23341
23502
|
reason: CR_DELETE_INVOKE_FAILED_SKIP_REASON
|
|
@@ -26283,6 +26444,81 @@ function ownPoliciesChange(change) {
|
|
|
26283
26444
|
return (change?.propertyChanges ?? []).some((c) => c.path === "Policies" && c.inPlacePropagated !== true && c.replacementPropagated !== true);
|
|
26284
26445
|
}
|
|
26285
26446
|
|
|
26447
|
+
//#endregion
|
|
26448
|
+
//#region src/analyzer/destructive-changes.ts
|
|
26449
|
+
const IGNORED_RESOURCE_TYPES = /* @__PURE__ */ new Set(["AWS::CDK::Metadata"]);
|
|
26450
|
+
const PATH_METADATA_KEY = "aws:cdk:path";
|
|
26451
|
+
function findDestructiveChanges(stackName, changes, records, template, recreateTargets = /* @__PURE__ */ new Set()) {
|
|
26452
|
+
const found = [];
|
|
26453
|
+
for (const change of changes) {
|
|
26454
|
+
const record = Object.hasOwn(records, change.logicalId) ? records[change.logicalId] : void 0;
|
|
26455
|
+
const resourceType = record?.resourceType ?? change.resourceType;
|
|
26456
|
+
if (IGNORED_RESOURCE_TYPES.has(resourceType) || IGNORED_RESOURCE_TYPES.has(change.resourceType)) continue;
|
|
26457
|
+
const impact = change.changeType === "UPDATE" && recreateTargets.has(change.logicalId) ? "WILL_REPLACE" : destructiveImpactOf(change, record);
|
|
26458
|
+
if (impact === void 0) continue;
|
|
26459
|
+
const recorded = typeof record?.constructPath === "string" ? record.constructPath : void 0;
|
|
26460
|
+
const constructPath = constructPathOf(template, change.logicalId) ?? recorded;
|
|
26461
|
+
found.push({
|
|
26462
|
+
stackName,
|
|
26463
|
+
logicalId: change.logicalId,
|
|
26464
|
+
resourceType,
|
|
26465
|
+
...constructPath !== void 0 && { constructPath },
|
|
26466
|
+
impact
|
|
26467
|
+
});
|
|
26468
|
+
}
|
|
26469
|
+
return found;
|
|
26470
|
+
}
|
|
26471
|
+
function destructiveImpactOf(change, record) {
|
|
26472
|
+
switch (change.changeType) {
|
|
26473
|
+
case "DELETE": return shouldRetainResource(record?.deletionPolicy) ? "WILL_ORPHAN" : "WILL_DESTROY";
|
|
26474
|
+
case "UPDATE": {
|
|
26475
|
+
if (record !== void 0 && record.resourceType !== change.resourceType) return "WILL_REPLACE";
|
|
26476
|
+
let mayReplace = false;
|
|
26477
|
+
for (const pc of change.propertyChanges ?? []) {
|
|
26478
|
+
if (!pc.requiresReplacement) continue;
|
|
26479
|
+
if (pc.inPlacePropagated === true || pc.replacementPropagated === true) mayReplace = true;
|
|
26480
|
+
else return "WILL_REPLACE";
|
|
26481
|
+
}
|
|
26482
|
+
return mayReplace ? "MAY_REPLACE" : void 0;
|
|
26483
|
+
}
|
|
26484
|
+
default: return;
|
|
26485
|
+
}
|
|
26486
|
+
}
|
|
26487
|
+
function constructPathOf(template, logicalId) {
|
|
26488
|
+
const resources = template?.Resources;
|
|
26489
|
+
if (resources === void 0 || !Object.hasOwn(resources, logicalId)) return void 0;
|
|
26490
|
+
const path = resources[logicalId]?.Metadata?.[PATH_METADATA_KEY];
|
|
26491
|
+
return typeof path === "string" && path !== "" ? path : void 0;
|
|
26492
|
+
}
|
|
26493
|
+
function describeDestructiveImpact(impact) {
|
|
26494
|
+
switch (impact) {
|
|
26495
|
+
case "WILL_REPLACE": return "will be replaced";
|
|
26496
|
+
case "MAY_REPLACE": return "may be replaced";
|
|
26497
|
+
case "WILL_DESTROY": return "will be destroyed";
|
|
26498
|
+
case "WILL_ORPHAN": return "will be orphaned";
|
|
26499
|
+
}
|
|
26500
|
+
}
|
|
26501
|
+
function formatDestructiveChange(change) {
|
|
26502
|
+
const path = change.constructPath !== void 0 ? `${displaySafe(displayPath(change.constructPath))} ` : "";
|
|
26503
|
+
return `${displayIdent(change.stackName)}: ${displaySafe(change.resourceType)} ${path}${displayIdent(change.logicalId)} ${describeDestructiveImpact(change.impact)}`;
|
|
26504
|
+
}
|
|
26505
|
+
function displayPath(constructPath) {
|
|
26506
|
+
let parts = constructPath.replace(/^\//, "").split("/");
|
|
26507
|
+
if (parts.length > 1) {
|
|
26508
|
+
parts = parts.slice(1);
|
|
26509
|
+
const last = parts[parts.length - 1];
|
|
26510
|
+
if (parts.length > 1 && (last === "Resource" || last === "Default")) parts = parts.slice(0, -1);
|
|
26511
|
+
}
|
|
26512
|
+
return parts.join("/");
|
|
26513
|
+
}
|
|
26514
|
+
function withConstructPath(record, path) {
|
|
26515
|
+
if (path === void 0 || record.constructPath === path) return record;
|
|
26516
|
+
return {
|
|
26517
|
+
...record,
|
|
26518
|
+
constructPath: path
|
|
26519
|
+
};
|
|
26520
|
+
}
|
|
26521
|
+
|
|
26286
26522
|
//#endregion
|
|
26287
26523
|
//#region src/deployment/masking-retry-logger.ts
|
|
26288
26524
|
function maskingRetryLogger(logger, secrets) {
|
|
@@ -27178,9 +27414,9 @@ const REDACTED_DELETE_ADDRESS_SKIP_REASON = "redacted address property in state
|
|
|
27178
27414
|
function redactedDeleteAddressFields(fields) {
|
|
27179
27415
|
return Object.keys(fields).filter((key) => isRedactedRecordedValue(fields[key]));
|
|
27180
27416
|
}
|
|
27181
|
-
function redactedDeleteAddressSkip(logger, logicalId, what, redactedFields) {
|
|
27417
|
+
function redactedDeleteAddressSkip(logger, logicalId, what, redactedFields, context) {
|
|
27182
27418
|
if (redactedFields.length === 0) return void 0;
|
|
27183
|
-
logger.warn(safeMsg`${what} ${logicalId} is recorded in state with ${redactedFields.join(", ")} ` + "redacted (the '***' mask of a NoEcho value it read, or a secret '{{resolve:...}}' reference), which names nothing in AWS; skipping deletion — no AWS call is issued, so the resource is LEFT IN PLACE unless a parent resource this run also deletes removes it (then only the record is stale). Re-deploying records the same redaction again. The state record is KEPT and the run reports the skip: on 'cdkd destroy' / 'cdkd state destroy' (which exits non-zero) and, since issue 1762, on the plain DELETE of a resource removed from the template during cdkd deploy. Remove the resource by hand, then
|
|
27419
|
+
logger.warn(safeMsg`${what} ${logicalId} is recorded in state with ${redactedFields.join(", ")} ` + "redacted (the '***' mask of a NoEcho value it read, or a secret '{{resolve:...}}' reference), which names nothing in AWS; skipping deletion — no AWS call is issued, so the resource is LEFT IN PLACE unless a parent resource this run also deletes removes it (then only the record is stale). Re-deploying records the same redaction again. The state record is KEPT and the run reports the skip: on 'cdkd destroy' / 'cdkd state destroy' (which exits non-zero) and, since issue 1762, on the plain DELETE of a resource removed from the template during cdkd deploy. Remove the resource by hand, " + safeMsg`then drop the record with ${stateOrphanRecordRemedy(context, logicalId)}. ` + "NOTE a deploy-side REPLACEMENT or rollback delete instead FAILS the resource (https://github.com/go-to-k/cdkd/issues/1762) — the old resource is left untracked there, so remove it by hand.");
|
|
27184
27420
|
return {
|
|
27185
27421
|
outcome: "skipped",
|
|
27186
27422
|
reason: REDACTED_DELETE_ADDRESS_SKIP_REASON
|
|
@@ -28154,6 +28390,15 @@ function classifyFailedOp(op, stateResources) {
|
|
|
28154
28390
|
const current = stateResources[op.logicalId];
|
|
28155
28391
|
if (op.changeType === "CREATE") {
|
|
28156
28392
|
if (!op.physicalId) return "skip-failed-unknown";
|
|
28393
|
+
if (op.physicalIdRecoveredFromError === false) return "skip-failed-superseded";
|
|
28394
|
+
if (op.physicalIdRecoveredFromError === true) {
|
|
28395
|
+
if (current) return current.physicalId === op.physicalId ? "skip-failed-noop" : "skip-failed-mismatch";
|
|
28396
|
+
if (stateHoldsPhysicalId(stateResources, op.resourceType, op.physicalId)) return "skip-failed-noop";
|
|
28397
|
+
const orphanPolicy = effectiveDeletionPolicy(op.resourceType, op.deletionPolicy, op.attemptedProperties);
|
|
28398
|
+
if (orphanPolicy === "Retain") return "orphan-failed-create-retain";
|
|
28399
|
+
if (orphanPolicy === "Snapshot") return "delete-failed-create-with-final-snapshot";
|
|
28400
|
+
return "delete-failed-create";
|
|
28401
|
+
}
|
|
28157
28402
|
if (!current) return "skip-failed-noop";
|
|
28158
28403
|
if (current.physicalId !== op.physicalId) return "skip-failed-mismatch";
|
|
28159
28404
|
const policy = effectiveDeletionPolicy(current.resourceType, current.deletionPolicy, current.properties);
|
|
@@ -28165,6 +28410,31 @@ function classifyFailedOp(op, stateResources) {
|
|
|
28165
28410
|
if (isTypeChangeOp(op)) return "skip-failed-type-change";
|
|
28166
28411
|
return "revert-failed-update";
|
|
28167
28412
|
}
|
|
28413
|
+
function stateHoldsPhysicalId(stateResources, resourceType, physicalId) {
|
|
28414
|
+
return Object.values(stateResources).some((r) => r?.resourceType === resourceType && r.physicalId === physicalId);
|
|
28415
|
+
}
|
|
28416
|
+
function demoteSupersededOrphans(segments, orphans = []) {
|
|
28417
|
+
let demoted = 0;
|
|
28418
|
+
segments.forEach((segment, s) => {
|
|
28419
|
+
for (const op of segment.failedOperations ?? []) {
|
|
28420
|
+
if (op.changeType !== "CREATE" || op.physicalIdRecoveredFromError !== true) continue;
|
|
28421
|
+
if (segments.slice(s + 1).some((t) => (t.operations ?? []).some((o) => mayOwn(o, op, true)) || (t.failedOperations ?? []).some((o) => mayOwn(o, op, false))) || segments.slice(s).some((t) => t.supersededLogicalIds?.includes(op.logicalId) === true) || orphans.some((o) => o?.logicalId === op.logicalId || o?.state?.resourceType === op.resourceType && o.state?.physicalId === op.physicalId)) {
|
|
28422
|
+
op.physicalIdRecoveredFromError = false;
|
|
28423
|
+
demoted++;
|
|
28424
|
+
}
|
|
28425
|
+
}
|
|
28426
|
+
});
|
|
28427
|
+
return demoted;
|
|
28428
|
+
}
|
|
28429
|
+
function mayOwn(o, orphan, completed) {
|
|
28430
|
+
if (o?.resourceType !== orphan.resourceType) return false;
|
|
28431
|
+
if (completed && o.changeType === "CREATE") return true;
|
|
28432
|
+
if (o.physicalId === orphan.physicalId) return true;
|
|
28433
|
+
return o.previousState?.physicalId === orphan.physicalId;
|
|
28434
|
+
}
|
|
28435
|
+
function isJournaledOrphan(op) {
|
|
28436
|
+
return op.changeType === "CREATE" && typeof op.physicalIdRecoveredFromError === "boolean";
|
|
28437
|
+
}
|
|
28168
28438
|
function planFailedOps(failedOps, stateResources) {
|
|
28169
28439
|
return failedOps.map((op) => ({
|
|
28170
28440
|
op,
|
|
@@ -28997,6 +29267,10 @@ async function replayFailedOperationsUnbound(failedOps, stateResources, stackNam
|
|
|
28997
29267
|
logger.warn(safeMsg` Rollback: Skipping failed CREATE of ${shownLogicalId(op.logicalId)} (${refusalResourceType(op.resourceType)}) — it recorded ${mask(String(op.physicalId))}, which is not the resource state tracks under this id; manual attention may be required`);
|
|
28998
29268
|
recordRollbackSkip(skipScope, op, "The failed CREATE recorded a physical id other than the one state now tracks under this logical id, so the rollback left it as it is; manual attention may be required.");
|
|
28999
29269
|
break;
|
|
29270
|
+
case "skip-failed-superseded":
|
|
29271
|
+
logger.warn(safeMsg` Rollback: Skipping failed CREATE of ${shownLogicalId(op.logicalId)} (${refusalResourceType(op.resourceType)}) — it created ${mask(String(op.physicalId))} before failing, and a later deploy or rollback may own a resource under that id now; if it is not in use, delete it manually`);
|
|
29272
|
+
recordRollbackSkip(skipScope, op, "The failed CREATE created its resource before failing, but a later deploy or rollback may own a resource under that id now, so the rollback left it as it is; manual attention may be required.");
|
|
29273
|
+
break;
|
|
29000
29274
|
case "skip-failed-unknown":
|
|
29001
29275
|
logger.warn(` Rollback: failed CREATE of ${safe(op.logicalId)} (${safe(op.resourceType)}) recorded no physical id — if it was partially created in AWS, delete it manually`);
|
|
29002
29276
|
recordRollbackSkip(skipScope, op, "The failed CREATE recorded no physical id, so the rollback cannot address it; if it was partially created in AWS, delete it manually.");
|
|
@@ -29024,7 +29298,7 @@ async function replayFailedOperationsUnbound(failedOps, stateResources, stackNam
|
|
|
29024
29298
|
}
|
|
29025
29299
|
delete stateResources[op.logicalId];
|
|
29026
29300
|
await noteRetainedResource(op.resourceType, op.logicalId);
|
|
29027
|
-
logger.info(` Rollback: leaving partially-created ${safe(op.logicalId)} (${safe(op.resourceType)}) in AWS (DeletionPolicy: Retain) — removed from state
|
|
29301
|
+
logger.info(` Rollback: leaving partially-created ${safe(op.logicalId)} (${safe(op.resourceType)}) in AWS (DeletionPolicy: Retain)` + (failedCreateRecord ? " — removed from state" : " — it was never in state"));
|
|
29028
29302
|
await options.afterOp?.(op.logicalId);
|
|
29029
29303
|
ctx.recordEvent?.({
|
|
29030
29304
|
eventType: "ROLLBACK_RESOURCE_SUCCEEDED",
|
|
@@ -29044,7 +29318,7 @@ async function replayFailedOperationsUnbound(failedOps, stateResources, stackNam
|
|
|
29044
29318
|
const takeFinalSnapshot = snapshotPolicy && ctx.skipFinalSnapshot !== true;
|
|
29045
29319
|
let finalSnapshotIdentifier;
|
|
29046
29320
|
if (takeFinalSnapshot) finalSnapshotIdentifier = await prepareCreateRollbackFinalSnapshot(op, deleteProvisionedBy, ctx, mask);
|
|
29047
|
-
logger.info(` Rollback: deleting partially-created ${safe(op.logicalId)} (${safe(op.resourceType)})
|
|
29321
|
+
logger.info(` Rollback: deleting partially-created ${safe(op.logicalId)} (${safe(op.resourceType)})` + (takeFinalSnapshot ? " — DeletionPolicy: Snapshot" : "") + (snapshotPolicy && !takeFinalSnapshot ? " — DeletionPolicy: Snapshot NOT taken (--skip-final-snapshot)" : ""));
|
|
29048
29322
|
const { provider, provisionedBy: deleteRoutedVia } = ctx.providerRegistry.getProviderFor({
|
|
29049
29323
|
resourceType: op.resourceType,
|
|
29050
29324
|
provisionedBy: deleteProvisionedBy
|
|
@@ -29058,7 +29332,7 @@ async function replayFailedOperationsUnbound(failedOps, stateResources, stackNam
|
|
|
29058
29332
|
deletionPolicy: snapshotPolicy ? "Snapshot" : "Delete",
|
|
29059
29333
|
recordedAttributes: stateResources[op.logicalId]?.attributes
|
|
29060
29334
|
});
|
|
29061
|
-
throwIfDeleteSkipped(failedCreateDelete, op.logicalId, op.physicalId, "while deleting the partially-created resource
|
|
29335
|
+
throwIfDeleteSkipped(failedCreateDelete, op.logicalId, op.physicalId, "while deleting the partially-created resource", {
|
|
29062
29336
|
ctx,
|
|
29063
29337
|
stackName,
|
|
29064
29338
|
resourceType: op.resourceType,
|
|
@@ -29165,7 +29439,7 @@ async function replayFailedOperationsUnbound(failedOps, stateResources, stackNam
|
|
|
29165
29439
|
error: maskedRollbackEventError(revertError, mask)
|
|
29166
29440
|
});
|
|
29167
29441
|
}
|
|
29168
|
-
inlinePolicyWriters.noteOutcome(op, action === "skip-failed-noop" || action === "skip-failed-mismatch" || ownRecord(stateResources, op.logicalId) !== recordBefore);
|
|
29442
|
+
inlinePolicyWriters.noteOutcome(op, action === "skip-failed-noop" || action === "skip-failed-mismatch" || action === "skip-failed-superseded" || ownRecord(stateResources, op.logicalId) !== recordBefore);
|
|
29169
29443
|
}
|
|
29170
29444
|
if (result.interrupted) await restoreHeldInlinePolicies(inlinePolicyWriters, stateResources, stackName, ctx, result, { refuseAll: true });
|
|
29171
29445
|
if (emitEnvelope) ctx.recordEvent?.({
|
|
@@ -29210,7 +29484,7 @@ async function collectNestedChildUnaddressed(fn) {
|
|
|
29210
29484
|
//#endregion
|
|
29211
29485
|
//#region src/deployment/nested-child-journal.ts
|
|
29212
29486
|
const NESTED_PENDING_PARENT_REASON = "nested-pending-parent";
|
|
29213
|
-
const NESTED_STACK_TYPE$
|
|
29487
|
+
const NESTED_STACK_TYPE$2 = "AWS::CloudFormation::Stack";
|
|
29214
29488
|
const MAX_NESTED_WALK_DEPTH = 32;
|
|
29215
29489
|
function nestedChildStackName(parentStackName, logicalId) {
|
|
29216
29490
|
return `${parentStackName}~${logicalId}`;
|
|
@@ -29266,7 +29540,7 @@ function recordDisplacedSkips(recordEvent, stackName, ops) {
|
|
|
29266
29540
|
});
|
|
29267
29541
|
}
|
|
29268
29542
|
function revertedNestedRowIds(ops) {
|
|
29269
|
-
return ops.filter((op) => op.resourceType === NESTED_STACK_TYPE$
|
|
29543
|
+
return ops.filter((op) => op.resourceType === NESTED_STACK_TYPE$2 && op.changeType === "UPDATE").map((op) => op.logicalId);
|
|
29270
29544
|
}
|
|
29271
29545
|
const revertRunStorage = new AsyncLocalStorage();
|
|
29272
29546
|
function withNestedRevertRun(runId, fn) {
|
|
@@ -29292,7 +29566,7 @@ async function dropNestedChildJournals(args) {
|
|
|
29292
29566
|
if (!isPlainRecord(resources)) return;
|
|
29293
29567
|
if (depthExceeded(depth, parentStackName, logger)) return;
|
|
29294
29568
|
for (const [logicalId, record] of Object.entries(resources)) {
|
|
29295
|
-
if (!isPlainRecord(record) || record["resourceType"] !== NESTED_STACK_TYPE$
|
|
29569
|
+
if (!isPlainRecord(record) || record["resourceType"] !== NESTED_STACK_TYPE$2) continue;
|
|
29296
29570
|
const child = nestedChildStackName(parentStackName, logicalId);
|
|
29297
29571
|
try {
|
|
29298
29572
|
const data = await stateBackend.getState(child, region);
|
|
@@ -29306,13 +29580,34 @@ async function dropNestedChildJournals(args) {
|
|
|
29306
29580
|
warnUncleared(logger, child, error);
|
|
29307
29581
|
}
|
|
29308
29582
|
try {
|
|
29309
|
-
await withChildLock(args.lockManager, child, region, logger, () =>
|
|
29310
|
-
|
|
29583
|
+
if (await withChildLock(args.lockManager, child, region, logger, async () => {
|
|
29584
|
+
if (args.beforeDelete) {
|
|
29585
|
+
if (!await args.beforeDelete(child, await readOwnRecord(stateBackend, child, region))) return false;
|
|
29586
|
+
}
|
|
29587
|
+
let gone;
|
|
29588
|
+
try {
|
|
29589
|
+
gone = await stateBackend.deleteRollbackJournal(child, region);
|
|
29590
|
+
} catch (error) {
|
|
29591
|
+
await args.onDeleteFailed?.(child);
|
|
29592
|
+
throw error;
|
|
29593
|
+
}
|
|
29594
|
+
if (gone === false) {
|
|
29595
|
+
await args.onDeleteFailed?.(child);
|
|
29596
|
+
return false;
|
|
29597
|
+
}
|
|
29598
|
+
return true;
|
|
29599
|
+
})) logger.debug(safeMsg`Deleted the rollback journal of nested stack ${displaySafe(child)}`);
|
|
29311
29600
|
} catch (error) {
|
|
29312
29601
|
warnUncleared(logger, child, error);
|
|
29313
29602
|
}
|
|
29314
29603
|
}
|
|
29315
29604
|
}
|
|
29605
|
+
async function readOwnRecord(stateBackend, child, region) {
|
|
29606
|
+
try {
|
|
29607
|
+
const data = await stateBackend.getState(child, region);
|
|
29608
|
+
if (data && isPlainRecord(data.state) && isPlainRecord(data.state.resources) && (data.state.stackName === void 0 || data.state.stackName === child)) return data.state;
|
|
29609
|
+
} catch {}
|
|
29610
|
+
}
|
|
29316
29611
|
async function dropSettledNestedJournals(args) {
|
|
29317
29612
|
const { stateBackend, parentStackName, region, runId, logger } = args;
|
|
29318
29613
|
const depth = args.depth ?? 0;
|
|
@@ -29622,6 +29917,306 @@ function makeSiblingClaimReader(params) {
|
|
|
29622
29917
|
};
|
|
29623
29918
|
}
|
|
29624
29919
|
|
|
29920
|
+
//#endregion
|
|
29921
|
+
//#region src/deployment/rollback-executor/journaled-orphans.ts
|
|
29922
|
+
const NONE = {
|
|
29923
|
+
segments: [],
|
|
29924
|
+
count: 0
|
|
29925
|
+
};
|
|
29926
|
+
async function loadJournaledOrphans(stateBackend, stackName, region, rollbackOrphans, logger, options = {}) {
|
|
29927
|
+
let segments;
|
|
29928
|
+
try {
|
|
29929
|
+
const journal = await stateBackend.loadRollbackJournal(stackName, region);
|
|
29930
|
+
if (!journal) return NONE;
|
|
29931
|
+
segments = journal.segments;
|
|
29932
|
+
} catch (err) {
|
|
29933
|
+
const detail = err instanceof Error ? err.message : String(err);
|
|
29934
|
+
logger.warn(safeMsg`Could not read the stack's rollback journal (${displaySafe(detail)}); ` + safeMsg`no resource it records for a failed CREATE is deleted, and ${options.unreadableOutcome ?? "a destroy that proceeds removes the journal with the state"}.`);
|
|
29935
|
+
return {
|
|
29936
|
+
...NONE,
|
|
29937
|
+
unreadable: true
|
|
29938
|
+
};
|
|
29939
|
+
}
|
|
29940
|
+
const physicalIdOnly = (ops) => ops.filter((op) => op.changeType !== "CREATE");
|
|
29941
|
+
const evidence = segments.map((segment) => options.deployRunId !== void 0 && segment.reason === "nested-pending-parent" && segment.runId === options.deployRunId ? {
|
|
29942
|
+
...segment,
|
|
29943
|
+
operations: physicalIdOnly(segment.operations)
|
|
29944
|
+
} : segment);
|
|
29945
|
+
const newer = options.newerOperations ?? [];
|
|
29946
|
+
if (newer.length > 0) evidence.push({ operations: physicalIdOnly(newer) });
|
|
29947
|
+
demoteSupersededOrphans(evidence, Array.isArray(rollbackOrphans) ? rollbackOrphans : []);
|
|
29948
|
+
const deployLogicalIds = new Set(newer.map((op) => op.logicalId));
|
|
29949
|
+
for (const segment of segments) if (options.deployRunId !== void 0 && segment.reason === "nested-pending-parent" && segment.runId === options.deployRunId) for (const op of segment.operations) deployLogicalIds.add(op.logicalId);
|
|
29950
|
+
const out = [];
|
|
29951
|
+
let count = 0;
|
|
29952
|
+
for (let s = segments.length - 1; s >= 0; s--) {
|
|
29953
|
+
const segment = segments[s];
|
|
29954
|
+
if (segment.reason === "nested-pending-parent") continue;
|
|
29955
|
+
const ops = splitImportedOps(segment.failedOperations ?? [], segment).replay.filter(isJournaledOrphan);
|
|
29956
|
+
if (ops.length === 0) continue;
|
|
29957
|
+
out.push({
|
|
29958
|
+
segment,
|
|
29959
|
+
ops
|
|
29960
|
+
});
|
|
29961
|
+
count += ops.length;
|
|
29962
|
+
}
|
|
29963
|
+
return {
|
|
29964
|
+
segments: out,
|
|
29965
|
+
count,
|
|
29966
|
+
deployLogicalIds
|
|
29967
|
+
};
|
|
29968
|
+
}
|
|
29969
|
+
function journaledOrphanLines(orphans, logger) {
|
|
29970
|
+
return orphans.segments.flatMap(({ ops }) => ops.map((op) => ` - ${logicalIdShown(op.logicalId)} (${resourceTypeShown(op.resourceType)}) ${displacedPhysicalIdShown(op, logger) ?? "a physical id"}`));
|
|
29971
|
+
}
|
|
29972
|
+
async function deleteJournaledOrphans(orphans, stateResources, stackName, ctx, options = {}) {
|
|
29973
|
+
const total = {
|
|
29974
|
+
failures: 0,
|
|
29975
|
+
warnings: 0,
|
|
29976
|
+
interrupted: false,
|
|
29977
|
+
handled: []
|
|
29978
|
+
};
|
|
29979
|
+
const inlinePolicyWriters = new RollbackInlinePolicyWriters();
|
|
29980
|
+
for (const { segment, ops } of orphans.segments) {
|
|
29981
|
+
if (options.isInterrupted?.()) {
|
|
29982
|
+
total.interrupted = true;
|
|
29983
|
+
break;
|
|
29984
|
+
}
|
|
29985
|
+
const replay = () => withStackName(stackName, () => replayFailedOperations(ops, stateResources, stackName, ctx, {
|
|
29986
|
+
emitEnvelope: false,
|
|
29987
|
+
inlinePolicyWriters,
|
|
29988
|
+
...options.isInterrupted && { isInterrupted: options.isInterrupted }
|
|
29989
|
+
}));
|
|
29990
|
+
const result = segment.skipPrefix === void 0 ? await replay() : await withSkipPrefix(segment.skipPrefix, replay);
|
|
29991
|
+
total.failures += result.failures;
|
|
29992
|
+
total.warnings += result.warnings;
|
|
29993
|
+
const pending = new Set(result.remainingFailedOps);
|
|
29994
|
+
for (const op of ops) if (!pending.has(op)) total.handled.push({
|
|
29995
|
+
segment,
|
|
29996
|
+
op
|
|
29997
|
+
});
|
|
29998
|
+
if (result.interrupted) {
|
|
29999
|
+
total.interrupted = true;
|
|
30000
|
+
break;
|
|
30001
|
+
}
|
|
30002
|
+
}
|
|
30003
|
+
return total;
|
|
30004
|
+
}
|
|
30005
|
+
async function settleJournaledOrphansOnSuccess(args) {
|
|
30006
|
+
const { stateBackend, stackName, region, stateResources, newerOperations, ctx, logger } = args;
|
|
30007
|
+
const stack = displayIdent(stackName);
|
|
30008
|
+
const newerIds = newerOperations.map((op) => op.logicalId);
|
|
30009
|
+
let orphans;
|
|
30010
|
+
try {
|
|
30011
|
+
orphans = await loadJournaledOrphans(stateBackend, stackName, region, args.rollbackOrphans, logger, {
|
|
30012
|
+
newerOperations,
|
|
30013
|
+
...args.deployRunId !== void 0 && { deployRunId: args.deployRunId },
|
|
30014
|
+
unreadableOutcome: "the successful deploy removes the journal"
|
|
30015
|
+
});
|
|
30016
|
+
} catch (err) {
|
|
30017
|
+
logger.warn(safeMsg`Could not act on the rollback journal of stack ${stack}: ${errorDetail(err)}. It is kept.`);
|
|
30018
|
+
await markSuperseded(stateBackend, stackName, region, newerIds);
|
|
30019
|
+
return {
|
|
30020
|
+
unaddressed: 1,
|
|
30021
|
+
keepJournal: true
|
|
30022
|
+
};
|
|
30023
|
+
}
|
|
30024
|
+
if (orphans.count === 0) return {
|
|
30025
|
+
unaddressed: 0,
|
|
30026
|
+
keepJournal: false
|
|
30027
|
+
};
|
|
30028
|
+
const all = orphans.segments.flatMap(({ segment, ops }) => ops.map((op) => ({
|
|
30029
|
+
segment,
|
|
30030
|
+
op
|
|
30031
|
+
})));
|
|
30032
|
+
let kept = all;
|
|
30033
|
+
if (stateResources === void 0) logger.warn(safeMsg`The rollback journal of stack ${stack} records ${all.length} resource(s) a failed deploy ` + `created, but the stack's state cannot be read, so whether a record now owns them is unknown: none is deleted.`);
|
|
30034
|
+
else {
|
|
30035
|
+
logger.info(safeMsg`The rollback journal of stack ${stack} records ${all.length} resource(s) a failed deploy ` + `created that no state record holds; acting on them per their DeletionPolicy before the journal is removed:`);
|
|
30036
|
+
for (const line of journaledOrphanLines(orphans, logger)) logger.info(line);
|
|
30037
|
+
try {
|
|
30038
|
+
const { unreadable, tracked } = await applySuccessRule(orphans, stateResources, orphans.deployLogicalIds ?? /* @__PURE__ */ new Set(), args.foreignHolder, stack, logger, args.isInterrupted);
|
|
30039
|
+
const outcome = await deleteJournaledOrphans({
|
|
30040
|
+
segments: orphans.segments.map(({ segment, ops }) => ({
|
|
30041
|
+
segment,
|
|
30042
|
+
ops: ops.filter((op) => !unreadable.has(op) && !tracked.has(op))
|
|
30043
|
+
})).filter(({ ops }) => ops.length > 0),
|
|
30044
|
+
count: orphans.count - unreadable.size - tracked.size
|
|
30045
|
+
}, { ...stateResources }, stackName, ctx, args.isInterrupted ? { isInterrupted: args.isInterrupted } : {});
|
|
30046
|
+
kept = all.filter(({ segment, op }) => unreadable.has(op) || !tracked.has(op) && !isHandledOrphan(outcome.handled, segment, op));
|
|
30047
|
+
} catch (err) {
|
|
30048
|
+
logger.warn(safeMsg`Acting on the journaled resources of stack ${stack} failed: ${errorDetail(err)}`);
|
|
30049
|
+
}
|
|
30050
|
+
}
|
|
30051
|
+
const keptOps = new Set(kept.map(({ op }) => op));
|
|
30052
|
+
const skipped = all.filter(({ op }) => !keptOps.has(op) && op.physicalIdRecoveredFromError === false).length;
|
|
30053
|
+
const cleared = all.filter(({ op }) => !keptOps.has(op));
|
|
30054
|
+
const stripCleared = cleared.length === 0 ? void 0 : async () => {
|
|
30055
|
+
try {
|
|
30056
|
+
await stateBackend.dropRollbackJournalFailedOperations(stackName, region, (op, segment) => isHandledOrphan(cleared, segment, op));
|
|
30057
|
+
} catch (err) {
|
|
30058
|
+
logger.warn(safeMsg`Failed to remove the settled entries from the rollback journal of stack ${stack}: ` + safeMsg`${errorDetail(err)}. A cdkd rollback or cdkd destroy could act on them again; run a ` + "successful cdkd deploy of the stack first, which settles them again.");
|
|
30059
|
+
}
|
|
30060
|
+
};
|
|
30061
|
+
if (kept.length === 0) return {
|
|
30062
|
+
unaddressed: skipped,
|
|
30063
|
+
keepJournal: false,
|
|
30064
|
+
...stripCleared && { stripCleared }
|
|
30065
|
+
};
|
|
30066
|
+
const keptIds = new Set(kept.map(({ op }) => op.logicalId));
|
|
30067
|
+
const supersededIds = newerIds.filter((id) => !keptIds.has(id));
|
|
30068
|
+
const demoted = kept.filter(({ op }) => op.physicalIdRecoveredFromError === false);
|
|
30069
|
+
const reduce = () => stateBackend.reduceRollbackJournalToFailedOperations(stackName, region, (op, segment) => isHandledOrphan(kept, segment, op), supersededIds, (op, segment) => isHandledOrphan(demoted, segment, op));
|
|
30070
|
+
let reduced = false;
|
|
30071
|
+
for (let attempt = 0; attempt < 2 && !reduced; attempt++) try {
|
|
30072
|
+
await reduce();
|
|
30073
|
+
reduced = true;
|
|
30074
|
+
} catch (err) {
|
|
30075
|
+
if (attempt === 1) logger.warn(safeMsg`Failed to reduce the rollback journal of stack ${stack} to its undeleted resources: ` + safeMsg`${errorDetail(err)}. The whole journal is kept.`);
|
|
30076
|
+
}
|
|
30077
|
+
if (!reduced) {
|
|
30078
|
+
await markSuperseded(stateBackend, stackName, region, supersededIds);
|
|
30079
|
+
await stripCleared?.();
|
|
30080
|
+
}
|
|
30081
|
+
logger.warn(safeMsg`${kept.length} resource(s) a failed deploy of stack ${stack} created were not deleted ` + (reduced ? "(see above). The rollback journal, their only record, is kept with just them; the next " : "(see above). The rollback journal, their only record, is kept; the next ") + "successful deploy retries.");
|
|
30082
|
+
return {
|
|
30083
|
+
unaddressed: kept.length + skipped,
|
|
30084
|
+
keepJournal: true
|
|
30085
|
+
};
|
|
30086
|
+
}
|
|
30087
|
+
async function applySuccessRule(orphans, stateResources, deployLogicalIds, foreignHolder, stack, logger, isInterrupted) {
|
|
30088
|
+
const unreadable = /* @__PURE__ */ new Set();
|
|
30089
|
+
const tracked = /* @__PURE__ */ new Set();
|
|
30090
|
+
let interrupted = false;
|
|
30091
|
+
for (const { ops } of orphans.segments) for (const op of ops) {
|
|
30092
|
+
if (op.physicalIdRecoveredFromError !== true || !op.physicalId) continue;
|
|
30093
|
+
if (interrupted || isInterrupted?.()) {
|
|
30094
|
+
interrupted = true;
|
|
30095
|
+
unreadable.add(op);
|
|
30096
|
+
continue;
|
|
30097
|
+
}
|
|
30098
|
+
if (Object.values(stateResources).some((r) => r?.resourceType === op.resourceType && r.physicalId === op.physicalId)) {
|
|
30099
|
+
tracked.add(op);
|
|
30100
|
+
continue;
|
|
30101
|
+
}
|
|
30102
|
+
if (Object.prototype.hasOwnProperty.call(stateResources, op.logicalId) || deployLogicalIds.has(op.logicalId)) {
|
|
30103
|
+
op.physicalIdRecoveredFromError = false;
|
|
30104
|
+
continue;
|
|
30105
|
+
}
|
|
30106
|
+
const holding = await foreignHolder(op.resourceType, op.physicalId);
|
|
30107
|
+
if (holding === void 0) continue;
|
|
30108
|
+
if (holding.kind === "held") {
|
|
30109
|
+
logger.warn(safeMsg`${logicalIdShown(op.logicalId)} (${resourceTypeShown(op.resourceType)}), which a failed deploy ` + safeMsg`of stack ${stack} created, is not deleted: ${holding.by} holds a resource of that type under ` + "the same physical id.");
|
|
30110
|
+
op.physicalIdRecoveredFromError = false;
|
|
30111
|
+
continue;
|
|
30112
|
+
}
|
|
30113
|
+
logger.warn(safeMsg`${logicalIdShown(op.logicalId)} (${resourceTypeShown(op.resourceType)}), which a failed deploy ` + safeMsg`of stack ${stack} created, is not deleted: ${holding.what}, so whether another stack holds it is unknown.`);
|
|
30114
|
+
unreadable.add(op);
|
|
30115
|
+
}
|
|
30116
|
+
return {
|
|
30117
|
+
unreadable,
|
|
30118
|
+
tracked
|
|
30119
|
+
};
|
|
30120
|
+
}
|
|
30121
|
+
function makeForeignHolderScan(stateBackend) {
|
|
30122
|
+
let scan;
|
|
30123
|
+
const key = (type, id) => JSON.stringify([type, id]);
|
|
30124
|
+
const run = async () => {
|
|
30125
|
+
const holders = /* @__PURE__ */ new Map();
|
|
30126
|
+
let refs;
|
|
30127
|
+
try {
|
|
30128
|
+
refs = await stateBackend.listStacks();
|
|
30129
|
+
} catch {
|
|
30130
|
+
return {
|
|
30131
|
+
holders,
|
|
30132
|
+
unreadable: "the state bucket listing (it could not be read)"
|
|
30133
|
+
};
|
|
30134
|
+
}
|
|
30135
|
+
let unreadable;
|
|
30136
|
+
await Promise.all(refs.map(async (ref) => {
|
|
30137
|
+
const named = (why) => safeMsg`the state record of stack ${displayIdent(ref.stackName)} (${why})`;
|
|
30138
|
+
if (ref.region === void 0) {
|
|
30139
|
+
unreadable ??= named("its region cannot be read");
|
|
30140
|
+
return;
|
|
30141
|
+
}
|
|
30142
|
+
const region = ref.region;
|
|
30143
|
+
let state;
|
|
30144
|
+
try {
|
|
30145
|
+
state = (await stateBackend.getState(ref.stackName, region))?.state;
|
|
30146
|
+
} catch {
|
|
30147
|
+
unreadable ??= named("it could not be read");
|
|
30148
|
+
return;
|
|
30149
|
+
}
|
|
30150
|
+
if (state === void 0) return;
|
|
30151
|
+
const resources = state.resources;
|
|
30152
|
+
if (resources !== void 0 && (typeof resources !== "object" || resources === null || Array.isArray(resources))) {
|
|
30153
|
+
unreadable ??= named("its resources cannot be read");
|
|
30154
|
+
return;
|
|
30155
|
+
}
|
|
30156
|
+
if (!hasReadableOrphans(state) || unreadableOrphanRecords(state).length > 0) {
|
|
30157
|
+
unreadable ??= named("its rollback-orphan records cannot be read");
|
|
30158
|
+
return;
|
|
30159
|
+
}
|
|
30160
|
+
const held = [...Object.values(resources ?? {}), ...(state.orphans ?? []).map((record) => record.state)];
|
|
30161
|
+
for (const record of held) {
|
|
30162
|
+
const r = record;
|
|
30163
|
+
if (typeof r?.resourceType !== "string" || typeof r.physicalId !== "string") continue;
|
|
30164
|
+
const k = key(r.resourceType, r.physicalId);
|
|
30165
|
+
const list = holders.get(k) ?? [];
|
|
30166
|
+
list.push({
|
|
30167
|
+
stackName: ref.stackName,
|
|
30168
|
+
region
|
|
30169
|
+
});
|
|
30170
|
+
holders.set(k, list);
|
|
30171
|
+
}
|
|
30172
|
+
}));
|
|
30173
|
+
return {
|
|
30174
|
+
holders,
|
|
30175
|
+
...unreadable !== void 0 && { unreadable }
|
|
30176
|
+
};
|
|
30177
|
+
};
|
|
30178
|
+
return (self) => async (resourceType, physicalId) => {
|
|
30179
|
+
scan ??= run();
|
|
30180
|
+
const { holders, unreadable } = await scan;
|
|
30181
|
+
const other = (holders.get(key(resourceType, physicalId)) ?? []).find((h) => !(h.stackName === self.stackName && h.region === self.region));
|
|
30182
|
+
if (other) return {
|
|
30183
|
+
kind: "held",
|
|
30184
|
+
by: safeMsg`the state record of stack ${displayIdent(other.stackName)} (${displaySafe(other.region)})`
|
|
30185
|
+
};
|
|
30186
|
+
return unreadable === void 0 ? void 0 : {
|
|
30187
|
+
kind: "unreadable",
|
|
30188
|
+
what: unreadable
|
|
30189
|
+
};
|
|
30190
|
+
};
|
|
30191
|
+
}
|
|
30192
|
+
async function markSuperseded(stateBackend, stackName, region, ids) {
|
|
30193
|
+
try {
|
|
30194
|
+
await stateBackend.markRollbackJournalSuperseded(stackName, region, ids);
|
|
30195
|
+
} catch {}
|
|
30196
|
+
}
|
|
30197
|
+
function errorDetail(err) {
|
|
30198
|
+
return displaySafe(err instanceof Error ? err.message : String(err));
|
|
30199
|
+
}
|
|
30200
|
+
function isHandledOrphan(handled, segment, op) {
|
|
30201
|
+
return handled.some((h) => h.segment.timestamp === segment.timestamp && h.segment.runId === segment.runId && h.op.logicalId === op.logicalId && h.op.changeType === op.changeType && h.op.resourceType === op.resourceType && h.op.physicalId === op.physicalId);
|
|
30202
|
+
}
|
|
30203
|
+
function orphanKey(segment, op) {
|
|
30204
|
+
return JSON.stringify([
|
|
30205
|
+
segment.timestamp,
|
|
30206
|
+
segment.runId ?? null,
|
|
30207
|
+
op.logicalId,
|
|
30208
|
+
op.changeType,
|
|
30209
|
+
op.resourceType,
|
|
30210
|
+
op.physicalId ?? null
|
|
30211
|
+
]);
|
|
30212
|
+
}
|
|
30213
|
+
function sameJournaledOrphans(a, b) {
|
|
30214
|
+
const keys = (o) => o.segments.flatMap(({ segment, ops }) => ops.map((op) => orphanKey(segment, op))).sort();
|
|
30215
|
+
const ka = keys(a);
|
|
30216
|
+
const kb = keys(b);
|
|
30217
|
+
return ka.length === kb.length && ka.every((k, i) => k === kb[i]);
|
|
30218
|
+
}
|
|
30219
|
+
|
|
29625
30220
|
//#endregion
|
|
29626
30221
|
//#region src/deployment/deploy-engine/rollback.ts
|
|
29627
30222
|
function redactOperationsForJournal(operations) {
|
|
@@ -29670,33 +30265,109 @@ async function adoptRollbackOrphans(currentState, effectiveTemplate) {
|
|
|
29670
30265
|
if (records.length > 0) currentState.orphans = plan.remaining;
|
|
29671
30266
|
return plan;
|
|
29672
30267
|
}
|
|
29673
|
-
async function performRollback(completedOperations, stateResources, stackName, previousState) {
|
|
30268
|
+
async function performRollback(completedOperations, stateResources, stackName, previousState, failedOperations = [], priorOrphans = []) {
|
|
30269
|
+
const orphanIndexes = [];
|
|
30270
|
+
const orphanOps = [];
|
|
30271
|
+
failedOperations.forEach((op, i) => {
|
|
30272
|
+
if (!isJournaledOrphan(op)) return;
|
|
30273
|
+
orphanIndexes.push(i);
|
|
30274
|
+
orphanOps.push({ ...op });
|
|
30275
|
+
});
|
|
30276
|
+
demoteSupersededOrphans([{
|
|
30277
|
+
operations: completedOperations,
|
|
30278
|
+
failedOperations: orphanOps
|
|
30279
|
+
}], priorOrphans);
|
|
30280
|
+
const ctx = this.rollbackExecutorContext(previousState, stackName);
|
|
30281
|
+
const inlinePolicyWriters = new RollbackInlinePolicyWriters();
|
|
29674
30282
|
const runId = this.options.eventRecorder?.runId;
|
|
29675
|
-
const { result, run } = await withNestedRevertRun(runId, async (scope) =>
|
|
29676
|
-
|
|
29677
|
-
|
|
29678
|
-
|
|
30283
|
+
const { result, failed, run } = await withNestedRevertRun(runId, async (scope) => {
|
|
30284
|
+
return {
|
|
30285
|
+
failed: orphanOps.length > 0 ? await replayFailedOperations(orphanOps, stateResources, stackName, ctx, {
|
|
30286
|
+
emitEnvelope: completedOperations.length === 0,
|
|
30287
|
+
inlinePolicyWriters
|
|
30288
|
+
}) : void 0,
|
|
30289
|
+
result: await replayRollback(completedOperations, stateResources, stackName, ctx, { inlinePolicyWriters }),
|
|
30290
|
+
run: scope
|
|
30291
|
+
};
|
|
30292
|
+
});
|
|
30293
|
+
const pendingOrphans = new Set(failed?.remainingFailedOps ?? []);
|
|
30294
|
+
const handled = new Set(orphanIndexes.filter((_, k) => !pendingOrphans.has(orphanOps[k])));
|
|
29679
30295
|
return {
|
|
29680
|
-
failures: result.failures,
|
|
29681
|
-
warnings: result.warnings + run.warnings,
|
|
29682
|
-
skipped: result.skipped,
|
|
29683
|
-
orphaned: result.orphaned,
|
|
29684
|
-
settledNested: run.settled
|
|
30296
|
+
failures: result.failures + (failed?.failures ?? 0),
|
|
30297
|
+
warnings: result.warnings + run.warnings + (failed?.warnings ?? 0),
|
|
30298
|
+
skipped: result.skipped + (failed?.skipped ?? 0),
|
|
30299
|
+
orphaned: [...failed?.orphaned ?? [], ...result.orphaned],
|
|
30300
|
+
settledNested: run.settled,
|
|
30301
|
+
remainingFailedOps: failedOperations.filter((_, i) => !handled.has(i))
|
|
29685
30302
|
};
|
|
29686
30303
|
}
|
|
29687
30304
|
async function settleJournalAfterSuccess(stackName, completedOperations, previousState, finalResources, initialDeploy) {
|
|
29688
30305
|
if (this.options.parentStackInfo) {
|
|
29689
30306
|
await this.writeRollbackJournalSegment(stackName, completedOperations, [], NESTED_PENDING_PARENT_REASON, initialDeploy, nestedPendingSnapshot(previousState));
|
|
29690
|
-
return;
|
|
29691
|
-
}
|
|
29692
|
-
|
|
30307
|
+
return 0;
|
|
30308
|
+
}
|
|
30309
|
+
let nestedLeft = 0;
|
|
30310
|
+
const foreignHolderFor = makeForeignHolderScan(this.stateBackend);
|
|
30311
|
+
const deployRunId = this.options.eventRecorder?.runId;
|
|
30312
|
+
const stripOnFailure = /* @__PURE__ */ new Map();
|
|
30313
|
+
const [ownLeft] = await Promise.all([(async () => {
|
|
30314
|
+
const own = await settleJournaledOrphansOnSuccess({
|
|
30315
|
+
stateBackend: this.stateBackend,
|
|
30316
|
+
stackName,
|
|
30317
|
+
region: this.stackRegion,
|
|
30318
|
+
stateResources: finalResources,
|
|
30319
|
+
rollbackOrphans: previousState.orphans,
|
|
30320
|
+
newerOperations: completedOperations,
|
|
30321
|
+
...deployRunId !== void 0 && { deployRunId },
|
|
30322
|
+
foreignHolder: foreignHolderFor({
|
|
30323
|
+
stackName,
|
|
30324
|
+
region: this.stackRegion
|
|
30325
|
+
}),
|
|
30326
|
+
ctx: this.rollbackExecutorContext(previousState, stackName),
|
|
30327
|
+
isInterrupted: () => this.interrupted,
|
|
30328
|
+
logger: this.logger
|
|
30329
|
+
});
|
|
30330
|
+
if (own.keepJournal) return own.unaddressed;
|
|
30331
|
+
if (!await this.deleteRollbackJournalBestEffort(stackName, completedOperations.map((op) => op.logicalId))) await own.stripCleared?.();
|
|
30332
|
+
return own.unaddressed;
|
|
30333
|
+
})(), dropNestedChildJournals({
|
|
29693
30334
|
stateBackend: this.stateBackend,
|
|
29694
30335
|
lockManager: this.lockManager,
|
|
29695
30336
|
parentStackName: stackName,
|
|
29696
30337
|
region: this.stackRegion,
|
|
29697
30338
|
resources: finalResources,
|
|
29698
|
-
logger: this.logger
|
|
30339
|
+
logger: this.logger,
|
|
30340
|
+
beforeDelete: async (child, childRecord) => {
|
|
30341
|
+
const childState = childRecord !== void 0 && hasReadableOrphans(childRecord) ? childRecord : void 0;
|
|
30342
|
+
const settled = await settleJournaledOrphansOnSuccess({
|
|
30343
|
+
stateBackend: this.stateBackend,
|
|
30344
|
+
stackName: child,
|
|
30345
|
+
region: this.stackRegion,
|
|
30346
|
+
stateResources: childState?.resources,
|
|
30347
|
+
rollbackOrphans: childState?.orphans,
|
|
30348
|
+
newerOperations: [],
|
|
30349
|
+
...deployRunId !== void 0 && { deployRunId },
|
|
30350
|
+
foreignHolder: foreignHolderFor({
|
|
30351
|
+
stackName: child,
|
|
30352
|
+
region: this.stackRegion
|
|
30353
|
+
}),
|
|
30354
|
+
isInterrupted: () => this.interrupted,
|
|
30355
|
+
ctx: {
|
|
30356
|
+
...this.rollbackExecutorContext(childState ?? previousState, child),
|
|
30357
|
+
producerRegionsIncomplete: true,
|
|
30358
|
+
nestedChildStack: child
|
|
30359
|
+
},
|
|
30360
|
+
logger: this.logger
|
|
30361
|
+
});
|
|
30362
|
+
nestedLeft += settled.unaddressed;
|
|
30363
|
+
if (settled.stripCleared) stripOnFailure.set(child, settled.stripCleared);
|
|
30364
|
+
return !settled.keepJournal;
|
|
30365
|
+
},
|
|
30366
|
+
onDeleteFailed: async (child) => {
|
|
30367
|
+
await stripOnFailure.get(child)?.();
|
|
30368
|
+
}
|
|
29699
30369
|
})]);
|
|
30370
|
+
return ownLeft + nestedLeft;
|
|
29700
30371
|
}
|
|
29701
30372
|
async function deleteRollbackJournalBestEffort(stackName, supersededLogicalIds = []) {
|
|
29702
30373
|
let deleted;
|
|
@@ -29706,12 +30377,14 @@ async function deleteRollbackJournalBestEffort(stackName, supersededLogicalIds =
|
|
|
29706
30377
|
this.logger.debug(safeMsg`Failed to delete rollback journal for ${stackName}: ${err instanceof Error ? err.message : String(err)}`);
|
|
29707
30378
|
deleted = false;
|
|
29708
30379
|
}
|
|
29709
|
-
if (deleted !== false
|
|
30380
|
+
if (deleted !== false) return true;
|
|
30381
|
+
if (supersededLogicalIds.length === 0) return false;
|
|
29710
30382
|
try {
|
|
29711
30383
|
await this.stateBackend.markRollbackJournalSuperseded(stackName, this.stackRegion, supersededLogicalIds);
|
|
29712
30384
|
} catch (markErr) {
|
|
29713
30385
|
this.logger.debug(safeMsg`Failed to record superseded logical ids on the rollback journal for ${stackName}: ${markErr instanceof Error ? markErr.message : String(markErr)}`);
|
|
29714
30386
|
}
|
|
30387
|
+
return false;
|
|
29715
30388
|
}
|
|
29716
30389
|
async function settleJournalAfterCleanRollback(stackName, failedOperations, initialDeploy) {
|
|
29717
30390
|
if (failedOperations.length === 0) {
|
|
@@ -30850,6 +31523,7 @@ function priorAttemptsInJournal(journal, logicalId, resourceType) {
|
|
|
30850
31523
|
}
|
|
30851
31524
|
function recordedAsNewResource(op) {
|
|
30852
31525
|
if (typeof op.physicalId !== "string" || op.physicalId === "") return false;
|
|
31526
|
+
if (op.physicalIdRecoveredFromError === true) return false;
|
|
30853
31527
|
if (op.changeType === "CREATE") return true;
|
|
30854
31528
|
const previous = op.previousState?.physicalId;
|
|
30855
31529
|
return typeof previous === "string" && previous !== op.physicalId;
|
|
@@ -31502,6 +32176,7 @@ var DynamoDBGlobalTableProvider = class {
|
|
|
31502
32176
|
};
|
|
31503
32177
|
} catch (wiringError) {
|
|
31504
32178
|
warn(`Wiring failed after CreateTable for ${tableName}; attempting best-effort cleanup`);
|
|
32179
|
+
let tableLeftBehind = false;
|
|
31505
32180
|
try {
|
|
31506
32181
|
const replicasForCleanup = (await this.dynamoDBClient.send(new DescribeTableCommand({ TableName: tableName }))).Table?.Replicas ?? [];
|
|
31507
32182
|
for (const replica of replicasForCleanup) {
|
|
@@ -31520,12 +32195,15 @@ var DynamoDBGlobalTableProvider = class {
|
|
|
31520
32195
|
}
|
|
31521
32196
|
await this.dynamoDBClient.send(new DeleteTableCommand({ TableName: tableName }));
|
|
31522
32197
|
} catch (cleanupErr) {
|
|
32198
|
+
tableLeftBehind = true;
|
|
31523
32199
|
const cleanupMsg = describeAwsFailure(cleanupErr).detail;
|
|
31524
32200
|
warn(`Partial-create cleanup failed for ${tableName}: ${cleanupMsg}. To remove the orphaned AWS-side table, run: ` + pasteableAwsCommand(maskSecrets)`aws dynamodb delete-table --table-name ${tableName}`.render());
|
|
31525
32201
|
}
|
|
31526
32202
|
markAuxiliaryFailure(wiringError, logicalId);
|
|
31527
32203
|
const cause = wiringError instanceof Error ? wiringError : void 0;
|
|
31528
|
-
|
|
32204
|
+
const thrown = this.wrapMaskedError(log, wiringError, (text) => new ProvisioningError(`Failed to create DynamoDB GlobalTable ${logicalId}: ${text}`, resourceType, logicalId, tableName, cause));
|
|
32205
|
+
if (tableLeftBehind) markCreatedBeforeFailure(thrown, logicalId, resourceType, tableName);
|
|
32206
|
+
throw thrown;
|
|
31529
32207
|
}
|
|
31530
32208
|
}
|
|
31531
32209
|
reportThroughputDiagnostics(diagnostics, logicalId, physicalId, maskSecrets = (text) => text) {
|
|
@@ -34547,31 +35225,61 @@ function validateOptions(opts) {
|
|
|
34547
35225
|
}
|
|
34548
35226
|
async function withResourceDeadline(operation, opts) {
|
|
34549
35227
|
validateOptions(opts);
|
|
34550
|
-
const startedAt = Date.now();
|
|
34551
35228
|
return new Promise((resolve, reject) => {
|
|
34552
35229
|
let settled = false;
|
|
35230
|
+
let timedOut = false;
|
|
35231
|
+
let warned = false;
|
|
34553
35232
|
let warnTimer;
|
|
34554
35233
|
let timeoutTimer;
|
|
35234
|
+
let elapsedBeforePause = 0;
|
|
35235
|
+
let runningSince = Date.now();
|
|
35236
|
+
let pauses = 0;
|
|
35237
|
+
const elapsed = () => elapsedBeforePause + (pauses > 0 ? 0 : Date.now() - runningSince);
|
|
34555
35238
|
const cleanup = () => {
|
|
34556
35239
|
if (warnTimer !== void 0) clearTimeout(warnTimer);
|
|
34557
35240
|
if (timeoutTimer !== void 0) clearTimeout(timeoutTimer);
|
|
34558
35241
|
warnTimer = void 0;
|
|
34559
35242
|
timeoutTimer = void 0;
|
|
34560
35243
|
};
|
|
34561
|
-
|
|
34562
|
-
if (
|
|
34563
|
-
|
|
34564
|
-
|
|
34565
|
-
|
|
34566
|
-
|
|
34567
|
-
|
|
34568
|
-
|
|
34569
|
-
|
|
34570
|
-
|
|
34571
|
-
|
|
34572
|
-
|
|
34573
|
-
|
|
34574
|
-
|
|
35244
|
+
const arm = () => {
|
|
35245
|
+
if (opts.onWarn && !warned) warnTimer = setTimeout(() => {
|
|
35246
|
+
if (settled) return;
|
|
35247
|
+
warned = true;
|
|
35248
|
+
try {
|
|
35249
|
+
opts.onWarn(elapsed());
|
|
35250
|
+
} catch {}
|
|
35251
|
+
}, Math.max(0, opts.warnAfterMs - elapsed()));
|
|
35252
|
+
timeoutTimer = setTimeout(() => {
|
|
35253
|
+
if (settled) return;
|
|
35254
|
+
settled = true;
|
|
35255
|
+
timedOut = true;
|
|
35256
|
+
cleanup();
|
|
35257
|
+
reject(opts.onTimeout(elapsed()));
|
|
35258
|
+
}, Math.max(0, opts.timeoutMs - elapsed()));
|
|
35259
|
+
};
|
|
35260
|
+
arm();
|
|
35261
|
+
const outer = deadlineScope.getStore();
|
|
35262
|
+
const control = {
|
|
35263
|
+
pause: () => {
|
|
35264
|
+
pauses += 1;
|
|
35265
|
+
if (pauses === 1) {
|
|
35266
|
+
elapsedBeforePause += Date.now() - runningSince;
|
|
35267
|
+
cleanup();
|
|
35268
|
+
}
|
|
35269
|
+
outer?.pause();
|
|
35270
|
+
},
|
|
35271
|
+
resume: () => {
|
|
35272
|
+
if (pauses === 0) return;
|
|
35273
|
+
pauses -= 1;
|
|
35274
|
+
if (pauses === 0) {
|
|
35275
|
+
runningSince = Date.now();
|
|
35276
|
+
if (!settled) arm();
|
|
35277
|
+
}
|
|
35278
|
+
outer?.resume();
|
|
35279
|
+
},
|
|
35280
|
+
expired: () => timedOut || (outer?.expired() ?? false)
|
|
35281
|
+
};
|
|
35282
|
+
Promise.resolve().then(() => deadlineScope.run(control, operation)).then((value) => {
|
|
34575
35283
|
if (settled) return;
|
|
34576
35284
|
settled = true;
|
|
34577
35285
|
cleanup();
|
|
@@ -34584,6 +35292,20 @@ async function withResourceDeadline(operation, opts) {
|
|
|
34584
35292
|
});
|
|
34585
35293
|
});
|
|
34586
35294
|
}
|
|
35295
|
+
const deadlineScope = new AsyncLocalStorage();
|
|
35296
|
+
async function whileEnclosingDeadlinesPaused(fn) {
|
|
35297
|
+
const control = deadlineScope.getStore();
|
|
35298
|
+
if (control === void 0) return fn();
|
|
35299
|
+
control.pause();
|
|
35300
|
+
try {
|
|
35301
|
+
return await fn();
|
|
35302
|
+
} finally {
|
|
35303
|
+
control.resume();
|
|
35304
|
+
}
|
|
35305
|
+
}
|
|
35306
|
+
function enclosingDeadlineExpired() {
|
|
35307
|
+
return deadlineScope.getStore()?.expired() ?? false;
|
|
35308
|
+
}
|
|
34587
35309
|
|
|
34588
35310
|
//#endregion
|
|
34589
35311
|
//#region src/deployment/deploy-engine/provision.ts
|
|
@@ -34979,15 +35701,20 @@ async function executeDeployment(template, currentState, changes, dag, execution
|
|
|
34979
35701
|
this.interrupted = true;
|
|
34980
35702
|
this.interruptCause ??= "sibling-failure";
|
|
34981
35703
|
const refused = isRefusedBeforeApplying(provisionError, logicalId);
|
|
34982
|
-
const
|
|
34983
|
-
if (refused && change.changeType === "CREATE" &&
|
|
35704
|
+
const statePhysicalId = newResources[logicalId]?.physicalId ?? previousState?.physicalId;
|
|
35705
|
+
if (refused && change.changeType === "CREATE" && statePhysicalId === void 0) throw provisionError;
|
|
35706
|
+
const createdId = change.changeType === "CREATE" && statePhysicalId === void 0 ? createdBeforeFailure(provisionError, logicalId, change.resourceType) : void 0;
|
|
34984
35707
|
failedOperations.push({
|
|
34985
35708
|
logicalId,
|
|
34986
35709
|
changeType: change.changeType,
|
|
34987
35710
|
resourceType: change.resourceType,
|
|
34988
|
-
provisionedBy: newResources[logicalId]?.provisionedBy ?? previousState?.provisionedBy,
|
|
35711
|
+
provisionedBy: createdId !== void 0 ? "sdk" : newResources[logicalId]?.provisionedBy ?? previousState?.provisionedBy,
|
|
34989
35712
|
...previousState && { previousState },
|
|
34990
|
-
physicalId,
|
|
35713
|
+
physicalId: createdId ?? statePhysicalId,
|
|
35714
|
+
...createdId !== void 0 && {
|
|
35715
|
+
physicalIdRecoveredFromError: true,
|
|
35716
|
+
deletionPolicy: journaledOrphanPolicy(this.extractTemplateAttributes(template, logicalId).deletionPolicy)
|
|
35717
|
+
},
|
|
34991
35718
|
...!refused && { attemptedProperties: this.attemptedResolvedProps.get(logicalId) }
|
|
34992
35719
|
});
|
|
34993
35720
|
throw provisionError;
|
|
@@ -35141,6 +35868,7 @@ async function executeDeployment(template, currentState, changes, dag, execution
|
|
|
35141
35868
|
let autoRollbackJournaled = false;
|
|
35142
35869
|
let rollbackOrphans = [];
|
|
35143
35870
|
let rollbackSettledNested = /* @__PURE__ */ new Map();
|
|
35871
|
+
let rollbackRemainingFailedOps = failedOperations;
|
|
35144
35872
|
if (error instanceof InterruptedError || isInterruptedWaitError(error) || this.interruptCause === "user") {
|
|
35145
35873
|
await this.writeRollbackJournalSegment(stackName, completedOperations, failedOperations, "interrupted", initialDeploy);
|
|
35146
35874
|
this.logger.info(`Partial state saved (${Object.keys(newResources).length} resources). Run deploy again to resume, 'cdkd rollback' to revert, or destroy to clean up.`);
|
|
@@ -35152,7 +35880,7 @@ async function executeDeployment(template, currentState, changes, dag, execution
|
|
|
35152
35880
|
this.logger.warn(safeMsg`Partial state has been saved. ${this.recoveryHint("Run 'cdkd deploy' to resume, 'cdkd rollback' to revert, or destroy to clean up.")}`);
|
|
35153
35881
|
} else {
|
|
35154
35882
|
autoRollbackJournaled = await this.writeRollbackJournalSegment(stackName, completedOperations, failedOperations, "auto-rollback-started", initialDeploy);
|
|
35155
|
-
const rollbackResult = await this.performRollback(completedOperations, newResources, stackName, currentState);
|
|
35883
|
+
const rollbackResult = await this.performRollback(completedOperations, newResources, stackName, currentState, failedOperations, currentState.orphans ?? []);
|
|
35156
35884
|
autoRollbackClean = autoRollbackJournaled && rollbackResult.failures === 0 && rollbackResult.skipped === 0;
|
|
35157
35885
|
if (rollbackResult.failures === 0 && rollbackResult.skipped > 0) {
|
|
35158
35886
|
this.logger.warn(safeMsg`The automatic rollback could not revert ${rollbackResult.skipped} operation(s) ` + `(see the warnings above; each is recorded as a ROLLBACK_RESOURCE_SKIPPED event).` + (autoRollbackJournaled ? ` The rollback journal keeps them.` : ""));
|
|
@@ -35163,6 +35891,7 @@ async function executeDeployment(template, currentState, changes, dag, execution
|
|
|
35163
35891
|
}
|
|
35164
35892
|
rollbackOrphans = rollbackResult.orphaned;
|
|
35165
35893
|
rollbackSettledNested = rollbackResult.settledNested;
|
|
35894
|
+
rollbackRemainingFailedOps = rollbackResult.remainingFailedOps;
|
|
35166
35895
|
}
|
|
35167
35896
|
try {
|
|
35168
35897
|
const postRollbackState = {
|
|
@@ -35179,7 +35908,7 @@ async function executeDeployment(template, currentState, changes, dag, execution
|
|
|
35179
35908
|
};
|
|
35180
35909
|
await this.stateBackend.saveState(stackName, this.stackRegion, this.withParentInfo(postRollbackState), { ...currentEtag !== void 0 && { expectedEtag: currentEtag } });
|
|
35181
35910
|
this.logger.debug("State saved after deployment failure");
|
|
35182
|
-
if (autoRollbackClean) await this.settleNestedChildrenAfterCleanRollback(stackName, rollbackSettledNested, await this.settleJournalAfterCleanRollback(stackName,
|
|
35911
|
+
if (autoRollbackClean) await this.settleNestedChildrenAfterCleanRollback(stackName, rollbackSettledNested, await this.settleJournalAfterCleanRollback(stackName, rollbackRemainingFailedOps, initialDeploy));
|
|
35183
35912
|
} catch (saveError) {
|
|
35184
35913
|
this.logger.debug(`Retrying state save after rollback (ETag mismatch): ${saveError instanceof Error ? saveError.message : String(saveError)}`);
|
|
35185
35914
|
try {
|
|
@@ -35198,7 +35927,7 @@ async function executeDeployment(template, currentState, changes, dag, execution
|
|
|
35198
35927
|
};
|
|
35199
35928
|
await this.stateBackend.saveState(stackName, this.stackRegion, this.withParentInfo(postRollbackState), { ...freshEtag !== void 0 && { expectedEtag: freshEtag } });
|
|
35200
35929
|
this.logger.debug("State saved after deployment failure (retry succeeded)");
|
|
35201
|
-
if (autoRollbackClean) await this.settleNestedChildrenAfterCleanRollback(stackName, rollbackSettledNested, await this.settleJournalAfterCleanRollback(stackName,
|
|
35930
|
+
if (autoRollbackClean) await this.settleNestedChildrenAfterCleanRollback(stackName, rollbackSettledNested, await this.settleJournalAfterCleanRollback(stackName, rollbackRemainingFailedOps, initialDeploy));
|
|
35202
35931
|
} catch (retryError) {
|
|
35203
35932
|
this.logger.warn(`Failed to save state after rollback: ${retryError instanceof Error ? retryError.message : String(retryError)}`);
|
|
35204
35933
|
}
|
|
@@ -35265,6 +35994,10 @@ async function persistStateAfterOutputFailure(stackName, currentState, newResour
|
|
|
35265
35994
|
}
|
|
35266
35995
|
}
|
|
35267
35996
|
}
|
|
35997
|
+
function journaledOrphanPolicy(policy) {
|
|
35998
|
+
if (policy === void 0) return void 0;
|
|
35999
|
+
return policy === "Delete" || policy === "Retain" || policy === "Snapshot" || policy === "RetainExceptOnCreate" ? policy : "Retain";
|
|
36000
|
+
}
|
|
35268
36001
|
|
|
35269
36002
|
//#endregion
|
|
35270
36003
|
//#region src/provisioning/canonicalize-properties.ts
|
|
@@ -35366,6 +36099,62 @@ function refuseNoValueOutputs(outputs, conditions) {
|
|
|
35366
36099
|
throw markNonRetryable(/* @__PURE__ */ new Error(`Output ${offending.join(", ")} evaluates to AWS::NoValue, and CloudFormation rejects the template for it ("The Value field of every Outputs member must evaluate to a String") before creating anything. To publish an Output only sometimes, give it a Condition instead of selecting AWS::NoValue in its Value.`));
|
|
35367
36100
|
}
|
|
35368
36101
|
|
|
36102
|
+
//#endregion
|
|
36103
|
+
//#region src/deployment/deployment-approval.ts
|
|
36104
|
+
const NESTED_STACK_TYPE$1 = "AWS::CloudFormation::Stack";
|
|
36105
|
+
async function requireDeploymentApproval(args) {
|
|
36106
|
+
const level = args.options.requireApproval ?? "never";
|
|
36107
|
+
const approve = args.options.approveDeployment;
|
|
36108
|
+
if (level === "never" || approve === void 0) return;
|
|
36109
|
+
const changes = [...args.changes].filter((c) => c.changeType !== "NO_CHANGE");
|
|
36110
|
+
const destructiveChanges = findDestructiveChanges(args.stackName, changes, args.records, args.template, new Set(args.recreateTargetIds ?? []));
|
|
36111
|
+
const onlyNestedUpdates = changes.every((c) => c.changeType === "UPDATE" && c.resourceType === NESTED_STACK_TYPE$1);
|
|
36112
|
+
if (!(level === "destructive" ? destructiveChanges.length > 0 : changes.length > 0 && !onlyNestedUpdates)) return;
|
|
36113
|
+
const count = (type) => changes.filter((c) => c.changeType === type).length;
|
|
36114
|
+
if (enclosingDeadlineExpired()) throw approvalAfterTimeout(args.stackName);
|
|
36115
|
+
let approved;
|
|
36116
|
+
try {
|
|
36117
|
+
approved = await whileEnclosingDeadlinesPaused(() => approve({
|
|
36118
|
+
stackName: args.stackName,
|
|
36119
|
+
level,
|
|
36120
|
+
counts: {
|
|
36121
|
+
create: count("CREATE"),
|
|
36122
|
+
update: count("UPDATE"),
|
|
36123
|
+
delete: count("DELETE")
|
|
36124
|
+
},
|
|
36125
|
+
destructiveChanges
|
|
36126
|
+
}));
|
|
36127
|
+
} catch (error) {
|
|
36128
|
+
throw error instanceof Error ? markNonRetryable(error) : error;
|
|
36129
|
+
}
|
|
36130
|
+
if (!approved) throw markNonRetryable(new CdkdError(safeMsg`Deployment of stack ${args.stackName} was not approved (--require-approval=${level}). Nothing was changed.`, "DEPLOY_NOT_APPROVED"));
|
|
36131
|
+
}
|
|
36132
|
+
function approvalAfterTimeout(stackName) {
|
|
36133
|
+
return markNonRetryable(new CdkdError(safeMsg`Deployment of stack ${stackName} was not started: its parent's nested-stack row already timed out (--resource-timeout). Nothing was changed.`, "DEPLOY_APPROVAL_AFTER_TIMEOUT"));
|
|
36134
|
+
}
|
|
36135
|
+
async function requireOutputsOnlyApproval(args) {
|
|
36136
|
+
const approve = args.options.approveDeployment;
|
|
36137
|
+
if (args.options.requireApproval !== "any-change" || approve === void 0) return;
|
|
36138
|
+
if (enclosingDeadlineExpired()) throw approvalAfterTimeout(args.stackName);
|
|
36139
|
+
let approved;
|
|
36140
|
+
try {
|
|
36141
|
+
approved = await whileEnclosingDeadlinesPaused(() => approve({
|
|
36142
|
+
stackName: args.stackName,
|
|
36143
|
+
level: "any-change",
|
|
36144
|
+
counts: {
|
|
36145
|
+
create: 0,
|
|
36146
|
+
update: 0,
|
|
36147
|
+
delete: 0
|
|
36148
|
+
},
|
|
36149
|
+
destructiveChanges: [],
|
|
36150
|
+
outputsOnly: true
|
|
36151
|
+
}));
|
|
36152
|
+
} catch (error) {
|
|
36153
|
+
throw error instanceof Error ? markNonRetryable(error) : error;
|
|
36154
|
+
}
|
|
36155
|
+
if (!approved) throw markNonRetryable(new CdkdError(safeMsg`Deployment of stack ${args.stackName} was not approved (--require-approval=any-change). Nothing was changed.`, "DEPLOY_NOT_APPROVED"));
|
|
36156
|
+
}
|
|
36157
|
+
|
|
35369
36158
|
//#endregion
|
|
35370
36159
|
//#region src/deployment/condition-verdicts.ts
|
|
35371
36160
|
function conditionInputsFrom(args) {
|
|
@@ -35893,6 +36682,7 @@ async function doDeployWithPrefetch(stackName, template, createOnlyPrefetch) {
|
|
|
35893
36682
|
}));
|
|
35894
36683
|
}
|
|
35895
36684
|
const effectiveTemplate = this.templateParser.filterResourcesByCondition(template, conditions);
|
|
36685
|
+
this.constructPathTemplate = effectiveTemplate;
|
|
35896
36686
|
const orphanCountBeforeAdoption = (currentState.orphans ?? []).length;
|
|
35897
36687
|
const orphanPlan = await this.adoptRollbackOrphans(currentState, effectiveTemplate);
|
|
35898
36688
|
if (Object.keys(orphanPlan.adopted).length > 0) {
|
|
@@ -35986,6 +36776,10 @@ async function doDeployWithPrefetch(stackName, template, createOnlyPrefetch) {
|
|
|
35986
36776
|
const skippedOutputsChanged = !skippedOutputsEqual(currentState.skippedOutputs, this.skippedOutputs);
|
|
35987
36777
|
const healedAttributesPending = this.hasUnpersistedHeals(currentState.resources);
|
|
35988
36778
|
const conditionVerdictsChanged = !conditionVerdictRecordsEqual(readRecordedConditionVerdicts(currentState), conditionVerdicts);
|
|
36779
|
+
if (outputsChanged || exportSetChanged && currentState.exportNames !== void 0) await requireOutputsOnlyApproval({
|
|
36780
|
+
options: this.options,
|
|
36781
|
+
stackName
|
|
36782
|
+
});
|
|
35989
36783
|
if (observedRefresh || maskedFingerprintsBackfilled || conditionVerdictsChanged || outputsChanged || exportSetChanged || skippedOutputsChanged || orphansChanged || healedAttributesPending) try {
|
|
35990
36784
|
const refreshedState = {
|
|
35991
36785
|
version: 10,
|
|
@@ -36019,13 +36813,12 @@ async function doDeployWithPrefetch(stackName, template, createOnlyPrefetch) {
|
|
|
36019
36813
|
this.logger.warn(`Failed to persist no-change state update: ${saveError instanceof Error ? saveError.message : String(saveError)} — drift baseline / outputs will be re-resolved on next deploy.`);
|
|
36020
36814
|
}
|
|
36021
36815
|
}
|
|
36022
|
-
if (!this.options.dryRun) await this.settleJournalAfterSuccess(stackName, [], currentState, currentState.resources, currentEtag === void 0);
|
|
36023
36816
|
return {
|
|
36024
36817
|
stackName,
|
|
36025
36818
|
created: 0,
|
|
36026
36819
|
updated: 0,
|
|
36027
36820
|
deleted: 0,
|
|
36028
|
-
deleteSkipped: 0,
|
|
36821
|
+
deleteSkipped: this.options.dryRun ? 0 : await this.settleJournalAfterSuccess(stackName, [], currentState, currentState.resources, currentEtag === void 0),
|
|
36029
36822
|
updatePartial: 0,
|
|
36030
36823
|
unchanged: Object.keys(currentState.resources).length,
|
|
36031
36824
|
durationMs: Date.now() - startTime,
|
|
@@ -36051,6 +36844,14 @@ async function doDeployWithPrefetch(stackName, template, createOnlyPrefetch) {
|
|
|
36051
36844
|
attributeFallbackCount: this.resolver.getPhysicalIdFallbackCount()
|
|
36052
36845
|
};
|
|
36053
36846
|
}
|
|
36847
|
+
await requireDeploymentApproval({
|
|
36848
|
+
options: this.options,
|
|
36849
|
+
stackName,
|
|
36850
|
+
changes: changes.values(),
|
|
36851
|
+
records: currentState.resources,
|
|
36852
|
+
template: effectiveTemplate,
|
|
36853
|
+
recreateTargetIds: recreateTargetIdsFor(this.options.recreateTargets, stackName)
|
|
36854
|
+
});
|
|
36054
36855
|
this.resolver.resetPhysicalIdFallbackCount();
|
|
36055
36856
|
const progress = {
|
|
36056
36857
|
current: 0,
|
|
@@ -36064,7 +36865,7 @@ async function doDeployWithPrefetch(stackName, template, createOnlyPrefetch) {
|
|
|
36064
36865
|
} : newState));
|
|
36065
36866
|
this.logger.debug(`State saved (ETag: ${newEtag})`);
|
|
36066
36867
|
await forgetRecordedCreateTokens(Object.keys(newState.resources));
|
|
36067
|
-
await Promise.all([this.settleJournalAfterSuccess(stackName, completedOperations, currentState, newState.resources, currentEtag === void 0), this.exportIndexStore ? this.exportIndexStore.updateForStack(stackName, this.stackRegion, importableOutputs({
|
|
36868
|
+
const [journaledOrphansLeft] = await Promise.all([this.settleJournalAfterSuccess(stackName, completedOperations, currentState, newState.resources, currentEtag === void 0), this.exportIndexStore ? this.exportIndexStore.updateForStack(stackName, this.stackRegion, importableOutputs({
|
|
36068
36869
|
...newState,
|
|
36069
36870
|
outputs: this.redactOutputs(newState.outputs)
|
|
36070
36871
|
})) : Promise.resolve()]);
|
|
@@ -36075,7 +36876,7 @@ async function doDeployWithPrefetch(stackName, template, createOnlyPrefetch) {
|
|
|
36075
36876
|
created: actualCounts.created,
|
|
36076
36877
|
updated: actualCounts.updated,
|
|
36077
36878
|
deleted: actualCounts.deleted,
|
|
36078
|
-
deleteSkipped: actualCounts.deleteSkipped,
|
|
36879
|
+
deleteSkipped: actualCounts.deleteSkipped + journaledOrphansLeft,
|
|
36079
36880
|
updatePartial: actualCounts.updatePartial,
|
|
36080
36881
|
nestedUpdatePartial: actualCounts.nestedUpdatePartial,
|
|
36081
36882
|
unchanged: unchangedCount,
|
|
@@ -36400,6 +37201,7 @@ var DeployEngine = class {
|
|
|
36400
37201
|
outputsTemplateSource = Object.create(null);
|
|
36401
37202
|
resolvedExportNames = [];
|
|
36402
37203
|
skippedOutputs;
|
|
37204
|
+
constructPathTemplate;
|
|
36403
37205
|
outputsSourceUsable = true;
|
|
36404
37206
|
attemptedResolvedProps = /* @__PURE__ */ new Map();
|
|
36405
37207
|
liveTaskLabels = /* @__PURE__ */ new Map();
|
|
@@ -36441,6 +37243,7 @@ var DeployEngine = class {
|
|
|
36441
37243
|
this.perResourceSecrets = /* @__PURE__ */ new Map();
|
|
36442
37244
|
this.noEchoAttributeResources = /* @__PURE__ */ new Map();
|
|
36443
37245
|
this.perResourceTemplateProps = /* @__PURE__ */ new Map();
|
|
37246
|
+
this.constructPathTemplate = void 0;
|
|
36444
37247
|
this.perResourceResolvedType = /* @__PURE__ */ new Map();
|
|
36445
37248
|
this.fingerprintNoEchoValues = void 0;
|
|
36446
37249
|
this.fingerprintParameters = void 0;
|
|
@@ -36473,7 +37276,7 @@ var DeployEngine = class {
|
|
|
36473
37276
|
const secrets = this.perResourceSecrets.get(logicalId);
|
|
36474
37277
|
const templateProps = this.perResourceTemplateProps.get(logicalId);
|
|
36475
37278
|
const scrubbed = scrubResourceRecord(this.withHealedAttributes(logicalId, record), secrets ?? /* @__PURE__ */ new Map(), templateProps);
|
|
36476
|
-
resources[logicalId] = withMaskedPropertyFingerprints(scrubbed, record.properties, templateProps, secrets, this.fingerprintNoEchoValues, this.perResourceInputFingerprints.get(logicalId));
|
|
37279
|
+
resources[logicalId] = withConstructPath(withMaskedPropertyFingerprints(scrubbed, record.properties, templateProps, secrets, this.fingerprintNoEchoValues, this.perResourceInputFingerprints.get(logicalId)), constructPathOf(this.constructPathTemplate, logicalId));
|
|
36477
37280
|
}
|
|
36478
37281
|
const orphans = state.orphans?.map((entry) => {
|
|
36479
37282
|
const sameResource = this.perResourceResolvedType.get(entry.logicalId) === entry.state.resourceType;
|
|
@@ -36654,5 +37457,5 @@ DeployEngine.prototype.replacementNameOrigin = replacementNameOrigin;
|
|
|
36654
37457
|
DeployEngine.prototype.orphanedNameCollisionAdvice = orphanedNameCollisionAdvice;
|
|
36655
37458
|
|
|
36656
37459
|
//#endregion
|
|
36657
|
-
export { resourcesNamingDeclaredParameter as $, wholeStringLeavesOf as $a, isWarmThroughputDecrease as $i, explicitRoleArnOrThrow as $n, partitionSensitiveEnv as $o, malformedOutputsWarning as $r, noEchoParameterValueSeed as $t, resolveDynamoDbDeleteBudgetClock as A, printingCorpusOf as Aa, repairMalformedOrphanRecordsForReadOnly as Ai, ccProtectionRegistryTypes as An, rewriteTemplateAssetReferences as Ao, STATE_REGION_DIVERGED as Ar, expectedOwnerParam as As, ccRoutedFinalSnapshotError as At, getPriorAttempts as B, scrubResourceRecord as Ba, findSilentDropProperties as Bi, isTerminationProtectionPropagationError as Bn, validateContainerRepoName as Bo, isReadableResourceEntry as Br, nullPrototypeRecord as Bs, updatePartialMessage as Bt, perType as C, inheritNestedStackParameterAssociations as Ca, refuseMalformedResourcePropertiesForDrift as Ci, ProviderRegistry as Cn, AssetPublisher as Co, isStalePlaceholderArnAttribute as Cr, CFN_TEMPLATE_BODY_LIMIT as Cs, resolveReplacementOldType as Ct, beginDeleteWait as D, hasMaskableValues as Da, refuseMalformedResourcesForDestroy as Di, getCurrentResourceSecrets as Dn, buildAssetRedirectMap as Do, parameterInputsFor as Dr, uploadCfnTemplate as Ds, ATOMIC_FINAL_SNAPSHOT_TYPES as Dt, DYNAMODB_DELETE_MIN_RESOURCE_TIMEOUT_MS as E, createUnionSecretMasker as Ea, refuseMalformedResourcesForDeploy as Ei, isCustomResourceType as En, WorkGraph as Eo, withSharedDrainBudget as Er, findLargeInlineResources as Es, inheritProducerRegions as Et, waitForIndexesSettled as F, errorCauseChain as Fa, repairMalformedResourcesForReadOnly as Fi, withIndeterminateGuard as Fn, getBootstrapMarkerKey as Fo, displayLogicalId as Fr, StageLoadError as Fs, unsupportedFinalSnapshotError as Ft, cyan as G, pathCrossesDottedKey as Ga, findReplacedReadersOfRecreateTargets as Gi, INTRINSIC_KEYS as Gn, describeDockerExecFailure as Go, malformedLocalResourceEntriesWarning as Gr, renderAssemblyPathEscape as Gs, WITHHELD_NAME_DISPLAY as Gt, formatResourceLine as H, DYNAMIC_REFERENCE_TOKEN_SCAN as Ha, withoutSilentDropProperties as Hi, reDisableInstanceApiTermination as Hn, buildDockerImage as Ho, malformedExportNamesWarning as Hr, absoluteAssemblyPathEscape as Hs, DeploymentEventsReader as Ht, ECR_AUTO_DELETE_IMAGES_TAG as I, maskSecretsInError as Ia, unpreviewableOrphanRecords as Ii, isWaitAbandonedError as In, isCrossRegionRedirect as Io, hasReadableOrphans as Ir, processStackMessages as Is, REDACTED_DELETE_ADDRESS_SKIP_REASON as It, red as J, provenPublicValue as Ja, isStatefulRecreateTargetForReplace as Ji, producerRegionsFromState as Jn, finchSecretArgvRefusal as Jo, malformedOrphanRecordsWarning as Jr, resolveBucketRegion as Js, secretBearing as Jt, gray as K, identityKeyFor as Ka, shownType as Ki, IntrinsicFunctionResolver as Kn, describeDockerFailure as Ko, malformedLocalResourcesWarning as Kr, resolveAssemblyPath as Ks, displayTextOrWithheld as Kt, S3_AUTO_DELETE_OBJECTS_TAG as L, maskSecretsInText as La, unreadableOrphanRecords as Li, markWaitAbandoned as Ln, parseBootstrapMarker as Lo, hasReadableOutputs as Lr, defineOwnKey as Ls, isRedactedRecordedValue as Lt, DELETE_INDEX_WAIT_PROCEED_NOTE as M, recordLogOnlyValue as Ma, repairMalformedOutputsForReadOnly as Mi, UNSPECIFIED_SKIP_REASON as Mn, BOOTSTRAP_MARKER_PREFIX as Mo, UNREADABLE_ORPHANS_CONTAINER_ROW as Mr, canonicalizeRegion as Ms, effectiveDeletionPolicy as Mt, INDEX_SETTLE_POLL_INTERVAL_MS as N, shareLogOnlyValues as Na, repairMalformedResourceEntriesForReadOnly as Ni, deleteIndeterminateGuards as Nn, assertAssetBucketRegion as No, UNREADABLE_RESOURCES_MAP_ROW as Nr, derivePartitionAndUrlSuffix as Ns, isFinalSnapshotError as Nt, compensateRemovedDeletionProtection as O, literalSplitDelimitersOf as Oa, refuseMalformedResourcesForExport as Oi, CloudControlProvider as On, createAssetRedirectResolver as Oo, passedParameterClassesOf as Or, CUSTOM_RESOURCE_RESPONSE_OBJECT_DESCRIPTION as Os, PRE_DELETE_SNAPSHOT_TYPES as Ot, deleteTableWithIndexBusyRetry as P, createSecretMasker as Pa, repairMalformedResourcePropertiesForReadOnly as Pi, deleteSkipReason as Pn, ensureAssetStorage as Po, deployRefusesOrphanRowsReason as Pr, AssemblyReader as Ps, refusesFinalSnapshot as Pt, reachableDivergentParameters as Q, recordProvenPublicExpression as Qa, coerceWarmThroughput as Qi, assertSendableRoleArn as Qn, isMalformedEnvKey as Qo, malformedOutputsRefusalMessage as Qr, isWholeDynamicReferenceValue as Qt, hasCdkAutoDeleteTag as R, markSameGenerationBag as Ra, unreadableResourceEntries as Ri, disableInstanceApiTermination as Rn, readBootstrapMarkerBody as Ro, hasReadableResources as Rr, hasOwnKey as Rs, redactedDeleteAddressFields as Rt, isProtectionValueActive as S, liveMatchesUnresolvedTokenFrame as Sa, refuseMalformedResourceEntriesForOrphan as Si, CC_BROKEN_REASON as Sn, shouldRetainResource as So, cfnRefValueFromPhysicalId as Sr, ssmResolvedValueType as Ss, planRollback as St, DynamoDBGlobalTableProvider as T, carryLogOnlyValues as Ta, refuseMalformedResourcePropertiesForOrphan as Ti, wouldReturnToSdkProvider as Tn, stringifyValue as To, parseWebACLArn as Tr, MIGRATE_TMP_PREFIX as Ts, getCurrentProducerRegions as Tt, createReadOnlyAttributeHealerFactory as U, dynamicReferenceTokens as Ua, NO_CC_HANDLERS_REASON as Ui, reEnableInstanceApiTermination as Un, resolveDockerContextDirectory as Uo, malformedExportSourceWarning as Ur, describeFileReadFailure as Us, DeploymentEventsStore as Ut, markRefusedBeforeApplying as V, recoverMaskedOutput as Va, unwrittenCreateOnlyReplacement as Vi, observeThenDisableInstanceApiTermination as Vn, buildDenyExternalAccessPolicy as Vo, malformedDriftResourcePropertiesWarning as Vr, ownValue as Vs, updatePartialReason as Vt, bold as W, isUncertifiedBaselineMaskPosition as Wa, hasNoCloudControlHandlers as Wi, DiffCalculator as Wn, describeDockerCapturedOutput as Wo, malformedLocalOutputsWarning as Wr, displayAssemblyPath as Ws, extractDeploymentEventError as Wt, computeParameterTaint as X, recordMaskOnlyValuesIn as Xa, renderStatefulReason as Xi, applyRoleArnIfSet as Xn, getDockerCmd as Xo, malformedOrphansRefusalMessage as Xr, secretSafeKeyDisplay as Xt, yellow as Y, recordMaskOnlyValue as Ya, isStatefulRecreateTargetSync as Yi, regionLessSecretName as Yn, formatDockerLoginError as Yo, malformedOrphanRowsKeptWarning as Yr, secretBearingStateKeyWarning as Yt, namesAnyDeclaredParameter as Z, recordNoEchoAttributeValues as Za, WARM_THROUGHPUT_MEMBERS as Zi, assertFlagRoleArn as Zn, isDockerClientEnvKey as Zo, malformedOrphansWarning as Zr, exportNameSecretExposure as Zt, makeCanonicalizePropertiesFn as _, canonicalLambdaFunctionName as _a, refuseMalformedResourceEntries as _i, refuseMalformedDesiredTags as _n, importableOutputKeys as _o, carriesDynamicReference as _r, resolveStateBucketWithDefault as _s, destroyStackRecordsView as _t, findNestedTemplateTreeDefect as a, configIntegerRefusal as aa, malformedStateRefusalMessage as ai, DEFAULT_RESOURCE_WARN_AFTER_MS as an, isSingleDynamicReferenceToken as ao, envCredentialsAreAssumedRole as ar, escapeRegExp$2 as as, dropSettledNestedJournals as at, recordedProtectionNote as b, DagBuilder as ba, refuseMalformedResourceEntriesForImport as bi, definedAttributes as bn, orphansAfterRollback as bo, keepsSecretReferenceToken as br, stateBucketExistenceConfirmed as bs, recordAfterRollbackUpdate as bt, renderNestedTemplateTreeDefect as c, replayWarn as ca, refuseMalformedNestedChildOutputs as ci, earliestDefined as cn, S3StateBackend as co, s3BucketDomainName as cr, getDockerImageBySourceHash as cs, recordDisplacedSkips as ct, conditionInputsFrom as d, requireConfigString as da, refuseMalformedOrphans as di, withCreateTokenLedger as dn, acceptedCreateOnlyDropsOf as do, s3BucketWebsiteUrl as dr, getDefaultStateBucketName as ds, withNestedRevertRun as dt, toCfnInteger as ea, malformedRenderedContainersWarning as ei, collectDeclaredOutputNames as en, STATE_SOURCED_BASELINE_RULES as eo, isIamRoleArn as er, redactDockerArgvValues as es, makeSiblingClaimReader as et, parentSuppliedValues as f, prefetchCreateOnlyPropertyPaths as fa, refuseMalformedOrphansForDestroy as fi, acquireIdempotencyToken as fn, describeRegionValueKind as fo, coerceParameterTypedValue as fr, getLegacyStateBucketName as fs, getCurrentNestedStackContext as ft, mergeNoChangeOutputs as g, markAuxiliaryFailure as ga, refuseMalformedResourceAttributesForOrphan as gi, readTagList as gn, hasUnverifiableParameterRefusal as go, isImpossibleEmptyStoredAttribute as gr, resolveSkipPrefix as gs, awaitInFlightSibling as gt, keptWholeReasonText as h, withRetry as ha, refuseMalformedOutputsForDestroy as hi, planTagDiff as hn, hasReasonlessBaselineRefusal as ho, getAccountInfo as hr, resolveCaptureObservedState as hs, replayRollback as ht, childTemplateLoader as i, configBooleanRefusal as ia, malformedScrubResourceEntriesRefusalMessage as ii, DEFAULT_RESOURCE_TIMEOUT_MS as in, WHOLE_DYNAMIC_REFERENCE_PATTERN as io, callerEnvCredentials as ir, warnFinchArgvExposure as is, displacedPhysicalIdShown as it, resolveDynamoDbDeleteBudgetMs as j, recordLogOnlyParameterValue as ja, repairMalformedOrphansForReadOnly as ji, unchangedBehindSecretReference as jn, AssetModeResolver as jo, STATE_RESOURCES_MALFORMED as jr, PARTITION_TABLE as js, createPreDeleteFinalSnapshot as jt, deleteBudgetKey as k, logOnlyValueCount as ka, refuseMalformedState as ki, slowCcOperationTimeoutMs as kn, loadPublishableAssetManifest as ko, JSON_LISTING_HOLE_VALUE as kr, decodeListingKey as ks, buildFinalSnapshotIdentifier as kt, templateIdentity as l, requireConfigArray as la, refuseMalformedOrphanRecords as li, ledgerForStack as ln, rebuildClientForBucketRegion as lo, s3BucketDualStackDomainName as lr, Synthesizer as ls, revertNestedChildFromJournal as lt, isSecretBearingReferenceString as m, describeTypeWithThrottleRetry as ma, refuseMalformedOutputs as mi, DBPROXY_TAG_OPTIONS as mn, hasReadableExportSet as mo, parameterTypeMayLoseSecretIdentity as mr, resolveAutoAssetStorage as ms, replayFailedOperations as mt, IMPLICIT_DELETE_DEPENDENCIES as n, coerceCfnBoolean as na, malformedResourcePropertiesWarning as ni, isExportAliasCollision as nn, STATE_SOURCED_READBACK_RULES as no, AWS_CREDENTIAL_ENV_KEYS as nr, runDockerForeground as ns, NESTED_PENDING_PARENT_REASON as nt, isAbsoluteAssetPath as o, configStringRefusal as oa, previewableOrphanRecords as oi, maskingRetryLogger as on, LockManager as oo, isSettledInstanceState as or, stripControlChars as os, getNestedRevertRun as ot, readRecordedConditionVerdicts as p, templateResourceTypes as pa, refuseMalformedOrphansForOrphan as pi, DBPROXY_TAGS_WHAT as pn, exportNamesCarriedFrom as po, isUnboundTemplateParameter as pr, resolveApp as ps, withNestedStackContext as pt, green as q, carriesSecretMask as qa, MULTI_REGION_RECREATE_BLOCKED_TYPES as qi, classifyReplaySecretRegion as qn, dockerSpawnEnvWithSensitive as qo, malformedOrphanRecordsRefusalMessage as qr, clearBucketRegionCache as qs, exportAliasCollisionScrubWarning as qt, computeImplicitDeleteEdges as r, coerceCfnInteger as ra, malformedResourcesWarning as ri, bindingSkippedOutputs as rn, TEMPLATE_SOURCED_RULES as ro, applyCallerIdentityCredentials as rr, runDockerStreaming as rs, displacedOpClause as rt, listNestedTemplateRows as s, readConfigString as sa, refuseDivergentRecordRegionForDestroy as si, RollbackInlinePolicyWriters as sn, isLockInfoExpired as so, s3BucketArn as sr, AssetManifestLoader as ss, nestedChildStackName as st, DeployEngine as t, toFiniteNumber as ta, malformedResourceEntriesWarning as ti, collectPublishedOutputNames as tn, STATE_SOURCED_CROSS_GENERATION_RULES as to, sendableAssumeRoleCommand as tr, redactedDockerCause as ts, planOrphanAdoption as tt, conditionFingerprint as u, requireConfigObject as ua, refuseMalformedOrphanRecordsForDestroy as ui, reserveStackCreateToken as un, splitImportedOps as uo, s3BucketRegionalDomainName as ur, synthesisStatusMessage as us, revertedNestedRowIds as ut, withResourceDeadline as v, lambdaFunctionNameForMask as va, refuseMalformedResourceEntriesForDeploy as vi, tagMapAsList as vn, importableOutputs as vo, carriesFetchableDynamicReference as vr, resolveStateBucketWithDefaultAndSource as vs, getStackRecords as vt, readProtection as w, recordNestedStackParameterExpressions as wa, refuseMalformedResourcePropertiesForExport as wi, ccBrokenReason as wn, isSensitiveAttributeName as wo, refStateLookupFromResource as wr, CFN_TEMPLATE_URL_LIMIT as ws, findNestedStackTypeChanges as wt, PROTECTION_PROPERTY_BY_TYPE as x, TemplateParser as xa, refuseMalformedResourceEntriesForImportSave as xi, stringifyIfAssigned as xn, orphansCarriedFrom as xo, AWS_NO_VALUE as xr, warnDeprecatedNoPrefixCliFlag as xs, planFailedOps as xt, recordedProtectionEvidence as y, sameLambdaFunctionAddress as ya, refuseMalformedResourceEntriesForDestroy as yi, tagPlanWarning as yn, isReadableBag as yo, isNamelessDynamicReferenceError as yr, resolveUseCdkBootstrapAssets as ys, withStackRecords as yt, isTruthyCfnBoolean as z, redactSecretsForState as za, findActionableSilentDrops as zi, ec2InstanceProtectionSite as zn, validateAssetBucketName as zo, isReadableOrphanRecord as zr, hasPlainPrototype$1 as zs, redactedDeleteAddressSkip as zt };
|
|
36658
|
-
//# sourceMappingURL=deploy-engine-
|
|
37460
|
+
export { resourcesNamingDeclaredParameter as $, dynamicReferenceTokens as $a, withoutSilentDropProperties as $i, reEnableInstanceApiTermination as $n, resolveDockerContextDirectory as $o, malformedExportSourceWarning as $r, absoluteAssemblyPathEscape as $s, displayTextOrWithheld as $t, resolveDynamoDbDeleteBudgetClock as A, DagBuilder as Aa, refuseMalformedResourceEntriesForImport as Ai, definedAttributes as An, orphansAfterRollback as Ao, keepsSecretReferenceToken as Ar, resolveUseCdkBootstrapAssets as As, resolveReplacementOldType as At, getPriorAttempts as B, printingCorpusOf as Ba, refuseMalformedState as Bi, ccProtectionRegistryTypes as Bn, rewriteTemplateAssetReferences as Bo, STATE_REGION_DIVERGED as Br, decodeListingKey as Bs, isFinalSnapshotError as Bt, perType as C, prefetchCreateOnlyPropertyPaths as Ca, refuseMalformedOrphansForOrphan as Ci, DBPROXY_TAGS_WHAT as Cn, exportNamesCarriedFrom as Co, isUnboundTemplateParameter as Cr, loadCdkJson as Cs, getStackRecords as Ct, beginDeleteWait as D, canonicalLambdaFunctionName as Da, refuseMalformedResourceEntries as Di, refuseMalformedDesiredTags as Dn, importableOutputKeys as Do, carriesDynamicReference as Dr, resolveSkipPrefix as Ds, isJournaledOrphan as Dt, DYNAMODB_DELETE_MIN_RESOURCE_TIMEOUT_MS as E, withRetry as Ea, refuseMalformedResourceAttributesForOrphan as Ei, readTagList as En, hasUnverifiableParameterRefusal as Eo, isImpossibleEmptyStoredAttribute as Er, resolveCaptureObservedState as Es, demoteSupersededOrphans as Et, waitForIndexesSettled as F, carryLogOnlyValues as Fa, refuseMalformedResourcePropertiesForExport as Fi, wouldReturnToSdkProvider as Fn, stringifyValue as Fo, parseWebACLArn as Fr, CFN_TEMPLATE_URL_LIMIT as Fs, PRE_DELETE_SNAPSHOT_TYPES as Ft, cyan as G, errorCauseChain as Ga, repairMalformedResourcePropertiesForReadOnly as Gi, withIndeterminateGuard as Gn, getBootstrapMarkerKey as Go, displayLogicalId as Gr, AssemblyReader as Gs, redactedDeleteAddressFields as Gt, formatResourceLine as H, recordLogOnlyValue as Ha, repairMalformedOrphansForReadOnly as Hi, UNSPECIFIED_SKIP_REASON as Hn, BOOTSTRAP_MARKER_PREFIX as Ho, UNREADABLE_ORPHANS_CONTAINER_ROW as Hr, PARTITION_TABLE as Hs, unsupportedFinalSnapshotError as Ht, ECR_AUTO_DELETE_IMAGES_TAG as I, createUnionSecretMasker as Ia, refuseMalformedResourcePropertiesForOrphan as Ii, isCustomResourceType as In, WorkGraph as Io, withSharedDrainBudget as Ir, MIGRATE_TMP_PREFIX as Is, buildFinalSnapshotIdentifier as It, red as J, markSameGenerationBag as Ja, unreadableOrphanRecords as Ji, disableInstanceApiTermination as Jn, readBootstrapMarkerBody as Jo, hasReadableResources as Jr, defineOwnKey as Js, updatePartialReason as Jt, gray as K, maskSecretsInError as Ka, repairMalformedResourcesForReadOnly as Ki, isWaitAbandonedError as Kn, isCrossRegionRedirect as Ko, hasReadableOrphans as Kr, StageLoadError as Ks, redactedDeleteAddressSkip as Kt, S3_AUTO_DELETE_OBJECTS_TAG as L, hasMaskableValues as La, refuseMalformedResourcesForDeploy as Li, getCurrentResourceSecrets as Ln, buildAssetRedirectMap as Lo, parameterInputsFor as Lr, findLargeInlineResources as Ls, ccRoutedFinalSnapshotError as Lt, DELETE_INDEX_WAIT_PROCEED_NOTE as M, liveMatchesUnresolvedTokenFrame as Ma, refuseMalformedResourceEntriesForOrphan as Mi, CC_BROKEN_REASON as Mn, shouldRetainResource as Mo, cfnRefValueFromPhysicalId as Mr, warnDeprecatedNoPrefixCliFlag as Ms, getCurrentProducerRegions as Mt, INDEX_SETTLE_POLL_INTERVAL_MS as N, inheritNestedStackParameterAssociations as Na, refuseMalformedResourcePropertiesForDestroy as Ni, ProviderRegistry as Nn, AssetPublisher as No, isStalePlaceholderArnAttribute as Nr, ssmResolvedValueType as Ns, inheritProducerRegions as Nt, compensateRemovedDeletionProtection as O, lambdaFunctionNameForMask as Oa, refuseMalformedResourceEntriesForDeploy as Oi, tagMapAsList as On, importableOutputs as Oo, carriesFetchableDynamicReference as Or, resolveStateBucketWithDefault as Os, planFailedOps as Ot, deleteTableWithIndexBusyRetry as P, recordNestedStackParameterExpressions as Pa, refuseMalformedResourcePropertiesForDrift as Pi, ccBrokenReason as Pn, isSensitiveAttributeName as Po, refStateLookupFromResource as Pr, CFN_TEMPLATE_BODY_LIMIT as Ps, ATOMIC_FINAL_SNAPSHOT_TYPES as Pt, reachableDivergentParameters as Q, DYNAMIC_REFERENCE_TOKEN_SCAN as Qa, unwrittenCreateOnlyReplacement as Qi, reDisableInstanceApiTermination as Qn, buildDockerImage as Qo, malformedExportNamesWarning as Qr, ownValue as Qs, WITHHELD_NAME_DISPLAY as Qt, hasCdkAutoDeleteTag as R, literalSplitDelimitersOf as Ra, refuseMalformedResourcesForDestroy as Ri, CloudControlProvider as Rn, createAssetRedirectResolver as Ro, passedParameterClassesOf as Rr, uploadCfnTemplate as Rs, createPreDeleteFinalSnapshot as Rt, isProtectionValueActive as S, requireConfigString as Sa, refuseMalformedOrphansForDestroy as Si, acquireIdempotencyToken as Sn, describeRegionValueKind as So, coerceParameterTypedValue as Sr, getLegacyStateBucketName as Ss, destroyStackRecordsView as St, DynamoDBGlobalTableProvider as T, describeTypeWithThrottleRetry as Ta, refuseMalformedOutputsForDestroy as Ti, planTagDiff as Tn, hasReasonlessBaselineRefusal as To, getAccountInfo as Tr, resolveAutoAssetStorage as Ts, recordAfterRollbackUpdate as Tt, createReadOnlyAttributeHealerFactory as U, shareLogOnlyValues as Ua, repairMalformedOutputsForReadOnly as Ui, deleteIndeterminateGuards as Un, assertAssetBucketRegion as Uo, UNREADABLE_RESOURCES_MAP_ROW as Ur, canonicalizeRegion as Us, REDACTED_DELETE_ADDRESS_SKIP_REASON as Ut, markRefusedBeforeApplying as V, recordLogOnlyParameterValue as Va, repairMalformedOrphanRecordsForReadOnly as Vi, unchangedBehindSecretReference as Vn, AssetModeResolver as Vo, STATE_RESOURCES_MALFORMED as Vr, expectedOwnerParam as Vs, refusesFinalSnapshot as Vt, bold as W, createSecretMasker as Wa, repairMalformedResourceEntriesForReadOnly as Wi, deleteSkipReason as Wn, ensureAssetStorage as Wo, deployRefusesOrphanRowsReason as Wr, derivePartitionAndUrlSuffix as Ws, isRedactedRecordedValue as Wt, computeParameterTaint as X, scrubResourceRecord as Xa, findActionableSilentDrops as Xi, isTerminationProtectionPropagationError as Xn, validateContainerRepoName as Xo, isReadableResourceEntry as Xr, hasPlainPrototype$1 as Xs, DeploymentEventsStore as Xt, yellow as Y, redactSecretsForState as Ya, unreadableResourceEntries as Yi, ec2InstanceProtectionSite as Yn, validateAssetBucketName as Yo, isReadableOrphanRecord as Yr, hasOwnKey as Ys, DeploymentEventsReader as Yt, namesAnyDeclaredParameter as Z, recoverMaskedOutput as Za, findSilentDropProperties as Zi, observeThenDisableInstanceApiTermination as Zn, buildDenyExternalAccessPolicy as Zo, malformedDriftResourcePropertiesWarning as Zr, nullPrototypeRecord as Zs, extractDeploymentEventError as Zt, makeCanonicalizePropertiesFn as _, configStringRefusal as _a, refuseDivergentRecordRegionForDestroy as _i, RollbackInlinePolicyWriters as _n, isLockInfoExpired as _o, s3BucketArn as _r, AssetManifestLoader as _s, getCurrentNestedStackContext as _t, findNestedTemplateTreeDefect as a, isStatefulRecreateTargetForReplace as aa, resolveBucketRegion as ac, malformedOrphanRowsKeptWarning as ai, isWholeDynamicReferenceValue as an, recordMaskOnlyValue as ao, regionLessSecretName as ar, formatDockerLoginError as as, makeSiblingClaimReader as at, recordedProtectionNote as b, requireConfigArray as ba, refuseMalformedOrphanRecordsForDestroy as bi, reserveStackCreateToken as bn, splitImportedOps as bo, s3BucketRegionalDomainName as br, synthesisStatusMessage as bs, replayRollback as bt, renderNestedTemplateTreeDefect as c, WARM_THROUGHPUT_MEMBERS as ca, malformedOutputsRefusalMessage as ci, collectPublishedOutputNames as cn, recordProvenPublicExpression as co, assertSendableRoleArn as cr, isMalformedEnvKey as cs, displacedOpClause as ct, conditionInputsFrom as d, toCfnInteger as da, malformedResourceEntriesWarning as di, DEFAULT_RESOURCE_TIMEOUT_MS as dn, STATE_SOURCED_CROSS_GENERATION_RULES as do, sendableAssumeRoleCommand as dr, redactedDockerCause as ds, getNestedRevertRun as dt, NO_CC_HANDLERS_REASON as ea, describeFileReadFailure as ec, malformedLocalOutputsWarning as ei, exportAliasCollisionScrubWarning as en, isUncertifiedBaselineMaskPosition as eo, DiffCalculator as er, describeDockerCapturedOutput as es, deleteJournaledOrphans as et, parentSuppliedValues as f, toFiniteNumber as fa, malformedResourcePropertiesWarning as fi, DEFAULT_RESOURCE_WARN_AFTER_MS as fn, STATE_SOURCED_READBACK_RULES as fo, AWS_CREDENTIAL_ENV_KEYS as fr, runDockerForeground as fs, nestedChildStackName as ft, mergeNoChangeOutputs as g, configIntegerRefusal as ga, previewableOrphanRecords as gi, formatDestructiveChange as gn, LockManager as go, isSettledInstanceState as gr, stripControlChars as gs, withNestedRevertRun as gt, keptWholeReasonText as h, configBooleanRefusal as ha, malformedStateRefusalMessage as hi, findDestructiveChanges as hn, isSingleDynamicReferenceToken as ho, envCredentialsAreAssumedRole as hr, escapeRegExp$3 as hs, revertedNestedRowIds as ht, childTemplateLoader as i, MULTI_REGION_RECREATE_BLOCKED_TYPES as ia, clearBucketRegionCache as ic, malformedOrphanRecordsWarning as ii, exportNameSecretExposure as in, provenPublicValue as io, producerRegionsFromState as ir, finchSecretArgvRefusal as is, sameJournaledOrphans as it, resolveDynamoDbDeleteBudgetMs as j, TemplateParser as ja, refuseMalformedResourceEntriesForImportSave as ji, stringifyIfAssigned as jn, orphansCarriedFrom as jo, AWS_NO_VALUE as jr, stateBucketExistenceConfirmed as js, findNestedStackTypeChanges as jt, deleteBudgetKey as k, sameLambdaFunctionAddress as ka, refuseMalformedResourceEntriesForDestroy as ki, tagPlanWarning as kn, isReadableBag as ko, isNamelessDynamicReferenceError as kr, resolveStateBucketWithDefaultAndSource as ks, planRollback as kt, templateIdentity as l, coerceWarmThroughput as la, malformedOutputsWarning as li, isExportAliasCollision as ln, wholeStringLeavesOf as lo, explicitRoleArnOrThrow as lr, partitionSensitiveEnv as ls, displacedPhysicalIdShown as lt, isSecretBearingReferenceString as m, coerceCfnInteger as ma, malformedScrubResourceEntriesRefusalMessage as mi, constructPathOf as mn, WHOLE_DYNAMIC_REFERENCE_PATTERN as mo, callerEnvCredentials as mr, warnFinchArgvExposure as ms, revertNestedChildFromJournal as mt, IMPLICIT_DELETE_DEPENDENCIES as n, findReplacedReadersOfRecreateTargets as na, renderAssemblyPathEscape as nc, malformedLocalResourcesWarning as ni, secretBearingStateKeyWarning as nn, identityKeyFor as no, IntrinsicFunctionResolver as nr, describeDockerFailure as ns, journaledOrphanLines as nt, isAbsoluteAssetPath as o, isStatefulRecreateTargetSync as oa, malformedOrphansRefusalMessage as oi, noEchoParameterValueSeed as on, recordMaskOnlyValuesIn as oo, applyRoleArnIfSet as or, getDockerCmd as os, planOrphanAdoption as ot, readRecordedConditionVerdicts as p, coerceCfnBoolean as pa, malformedResourcesWarning as pi, maskingRetryLogger as pn, TEMPLATE_SOURCED_RULES as po, applyCallerIdentityCredentials as pr, runDockerStreaming as ps, recordDisplacedSkips as pt, green as q, maskSecretsInText as qa, unpreviewableOrphanRecords as qi, markWaitAbandoned as qn, parseBootstrapMarker as qo, hasReadableOutputs as qr, processStackMessages as qs, updatePartialMessage as qt, computeImplicitDeleteEdges as r, shownType as ra, resolveAssemblyPath as rc, malformedOrphanRecordsRefusalMessage as ri, secretSafeKeyDisplay as rn, carriesSecretMask as ro, classifyReplaySecretRegion as rr, dockerSpawnEnvWithSensitive as rs, loadJournaledOrphans as rt, listNestedTemplateRows as s, renderStatefulReason as sa, malformedOrphansWarning as si, collectDeclaredOutputNames as sn, recordNoEchoAttributeValues as so, assertFlagRoleArn as sr, isDockerClientEnvKey as ss, NESTED_PENDING_PARENT_REASON as st, DeployEngine as t, hasNoCloudControlHandlers as ta, displayAssemblyPath as tc, malformedLocalResourceEntriesWarning as ti, secretBearing as tn, pathCrossesDottedKey as to, INTRINSIC_KEYS as tr, describeDockerExecFailure as ts, isHandledOrphan as tt, conditionFingerprint as u, isWarmThroughputDecrease as ua, malformedRenderedContainersWarning as ui, bindingSkippedOutputs as un, STATE_SOURCED_BASELINE_RULES as uo, isIamRoleArn as ur, redactDockerArgvValues as us, dropSettledNestedJournals as ut, withResourceDeadline as v, readConfigString as va, refuseMalformedNestedChildOutputs as vi, earliestDefined as vn, S3StateBackend as vo, s3BucketDomainName as vr, getDockerImageBySourceHash as vs, withNestedStackContext as vt, readProtection as w, templateResourceTypes as wa, refuseMalformedOutputs as wi, DBPROXY_TAG_OPTIONS as wn, hasReadableExportSet as wo, parameterTypeMayLoseSecretIdentity as wr, resolveApp as ws, withStackRecords as wt, PROTECTION_PROPERTY_BY_TYPE as x, requireConfigObject as xa, refuseMalformedOrphans as xi, withCreateTokenLedger as xn, acceptedCreateOnlyDropsOf as xo, s3BucketWebsiteUrl as xr, getDefaultStateBucketName as xs, awaitInFlightSibling as xt, recordedProtectionEvidence as y, replayWarn as ya, refuseMalformedOrphanRecords as yi, ledgerForStack as yn, rebuildClientForBucketRegion as yo, s3BucketDualStackDomainName as yr, Synthesizer as ys, replayFailedOperations as yt, isTruthyCfnBoolean as z, logOnlyValueCount as za, refuseMalformedResourcesForExport as zi, slowCcOperationTimeoutMs as zn, loadPublishableAssetManifest as zo, JSON_LISTING_HOLE_VALUE as zr, CUSTOM_RESOURCE_RESPONSE_OBJECT_DESCRIPTION as zs, effectiveDeletionPolicy as zt };
|
|
37461
|
+
//# sourceMappingURL=deploy-engine-D7204v7Z.js.map
|