¿Cómo usar el cliente HTTP Apache heredado en Android Marshmallow?

76

Antecedentes

En Android Marshmallow, Google ha eliminado por completo la compatibilidad con el cliente HTTP Apache (enlace aquí ) porque no tiene un buen rendimiento en comparación con las alternativas.

Esta también podría ser la causa de que muchas aplicaciones se bloqueen en Android Marshmallow.

El problema

Google le permite seguir usando esta API, pero no como una integrada, agregando esta línea al archivo gradle:

useLibrary 'org.apache.http.legacy'

Entonces, esto es lo que hice:

dependencies {
    classpath 'com.android.tools.build:gradle:1.3.0'
}

Y:

android {
    compileSdkVersion 'android-MNC'
    buildToolsVersion "23.0.0 rc3"
    useLibrary 'org.apache.http.legacy'

    defaultConfig {
        applicationId "com.example.user.androidmtest"
        minSdkVersion 'MNC'
        targetSdkVersion 'MNC'
        versionCode 1
        versionName "1.0"
    }

Cuando lo probé, se compiló bien (no se muestran errores y pude ejecutar la aplicación de prueba de concepto, ya que no tiene ningún código especial), pero cuando intenté usar algunas de las clases, sé que son parte de la antigua API (como la clase "HttpClient"), veo que no me permite hacerlo.

Sé que no se recomienda usar esta solución, pero debemos tener la aplicación lista para funcionar allí al menos temporalmente, hasta que trabajemos al 100% en todas las cosas que deberían cambiar para Android Marshmallow, y no queremos sorpresas en el forma de choques.

Aquí hay una captura de pantalla:

ingrese la descripción de la imagen aquí

La pregunta

¿Por qué ocurre? ¿Lo usé correctamente?


EDITAR: informó sobre este problema aquí:

https://code.google.com/p/android/issues/detail?id=181474

desarrollador de Android
fuente
por compilado bien, ¿ te refieres a gradle sincronizado bien o estás obteniendo una ClassNotFoundException en tiempo de ejecución?
Blackbelt
¿Puedes publicar alguna captura de pantalla de android studioat
DevUt
@Blackbelt Quiero decir que hasta el momento en que escribí las clases que se supone que deben ser compatibles, podría compilarse y ejecutarse bien (porque no hay nada para usarlo). No puede haber ninguna ClassNotFoundException, porque todavía no las uso. Solo cuando trato de usar clases que se supone que deben estar allí, no puedo. No me permite hacerlo y no me ofrece las importaciones necesarias.
desarrollador de Android
@ user4847410 ¿Captura de pantalla de qué exactamente? Intentar forzar la importación resultará en que no se reconozca. y usar una clase que existe allí también lo hace. De todos modos, he actualizado la pregunta para mostrar la situación actual, que es bastante mínima ...
desarrollador de Android
Comprueba si estás usando la última versión beta de Gradle. dependencias {classpath 'com.android.tools.build:gradle:1.3.0'} Parece que falta algo después de la versión (es decir, '-beta' o algo así). Usar la última versión beta me lo resolvió
milosmns

Respuestas:

93

Android Studio se quejaba de que org.apache.httpclases como

org.apache.http.NameValuePair
org.apache.http.client.utils.URLEncodedUtils

faltaban.

Así que agregué org.apache.http.legacy.jarcuál está en la Android/Sdk/platforms/android-23/optionalcarpeta aapp/libs

También agregué esta línea a mi app.gradlearchivo

compile files('libs/org.apache.http.legacy.jar')

Pero si está usando más bibliotecas, puede usar de esta manera

compile fileTree(dir: 'libs', include: ['*.jar'])

Esto resolvió todos mis errores causados ​​porque Google eliminó el soporte del cliente HTTP Apache.

CoPLas
fuente
2
Trabajó para mi. Sin embargo, tuve que agregar Jar como una biblioteca a mi módulo de aplicación, para deshacerme de los errores de Android Studio sobre HttpClient y demás.
Jürgen 'Kashban' Wahlmann
1
Tengo problemas con Proguard cuando incluyo org.apache.http.legacy.jar: ¿ IOExcpetion: Can't write [path to classes.jar] (Can't read [path to libs/org.apache.http.legacy.jar(;;;;;;!META-INF/MANIFEST.MF)] (Duplicate zip entry [org.apache.http.legacy.jar:org/apache/commons/codec/binary/Hex.class]))Alguien más usa Proguard? ¿Algunas ideas?
Ashughes
1
Es muy triste que Google haya optado por utilizar un truco que requiera que las personas agreguen un binario a su proyecto en lugar de publicar http-legacy en un repositorio de artefactos. Pensé que habíamos dejado atrás ese anti-patrón hace 10 años.
William
1
Eres un genio, señor.
actividad
1
Todavía no me ha funcionado incluso después de esto. Cualquier posible diagnóstico por favor @CoPLaS
Lakshmi Narayanan
9

useLibrary 'org.apache.http.legacy' no funcionó para mí hasta que actualicé la versión de las herramientas de Gradle en mi archivo principal build.gradle de mi proyecto de Android Studio, de la siguiente manera:

dependencies {
    classpath 'com.android.tools.build:gradle:1.3.0'
}
Jamie Hall
fuente
¡Muchas gracias! ¿Alguna idea de por qué solo este cambio resuelve el problema?
Shirane85
Aparentemente, la directiva useLibrary se agregó a Gradle recientemente, por lo que es necesario usar una versión más nueva como dije anteriormente.
Jamie Hall
Tengo esto en el archivo principal de gradle: classpath 'com.android.tools.build:gradle:1.0.0-rc2' Entonces, ¿debería eliminar esto y agregar su línea o mantener ambas líneas y funcionaría sin ningún problema?
Sagar Devanga
Quite eso y agregue lo anterior.
Jamie Hall
9

Solución perfecta aquí ejecutando una simple verificación de ruta de archivo. mediante la ejecución

   android {
    compileSdkVersion 'android-MNC'
    buildToolsVersion "23.0.0 rc3"
    useLibrary 'org.apache.http.legacy'

    defaultConfig {
        applicationId "com.example.user.androidmtest"
        minSdkVersion 'MNC'
        targetSdkVersion 'MNC'
        versionCode 1
        versionName "1.0"

    }

        getBootClasspath().each{File file ->
           println file.absolutePath
        }
    }
}

Obtendrás algo como a continuación

/Users/"yourname"/Development/android-sdk-macosx/platforms/android-MNC/android.jar /Users/"yourname"/Development/android-sdk-macosx/platforms/android-MNC/optional/org.apache .http.legacy.jar

Así que ahí lo tienes, el frasco está ahí. Por alguna razón, no se agregó al proyecto. pero siempre puedes agregarlo manualmente, supongo.

WenChao
fuente
1
No entiendo. ¿Qué es este código que escribiste? Quiere decir que debería buscar este frasco y agregarlo al proyecto. Por favor explique.
desarrollador de Android
Si, tienes razón. Escribí ese código en build.gradle bajo la cláusula de Android. Exactamente lo que estoy diciendo, el frasco no se recogió automáticamente. Tal vez necesite agregarlo manualmente
WenChao
¿Qué hace el código? ¿Es realmente necesario? Además, ¿lo ha comprobado? ¿Funciona bien?
desarrollador de Android
No, solo imprime la ruta del archivo. no hace nada elegante, puedes eliminarlo de forma segura. Ese frasco contiene todo, desde el antiguo frasco de apache (HttpClient, Log, etc.). Supongo que funcionará bien.
WenChao
Ok, gracias. Espero no necesitarlo cuando llegue el momento. Lo comprobaré de nuevo si es necesario. Por ahora, obtienes +1 por el esfuerzo.
desarrollador de Android
6

Después de muchas horas frustrantes, funcionó lo siguiente:

1. Localice el frasco de Apache. Debería residir en algún lugar como:

C:\Users\<yourname>\AppData\Local\Android\sdk\platforms\android-23\optional

2. Copie org.apache.http.legacy.jar a su carpeta libs.

Haga clic derecho en libs -> pegar, o use su explorador de archivos para navegar a la carpeta libs de su proyecto y pegar.

Si no tiene una carpeta libs, como yo, cree un nuevo proyecto e importe todos los archivos relevantes en sus respectivos lugares.

3. Haga clic en ok ver esto

4. Paso más importante: haga clic derecho en la carpeta de apache y seleccione Add As Library. mira esto

Espero que esto ayude a alguien a seguir adelante con su vida.

La AEB
fuente
5

La respuesta anterior solo ayuda a que se ejecuten las compilaciones de depuración y a lanzar compilaciones que utilizan gradle.

Inserte esto dentro de la etiqueta de la aplicación en el archivo de manifiesto, en todas las instancias del proyecto que usan las clases de apache heredadas:

<uses-library android:name="org.apache.http.legacy" android:required="false" />

Esto ayuda a aquellos que todavía están usando Eclipse y scripts ant durante la compilación.

Pier Betos
fuente
2

Sé que esta es una razón tonta, pero en la lista pruébalo ...

Experimenté este problema recientemente, y es causado por la restricción de la longitud de la ruta. Creo que es un máximo de 256 caracteres.

Reubique su proyecto y la construcción tendrá éxito. Espero que esto funcione para usted.

Arpit Patel
fuente
esto no es una tontería ... esta es la respuesta que funcionó en mi caso ... Las últimas 36 horas pasé probando todo en la tierra, excepto esto .. Suena tonto al principio, así que no lo tomé en serio ..
KawaiKx
Chicos, prueben esto también ... Realmente funcionó para mí, donde todo lo demás falló
KawaiKx
es un placer. @ KawaiKx
Arpit Patel
2

Biblioteca de Apache heredada ubicada en

[ANDROID_SDK]\platforms\android-23\optional\org.apache.http.legacy.jar 

Entonces puede copiarlo dentro de sus bibliotecas de proyecto o simplemente usar

compile files("${android.getSdkDirectory().getAbsolutePath()}" + File.separator + "platforms" + File.separator + "android-23" + File.separator + "optional" + File.separator + "org.apache.http.legacy.jar")

en su /app/build.gradle

AndreyICE
fuente
2

Primero tienes que verificar eso en tu carpeta libs

Asegúrese en la carpeta Libs Compruebe que la biblioteca de apache

Then add into your gradle file like this 

    android {
        compileSdkVersion 23
        buildToolsVersion '23.0.2'

        defaultConfig {
            applicationId "info.tranetech.laundry"
            minSdkVersion 15
            targetSdkVersion 23
            versionCode 1
            versionName "1.0"
        }
        buildTypes {
            release {
                minifyEnabled false
                proguardFiles getDefaultProguardFile('proguard-android.txt'), 'proguard-rules.pro'
            }
        }
    }
    android {
        useLibrary 'org.apache.http.legacy'
    }
    dependencies {
        compile fileTree(dir: 'libs', include: ['*.jar'])
        compile 'com.android.support:appcompat-v7:23.0.1
        compile 'com.android.support:design:23.0.1
        testCompile 'junit:junit:4.12'
        compile files('libs/android-async-http-1.4.4.jar')
        compile 'com.google.android.gms:play-services:8.4.0'
    }

Este es mi archivo gradle

También verifique la biblioteca externa

Arpit Patel
fuente
1

Habilite esto en sdk / platform / android-23 / Optional / Optional.json

[
  {
    "name": "org.apache.http.legacy",
    "jar": "org.apache.http.legacy.jar",
    "manifest": false
  }
]
arun-r
fuente
0

Eliminar

useLibrary 'org.apache.http.legacy' 

desde build.gradle y también agregué esta línea a mi archivo app.gradle

compile files('libs/org.apache.http.legacy.jar')

Pero si está usando más bibliotecas, puede usar de esta manera

compile fileTree(dir: 'libs', include: ['*.jar'])

La respuesta de CoPLaS solucionó mis problemas.

Roger Belk
fuente
2
¡Entonces solo vota la respuesta de CoPLaS en lugar de reproducirla aquí!
Leo apoya a Monica Cellio
0

¿Cómo usar el cliente HTTP Apache heredado en Android Marshmallow?

Para continuar usando las clases HTTP de Apache para API 23+:

En primer lugar, asegúrese de agregar la dependencia de gradle en la build.gradlef

buildscript {

    dependencies {
        classpath 'com.android.tools.build:gradle:2.0.0'
    }
}

Luego agregue la referencia dentro build.gradlede su proyecto:

android {
    compileSdkVersion 23
    buildToolsVersion "23.0.0"
    useLibrary 'org.apache.http.legacy'
    ...
}
Jorgesys
fuente
0

Una forma sencilla de resolver este problema es C: \ Users \ username \ AppData \ Local \ Android \ sdk \ platform. Aquí borre su android-23 y desde SDK manager actualice su API 23 nuevamente. Resolverá tu problema.

impathuri
fuente