Existe-t-il un moyen de vérifier si l'InputStream a été gzippé ? Voici le code :
public static InputStream decompressStream(InputStream input) {
try {
GZIPInputStream gs = new GZIPInputStream(input);
return gs;
} catch (IOException e) {
logger.info("Input stream not in the GZIP format, using standard format");
return input;
}
}
J'ai essayé de cette façon mais cela ne fonctionne pas comme prévu - les valeurs lues à partir du flux sont invalides. EDITION : J'ai ajouté la méthode que j'utilise pour compresser les données :
public static byte[] compress(byte[] content) {
ByteArrayOutputStream baos = new ByteArrayOutputStream();
try {
GZIPOutputStream gs = new GZIPOutputStream(baos);
gs.write(content);
gs.close();
} catch (IOException e) {
logger.error("Fatal error occured while compressing data");
throw new RuntimeException(e);
}
double ratio = (1.0f * content.length / baos.size());
if (ratio > 1) {
logger.info("Compression ratio equals " + ratio);
return baos.toByteArray();
}
logger.info("Compression not needed");
return content;
}
0 votes
Où se trouve le
InputStream
proviennent-ils ? DeURLConnection#getInputStream()
? Dans un protocole un peu décent comme HTTP, l'utilisateur final devrait déjà être informé d'une manière ou d'une autre que le contenu est gzippé.0 votes
Étant donné que GZIP a un CRC de 32 bits, je trouve cela surprenant. Un flux corrompu devrait au moins lever une exception à la fin.
0 votes
Je me demande si l'OP veut dire que les valeurs lues à partir du flux APRÈS l'apparition de l'IOException ne sont pas valides... ce qui serait logique car le constructeur de GZIPInputStream aurait consommé certains des octets du flux.
0 votes
Les valeurs sont corrompues après l'apparition de l'exception IOException. L'InputStream provient de HttpURLConnection#getInputStream()
0 votes
Exact, c'est parce que le GZipInputStream lit les octets du flux d'entrée original. Vous devez donc mettre en mémoire tampon le flux d'entrée comme indiqué dans la réponse ci-dessous.
1 votes
La solution générale consiste donc à créer un BufferedInputStream enveloppant le flux d'entrée original, puis à appeler "mark" pour marquer le début du flux. Ensuite, enveloppez un GZipInputStream autour de celui-ci. Si aucune exception ne se produit, retournez le GZipInputStream. Si une exception se produit, appelez "reset" et renvoyez le BufferedInputStream.