使用 Jsonp 进行 $.ajax 调用后无法在 Jquery 中检索数据
Posted
技术标签:
【中文标题】使用 Jsonp 进行 $.ajax 调用后无法在 Jquery 中检索数据【英文标题】:cannot retrieve data in Jquery after makin $.ajax call using Jsonp 【发布时间】:2012-05-09 15:59:37 【问题描述】:我有一个函数用于从我的 RESTFUL WCF 服务中检索数据。返回的数据必须是 JSON。
在客户端,我有一个名为 autosuggest 的 javascript 函数,如下所示:
function autosuggest(location)
var uri= 'http://localhost:2043/Suggest.svc/GetAirportsjson?location='+location;
$.ajax(
url:uri,
dataType: 'jsonp',
jsonp: 'callback',
jsonpCallback: 'jsonpCallback(e)',
success: function(e)
alert("success");
); ;
Service 接口为:
[WebInvoke(Method = "GET", ResponseFormat = WebMessageFormat.Xml, BodyStyle = WebMessageBodyStyle.Bare, UriTemplate = "/GetAirportsXML?location=location")]
[OperationContract]
List<Suggestions> GetAirportDataXml(string location);
[WebInvoke(Method = "GET", ResponseFormat = WebMessageFormat.Json, BodyStyle = WebMessageBodyStyle.Bare, UriTemplate = "/GetAirportsJSON?location=location")]
[OperationContract]
List<Suggestions> GetAirportDataJson(string location);
并且在 Firebug 中观察到 location=m 的响应是
["AirportCode":"MMZ","AirportName":"Maimana","AreaCode":"701","CountryCode":"AF","CountryName":"Afghanistan","AirportCode":"MZR","AirportName":"Mazar-i-sharif","AreaCode":"701","CountryCode":"AF","CountryName":"Afghanistan","AirportCode":"IMZ","AirportName":"Nimroz","AreaCode":"701","CountryCode":"AF","CountryName":"Afghanistan","AirportCode":"TMR","AirportName":"Aguemar","AreaCode":"500","CountryCode":"DZ","CountryName":"Algeria","AirportCode":"BMW","AirportName":"Bordj Badji Mokhtar","AreaCode":"500","CountryCode":"DZ","CountryName":"Algeria","AirportCode":"IAM","AirportName":"In Amenas","AreaCode":"500","CountryCode":"DZ","CountryName":"Algeria","AirportCode":"MUW","AirportName":"Mascara-Ghriss","AreaCode":"500","CountryCode":"DZ","CountryName":"Algeria","AirportCode":"MZW","AirportName":"Mechria","AreaCode":"500","CountryCode":"DZ","CountryName":"Algeria","AirportCode":"MQV","AirportName":"Mostaganem","AreaCode":"500","CountryCode":"DZ","CountryName":"Algeria","AirportCode":"HME","AirportName":"Oued Irara Apt","AreaCode":"500","CountryCode":"DZ","CountryName":"Algeria","AirportCode":"TMX","AirportName":"Timimoun","AreaCode":"500","CountryCode":"DZ","CountryName":"Algeria","AirportCode":"TLM","AirportName":"Zenata","AreaCode":"500","CountryCode":"DZ","CountryName":"Algeria"]
我还将提供我的服务代码
using System;
using System.Collections.Generic;
using System.Data;
using System.Data.SqlClient;
using System.ServiceModel.Activation;
namespace AutosuggestAPI.svc
// NOTE: You can use the "Rename" command on the "Refactor" menu to change the class name "Service1" in code, svc and config file together.
[AspNetCompatibilityRequirements(RequirementsMode = AspNetCompatibilityRequirementsMode.Allowed)]
public class Suggest : IService1
public string GetDateTime()
return DateTime.Now.ToString();
private static List<Suggestions> GetDistinct(List<Suggestions> suggestions)
var length = suggestions.Count;
var Arr = new Suggestions[length];
suggestions.CopyTo(Arr);
var dist = new HashSet<string>();
foreach (var suggestion in Arr)
if (!dist.Contains(suggestion.AirportCode.ToString()))
dist.Add(suggestion.AirportCode.ToString());
else
suggestions.Remove(suggestion);
return suggestions;
public List<Suggestions> GetAirportDataXml(string location)
var suggestions = new List<Suggestions>();
var val = string.Empty;
for (int i = 0; i < 2; i++)
val = i == 0 ? "AirPortName" : "AirPortCode";
SqlConnection conn = null;
try
// create and open a connection object
conn = new SqlConnection("Server=(local);DataBase=DBAirPortCodes;Integrated Security=SSPI");
conn.Open();
// 1. create a command object identifying
// the stored procedure
var cmd = new SqlCommand("sp_CheckCondition", conn) CommandType = CommandType.StoredProcedure ;
// 2. set the command object so it knows
// to execute a stored procedure
// 3. add parameter to command, which
// will be passed to the stored procedure
cmd.Parameters.Add(new SqlParameter("@lookup", val));
cmd.Parameters.Add(new SqlParameter("@searchfor", location));
var reader = cmd.ExecuteReader();
while (reader.Read())
var suggestion = new Suggestions()
_airportCode = Convert.ToString(reader["AirPortCode"]).Trim(),
_airportName = Convert.ToString(reader["AirPortName"]).Trim(),
_areaCode = Convert.ToString(reader["AreaCode"]).Trim(),
_countryCode = Convert.ToString(reader["CountryCode"]).Trim(),
_countryName = Convert.ToString(reader["CountryName"]).Trim()
;
suggestions.Add(suggestion);
finally
if (conn != null)
conn.Close();
var distinctList = GetDistinct(suggestions);
return distinctList;
List<Suggestions> GetAirportDataJson(string location)
List<Suggestions> suggestions = GetAirportDataXml(location);
return suggestions;
public List<Suggestions> GetAirportDataJsonp(string location)
return GetAirportDataXml(location);
public List<Suggestions> GetAllSuggestions()
var suggestions = new List<Suggestions>();
var val = string.Empty;
for (int i = 0; i < 2; i++)
val = i == 0 ? "AirPortName" : "AirPortCode";
SqlConnection conn = null;
try
// create and open a connection object
conn = new SqlConnection("Server=(local);DataBase=DBAirPortCodes;Integrated Security=SSPI");
conn.Open();
var cmd = new SqlCommand("sp_GetAllAirports", conn) CommandType = CommandType.StoredProcedure ;
var reader = cmd.ExecuteReader();
while (reader.Read())
var suggestion = new Suggestions()
_airportCode = Convert.ToString(reader["AirPortCode"]).Trim(),
_airportName = Convert.ToString(reader["AirPortName"]).Trim(),
_areaCode = Convert.ToString(reader["AreaCode"]).Trim(),
_countryCode = Convert.ToString(reader["CountryCode"]).Trim(),
_countryName = Convert.ToString(reader["CountryName"]).Trim()
;
suggestions.Add(suggestion);
finally
if (conn != null)
conn.Close();
var distinctList = GetDistinct(suggestions);
return distinctList;
问题是调用成功,我在浏览器中获取了数据,但我无法在 Jquery 或 Javascript 中捕获它。 有人可以帮忙吗?
【问题讨论】:
尝试将 console.log(e) 添加到你的成功函数中,看看你是否真的得到了什么,或者只是一个错误。我认为您在预期 jsonp 时返回 json。 我希望它是 json 但服务不在同一个域中。因此使用 jsonp.Also 成功函数根本没有被命中。添加 console.log(e) 后没有任何记录 很有可能问题出在返回的数据上。并且要使用跨域 jsonp,您使用的 REST 服务必须支持它,并返回有效的 jsonp,而不是 json,因为那将不起作用。您可以在服务器端执行此操作,因为这非常简单,或者您可以使用 Yahoo 的 YQL 之类的服务将数据转换为 jsonp。然而,最好的选择可能是让 REST 服务支持 jsonp,如果您可以访问它。 @adeneo:提供了服务代码,您现在能告诉我具体需要如何更改我的服务吗? 【参考方案1】:您将错误的字符串传递给 jsonCallback。
应该是
function autosuggest(location)
var uri= 'http://localhost:2043/Suggest.svc/GetAirportsjson?location='+location;
$.ajax(
url:uri,
dataType: 'jsonp',
jsonpCallback: 'jsonpCallback',
success: function(e)
alert("success");
);
;
为什么还要用默认值覆盖默认回调参数名称?
已编辑:似乎您并不真正了解 jquery 如何处理 jsonp 内容。
jquery 创建一个函数来处理 jsonp 请求的返回,该请求将 json 作为包含在此函数调用中的纯文本返回。你可以不提供任何功能,这对于 jquery 和更严格的来说更可取
看看following example
你需要提供的参数只有jsonp的数据类型
var r = $.ajax(
url : uri
, dataType:'jsonp'
, success: function (e)
viewModel.tweets(e.results);
);
编辑 2:您的服务应处理“回调”参数,如果提供,则将响应 json 包装在提供的函数调用中
即
请求:http://......../GetAirportsjson?location=....&callback=mycallback
回复:mycallback( .... you real json response goes here .... )
在你有这个之前你没有做正确的 jsonp 响应
【讨论】:
我需要覆盖默认回调,以便我可以访问返回的数据并根据我的应用程序进行更改 试过但没用。仍然无法获取数据。并注意到从未调用过 jsonpCallback。 您在 e 中的成功处理程序中拥有什么 您可以通过使用变量“e”以成功的方式访问jsondata。能不能给个jsonpCallback方法分析一下?? @poineer - 使用 jsonp 和 twitter api 调用查看更新的答案以及链接到实时示例以上是关于使用 Jsonp 进行 $.ajax 调用后无法在 Jquery 中检索数据的主要内容,如果未能解决你的问题,请参考以下文章
使用 JSONP 或 CORS 的跨域 JavaScript 调用