34

I have AWS step machine and one of the step is used to notify failure using SNS service. I want to select some metadata from input json into outgoing message. So i am trying to concatenate constant string with jsonpath like below

"Notify Failure": {
      "Type": "Task",
      "Resource": "arn:aws:states:::sns:publish",
      "Parameters": {
        "Message.$": "A job submitted through Step Functions failed for document id $.document_id",
        "Subject":"Job failed",
        "TopicArn": "arn:aws:sns:us-west-2:xxxxxxx:xxxxxxxx"
      },
      "End": true
    }

where document_id is one of the property in input json

However when i try save state machine defination i get error

There is a problem with your ASL definition, please review it and try again The value for the field 'Message.$' must be a valid JSONPath

LP13
  • 30,567
  • 53
  • 217
  • 400

4 Answers4

57

I was able to solve a similar issue using:

"Message.$": "States.Format('A job submitted through Step Functions failed for document id {}', $.document_id)",

Described in a AWS News Blog post.

ib.
  • 27,830
  • 11
  • 80
  • 100
Alex
  • 671
  • 5
  • 2
  • Amazing, been looking for this for days, thank you! Docs here https://docs.aws.amazon.com/step-functions/latest/dg/amazon-states-language-intrinsic-functions.html – phedro Aug 24 '23 at 12:49
3

The JSONPath implementation referenced from the AWS Step Functions documentation supports String concatenation via $.concat($..prop) but sadly this does not work when deployed to AWS, suggesting that AWS uses a different implementation.

Therefore there is no way to do string concatenation with JSONPath in AWS.

timxyz
  • 399
  • 2
  • 15
3

I know that this thread is quite old, but I think it might be useful for some people.

It IS actually possible to concatenate strings or JSONPaths in AWS Step Functions thanks to the function States.Format.

The principle is the same as the string format method in Python.

Example with strings

"States.Format('{}<separator_1>{}<separator_2>{}', 'foo', 'bar', 'baz')"

will give you

'foo<separator_1>bar<separator_2>baz'

Example with JSONPaths

"States.Format('{}<separator>{}', $.param_1, $.param_2)"

will give you

'<value of param_1><separator><value of param_2>'

NB: You can also combine strings with JSONPaths.

Hope it helps!

2

As the message suggest you need to provide a valid JSONPath.

"Message.$": "$.document_id"

You cannot use any string interpolation as it invalidates the JSONPath format. You will need to construct the message in the preceding state.

A.Khan
  • 3,826
  • 21
  • 25
  • 3
    Even in the preceding state how would you do that if I cannot cancatinate. And creating lambda just for concatenation is too much – LP13 Jan 19 '19 at 01:40
  • the state that set $.document_id needs to set full string. – A.Khan Jan 19 '19 at 07:17
  • also when there is an exception in preceding state, it passes the error to `Notify Failure` state, The error would not have `$document_id` – LP13 Jan 25 '19 at 22:52
  • Perhaps do a try/catch in your preceding state and then construct some sort of json output like `{ "error_message": "Failed for document id {document_id}" }`. This becomes part of your `ResultPath` that you can pass through to the next state. – Mark D May 26 '20 at 04:54