2015-06-19 3 views
0

Просто интересно, может ли кто-нибудь ответить на этот вопрос? Я пытаюсь загрузить файл на веб-сервер, используя функцию WebClient.UploadFile(). Это работает как ожидалось, однако я не могу декодировать ответ из-за того, что, по моему мнению, есть некоторая HTTP-связь между клиентом и сервером, заканчивающаяся контентом-типом image/jpeg.Как вернуть WebClient() UploadFile() 302 Ответ

Поток HTTP выглядит следующим образом:

POST/HTTP/1.1 ---> 
HTTP/1.1 100 Continue <--- 
HTTP/1.1 302 Found <--- 

Этот документ содержит URL для загружаемого контента.

GET /5109799364591616 HTTP/1.1 ---> 
HTTP/1.1 200 OK <---- 

Кажется, программа автоматически после переадресации означает, что, когда я возвращаюсь массив байт, который фактически содержит файл изображения.

Есть ли все равно, чтобы вернуть 302 здесь? Моя конечная цель - вернуть перенаправленный URL-адрес и поместить его в буфер обмена пользователя.

ответ

0

Для HTTP-запросов WebClient использует внутренние экземпляры объекта HttpWebRequest. HttpWebRequest позволяет включить/отключить автоматическое перенаправление с помощью свойства AllowAutoRedirect.

Чтобы получить доступ к объекту AllowAutoRedirect объекта HttpWebRequest, вы должны переопределить защищенный метод GetWebRequest класса WebClient. Чтобы просто отключить автоматическое перенаправление, этого было бы достаточно.

Если сервер отвечает на 302 (или аналогичный код, такой как 303), URL-адрес перенаправления можно найти в поле заголовка местоположения ответа. К счастью, WebClient предоставляет публичную коллекцию ResponseHeaders для легкого доступа к полям заголовка ответа.

Если вам нужно проверить фактический код состояния ответа, отправленный сервером, вам необходимо будет получить доступ к объекту HttpWebResponse, сгенерированному объектом HttpWebRequest. Аналогично доступу к объекту HttpWebRequest, WebClient имеет защищенный метод, который вы можете переопределить для доступа к объекту HttpWebResponse: GetWebResponse(...). GetWebResponse имеет перегрузку, которая используется для асинхронных операций. Обычно эта перегрузка также должна быть переопределена таким же образом.

Простая реализация пользовательского класса WebClient фитинга ваши основные потребности может выглядеть примерно так:

public class CustomWebClient : WebClient 
{ 
    public HttpStatusCode? ResponseStatusCode { get; set; } 


    protected override WebRequest GetWebRequest(Uri url) 
    { 
     WebRequest req = base.GetWebRequest(url); 
     if (req is HttpWebRequest) 
     { 
      ((HttpWebRequest) req).AllowAutoRedirect = false; 
     } 

     return req; 
    } 

    protected override WebResponse GetWebResponse(WebRequest request) 
    { 
     WebResponse resp = base.GetWebResponse(request); 
     ResponseStatusCode = (resp is HttpWebResponse) ? 
      ((HttpWebResponse) resp).StatusCode 
      : (HttpStatusCode?) null; 
     return resp; 
    } 

    protected override WebResponse GetWebResponse(WebRequest request, IAsyncResult result) 
    { 
     WebResponse resp = base.GetWebResponse(request, result); 
     ResponseStatusCode = (resp is HttpWebResponse) ? 
      ((HttpWebResponse) resp).StatusCode 
      : (HttpStatusCode?) null; 
     return resp; 
    } 
} 

Обратите внимание, что свойство ResponseStatusCode в реализации выше, является обнуляемым типа. Для запросов на основе http это свойство будет содержать код состояния ответа последнего запроса, выданного веб-клиентом. Для любых других запросов (например, ftp) значение этого свойства будет установлено на null.

В приложении, вы можете использовать этот простой класс CustomWebClient так:

var client = new CustomWebClient(); 
byte[] response = client.UploadFile("http://test.com", "POST", "upload.jpg"); 

if (client.ResponseStatusCode == HttpStatusCode.Found) 
{ 
    string redirectUri = client.ResponseHeaders[HttpResponseHeader.Location]; 

    ... do something with the redirection Uri ... 
} 
+0

Это прекрасно работает. Спасибо за быстрый ответ. –

Смежные вопросы