I am in quite an interesting situation. I work for a middle sized company and we have IE 11 for our browser but for a particular application I am programming, its document mode is set to IE 5. I am making calls to a web service located within the company Intranet (the particular URL is https) and the website where I'm making the call is http (not sure if I can set document.domain or anything here). I am currently using ajax and I'm able to successfully communicate with service and get code back using the code below. Although, each time I do get the message that says, "the information you're accessing is coming from another source." If I hit yes, then I get information back from the server, if I hit no, then the data does not come through. I tried to call this same method from a different page on the same website, and instead get the access denied error, without even having the prompt. That one really has me confused.
I've read through many many different articles on the subject of CORS at this point and know there's a few things to try to avoid this message. Credentials are omitted below. I am using Jquery 1.9.1 minimized version.
$.support.cors = true;
$.ajax
({
type: "POST",
crossDomain: true,
beforeSend: function(request)
{
request.setRequestHeader("Authorization", "");
return true;
},
url: webServiceURL,
dataType: "xml",
async: true,
data: soapMessage,
contentType: "text/xml; charset=\"utf-8\"",
success: OnSuccess,
error: OnError
});
}
function OnSuccess(data, status)
{
alert(status);
alert(data);
var documentValArr = parseXMLRrec(data);
insertDataIntoTable(documentValArr);
}
function OnError(request, status, error)
{
alert(request.responseText);
alert(error);
alert(status);
}
Enable cross domain sources IE setting. I suppose this can try to be set for that specific URL in that intranet zone, but it still feels wrong to me. Not sure how the security group at work would feel about it either.
Add the URL I'm trying to access to the Intranet trusted sites. I think this would fix the issue I'm seeing and this is something I definitely would want to try.
Also, when testing on my local workstation and calling the web service through IE 11 doc 5 mode, I do not get the message.
Work with the group that owns the server where the service lives, and see if they can somehow add URL's that can access the service alright. This would be interesting because there are quite a lot of production sites.
Because I'm using IE 11 in doc 5 mode I could try to use the XDomainRequest object but I am not sure if it would be a worth while effort to do this if the earlier options work out.
So there my interesting scenario is. I would very much like some feed back from people on the situation, what they would do, and what type of things and solutions go for. THank you very much for all input and ideas!
Related
We have recently noticed an issue where a common page on our site temporarily freezes when navigated to from Internet Explorer with the message "This web page is not responding due to a long running script".
After investigating, I can see that it is caused by an AJAX XMLHttpRequest that is taking 30 - 45 seconds to complete. Normally when there are performance issues with our AJAX calls like this, the long wait time is during the wait for the server's response. But here, it is the wait to create the request and send it that is taking so long:
Note that there are no issues with this request in Google Chrome at all, it only takes 200ms:
These results are consistent on every page refresh. Note also that this is not a large request nor a large response. The request body is actually empty:
and the response is quite small:
I figured since the problem appears to be client-side, there must be something off with our scripts, but we use the same generic function for all of our AJAX calls and don't have this problem with anything else:
JSONRequest: function (url, type, data, success, error) {
var customError = function (er) {
console.log(er);
}
if (error !== 'undefined' && error != null)
customError = error;
$.ajax({
url: url,
type: type,
cache: false,
data: JSON.stringify(data),
contentType: 'application/json; charset=utf-8',
success: success,
error: customError
});
},
I am quite puzzled here. Is this simply a matter of "Avoid IE", or is there something I am missing? 30+ seconds to create a small request and send it seems absurdly long, especially when it is fast in Chrome. What gives?
*Note that I am testing with IE 11.
For some reason, a line of JQuery that unchecks all check boxes in a list of them was causing the issue:
$('.list-check-buttons.check-button.only-button input:checkbox').prop('checked', false)
I verified this by stepping through in the Chrome Debugger and also removing this line resolved the issue for the most part. (It turns out we didn't need this line as the same logic was also being handled in another place which strangely enough was not causing performance issues.)
I use below function to get the Continent Code from the api which works fine on localhost but fail in live environment which is website
$.getJSON('//www.geoplugin.net/json.gp?jsoncallback=?', function (data) {
// console.log(JSON.stringify(data, null, 2));
console.log(JSON.stringify(data.geoplugin_continentCode));
});
Warning which i see in Console is
Loading failed for the with source
“https://www.geoplugin.net/json.gp?jsoncallback=jQuery16407901144106031991_1537089290623&_=1537089292750”.
I am not sure why it fails on website https://www.example.com
could SSL version some problem as i am not sure as i tried it on fiddle & it works fine http://jsfiddle.net/om8ahkp3/
UPDATE
Since problem was due to crossdomain issue which as this api used a different url for ssl version. i was not able to use this ssl version as it was not free.
So ended up using another api which had free option also limited to 50k request on monthly basis.
$.ajax({
url: 'https://api.ipgeolocation.io/ipgeo?fields=is_eu& excludes=ip&apiKey=YOURKEY',
dataType: 'json',
success: function (json) {
console.log("json.is_eu " + json.is_eu);
}
});
What is the whole problem?
You want to access to a third site (crossDomain). So, That site decides that you can access to it, or not. When a site provides a service (similar geo service that you have used it), it determines which part of it's services are free.
In your case, if your source site's protocol is http (like as localhost) and dest site (service provider site) is http too, you can access to this geo service with your above code (because this third site allows this now). But if you want to access to this service from a https site (I think you are trying this now) the geoPlugin don't allow you easily or free!
In this cases, the destination sites, provide another urls and define user levels (to getting money for special services.).
In act, if your dest site was for yourself too(which it is not in this case), you could add needed access to specific referer sites, but now...
I look at its site to be sure. You must use this url in this case:
https://ssl.geoplugin.net/json.gp?k=yourAPICode
But this is not all of things! What is k in above url? This site writes:
"For SSL access, an API Key is required to offset certificate prices and costs €12 per year."
I don't know, but if you need it, you should search for free plugins (if exists) or buy it.
Let me start off with saying I just figured out how to use JQuery's "$.ajax()" just a few days ago. I've been able to read local .xml and .json files.
Also, I've figured out how to use the google maps API to import dynamic and static maps. (just following the google documentation)
Now, I had an idea to use steam IDs for a school project, but I keep getting this error:
XMLHttpRequest cannot load http://api.steampowered.com/ISteamUser/GetFriendList/v0001/?key=[MY_SECRET_KEY]2&steamid=76561197960435530&relationship=friend. Origin http://local.mysite.com is not allowed by Access-Control-Allow-Origin.
(I took out the key, and the generated key is suppose to allow access to http://local.mysite.com)
Here is my code:
<script type="text/javascript">
$.ajax({
url: "http://api.steampowered.com/ISteamUser/GetFriendList/v0001/?key=[MY_SECRET_KEY]&steamid=76561197960435530&relationship=friend",
dataType: "json",
success: function(data){
console.log(data);
},
error: function(req,text,error){
console.log(text);
console.log(error);
console.log("DIDN'T WORK!")
}
});
</script>
Does anybody know what's going on? I can't seem to get this to work.
See this answer and the posts here. For more background visit mdn.
Essentially you're running into a security issue where the browser won't allow you to make a request from http://local.mysite.com to http://api.steampowered.com.
Do you have access to a server? Instead of making a request like this: browser -> steampowered you can make a request like this browser -> your server -> steampowered.
You're going to want to create an endpoint on your server (so that it's in your domain) that you can send a request to, that will in turn send a request to steam powered.
What language / framework are you running and we can give you example code.
The problem I am having is that when I use jquery ajax post, with very low frequency (< 2%), the post parameters never make it to the server. I do see the post request in the access log. It seems to happen only on IE (I've observed it on 7, 8, and 9 in the logs).
When I switch the call from type "post" to type "get" the issue goes away.
Has anyone else ever seen this odd behavior on IE? Thanks!
I have seen this for various ajax calls, but here is a typical one:
var data= {
"guess" : "m1",
"eas" : "hello world"
};
$.ajax({
url: "http://myco.com/ajaxcall.action",
data: data,
type : 'post',
dataType: 'json',
success: function(data) {},
error: function() {}
});
Update: passing "cache: false" does not fix the issue.
I have spent the last week tracking down a similar problem in my own application (uses Dojo, not JQuery). From your description and frequency of occurrence, I would say it's the same issue.
When HTTP persistent connections are used between browser and server (the default behavior), an HTTP connection can be closed down by the server at any time. This creates a very small timing hole when the browser starts to send a new request at the same time the server closes the connection. Most browsers will use a different connection or open a new connection and resend the request. This is the behavior suggested in RFC 2616 section 8.1.4:
A client, server, or proxy MAY close the transport connection at any
time. For example, a client might have started to send a new request
at the same time that the server has decided to close the "idle"
connection. From the server's point of view, the connection is being
closed while it was idle, but from the client's point of view, a
request is in progress.
This means that clients, servers, and proxies MUST be able to recover
from asynchronous close events. Client software SHOULD reopen the
transport connection and retransmit the aborted sequence of requests
without user interaction so long as the request sequence is
idempotent (see section 9.1.2).
Internet explorer does try to resend the request when this happens, but when it happens to be a POST, it mangles it up by sending the headers (with Content-Length) but no actual data. That is a malformed request and should always lead to an HTTP error (usually after some timeout waiting for the data that never comes).
This bug is documented by Microsoft as KB 895954 (see http://support.microsoft.com/kb/895954). Microsoft first recognized this bug in IE 6. They provided a hotfix, and appear to have shipped the hotfix with every version of IE since then including IE 9. There are two problems with the fix:
The hotfix is not activated by default. You have to create a really weird key using regedit to activate the fix: HKEY_LOCAL_MACHINE\Software\Microsoft\Internet Explorer\Main\FeatureControl\FEATURE_SKIP_POST_RETRY_ON_INTERNETWRITEFILE_KB895954.
The fix doesn't really fix the problem. The "fixed" behavior is that when the connection is closed when trying to send a request, it does not even try to resend it. It simply passes the error along to the javascript application.
It appears that you have to add error handlers in your code and re-post the request yourself if it fails. I am looking into this solution for my application. My concern is that I'm not sure how to tell if the error I get is caused by a failed attempt to send the query, or some error sent back from the server as a result of the query (in which case I don't want to resend it).
I wrote a C program to simulate a web server and explicitly close a connection to see how the browser handles it. I have found that IE reproduces the errant behavior 100% of the time, while Firefox, Safari and Chrome recover by properly resending the POST on another connection 100% of the time. Perhaps the answer is, "don't use IE."
As a direct answer to your question: Yes we have just come across this issue and could not find a reasonable explanation. It only affects IE and with a very low frequency - took a long while to get to the conclusion that it is a sporadic jQuery Ajax in IE bug. We had to 'fix' the issue by returning a fail from the server under this condition and re-posting the data after a 1 second delay!
Hacky as hell but seemed to be the only way.
There was definitely no clash with DOM elements etc. and no logical reason for this to happen, the page can be updated many times by the user successfully with intermittent fails.
Must be a bug.
I think you have to prevent caching in Internet Explorer. Try to set option cache to false.
Example:
$.ajax({
url: "http://myco.com/ajaxcall.action",
data: data,
type : 'post',
dataType: 'json',
success: function(data) {},
error: function() {},
cache: false
});
The params sent to the PHP are received from IE in GET:
$.ajax ({
url: "path/to/ajax.php"
,method: "POST"
,data: {
var1: "value1"
,var2: true
,varX: 123123
}
,cache: false
,success: function (data) {
alert (data);
}
});
Then on PHP you should use REQUEST instead of POST:
$var1 = $_REQUEST ["var1"]; // value1
$var2 = $_REQUEST ["var2"]; // true
$var3 = $_REQUEST ["var3"]; // 123123
This example could use it for compatibility with IE7
I'm writing some browser side dynamic functionality and using HTTP Basic Auth to protect some resources. The user experience is very important and is highly customized.
Here's a simple test JQuery method that eventually will test if a user has supplied the right credentials in a form:
$(document).ready(function() {
$("#submit").click(function() {
var token = Base64.encode($('#username').val() + ':' + $('#password').val());
$.ajax({
url: '/private',
method: 'GET',
async: false,
beforeSend: function(req) {
req.setRequestHeader('Authorization', 'test:password');
},
error: function(request, textStatus, error) {
if (request.status == 401) {
alert('401');
}
}
});
return false;
});
});
If they are not allowed to access /private, at the moment they should see just the alert box. However, on Firefox, a browser-provided login form pops up (to retry with new credentials). Safari does not do this.
We want to completely control the experience with custom forms, fades, transitions, etc. How can I keep Firefox's default box from being shown? (If this will be an issue when we test for IE, I'd love to hear solutions there, too.)
The solution is to set the WWW-Authenticate header to something other than Basic. For example set it to:
WWW-Authenticate: None
or
WWW-Authenticate: FormBased
if you use form based login. Then the browser will not show you a login window.
In case you haven't read it:
How can I supress the browser's authentication dialog?
Doesn't look too promising :)
Unfortunatly, I am hitting the same issue here.
In my opinion, Browsers should not give a prompt for an xmlhttprequest. I really wish someone would push that cause people are really wanting to move to jQuery for their auth needs.
Well here is the help I can give you, I found this jQuery Digest thing, I have no idea what it really does or anything, but if someone could take this code the right way, we could have a jquery digest auth system.
https://www.openhub.net/p/digestj
I would think with this handy new AuthDigestDomain option, we could have the above script rewritten or whatever and have the secured area 'linked' together and we could get past this problem once and for all. Well... best of luck =)
I found somewhere a workaround of this authentication popup issue.
WWW-Authenticate: None
doesn't work for me, but I've added
'Authorization': 'Basic'
to the headers and it works like a charm.