使用 LinqToTwitter 与 Twitter direct_messages/events 异步和等待

async and await with Twitter direct_messages/events using LinqToTwitter

我真的被困在这个问题上好几天了。我在 ASP.Net C#

中使用 LinqToTwitter

我正在尝试让新的 DirectMessages 正常工作,我按照示例操作但没有成功。

我希望该功能在按钮点击时起作用,所以我尝试的是:

  1. 按钮点击:

`

protected void Btn1_Click(object sender, EventArgs e)
        {
            string x = MyTest().Result;
        }

`

  1. 我的测试:

`

static async Task<string> mytest()
{
        AspNetAuthorizer auth = DoAuthorization();
        var twitterCtx = new TwitterContext(auth);
        List<DMEvent> AllDmEvents = new List<DMEvent>();
        string Cursor;
        DirectMessageEvents dmResponse =
            await
                (from dm in twitterCtx.DirectMessageEvents
                 where dm.Type == DirectMessageEventsType.List &&
                 dm.Count == 10
                 select dm)
                .SingleOrDefaultAsync(); //In debugging mode, after this line is executed, it will go away and keep loading forever and never come back
        AllDmEvents.AddRange(dmResponse.Value.DMEvents);
        Cursor = dmResponse.Value.NextCursor;
        string xxx = (JsonConvert.SerializeObject(AllDmEvents, Formatting.None));
        return xxx;
}

`

  1. 授权:

`

static AspNetAuthorizer DoAuthorization()
    {
        AspNetAuthorizer auth = new AspNetAuthorizer();
        auth = new AspNetAuthorizer
        {
            CredentialStore = new SessionStateCredentialStore
            {
                ConsumerKey = "MyConsumerKey",
                ConsumerSecret = "MyConsumerSecret ",
                OAuthToken = "MyOAuthToken ",
                OAuthTokenSecret = "MyOAuthTokenSecret ",
                ScreenName = "MyUserName",
                UserID = 12345678
            }
        };
        return auth;
    }`

如有任何帮助,SO 将不胜感激!

您代码中的 DoAuthorization() 看起来像是来自控制台示例,不适用于 ASP.NET。原因是 ASP.NET 是无状态的,OAuth 进程将您带到 Twitter 站点并返回。因此,您必须将授权分为两部分:开始和完成。

我猜您正在使用 ASP.NET MVC,但如果您使用的是 WebForms,则概念相似(但不同)。这是开始部分:

public class OAuthController : AsyncController
{
    public ActionResult Index()
    {
        return View();
    }

    public async Task<ActionResult> BeginAsync()
    {
        var auth = new MvcAuthorizer
        {
            CredentialStore = new SessionStateCredentialStore
            {
                ConsumerKey = ConfigurationManager.AppSettings["consumerKey"],
                ConsumerSecret = ConfigurationManager.AppSettings["consumerSecret"]
            }
        };

请注意,它使用 MvcAuthorizer 填充凭据。获得 MvcAuthorizer 实例后,将用户重定向到 Twitter 进行授权,如下所示:

        string twitterCallbackUrl = Request.Url.ToString().Replace("Begin", "Complete");
        return await auth.BeginAuthorizationAsync(new Uri(twitterCallbackUrl));
    }

这会将用户转到 Twitter 授权页面,他们会在该页面授予您的应用代表他们操作的权限。 Twitter 会将用户重定向回 twitterCallback,这就是上面的代码修改 URL 以将 Begin 替换为 Complete 的原因 URL。因此,Twitter 将用户重定向回您的应用,该应用调用下面的 CompleteAsync() 操作:

    public async Task<ActionResult> CompleteAsync()
    {
        var auth = new MvcAuthorizer
        {
            CredentialStore = new SessionStateCredentialStore()
        };

        await auth.CompleteAuthorizeAsync(Request.Url);

        // This is how you access credentials after authorization.
        // The oauthToken and oauthTokenSecret do not expire.
        // You can use the userID to associate the credentials with the user.
        // You can save credentials any way you want - database, 
        //   isolated storage, etc. - it's up to you.
        // You can retrieve and load all 4 credentials on subsequent 
        //   queries to avoid the need to re-authorize.
        // When you've loaded all 4 credentials, LINQ to Twitter will let 
        //   you make queries without re-authorizing.
        //
        //var credentials = auth.CredentialStore;
        //string oauthToken = credentials.OAuthToken;
        //string oauthTokenSecret = credentials.OAuthTokenSecret;
        //string screenName = credentials.ScreenName;
        //ulong userID = credentials.UserID;
        //

        return RedirectToAction("Index", "Home");
    }

现在您的应用程序已获得用户的权限,获取他们的令牌并保留它们以供后续查询使用,这样您就不必在用户每次想要使用您的应用程序时都继续 OAuth 流程。请参阅代码中有关如何获取这些凭据的注释。

现在,当您要执行查询时,实例化一个 MvcAuthorizer,如下所示:

static async Task<string> mytest()
{
    var auth = new MvcAuthorizer
    {
        CredentialStore = new SessionStateCredentialStore()
    };

    var twitterCtx = new TwitterContext(auth);
    List<DMEvent> AllDmEvents = new List<DMEvent>();
    string Cursor;
    DirectMessageEvents dmResponse =
        await
            (from dm in twitterCtx.DirectMessageEvents
             where dm.Type == DirectMessageEventsType.List &&
             dm.Count == 10
             select dm)
            .SingleOrDefaultAsync(); //In debugging mode, after this line is executed, it will go away and keep loading forever and never come back
    AllDmEvents.AddRange(dmResponse.Value.DMEvents);
    Cursor = dmResponse.Value.NextCursor;
    string xxx = (JsonConvert.SerializeObject(AllDmEvents, Formatting.None));
    return xxx;

}

您可以看到修改后的 myTest() 方法的第一条语句如何使用 SessionStateCredentialStore 实例化 MvcAuthorizer,保存您的凭据。

最后,在您希望用户使用 Twitter 授权您的应用程序的时间点(登录、首次查询或您选择的任何其他时间),检查他们是否已经获得授权,并且如果没有则重新定向,如下所示:

    public ActionResult Index()
    {
        if (!new SessionStateCredentialStore().HasAllCredentials())
            return RedirectToAction("Index", "OAuth");

        return View();
    }

注意上面的代码如何在 SessionStateCredentialStore 实例上调用 HasAllCredentials()。我假设您将添加自己的逻辑来确定何时加载用户的凭据,但希望您了解 HasAllCredentials() 辅助方法,以便更容易知道何时必须授权用户。

有关详细信息,请访问 LINQ to Twitter OAuth docs. The LINQ to Twitter source code also has Samples on how to use OAuth