Как дождаться загрузки файла (или проверки URL)?

У меня проблема, я хочу подождать в Main(), пока не закончится Download(). Однако загрузка/проверка файла начинается, в то же время начинают выполняться другие строки.

Как я могу использовать awaitили что-то еще, чтобы ждать в Main?

    private void Main()
    {
       Download("http://webserver/file.xml");
       //Do something here ONLY if the file exists!!
    }


    //This method invokes the URL validation
    private void Download(downloadURL)
    {
       System.Uri targetUri = new System.Uri(downloadURL);
       HttpWebRequest request = (HttpWebRequest)HttpWebRequest.Create(targetUri);
       request.BeginGetResponse(new AsyncCallback(WebRequestCallBack), request);
    }

    //In this method the URL is being checked for its validity
    void WebRequestCallBack(IAsyncResult result)
    {
        HttpWebRequest resultInfo = (HttpWebRequest)result.AsyncState;
        HttpWebResponse response;
        string statusCode;
        try
        {
            response = (HttpWebResponse)resultInfo.EndGetResponse(result);
            statusCode = response.StatusCode.ToString();
        }
        catch (WebException e)
        {
            statusCode = e.Message;
        }
        onCompletion(statusCode);
    }

    //This method does not help! I just added if it could be any useful
    private  void onCompletion(string status)
    {
        if (status == HttpStatusCode.OK.ToString())
            MessageBox.Show("file exists");  
        else
            MessageBox.Show("file does not exists");  
    }

Что мне нужно, подробно...

  • Скачать файл с заданного URL
  • Перед загрузкой проверьте URL
  • if (verfied) then
    • continue downloading and do other tasks
  • else
    • fail and stop the process, Don't download! and give a message that URL was broken (couldn't verified)!

Я пытаюсь выполнить часть "Проверка", проверяя правильность URL-адреса и ожидая ответа. Мне нужен какой-то СТАТУС процесса проверки, чтобы продолжить.


person wafers    schedule 28.01.2013    source источник
comment
По какой причине //Do something here ONLY if the file exists!! нельзя было сделать в WebRequestCallBack или onCompletion?   -  person JosephHirn    schedule 28.01.2013
comment
.net 4.5 или более ранняя версия?   -  person daryal    schedule 28.01.2013
comment
@Ginosaji хорошо, я просто привел пример в простой форме, использовать onCompletion нелегко. Мне нужна непрерывность кода.   -  person wafers    schedule 28.01.2013
comment
@daryal более ранняя версия .net 4.0   -  person wafers    schedule 28.01.2013
comment
Вы должны объяснить, что вам нужно более подробно. В противном случае ответ: используйте синхронную версию.   -  person Hamlet Hakobyan    schedule 28.01.2013
comment
Ваши единственные варианты: (1) поместить код в обратный вызов или (2) загрузить файл синхронно. Вариант 1 будет правильным, так как вариант 2 заблокирует поток пользовательского интерфейса и заставит приложение зависнуть на время загрузки.   -  person JosephHirn    schedule 28.01.2013
comment
@Hamlet Hakobyan: я добавил некоторые детали того, что я пытаюсь сделать.   -  person wafers    schedule 29.01.2013


Ответы (2)


Следует попытаться:

var task = Task.Factory.FromAsync<WebResponse>(request.BeginGetResponse,  
                                               request.EndGetResponse, null);
var response = task.Result;
person cuongle    schedule 28.01.2013
comment
Спасибо Куонг Ле за ответ, но нет доступного метода request.GetResponse(), по крайней мере, не для WP7. - person wafers; 28.01.2013
comment
Прямой вызов BeginGetResponse(), а затем EndGetResponse() был бы намного проще. - person svick; 28.01.2013
comment
Я использую приведенное выше решение, например... Task<WebResponse> task = Task.Factory.FromAsync<WebResponse>(request.BeginGetResponse, request.EndGetResponse, null); task.ContinueWith((t) => { WebResponse webResponse = t.Result; var response = (HttpWebResponse)webResponse; responseString = response.StatusCode.ToString(); }); ... Я всегда получаю пустой responseString, и хотя я передаю неверный URL-адрес, он не падает! Не работает пока! :) - person wafers; 29.01.2013

Вы можете использовать объект ManualResetEventSlim. Инициализируйте его значением true при его создании. В конце метода OnComplete вызовите метод Reset для объекта ManualResetEventSlim. В вашем основном приложении вам просто нужно вызвать метод WaitOne для объекта ManualResetEventSlim.

person TYY    schedule 28.01.2013
comment
Это то, что он хочет, но не то, что ему нужно. OP не должен использовать асинхронный ввод-вывод только для ожидания завершения. - person usr; 28.01.2013