Skip to content

Instantly share code, notes, and snippets.

@tmokmss
Created April 22, 2024 05:01
Show Gist options
  • Star 0 You must be signed in to star a gist
  • Fork 0 You must be signed in to fork a gist
  • Save tmokmss/aeb85fc8c3076cbc5d9ae1c6698969d1 to your computer and use it in GitHub Desktop.
Save tmokmss/aeb85fc8c3076cbc5d9ae1c6698969d1 to your computer and use it in GitHub Desktop.
Cross region AWS API proxy for Step Functions
import { Handler } from 'aws-lambda';
type Input = {
/**
* AWS Region name to call the service
*/
targetRegion: string;
/**
* AWS service name (must be in AWS SDK for JS v3 style)
*/
service: string;
/**
* API Action name (must be in PascalCase)
*/
action: string;
/**
* request parameters to call the API (must be in AWS SDK for JS v3 style)
*/
parameters: any;
};
// reference: code from CDK AwsCustomResource
function findV3ClientConstructor(pkg: object) {
const [_clientName, ServiceClient] = Object.entries(pkg).find(([name]) => {
// Services expose a base __Client class that we don't want ever
return name.endsWith('Client') && name !== '__Client';
}) as [
string,
{
new (config: any): {
send: (command: any) => Promise<any>;
config: any;
};
},
];
return ServiceClient;
}
function findCommandClass(pkg: object, action: string) {
const commandName = `${action}Command`;
const Command = Object.entries(pkg).find(([name]) => name.toLowerCase() === commandName.toLowerCase())?.[1] as {
new (input: any): any;
};
if (!Command) {
throw new Error(`Unable to find command named: ${commandName} for action: ${action} in service package ${pkg}`);
}
return Command;
}
export const handler: Handler<Input> = async (event, context) => {
// Log the event to understand the incoming request structure
console.log('Event: ', event);
try {
// eslint-disable-next-line @typescript-eslint/no-var-requires
const pkg = require(`@aws-sdk/client-${event.service}`);
const Client = findV3ClientConstructor(pkg);
const Command = findCommandClass(pkg, event.action);
const client = new Client({ region: event.targetRegion });
const command = new Command(event.parameters);
const res = await client.send(command);
return res;
} catch (error) {
console.error('Error: ', error);
throw error;
}
};
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment