IOException: “Desafío de autenticación recibida es nulo” (Apache Harmony / Android)

Estoy tratando de enviar un GET a través de HttpURLConnection de Android (importado de org.apache.harmony.luni.internal.net.www.protocol.http.HttpURLConnection ), y al recibir la respuesta, se lanza una IOException :

en doRequestInternal (): “Desafío de autenticación recibida es nulo”

¿Qué significa este error y qué está causando esto? Estoy escribiendo los parámetros de OAuth en el encabezado Autorización, pero también lo hago en otras ocasiones, sin problemas.

  if (connection == null) { connection = (HttpURLConnection) new URL(endpointUrl).openConnection(); connection.setRequestMethod("GET"); } //... do some OAuth message signing connection.connect(); int statusCode = connection.getResponseCode(); // throws IOException 

Descubrí el motivo.

En primer lugar, a todos los que no están conscientes de lo que significa este error (estoy seguro): esta excepción se produce si el servidor responde con un 401. Muy intuitivo, teniendo en cuenta que fue lanzado en getResponseCode () (iow nunca puede verificar 401 usted mismo, pero tiene que atrapar esta IOException en su lugar …).

La causa real para el 401 fue que no envié un código de verificador OAuth a donde se esperaba en este momento.

Tal vez será útil para alguien …

Esta excepción solo significa encabezados de respuesta mal formados: el encabezado “WWW-Authenticate” no se encontró. Además, las respuestas fragmentadas con código 401 no son compatibles, por lo que necesitará el encabezado “Content-Length” (puede ser cero).

Simplemente agregue este encabezado a la solicitud (en el lado del servidor):

 WWW-Authenticate: None 

Tenga en cuenta que existen dos enfoques de autenticación: Autenticación HTTP y autenticación basada en tokens . Si está utilizando Autenticación HTTP, debe seguir las especificaciones a las que se hace referencia: incluir el campo de encabezado WWW-Authenticate en el lado del servidor, usar java.net.Authenticator localmente, etc. Si está usando la autenticación basada en tokens, obviamente debe usar cookies para almacena el token y haz que puedas mantener vivas las sesiones de larga duración. En tal caso, coloque el siguiente código en android.app.Application.onCreate()

 CookieManager cookieManager = new CookieManager(); CookieHandler.setDefault(cookieManager); 

y no tendrá problemas cuando reciba HTTP 401 del servidor sin el campo de encabezado WWW-Authenticate .