Unzip à partir d'une réponse HTTP [Résolu]

Signaler
Messages postés
14869
Date d'inscription
lundi 11 juillet 2005
Statut
Modérateur
Dernière intervention
25 novembre 2020
-
Messages postés
14869
Date d'inscription
lundi 11 juillet 2005
Statut
Modérateur
Dernière intervention
25 novembre 2020
-
Hello z'à tou(te)s!
J'ai un petit souci dans une application Android mais le code incriminé étant du Java, je postes donc ici.

Contexte: Suite à une requête HTTP, je reçois en réponse un fichier ZIP contenant un seul fichier XML.

Objectif: J'aimerais pouvoir récupérer le contenu du fichier XML et le passer à mon parser qui prend en entrée un InputStreamReader.

Problème: le code suivant prend énormément de ressources et j'aimerais savoir s'il y a une méthode plus optimisée.

Voici le code:
private void parseResponse(HttpResponse response) {

  byte[] fileContent = null;
  BufferedInputStream responseContent = null;
  ZipInputStream zis = null;
  ByteArrayOutputStream baos = new ByteArrayOutputStream();
  InputStream fileStream = null;
  InputStreamReader inputStreamReader = null;

  // unzip data
  try {
    // Question: quelle est la version la plus optimum des 2 en terme de ressources?
    responseContent = new BufferedInputStream(response.getEntity().getContent());
    zis = new ZipInputStream(responseContent);
    // zis = new ZipInputStream(response.getEntity().getContent());

    while (zis.getNextEntry() != null) { // there is only one entry
      // extract file from zip
      int count;
      byte[] buffer = new byte[4096];
      while ((count = zis.read(buffer)) != -1) {
        baos.write(buffer, 0, count);
        // Question: rajouter un Thread.Sleep(50) permettrait "d'alléger le thread"?
      }

      // save content into byte array
      fileContent = baos.toByteArray();
    }
  } catch (Exception e) {
    Log.e(TAG, "exception: " + e.getLocalizedMessage());
  } finally {
    try {
      // close streams
      if (zis != null) {
        zis.close();
      }

      if (responseContent != null) {
        responseContent.close();
      }

      if (baos != null) {
        baos.close();
      }
    } catch (Exception e) {
      Log.e(TAG, "exception when closing streams: " + e.getLocalizedMessage());
    }
  }

  // XML Parsing
  try {
    fileStream = new ByteArrayInputStream(fileContent);
    inputStreamReader = new InputStreamReader(fileStream, "ISO-8859-1");

    MonParser parser = new MonParser();
    MonParserResult result = parser.parse(inputStreamReader); // parse the data

    if (result.status()) {
      // Ajout dans la base
    }
  } catch (Exception e) {
    Log.e(TAG, "Exception " + e.getLocalizedMessage());
  } finally {
    try {
      if (fileStream != null) {
        fileStream.close();
      }

      if (inputStreamReader != null) {
        inputStreamReader.close();
      }
    } catch (Exception e) {
      Log.e(TAG, "exception when closing streams: " + e.getLocalizedMessage());
    }
  }
}


J'ai glissé 2 questions dans le code, merci à ceux qui voudront bien y jeter un coup d'oeil.

Ah, et si vous voyez des choses affreuses dans le code, n'hésitez pas à me le signaler

@+
Buno, Admin CS
L'urgent est fait, l'impossible est en cours. Pour les miracles, prévoir un délai...

6 réponses


Salut !

Désolé, je manque de temps libre en ce moment U_U" En plus, je ne suis pas très inspiré sur ce coup là O_ô Je répond sûrement trop tard, mais s'il faut opter pour une de tes deux solutions d'optimisation, je pencherai pour la deuxième. Car la première fait instancier deux objets, et vu que ça a l'air d'être lourd, je pense que tu économiserais des ressources à tout faire d'un coup sans intermédiaire.

Désole du retard :'(


--
Pylouq
Heureux sont ceux qui lisent le Réglement, ils ne finiront peut-être pas au bûcher.
Messages postés
14869
Date d'inscription
lundi 11 juillet 2005
Statut
Modérateur
Dernière intervention
25 novembre 2020
93
Re,
Question annexe: quels seraient les avantages et inconvénients de passer par un fichier temporaire plutôt qu'un ByteArrayOutputStream?


@+
Buno, Admin CS
L'urgent est fait, l'impossible est en cours. Pour les miracles, prévoir un délai...

Salut !

Je voudrais avoir quelques précisions sur les questions de ton code. Pourquoi voudrais-tu alléger ton thread ? Et quand tu parles du choix de la plus optimisée entre deux méthodes, tu pourrais dire quelles sont les lignes concernées ?

Merci :D

A+

--
Pylouq
Heureux sont ceux qui lisent le Réglement, ils ne finiront peut-être pas au bûcher.
Messages postés
14869
Date d'inscription
lundi 11 juillet 2005
Statut
Modérateur
Dernière intervention
25 novembre 2020
93
Hello,
J'aimerais alléger mon thread car il monte à 90% de CPU, ce qui fait que le UI Thread n'arrive plus à garder la main et je me retrouve avec une ANR "Application Not Responding"

Concernant la question d'optimisation: soit j'alloue mon ZipInputStream en 2 fois, c'est-à-dire en passant par un stream intermédiaire récupérant le résultat HTTP:
responseContent = new BufferedInputStream(response.getEntity().getContent());
zis = new ZipInputStream(responseContent);

Soit je branche directement mon ZipInputStream sur le résultat HTTP:
zis = new ZipInputStream(response.getEntity().getContent());

@+
Buno, Admin CS
L'urgent est fait, l'impossible est en cours. Pour les miracles, prévoir un délai...
Messages postés
14869
Date d'inscription
lundi 11 juillet 2005
Statut
Modérateur
Dernière intervention
25 novembre 2020
93
Hello,
Je relance le sujet. Personnes n'a de remarques sur le code?


@+
Buno, Admin CS
L'urgent est fait, l'impossible est en cours. Pour les miracles, prévoir un délai...
Messages postés
14869
Date d'inscription
lundi 11 juillet 2005
Statut
Modérateur
Dernière intervention
25 novembre 2020
93
Hello,
Merci de ta réponse.
J'ai effectivement résolu le problème car le souci était ailleurs. Néanmoins, je valide ta réponse pour la question que j'avais posée.


@+
Buno, Admin CS
L'urgent est fait, l'impossible est en cours. Pour les miracles, prévoir un délai...