我能够从ajax脚本将表单数据传递给ASP.Net Web服务并接收响应的JSON对象,效果很好。当我在JQ网格中使用相同的参数进行相同的调用时,我会收到“无效的Web服务调用”或“无效的JSON原语”作为响应。
我认为这与以下帖子相当接近,我已经应用了这些建议(以及许多其他帖子中的建议),但没有成功。 JQGrid - Cannot call ASP.NET WebMethod but can with Ajax
以下Ajax代码成功,它将表单参数传递给Web服务并以JSON格式检索结果。
Ajax Javascript代码: 此代码可以这是问题所在的JQ Grid(下面是)
<script language="JavaScript">
function populateResults() {
var arForm = $("#searchForm").serializeArray();
$.ajax({
type: "POST",
url: "./WebService/Service.asmx/doSearch",
data: JSON.stringify({ formVars: arForm }),
contentType: "application/json",
dataFilter: function(data) {
var msg = eval('(' + data + ')');
if (msg.hasOwnProperty('d'))
return msg.d;
else
return msg;
},
success: function(msg) {
// This will now output the same thing
// across any current version of .NET.
//console.log(msg.foo);
}
});
};
</script>
网络服务:
[WebMethod]
[ScriptMethod(ResponseFormat = ResponseFormat.Json)]
public string doSearch(NameValue[] formVars)
{...
问题: 以下是失败的JQ Grid代码:
<script type="text/javascript">
function populateResults() {
var arForm = $("#searchForm").serializeArray();
var searchParams = JSON.stringify({ formVars: arForm });
var grid = $("#tblResults");
grid.jqGrid({
url: "./WebService/Service.asmx/doSearch",
ajaxGridOptions: { contentType: 'application/json; charset=utf-8' },
data: searchParams,
dataType: 'json',
dataFilter: function(data) {
var msg = eval('(' + data + ')');
alert(msg.d);
if (msg.hasOwnProperty('d'))
return msg.d;
else
return msg;
},
mtype: 'POST',
colNames:['Exam Date','Type','Name','UR Number','Pathology Type','Result Date','Modality', 'Results'],
colModel:[
{name:'resExamDate',index:'resExamDate', editable:false, width:120},
{name:'resType',index:'resType', editable:false, width:60},
{name:'name',index:'name', editable:false, width:120},
{name:'urnumber',index:'urnumber', width:65, sorttype:'int'},
{name:'resPathologyType',index:'resPathologyType', editable:false, width:120},
{name:'resResultDate',index:'resResultDate', editable:false, width:120},
{name:'resModality',index:'resModality', editable:false, width:170, cellattr: function (rowId, tv, rawObject, cm, rdata) { return 'style="white-space: normal;"'}},
{name:'results',index:'results', editable:false, width:240, cellattr: function (rowId, tv, rawObject, cm, rdata) { return 'style="white-space: normal;"'}}
],
rowNum:10,
rowList:[5,10,20],
pager: '#pager',
sortname: 'surname',
viewrecords: true,
sortorder: "desc",
height: "100%",
processData: false, //jquery will stringify again apparently: https://stackoverflow.com/questions/6471759/invalid-web-service-call-missing-value-for-parameter
serializeGridData: function (postData) { return JSON.stringify(postData); },
jsonReader: {
total: "total",
page: "page",
records: "records",
root: "rows",
id: "id",
cell: "cell",
repeatitems: false
}
});
}
</script>
在Firebug中我收到:
Post
{"_search":false,"nd":1338180778103,"rows":10,"page":1,"sidx":"surname","sord":"desc"}
Response
{"Message":"Invalid web service call, missing value for parameter: \u0027formVars\u0027.","StackTrace":" at System.Web.Script.Services.WebServiceMethodData.CallMethod(Object target, IDictionary`2 parameters)\r\n
或者,如果我注释掉“serializeGridData:”行(我想我将它序列化两次或者其他什么,所以我试着将它评论出来),我得到:
Post:
_search=false&nd=1338180203206&rows=10&page=1&sidx=surname&sord=desc
Response:
{"Message":"Invalid JSON primitive: _search.","StackTrace":" at System.Web.Script.Serialization.JavaScriptObjectDeserializer.DeserializePrimitiveObject()\r\n ......
关于它为什么不起作用的任何可靠的想法?我花了好几天试图让这个以这种方式工作。虽然我可以通过执行Ajax调用并将数据存储在变量中并将其设置为JQ Grid来使其工作,但我需要来自JQ GRid的直接Web服务调用来处理过滤和其他事情......
提前感谢:)
编辑: - 使用JQ Grid v4.3.2 - 发送到Web服务的JSON数据已使用http://jsonlint.com/验证(这是上面javascript代码中的变量“searchParams”)
答案 0 :(得分:2)
您在呼叫的{}
(请参阅/*here*/
)内使用的内容
grid.jqGrid({/*here*/});
是 jqGrid参数或jqGrid options。在这里使用dataFilter
是错误的,因为jqGrid将忽略该选项。以同样的方式,jqGrid不知道dataType
选项,它忽略dataType: 'json'
。默认值datatype
(小心字母大小写)为'xml'
。由于来自服务器的JSON响应是错误的XML文件,因此您将收到错误。
以同样的方式,jqGrid的data
参数将以另一种方式使用。您应该使用postData
参数。重要的是要了解您应该使用grid.jqGrid({/*here*/});
一次之类的代码创建jqGrid。因此,如果您希望分页,排序或过滤数据,"#searchForm"
形式的当前值将发送到服务器,您应该将formVars
定义为函数。有关详细信息,请参阅the answer。如果您使用mtype: 'POST'
,则可能很容易在formVars
回调中添加serializeGridData
属性。
因此,您应该将当前代码重写为以下内容:
$(function () {
var grid = $("#tblResults");
grid.jqGrid({
url: "./WebService/Service.asmx/doSearch",
ajaxGridOptions: { contentType: 'application/json; charset=utf-8' },
serializeGridData: function (postData) {
// extend the parameter which will be send to the server
postData.formVars = $("#searchForm").serializeArray();
// serialize the parameters as JSON string
return JSON.stringify(postData);
},
datatype: 'json',
mtype: 'POST',
colNames:['Exam Date','Type','Name','UR Number','Pathology Type','Result Date','Modality', 'Results'],
colModel:[
{name:'resExamDate',index:'resExamDate', width:120},
{name:'resType',index:'resType', width:60},
{name:'name',index:'name', width:120},
{name:'urnumber',index:'urnumber', width:65},
{name:'resPathologyType',index:'resPathologyType', width:120},
{name:'resResultDate',index:'resResultDate', width:120},
{name:'resModality',index:'resModality', width:170,
cellattr: function () {
return ' style="white-space: normal;"'
}},
{name:'results',index:'results', width:240,
cellattr: function () {
return ' style="white-space: normal;"'
}}
],
rowNum: 10,
rowList: [5, 10, 20],
pager: '#pager',
sortname: 'surname',
viewrecords: true,
sortorder: "desc",
height: "100%",
jsonReader: {
root: function (obj) { return obj.d; },
page: function () { return 1; },
total: function () { return 1; },
records: function (obj) { return obj.d.length; }
}
});
});
此外,您的服务器部分似乎未实现数据分页。如果它忽略了所有标准jqGrid参数(rows
,page
,sidx
,sord
),您应该将rowNum
的值增加到{{1}例如,删除rowNum: 10000
和其他寻呼机信息(请参阅the documentation):rowList
。另外你可以使用
pgbuttons: false, pginput: false
如果jqGrid只发送serializeGridData: function () {
return JSON.stringify({formVars: $("#searchForm").serializeArray()});
}
到服务器。
答案 1 :(得分:0)
您需要包含Web服务的预期参数名称,如
var grid = $("#tblResults");
grid.jqGrid({
url: "./WebService/Service.asmx/doSearch",
ajaxGridOptions: { contentType: 'application/json; charset=utf-8' },
data:{u0027formVars: searchParams},
以前的代码是成功的,因为包含了输入参数名称
答案 2 :(得分:0)
你需要传递这样的数据:
function populateResults() {
var arForm = $("#searchForm").serializeArray();
var formvars = JSON.stringify(arForm);
$.ajax({
type: "POST",
url: "./WebService/Service.asmx/doSearch",
data: "{'formVars':'" + formvars + "'}",
contentType: "application/json",
dataFilter: function(data) {
var msg = eval('(' + data + ')');
if (msg.hasOwnProperty('d'))
return msg.d;
else
return msg;
},
success: function(msg) {
// This will now output the same thing
// across any current version of .NET.
//console.log(msg.foo);
}
});
};