异步Web服务调用无法获取数据

时间:2014-12-11 11:04:30

标签: c# async-await

我的泛型类有以下代码。这可以用于我传递给方法的任何类。

public static async Task<T>GetData<T>(string req, bool weather = false)
    {
        string webrequest = string.Format("{0}&{1}", req, !weather ? string.Format("key={0}", MainClass.GoogleAPI) : string.Format("APPID={0}", MainClass.WeatherID));
        var request = WebRequest.Create(webrequest) as HttpWebRequest;
        request.Method = "GET";
        request.Accept = "application/json";
        request.ContentType = "application/json";
        string responseContent = "";

        T obj = Activator.CreateInstance<T>();

        try
        {
            var asyncResult = request.BeginGetResponse(new AsyncCallback(s =>
                    {
                        var response = (s.AsyncState as WebRequest).EndGetResponse(s);

                        using (var reader = new StreamReader(response.GetResponseStream()))
                        {
                            responseContent = reader.ReadToEnd();
                            obj = GeneralUtils.Deserialize<T>(responseContent);
                        }

                }), request);
            return obj;
        }
        catch (WebException ex)
        {
            Debug.WriteLine("Deserialiser failed : {0}--{1}", ex.StackTrace, ex.Message);
            return default(T);
        }
    }

请求字符串包含此

之类的内容
var servercall = "https://maps.googleapis.com/maps/api/directions/json?origin=Warrington,UK&destination=Whiston,UK&waypoints=Preston,UK|Dundee,UK";

API密钥没问题。

我发现的是asyncResult中的响应行永远不会被命中,所以只返回传入的类。这些类是使用jsontocsharp网站使用google API网站上的示例生成的。

通常情况下,我不会使用此代码,但这是针对PCL库的,因此需要以这种方式完成(除非有其他方法可以同步执行此操作)。

我没有使用JSON.Net(应用程序规范禁止任何不属于标准.NET的内容)。测试作为控制台应用程序运行。

1 个答案:

答案 0 :(得分:3)

您的方法不等待来自BeginGetResponse的响应,因此它会立即结束并返回obj这是一个空对象。

有很多方法可以做到这一点,这是其中之一:

public static async Task<T> GetData<T>(string req, bool weather = false)
{
    string webrequest = string.Format("{0}&{1}", req, !weather ? string.Format("key={0}", MainClass.GoogleAPI) : string.Format("APPID={0}", MainClass.WeatherID));
    var request = WebRequest.Create(webrequest) as HttpWebRequest;
    request.Method = "GET";
    request.Accept = "application/json";
    request.ContentType = "application/json";
    try
    {
       var response = await request.GetResponseAsync();

       using (var reader = new StreamReader(response.GetResponseStream()))
          return GeneralUtils.Deserialize<T>(reader.ReadToEnd());
    }
    catch (Exception ex)
    {
       Debug.WriteLine("Deserialiser failed : {0}--{1}", ex.StackTrace, ex.Message);
       throw;
    }
}