Java中的署理道理及署理應用示例。本站提示廣大學習愛好者:(Java中的署理道理及署理應用示例)文章只能為提供參考,不一定能成為您想要的結果。以下是Java中的署理道理及署理應用示例正文
明天再測試Socket編程時,沒法銜接外網。公司用的是Http的署理。上彀搜刮也沒看太懂,所以花了年夜量時光來進修。看了HTTP和TCP協定的關系好,才有所明確。如今能經由過程Socket應用HTTP署理了,成果很簡略,進程卻好難。
1. 先扼要說說HTTP和TCP(詳細內容自行Google,材料許多很全),這裡就講講要點:
HTTP:是運用層協定,是基於傳輸層協定的。
TCP: 是傳輸層協定,是基於收集層協定的。
IP: 是收集層協定。
一個TCP的銜接要停止三次握手(就像轉戶口一樣,不詳說),HTTP只是一個運用協定,也就是相當於一個自界說協定,即其沒有對底層的傳輸方法停止干預,只是對數據內容格局停止了界說。打個比喻,他人說“SB”(你的名字),你答復“是”,僅僅是內容格局,沒有轉變聲響的傳輸方法(經由過程聲波傳送<收集硬件介質>,經由過程兩邊都能聽懂的說話<TCP/IP>)。同理,FTP, Telnet也是一種運用層協定,打個比喻關於FTP,他人說“SB",你答復“哎”,只是格局內容分歧罷了。
2. 熟悉到以上以後,我們再說說HTTP署理,從上可以懂得,HTTP署理辦事器就是如許一台機械:你把一切的HTTP要求(不論是想要求百度照樣Google)都發到這個HTTP署理辦事器,然後這個HTTP署理辦事器要求你要拜訪的終究地址,把呼應回傳給你。這裡還要留意它署理的是HTTP協定,而HTTP又是基於TCP的,也就是說這個辦事器署理的是指定HTTP內容格局的TCP銜接。再說下去也沒意思了,看以下代碼:
//以下地址是署理辦事器的地址
Socket socket = new Socket("10.1.2.188", 80);
//寫與的內容就是遵守HTTP要求協定格局的內容,要求百度
socket.getOutputStream().write(new String("GET http://www.百度.com/ HTTP/1.1\r\n\r\n").getBytes());
byte[] bs = new byte[1024];
InputStream is = socket.getInputStream();
int i;
while ((i = is.read(bs)) > 0) {
System.out.println(new String(bs, 0, i));
}
is.close();
固然在Java中,有Proxy署理上彀的應用,此時應用URL(HTTP)就不觸及Socket(TCP)了,看以下代碼
//設置署理
System.setProperty("http.proxySet", "true");
System.setProperty("http.proxyHost", "10.1.2.188");
System.setProperty("http.proxyPort", "80");
//直接拜訪目標地址
URL url = new URL("http://www.百度.com");
URLConnection con = url.openConnection();
InputStreamReader isr = new InputStreamReader(con.getInputStream());
char[] cs = new char[1024];
int i = 0;
while ((i = isr.read(cs)) > 0) {
System.out.println(new String(cs, 0, i));
}
isr.close();
最初總結一下:
在應用HTTP署理的情況中,
假如應用Socket(TCP)銜接外網,則直接銜接署理辦事器,然後在發送的HTTP要求中指明要轉發到的外網網址。
假如應用URL(HTTP)銜接外網,則須要設置HTTP署理參數或應用Proxy。
OK,明確今後可以隨便應用了,看以下代碼,應用NIO的Socket經由過程HTTP署理拜訪外網的例子:
SocketChannel sc = SocketChannel.open(new InetSocketAddress("10.1.2.188", 80));
sc.write(Charset.forName("utf8").encode("GET http://www.百度.com/ HTTP/1.1\r\n\r\n"));
ByteBuffer buffer = ByteBuffer.allocate(1024);
while (sc.read(buffer) != -1) {
buffer.flip();
System.out.println(Charset.forName("utf8").decode(buffer));
buffer.clear();
}
sc.close();
Java Socket編程中參加署理示例
有些時刻我們的收集不克不及直接銜接到外網, 須要應用http或是https或是socket署理來銜接到外網, 這裡是java應用署理銜接到外網的一些辦法,:辦法一應用體系屬性來完成署理設置, 這類辦法比擬簡略, 然則不克不及對零丁的銜接來設置署理:
public static void main(String[] args) {
Properties prop = System.getProperties();
// 設置http拜訪要應用的署理辦事器的地址
prop.setProperty("http.proxyHost", "192.168.0.254");
// 設置http拜訪要應用的署理辦事器的端口
prop.setProperty("http.proxyPort", "8080");
// 設置不須要經由過程署理辦事器拜訪的主機,可使用*通配符,多個地址用|分隔
prop.setProperty("http.nonProxyHosts", "localhost|192.168.0.*");
// 設置平安拜訪應用的署理辦事器地址與端口
// 它沒有https.nonProxyHosts屬性,它依照http.nonProxyHosts 中設置的規矩拜訪
prop.setProperty("https.proxyHost", "192.168.0.254");
prop.setProperty("https.proxyPort", "443");
// 應用ftp署理辦事器的主機、端口和不須要應用ftp署理辦事器的主機
prop.setProperty("ftp.proxyHost", "192.168.0.254");
prop.setProperty("ftp.proxyPort", "2121");
prop.setProperty("ftp.nonProxyHosts", "localhost|192.168.0.*");
// socks署理辦事器的地址與端口
prop.setProperty("socksProxyHost", "192.168.0.254");
prop.setProperty("socksProxyPort", "8000");
// 設置上岸到署理辦事器的用戶名和暗碼
Authenticator.setDefault(new MyAuthenticator("userName", "Password"));
}
static class MyAuthenticator extends Authenticator {
private String user = "";
private String password = "";
public MyAuthenticator(String user, String password) {
this.user = user;
this.password = password;
}
protected PasswordAuthentication getPasswordAuthentication() {
returnnew PasswordAuthentication(user, password.toCharArray());
}
}
辦法二應用Proxy來對每一個銜接完成署理, 這類辦法只能在jdk 1.5以上的版本應用(包括jdk1.5), 長處是可以零丁的設置每一個銜接的署理, 缺陷是設置比擬費事:
public static void main(String[] args) {
try {
URL url = new URL("http://www.百度.com");
// 創立署理辦事器
InetSocketAddress addr = new InetSocketAddress("192.168.0.254",
8080);
// Proxy proxy = new Proxy(Proxy.Type.SOCKS, addr); // Socket 署理
Proxy proxy = new Proxy(Proxy.Type.HTTP, addr); // http 署理
// 假如我們曉得署理server的名字, 可以直接應用
// 停止
URLConnection conn = url.openConnection(proxy);
InputStream in = conn.getInputStream();
// InputStream in = url.openStream();
String s = IOUtils.toString(in);
System.out.println(s);
} catch (Exception e) {
e.printStackTrace();
}
}