我正在将 JSON 数据发布到 ASP.NET MVC2 服务器。我正在发布大型 JSON 字符串(其中包含从本地文件系统读取的 Base64 编码文件流)。 jQuery ajax 调用在文件大小约为 2.5Mb 时工作正常。一旦超过这个大小,ajax 调用就会失败(永远不会到达 Controller )。我无法准确检测出错误是什么 - 它似乎没有填充错误变量。
ajax调用如下:
$.ajax({
type: "POST",
dataType: 'json',
timeout: 10000,
url: "/Molecule/SaveMolecule",
data: { jsonpost: postdata, moleculetype: _moleculeType, moleculefilestream: _moleculefilestream, changedproducts: stringifiedChangedProducts }, // NOTE the moleculeType being added here
success: function (data) {
if (data.rc == "success") {
$.log('ServerSuccess:' + data.message);
molecule_updateLocalInstance();
_bMoleculeIsDirty = false;
if (bReturnToMoleculeList != null && bReturnToMoleculeList == true) {
navigator_Go('/Molecule/Index/' + _moleculeType);
}
else {
_saveMoleculeButtonFader = setTimeout(function () {
$('#profilesave-container').delay(500).html('<img src="/content/images/tick.png" width="32px" height="32px" /><label>' + _moleculeSingularTerm + ' was saved</label>').fadeIn(500);
_saveMoleculeButtonFader = setTimeout(function () { $('#profilesave-container').fadeOut(1000); }, 2000);
}, 500);
}
} else {
$.log('ServerUnhappy:' + data.message);
RemoveMoleculeExitDialog();
}
}
, error: function (jqXHR, textStatus, errorThrown) {
alert('Save failed, check console for error message:' +textStatus+' '+ errorThrown);
MarkMoleculeAsDirty();
$.log('Molecule Save Error:' + helper_objectToString(textStatus+' '+errorThrown));
}
});
其中 _moleculefilestream 是大型 Base64 编码流。
我的 web.config 包括以下内容:
<system.web.extensions>
<scripting>
<webServices>
<jsonSerialization maxJsonLength="50000000">
</jsonSerialization>
</webServices>
</scripting>
</system.web.extensions>
有人有什么好主意吗?
最佳答案
更新
a spnet:MaxJsonDeserializerMembers
元素必须添加到 <appSettings>
web.config 文件的部分,设置为 2147483647,这相当于 Int32
的最大值数据类型。
<configuration>
<appSettings>
<add key="aspnet:MaxJsonDeserializerMembers" value="2147483647" />
</appSettings>
</configuration>
在官方这个页面documentation ,您将能够找到有关元素及其用途的所有信息。
注意:在官方文档的部分中,建议不要调整为最大值,因为这存在安全风险。理想情况下,您应该检查要反序列化的项目数量,并尝试根据您使用的最大 json 大小进行估计。
@Flxtr 的原始帖子:Here
旧
如果您想上传文件,为什么不尝试使用 FormData
例如:
function getDataForm() {
var data = new FormData();
var files = fileUploader.get(0).files;
if (files.length > 0) {
data.append("File", files[0]);
}
data.append("ImagePath", "");
data.append("Id", ImageId);
data.append("Name", txtName.val().trim());
data.append("Description", txtDescription.val().trim());
return data;
}
function save(data) {
$.ajax({
type: "POST",
url: "/Files/SaveImage",
contentType: false,
processData: false,
data: data,
success: function (response) {
if (response.success) {
$.showMessage(messages.NAME, messages.SUCCESS, "success");
closeForm();
Files.ImageList.gridImages.ajax.reload();
}
else {
$.showMessage(messages.NAME, response.message, "error");
};
btnSave.button('reset');
},
error: function (request, status, exception) {
$.showMessage(messages.NAME, exception, "error");
btnSave.button('reset');
}
});
};
然后,在服务器端,更改 Web 配置中的请求长度:
<httpRuntime targetFramework="4.6.1" maxRequestLength="65536"/>
例如:
<system.web>
<compilation debug="true" targetFramework="4.6.1" />
<httpRuntime targetFramework="4.6.1" maxRequestLength="65536"/>
<customErrors mode="RemoteOnly">
<error statusCode="401" redirect="/Error/401" />
...
<error statusCode="411" redirect="/Error/411" />
</customErrors>
</system.web>
另外,更改参数 processData
至false
在ajax请求中:
$.ajax({
url: "/Security/SavePermissions",
type: "POST",
processData: false,
contentType: "application/json; charset=utf-8",
data: JSON.stringify(pStrPermissions),
success: function (response) {
if (response.success) {
panel.showAlert("Permisos", "Se han actualizado correctamente los permisos.", "success");
resetForm();
}
else {
$.showMessage("Permisos", response.message, "error");
};
},
error: function (request, status, exception) {
$.showMessage("Permisos", exception, "error");
}
});
这些只是建议。唯一真正对我有用的是序列化列表并在服务器上反序列化它。
例如,在客户端:
function savePermissions(pLstObjPermissions) {
$.ajax({
url: "/Security/SavePermissions",
type: "POST",
dataType: "json",
contentType: "application/json; charset=utf-8",
data: JSON.stringify({ pStrPermissions: JSON.stringify(pLstObjPermissions)}) ,
success: function (response) {
if (response.success) {
panel.showAlert("Permisos", "Se han actualizado correctamente los permisos.", "success");
resetForm();
}
else {
$.showMessage("Permisos", response.message, "error");
};
},
error: function (request, status, exception) {
$.showMessage("Permisos", exception, "error");
}
});
};
在服务器端:
public ActionResult SavePermissions(string pStrPermissions)
{
var lLstObjResult = new Dictionary<string, object>();
try
{
SecurityFactory.GetPermissionService().UpdateList(JsonConvert.DeserializeObject<IList<Permission>>(pStrPemissions));
lLstObjResult.Add(MESSAGE, "Registro guardado exitosamente");
lLstObjResult.Add(SUCCESS, true);
}
catch (Exception e)
{
lLstObjResult.Add(MESSAGE, e.Message);
lLstObjResult.Add(SUCCESS, false);
}
return Json(lLstObjResult, JsonRequestBehavior.AllowGet);
}
我知道这不是最好的方法,但它会起作用,直到出现更好的方法。
如果您有更好的方法来解决此问题,请分享。
关于jQuery .ajax post 因大型 JSON 对象而失败,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/7931649/