.NET 8 Web应用Ajax获取超长字符串失败,求解决方案
.NET 8 Web应用中Ajax获取大体积Base64图表的问题与解决
问题背景
在.NET 8 Web应用中,通过Ajax从控制器获取约65000字节的Base64格式图表时,一旦返回字符串超过4095字节就会请求失败。旧版.NET可通过web.config配置maxJsonLength解决,但.NET 8无此配置文件,尝试在Program.cs中配置Kestrel的MaxResponseBufferSize也无效。
现有代码
控制器代码
ReturnResult ret = new() { Error = "" }; using var ms = new MemoryStream(); ChrtGraph.SaveImage(ms, ChartImageFormat.Png); ret.Img = Convert.ToBase64String(ms.ToArray()); return System.Text.Json.JsonSerializer.Serialize(ret);
ReturnResult类定义
public class ReturnResult { public string? Img { get; set; } public required string Error { get; set; } = ""; }
Ajax调用代码
var form = $('#__AjaxAntiForgeryForm'), token = $('input[name="__RequestVerificationToken"]', form).val(), GetTextureChart = {}; GetTextureChart.Width = 943; GetTextureChart.Height = 466; $.ajax({ url: "Chart/GetTextureChart", type: "POST", data: JSON.stringify(JSON.stringify(GetTextureChart)), contentType: "application/json; charset=utf-8", dataType: "json", headers: { RequestVerificationToken: $(token).val() }, success: function (response) { var ret = JSON.parse(JSON.stringify(response)); if (ret.Error == "") $("#chrtgraph").attr('src', 'data:image/png;base64,' + ret.Img); else $("#lblerr").text("Error " + ret.Error); }, failure: function (response) { $("#lblerr").text("fail " + response.responseText); }, error: function (response) { $("#lblerr").text("Error " + response.responseText); } });
旧版本web.config配置(.NET 8不适用)
<system.web.extensions> <scripting> <webServices> <jsonSerialization maxJsonLength="50000000" /> </webServices> </scripting> </system.web.extensions>
无效的Kestrel配置(Program.cs)
builder.WebHost.ConfigureKestrel(serverOptions => { serverOptions.Limits.MaxResponseBufferSize = 100000; });
临时可行方案
1. Razor页面配置
在目标Razor页面顶部添加路由支持:
@page "{handler?}"
2. PageModel代码(somepage.cshtml.cs)
通过Razor页面的Handler方法返回JsonResult:
public JsonResult OnGetGetChart() { ReturnResult ret = new() { Img = "", Error = "" }; // 图表生成逻辑 using var ms = new MemoryStream(); ChrtGraph.SaveImage(ms, ChartImageFormat.Png); ret.Img = Convert.ToBase64String(ms.ToArray()); return new JsonResult(ret); }
3. 前端调用代码
使用$.get发起请求:
$.get("/somepage/GetChart").done(function (img) { var ret = JSON.parse(JSON.stringify(img)); if (ret.error == "") $("#chrtgraph").attr('src', 'data:image/png;base64,' + ret.img); else $("#lblerr").text("Error " + ret.Error); });
临时方案的疑问
- 为什么必须返回
JsonResult而非直接序列化字符串? - 为什么只有
$.get可行,原Ajax POST调用仍失效? $.get返回的JSON键自动转为小写的原因是什么?- 后续给该页面添加授权,是否会影响此方案的可用性?
内容的提问来源于stack exchange,提问作者Joe Oliphant
相关产品推荐
相关产品推荐

