What is the right way to use "context:..." in an AJAX call? - javascript

So I'm aware that there are a big amount of threads about AJAX and the use of the context but after hours of reading and trying I open a new Thread.
So I have this (shorten version) javascript function:
this.CallService = function () {
var Type = this.Type;
var Url = this.Url;
var Data = this.Data;
var ContentType = this.ContentType;
var DataType = this.DataType;
var ProcessData = this.ProcessData;
var ClipUrl = this.ClipUrl;
var CountMax = this.CountMax;
var Callback = this.Callback;
var SucceededServiceCallback = this.SucceededServiceCallback;
var FailedServiceCallback = this.FailedServiceCallback;
return $.ajax({
type: Type, //GET or POST or PUT or DELETE verb
url: Url, // Location of the service
data: Data, //Data sent to server
contentType: ContentType, // content type sent to server
dataType: DataType, //Expected data format from server
processdata: ProcessData, //True or False
context: this,
}).done(function (msg) {//On Successfull service call
SucceededServiceCallback(this, msg);
}).fail(function (msg) {
FailedServiceCallback(this, msg);
});
}
The Important part here are the context: this and the two callbacks done and fail. Im those two callbacks I give the this context to my callback functions:
this.SucceededServiceCallback = function (context, result) {
if (null != context) {
UpdateDebugInfo(context, "succeeded: " + context.DataType + " URL: " + context.Url + " Data: " + context.Data + " Result: " +result);
}
if (context != null && context.DataType == "json" && result != null && context.Callback != null) {
context.Callback(context, result);
}
}
Here the important part is that I use the context to see access the variables DataType, Callback, Url etc.
The Problem now is that the context is set to the last context used (it's an asynchron call so all the variable are the variable from the last call). So I'm pretty sure something is wrong with that context: this, part. I just don't know how to use this right. Thanks for your help.
tl;dr:
I use context: this in an Ajax call. Context is always set to the last "this" called. I want to use the "this" of the call.

You are "caching" all your variables before you fire each request, but in your SucceededServiceCallback function you are inspecting this.XXX - which is not the var Type it looks like you are expecting, but the actual this.Type itself.
What you could do is put these properties into an object and pass it as context, rather than your main object:
this.CallService = function () {
var context = {
Type : this.Type,
Url : this.Url,
Data : this.Data,
ContentType : this.ContentType,
DataType : this.DataType,
ProcessData : this.ProcessData,
ClipUrl : this.ClipUrl,
CountMax : this.CountMax,
Callback : this.Callback
};
var SucceededServiceCallback = this.SucceededServiceCallback;
var FailedServiceCallback = this.FailedServiceCallback;
return $.ajax({
type: Type, //GET or POST or PUT or DELETE verb
url: Url, // Location of the service
data: Data, //Data sent to server
contentType: ContentType, // content type sent to server
dataType: DataType, //Expected data format from server
processdata: ProcessData, //True or False
context: context,
}).done(function (msg) {//On Successfull service call
SucceededServiceCallback(this, msg);
}).fail(function (msg) {
FailedServiceCallback(this, msg);
});
}

Related

jquery ajax inside loop return statusText error, Status 0 after certain time in IE

I m trying to update bulk of data one by one using Jquery ajax,so that i can show update progress. every thing goes well at beginning but after 5 min, it throw an error like in
Image while checking network request/respond:.
Error on error function of ajax:.
MainData is array of json object and is contain around 3000 number of json object.
function DoPost()
{
$.each(MainData, function (key, value) {
var mainCode = value.MainCode;
var companyCode = value.CompanyCode;
$.ajax({
url: "Allotment.asmx/DoAllotment",
data: "{MainCode:'" + mainCode + "', sNoOfAllotment:'" + noOfAllot + "',CompanyCode:'" + companyCode + "'}",
dataType: 'text',
contentType: "application/json; charset=utf-8",
type: "Post",
success: function (res){
Progress(res); // this funtion will show progress of update.
},
error: function (res) {
console.log(res);
}
});
});
}
I am using web service of asp.net webform
The issue could be maximum number of concurrent connections to same URL. You can schedule next $.ajax() call when current $.ajax() completes.
See also multiple, sequential fetch() Promise
function DoPost(value) {
var mainCode = value.MainCode;
var companyCode = value.CompanyCode;
return $.ajax({
url: "Allotment.asmx/DoAllotment",
data: "{MainCode:'" + mainCode + "', sNoOfAllotment:'"
+ noOfAllot + "',CompanyCode:'" + companyCode + "'}",
dataType: 'text',
contentType: "application/json; charset=utf-8",
type: "POST",
success: function(res) {
Progress(res); // this funtion will show progress of update.
},
error: function(res) {
console.log(res);
}
});
}
var copy = MainData.slice(0);
var res = (function re(value) {
return DoPost(value).then(function() {
return copy.length ? re(copy.shift()) : "complete"
})
})(copy.shift());
res.then(function(complete) {
console.log(complete)
}, function(err, textStatus, jqxhr) {
console.log(err)
});
The error 0x2ee2 is IE's representation of timeout error. The occurrence of this error shows that the server has stopped responding to the requests due to a high number of requests sent from the same client. This is the server avoiding DOS attacks from the client.
The proper method is to optimize the code and try to utilize the maximum available bandwidth in order to minimize the number of requests to the server.

Returning an object from Web Service to Ajax Request success callback function

Hello Fellow Developers,
I have a SSN textbox that onblur calls a function which does an ajax request to a Web Method to decide if an employee has been previously hired.
The Web Method returns a TermedEmployee Object to the success callback, but I'm unsure how to parse the object.
$('#<%=FormView1.FindControl("SSNField").ClientID%>').blur(hideValue);
hideValue = function (ev) {
var $this = $(this);
$this.data('value', $this.val());
$('#<%=FormView1.FindControl("hiddenSSN").ClientID%>').val($this.val());
var data2Send = '{"SSN": ' + $this.val() + ' }';
$.ajax({
type: "POST",
url: "AuthforHire.aspx/EmployeeisRehire",
data: data2Send,
contentType: "application/json; charset=utf-8",
dataType: "json",
success: function (result) {
var obj = JSON.stringify(result.d);
if (obj.IsTermed) {
$('#%=RadWindowRehire.ContentContainer.FindControl("TextBoxTermID").ClientID%>').val(arg.d);
var wndWidth = 900;
var wndHeight = 500;
var wnd = window.radopen(null, "RadWindowRehire");
}
},
error: function (xhr) {
alert('Form update failed. '); //error occurred
}
});
Below is a minified version of my webMethod, which works correctly
[System.Web.Services.WebMethod]
public static TermedEmployee EmployeeisRehire(string SSN)
{
TermedEmployee termedEmp = new TermedEmployee();
// Db call to get necessary data.
termedEmp.Name = dr["name"];
termedEmp.TermDate = Convert.ToDateTime(dr["TermDate"].ToString());
......
}
So How Can I extract Name, TermDate,StartDate, ReasonforTerm, etc from the object returned to the callback function?
Thank you in advance!
The first line in your success callback is:
var obj = JSON.stringify(result.d);
Which is trying to serialize what ASP.Net will already have serialized for you.
Change this to:
var obj = result.d;
And you will then have access to obj.Name, obj.TermDate and all the other properties by name.

Callback with javascript and jquery

I am more of a java developer and am having difficulty with javascript callback. I am wondering if any experts here would help me out of my struggle with this code.
I am trying to pull our locations from db and populating in an array. On first load i am trying to refresh all locations and I am having trouble to control the flow of execution and loading values. Below is the code and I have put in the output at the end.
JQUERY CODE:
// load all locations on first load.
refreshLocations();
$("#locInput").autocomplete({source: locationData});
}); // end of document.ready
// function to refresh all locations.
function refreshLocations() {
getLocationArray(function(){
console.log("firing after getting location array");
});
}
// function to get the required array of locations.
function getLocationArray() {
getJsonValues("GET", "getLocalityData.php", "", getLocalityFromJson);
}
// function to pick up localities from json.
function getLocalityFromJson(json){
if (!json) {
console.log("====> JSON IS NOT DEFINED !! <====");
return;
} else {
console.log("json is defined so processing...");
var i = 0;
$.each(json.listinginfo, function() {
var loc = json.listinginfo[i].locality;
locationArray[i] = loc;
console.log("added location ->" + locationArray[i]);
i++;
});
}
//return locationArray;
}
// function to get raw json from db.
function getJsonValues(type, url, query, getLocalityFromJson) {
var json;
// if the previous request is still pending abort.
if (req !== null)
req.abort();
var searchString = "";
if (query !== "") {
searchString = "searchStr" + query;
}
console.log("searchString : (" + query + ")");
req = $.ajax({
type: type,
url: url,
data: searchString,
contentType: "application/json; charset=utf-8",
dataType: "text",
success: function(result) {
json = JSON.parse(result);
console.log("========start of json
return============");
console.log(JSON.stringify(json));
console.log("========end of json
return============");
//return json;
}
});
getLocalityFromJson(json);
return json;
}
the output from above code is as follows:
searchString : () (18:25:36:473)
at locality1.php:74
====> JSON IS NOT DEFINED !! <==== (18:25:36:518)
at locality1.php:48
========start of json return============ (18:25:37:606)
at locality1.php:83
{"listinginfo":[{"listing":"1","locality":"birmingham"},
{"listing":"2","locality":"oxford"}]} (18:25:37:624)
at locality1.php:84
========end of json return============ (18:25:37:642)
at locality1.php:85
>
Help will be greatly appreciated.
call getLocalityFromJson(json); inside your success callback
function getJsonValues(type, url, query, getLocalityFromJson) {
var json;
// if the previous request is still pending abort.
if (req !== null)
req.abort();
var searchString = "";
if (query !== "") {
searchString = "searchStr" + query;
}
console.log("searchString : (" + query + ")");
req = $.ajax({
type: type,
url: url,
data: searchString,
contentType: "application/json; charset=utf-8",
dataType: "text",
success: function(result) {
json = JSON.parse(result);
console.log("========start of json return============");
console.log(JSON.stringify(json));
console.log("========end of json return============");
//return json;
getLocalityFromJson(json);
}
});
}
You need to call getLocalityFromJson(json) and return json inside your ajax success function. Ajax requests are asynchronous, there's no guarantee that the request will be finished by the time you get to the lines getLocalityFromJson(json); return(json); where they are currently.
The call back functions from a jquery ajax call is complete, failure, success, etc..
Success is called after a request is successful,
Failure is called if theres something like an error 500, or a 404, or w/e.
Complete is Always called after a ajax call.
If you want your code to just follow sequence like in java, throw async: false into your ajax call.. but I wouldnt' recommend this as it defeats the purpose of using this method, and also locks up your browser.
You should make sure you are waiting for the request to finish before moving on - so put code in the success function that you want to run AFTER the request has finished fetching your data.
I think you need to remember Ajax is running async, so you need to follow this thread to execute your refresh.

What are the differences between Ajax & getJSON when calling an action method that return JSON

I am reading a book about asp.net MVC and I found different methods for calling Action methods that return JSON:, either using Ajax OR getJSOn, so are these two methods equivalent to:-
$.ajax({
type: "GET",
url: "http://localhost:11279/test/testcall",
dataType: "json",
success: function (result) {
var message = result.Title + ": $" + result.CurrentPrice;
$('#Result').html(message);
},
error: function (XMLHttpRequest, textStatus, errorThrown) {
alert("Error: " + errorThrown);
}
});
And the getJSON is:-
<script type="text/javascript">
$(function () {
$.getJSON("http://localhost:11279/test/testcall",
function (data) {
$.each(data, function (key, val) {
var str = val.Description;
$('<li/>', { html: str }).appendTo($('#auctions'));
});
});
});
</script>
Second question
if I want to call the above action method or an external web service from a controller class instead of using javaScript, so which c-sharp methods I should use ?, and how I am going to pass the returned JSON from the controller class to the view.
BR
getJson-
Method allow get json data by making ajax call to page. This method allows only to pass the parameter by get method posting parameter is not allowed.
Ajax ()- This method provide more control than all other methods we seen. you can figure out the difference by checking the list of parameter
Provide more control on the data sending and on response data.
Allow to handle error occur during call.
Allow to handle data if the call to ajax page is successfull.
Answer to 2
You can make use of jquery + Ajax() function to consume it in your html page..
here is article for you : Steps to Call WCF Service using jQuery.
something like this
function WCFJSON() {
var userid = "1";
Type = "POST";
Url = "Service.svc/GetUser";
Data = '{"Id": "' + userid + '"}';
ContentType = "application/json; charset=utf-8";
DataType = "json"; varProcessData = true;
CallService();
}
//function to call WCF Service
function CallService() {
$.ajax({
type: Type, //GET or POST or PUT or DELETE verb
url: Url, // Location of the service
data: Data, //Data sent to server
contentType: ContentType, // content type sent to server
dataType: DataType, //Expected data format from server
processdata: ProcessData, //True or False
success: function(msg) {//On Successfull service call
ServiceSucceeded(msg);
},
error: ServiceFailed// When Service call fails
});
}

backbone javascript setTimeOut method

im have a problem with method setTimeOut that call the function self and set a delay, the function should be called again and again after every request is done but it only runs once. It works without using backbone.js tho, don't know it doesnt work after integration with backbone.js. Any help is appreciated!
So this is a function in client that runs a GET request gets data from server, the request runs in a time interval(decided in the server), as soon as a data comes in, client gets it and the request runs again after.
getRequest:function() {
var XHR = $.ajax({
url: '/nextdocument',
type: 'GET',
async: true,
cache: false,
timeout: 11000,
success:function(data) {
var name = data.description;
var price = data.price;
console.log("read--> " + name + price);
setTimeout("this.getRequest", 1000);
if (data.ok == "true") {
data["ok"] = data.ok;
$.ajax(
{
url: "/customerdone",
data: JSON.stringify(data),
processData: false,
type: 'POST',
contentType: 'application/json'
}
)
}else{
//no document if no read in
console.log("error--> " + data.errorMessage)
}
}
})
return XHR;
}
The problem is that you're using "this" in your setTimeout call. You can't do this because "this" will be the global object when the timer executes the function you're trying to reference.
like others have suggested, you need to pass an actual function to your timer, not a string. then you can reference whatever function from whatever object you want.
probably, the function getRequest isn't being called. This is, as far as I think, because you are sending a string -- "this.getRequest" to the setTimeout function. As a rule of thumb, never pass string to this, pass functions. Although, it might be perfectly ok in some situations (i'd never recommend it anyway), here 'this' might be causing trouble. Use something like this:
getRequest:function() {
var fn = arguments.callee;
var XHR = $.ajax({
url: '/nextdocument',
type: 'GET',
async: true,
cache: false,
timeout: 11000,
success:function(data) {
var name = data.description;
var price = data.price;
console.log("read--> " + name + price);
setTimeout(fn, 1000);
if (data.ok == "true") {
data["ok"] = data.ok;
$.ajax(
{
url: "/customerdone",
data: JSON.stringify(data),
processData: false,
type: 'POST',
contentType: 'application/json'
}
)
}else{
//no document if no read in
console.log("error--> " + data.errorMessage)
}
}
})
return XHR;
}

Categories