Extract variables policy is not working as expected.

Tried to search and extract few elements from JSON payload using Extract Variables policy. Responded no values with 200 response.

FYI: tried response.content value for the <Source> tag. @Anil Sagar @ Google @Dino-at-Google @Siddharth Barahalikar

<?xml version="1.0" encoding="UTF-8" standalone="yes"?>
<ExtractVariables async="false" continueOnError="false" enabled="true" name="EV-ExtractEmployeeInfo">
    <DisplayName>EV-ExtractEmployeeInfo</DisplayName>
    <Properties/>
    <IgnoreUnresolvedVariables>true</IgnoreUnresolvedVariables>
    <JSONPayload>
        <Variable name="name">
            <JSONPath>$.[?(@.id=='66712')].employee_name</JSONPath>
            <!-- Returns specific value as array ["pod1"] -->
        </Variable>
        <Variable name="salary">
            <JSONPath>$.[?(@.id=='66712')].employee_salary</JSONPath>
            <!-- Returns specific value as string pod1 -->
        </Variable>
    </JSONPayload>
    <Source clearPayload="false">response</Source>
</ExtractVariables>
<?xml version="1.0" encoding="UTF-8" standalone="yes"?>
<AssignMessage async="false" continueOnError="false" enabled="true" name="AM-SetEmployeeInfo">
    <DisplayName>AM-SetEmployeeInfo</DisplayName>
    <AssignTo createNew="false" type="response"/>
    <IgnoreUnresolvedVariables>true</IgnoreUnresolvedVariables>
    <Set>
        <Payload contentType="application/json" variablePrefix="@" variableSuffix="#">
        {"name":"@name#", "salary":"@salary#"}
    </Payload>
    </Set>
</AssignMessage>

Expected response

{
 "name": "["Rahul3210"]",
 "salary": "["30000"]"
}

Actual Response

{
 "name": " ",
 "salary": ""
}

PFA the image which shows the response payload where we extract the elements.original-response-payload.png

1 16 601
16 REPLIES 16

Could you please share the trace logs? with the above code snippet its difficult to assume what is the execution flow and what data you were getting where.

plz find the image attached

9057-trace-flow.png

There is an option to download the trace. that would be more helpful. send that in txt format.

Hi @Arun Prasath Sivanesan, I have created a demo proxy for you where I have implemented your use cases with some mock response (hardcoded in assign message). which returns the correct result.

9059-screen-shot-2019-08-23-at-110737-pm.png

I am also attaching the proxy code. ev-demo-rev1-2019-08-23.zip

You just need to import. deploy and see the result then check the proxies. so overall your extract variable policy seems fine but placement or response from target server might differ in terms of type casting. please validate those as well In the trace, please check if "id" is string or integer based on that decide single quote or double quote.

If that still doesn't work, please check if you can share the proxy bundle.

Thanks @Ravindra Singh for taking effort. I tried with different types as well but no luck. plz find attached the zip.fei-employee-info-rev7-2019-08-23.zip.

sample proxy call: http://arunprasath25-eval-test.apigee.net/v1/emp/66712

sidd-harth
Participant V

Why are you using prefixes?

Are you getting the response from backend?

Since you have multiple extract variable policy, i suggest you to use variable prefix tag in extract variable policy & then use that to get the values in assign message policy.

<Set>
        <Payload contentType="application/json">
        {"name":"{prefix.name}", "salary":"{prefixsalary}"}
    </Payload>
    </Set>


You can also look at message templates. With this we can use a single assign message policy to extract and set a new payload.

Thanks for responding @Siddharth Barahalikar. I do get the response from the backend. and I tried using the variable prefix tag but no luck.

The following article talks about the same problem

https://community.apigee.com/questions/164/extractvariables-not-shown-in-trace.html

I just looked at your proxy.

The response from your target server is coming back with this response header:

Content-Type text/html; charset=UTF-8

That says the content is HTML.

It may be frustrating, but the ExtractVariables / JSONPayload will work only with a message that has Content-type = "application/json" or similar.

This is ONE reason your ExtractVariables is not working.

To solve this problem:

  • have your backend set the appropriate content-type in the response
  • OR, use AssignMessage in the response flow to force the content-type header to be application/json, before the ExtractVariables policy

Separately, I encourage you to accept Siddharth's advice on using the curly braces.

  <Set>
      <Payload contentType="application/json">
        {"name":"{name}", "salary":"{salary}" }
      </Payload>
  </Set>

Using that fragment, at runtime the {name} will be replaced with the value of the variable "name".

Also, it might be a good idea to use a prefix in the ExtractVariables policy.

<ExtractVariables name="EV-ExtractEmployeeInfo">
    <IgnoreUnresolvedVariables>true</IgnoreUnresolvedVariables>
    <VariablePrefix>myprefix</VariablePrefix>
    <JSONPayload>
        <Variable name="name">
            <JSONPath>$.[?(@.id=='66712')].employee_name</JSONPath>
            <!-- Returns specific value as array ["pod1"] -->
        </Variable>
        <Variable name="salary">
            <JSONPath>$.[?(@.id=='66712')].employee_salary</JSONPath>
            <!-- Returns specific value as string pod1 -->
        </Variable>
    </JSONPayload>
    <Source clearPayload="false">response</Source>
</ExtractVariables>

In which case you need:

<AssignMessage name="AM-SetEmployeeInfo">
    <AssignTo>response</AssignTo>
    <IgnoreUnresolvedVariables>true</IgnoreUnresolvedVariables>
    <Set>
        <Payload contentType="application/json">{
   "name":"{myprefix.name}", 
   "salary":"{myprefix.salary}"
}
</Payload>
    </Set>
</AssignMessage>

Yes, the main reason is that target server is returning text content type.

I understand that. But I tried with a different API. The problem remains the same. Tried everything you suggested. Also, the content type is application/json.fei-sample-rev5-2019-08-26.zip

Also, the content type is application/json

Not according to my direct observation. Check your assumption.

If you disagree, show a trace that proves this, please. (Not the proxy) Or even show a screenshot of the Trace UI showing the content-type header. Your previous screenshots did not show the header.

i meant that the new api returns json data

i agree the old data is text

yes, and I can see that the data is json. I said this in my answer above, and I will repeat it here: the content-type is not consistent with the payload, and the ExtractVariables / JSONPayload will not work if your content-type header is not application/json.

look here.

Re-read my answer above. I gave you two ways to solve the problem. If you didn't understand the answer, ask for clarification. My answer is still right. It will help you. Trust me on this.

9073-tracetool.png

9074-postman.pngplease refer the pics