I'm setting up AWS X-Ray integration for my lambda service in Python, but I've encountered a strange issue.
I make an external HTTP call with the built in Python requests library, and my logs show that the status code is 404. Here's a snippet:
...
response = get_request(url, headers, params)
print(f"stat = {response.status_code}") # logs as 404
...
When I check AWS X-Ray, I can see the error rate is 100%:
But when I click on traces, the response code then becomes 200.
Why is there a discrepancy between the response codes?
From the documentation here, I should only need to add patch_all() method in order to trace my requests, which I've already done, so why is it I am still seeing 200 response.
Related
I have a non-simple cross-origin HTTP request to my POST method in API Gateway.
I have set up CORS support as per : https://docs.aws.amazon.com/apigateway/latest/developerguide/how-to-cors.html
The POST request succeeds from Postman/AWS console but fails from a local development server where the origin is of type localhost.
After browsing through many answers and trying to debug i have concluded that all the required headers are present on the integration response of both POST and OPTIONS. However when making a call to OPTIONS from postman i see that it returns 500 Internal server error. This looks like a configuration issue with OPTIONS. How do i fix it? I don't have a serverless yaml, the gateway has been configured manually. Any way of resolving this via the console ?
I am using X-Ray tracing in API Gateway and Lambda authorizer. Inside the authorizer, I am calling two HTTP URLs.
When I give invalid URL for one http call, I am throwing callback ("unauthorized") from lambda authorizer. Hence, the response status will be 401. When I look into the response headers, I couldn't find X-Amzn-Trace-Id.
When the URL is valid and status is 200, X-Amzn-Trace-Id is seen in response headers.
Is there anyway to retrieve X-Amzn-Trace-Id irrespective of the status (always)?
Apologies for delay in the response. We have raised this issue with API Gateway team and actively working with them to resolve this issue. I cannot provide any ETA at this point but please stay tuned. At the moment, there is no way to retrieve "X-Amzn-Trace-Id" irrespective of the status from the response. The "X-Amzn-Trace-Id" is populated by API Gateway segment and it seems missing for the above use case other than 200 status code.
Thanks for the patience.
I'll preface this by saying that in my case the answer appears to be no, however I might have misconfigured my setup and cannot find mention of this anywhere in the documentation, so I'd like to know how it is expected to work.
When defining a Custom Error Response, you choose the Error Code from the Origin, the response page to return, and the error code to replace the one at the Origin.
Normally this works as expected - say for example I set up CloudFront to return "error.html" with code 404 when the Origin provides a 403. When probing for a link I know should return a 403, I receive "error.html" with 404.
Unfortunately, it seems that when the Origin provides it's own body (I've seen this happen with a JSON as well as an HTML page), CloudFront only replaces the headers - the error code switches correctly from 403 to 404, but the body is the one sent by Origin - "error.html" is not provided.
Is this the expected behavior? Does the documentation mention this anywhere?
What you describe is not expected.
Configuring a custom error page and a custom response code should replace the entire response with the custom response -- headers and body -- along with the custom status code -- including none of the original response headers or body.
In the event of a second error occurring -- that is, an error encountered by CloudFront during the actual fetching the custom error document -- both the code and body will be whatever the origin provided during that second request.
https://docs.aws.amazon.com/AmazonCloudFront/latest/DeveloperGuide/custom-error-pages.html
You might check the response headers, particularly the Age header, to verify that you aren't getting a cached response much older than you expect. Changing the custom error page configuration doesn't invalidate any already-cached error responses.
Cross-check the CloudFront logs with the origin logs to verify that what you're seeing is indeed live.
Note also that none of the above is applicable to the error responses from the "hidden" CloudFront distribution associated with an edge-optimized API Gateway endpoint, nor with Lambda#Edge customization of error responses.
I want to set a 404 response code in API Gateway based on error message from Lambda function, here's integration response mapping:
And here's testing output:
The issue is that when making request in browser, I still don't get 404 status code, but rather the default one. What could the issue be here?
On your method execution configuration, you need to set 404 as a status both on your Method Response and both at your Integration response.
First you set it on your Method Response configuration and the you proceed in configuring the Integration response for 404.
When invoking the deployed API's URL from the browser, the behavior should be the same as invoking from API Gateway console (as shown in above screenshot). Please make sure you have deployed to the stage that you are invoking, after you made all the configuration changes to the API.
I wrote simple script to check url's affected by error 404.
When I run the script on url with 404 it indeed returns me correct response however sometimes it returns a different one(503) , I don't understand why this is happening ,I've tested that on many other URL's and the results are never consistent. Would someone be that kind and explain why my results keep changing even though the actual url status doesn't ??
Thanks in advance for assistance
I've tried to use the following modules:
urllib,urllib2, requets
All of them produced the same inconsistent results.
Here are the scripts:
I
import requests
for url in ['https://www.amazon.es/gp/product/B00QTVL0T4']:
response = requests.get(url)
response.status_code
print(response)
Response [404] and Response [503] (incorrect)
II
import urllib
result=''
#***** paste url into square bracket ****#
for url in ["https://www.amazon.es/gp/product/B003ODEJZ2",'https://www.amazon.fr/gp/product/B01H801C9C']:
a=urllib.urlopen(url)
e=a.getcode()
if e==404:
result+=(url+" Error_404 "+"\n")
else:
result+=(url+" Link_OK "+"\n")
print result
III
import urllib2
for url in ['https://www.amazon.es/gp/product/B003ODEJZ2','https://www.amazon.fr/gp/product/B01H801C9C','https://www.amazon.de/dp/B00B8PRE1Y']:
try:
connection = urllib2.urlopen(url)
except urllib2.HTTPError, e:
if e.getcode()==404:
print (url+" Error_404")
else:
print(url+" Link_Ok")
503's Reason is typically "Service Unavailable" which means that whatever is handling your request cannot find a backing service to supply a response. This may be returned by a physical or software-provided load balancer (F5s, HAProxy, etc.), CDN (Fastly, Cloudflare, etc.), or something like Apache or Nginx that are running but do not have an appropriate application to contact (for whatever reason).
Since the URLs in your example are Amazon URLs, it's likely that the CDN is returning the 503. CDNs (like Fastly) use Varnish and Varnish will return a 503 in the following cases:
The backend server returned a 503 so Varnish forwards it along
The backend server returned a response which was not parseable
Some other times a CDN might return a 503:
The CDN timed out reading from the origin
The CDN timed out connecting to the origin
The CDN cannot read/write to the origin
The origin server refused the connection from the CDN
The CDN cannot find a route to the origin
The origin has misconfigured TLS
(And so so so many other problems)
So really, it's not quite possible for us to tell you why you're getting a 503. You need to introspect the response a bit more and look up documentation surrounding that.