java ज़िप फ़ाइल के अंदर मौजूद फ़ाइलों से सामग्री पढ़ें




zip extract (4)

मैं एक साधारण जावा प्रोग्राम बनाने की कोशिश कर रहा हूं जो ज़िप फ़ाइल के अंदर फ़ाइल (फाइलों) से सामग्री को पढ़ता है और निकालता है। ज़िप फ़ाइल में 3 फाइलें हैं (txt, pdf, docx)। मुझे इन सभी फ़ाइलों की सामग्री को पढ़ने की जरूरत है और मैं इस उद्देश्य के लिए अपाचे टिका का उपयोग कर रहा हूं।

क्या कोई कार्यक्षमता प्राप्त करने के लिए यहां मेरी मदद कर सकता है। मैंने अभी तक यह कोशिश की है लेकिन कोई सफलता नहीं है

सांकेतिक टुकड़ा

public class SampleZipExtract {


    public static void main(String[] args) {

        List<String> tempString = new ArrayList<String>();
        StringBuffer sbf = new StringBuffer();

        File file = new File("C:\\Users\\xxx\\Desktop\\abc.zip");
        InputStream input;
        try {

          input = new FileInputStream(file);
          ZipInputStream zip = new ZipInputStream(input);
          ZipEntry entry = zip.getNextEntry();

          BodyContentHandler textHandler = new BodyContentHandler();
          Metadata metadata = new Metadata();

          Parser parser = new AutoDetectParser();

          while (entry!= null){

                if(entry.getName().endsWith(".txt") || 
                           entry.getName().endsWith(".pdf")||
                           entry.getName().endsWith(".docx")){
              System.out.println("entry=" + entry.getName() + " " + entry.getSize());
                     parser.parse(input, textHandler, metadata, new ParseContext());
                     tempString.add(textHandler.toString());
                }
           }
           zip.close();
           input.close();

           for (String text : tempString) {
           System.out.println("Apache Tika - Converted input string : " + text);
           sbf.append(text);
           System.out.println("Final text from all the three files " + sbf.toString());
        } catch (FileNotFoundException e) {
            // TODO Auto-generated catch block
            e.printStackTrace();
        } catch (IOException e) {
            // TODO Auto-generated catch block
            e.printStackTrace();
        } catch (SAXException e) {
            // TODO Auto-generated catch block
            e.printStackTrace();
        } catch (TikaException e) {
            // TODO Auto-generated catch block
            e.printStackTrace();
        }
    }
}

हालात की स्थिति के कारण, लूप कभी नहीं तोड़ सकता है:

while (entry != null) {
  // If entry never becomes null here, loop will never break.
}

null जांच के बजाय, आप इसे आजमा सकते हैं:

ZipEntry entry = null;
while ((entry = zip.getNextEntry()) != null) {
  // Rest of your code
}

इसे प्राप्त करने का मेरा तरीका ज़िपपूटस्ट्रीम रैपिंग क्लास बनाकर है जो संभाल लेगा जो केवल वर्तमान प्रविष्टि की धारा प्रदान करेगा:

रैपर वर्ग:

public class ZippedFileInputStream extends InputStream {

    private ZipInputStream is;

    public ZippedFileInputStream(ZipInputStream is){
        this.is = is;
    }

    @Override
    public int read() throws IOException {
        return is.read();
    }

    @Override
    public void close() throws IOException {
        is.closeEntry();
    }

}

इसका उपयोग:

    ZipInputStream zipInputStream = new ZipInputStream(new FileInputStream("SomeFile.zip"));

    while((entry = zipInputStream.getNextEntry())!= null) {

     ZippedFileInputStream archivedFileInputStream = new ZippedFileInputStream(zipInputStream);

     //... perform whatever logic you want here with ZippedFileInputStream 

     // note that this will only close the current entry stream and not the ZipInputStream
     archivedFileInputStream.close();

    }
    zipInputStream.close();

इस दृष्टिकोण का एक लाभ: इनपुटस्ट्रीम को उन तरीकों के लिए एक तर्क के रूप में पारित किया जाता है जो उन्हें संसाधित करते हैं और उन तरीकों के साथ इनपुट स्ट्रीम को तत्काल बंद करने की प्रवृत्ति होती है।


यदि आप सोच रहे हैं कि प्रत्येक ZipEntry से फ़ाइल सामग्री कैसे प्राप्त करें, यह वास्तव में काफी सरल है। नमूना कोड यहां दिया गया है:

public static void main(String[] args) throws IOException {
    ZipFile zipFile = new ZipFile("C:/test.zip");

    Enumeration<? extends ZipEntry> entries = zipFile.entries();

    while(entries.hasMoreElements()){
        ZipEntry entry = entries.nextElement();
        InputStream stream = zipFile.getInputStream(entry);
    }
}

एक बार आपके पास इनपुटस्ट्रीम हो जाने के बाद भी आप इसे पढ़ सकते हैं।


नमूना कोड जिसका उपयोग आप टिका को आपके लिए कंटेनर फाइलों का ख्याल रखने के लिए कर सकते हैं। http://wiki.apache.org/tika/RecursiveMetadata

फॉर्म जो मैं बता सकता हूं, स्वीकार्य समाधान उन मामलों के लिए काम नहीं करेगा जहां नेस्टेड ज़िप फ़ाइलें हैं। हालांकि, टीका भी ऐसी परिस्थितियों का ख्याल रखेगी।





apache-tika