.NET API两个相同控制器,仅WeatherForecast可被React正常调用,另一个返回HTML
问题描述
我有两个逻辑完全一致的控制器:WeatherForecastController(来自.NET API/React模板项目,已精简)和ExampleReactController,代码如下:
控制器代码
using Microsoft.AspNetCore.Mvc; namespace DotNetReact_BackEnd.Controllers { [ApiController] [Route("[controller]")] public class WeatherForecastController : ControllerBase { private static List<string> Data = new List<string>() { "Testing", "123" }; [HttpGet] public IEnumerable<string> Get() { return Data; } } } using Microsoft.AspNetCore.Mvc; namespace DotNetReact_BackEnd.Controllers { [ApiController] [Route("[controller]")] public class ExampleReactController : ControllerBase { private static List<string> Data = new List<string>() { "Testing", "123" }; [HttpGet] public IEnumerable<string> Get() { return Data; } } }
React代理配置
const { createProxyMiddleware } = require('http-proxy-middleware'); const context = [ "/weatherforecast", "/examplereact" ]; module.exports = function (app) { const appProxy = createProxyMiddleware(context, { target: 'https://localhost:7048', secure: false }); app.use(appProxy); };
异常现象
两个控制器在Swagger和Postman中均能正常返回JSON数据,但React前端调用时出现差异:
- 调用
WeatherForecastController的代码可正常返回包含2个元素的数组:
async populateStrings() { const response = await fetch('weatherforecast'); console.log(response); const data = await response.json(); console.log(data); this.setState({ forecasts: data, loading: false }); }
- 调用
ExampleReactController的代码返回HTML页面,触发JSON解析错误:Uncaught (in promise) SyntaxError: Unexpected token '<', "<!DOCTYPE "... is not valid JSON"
async populateStrings() { const response = await fetch('examplereact'); console.log(response); const data = await response.json(); console.log(data); this.setState({ forecasts: data, loading: false }); }
解决方法
核心原因
问题出在路由大小写不匹配:
- .NET控制器通过
[Route("[controller]")]生成的路由是/ExampleReact(控制器类名去掉后缀后的首字母大写形式) - React请求的路径是全小写的
examplereact,而.NET默认路由是区分大小写的,找不到对应控制器时会返回React的默认HTML入口页面,导致JSON解析失败
修复方案
有两种可行的修复方式:
修改React请求路径,匹配.NET路由大小写
将fetch的路径改为首字母大写的形式:async populateStrings() { const response = await fetch('ExampleReact'); console.log(response); const data = await response.json(); console.log(data); this.setState({ forecasts: data, loading: false }); }配置.NET路由大小写不敏感
在项目的Program.cs中添加路由全局配置,强制URL小写:builder.Services.Configure<RouteOptions>(options => { options.LowercaseUrls = true; options.LowercaseQueryStrings = true; });配置完成后,
/examplereact就能正确匹配ExampleReactController的路由。
验证方式
可以直接在浏览器地址栏访问https://localhost:7048/examplereact和https://localhost:7048/ExampleReact,观察哪个能返回正确的JSON数据,快速确认是否为大小写问题。
内容的提问来源于stack exchange,提问作者Jameson Grieve
相关产品推荐
相关产品推荐

