2011-01-15 29 views
13

Bir dosyayı indirmek ve kaydedilen baytları yazdırmak için kütüphaneyi nasıl kullanabilirim?Java apache commons kullanarak dosya indirin?

kullanmayı denedim, ancak bayt veya ilerleme çubuğu gösteremiyorum. Hangi yöntemi kullanmalıyım?

public class download { 
    public static void Download() { 
     URL dl = null; 
     File fl = null; 
     String x = null; 
     try { 
      fl = new File(System.getProperty("user.home").replace("\\", "/") + "/Desktop/Screenshots.zip"); 
      dl = new URL("http://ds-forums.com/kyle-tests/uploads/Screenshots.zip"); 
      OutputStream os = new FileOutputStream(fl); 
      InputStream is = dl.openStream(); 
      CountingOutputStream count = new CountingOutputStream(os); 
      dl.openConnection().getHeaderField("Content-Length"); 
      IOUtils.copy(is, os);//begin transfer 

      os.close();//close streams 
      is.close();//^ 
     } catch (Exception e) { 
      System.out.println(e); 
     } 
    } 

cevap

13

İndirmeden önce toplam bayt sayısını elde etmenin bir yolunu arıyorsanız, bu değeri http yanıtında Content-Length başlığından edinebilirsiniz.

İndirmeden sonra yalnızca son bayt sayısını istiyorsanız, yazdığınız dosya boyutunu kontrol etmek en kolay yoldur. Eğer indirilmiş olan kaç bayt mevcut ilerlemesini görüntülemek istiyorsanız

Ancak, bunu write yöntemleri denir ki her geçen bayt ve güncelleme sayar FileOutputStream sarmak için apache CountingOutputStream uzatmak isteyebilirsiniz ilerleme çubuğu.

Güncelleme İşte

DownloadCountingOutputStream basit bir uygulamasıdır. ActionListener'u kullanmaya alışkın olup olmadığınızdan emin değilim, ancak GUI'yi uygulamak için kullanışlı bir sınıf.

public class DownloadCountingOutputStream extends CountingOutputStream { 

    private ActionListener listener = null; 

    public DownloadCountingOutputStream(OutputStream out) { 
     super(out); 
    } 

    public void setListener(ActionListener listener) { 
     this.listener = listener; 
    } 

    @Override 
    protected void afterWrite(int n) throws IOException { 
     super.afterWrite(n); 
     if (listener != null) { 
      listener.actionPerformed(new ActionEvent(this, 0, null)); 
     } 
    } 

} 

Bu kullanım örneğidir:

public class Downloader { 

    private static class ProgressListener implements ActionListener { 

     @Override 
     public void actionPerformed(ActionEvent e) { 
      // e.getSource() gives you the object of DownloadCountingOutputStream 
      // because you set it in the overriden method, afterWrite(). 
      System.out.println("Downloaded bytes : " + ((DownloadCountingOutputStream) e.getSource()).getByteCount()); 
     } 
    } 

    public static void main(String[] args) { 
     URL dl = null; 
     File fl = null; 
     String x = null; 
     OutputStream os = null; 
     InputStream is = null; 
     ProgressListener progressListener = new ProgressListener(); 
     try { 
      fl = new File(System.getProperty("user.home").replace("\\", "/") + "/Desktop/Screenshots.zip"); 
      dl = new URL("http://ds-forums.com/kyle-tests/uploads/Screenshots.zip"); 
      os = new FileOutputStream(fl); 
      is = dl.openStream(); 

      DownloadCountingOutputStream dcount = new DownloadCountingOutputStream(os); 
      dcount.setListener(progressListener); 

      // this line give you the total length of source stream as a String. 
      // you may want to convert to integer and store this value to 
      // calculate percentage of the progression. 
      dl.openConnection().getHeaderField("Content-Length"); 

      // begin transfer by writing to dcount, not os. 
      IOUtils.copy(is, dcount); 

     } catch (Exception e) { 
      System.out.println(e); 
     } finally { 
      IOUtils.closeQuietly(os); 
      IOUtils.closeQuietly(is); 
     } 
    } 
} 
+0

Bunu kullanmak için apache'yi nasıl uzatabilirim? fl = new File (System.getProperty ("user.home"). değiştirin ("\\", "/") + "/Desktop/Screenshots.zip"); dl = yeni URL ("http://ds-forums.com/kyle-tests/uploads/Screenshots.zip"); OutputStream os = yeni FileOutputStream (fl); InputStream is = dl.openStream(); CountingOutputStream count = new CountingOutputStream (os); dl.openConnection().getHeaderField ("İçerik-Uzunluk"); IOUtils.copy (is, os); // transfer işlemini başlat Doğru mu yapıyorum? – Kyle

+0

Yukarıdaki kodu sorunuza ekleyebilir misiniz? Okuması zor. Yardım etmeye çalışacağım. – gigadot

+0

Kodu ekledim yardım için teşekkür ederim. – Kyle

10

commons-ioIOUtils.copy(inputStream, outputStream) sahiptir. Yani:

OutputStream os = new FileOutputStream(fl); 
InputStream is = dl.openStream(); 

IOUtils.copy(is, os); 

Ve IOUtils.toByteArray(is) bayt almak için kullanılabilir.

Toplam bayt sayısı almak farklı bir öyküdür. Akarsular size herhangi bir toplam vermez - size yalnızca şu anda akışta mevcut olanı verebilirler. Ama bir akış olduğu için, daha fazla gelebilir.

Bu yüzden http, toplam bayt sayısını belirleme özel yöntemine sahiptir. Yanıt başlığında Content-Length bulunur. Yani url.openConnection()'u aramalı ve numaralı telefonu URLConnection nesnesinde aramalısınız. Bayt sayısını dize olarak döndürür. Daha sonra Integer.parseInt(bytesString) kullanın ve toplamınızı alırsınız.

+0

Hmm .. o akışından indirilen bayt görüntülemek için bir yol var? Bakıyorum ama bir yol göremiyorum. Cevap için teşekkürler. – Kyle

+0

'IOUtils.toByteArray (..)' – Bozho

+0

btw, baytların kendileri veya sayıları? – Bozho

İlgili konular