Usar o AWS CDK para criar um fluxo de trabalho padrão no Step Functions
É possível usar o framework de infraestrutura como código (IAC) do AWS Cloud Development Kit (AWS CDK) para criar uma máquina de estado do AWS Step Functions que contenha uma função do AWS Lambda.
Você definirá a infraestrutura da AWS usando uma das linguagens aceitas do CDK. Depois de definir a infraestrutura, você sintetizará a aplicação em um modelo do CloudFormation e o implantará na conta da AWS.
Você usará esse método para definir uma máquina de estado do Step Functions que contém uma função do Lambda e executará a máquina de estado usando o Console de gerenciamento da AWS do Step Functions.
Antes de começar este tutorial, você deve configurar seu ambiente de desenvolvimento do AWS CDK conforme descrito em Introdução aos AWS CDK – pré-requisitos no Guia do desenvolvedor do AWS Cloud Development Kit (AWS CDK). Então instale o AWS CDK com o seguinte comando na AWS CLI:
npm install -g aws-cdk
Este tutorial produz o mesmo resultado que Usar o CloudFormation para criar um fluxo de trabalho no Step Functions. Porém, neste tutorial, o AWS CDK não exige que você crie nenhuma função do IAM; o AWS CDK faz isso por você. A versão do AWS CDK também inclui uma etapa Estado de sucesso do fluxo de trabalho para ilustrar como adicionar mais etapas à sua máquina de estado.
Para implantar uma aplicação de tecnologia sem servidor de exemplo que inicia um fluxo de trabalho do Step Functions usando o AWS CDK com o TypeScript, consulte Deploy with AWS CDK no Workshop AWS Step Functions.
Etapa 1: configurar o projeto do AWS CDK
-
No diretório inicial ou em outro diretório, se preferir, execute o comando a seguir para criar um diretório para a nova aplicação AWS CDK.
Dê ao diretório o nome step. O modelo de aplicação do AWS CDK usa o nome do diretório para gerar nomes para arquivos e classes de origem. Se você escolher outro nome, sua aplicação não combinará com este tutorial.
- TypeScript
-
mkdir step && cd step
- JavaScript
-
mkdir step && cd step
- Python
-
mkdir step && cd step
- Java
-
mkdir step && cd step
- C#
-
Verifique se você instalou o .NET versão 6.0 ou superior. Para obter informações, consulte Versões compatíveis.
mkdir step && cd step
-
Inicialize o aplicativo usando o comando cdk init. Especifique o modelo (“aplicação”) e a linguagem de programação desejados conforme mostrado nos exemplos a seguir.
- TypeScript
-
cdk init --language typescript
- JavaScript
-
cdk init --language javascript
- Python
-
cdk init --language python
Depois que o projeto foi inicializado, ative o ambiente virtual do projeto e instale as dependências de linha de base do AWS CDK.
source .venv/bin/activate
python -m pip install -r requirements.txt
- Java
-
cdk init --language java
- C#
-
cdk init --language csharp
Etapa 2: Usar o AWS CDK para criar uma máquina de estado
Primeiro, vamos apresentarem as partes individuais do código que definem a função do Lambda e a máquina de estado do Step Functions. Em seguida, explicaremos como colocá-los juntos em sua aplicação AWS CDK. Por fim, você verá como sintetizar e implantar esses recursos.
Como criar uma função do Lambda
O código AWS CDK a seguir define a função Lambda, fornecendo seu código-fonte em linha.
- TypeScript
-
const helloFunction = new lambda.Function(this, 'MyLambdaFunction', {
code: lambda.Code.fromInline(`
exports.handler = (event, context, callback) => {
callback(null, "Hello World!");
};
`),
runtime: lambda.Runtime.NODEJS_18_X,
handler: "index.handler",
timeout: cdk.Duration.seconds(3)
});
- JavaScript
-
const helloFunction = new lambda.Function(this, 'MyLambdaFunction', {
code: lambda.Code.fromInline(`
exports.handler = (event, context, callback) => {
callback(null, "Hello World!");
};
`),
runtime: lambda.Runtime.NODEJS_18_X,
handler: "index.handler",
timeout: cdk.Duration.seconds(3)
});
- Python
-
hello_function = lambda_.Function(
self, "MyLambdaFunction",
code=lambda_.Code.from_inline("""
exports.handler = (event, context, callback) => {
callback(null, "Hello World!");
}"""),
runtime=lambda_.Runtime.NODEJS_18_X,
handler="index.handler",
timeout=Duration.seconds(25))
- Java
-
final Function helloFunction = Function.Builder.create(this, "MyLambdaFunction")
.code(Code.fromInline(
"exports.handler = (event, context, callback) => { callback(null, 'Hello World!' );}"))
.runtime(Runtime.NODEJS_18_X)
.handler("index.handler")
.timeout(Duration.seconds(25))
.build();
- C#
-
var helloFunction = new Function(this, "MyLambdaFunction", new FunctionProps
{
Code = Code.FromInline(@"`
exports.handler = (event, context, callback) => {
callback(null, 'Hello World!');
}"),
Runtime = Runtime.NODEJS_12_X,
Handler = "index.handler",
Timeout = Duration.Seconds(25)
});
Você pode ver, neste exemplo de código curto:
-
O nome lógico da função, MyLambdaFunction.
-
O código-fonte da função, incorporado como uma string no código-fonte da aplicação AWS CDK.
-
Outros atributos da função, como o runtime a ser usado (Node 18.x), o ponto de entrada da função e um tempo limite.
Para criar uma máquina de estado do
Nossa máquina de estados tem dois estados: uma função do Lambda, tarefa e um estado do Estado de sucesso do fluxo de trabalho. A função exige criar um Step Functions Estado de tarefa do fluxo de trabalho que invoca nossa função. Esse estado de tarefa é usado como a primeira etapa na máquina de estado. O estado de sucesso é adicionado à máquina de estado usando o método next() do estado da tarefa. O código a seguir primeiro invoca a função chamada MyLambdaTask e depois, usa o método next() para definir um estado de sucesso chamado GreetedWorld.
- TypeScript
-
const stateMachine = new sfn.StateMachine(this, 'MyStateMachine', {
definition: new tasks.LambdaInvoke(this, "MyLambdaTask", {
lambdaFunction: helloFunction
}).next(new sfn.Succeed(this, "GreetedWorld"))
});
- JavaScript
-
const stateMachine = new sfn.StateMachine(this, 'MyStateMachine', {
definition: new tasks.LambdaInvoke(this, "MyLambdaTask", {
lambdaFunction: helloFunction
}).next(new sfn.Succeed(this, "GreetedWorld"))
});
- Python
-
state_machine = sfn.StateMachine(
self, "MyStateMachine",
definition=tasks.LambdaInvoke(
self, "MyLambdaTask",
lambda_function=hello_function)
.next(sfn.Succeed(self, "GreetedWorld")))
- Java
-
final StateMachine stateMachine = StateMachine.Builder.create(this, "MyStateMachine")
.definition(LambdaInvoke.Builder.create(this, "MyLambdaTask")
.lambdaFunction(helloFunction)
.build()
.next(new Succeed(this, "GreetedWorld")))
.build();
- C#
-
var stateMachine = new StateMachine(this, "MyStateMachine", new StateMachineProps {
DefinitionBody = DefinitionBody.FromChainable(new LambdaInvoke(this, "MyLambdaTask", new LambdaInvokeProps
{
LambdaFunction = helloFunction
})
.Next(new Succeed(this, "GreetedWorld")))
});
Para criar e implantar a aplicação AWS CDK
No projeto AWS CDK que acaba de ser criado, edite o arquivo que contém a definição de pilha para que seja parecido com o código de exemplo a seguir. Você vai reconhecer as definições da função do Lambda e da máquina de estado do Step Functions das seções anteriores.
-
Atualize a pilha como mostrado nos exemplos a seguir.
- TypeScript
-
Atualize o lib/step-stack.ts com o código a seguir.
import * as cdk from 'aws-cdk-lib';
import * as lambda from 'aws-cdk-lib/aws-lambda';
import * as sfn from 'aws-cdk-lib/aws-stepfunctions';
import * as tasks from 'aws-cdk-lib/aws-stepfunctions-tasks';
export class StepStack extends cdk.Stack {
constructor(app: cdk.App, id: string) {
super(app, id);
const helloFunction = new lambda.Function(this, 'MyLambdaFunction', {
code: lambda.Code.fromInline(`
exports.handler = (event, context, callback) => {
callback(null, "Hello World!");
};
`),
runtime: lambda.Runtime.NODEJS_18_X,
handler: "index.handler",
timeout: cdk.Duration.seconds(3)
});
const stateMachine = new sfn.StateMachine(this, 'MyStateMachine', {
definition: new tasks.LambdaInvoke(this, "MyLambdaTask", {
lambdaFunction: helloFunction
}).next(new sfn.Succeed(this, "GreetedWorld"))
});
}
}
- JavaScript
-
Atualize o lib/step-stack.js com o código a seguir.
import * as cdk from 'aws-cdk-lib';
import * as lambda from 'aws-cdk-lib/aws-lambda';
import * as sfn from 'aws-cdk-lib/aws-stepfunctions';
import * as tasks from 'aws-cdk-lib/aws-stepfunctions-tasks';
export class StepStack extends cdk.Stack {
constructor(app, id) {
super(app, id);
const helloFunction = new lambda.Function(this, 'MyLambdaFunction', {
code: lambda.Code.fromInline(`
exports.handler = (event, context, callback) => {
callback(null, "Hello World!");
};
`),
runtime: lambda.Runtime.NODEJS_18_X,
handler: "index.handler",
timeout: cdk.Duration.seconds(3)
});
const stateMachine = new sfn.StateMachine(this, 'MyStateMachine', {
definition: new tasks.LambdaInvoke(this, "MyLambdaTask", {
lambdaFunction: helloFunction
}).next(new sfn.Succeed(this, "GreetedWorld"))
});
}
}
- Python
-
Atualize o step/step_stack.py com o código a seguir.
from aws_cdk import (
Duration,
Stack,
aws_stepfunctions as sfn,
aws_stepfunctions_tasks as tasks,
aws_lambda as lambda_
)
class StepStack(Stack):
def __init__(self, scope: Construct, construct_id: str, **kwargs) -> None:
super().__init__(scope, construct_id, **kwargs)
hello_function = lambda_.Function(
self, "MyLambdaFunction",
code=lambda_.Code.from_inline("""
exports.handler = (event, context, callback) => {
callback(null, "Hello World!");
}"""),
runtime=lambda_.Runtime.NODEJS_18_X,
handler="index.handler",
timeout=Duration.seconds(25))
state_machine = sfn.StateMachine(
self, "MyStateMachine",
definition=tasks.LambdaInvoke(
self, "MyLambdaTask",
lambda_function=hello_function)
.next(sfn.Succeed(self, "GreetedWorld")))
- Java
-
Atualize o src/main/java/com.myorg/StepStack.java com o código a seguir.
package com.myorg;
import software.constructs.Construct;
import software.amazon.awscdk.Stack;
import software.amazon.awscdk.StackProps;
import software.amazon.awscdk.Duration;
import software.amazon.awscdk.services.lambda.Code;
import software.amazon.awscdk.services.lambda.Function;
import software.amazon.awscdk.services.lambda.Runtime;
import software.amazon.awscdk.services.stepfunctions.StateMachine;
import software.amazon.awscdk.services.stepfunctions.Succeed;
import software.amazon.awscdk.services.stepfunctions.tasks.LambdaInvoke;
public class StepStack extends Stack {
public StepStack(final Construct scope, final String id) {
this(scope, id, null);
}
public StepStack(final Construct scope, final String id, final StackProps props) {
super(scope, id, props);
final Function helloFunction = Function.Builder.create(this, "MyLambdaFunction")
.code(Code.fromInline(
"exports.handler = (event, context, callback) => { callback(null, 'Hello World!' );}"))
.runtime(Runtime.NODEJS_18_X)
.handler("index.handler")
.timeout(Duration.seconds(25))
.build();
final StateMachine stateMachine = StateMachine.Builder.create(this, "MyStateMachine")
.definition(LambdaInvoke.Builder.create(this, "MyLambdaTask")
.lambdaFunction(helloFunction)
.build()
.next(new Succeed(this, "GreetedWorld")))
.build();
}
}
- C#
-
Atualize o src/Step/StepStack.cs com o código a seguir.
using Amazon.CDK;
using Constructs;
using Amazon.CDK.AWS.Lambda;
using Amazon.CDK.AWS.StepFunctions;
using Amazon.CDK.AWS.StepFunctions.Tasks;
namespace Step
{
public class StepStack : Stack
{
internal StepStack(Construct scope, string id, IStackProps props = null) : base(scope, id, props)
{
var helloFunction = new Function(this, "MyLambdaFunction", new FunctionProps
{
Code = Code.FromInline(@"exports.handler = (event, context, callback) => {
callback(null, 'Hello World!');
}"),
Runtime = Runtime.NODEJS_18_X,
Handler = "index.handler",
Timeout = Duration.Seconds(25)
});
var stateMachine = new StateMachine(this, "MyStateMachine", new StateMachineProps
{
DefinitionBody = DefinitionBody.FromChainable(new LambdaInvoke(this, "MyLambdaTask", new LambdaInvokeProps
{
LambdaFunction = helloFunction
})
.Next(new Succeed(this, "GreetedWorld")))
});
}
}
}
-
Salve o arquivo de origem e execute o comando cdk synth no diretório principal da aplicação.
O AWS CDK executa a aplicação e sintetiza um modelo do CloudFormation com base nela. O AWS CDK então exibe o modelo.
Se você usou o TypeScript para criar seu projeto do AWS CDK, a execução do comando cdk synth pode retornar o seguinte erro.
TSError: ⨯ Unable to compile TypeScript:
bin/step.ts:7:33 - error TS2554: Expected 2 arguments, but got 3.
Modifique o arquivo bin/step.ts conforme mostrado no exemplo a seguir para resolver esse erro.
#!/usr/bin/env node
import 'source-map-support/register';
import * as cdk from 'aws-cdk-lib';
import { StepStack } from '../lib/step-stack';
const app = new cdk.App();
new StepStack(app, 'StepStack');
app.synth();
-
Para implantar a função do Lambda e a máquina de estado do Step Functions em sua conta da AWS, emita cdk deploy. Você será solicitado a aprovar as políticas do IAM que o AWS CDK gerou.
Etapa 3: Iniciar a execução de uma máquina de estado
Assim que você criar sua máquina de estado, poderá iniciar sua execução.
Para iniciar a execução da máquina de estado
-
Abra o console do Step Functions e escolha o nome da máquina de estado que você criou usando o AWS CDK.
-
Na página da máquina de estado, escolha Iniciar execução.
A caixa de diálogo Iniciar execução é exibida.
(Opcional) Insira um nome de execução personalizado para substituir o padrão gerado.
Nomes e registro em log não ASCII
O Step Functions aceita nomes de máquina de estado, execuções, atividades e rótulos que contenham caracteres não ASCII. Como esses caracteres não permitem que o Amazon CloudWatch registre dados em log, recomendamos usar somente caracteres ASCII para monitorar as métricas do Step Functions.
-
Escolha Start Execution.
A execução da máquina de estado começa e uma nova página mostrando a execução em andamento é exibida.
-
O console do Step Functions direciona você para uma página em que o título é o ID da execução. Essa página é conhecida como página de Detalhes da execução. Nesta página, você pode revisar os resultados da execução à medida que a execução avança ou após a conclusão.
Para revisar os resultados da execução, escolha estados individuais na Exibição em gráfico e, em seguida, escolha as guias individuais no painel Detalhes da etapa para visualizar os detalhes de cada estado, incluindo entrada, saída e definição, respectivamente. Para obter detalhes sobre as informações de execução que você pode visualizar na página Detalhes da execução, consulte Visão geral dos detalhes da execução.
Etapa 4: Limpeza
Depois de testar sua máquina de estado, recomendamos remover a máquina de estado e a função do Lambda relacionada para liberar recursos na sua Conta da AWS. Execute o comando cdk destroy no diretório principal da aplicação para remover sua máquina de estado.
Próximas etapas
Para saber mais a respeito do desenvolvimento da Infraestrutura da AWS usando o AWS CDK, consulte o Guia do desenvolvedor do AWS CDK.
Para obter informações sobre como criar aplicações do AWS CDK na sua linguagem preferencial, consulte:
- TypeScript
-
Trabalhar com o AWS CDK no TypeScript
- JavaScript
-
Trabalhar com o AWS CDK no JavaScript
- Python
-
Trabalhar com o AWS CDK no Python
- Java
-
Trabalhar com o AWS CDK no Java
- C#
-
Trabalhar com o AWS CDK no C#
Para obter mais informações sobre os módulos da AWS Construct Library usados neste tutorial, consulte as seguintes visões gerais da Referência da API do AWS CDK: