Created
October 21, 2023 12:03
-
-
Save orangain/569b8df21cbce82057d606459fc44701 to your computer and use it in GitHub Desktop.
cdk-auto-mapper.ts: Deno script to fill CDK's import mapping file using result of `aws cloudformation list-stack-resources`
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
if (Deno.args.length !== 2) { | |
console.error( | |
"Usage: deno run --allow-read cdk-auto-mapper.ts <resource-file-path> <mapping-file-path>" | |
); | |
Deno.exit(1); | |
} | |
const [resourcePath, mappingPath] = Deno.args; | |
const resourceFileContent = await Deno.readTextFile(resourcePath); | |
const mappingFileContent = await Deno.readTextFile(mappingPath); | |
type Resources = { | |
StackResourceSummaries: ResourceSummary[]; | |
}; | |
type ResourceSummary = { | |
LogicalResourceId: string; | |
PhysicalResourceId: string; | |
ResourceType: string; | |
}; | |
type Mapping = Record<string, Record<string, string>>; | |
const resources = JSON.parse(resourceFileContent) as Resources; | |
const mapping = JSON.parse(mappingFileContent) as Mapping; | |
const resourceMap = resources.StackResourceSummaries.reduce((acc, resource) => { | |
acc[resource.LogicalResourceId] = resource; | |
return acc; | |
}, {} as Record<string, ResourceSummary>); | |
Object.entries(mapping).forEach(([logicalId, attributes]) => { | |
const resource = resourceMap[logicalId]; | |
if (!resource) { | |
throw new Error(`Resource ${logicalId} not found`); | |
} | |
const attributesResolver = getAttributesResolver(resource.ResourceType); | |
if (attributesResolver !== null) { | |
const physicalId = resource.PhysicalResourceId; | |
const resolvedAttributes = attributesResolver(physicalId); | |
Object.assign(attributes, resolvedAttributes); | |
} else { | |
Object.keys(attributes).forEach((attribute) => { | |
attributes[attribute] = resource.PhysicalResourceId; | |
}); | |
} | |
}); | |
console.log(JSON.stringify(mapping, null, 2)); | |
type AttributesResolver = (physicalId: string) => Record<string, string>; | |
function getAttributesResolver( | |
resourceType: string | |
): AttributesResolver | null { | |
const attributesResolvers: Record<string, AttributesResolver> = { | |
"AWS::EC2::EIP": (physicalId) => { | |
return { | |
PublicIp: physicalId, | |
}; | |
}, | |
"AWS::EC2::Route": (physicalId) => { | |
const [routeTableId, destinationCidrBlock] = physicalId.split("|"); | |
return { | |
RouteTableId: routeTableId, | |
CidrBlock: destinationCidrBlock, | |
}; | |
}, | |
}; | |
return attributesResolvers[resourceType] ?? null; | |
} |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment