How to tie custom HTTP response with the Python Handler in the last step of my flow?

Hi there,

Any guidance with how to resolve this would be much appreciated?

Workflow Overview

  1. I’ve created workflow which uses a webhook to listen for a new event coming from Intercom.
  2. Event is received a call on a 3rd party API that looks up job data for the most recent 7 days
  3. I receive the response from that 3rd party, parse through it and build a new response

It’s at this point I get stuck as the ;
Actual Result


When called upon via a custom action I get 400 Bad request , $.respond() not called for this invocation
However, I have set HTTP response in the first step of the workflow / trigger to be Return a customer response from your workflow
image

Below is the code from the last step in my workflow

def handler(pd: "pipedream"):
    # Reference data from previous steps
    print(pd.steps["trigger"]["context"]["id"])
    # Return data for use in future steps
    return pd.steps["python_Generate_Response_with_Payload"]["response"]

Here is a screenshot of the last step, including the successful results and a snippet of the json payload that should be sent back as the HTTP response

I feel like there’s something minor I’m missing so any advice or guidance is very much appreciated.

Thanks
H

Hi @han50l0,

I understand that you’re trying to return a custom HTTP response from your workflow. It looks like you’re using Python code, so you’ll need to use the $.respond() function to send the custom response. Here’s an example of how to use $.respond() in a Python code step:

def handler(pd: "pipedream"):
    # Reference data from previous steps
    print(pd.steps["trigger"]["context"]["id"])
    # Get the response data
    response_data = pd.steps["python_Generate_Response_with_Payload"]["response"]

    # Send the custom HTTP response
    pd.$respond({
        "status": 200,
        "headers": {
            "Content-Type": "application/json"
        },
        "body": response_data
    })

This code will send the custom HTTP response with a 200 status code and the response data you’ve generated in the previous step. Make sure to replace the step names with the appropriate names from your workflow.
I’m a bot powered by Pipedream and GPT-4. I’m still learning, so please double check my answers and code! Learn how to build your own.

Thanks pi bot, that worked ! only thing is to remove the leading $ within the pd.$respond as that threw an error

from flask import Flask, jsonify, request
import requests
import json

app = Flask(name)

@app.route(‘/getrates’ , methods=[“POST”])
def get_rates():
data12 = json.loads(request.data)
print("Data12 $$$$$$$$$4 : ",data12)
headers = {
‘Content-Type’: ‘application/json’,
‘API-Key’: ‘’
}

payload = {
    "rate_options": {
        "carrier_ids": data12['rate_options']['carrier_ids'],
        "service_codes": data12['rate_options']['service_codes']
    },
    "shipment": {
        "ship_from": {
            "name": "Customer Service",
            "company_name": " Warehouse",
            "address_line1": " Wolf Rd",
            "city_locality": "Lat",
            "state_province": "NY",
            "postal_code": "12110",
            "country_code": "US",
            "phone": "212-400-7488"
        },
        "ship_to": {
            "name": data12['shipment']['ship_to']['name'],

            "address_line1": data12['shipment']['ship_to']['address_line1'],

            "city_locality": data12['shipment']['ship_to']['city_locality'],

            "state_province": data12['shipment']['ship_to']['state_province'],

            "postal_code": data12['shipment']['ship_to']['postal_code'],

            "country_code": data12['shipment']['ship_to']['country_code'],
            "address_residential_indicator": data12['shipment']['ship_to']['address_residential_indicator'],
        },
        "packages": [
            {
                "weight": {
                    "value": data12['shipment']['packages'][0]['weight']['value'],
                    "unit": "pound"
                },
                "dimensions": {
                    "length": data12['shipment']['packages'][0]['dimensions']['length'],
                    "width": data12['shipment']['packages'][0]['dimensions']['width'],
                    "height": data12['shipment']['packages'][0]['dimensions']['height'],
                    "unit": "inch"
                }
            }
        ]
    }
}

endpoint_url = "https://api.shipengine.com/v1/rates"

# custom functions to get employee info
def get_name(data):
    return data.get('total_amount')

response = requests.post(endpoint_url, headers=headers, json=payload)
print("Response : ", response)


# Check if the request was successful (status code 200)
# global l_rate_id,l_carrier_id,l_total_amount
service_code = []
if response.status_code == 200:
    # Parse the JSON response
    data = response.json()
    print("Data@@@@@@@@@@@@ : ", data)
    print(len(data))
# return "True"



    for doc in data['rate_response']['rates']:
        if doc['service_code'] == "usps_priority_mail":
            if doc["package_type"] == "package":
                rate_id = doc['rate_id']
                carrier_id = doc['carrier_id']
                service_type = doc['service_type']
                carrier_nickname = doc['carrier_nickname']
                service = doc['service_code']
                total_amount = doc['shipping_amount']['amount'] + doc['insurance_amount']['amount'] + doc['confirmation_amount']['amount'] + doc['other_amount']['amount']
                doc['total_amount'] = total_amount
                service_code.append(doc)
        else:
            rate_id = doc['rate_id']
            carrier_id = doc['carrier_id']
            service_type = doc['service_type']
            carrier_nickname = doc['carrier_nickname']
            service = doc['service_code']
            total_amount = doc['shipping_amount']['amount'] + doc['insurance_amount']['amount'] + doc['confirmation_amount']['amount'] + doc['other_amount']['amount']
            doc['total_amount'] = total_amount
            service_code.append(doc)
    print("Service_code : ", service_code)
    print(len(service_code))
    service_code.sort(key=get_name)
    print("Service_code : ", service_code[0])



else:
    pass

# Create a JSON response with the desired variables


return jsonify(service_code)

this is flask code and i want to sent the custom response, I am getting this error in postman ($.respond() not called for this invocation) . Please help me to resolve this error.

Hey @vijay.sharma,

I haven’t much experience executing flash python code in steps but perhaps try the following;

  1. Keep the code you have in your trigger where you initiate the flask app
  2. Populate your responses in that code and then reference that variable in another new step in the workflow
  3. To do so include from pipedream.script_helpers import (steps, export) as an additional line when you import your flask modules
  4. Then after your have populated your var ‘service_code’ use the export pipedream function
  5. export("response_data", jsonify(service_code)
  6. then in the brand new step simply have only the following code below;
def handler(pd: "pipedream"):
    # Reference data from previous steps
    print(pd.steps["trigger"]["context"]["id"])
    # Get the response data
    response_data = pd.steps["*python_what_ever_previous_step_is_called*"]["response_data"]

    # Send the custom HTTP response
    pd.$respond({
        "status": 200,
        "headers": {
            "Content-Type": "application/json"
        },
        "body": response_data
    })
  1. then be sure to configure the HTTP_Response in your first step / trigger / webhook listener to ‘Return a custom response from your workflow’

That should hopefully work for you