Windows Forms中部分URL调用GetResponse触发Bad Request问题排查
问题排查与修复方案
嘿,我仔细看了你的代码和遇到的问题,发现几个关键问题,应该能解决你遇到的崩溃和异常情况:
1. URL格式完全错误
这绝对是导致请求崩溃的核心原因之一!你代码里的URL写的是https//:www.example.com/...,正确的HTTP/HTTPS URL格式应该是https://www.example.com/...——冒号应该在双斜杠的前面,而不是后面。这种无效的URL格式会直接让WebRequest.Create()方法抛出异常,更别说后续的请求了。
2. 重复发起HTTP请求,浪费资源还易出问题
你在同一个循环里同时用了WebClient.DownloadString(url)和HttpWebRequest.GetResponse(),这相当于对同一个URL发起了两次完全独立的HTTP请求。这不仅会浪费服务器带宽和本地资源,还可能触发目标服务器的限流机制,导致其中一个请求失败抛出异常。你只需要选择一种方式来检查URL状态即可。
3. 条件判断逻辑错误
你的异常判断条件有逻辑漏洞:
if ((httpRes.StatusCode != HttpStatusCode.OK || httpRes.StatusCode != HttpStatusCode.Found) && downloadString.Contains("404 -") || downloadString.Contains("Server Error"))
这里的!=OK || !=Found永远为true——因为一个HTTP状态码不可能同时是OK和Found,所以这个条件相当于永远成立,会导致你误触发通知。正确的写法应该是判断状态码既不是OK也不是Found:
if (!(httpRes.StatusCode == HttpStatusCode.OK || httpRes.StatusCode == HttpStatusCode.Found) && (downloadString.Contains("404 -") || downloadString.Contains("Server Error")))
或者用&&组合:
if ((httpRes.StatusCode != HttpStatusCode.OK && httpRes.StatusCode != HttpStatusCode.Found) && (downloadString.Contains("404 -") || downloadString.Contains("Server Error")))
4. 未正确释放资源,易导致连接耗尽
HttpWebResponse和WebClient都是实现了IDisposable接口的类型,你没有用using语句来自动释放资源,长期运行可能导致内存泄漏或者HTTP连接池耗尽,进而引发后续请求崩溃。
修正后的代码示例
public void CheckUrl() { List<string> urls = new List<string>() { "https://www.example.com/something1/buy", "https://www.example.com/something2/buy", "https://www.example.com/something3/buy", "https://www.example.com/something4/buy", }; foreach (var url in urls) { try { // 使用HttpWebRequest,并用using自动释放资源 using (HttpWebRequest httpReq = (HttpWebRequest)WebRequest.Create(url)) { httpReq.AllowAutoRedirect = false; httpReq.Timeout = 5000; // 添加超时时间,避免请求挂起 using (HttpWebResponse httpRes = (HttpWebResponse)httpReq.GetResponse()) { // 先判断状态码是否正常 bool isStatusNormal = httpRes.StatusCode == HttpStatusCode.OK || httpRes.StatusCode == HttpStatusCode.Found; if (!isStatusNormal) { // 状态码异常,发送通知 SendVerificationLinkEmail(httpRes.StatusCode.ToString(), url); foreach (var number in Numbers) { SendSms(url, number); } continue; } // 如果需要检查响应内容,再读取(可选) using (StreamReader reader = new StreamReader(httpRes.GetResponseStream())) { string downloadString = reader.ReadToEnd(); if (downloadString.Contains("404 -") || downloadString.Contains("Server Error")) { SendVerificationLinkEmail("Content Error", url); foreach (var number in Numbers) { SendSms(url, number); } } } } } } catch (WebException we) { // 捕获WebException,获取更详细的错误信息 string errorMsg = we.Message; if (we.Response is HttpWebResponse errorRes) { errorMsg += $" | Status Code: {errorRes.StatusCode}"; } // 发送异常通知给管理员 SendExeptionUrl($"{url} - Error: {errorMsg}"); foreach (var number in Numbers) { SendSms($"{url} 异常: {errorMsg}", number); } } catch (Exception e) { // 捕获其他未知异常 SendExeptionUrl($"{url} - Unexpected Error: {e.Message}"); foreach (var number in Numbers) { SendSms($"{url} 未知异常: {e.Message}", number); } } } Application.Exit(); }
额外排查建议
- 优先捕获
WebException而不是泛泛的Exception,这样你能获取到目标服务器返回的具体状态码和错误信息,更容易定位问题; - 如果部分URL还是有问题,可以手动在浏览器里访问这些URL,看看是否有证书错误、跳转异常或者需要特殊请求头的情况;
- 给请求添加超时时间,避免因网络问题导致请求长时间挂起占用资源。
内容的提问来源于stack exchange,提问作者leiit
相关产品推荐
相关产品推荐

