我正在使用OAuth2在Windows Phone 7中使用Google API。
在我调用API之前,我需要更新访问令牌(如果需要)。
我遇到的问题是在继续调用API之前等待更新令牌的异步请求完成。
我已经使用了下面的代码,但我对它不满意。我正在寻找一种更好的替代方法来简单地在while循环中轮询变量。
/// <summary>
/// Calls the API.
/// </summary>
/// <param name="callback">The callback.</param>
/// <param name="api">The API.</param>
/// <param name="queryStrings">The query strings.</param>
public static void CallApi(AsyncCallback callback, string api, Dictionary<string, string> queryStrings = null)
{
var uri = new Uri(string.Format("{0}{1}{2}", ApiBaseUrl, api, queryStrings.ToQueryString()));
if (accessTokenExpires < DateTime.Now.AddSeconds(300))
{
RefreshAccessToken();
}
// Start new thread so we don't lock up the UI thread while waiting
var thread = new Thread(
() =>
{
// Wait for the access token to be updated
while (accessTokenExpires < DateTime.Now.AddSeconds(300)) ;
var request = WebRequest.CreateHttp(uri);
request.Headers["Authorization"] = string.Format("OAuth {0}", accessToken);
request.BeginGetResponse(callback, request);
});
thread.Start();
}
/// <summary>
/// Refresh the access token.
/// </summary>
private static void RefreshAccessToken()
{
if (Config.GoogleOAuthRefreshToken == string.Empty)
{
// TODO - Present the OAuth popup to the user
return;
}
var uri = new Uri(GetTokenUrl);
var request = WebRequest.CreateHttp(uri);
request.Method = "POST";
request.ContentType = "application/x-www-form-urlencoded";
request.BeginGetRequestStream(RefreshToken_GetRequest, request);
}
答案 0 :(得分:2)
我认为你有自己需要的开端,但只需要使用WebRequest的Async特性就可以了。这是一个如何做到这一点的例子
public static void CallApi(AsyncCallback callback, string api, Dictionary<string, string> queryStrings = null)
{
var uri = new Uri(string.Format("{0}{1}{2}", ApiBaseUrl, api, queryStrings.ToQueryString()));
RefreshAccessToken(() =>
{
var request = WebRequest.CreateHttp(uri);
request.Headers["Authorization"] = string.Format("OAuth {0}", accessToken);
request.BeginGetResponse(callback, request);
});
}
private static void RefreshAccessToken(Action callback)
{
if(IsTokenExpired() == false)
{
if(callback != null) callback();
return;
}
if (Config.GoogleOAuthRefreshToken == string.Empty)
{
// TODO - Present the OAuth popup to the user
return;
}
var uri = new Uri(GetTokenUrl);
var request = WebRequest.CreateHttp(uri);
request.Method = "POST";
request.ContentType = "application/x-www-form-urlencoded";
request.BeginGetRequestStream(asyncResult =>
{
// Do anything for POST
request.BeginGetResponse(asyncResult2 =>
{
// Read stream, and process
if(callback != null) callback();
}, null);
}, request);
}
private bool IsTokenExpired()
{
return accessTokenExpires < DateTime.Now.AddSeconds(300);
}
答案 1 :(得分:0)
您是否考虑过使用Async-CTP或VS 2012将此逻辑转换为Task.Delay调用?它甚至可以帮助您处理网络请求代码。