Apigee blocking request header

Hi!

I am using AppDynamics APM to instrument my Java based applications behind Apigee and in my front end website I am using the AppDynamics JavaScript agent. I am NOT instrumenting the Apigee software itself as advised. I believe that Apigee is somehow blocking or preventing my request and response that AppDynamics is attempting to add to my AJAX calls which inhibits specific functionality.

On the left you'll see my AJAX request going through my environment using Apigee and on the right you'll see a "good" request that has the correct headers which are circled that does NOT use Apigee.

Request Headers:

9480-test.png

Response Headers:

9481-testing.png

Do I need to set a rule to "allow" the "isAdrum:true" header? I've already set to allow the appd cookies per the AppD instructions in my AssignMessage rules..

<Headers>
<Header name="Access-Control-Allow-Origin">{request.header.origin}</Header>
<Header name="Access-Control-Allow-Headers">origin, x-requested-with, accept, content-type,domain,authorization,Project-Name</Header>
<Header name="Access-Control-Max-Age">3628800</Header>
<Header name="Access-Control-Expose-Headers">ADRUM_0,ADRUM_1,ADRUM_2,ADRUM_3,ADRUM_4,ADRUM_5,ADRUM_6,ADRUM_7,ADRUM_8,ADRUM_9,ADRUM_10,ADRUM_11,ADRUM_12,ADRUM_13,ADRUM_14,ADRUM_15,ADRUM_16,ADRUM_17,ADRUM_18</Header>
<Header name="Access-Control-Allow-Methods">GET, PUT, POST</Header>
</Headers>

Any help would be greatly appreciated!

0 4 928
4 REPLIES 4

First, a disclaimer: I'm not clear on the difference between what you're expecting to see, and what you are actually seeing. Is a header being blocked? Is the entire request being blocked? Does Apigee even see the request? (can you view it in the Trace UI?) I'm not clear whether the difference in what you expect and what you observe is in the request, or the response, or both. I'm not clear on what the "success case" corresponds to. Is there any Apigee involved in that transaction?

Now, some details:

Apigee doesn't strip out any particular headers, whether ADRUM or something else. Apigee doesn't "block" requests that contain any particular header.

> I believe that Apigee is somehow blocking or preventing my request

OK, so your observation is that from a web app, the request into Apigee is not successful, is that right? It's "blocked". The next obvious question is, at what point is this request "blocked"? Which system is blocking it? One way to narrow that down is to examine the browser devtools. If Chrome or Safari or whatever you use is blocking the outbound request, you should see that clearly in the network activity tab. IF the browser is not blocking the request, you should see that it gets successfully sent out (though the response may not be what you expect or desire).

I see that you have CORS headers in your ... ?? I don't know what that is, maybe it's a fragment of an AssignMessage policy. It looks like you're using CORS.

CORS is enforced by the user agent, the browser. Generally the way it works is :

  • the browser runtime checks the "intended" outbound request, including the intended hostname (domain), headers, and etc. It then checks its cache to see whether that combination of things is legal to send to the intended domain.
  • If the browser doesn't have information as to what the intended domain wishes to allow, the browser will send a CORS "preflight" request to that domain. This is an OPTIONS request to ask the endpoint "when a browser sends requests, what restrictions apply?" The response to that preflight includes headers like Access-Control-Allow-XXX where XXX is { Origin, Headers }. The Origin header in the response says "allow AJAX calls from Javascript that was originally served from _this_ origin. and no other." That means, if the AJAX request is intended for example.com, and the preflight response from example.com says "Access-Control-Allow-Origin: example.com" then... only Javascript originally served from a webpage at example.com should be allowed to call the server endpoint. The browser itself enforces this. And, the Headers response is similar. The Access-Control-Allow-Headers header stipulates the set of headers that can legally be included in a request to the intended domain. And again, the browser enforces this.
  • ok now the browser has information about what the intended domain wants to allow. It then compares that information to the pending outbound request. If the pending request includes a header not on the allowed list, or if the JS that is the source of the request was not downloaded from the allowed origin, then the browser blocks the request. The endpoint never sees the request.

It looks to me that your AssignMessage that is intended to enable CORS does not include "Adrum" as an allowed header. It includes: origin, x-requested-with, accept, content-type, domain, authorization, Project-Name , but not adrum.

The effect of this, I would expect, would be that the browser would block any request that includes a header named "adrum". The browser doesn't "strip" the header and send the modified request. The browser will block the request entirely. If you remove that header from the outbound request, the browser will allow the request (* assuming that the remaining headers are all on the allowed list).

The difference between the successful case you have observed and the unsuccessful one, is probably that in the former case, the CORS preflight response includes adrum in the list of allowed headers, while in the latter case, the adrum header is not in the list.

Which system is sending the CORS preflight response in the former case? I don't know. I'm not clear on what you did to get the success case. I'm not sure which systems are interacting.

But you should be able to check it yourself.

Did this help?

Tried adding an adrum header with the value but it only added it to the response header and not the request. Do I need to create a separate policy to add this to the request headers?

<?xml version="1.0" encoding="UTF-8" standalone="yes"?>
<AssignMessage async="false" continueOnError="false" enabled="true" name="add-cors">
    <DisplayName>Add CORS</DisplayName>
    <FaultRules/>
    <Properties/>
     
    <Set>
        <Headers>
            <Header name="adrum">isAjax:true</Header>
            <Header name="Access-Control-Allow-Origin">{request.header.origin}</Header>
            <Header name="Access-Control-Allow-Headers">origin, x-requested-with, accept, content-type,domain,authorization,Project-Name</Header>
            <Header name="Access-Control-Max-Age">3628800</Header>
            <Header name="Access-Control-Expose-Headers">ADRUM_0,ADRUM_1,ADRUM_2,ADRUM_3,ADRUM_4,ADRUM_5,ADRUM_6,ADRUM_7,ADRUM_8,ADRUM_9,ADRUM_10,ADRUM_11,ADRUM_12,ADRUM_13,ADRUM_14,ADRUM_15,ADRUM_16,ADRUM_17,ADRUM_18</Header>
            <Header name="Access-Control-Allow-Methods">GET, PUT, POST</Header>
        </Headers>


<br>

it only added it to the response header and not the request.

That means either

  • You did not provide an AssignTo element in the AssignMessage policy, and you attached the AssignMessage policy in the response flow, OR
  • you DID provide an AssignTo element and you explicitly assigned to the response message.

Check your configuration and where you attached the policy.

Policy attachment can be confusing, so maybe you want to review the documentation on the topic.

https://docs.apigee.com/api-platform/develop/attaching-policy-proxyendpoint-or-targetendpoint-flow