Ajax request to Wcf Service get error Object object - javascript

I have a method WCF, which returns a JSON:
enter image description here
the client has a script that should take the data from the wcf service
Script:
<script src="//ajax.googleapis.com/ajax/libs/jquery/1.11.1/jquery.min.js"></script>
<script>
function createCORSRequest(method, url) {
var xhr = new XMLHttpRequest();
if ("withCredentials" in xhr) {
xhr.open(method, url, true);
} else if (typeof XDomainRequest != "undefined") {
xhr = new XDomainRequest();
xhr.open(method, url);
} else {
xhr = null;
}
return xhr;
}
$(document).ready(function () {
$('#btn').click(function () {
$.ajax({
url: 'http://192.168.200.100/Searching.BE.Service//WCFRESTService.svc/GetCategories',
method: 'get',
contentType: 'application/json;charset=utf-8',
dataType: 'json',
success:function(data)
{
alet(data.Announcing[0].Categories.id);
},
error: function (error)
{
alert(error);
}
})
var request = createCORSRequest("get", "http://192.168.200.100/Searching.BE.Service//WCFRESTService.svc/GetCategories");
request.send();
})
})
</script>
<input id="btn" type="button" />
After click button i have this error: Object object
and i have console message:
SCRIPT7002: XMLHttpRequest: Network error 0x80070005, Access Denied .
SEC7120: Source http: // localhost: 4945 is not found in the header Access-Control-Allow-Origin ..
How to solve these problems?

Well, because your web server is running locally (see the 192.168...) address, I can't test it, but your error messages tell me the following:
The first one indicates that you are trying to access an unavailable resource. Try visiting the url with your browser, and see if that gives a response. Also in, http://192.168.200.100/Searching.BE.Service//WCFRESTService.svc/GetCategories, the double slash might indicate it's the wrong url.
The second error is not complete, but are you maybe serving the web page from a different server than the api? Because a quick google search reveals that it has something to do with a cross-site request.

Related

How to avoid REST API authentication when user is already authenticated in TFS dashboard

I'm writing a TFS widget (HTML & Javascript), when I add the widget to my dashboard, I'm correctly logged in TFS.
The widget make a simple GET API such as:
https://{account}.VisualStudio.com/DefaultCollection/_apis[/{area}]/{resource}?api-version={version}
But the response is unauthorized.
Why I've to authenticate me again? The widget is launched from my TFS dashboard...
I don't want to put the credential again, indeed if I open a browser tab and paste the API in the URL it works...
There is a way to solve this problem?
!!!!UPDATE:
I try this code but I see always unauthorized (P.S. from the console I see the token):
<!DOCTYPE html>
<html>
<head>
<script src="bower_components/vss-web-extension-sdk/lib/VSS.SDK.min.js">
</script>
<script>
"use strict";
VSS.init({
explicitNotifyLoaded: true,
usePlatformStyles: true
});
VSS.require(["VSS/Authentication/Services"],
function (VSS_Auth_Service) {
VSS.getAccessToken().then(function(token){
// Format the auth header
var authHeader = VSS_Auth_Service.authTokenManager.getAuthorizationHeader(token);
var xhttp = new XMLHttpRequest();
xhttp.onreadystatechange = function () {
if (this.readyState == 4 && this.status == 200) {
var fileData = this.responseText;
alert(fileData);
}
};
xhttp.open("GET", "https://........./_apis/build/builds?api-version=4.1", true);
xhttp.setRequestHeader('Authorization', authHeader);
console.log(authHeader);
xhttp.send();
// Add token as an Authorization header to your request
});
});
</script>
</head>
<body>
<div class="widget">
<h1 class="title">Builds</h1>
</div>
</body>
</html>
You need to check whether you have vso.build and vso.build_execute scopes.
How are you initiating a REST call? It's better to use Rest Client API. It also matters which resource you are asking from server, there must be an specific scope set in extension for it.
Also tell me which authentication are you using? Use oAuth for this purpose, VSS SDK will give you oAuth AccessToken based on your credentials saved in TFS. You have to use that token for all of your REST calls.
Authenticate using oAuth token. Sample is bellow:
var getWorkItem1 = function (access_token) {
$.ajax({
type: 'GET',
url: 'https://{accountName}.visualstudio.com/{projectname}/_apis/wit/workitems/1?api-version=4.1',
cache: false,
dataType: 'json',
beforeSend: function (xhr) {
var b = "Bearer "+access_token;
xhr.setRequestHeader("Authorization", b);
},
}).done(function (data) {
var workItemType = data.fields['System.WorkItemType'];
}).error(function (e) {
});
}
For obtaining AccessToken use Core Client SDK, please refer to below link:
https://learn.microsoft.com/en-us/vsts/extend/reference/client/core-sdk?view=vsts

how to programmatically enable data sources across domains in browser.?

I am using $.ajax() function in my script which is calling web service from other domain. but I am getting error in IE. Then after doing research, I came to know error was coming due to Internet Explorer by default set "Access data sources across domains" to "prompt". How to set it "Enable" using script..?
Code:
var serviceURL = "https://www.other-domain.com/webservice/showbills?billID=12458";
if ($.browser.msie && window.XDomainRequest) {
var xhr = new XMLHttpRequest();
xhr.onreadystatechange = function () {
if (xhr.readyState == 4) {
var data = xhr.responseText;
var xmlDoc = $.parseXML(data); // then parse into xml
var xml = $(xmlDoc); // create doc
console.log(xml);
// show bill here in table.
}
}
xhr.open('POST', serviceURL, true);
xhr.send();
} else {
$.ajax({
type: "POST",
url: serviceURL,
dataType: "text",
crossOrigin: true,
crossDomain: true,
success: function (data) {
var xmlDoc = $.parseXML(data); // then parse into xml
var xml = $(xmlDoc);// create doc
console.log(xml);
// show bill here in table.
}
});
}
This giving error in browser.
I am getting SEC7120: Origin http://localhost:8080 not found in Access-Control-Allow-Origin header and SCRIPT7002: XMLHttpRequest: Network Error 0x80070005, Access is denied
Microsoft has created its own solution for cross domain AJAX requests in Internet Explorer, called XDomainRequest.
There is a plugin for jQuery to support this: https://github.com/MoonScript/jQuery-ajaxTransport-XDomainRequest
You just have to include this script after including jQuery and then it should work.

javascript cross domain GET method

I'm trying to get an html content to an external url using ajax request and load it to specific div element but I'm having error by doing the cross domain ajax request
Cross-Origin Request Blocked: The Same Origin Policy disallows reading
the remote resource at
http://www.myowndomain.com/embed.php?c=5576b014b210a. (Reason:
CORS header 'Access-Control-Allow-Origin' missing).
This is the sample code that must be pasted in any blogs, forum or website of a users (any domain):
<script type="text/javascript" src="http://myowndomain.com/embed.js"></script><script type="text/javascript">embed.init(["5576b014b210a", "myembeded"]);embed.myCollage();</script><div id="myembeded"></div>
then here's the code for embed.js resided in my domain
var embed = embed || (function(){
var _args = {};
return {
init : function(param) {
_args = param;
},
myCollage : function() {
embed.load_home(_args[0],_args[1]);
},
load_home:function (id,elementId) {
var request = embed.createCORSRequest("get", "http://myowndomain.com/embed.php?c="+id);
if (request){
request.onload = function(){
document.getElementById(elementId).innerHTML = request.responseText;
};
request.send();
}
},
createCORSRequest:function (method, url){
var xhr = new XMLHttpRequest();
if ("withCredentials" in xhr){
xhr.open(method, url, true);
} else if (typeof XDomainRequest != "undefined"){
xhr = new XDomainRequest();
xhr.open(method, url);
} else {
xhr = null;
}
return xhr;
}
};
}());
and for the embed.php resided in my domain
if(isset($_GET['c'])){
echo file_get_contents('http://myowndomain.com/embed/?u='.$_GET['c']);
}
This is a feature implemented into browsers to prevent you from performing requests that aren't on your local domain.
If the other site has an API that allows that, then use their API. Otherwise you can't get the data. If it's your site, modify your web server to enable the requests by adding the header info.
This is all info that could have been gotten by just looking up the error yourself.
Already solved it. by adding this to my embed.js:
header("Access-Control-Allow-Origin: *");
Thanks for the idea.

Ajax request over https hangs for 40 seconds in chrome only

I'm submitting an Ajax request from an https page to an https page. In all other browsers, this goes through instantly, but in Chrome it hangs for a long time (usually about 40 seconds).
What could be causing this? how do I fix it?
EXAMPLE JQUERY CODE THAT ALSO CAUSES THE HANG
<html>
<head>
<script type="text/javascript" src="jquery-1-9-1.js"></script>
</head>
<body>
<br/>
<a onclick="doit()">go</a>
<script>
function doit()
{
var myData = { "key": "value" };
$.ajax({
url: "myhandlepage.php",
data: myData,
dataType: 'json',
type: 'POST',
contentType: 'application/x-www-form-urlencoded',
success: function (data) { alert("OK = " + data.eric); },
error: function (data, status) { alert("FAILED:" + status); }
});
}
</script>
</body>
</html>
EXAMPLE CODE
//Create browser-compliant request object
if( typeof XMLHttpRequest === "undefined" ) XMLHttpRequest = function()
{
try { return new ActiveXObject("Msxml2.XMLHTTP.6.0"); } catch(e) {}
try { return new ActiveXObject("Msxml2.XMLHTTP.3.0"); } catch(e) {}
try { return new ActiveXObject("Msxml2.XMLHTTP"); } catch(e) {}
try { return new ActiveXObject("Microsoft.XMLHTTP"); } catch(e) {}
throw new Error( "This browser does not support XMLHttpRequest." );
};
//Create object
var ajax = new XMLHttpRequest();
//We need to open the object
ajax.open( "post", "/myhandlepage.php", true );
//Now set the callback
ajax.onreadystatechange = function()
{
//elided, but doesn't matter, I can see the 40+ second delay in chrome developer tools
}.bind( this );
//Send the request
ajax.send( mycontent );
For clarification: no errors are shown in Chrome's developer tools.
EDIT: It appears that this issue only happens on the first request for a tab/page in Chrome. All ajax requests in that same tab/page seem to go through instantly after the first lagging request.
MORE INFO
Looking in chrome:net-internals/#events on the hanging request only, in the middle of all the requests, I see this:
t=1360622033867 [st= 4] HTTP_STREAM_PARSER_READ_HEADERS [dt=38643]
--> net_error = -100 (ERR_CONNECTION_CLOSED)
Then it sends the entire request again, and that second time it goes through instantly. What could be causing this first failed request? It occurs every time I do the request for the first time to that URL since opening the browser.

JavaScript - How to set request header for a browser GET

If we do window.location = "http://MyApi.com/Pdf";, browser does a GET of the URL http://MyApi.com/Pdf. But if we want to set authentication header of the request before doing GET of the URL because the server is a REST server and it doesn't support cookies. How to do this?
In all of the cases, I'm using $.ajax to call service but this time I need to show the response in a new window. Response is a PDF file content.
Thanks in advance.
In more recent browsers, you might be able to use blobs:
<!DOCTYPE html>
<html>
<head>
</head>
<body>
<button onclick="tryit();">PDF</button>
<script>
function tryit() {
var win = window.open('_blank');
downloadFile('/pdf', function(blob) {
var url = URL.createObjectURL(blob);
win.location = url;
});
}
function downloadFile(url, success) {
var xhr = new XMLHttpRequest();
xhr.open('GET', url, true);
xhr.setRequestHeader("Authorization", "Basic " + btoa("username:password"));
xhr.responseType = "blob";
xhr.onreadystatechange = function() {
if (xhr.readyState == 4) {
if (success) success(xhr.response);
}
};
xhr.send(null);
}
</script>
</body>
</html>
In IE, ask the user:
window.navigator.msSaveOrOpenBlob(blob, 'readme.pdf');
P.S.
You can test the backend in Node:
router.get('/pdf', function(req, res) {
if(req.headers.authorization !== 'Basic dXNlcm5hbWU6cGFzc3dvcmQ=') return res.status(403).send('Not allowed');
res.sendFile(path.join(__dirname, 'public', 'render.pdf'));
});
router.get('/', function(req, res) {
res.render('index');
});
I think this is what you are looking for... Or correct me if i am wrong.
https://developer.mozilla.org/en/docs/Setting_HTTP_request_headers
If you don't care about hiding or obfuscating the user credentials then just use plain GET authentification:
use http://username:password#MyApi.com/ instead of http://MyApi.com/
Does it have to be a GET?
The reason I am asking is that you could just have a POST form (to a target="_BLANK") that posts whatever but shows an embedded file in a new window. Of course this wouldn't solve the issue with your custom headers, but then since you can also POST using jquery.ajax - which does allow you to set your own headers - you'd have the best of both worlds.
Here's a jQuery plugin that creates such a form dynamically in order to download whichever file. You could use this as a reference...
Hope this helps
You may consider setting the header in beforeunload or onunload event handler
You should configure $.ajax using beforeSend. Below an example, but of course I don't know if the exact setup will work for you without any code to look at.
$.ajax( {
url : '/model/user.json',
dataType : 'json',
'beforeSend' : function(xhr) {
var bytes = Crypto.charenc.Binary.stringToBytes(username + ":" + password);
var base64 = Crypto.util.bytesToBase64(bytes);
xhr.setRequestHeader("Authorization", "Basic " + base64);
},
error : function(xhr, ajaxOptions, thrownError) {
reset();
onError('Invalid username or password. Please try again.');
$('#loginform #user_login').focus();
},
success : function(model) {
cookies();
...
}
});
For this to work you need crypto-js.

Categories