启动 StepFunction 并退出不会触发执行
Starting a StepFunction and exiting doesn't trigger execution
我有 Lambda 函数 tranportKickoff
,它接收输入,然后 sends/proxies 将输入转发到 Step Function。下面的代码 执行 运行 并且我没有收到任何错误,但同时 step 函数没有执行。
对设计也很关键,我不希望 transportKickoff
函数等待 step 函数完成,因为它可能会很长 运行ning。然而,我期望 Step Function 的 calling 中的任何错误都会被同步报告回来。也许这个想法是错误的,我不知何故错过了某处抛出的错误。但是,如果是这样的话,我想找到一种方法来实现在 Step Function 开始执行后立即退出 kickoff lambda 函数的目标。
note: I can execute the step function independently and I know that it works correctly
const stepFn = new StepFunctions({ apiVersion: "2016-11-23" });
const stage = process.env.AWS_STAGE;
const name = `transport-steps ${message.command} for "${stage}" environment at ${Date.now()}`;
const params: StepFunctions.StartExecutionInput = {
stateMachineArn: `arn:aws:states:us-east-1:999999999:stateMachine:transportion-${stage}-steps`,
input: JSON.stringify(message),
name
};
const request = stepFn.startExecution(params);
request.send();
console.info(
`startExecution request for step function was sent, context sent was:\n`,
JSON.stringify(params, null, 2)
);
callback(null, {
statusCode: 200
});
我还从控制台检查了我认为我拥有开始执行步骤功能的正确权限:
我现在添加了更多权限(见下文)但仍然遇到同样的问题:
- 'states:ListStateMachines'
- 'states:CreateActivity'
- 'states:StartExecution'
- 'states:ListExecutions'
- 'states:DescribeExecution'
- 'states:DescribeStateMachineForExecution'
- 'states:GetExecutionHistory'
好的,我已经自己弄明白了,希望这个答案对其他人有帮助:
首先,send()
方法不是同步调用,但它也不是 return 承诺。相反,您必须在发送前在 Request
对象上设置侦听器,以便您可以适当地响应 success/failure 状态。
我使用以下代码完成了此操作:
const stepFn = new StepFunctions({ apiVersion: "2016-11-23" });
const stage = process.env.AWS_STAGE;
const name = `${message.command}-${message.upc}-${message.accountName}-${stage}-${Date.now()}`;
const params: StepFunctions.StartExecutionInput = {
stateMachineArn: `arn:aws:states:us-east-1:837955377040:stateMachine:transportation-${stage}-steps`,
input: JSON.stringify(message),
name
};
const request = stepFn.startExecution(params);
// listen for success
request.on("extractData", req => {
console.info(
`startExecution request for step function was sent and validated, context sent was:\n`,
JSON.stringify(params, null, 2)
);
callback(null, {
statusCode: 200
});
});
// listen for error
request.on("error", (err, response) => {
console.warn(
`There was an error -- ${err.message} [${err.code}, ${
err.statusCode
}] -- that blocked the kickoff of the ${message.command} ITMS command for ${
message.upc
} UPC, ${message.accountName} account.`
);
callback(err.statusCode, {
message: err.message,
errors: [err]
});
});
// send request
request.send();
现在请记住有一个 "success" 事件,但我使用 "extractData" 来捕获成功,因为我想尽快得到响应。成功也可能同样有效,但查看 Typescript 类型中的语言并不完全清楚,在我的测试中,我确定 "extractData" 方法确实按预期工作。
至于为什么我没有在我的步骤函数上执行任何操作......它必须按照我命名函数的方式......你仅限于名称中的字符子集而且我会跨过该限制,但直到我能够使用上面的代码捕获错误后才意识到。
对于从 Lambda 执行状态机时遇到问题的任何人,请确保将权限 'states:StartExecution' 添加到 Lambda 权限并且 区域 匹配。
基于 Promise 的版本:
import { StepFunctions } from 'aws-sdk';
const clients = {
stepFunctions: new StepFunctions();
}
const createExecutor = ({ clients }) => async (event) => {
console.log('Executing media pipeline job');
const params = {
stateMachineArn: '<state-machine-arn>',
input: JSON.stringify({}),
name: 'new-job',
};
const result = await stepFunctions.startExecution(params).promise();
// { executionArn: "string", startDate: number }
return result;
};
const startExecution = createExecutor({ clients });
// Pass in the event from the Lambda e.g S3 Put, SQS Message
await startExecution(event);
结果应包含执行 ARN 和开始日期 (read more)
我有 Lambda 函数 tranportKickoff
,它接收输入,然后 sends/proxies 将输入转发到 Step Function。下面的代码 执行 运行 并且我没有收到任何错误,但同时 step 函数没有执行。
对设计也很关键,我不希望 transportKickoff
函数等待 step 函数完成,因为它可能会很长 运行ning。然而,我期望 Step Function 的 calling 中的任何错误都会被同步报告回来。也许这个想法是错误的,我不知何故错过了某处抛出的错误。但是,如果是这样的话,我想找到一种方法来实现在 Step Function 开始执行后立即退出 kickoff lambda 函数的目标。
note: I can execute the step function independently and I know that it works correctly
const stepFn = new StepFunctions({ apiVersion: "2016-11-23" });
const stage = process.env.AWS_STAGE;
const name = `transport-steps ${message.command} for "${stage}" environment at ${Date.now()}`;
const params: StepFunctions.StartExecutionInput = {
stateMachineArn: `arn:aws:states:us-east-1:999999999:stateMachine:transportion-${stage}-steps`,
input: JSON.stringify(message),
name
};
const request = stepFn.startExecution(params);
request.send();
console.info(
`startExecution request for step function was sent, context sent was:\n`,
JSON.stringify(params, null, 2)
);
callback(null, {
statusCode: 200
});
我还从控制台检查了我认为我拥有开始执行步骤功能的正确权限:
我现在添加了更多权限(见下文)但仍然遇到同样的问题:
- 'states:ListStateMachines'
- 'states:CreateActivity'
- 'states:StartExecution'
- 'states:ListExecutions'
- 'states:DescribeExecution'
- 'states:DescribeStateMachineForExecution'
- 'states:GetExecutionHistory'
好的,我已经自己弄明白了,希望这个答案对其他人有帮助:
首先,send()
方法不是同步调用,但它也不是 return 承诺。相反,您必须在发送前在 Request
对象上设置侦听器,以便您可以适当地响应 success/failure 状态。
我使用以下代码完成了此操作:
const stepFn = new StepFunctions({ apiVersion: "2016-11-23" });
const stage = process.env.AWS_STAGE;
const name = `${message.command}-${message.upc}-${message.accountName}-${stage}-${Date.now()}`;
const params: StepFunctions.StartExecutionInput = {
stateMachineArn: `arn:aws:states:us-east-1:837955377040:stateMachine:transportation-${stage}-steps`,
input: JSON.stringify(message),
name
};
const request = stepFn.startExecution(params);
// listen for success
request.on("extractData", req => {
console.info(
`startExecution request for step function was sent and validated, context sent was:\n`,
JSON.stringify(params, null, 2)
);
callback(null, {
statusCode: 200
});
});
// listen for error
request.on("error", (err, response) => {
console.warn(
`There was an error -- ${err.message} [${err.code}, ${
err.statusCode
}] -- that blocked the kickoff of the ${message.command} ITMS command for ${
message.upc
} UPC, ${message.accountName} account.`
);
callback(err.statusCode, {
message: err.message,
errors: [err]
});
});
// send request
request.send();
现在请记住有一个 "success" 事件,但我使用 "extractData" 来捕获成功,因为我想尽快得到响应。成功也可能同样有效,但查看 Typescript 类型中的语言并不完全清楚,在我的测试中,我确定 "extractData" 方法确实按预期工作。
至于为什么我没有在我的步骤函数上执行任何操作......它必须按照我命名函数的方式......你仅限于名称中的字符子集而且我会跨过该限制,但直到我能够使用上面的代码捕获错误后才意识到。
对于从 Lambda 执行状态机时遇到问题的任何人,请确保将权限 'states:StartExecution' 添加到 Lambda 权限并且 区域 匹配。
基于 Promise 的版本:
import { StepFunctions } from 'aws-sdk';
const clients = {
stepFunctions: new StepFunctions();
}
const createExecutor = ({ clients }) => async (event) => {
console.log('Executing media pipeline job');
const params = {
stateMachineArn: '<state-machine-arn>',
input: JSON.stringify({}),
name: 'new-job',
};
const result = await stepFunctions.startExecution(params).promise();
// { executionArn: "string", startDate: number }
return result;
};
const startExecution = createExecutor({ clients });
// Pass in the event from the Lambda e.g S3 Put, SQS Message
await startExecution(event);
结果应包含执行 ARN 和开始日期 (read more)