[英]How to share data in `AWS Step Functions` without passing it between the steps
我使用AWS Step Functions
並具有以下工作流程
initStep - 這是一個 lambda 函數處理程序,它獲取一些數據並將其發送到SQS
以供外部服務。
activity = os.getenv('ACTIVITY')
queue_name = os.getenv('QUEUE_NAME')
def lambda_handler(event, context):
event['my_activity'] = activity
data = json.dumps(event)
# Retrieving a queue by its name
sqs = boto3.resource('sqs')
queue = sqs.get_queue_by_name(QueueName=queue_name)
queue.send_message(MessageBody=data, MessageGroupId='messageGroup1' + str(datetime.time(datetime.now())))
return event
validationWaiting - 這是一個等待來自包含數據的外部服務的答案的activity
。
complete - 它是一個 lambda 函數處理程序,它使用來自initStep
的數據。
def lambda_handler(event, context):
email = event['email'] if 'email' in event else None
data = event['data'] if 'data' in event else None
client = boto3.client(service_name='ses')
to = email.split(', ')
message_conrainer = {'Subject': {'Data': 'Email from step functions'},
'Body': {'Html': {
'Charset': "UTF-8",
'Data': """<html><body>
<p>""" + data """</p>
</body> </html> """
}}}
destination = {'ToAddresses': to,
'CcAddresses': [],
'BccAddresses': []}
return client.send_email(Source=from_addresses,
Destination=destination,
Message=message_container)
它確實有效,但問題是我將完整數據從initStep
發送到外部服務,只是為了稍后將其傳遞給complete
。 可能會添加更多步驟。
我相信最好將其作為某種全局數據(當前步驟函數的)共享,這樣我就可以添加或刪除步驟,並且數據仍然可供所有人使用。
您可以使用InputPath
和ResultPath
。 在initStep
您只會將必要的數據發送到外部服務(可能還有一些唯一的執行標識符)。 在ValidaitonWaiting
步驟中,您可以設置以下屬性(在狀態機定義中):
InputPath
:將提供給GetActivityTask
數據。 可能您想將其設置為$.execution_unique_id
,其中execution_unique_id
是外部服務用於識別執行的數據中的字段(以在initStep
期間將其與特定請求initStep
)。ResultPath
: ValidationWaiting Activity 的輸出將保存在數據中的位置。 您可以將其設置為$.validation_output
並且來自外部服務的 json 結果將出現在那里。 通過這種方式,您可以僅將外部服務實際需要的數據發送到外部服務,並且您不會失去對之前(在ValidationWaiting
步驟之前)輸入中的任何數據的訪問權限。
例如,您可以對狀態機進行以下定義:
{
"StartAt": "initStep",
"States": {
"initStep": {
"Type": "Pass",
"Result": {
"executionId": "some:special:id",
"data": {},
"someOtherData": {"value": "key"}
},
"Next": "ValidationWaiting"
},
"ValidationWaiting": {
"Type": "Pass",
"InputPath": "$.executionId",
"ResultPath": "$.validationOutput",
"Result": {
"validationMessages": ["a", "b"]
},
"Next": "Complete"
},
"Complete": {
"Type": "Pass",
"End": true
}
}
}
我已經使用initStep
和ValidationWaiting
Pass
狀態來簡化示例(我沒有運行它,但它應該可以工作)。 Result
字段特定於Pass
任務,它相當於您的 Lambda 函數或活動的結果。
在這種情況下, Complete
步驟將獲得以下輸入:
{
"executionId": "some:special:id",
"data": {},
"someOtherData": {"value": key"},
"validationOutput": {
"validationMessages": ["a", "b"]
}
}
因此ValidationWaiting
步驟的結果已保存到validationOutput
字段中。
根據Marcin Sucharski的回答,我提出了自己的解決方案。
我需要使用Type: Task
因為initStep
是一個 lambda,它發送 SQS。
我不需要ValidationWaiting
InputPath
,而只需要ResultPath
,它存儲活動中收到的數據。
我使用無服務器框架,這是我的最終解決方案:
StartAt: initStep
States:
initStep:
Type: Task
Resource: arn:aws:lambda:#{AWS::Region}:#{AWS::AccountId}:function:init-step
Next: ValidationWaiting
ValidationWaiting:
Type: Task
ResultPath: $.validationOutput
Resource: arn:aws:states:#{AWS::Region}:#{AWS::AccountId}:activity:validationActivity
Next: Complete
Catch:
- ErrorEquals:
- States.ALL
ResultPath: $.validationOutput
Next: Complete
Complete:
Type: Task
Resource: arn:aws:lambda:#{AWS::Region}:#{AWS::AccountId}:function:complete-step
End: true
這是一個簡短而簡單的 InputPath 和 ResultPath 解決方案。 我的 Lambda Check_Ubuntu_Updates 返回准備更新的實例列表。 此實例列表由步驟 Notify_Results 接收,然后使用此數據。 請記住,如果您的 Step Function 中有多個 ResultPath 並且您在一個步驟中需要超過 1 個輸入,則您只能將 InputPath 與 $ 一起使用。
{
"Comment": "A state machine that check some updates systems available.",
"StartAt": "Check_Ubuntu_Updates",
"States": {
"Check_Ubuntu_Updates": {
"Type": "Task",
"Resource": "arn:aws:lambda:us-east-1:#############:function:Check_Ubuntu_Updates",
"ResultPath": "$.instances",
"Next": "Notify_Results"
},
"Notify_Results": {
"Type": "Task",
"InputPath": "$.instances",
"Resource": "arn:aws:lambda:us-east-1:#############:function:Notify_Results",
"End": true
}
}
}
聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.