2012-07-11 16 views
6

का उपयोग कर एक टीएआर फ़ाइल को कैसे खोलें I ".tar.gz" फ़ाइलों को संकुचित और असम्पीडित करने के लिए अपाचे कॉमन्स 1.4.1 लाइब्रेरी का उपयोग कर रहा हूं।अपाचे कॉमन्स

मुझे अंतिम बिट में परेशानी हो रही है - TarArchiveInputStream को FileOutputStream में परिवर्तित करना।

अजीब तरह से पर्याप्त है, यह इस लाइन पर तोड़ रहा है: C:

FileOutputStream fout = new FileOutputStream(destPath); 

destPath की एक विहित पथ के साथ एक फ़ाइल है \ दस्तावेज़ और \ My Documents सेटिंग्स \ प्रशासक \ JavaWorkspace \ BackupUtility \ untarred \ टेस्ट \ subdir \ testinsub.txt

त्रुटि का उत्पादन:

Exception in thread "main" java.io.IOException: The system cannot find the path specified 

कोई विचार यह क्या हो सकता है? और यह पथ खोजने में सक्षम क्यों नहीं है?

मैं नीचे दी गई पूरी विधि को जोड़ रहा हूं (जिनमें से अधिकांश here से उठाया गया है)।

private void untar(File dest) throws IOException { 
    dest.mkdir(); 
    TarArchiveEntry tarEntry = tarIn.getNextTarEntry(); 
    // tarIn is a TarArchiveInputStream 
    while (tarEntry != null) {// create a file with the same name as the tarEntry 
     File destPath = new File(dest.toString() + System.getProperty("file.separator") + tarEntry.getName()); 
     System.out.println("working: " + destPath.getCanonicalPath()); 
     if (tarEntry.isDirectory()) { 
      destPath.mkdirs(); 
     } else { 
      destPath.createNewFile(); 
      FileOutputStream fout = new FileOutputStream(destPath); 
      tarIn.read(new byte[(int) tarEntry.getSize()]); 
      fout.close(); 
     } 
     tarEntry = tarIn.getNextTarEntry(); 
    } 
    tarIn.close(); 
} 
+0

यह पूछने के लिए शर्मिंदा है, लेकिन मैंने आपके कोड नमूने का उपयोग करने की कोशिश की और इसे एक विशेष 'gzip' फ़ाइल' के साथ काम करने के लिए देखा जो मैं काम कर रहा था। यह इनपुटस्ट्रीम पर पढ़ने वाली सामग्री को देखते हुए 'fout.write (...) 'के किसी भी कॉल के बिना कैसे काम करता है? [Answer @ user1894600 सुझाता है] में (http://stackoverflow.com/a/14211580/320399), उसे स्पष्ट रूप से 'लिखना (...)' कॉल करना होगा और बाइट सरणी प्रदान करना होगा जिसे स्मृति में पढ़ा गया है। – blong

उत्तर

5

सामान्य अंक की एक जोड़ी, क्यों, जहां एक perfectly usable constructor जहां की File आप बना सकते हैं और एक माता पिता फ़ाइल देना चाहता हूँ नाम निर्धारित कर सकते हैं File निर्माता के साथ वूडू करते हैं?

दूसरा, मुझे यह भी सुनिश्चित नहीं है कि विंडोज़ में पथों में रिक्त स्थान कितने खाली हैं। यह आपकी समस्याओं का कारण हो सकता है। निर्माता मैं उपर्युक्त उपयोग करने का प्रयास करें और देखें कि यह एक फर्क नहीं पड़ता:। File destPath = new File(dest, tarEntry.getName()); (यह मानते हुए कि File dest एक उचित फ़ाइल है, और मौजूद है और आप के द्वारा पहुँचा जा सकता है

तीसरा, इससे पहले कि आप एक File वस्तु के साथ कुछ भी कर आप की जाँच करनी चाहिए यदि वह मौजूद है और अगर यह सुलभ है। यही कारण है कि अंत में यहाँ आप समस्या का पता लगाने जाएगा।

+0

आपकी प्रतिक्रिया के लिए धन्यवाद। मैंने मॉड्यूल को फिर से लिखने का फैसला किया है और यह बहुत अच्छा काम करता है। मैंने फ़ाइल ऑब्जेक्ट के साथ नहीं खेलने के बारे में आपकी सलाह ली है, और इसलिए मैं आपके उत्तर को सही (एक सिद्धांत के आधार पर) के रूप में चिह्नित करने जा रहा हूं – Redandwhite

+0

खुशी ने मदद की, और उम्मीद है कि यह सब अंत में ठीक काम करेगा। शुभकामनाएँ :) – posdef

+0

मैं एक .tar फ़ाइल को untar करने के लिए एक ही कोड का उपयोग कर रहा हूँ .tar.gz नहीं। और मैं इस लाइन से 'नई फ़ाइल (dest, tarEntry.getName()) से प्राप्त कर रहा हूं, फ़ाइल सामग्री फ़ाइल नाम नहीं है। .tar –

13

आपका कार्यक्रम जावा ढेर अंतरिक्ष त्रुटि है। तो मुझे लगता है एक छोटे से बदलाव की जरूरत है। कोड है ...

public static void uncompressTarGZ(File tarFile, File dest) throws IOException { 
    dest.mkdir(); 
    TarArchiveInputStream tarIn = null; 

    tarIn = new TarArchiveInputStream(
       new GzipCompressorInputStream(
        new BufferedInputStream(
         new FileInputStream(
          tarFile 
         ) 
        ) 
       ) 
      ); 

    TarArchiveEntry tarEntry = tarIn.getNextTarEntry(); 
    // tarIn is a TarArchiveInputStream 
    while (tarEntry != null) {// create a file with the same name as the tarEntry 
     File destPath = new File(dest, tarEntry.getName()); 
     System.out.println("working: " + destPath.getCanonicalPath()); 
     if (tarEntry.isDirectory()) { 
      destPath.mkdirs(); 
     } else { 
      destPath.createNewFile(); 
      //byte [] btoRead = new byte[(int)tarEntry.getSize()]; 
      byte [] btoRead = new byte[1024]; 
      //FileInputStream fin 
      // = new FileInputStream(destPath.getCanonicalPath()); 
      BufferedOutputStream bout = 
       new BufferedOutputStream(new FileOutputStream(destPath)); 
      int len = 0; 

      while((len = tarIn.read(btoRead)) != -1) 
      { 
       bout.write(btoRead,0,len); 
      } 

      bout.close(); 
      btoRead = null; 

     } 
     tarEntry = tarIn.getNextTarEntry(); 
    } 
    tarIn.close(); 
} 

अच्छा एल uck

+0

के अंदर फ़ाइल नाम प्राप्त करने के लिए मैं क्या कर सकता हूं, तो हीप स्पेस त्रुटि उत्पन्न होगी क्योंकि बाइट सरणी संभावित रूप से बहुत बड़ी है जब इसे 'बाइट [] btoRead = new byte [(int) tarEntry.getSize() ]; '? – blong

+1

उत्कृष्ट प्रतिक्रिया। हालांकि, निम्नलिखित 'deskPath.createNewFile();' मूल निर्देशिका बनाने के लिए संशोधित किया जाना चाहिए 'if (! DestPath.getParentFile()।मौजूद है()) { destPath.getParentFile()। mkdirs(); } destPath.createNewFile(); ' –

संबंधित मुद्दे