Currency exchange script does not work - javascript

for some reason i cant get a value of the JSON, can any body help me?
function forex() {
var to = document.getElementById("to").value;
alert(to);
var from = document.getElementById("from").value;
alert(from);
var amount = document.getElementById("amount").value;
alert(amount);
$.getJSON("http://rate-exchange.appspot.com/currency?from=" + from + "&to=" + to + "&q=" + amount, function (response) {
alert(response);
});
}

Demo
Due to Same Origin Policy, you can't access the resource on rate-exchange.appspot.com via ajax because of your Javascript executing on a different domain.
In your case, this particular site supports JSONP, so you can use jQuery's JSONP implementation to get around the Same Origin Policy. JSONP works by including the target URL as a <script> tag and using a callback, which is not bound by Same Origin Policy.
The $.getJSON() method will use JSONP if it finds a parameter in the URL such as callback=?.
Example:
function forex() {
var to = document.getElementById("to").value;
var from = document.getElementById("from").value;
var amount = document.getElementById("amount").value;
$.getJSON("http://rate-exchange.appspot.com/currency?&callback=?", { from : from, to : to, q : amount }, function (response) {
alert(response.v);
});
}
I also changed your manual URL variables to an object which is preferred because jQuery will handle the URL encoding.

Instead of the below code:
$.getJSON("http://rate-exchange.appspot.com/currency?from=" + from + "&to=" + to + "&q=" + amount, function (response) {
alert(response);
});
use the following code:
$.ajax({
url: "http://rate-exchange.appspot.com/currency?from=" + from + "&to=" + to + "&q=" + amount,
dataType: 'jsonp',
success: function(response) {
alert(response.v);
}
});

Related

JQuery UI Widgets with AJAX requests

I'm doing some geolocation/map work and building a JQuery widget so that the code is nice and portable for future projects.
I've run into a wall as far as making an AJAX request though; here's a couple of the methods from my widget:
getGeocodeForAddress: function(address) {
req = this._googleMapsApiRequest('geocode','json','address='+address);
//We need 'req' to be the response from the API request so we can do work with it.
},
/**
* Private Maps API request method. This will help to construct a call to Google Maps API.
*
* #param service
* #param output
* #param params
*/
_googleMapsApiRequest: function(service,output,params) {
var widget = this;
var protocol = (this.options.useHttps) ? 'https://' : 'http://';
if (this.options.googleMapsApiKey != '') {
params += '&key' + this.options.googleMapsApiKey;
}
var uri = protocol + 'maps.googleapis.com/maps/api/' + service + '/' + output + '?' + params;
this._sendToLog("Google Maps API Request: " + uri);
$.ajax({
async: false,
type: "GET",
cache: false,
url: encodeURI(uri),
success: function(response) {
//We need the contents of response to be available to the method that called this one.
},
error: function() {
widget._sendToLog('AJAX error');
},
});
},
The specific problem is that once the ajax request is made and returns its success, I can't get the data back into the method that calls it.
I've tried setting an internal option using widget.options.ajaxResponse in _googleMapsApiRequest but that seems to only be 'null' in the calling method, I've tried returning the response from inside the AJAX method but that doesn't work either.
I'm sure I need a callback in the _googleMapsApiRequest method so that it will wait for that method to complete and I can then execute code based on that, but how can I do that within a widget?
A break to think about something else and then a bit more research and I have come up with a callback solution.... it seems a bit clunky but it seems also to do the trick, can anyone improve on it?
getGeocodeForAddress: function(address) {
this._googleMapsApiRequest('geocode','json','address='+address, function(response)
{
//I can access response within this callback.
});
},
/**
* Private Maps API request method. This will help to construct a call to Google Maps API.
*
* #param service
* #param output
* #param params
*/
_googleMapsApiRequest: function(service, output, params, callback) {
var widget = this;
var protocol = (this.options.useHttps) ? 'https://' : 'http://';
if (this.options.googleMapsApiKey != '') {
params += '&key' + this.options.googleMapsApiKey;
}
var uri = protocol + 'maps.googleapis.com/maps/api/' + service + '/' + output + '?' + params;
this._sendToLog("Google Maps API Request: " + uri);
$.ajax({
async: false,
type: "GET",
cache: false,
url: encodeURI(uri),
success: function(response) {
widget._sendToLog('AJAX success, response follows');
widget._sendToLog(response);
},
error: function() {
widget._sendToLog('AJAX error');
}
}).done(function(response) {
if (typeof callback == "function") {
callback(response);
}
});
},
I haven't tested yet to see how this handles unsuccessful ajax requests, but it does the trick at least when the request works.

using .ajax() in .each()

I'm trying to iterate through elements of .ball class and check if their associated url exists:
$(".ball").each(function(i){
var url;
var c_day = $(this).data('day');
var c_mon = $(this).data('mon');
var c_year = $(this).data('year');
url = c_year + "/" + c_mon + "/" + c_day + ".html";
$.ajax({
url: url,
error: function()
{
alert('file: ' + url + ' does not exist');
},
success: function()
{
alert('file: ' + url + 'EXXXXXXISTS!!!!!');
blogA[ blog_count ] = url;
blog_count++;
$(this).css("color", "red" );
}
});
});
I've done some research and read that using .ajax in .each causes a lot of problems but I couldn't wrap my head around on how to fix it.
The problem is that I get really weird results (has to do with asynchronous?). If I alert url outside of ajax, it correctly iterates through the elements. If I alert url in ajax, it spits out urls that belong to the last element of the class.
Something like this, in order to simplify your code
function successHandler(url, ball) {
return function(ret) {
alert('file: ' + url + 'EXXXXXXISTS!!!!!');
ball.css('color','red')
}
}
var balls = $('.ball'), requests = []
balls.each(function(index, ball) {
var url = ...
requests.push($.ajax({ url : url , success : successHandler(url, ball) })
})
$.when.apply($, requests).done(function() {
alert('all balls are checked')
})
Or with ES6:
const success = (url,ball)=>(ret)=>ball.css('color','red')
const balls = $('.balls')
, reqs = balls.map( (b, i) => {
const url = ...
return $.ajax({url, success:success(url,ball)})
})
$.when.apply($, reqs).done( (resps) => alert('all done'))
A Little explanation: You are blindly using this in your callback, not knowing in which context it is going to be executed. In order to work around it and has your URL into callback we are creating function that returns a function, so it will have URL of current .ball DOM object in the context.
You'll probably also need to execute code after all ajax requests are done, so using $.when is the simplest way of doing it. And we are storing all promises just for this reason.
If you aren't concerned about the order of execution of each ajax call and just want to know when they are all done and the array is fully populated, then you can get this to work by fixing your reference to this and by adding a callback function that is called when all items are done:
// this function called when the ajax calls for all balls have finished
// at this point, blogA and blog_count will be populated
function ballsDone() {
// put your code here
}
var balls = $(".ball");
var cnt = balls.length;
balls.each(function(i){
var url;
var self = $(this);
var c_day = self.data('day');
var c_mon = self.data('mon');
var c_year = self.data('year');
url = c_year + "/" + c_mon + "/" + c_day + ".html";
$.ajax({
url: url,
error: function()
{
alert('file: ' + url + ' does not exist');
if (--cnt <= 0) {
ballsDone();
}
},
success: function()
{
blogA[ blog_count ] = url;
blog_count++;
self.css("color", "red" );
if (--cnt <= 0) {
ballsDone();
}
}
});
});
Keep in mind that the ajax calls are asynchronous so the ONLY place you can use the results from the ajax call is in the success handler. You can't use the results of the ajax calls right after the .each() call in a synchronous fashion because the ajax calls have not yet finished. You must wait for the success handler to be called and when cnt success handlers have been called, then they are all done and you can then process the results.

Request for JSON from externel source using $.getjson. 200 success but where is it?

I'm trying to get weather data from openweathermap. This url works with coordinates I put in, and I can download the JSON when I input the url the in the browser bar. I'm trying to get this working in my page. When I run this code, in Firebug I can see the HTTP request got the 200 success code, but it's not printing the response for some reason. Am I not using getJSON properly?
var url = "http://api.openweathermap.org/data/2.5/forecast?lat="+ position.coords.latitude +"&lon=" + position.coords.longitude;
$.getJSON(url, function(res) {
console.log(res);
});
You are trying to read cross domain JSON in a function which reads JSONP.
Cross domain JSON reading is not possible.
Try a JSONP request instead;, by appending a callback
var url = "http://api.openweathermap.org/data/2.5/forecast?lat=" +
position.coords.latitude +"&lon=" + position.coords.longitude + "&callback=?" ;
$.getJSON(url, function(res) {
console.log(res);
});
JSON response is like this :
{ 'a':22 }
JSONP response is like :
myFunction({'a':22} ) , where myFunction was the value passed as callback
jQuery does not need the name of the callback function, however needs callback to be mentioned in the URL so that it can indentify it as a JSONP request.
JSONP
If the URL includes the string "callback=?" (or similar, as defined by
the server-side API), the request is treated as JSONP instead. See the
discussion of the jsonp data type in $.ajax() for more details.
Append this ?callback=? to the url and try again like:
$.getJSON(url + '?callback=?', function(res) {
console.log(res);
});
Try this
function buildQuery() {
var str = "http://api.openweathermap.org/data/2.5/forecast?lat=27.175009&lon=78.041849";
return "select * from json where url ='" + str + "' ";
}
$.ajax({
url: 'http://query.yahooapis.com/v1/public/yql',
data: {
q: buildQuery(),
format: "json"
},
dataType: "jsonp",
success: function (data) {
alert(JSON.stringify(data));
},
error: function (data) {
consol.log(data);
}
});
working Demo :-
http://jsfiddle.net/HWuDk/1/

How could I remake FetchUtil.js for CRM 2011 UR 12

I have to remake FetchUtil.js for using it in CRM 2011 UR 12. I'm not very good in javascript, so I need some help.
This is the native code
var sFetchResult = xmlhttp.responseXML.selectSingleNode("//a:Entities").xml;
var resultDoc = new ActiveXObject("Microsoft.XMLDOM");
resultDoc.async = false;
resultDoc.loadXML(sFetchResult);
It doesn't work even in IE now, because of .selectSingleNode("//a:Entities").xml
I did it like this, but there is no xml field there.
sFetchResult = xmlhttp.responseXML.getElementsByTagName('a:Entities')[0].xml;
var resultDoc = new ActiveXObject("Microsoft.XMLDOM");
resultDoc.async = false;
resultDoc.loadXML(sFetchResult);
Help me to remake this for IE and Chrome.
Thanks a lot!
Here is my calling module (include as webresource)
(function (module, undefined) {
module.buildFetchRequest = function (fetch) {
/// <summary>
/// builds a properly formatted FetchXML request
/// based on Paul Way's blog post "Execute Fetch from JavaScript in CRM 2011"
/// http://blog.customereffective.com/blog/2011/05/execute-fetch-from-javascript-in-crm-2011.html
/// </summary>
var request = "<s:Envelope xmlns:s=\"http://schemas.xmlsoap.org/soap/envelope/\">";
request += "<s:Body>";
request += '<Execute xmlns="http://schemas.microsoft.com/xrm/2011/Contracts/Services">' +
'<request i:type="b:RetrieveMultipleRequest" ' +
' xmlns:b="http://schemas.microsoft.com/xrm/2011/Contracts" ' +
' xmlns:i="http://www.w3.org/2001/XMLSchema-instance">' +
'<b:Parameters xmlns:c="http://schemas.datacontract.org/2004/07/System.Collections.Generic">' +
'<b:KeyValuePairOfstringanyType>' +
'<c:key>Query</c:key>' +
'<c:value i:type="b:FetchExpression">' +
'<b:Query>';
request += CrmEncodeDecode.CrmXmlEncode(fetch);
request += '</b:Query>' +
'</c:value>' +
'</b:KeyValuePairOfstringanyType>' +
'</b:Parameters>' +
'<b:RequestId i:nil="true"/>' +
'<b:RequestName>RetrieveMultiple</b:RequestName>' +
'</request>' +
'</Execute>';
request += '</s:Body></s:Envelope>';
return request;
};
module.sendFetchQuery = function (fetchRequest, doneCallback, failCallback) {
//path to CRM root
var server = window.location.protocol + "//" + window.location.host;
//full path to CRM organization service - you may need to modify this depending on your particular situation
var path = server + "/XRMServices/2011/Organization.svc/web";
$.ajax({
type: "POST",
dataType: 'xml',
async: false,
contentType: "text/xml; charset=utf-8",
processData: false,
url: path,
data: fetchRequest,
beforeSend: function (xhr) {
xhr.setRequestHeader(
"SOAPAction",
"http://schemas.microsoft.com/xrm/2011/Contracts/Services/IOrganizationService/Execute"
); //without the SOAPAction header, CRM will return a 500 error
}
}).done(doneCallback)
.fail(failCallback);
};
}(window.xFetch = window.xFetch || {}));
Usage
(the parser requires jQuery ... I am doing most of my fetch calls in web resourced html pages so this isn't a problem) this works in IE and Chrome haven't checked firefox but I can't see why it wouldn't work.
var fetchXml =
xFetch.buildFetchRequest("<fetch version='1.0' output-format='xml-platform' mapping='logical' distinct='false'>" +
" <entity name='ENTITYNAME'>" +
" <attribute name='ATTRIBUTE' />" +
" </entity>" +
"</fetch>");
var entityList = new Array();
xFetch.sendFetchQuery(fetchXml,
function (fetchResponse) {
// chrome doesn't like the namespaces because of
// selectSingleNode implementations (which make sense btw)
// I'll never understand why Microsoft have to pepper their xml
// with namespace dross
$(fetchResponse).find("a\\:Entity, Entity").each(function () {
var entityData = {};
$(this).find("a\\:KeyValuePairOfstringanyType, KeyValuePairOfstringanyType").each(function () {
var xmlElement = $(this);
var key = xmlElement.find("b\\:key, key").text();
var value = xmlElement.find("b\\:value, value").text();
entityData[key] = value;
});
//inner loop
$(this).find("a\\:KeyValuePairOfstringstring, KeyValuePairOfstringstring").each(function () {
var xmlElement = $(this);
var key = xmlElement.find("b\\:key, key").text();
var value = xmlElement.find("b\\:value, value").text();
entityData[key] = value;
});
entityList.push(entityData);
});
}, function (jqXhr, textStatus, errorThrown) {
// if unsuccessful, generate an error alert message
});
for (var i = 0; i < entityList.length; i++) {
if (entityList[i].ATTRIBUTE === "Yes" ){
// DO WHATEVER
}
}
I only needed attributes with KeyValuePairOfstringstring and KeyValuePairOfstringanyType but you could parse out any attribute with the right combination of selectors
each item in retrieved
I was facing the similar issue and I resolved it by using below workaround.
var sFetchResult = xmlhttp.response;
var tempresultDoc = new ActiveXObject("Microsoft.XMLDOM");
tempresultDoc.async = false;
tempresultDoc.loadXML(sFetchResult);
// Now at this point we will have the XML file. Get the singleNode from the XML by using below code.
var resultDoc = new ActiveXObject("Microsoft.XMLDOM");
resultDoc.async = false;
resultDoc.loadXML(tempresultDoc.childNodes[0].selectSingleNode("//a:Entities").xml);
Regards,
Krutika Suchak
If you're looking for a version that doesn't require JQuery, and one that parses the results, check this out. It not only wraps the FetchXML, but also parses the response XML into JavaScript objects for easy retrieval.

$.getJSON not doing anything

I am unsure why, but it seems that when I call $.getJSON after another getJson has been called, nothing happens. Here is the code:
getWeather();
function getWeather() {
$.getJSON("http://where.yahooapis.com/geocode?q=" + lat + ",+" + lon + "&gflags=R&flags=J", function(data){
zipCode = data.ResultSet.Results[0].postal;
WOEID = data.ResultSet.Results[0].woeid;
getYahooWeather(WOEID);
});
}
function getYahooWeather(x) {
var query = escape('select item from weather.forecast where woeid="'+x+'"');
var url = "http://query.yahooapis.com/v1/public/yql?q=" + query + "&format=json&callback=c";
console.log(url);
$.getJSON(url, function(data2){
console.log("hey");
});
}
My question is, am I doing something wrong with these $.getJSON calls?
Thanks so much
You have specified that the callback should be the c function, so declare it:
function getYahooWeather(x) {
var query = escape('select item from weather.forecast where woeid="'+x+'"');
var url = "http://query.yahooapis.com/v1/public/yql?q=" + query + "&format=json&callback=c";
console.log(url);
$.getJSON(url);
}
function c(data2) {
console.log("hey");
}
Your request is outside the current domain. You cannot make foreign request, it is restricted by cross-domain policy.
Such requests and made using a jsonp request instead. And here is a guide to get you started.

Categories

Resources