intercept response header with jquery ajax request - javascript

Exactly what the title suggests:
I perform an ajax request to my server, it responds with a 403 but there are headers I want to retrieve and save on localStorage. This is for a phonegap app (Android and iOS), so the initiating domain isLocal (file://). When performing the call, I use the following code to try to intercept the response, but it returns undefined or an empty string.
Ajax:
$.ajax({
url: serverLink+action,
type: "POST",
data: "access_token="+accessToken+"&uid="+uid,
crossDomain: true,
complete: function(resp){
var header = resp.getAllResponseHeaders();
var match = header.match(/(Set-Cookie|set-cookie): (.+?);/);
if (match) session = match[2];
console.log(header, session)
}
})
Response Headers
Connection Keep-Alive
Content-Encoding gzip
Content-Length 1198
Content-Type text/html
Date Fri, 13 Apr 2012 22:51:02 GMT
Keep-Alive timeout=15, max=100
Server Apache/2.2.14 (Ubuntu)
Set-Cookie sessionid=ebd26167e32bada2d2ed0bd3cc16d8a2; expires=Fri, 27-Apr-2012 22:51:02 GMT; Max-Age=1209600; Path=/
Vary Cookie,Accept-Encoding
Further reading led me to here, which speaks of the CSRF on a django server. We are using a django server and either this or the 403 is the problem I suspect. There doesn't seem to be a way (from the example answer there) to collect the cookie from webview and send it back to the server on subsequent requests.

use the jquery XHR object which as a method getAllResponseHeaders() which should provide what you are after.
http://api.jquery.com/jQuery.ajax/

This problem was most definitely caused by CSRF protection on the django server. Disabling or implementing workarounds as per django is the only way around this.
Actually this post helped tremendously: Django CSRF check failing with an Ajax POST request

Related

Set-Cookie in response header is not saved into browser cookie storage

the response header is
Access-Control-Allow-Credentials:true
Access-Control-Allow-Headers:Origin, X-Requested-With, x-request, Content-Type, Accept
Access-Control-Allow-Origin:*
Cache-Control:private
Connection:close
Content-Length:100
Content-Type:application/json; charset=utf-8
Date:Tue, 14 Feb 2017 02:45:56 GMT
Server:nginx/1.2.8
Set-Cookie:USER=6ae633831f39447688892e6b2b156cec; Max-Age=604800; Path=/
Set-Cookie:USERINFO=298967; Max-Age=604800; Path=/
X-Powered-By:node.js
X-Ua-Compatible:chrome=1
the cookie format's right (used cookie package to serialize ). the server is developed by node.js.
not only chrome, Firefox doesn't work too. the document.cookie is empty and also i can't see cookie in application section of chrome developer tool.
Any wrong in response header ?? Please help .
This problem occur due to multiple responses from server to client.
For example if you are sending a response to the server using response.send() and same time using
you are using response.setHeader()
This problem can be solve by creating cookie in client side using javascript.
And reading its value from node.js
The answer is because i used fetch() API that have to pass {credentials => 'same-origin'} option.

Using Parse Client Key in Angular gives CORS error

I am attempting to retrieve a class (with GET) from Parse using a client key. I was able to send a successful request using Advanced Rest Client for Google Chrome; I used X-Parse-Application-Id and X-Parse-Client-Key headers.
[edit] [edit2]
Response headers (obtained from Chrome Developer Tools OPTIONS):
HTTP/1.1 200 OK
Access-Control-Allow-Headers: X-Parse-REST-API-Key, X-Parse-Javascript-Key, X-Parse-Application-Id, X-Parse-Client-Version, X-Parse-Session-Token, X-Requested-With, X-Parse-Revocable-Session, Content-Type
Access-Control-Allow-Methods: OPTIONS, POST, GET, PUT, DELETE
Access-Control-Allow-Origin: *
Access-Control-Max-Age: 86400
Content-Type: application/json; charset=utf-8
Date: Sun, 29 Nov 2015 04:23:08 GMT
Server: nginx/1.6.0
X-Parse-Platform: G1
X-Runtime: 0.000118
Content-Length: 0
Connection: keep-alive
However, attempting to do the same in an Angular app gives me the following error:
XMLHttpRequest cannot load https://api.parse.com/1/classes/GenResources. Request header field X-Parse-Client-Key is not allowed by Access-Control-Allow-Headers in preflight response.
Parse says it supports using cross-origin resource sharing, and I was able to make the request earlier using a different client so I'm pretty sure the server isn't the issue. I wouldn't be able to modify what the response header is anyways.
Here's the code I used to form the GET request.
var ng_portal = angular.module("ngPortal", []);
ng_portal.controller("GenResourcesCtrl", ["$http", function($http) {
$http({
method: "GET",
url: PARSE_URL + "/1/classes/GenResources",
headers: {
"Content-Type": "application/json",
"X-Parse-Application-Id": PARSE_APP_ID,
"X-Parse-Client-Key": PARSE_CLIENT_KEY
}
}).then(
function success(res) {
console.log(res);
},
function error(res) {
console.log(res);
}
);
}]);
You are setting custom headers in the request, which will trigger a pre-flight (OPTIONS) request. The response from that request must include a header called "access-control-allow-headers" with the value being a list of the headers you are trying to set.
See https://developer.mozilla.org/en-US/docs/Web/HTTP/Access_control_CORS
specifically the section on pre-flight requests.
I suggest using the browser developer tools to look at the headers of the requests and responses to see if they conform to the CORS spec. From the error message you provided, it looks like the server hosting the cross domain call you are making, does not support custom headers. If you see otherwise, please update your question with the headers and I can provide more help.
This seems to be an issue with Parse.com actually. After exactly one frustrated hour, I came across this Google Groups post
Relevant quote
From my testing, this never ( client or javascript key) worked via javascript rest interactions through the browser.
I actually created a Parse Bug on this:
https://developers.facebook.com/bugs/488204124680438
Because I thought both of those keys should work through the browser ( WITHOUT NEEDING TO USE A SDK ).
I’d suggest reading reading my bug. I still think the the correct implementation is to enable these keys to work properly with browser requests because it works if you do it outside the browser.
But alas, they don’t seem to get the issue, or don’t understand why disabling it only in the browser doesn’t make sense since you can use it on any other platform without issues. Just… Doesn’t… Make… Sense.
I instead used my JavaScript Key X-Parse-Javascript-Key (which, according to the docs as of today, only works with their JavaScript SDK) and it works fine as a drop-in replacement for X-Parse-Client-Key

Web Browser Does Not Set cookie on an Ajax Call

I'm very confused. I've got an AJAX call which causes a login form to be processed, and creates a cookie on a successful login. The web browser is not registering the cookie.
In troubleshooting, I isolated it down to something to do with the AJAX calling the site, rather than navigating directly.
e.g. I created a simple page "test" which returns the following output:
HTTP/1.1 200 OK
X-Powered-By: Express
Set-Cookie: token=ABCDEFG; Domain=localhost; Path=/
Content-Type: application/json; charset=utf-8
Content-Length: 19
ETag: W/"13-S4werj8PuppRlonJZs+jKA"
Date: Wed, 23 Sep 2015 22:09:03 GMT
Connection: keep-alive
{"message":"value"}
If I navigate directly to the page, the cookie is created in the browser.
If I make an AJAX call to the page, the cookie is not created in the browser.
e.g:
$.get('http://localhost:8081/test');
I've found similar posts which state that this happens with AJAX if the domain or the path are not defined, but as you can see, I defined these and still no dice.
If it matters, the majority of my testing has been on Firefox, but I did do at least a couple of tests on Chrome.
Any help you have would greatly be appreciated. I'm confused by this, as everything I read suggests this should be possible.
To clarify further:
1) I'm not seeing the cookie created when reviewing CookieManager+ addon for Firefox.
2) I'm also not seeing the cookie added to subsequent requests to the same host (even the same port).
3) What I read seems to suggest that cookies are tied to a host, not a port (But that doesn't seem to be the issue based on #1 and #2):
Are HTTP cookies port specific?
Try setting withCredentials in your request:
$.get('http://localhost:8081/test', {xhrFields: {withCredentials: true}});
Alternatively try setting the crossDomain value:
$.ajax({type:"GET", url:"localhost:8081/test", crossDomain:true});
If you're trying to do this in Angular, as I was, this is how you do it there:
$http doesn't send cookie in Requests
config(function ($httpProvider) {
$httpProvider.defaults.withCredentials = true;

Digest access authentication with javascript

I'm trying to use the cloudapp api with javascript, the problem is that the api is using Digest access authentication for authentication.
I visited the app documentation but there is no examples or wrappers for javascript.
I tried many things but here is my latest code:
$.ajax({
headers: { "Accept": "application/json"},
type: "GET",
url: "http://my.cl.ly/account",
crossDomain: true,
success:function(data, textStatus, request){
console.log(data);
}
});
All I'm getting with this code is Cross-origin resource sharing (CORS) problems and a 401 Unauthorized error.
here is the response headers:
Cache-Control no-cache
Connection keep-alive
Content-Type text/plain; charset=utf-8
Date Wed, 17 Sep 2014 20:15:26 GMT
Transfer-Encoding chunked
WWW-Authenticate Digest realm="Application", qop="auth", algorithm=MD5, nonce="MTQxMDk4NDkyNjo4MmE4ZWU0ZDY4YWUwYTAyMjRjNzIzYWU2NzE5YTQyMQ==", opaque="9eb56ccb2e8b017ae42bdb4739690863"
X-Request-Id b6bdbf12-f1d9-4769-a06d-216d5d7ae669
X-Runtime 0.008105
status 401 Unauthorized
x-ua-compatible IE=Edge,chrome=1
So how can I use the WWW-Authenticate to authenticate and retrieve data?
Also I tried adding
xhrFields: {
withCredentials: true
}
I got a promt, I filled it and now I'm getting 200 OK status but no response.
All I need is to get this working and getting a return.
Thanks.
It looks like you're using Digest Access Authentication algorithm. Getting 401 on your first request is a part of algorithm, you have to implement it completely. In WWW-Authenticate header you've got all required fields. I hope this will help you:
http://en.wikipedia.org/wiki/Digest_access_authentication
What is digest authentication?

Firefox 3 not using cache when ajax call made during page load

I get some json data with ajax when the page DOM is loaded using jQuery like this:
$(document).ready(function(){
getData();
});
...where getData() is a simple jQuery ajax call, something like this:
function getData(){
$.ajax({cache: true, dataType: 'json', url: '/foo/bar'});
}
The Expires header for this request is set to some time in the future, so the next time I load the page, the ajax call should use the cached data. Firefox 3 does not.
But, if I instead ask for the data like this:
$(document).ready(function(){
setTimeout("getData()", 1);
});
Firefox does respect the Expires header, and uses the cache. Any ideas why this would be?
This page mentions that browsers may treat ajax calls that occur when a page loads differently from ajax calls that occur in response to a user UI event.
Edit: I forgot to include the http headers in my original post. I think the headers are fine, because the caching works as long as the request isn't made in an ajax call when the page loads. If I visit the url that the ajax call uses in my browser URL bar, caching works, and as I explain above, caching works if I add a little delay to the ajax call.
Request headers
Host 10.0.45.64:5004
User-Agent Mozilla/5.0 (Windows; U; Windows NT 5.1; en-US; rv:1.9.2.9) Gecko/20100824 Firefox/3.6.9
Accept application/json, text/javascript, /
Accept-Language en-us,en;q=0.5
Accept-Encoding gzip,deflate
Accept-Charset ISO-8859-1,utf-8;q=0.7,*;q=0.7
Keep-Alive 115
Connection keep-alive
X-Requested-With XMLHttpRequest
Cookie
Response headers
I set the Expires header to 1 week in the future so that users only need to refresh once a week.
Date Wed, 04 May 2011 15:32:04 GMT
Last-Modified Wed, 04 May 2011 15:32:03 GMT
Expires Wed, 11 May 2011 15:32:03 GMT
Content-Type text/javascript
Cache-Control Public
Connection close
Define an error handler in the $.ajax() call and inspect the response headers (using jqXHR.getAllResponseHeaders() where jqXHR is the jQuery Ajax object, status code, and responseText.length. You may find that the request is successful, but jQuery treats them as unsuccessful. I've recently had a similar issue with cached files and $.ajax(), and it turns out that sometimes when files are loaded when the browser is offline, or from a local file, return a status code of 0. Because the status doesn't fall in the range of success codes (200-300), jQuery considers the request to have failed. See this for what I did to fix this issue. Basically, in your error handler, you can check the responseText.length. If it is non-empty, consider the request successful and parse the JSON using JSON.parse(). BUT!!! you have to make sure on your server-side that invalid requests are empty.

Categories