Tanpa pustaka pihak ketiga, klien unduhan file http minimal diimplementasikan sepenuhnya berdasarkan soket java. Demonstrasi lengkap tentang cara mengimplementasikan header permintaan HTTP untuk mengunduh file melalui soket untuk mengirim paket respons http (header respons, badan respons) dari soket dan parse dan menyimpan konten file. Cara mewujudkan UI Refresh melalui Swingwork untuk menampilkan kemajuan unduhan secara real time.
Pertama -tama lihat bagian UI:
【Tambahkan unduhan】 Tombol:
Klik kotak input URL pop-up. Setelah pengguna ingin mengunduh URL file ke kotak input, klik tombol [OK] untuk memulai.
unduh
【Bersihkan Lengkap】 Tombol:
Bersihkan semua daftar file yang diunduh
Status unduhan file dibagi menjadi beberapa jenis berikut:
paket com.gloomyfish.socket.tutorial.http.download; public enum downloadstatus {not_started, in_process, selesai, kesalahan} Bagian UI terutama dilakukan dengan menggunakan komponen ayunan. Klik [Tambah Unduh] untuk menjalankan kode sebagai berikut:
Dialog JDialog terakhir = JDialog baru (ini, "Tambahkan tautan file", true); dialog.getContentPane (). setLayout (borderlayout baru ()); // dialog.setsize (dimensi baru (400.200)); Panel Urlfilepanel Akhir = Urlfilepanel baru (); panel.setuplistener (actionListener () {@Override public void actionPerformed (actionEvent e) {if ("ok" .equals (e.getActionCommand ())) {if (panel.validateInput ()) {downloadDetailstatusInfomodel Data = new downloadDetailSTATSTATSTATSTAT ( Tablemodel.getData (). Add (data); dialog.getContentPane (). Tambah (panel, borderlayout.center); dialog.pack (); pusat (dialog); dialog.setVisible (true); Kode yang dieksekusi oleh tombol [CLEAR Complete] adalah sebagai berikut:
private void clearownloaded () {list <downloadDetailStatusInfomodel> downloadList = new ArrayList <ROWNLOVERDetailStatusInfomodel> (); untuk (downloadDetailStatusInfomodel filestatus: tablemodel.getData ()) {if (filestatus.getStatus (). tostring (). setara (downloadstatus.toPleTed.toString ())) {downloudlist.add (filestatus); }} tablemodel.getData (). RemoveAll (DownloadedList); Refreshui (); } Kode untuk memusatkan komponen JFrame adalah sebagai berikut:
pusat void statis publik (jendela w) {dimensi us = w.getsize (); Dimensi mereka = toolkit.getDefaultToolKit (). Getscreensize (); int newx = (mereka.width - us.width) / 2; int newy = (them.height - us.height) / 2; w.setlocation (newx, newy); }Bagian Implementasi Protokol HTTP:
Ikhtisar: Struktur Dasar dan Penjelasan HEader Permintaan HTTP dan Paket Header yang sesuai
Permintaan HTTP: Paket Permintaan HTTP standar seperti
Mungkin ada beberapa header permintaan, dan tubuh pesan tidak ada, yang tidak diperlukan. Format baris permintaan adalah sebagai berikut:
Request-line = Metode SP Request-URI SPHTTP-Versi CRLF memberikan contoh sebagai berikut:
Request-line = dapatkan http://www.w3.org/pub/www/theproject.htmlhttp/1.1/r/n
Di mana SP mewakili spasi, CRLF mewakili jeda jalur kembali carriage/r/n
Ketika Anda ingin mengunggah file, gunakan posting untuk mengisi data ke dalam tubuh pesan. Kirim satu
Pesan permintaan HTTP sederhana adalah sebagai berikut:
Respons HTTP: Pesan respons HTTP standar adalah sebagai berikut
Hal pertama yang Anda dapatkan adalah garis status, formatnya adalah sebagai berikut:
Status-line = http-versi SP status-codesp Alasan-frase-frase CRLF, contoh sederhana dari garis status adalah sebagai berikut: status-line = http/1.1 200 OK secara umum, favorit semua orang adalah kode status yang akan memberi Anda banyak petunjuk, yang paling umum adalah kode status seperti 404, 500, dll. Makna dari kode status dapat diserahkan kepada penjelasan yang diserahkan. Hal terpenting untuk mengunduh file adalah memeriksa panjang konten dan tipe konten di header respons HTTP.
Panjang dan jenis file dinyatakan secara terpisah. Yang lain, seperti menerima rentang, mewakili berapa banyak dari berapa banyak byte yang diterima. Mungkin digunakan dalam unduhan multi-utas. Setelah memahami format paket dari permintaan dan respons HTTP, kami dapat menguraikan konten dalam format paket melalui soket, mengirim dan membaca permintaan dan respons HTTP. Langkah -langkah tertentu
sebagai berikut:
1. Menetapkan koneksi soket berdasarkan URL file yang dimasukkan oleh pengguna
Url url = url baru (fileInfo.getFileUrl ()); Host string = url.getHost (); int port = (url.getport () == -1)? url.getDefaultport (): url.getport (); System.out.println ("Host Name =" + Host); System.out.println ("port =" + port); System.out.println ("File URI =" + url.getFile ()); // Buat soket dan mulailah untuk membangun soket saluran permintaan soket = soket baru (); Socketaddress alamat = inetsocketAddress baru (host, port); socket.connect (alamat); Kelas URL digunakan untuk mengubah string URL yang dimasukkan oleh pengguna menjadi URL yang lebih mudah diurai.
2. Bangun permintaan http
BufferedWriter BufferedWriter = BufferedWriter baru (outputStreamWriter baru (socket.getoutputStream (), "utf8")); String requeststr = "get" + url.getFile () + "http/1.1/r/n"; // baris permintaan // buat header permintaan - buat header permintaan http (header permintaan) string hostheader = "host:" + host + "/r/n"; String accepTheader = "AcCET: TEXT/HTML, Aplikasi/XHTML+XML, Aplikasi/XML; q = 0.9,*/*; q = 0.8/r/n"; String charsetHeader = "Accept-Charset: GBK, UTF-8; q = 0,7,*; q = 0,3/r/n"; String languageheader = "penerimaan-bahasa: zh-cn, zh; q = 0,8/r/n"; String KeepHeader = "Koneksi: Tutup/R/N";
3. Kirim Permintaan HTTP
// Kirim permintaan http bufferedwriter.write (requeststr); bufferedwriter.write (hostheader); bufferedwriter.write (acceptheader); BufferedWriter.Write (CharsetHeader); BufferedWriter.Write (LanguageHeader); BufferedWriter.write (KeepHeader); bufferedwriter.write ("/r/n"); // Permintaan pesan header mengirimkan bendera akhir bufferedwriter.flush (); 4. Terima respons http dan konten parse, dan tulis ke file yang dibuat
// Bersiaplah untuk menerima header respons HTTP dan parse customDataInputStream input = new CustomDataInputStream (socket.getInputStream ()); File myfile = file baru (fileInfo.getStoreLocation () + file.separator + fileInfo.getFileName ()); Konten String = NULL; Httpresponseaderparser responseHeaderer = httpresponseaderparser baru (); BufferedOutputStream output = baru bufferedOutputStream (FileOutputStream baru (myFile)); boolean hasdata = false; while ((content = input.readHttpresponseaderLine ())! = null) {System.out.println ("Kontak header respons ->>" + konten); responseHeader.addresponseHeaderline (konten); if (content.length () == 0) {hasData = true; } if (hasData) {int totalBytes = responseHeader.getFileLength (); if (totalBytes == 0) break; // Tidak ada Badan Respons dan Data Int Offset = 0; byte [] mydata = null; if (totalBytes> = 2048) {mydata = byte baru [2048]; } else {mydata = byte baru [totalBytes]; } int numofbytes = 0; while ((numofbytes = input.read (mydata, 0, mydata.length))> 0 && offset <totalBytes) {offset += numofbytes; float p = ((float) offset) / ((float) totalBytes) * 100.0f; if (offset> totalBytes) {numofbytes = numofbytes + totalBytes - offset; p = 100.0F; } output.write (mydata, 0, numofbytes); UpdateStatus (P); } hasdata = false; merusak; }} Kode Parser Header Respons HTTP Sederhana dari kelas HTTPResponseaderParser adalah sebagai berikut:
paket com.gloomyfish.socket.tutorial.http.download; impor java.util.hashmap; impor java.util.map; /** * Ini dapat menguraikan header entitas, head respons * dan baris respons <kode status, charset, dll ...> * merujuk ke rfc2616. Untuk header respons HTTP, silakan lihat dokumen RFC, yang dijelaskan secara rinci! Lai */ kelas publik httpresponsheaderparser {public final static string content_length = "content-length"; String statis final publik content_type = "tipe konten"; string statis akhir publik accept_ranges = "accetp-ranges"; peta pribadi <string, string> headermap; public httpresponseaderParser () {headermap = new HashMap <string, string> (); }/** * <p> Dapatkan pasangan nilai tombol header respons </p> * @param responseHeaderline */public void addResponseHeaderline (string responseHeaderline) {if (responseHeaderline.contains (":")) {string [] keyValue = responseHeadline.split ("); if (keyValue [0] .equalSignorecase (content_length)) {headermap.put (content_length, keyValue [1]); } else if (keyValue [0] .equalSignorecase (content_type)) {headermap.put (content_type, keyValue [1]); } else {headermap.put (keyValue [0], keyValue [1]); }}} public int getFileLength () {if (headerMap.get (content_length) == null) {return 0; } return integer.parseint (headermap.get (content_length)); } public string getFileType () {return headermap.get (content_type); } peta publik <string, string> getAllHeaders () {return headermap; }}Di atas adalah semua tentang artikel ini, saya harap akan sangat membantu bagi semua orang untuk belajar pemrograman Java.