Visual Studio 2017+MySQL开发遇HttpRequestException:请求发送失败排查
排查和解决你的HttpRequestException问题
看起来你遇到了API调用失败的问题,结合你的代码和环境重建的背景,我整理了几个关键排查点:
1. 确认本地Web API服务是否正常运行
你的RestClient里调用的是http://localhost:57645/api/MainUserData/,首先要确保:
- 这个Web API项目已经启动,并且确实监听在57645端口(可以直接用浏览器访问该URL,看是否能正常返回JSON数据)
- 如果是在移动端(比如Xamarin)运行前端代码,
localhost指向的是设备/模拟器自身的本地服务,而非你的电脑!这时候需要把URL换成电脑的局域网IP地址(比如http://192.168.1.100:57645/api/MainUserData/),同时确保电脑和设备在同一个局域网内,防火墙没有拦截该端口。
2. 检查Web API的CORS配置
如果你的前端是跨域调用(比如Xamarin应用调用本地Web API),默认情况下API会拒绝跨域请求,这会直接触发HttpRequestException。你需要在Web API项目里开启CORS:
- 安装
Microsoft.AspNet.WebApi.CorsNuGet包 - 在
WebApiConfig.cs里添加配置:
using System.Web.Http; using System.Web.Http.Cors; public static class WebApiConfig { public static void Register(HttpConfiguration config) { // 开发环境允许所有来源的跨域请求,生产环境需限制指定来源 var cors = new EnableCorsAttribute("*", "*", "*"); config.EnableCors(cors); // 其他路由配置 config.MapHttpAttributeRoutes(); config.Routes.MapHttpRoute( name: "DefaultApi", routeTemplate: "api/{controller}/{id}", defaults: new { id = RouteParameter.Optional } ); } }
3. 修复Controller里的数据库查询逻辑(潜在异常源)
你的MainUserDataController存在几个问题,可能导致API返回500错误,进而让前端请求失败:
- 参数未赋值:你实例化了
MainPhoneNumber MNP = new MainPhoneNumber();,但没有给MNP.PhoneNumber赋值,导致@id参数为空字符串,执行SELECT * FROM test.maintable where Telephone = ''大概率返回空列表,若后续操作出错还会抛出未捕获异常。 - 未处理全流程异常:你仅捕获了
conn.Open()的异常,但cmd.ExecuteReader()和数据读取过程中如果出错(比如表不存在、字段名错误),会直接抛出异常,导致API返回500内部错误。建议把整个数据库操作包裹在try-catch块中:
[HttpGet] public List<string> Get() { string sqlstring = "server=localhost; port=3306 ; user id =root;Password=;Database=test;"; List<string> GetBizList = new List<string>(); using (MySqlConnection conn = new MySqlConnection(sqlstring)) { try { conn.Open(); // 注意:当前逻辑缺少查询手机号的来源,需根据业务调整(比如从请求参数获取) string Query = "SELECT Telephone FROM test.maintable where Telephone = @id "; using (MySqlCommand cmd = new MySqlCommand(Query, conn)) { // 示例:替换为实际要查询的手机号,或改成从请求参数接收 cmd.Parameters.AddWithValue("@id", "目标手机号"); using (MySqlDataReader MSQLRD = cmd.ExecuteReader()) { while (MSQLRD.Read()) { string BV = MSQLRD["Telephone"].ToString(); GetBizList.Add(BV); } } } } catch (MySqlException ex) { // 记录日志或返回友好错误信息 throw new HttpResponseException(Request.CreateErrorResponse(HttpStatusCode.InternalServerError, ex.Message)); } } return GetBizList; }
另外,新安装的MySQL默认root账号通常设置了密码,你需要确认连接字符串里的Password=;是否正确,否则conn.Open()会抛出异常,导致API返回错误。
4. 捕获更详细的异常信息
你可以在RestClient的GetAsync方法中添加异常捕获,打印内部异常细节,方便精准排查:
public async Task<List<T>> GetAsync() { try { var httpClient = new HttpClient(); var json = await httpClient.GetStringAsync(WebServiceUrl); var taskModels = JsonConvert.DeserializeObject<List<T>>(json); return taskModels; } catch (HttpRequestException ex) { // 打印内部异常,定位具体问题(连接失败/超时/证书问题等) Console.WriteLine($"请求错误: {ex.Message}, 内部异常: {ex.InnerException?.Message}"); throw; } }
优先从API服务运行状态和跨域配置入手排查,这是触发该异常最常见的原因。
内容的提问来源于stack exchange,提问作者LBG




