想必我们大家都遇到过在百度,谷歌中搜索过不少东西那我们一定见过豆瓣电影类似的;
其中http是HTTP网络协议:HTTP 就是目前使用最广泛的Web应用程序使用的基础协议,例如,浏览器访问网站,手机App访问后台服务器,都是通过 HTTP 协议实现的。 HTTP 是 HyperText Transfer Protocol 的缩写,翻译为超文本传输协议,它是基于 TCP 协议之上的一种请求-响应协议。
HTTP 请求的格式是固定的,它由 HTTP Header 和 HTTP Body 两部分构成。第一行总是 请求方法 路径 HTTP版本 :例如, GET / HTTP/1.1 表示使用 GET 请求,路径是 / ,版本是 HTTP/1.1 。 后续的每一行都是固定的 Header: Value 格式,我们称为 HTTP Header ,服务器依靠某些特定的 Header 来识别客户端请求,例 如: Host :表示请求的域名,因为一台服务器上可能有多个网站,因此有必要依靠 Host 来识别请求是发给哪个网站的; User-Agent :表示客户端自身标识信息,不同的浏览器有不同的标识,服务器依靠 User-Agent 判断客户端类型是 IE 还是 Chrome ,是 Firefox 还是一个 Python 爬虫; Accept :表示客户端能处理的 HTTP 响应格式, */* 表示任意格式, text/* 表示任意文本, image/png 表示PNG格式的图 片; Accept-Language :表示客户端接收的语言,多种语言按优先级排序,服务器依靠该字段给用户返回特定语言的网页版本。
URL:统一定位资源符:
URL ur1 = new URL("https://WWW.163.com/index.html");
打开链接:?
HttpURLConnection connection = (HttpURLConnection)imger.openConnection();
设置请求方式GET:
connection.setRequestMethod("GET");
设置请求属性:(防止在访问时被网页识别出来伪装成为一个用户)
connection.setRequestProperty("User-Agent","Mozilla/5.0 (Windows NT 10.0; WOW64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/92.0.4515.131 Safari/537.36 SLBrowser/8.0.0.3161 SLBChan/8");
完整读取网页图片:
package liuzhen08;
import java.io.BufferedInputStream;
import java.io.BufferedOutputStream;
import java.io.BufferedReader;
import java.io.FileOutputStream;
import java.io.IOException;
import java.io.InputStreamReader;import java.io.OutputStream;
import java.net.HttpURLConnection;
import java.net.URL;
import java.nio.Buffer;
import java.nio.charset.StandardCharsets;
import org.jsoup.Jsoup;
import org.jsoup.nodes.Document;
import org.jsoup.nodes.Element;
public class woker03 {
public static void main(String[] args) {
try {
URL imger = new URL("https://movie.douban.com/");
//打开链接
HttpURLConnection connection = (HttpURLConnection)imger.openConnection();
//设置请求方式GET
connection.setRequestMethod("GET");
//设置请求属性
connection.setRequestProperty("User-Agent","Mozilla/5.0 (Windows NT 10.0; WOW64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/92.0.4515.131 Safari/537.36 SLBrowser/8.0.0.3161 SLBChan/8");
BufferedReader read = new BufferedReader(new InputStreamReader(connection.getInputStream(),StandardCharsets.UTF_8));
String line = null;
while((line = read.readLine())!=null) {
line = line.trim();
//判断当前行是否包含海报图片路径
if(line.contains("<img") && line.contains("https://img") && line.contains(".jpg")) {
//System.out.println(line);
//使用jsoup解析html
//JSoUP类的作用进行源解析
//Document类:网页文档(包含解析到的所有标签)
//Elements类:若干元素Element形成的集合(继承自ArrayList)
//提取图片路径srcj 电影名称altj
String srcj ="",altj="";
//解析成Document对象
Document doc = Jsoup.parse(line);
//从Document中获取名称为img的所有标签元素(Elements)
//从所有代表img的Elements元素集合中获取第一个
Element img = doc.getElementsByTag("img").first();
//获取img标签元素的src属性和alt属性
srcj = img.attr("src");
altj = img.attr("alt");
//图片路经
// int be = line.indexOf("https://img");
// int end = line.indexOf(".jpg") +4;
// String src = line.substring(be,end);
// //名字路经
// int a = line.indexOf("alt")+5;
// int s =line.indexOf("\"",a);
// String alt = line.substring(a,s);
// System.out.println(alt);
// System.out.println(src);
//读取图片
URL imsge = new URL(srcj);
HttpURLConnection imgert =(HttpURLConnection) imsge.openConnection();
try {
BufferedInputStream bis = new BufferedInputStream(imgert.getInputStream());
BufferedOutputStream bos = new BufferedOutputStream(new FileOutputStream("d:\\text\\电影图片"+altj+".jpg"));
//边读边写
byte [] buff = new byte[1024];
int len = -1;
while((len = bis.read(buff))!=-1) {
bos.write(buff,0,len);
}
} catch (Exception e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
}
}
} catch (Exception e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
}
}
其中需要注意的是:因为 HTTP 协议是一个请求-响应协议,客户端在发送了一个 HTTP 请求后,必须等待服务器响应后,才能发送下一个请求,这样一来,如果某个 响应太慢,它就会堵住后面的请求。所以,为了进一步提速, HTTP/2.0 允许客户端在没有收到响应的时候,发送多个 HTTP 请求,服务器返回 响应的时候,不一定按顺序返回,只要双方能识别出哪个响应对应哪个请求,就可以做到并行发送和接收
响应行:响应的第一行总是 HTTP版本 响应代码 响应说明 :例如, HTTP/1.1 200 OK 表示版本是 HTTP/1.1 ,响应代码是 200 ,响应说明是 OK 。客户端只依赖响应代码判断 HTTP 响应是否成功。 HTTP 有固定的响应代码:
1xx:表示一个提示性响应,例如101表示将切换协议,常见于WebSocket连接;
2xx:表示一个成功的响应,例如200表示成功,206表示只发送了部分内容;
3xx:表示一个重定向的响应,例如301表示永久重定向,303表示客户端应该按指定路径重新发送请求;
4xx:表示一个因为客户端问题导致的错误响应,例如400表示因为Content-Type等各种原因导致的无效请求,404表示指定的路 径不存在;
5xx:表示一个因为服务器问题导致的错误响应,例如500表示服务器内部故障,503表示服务器暂时无法响应。
可以Java中模拟http响应:
package liuzhen08;
import java.io.BufferedReader;
import java.io.BufferedWriter;
import java.io.IOException;
import java.io.InputStreamReader;
import java.io.OutputStreamWriter;
import java.io.Writer;
import java.net.ServerSocket;
import java.net.Socket;
import java.nio.charset.StandardCharsets;
import java.util.UUID;
public class work01 {
public static void main(String[] args) {
try {
ServerSocket serve = new ServerSocket(8080);
while(true) {
Socket socket = serve.accept();//等待链接·
//读取用户请求
// BufferedReader buf = new BufferedReader(new InputStreamReader(socket.getInputStream(),
// StandardCharsets.UTF_8)) ;
// String line = null;
// while((line = buf.readLine())!=null) {
// System.out.println(line);
//
// }
//模拟服务器的响应
try(BufferedWriter write = new BufferedWriter(new OutputStreamWriter(
socket.getOutputStream()));){
//响应头
write.write("HTTP/1.1 200 Ok");
write.newLine();
write.newLine();
//相应内容
write.write(UUID.randomUUID().toString());
System.out.println(write);
}
}
} catch (IOException e) {
e.printStackTrace();
}
}
}
|