相关疑难解决方法(0)

抛出特定异常时,SmtpClient.SendMailAsync会导致死锁

我正在尝试基于VS2013项目模板中的示例AccountController为ASP.NET MVC5网站设置电子邮件确认.我已经实现了IIdentityMessageService使用SmtpClient,试图尽可能简单:

public class EmailService : IIdentityMessageService
{
    public async Task SendAsync(IdentityMessage message)
    {
        using(var client = new SmtpClient())
        {
            var mailMessage = new MailMessage("some.guy@company.com", message.Destination, message.Subject, message.Body);
            await client.SendMailAsync(mailMessage);
        }
    }
}
Run Code Online (Sandbox Code Playgroud)

调用它的控制器代码直接来自模板(由于我想排除其他可能的原因,因此将其解压缩为单独的操作):

public async Task<ActionResult> TestAsyncEmail()
{
    Guid userId = User.Identity.GetUserId();

    string code = await UserManager.GenerateEmailConfirmationTokenAsync(userId);
    var callbackUrl = Url.Action("ConfirmEmail", "Account", new { userId = userId, code = code }, protocol: Request.Url.Scheme);
    await UserManager.SendEmailAsync(userId, "Confirm your account", "Please confirm your account by clicking <a …
Run Code Online (Sandbox Code Playgroud)

c# asp.net-mvc smtpclient async-await asp.net-identity

16
推荐指数
1
解决办法
5855
查看次数

库中的Task.Yield()需要ConfigureWait(false)

建议使用一个ConfigureAwait(false)当你可以随时,特别是在图书馆,因为它可以帮助避免死锁和提高性能.

我编写了一个大量使用异步的库(访问数据库的Web服务).图书馆的用户遇到了僵局,经过多次痛苦的调试和修补后,我将其追踪到了单独使用await Task.Yield().我使用过的其他任何地方.ConfigureAwait(false),但是不支持Task.Yield().

对于需要等效的情况,推荐的解决方案是Task.Yield().ConfigureAwait(false)什么?

我已经读过有关如何SwitchTo移除某个方法的内容.我可以看出为什么那可能是危险的,但为什么没有相应的Task.Yield().ConfigureAwait(false)

编辑:

为了提供我的问题的进一步背景,这里有一些代码.我正在实现一个开源库,用于访问支持异步的DynamoDB(作为AWS的服务的分布式数据库).IX-Async库IAsyncEnumerable<T>提供了许多操作返回.该库不提供从以"块"提供行的数据源生成异步枚举的好方法,即每个异步请求返回许多项.所以我有自己的通用类型.该库支持预读选项,允许用户指定在调用实际需要之前应该请求多少数据.MoveNext()

基本上,这是如何工作的,我通过调用GetMore()和传递这些块之间的状态来请求块.我将这些任务放入chunks队列并将它们出列并将它们转换为我放在单独队列中的实际结果.这个NextChunk()方法就是问题所在.根据值的不同,ReadAhead我会在完成最后一个(最多)之后保持获取下一个块,直到需要一个值但不可用(无)或仅获取超出当前使用值的下一个块(一些).因此,获取下一个块应该并行/不阻止获取下一个值.枚举器代码是:

private class ChunkedAsyncEnumerator<TState, TResult> : IAsyncEnumerator<TResult>
{
    private readonly ChunkedAsyncEnumerable<TState, TResult> enumerable;
    private readonly ConcurrentQueue<Task<TState>> chunks = new ConcurrentQueue<Task<TState>>();
    private readonly Queue<TResult> results = new Queue<TResult>();
    private CancellationTokenSource cts = new CancellationTokenSource();
    private TState lastState;
    private TResult current;
    private …
Run Code Online (Sandbox Code Playgroud)

.net c# task-parallel-library async-await

12
推荐指数
2
解决办法
1920
查看次数

SignalR - 如何在集线器中执行异步任务?

我正在尝试使用C#5 async/await功能创建SignalR应用程序,但无论何时运行代码,它都会抛出System.InvalidOperationException.这是重现问题的最简单的代码.

public class SampleHub : Hub
{
    public Task<string> GetGoogle()
    {
        var http = new WebClient();
        return http.DownloadStringTaskAsync("http://www.google.com");
    }
}
Run Code Online (Sandbox Code Playgroud)

例外细节:

此时无法启动异步操作.异步操作只能在异步处理程序或模块中启动,或者在页面生命周期中的某些事件中启动.如果在执行页面时发生此异常,请确保将页面标记为<%@ Page Async = \"true \"%>.

堆栈跟踪:

at System.Web.AspNetSynchronizationContext.OperationStarted()
at System.Net.WebClient.DownloadStringAsync(Uri address, Object userToken)
at System.Net.WebClient.DownloadStringTaskAsync(Uri address)
at System.Net.WebClient.DownloadStringTaskAsync(String address)
Run Code Online (Sandbox Code Playgroud)

在客户端,Javascript看起来像这样.

$.connection.hub.start().done(function () {
    $('#google').click(function () {
        var google = sample.server.getGoogle();
        console.log(google);
    });
});
Run Code Online (Sandbox Code Playgroud)

我做错了什么?有没有解决方法?我真的很想坚持使用C#中的异步/等待模式,如果可能的话.

c# async-await signalr signalr-hub

8
推荐指数
1
解决办法
5260
查看次数

SignalR异步操作错误

我正在使用SignalR 1.1.2,我遇到了异步集线器方法的问题.使用ForeverFrame传输在我的PC上一切正常,但在服务器上部署并切换到Web套接字传输后,我收到以下错误:

此时无法启动异步操作.异步操作只能在异步处理程序或模块中启动,或者在页面生命周期中的某些事件中启动.如果在执行页面时发生此异常,请确保将页面标记为<%@ Page Async ="true"%>.

我的中心方法代码:

public async Task<string> getUrl()
    {
        var url = await MyWebservice.GetMyRoomUrlAsync(Context.User.Identity.Name);

        return url;
    }
Run Code Online (Sandbox Code Playgroud)

SignalR中是否支持使用Web套接字传输的异步方法?

更新:GetMyRoomUrlAsync代码:

public static Task<string> GetMyRoomUrlAsync(string email)
    {
        var tcs = new TaskCompletionSource<string>();

        var client = new Onif40.VisualStudioGeneratedSoapClient();

        client.GetRoomUrlCompleted += (s, e) =>
        {
            if (e.Error != null)
                tcs.TrySetException(e.Error);
            else if (e.Cancelled)
                tcs.TrySetCanceled();
            else
                tcs.TrySetResult(e.Result);
        };

        client.GetRoomUrlAsync(email);

        return tcs.Task;
    }
Run Code Online (Sandbox Code Playgroud)

在Stephen Cleary澄清问题所在之后,通过将EAP重写为APM来解决问题是微不足道的.

public static Task<string> GetMyRoomUrlAsync(string email)
    {
        var tcs = new TaskCompletionSource<string>();

        var client = new Onif40.VisualStudioGeneratedSoapClient();

        client.BeginGetRoomUrl(email, iar …
Run Code Online (Sandbox Code Playgroud)

asp.net .net-4.5 signalr

2
推荐指数
1
解决办法
1768
查看次数