调试器在异步 HttpClient.GetAsync() 调用 visual studio 后停止
Debugger stops after async HttpClient.GetAsync() call in visual studio
我正在尝试测试以下http请求方法
public async Task<HttpContent> Get(string url)
{
using (HttpClient client = new HttpClient())
// breakpoint
using (HttpResponseMessage response = await client.GetAsync(url))
// can't reach anything below this point
using (HttpContent content = response.Content)
{
return content;
}
}
但是,调试器似乎跳过了第二条注释下方的代码。我正在使用 Visual studio 2015 RC,有什么想法吗?我也尝试检查任务 window 但什么也没看到
编辑:找到解决方案
using System;
using System.Net.Http;
using System.Threading.Tasks;
namespace ConsoleTests
{
class Program
{
static void Main(string[] args)
{
Program program = new Program();
var content = program.Get(@"http://www.google.com");
Console.WriteLine("Program finished");
}
public async Task<HttpContent> Get(string url)
{
using (HttpClient client = new HttpClient())
using (HttpResponseMessage response = await client.GetAsync(url).ConfigureAwait(false))
using (HttpContent content = response.Content)
{
return content;
}
}
}
}
因为这是一个 C# 控制台应用程序,所以我猜它在主线程结束后结束,因为在添加 Console.ReadLine() 并稍等片刻后,请求完成了 return。我猜 C# 会等到我的任务执行,而不是在它之前结束,但我想我错了。如果有人能详细说明为什么会发生这种情况,那就太好了。
当Main
退出时,程序退出。取消任何未完成的异步操作并丢弃其结果。
因此,您需要阻止 Main
退出,方法是阻止异步操作或其他一些方法(例如,调用 Console.ReadKey
以阻止直到用户按下某个键):
static void Main(string[] args)
{
Program program = new Program();
var content = program.Get(@"http://www.google.com").Wait();
Console.WriteLine("Program finished");
}
一种常见的方法是定义一个也执行异常处理的 MainAsync
:
static void Main(string[] args)
{
MainAsync().Wait();
}
static async Task MainAsync()
{
try
{
Program program = new Program();
var content = await program.Get(@"http://www.google.com");
Console.WriteLine("Program finished");
}
catch (Exception ex)
{
Console.WriteLine(ex);
}
}
请注意,阻塞异步代码通常被认为是一个坏主意;在极少数情况下应该这样做,控制台应用程序的 Main
方法恰好是其中之一。
我正在尝试测试以下http请求方法
public async Task<HttpContent> Get(string url)
{
using (HttpClient client = new HttpClient())
// breakpoint
using (HttpResponseMessage response = await client.GetAsync(url))
// can't reach anything below this point
using (HttpContent content = response.Content)
{
return content;
}
}
但是,调试器似乎跳过了第二条注释下方的代码。我正在使用 Visual studio 2015 RC,有什么想法吗?我也尝试检查任务 window 但什么也没看到
编辑:找到解决方案
using System;
using System.Net.Http;
using System.Threading.Tasks;
namespace ConsoleTests
{
class Program
{
static void Main(string[] args)
{
Program program = new Program();
var content = program.Get(@"http://www.google.com");
Console.WriteLine("Program finished");
}
public async Task<HttpContent> Get(string url)
{
using (HttpClient client = new HttpClient())
using (HttpResponseMessage response = await client.GetAsync(url).ConfigureAwait(false))
using (HttpContent content = response.Content)
{
return content;
}
}
}
}
因为这是一个 C# 控制台应用程序,所以我猜它在主线程结束后结束,因为在添加 Console.ReadLine() 并稍等片刻后,请求完成了 return。我猜 C# 会等到我的任务执行,而不是在它之前结束,但我想我错了。如果有人能详细说明为什么会发生这种情况,那就太好了。
当Main
退出时,程序退出。取消任何未完成的异步操作并丢弃其结果。
因此,您需要阻止 Main
退出,方法是阻止异步操作或其他一些方法(例如,调用 Console.ReadKey
以阻止直到用户按下某个键):
static void Main(string[] args)
{
Program program = new Program();
var content = program.Get(@"http://www.google.com").Wait();
Console.WriteLine("Program finished");
}
一种常见的方法是定义一个也执行异常处理的 MainAsync
:
static void Main(string[] args)
{
MainAsync().Wait();
}
static async Task MainAsync()
{
try
{
Program program = new Program();
var content = await program.Get(@"http://www.google.com");
Console.WriteLine("Program finished");
}
catch (Exception ex)
{
Console.WriteLine(ex);
}
}
请注意,阻塞异步代码通常被认为是一个坏主意;在极少数情况下应该这样做,控制台应用程序的 Main
方法恰好是其中之一。