6
votes

Jarenterry.getsize () renvoie -1 lorsque les fichiers JAR sont ouverts en Inverstream de l'URL

J'essaie de lire le fichier à partir du jarinputtream et de la taille du fichier renvoie -1. J'accède à un fichier JAR de l'URL en tant qu'inpurstream. xxx


0 commentaires

3 Réponses :


4
votes

Ceci est un comportement documenté. Javadoc dit que obtient () ...

"renvoie la taille non compressée des données d'entrée, ou -1 si non connu."

Évidemment, il s'agit d'une situation où la taille réelle des données non compressées n'est pas connue. Votre candidature devra simplement faire face à cela.


suivi

Vous avez commenté une autre réponse:

Bien que nous ayons la taille totale du contenu, je pense que la taille du fichier individuel ne peut pas lire les fichiers.

Si vous n'avez pas la taille, vous pouvez toujours lire le fichier et la tamponner à l'aide d'un byteArrayOutPutStream , puis appelez TOBYArraRay () pour extraire les octets tamponnés comme un octet [] . En fait, étant donné que (le commentaire de Tom Hawtin), la taille déclarée pourrait être incorrecte, vous devriez éventuellement le faire quand même, et il suffit de traiter la taille rapportée comme indice ... et simplement l'utiliser comme le BYARTARRAYOutPutStream La capacité initiale de celle-ci.

(Incidemment, le code de votre question semble avoir l'impression d'avoir été destiné à fonctionner de cette façon ... à juger du 2e à la dernière ligne. Le problème est que le reste du code n'utilise pas le Baos Objet.)


3 commentaires

Même si on sait, cela pourrait être un mensonge.


J'essaie de lire le fichier et de la tamponner, maintenant, je suis confronté à un autre problème. La taille d'origine de la jarente et la taille tamponnée est différente et obtient plus d'octets que les attentes. J'ai même vérifié et que le fichier JAR confirmé n'est pas corrompu.


@Reshmadontikeddy - C'est ce que Tom Hawtin signifie quand il dit que la taille pourrait être un mensonge.



1
votes

Cela pourrait être parce que le serveur qui servait cette URL ne fournit pas de contenu. Ceci est similaire à quand vous téléchargez parfois un fichier avec votre navigateur et il dit 33kb / ?? téléchargé (par opposition à 33kb / 2049kb téléchargée).

Pour vérifier rapidement si c'est le cas, vous pouvez faire quelque chose comme ceci: p>

URL url = new URL(yourUrl);
conn = url.openConnection();
size = conn.getContentLength();
if(size < 0) {
    System.out.println("Could not determine file size.");
} else {
    System.out.println(yourUrl + "\nSize: " + size);
}


3 commentaires

Merci Andrei Bodnarescu. La longueur du contenu va bien. Je suis en mesure d'accéder aux noms de fichiers également. Le problème est de trouver la taille du fichier individuel. J'ai besoin de lire ces fichiers d'Inverstream et de mettre dans une hache.


Eh bien, si la longueur du contenu renvoie la valeur correcte, vous ne pouvez pas utiliser cela pour le déterminer (comme, avant d'ouvrir le flux)?


Bien que nous ayons la taille totale du contenu, je pense que la taille du fichier individuel ne peut pas lire les fichiers.



4
votes
byte[] classbytes = null;
JarInputStream jis = new JarInputStream(is);
JarEntry je = null;
String jename = null;
while((je = jis.getNextJarEntry()) != null){
    jename = je.getName();
    if(je.getSize() != -1){
        classbytes = new byte[(int)je.getSize()];
        int len = (int) je.getSize();
        int offset = 0;
        while (offset != len)
            offset += jis.read(classbytes, offset, len - offset);
        classes.put(jename, classbytes);
    } else {
        ByteArrayOutputStream baos = new ByteArrayOutputStream();
        while(true){
            int qwe = jis.read();
            if(qwe == -1) break;
            baos.write(qwe);
        }
        classbytes = baos.toByteArray();
        classes.put(jename, classbytes);
    }
}

1 commentaires

Cela répond à la question. Lorsque la taille est inconnue, elle lit le flux d'entrée dans un flux de sortie de réseau d'octets temporaire jusqu'à la fin du flux d'entrée, puis renvoie la matrice d'octet correspondante. Merci, cela a travaillé pour moi!