1.1、基本概念
web开发:
- 静态web
- html,css
- 提供给所有人看的数据始终不会发生变化
- 动态web
- 提供给所有人看的数据会发生变化,每个人在不同的时间,不同的地点看到的信息各不相同
- 技术栈:Serviet/JSP, ASP, PHP
- 在java中,动态web资源开发的技术统称为javaWeb
1.2 web应用程序
web应用程序,可以提供浏览器访问的程序:
- a.html 、b.html、多个web资源,这些web资源可以被外界访问
- 你们能访问到的任何一个页面或者资源,都存在于这个世界的某一个角落
- URL
- 这个统一的web资源都会被放在同一个文件夹下,web应用程序—Tomcat:服务器
- 一个web应用由多个部分组成(静态web,动态web)
- html,css,js
- jsp,serviet
- java程序
- jar包
- 配置文件(Properties)
- web应用程序编写完毕后,若想提供给外界访问,需要一个服务器来统一管理
1.3、静态web
-
htm,html都是网页的后缀,如果服务器上一直存在这些东西,我们就可以直接进行读取
-
[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-OLREJtRe-1634477384975)(JavaWeb.assets/image-20211006110131835.png)]
-
静态web存在的缺点
- Web页面无法动态更新,所有用户看到都是同一个页面
- 轮播图,点击特效:伪动态
- JavaScript
- VBScript
- 它无法和数据库交互(数据无法持久化,用户无法交互)
- Web页面无法动态更新,所有用户看到都是同一个页面
动态web
- 页面会动态展示:“”Web的页面展示的效果因人而异“
[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-JS9z9rBe-1634477384977)(JavaWeb.assets/image-20211006111132265.png)]
- 缺点
- 假如服务器的动态web资源出现了错误,我们需要重写编写我们的后台程序,重新发布;
- 停机维护
- 假如服务器的动态web资源出现了错误,我们需要重写编写我们的后台程序,重新发布;
- 优点
- Web页面可以动态更新,所有用户看到都不是同一个页面
- 它可以和数据库交互(数据持久化:注册,商品信息,用户信息)
2、web服务器
2.1技术讲解
ASP
- 微软:国内最早流行的
- 在HTML中嵌入了VB的脚本、ASP+COM;
PHP
- PHP开发速度快,功能很强大,跨平台,代码很简单
- 无法承载大访问量的情况,局限性
JSP/Serviet:
B/S:浏览器和服务器
C/S:客户端和服务器
- sun公司主推的B/S架构
- 基于java语言的
- 可以承载三高问题(高并发,高可用,高性能)
2.2、web服务器
服务器是一种被动的操作,用来处理用户的一些请求和给用户一些相应信息;
IIS:微软的;ASP…Windows自带
Tomcat:
- 下载tomcat:
- 安装 or 解压
- 了解配置文件及目录结构
- 这个东西的作用
3、Tomcat
3.1 安装tomcat
3.2Tomcat启动和配置
启动
-
启动目录:C:\Users\ljj\Desktop\JAVA\Tomcat\apache-tomcat-9.0.54\bin
-
启动文件:startup.bat
-
关闭文件:shutdown.bat
配置:
- tomcat默认端口号:8080
- masql:3306
- http:80
- https:443
<Connector port="8080" protocol="HTTP/1.1"
connectionTimeout="20000"
redirectPort="8443" />
可以配置主机的名称
- 默认主机名为:locathost:127.0.0.1
- 默认网站应用存放的位置:webapps
<Host name="localhost" appBase="webapps"
unpackWARs="true" autoDeploy="true">
谈谈网站是如何进行访问的
-
输入一个域名:回车
-
检查本机的host配置文件下有没有这个域名映射:
-
有:直接返回对应的ip地址,这个地址中,有我们需要访问的web程序,可以直接访问
-
没有:去DNS服务器上去找,找到的话就返回,找不到就报错
[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-W5SMzmIu-1634477384979)(JavaWeb.assets/image-20211006140229484.png)]
-
3.3、发布一个网站
4、Http
超文本传输协议(Hyper Text Transfer Protocol,HTTP)是一个简单的请求-响应协议,它通常运行在TCP之上。
- 文本:html,字符串…
- 超文本:图片、音乐、视频、定位、地图…
Https:安全的
- 443
4.1 Http请求
- 客户端发请求给服务器
百度:
Request URL: https://www.baidu.com/ 请求地址
Request Method: GET //get方法/post方法
Status Code: 200 OK //状态码
Remote Address: 14.215.177.38:443
Referrer Policy: unsafe-url
1、请求行
- 请求行中的请求方式:GET
- 请求方式:Get,Post
- get:请求能够携带的参数比较少,大小有限制,会在浏览器的url地址栏显示数据类容,不安全但高效
- post:请求能够携带的参数没显示,大小没限制,不会在浏览器的url地址栏显示数据类容,安全但高效
2、请求头
Accept: //告诉浏览器,它所支持的数据类型
Accept-Encoding: gzip, deflate, br//支持的编码格式
Accept-Language: zh-CN,zh;q=0.9 //告诉浏览器的语言环境
Cache-Control //缓存控制
Connection: keep-alive //告诉浏览器请求完成是断开还是保持连接
4.2 Http响应
- 服务器响应给客户端
百度服务器响应
Cache-Control: private //Cache-Control缓存控制
Connection: keep-alive //保持连接
Content-Encoding: gzip //编码
Content-Type: text/html;charset=utf-8 //类型
1、响应体
Accept: //告诉浏览器,它所支持的数据类型
Accept-Encoding: gzip, deflate, br//支持的编码格式
Accept-Language: zh-CN,zh;q=0.9 //告诉浏览器的语言环境
Cache-Control //缓存控制
Connection: keep-alive //告诉浏览器请求完成是断开还是保持连接
Refreush: //告诉客户端,多久刷新一次
Location://让网页重新定位
2、响应状态码
200:响应成功
3xx:请求重定向
- 重定向:你重新到我给你新位置去
4xx:找不到资源
- 资源不存在
5xx:服务器代码错误
- 502:网关错误
5、Maven
为啥要学Maven
-
在javaweb开发中,需要使用大量的jar包,我们要手动导入
-
如何能够让一个东西自动帮我导入和配置这个jar包
由此,Maven诞生了
5.1 Maven项目架构管理工具
用法:方便导入jar包
Maven的核心思想:约定大于配置
- 有约束不要违反
Maven会规定好你该如何编写我们的java代码,必须要按照这个规范
5.2下载安装Maven
5.3配置环境变量
5.4修改阿里云镜像
- 镜像:mirrors
- 作用:加速下载
- 国内建议用阿里云的镜像
5.5本地仓库
在本地的仓库,远程仓库;
建立一个仓库;
5.6、在IDEA中使用Maven
回看:狂神 javaweb-06:IDEA中的Maven操作
4、Serblet
4.1、Servlet简介
- Servlet就是开发动态web的技术
- Sun在这些API中提供一个接口:Servlet,如果你想开发一个Servlet程序,只需完成如下步骤
- 编写一个类,实现Servlet接口
- 把开发好的java类部署到web服务器中
把实现了Servlet接口的java程序叫:Servlet
4.2、HelloServlet
-
构建一个普通的Maven项目,删除里面的src,以后我们的学习就在这个项目里面建立Model,这个孔的工程就是Maven主工程:
-
关于Maven父子工程的理解:
-
父项目中会有
<modules> <module>servlet-01</module> </modules>
-
子项目会有
<parent> <artifactId>javaweb-03</artifactId> <groupId>com.ljj</groupId> <version>1.0-SNAPSHOT</version> </parent>
父项目中的java子项目可以直接使用
son extends father
-
注意:建立Maven子工程的时候,如果选择了模版的话,创建完成后没有生成parent标签,要手动去加。
//手动添加parent <parent> <artifactId>javaweb-03</artifactId> <groupId>com.ljj</groupId> <version>1.0-SNAPSHOT</version> </parent> <artifactId>servlet-02</artifactId> <packaging>war</packaging>
-
-
编写一个Servlet程序
-
编写一个普通类
-
实现Servlet接口,这里我们直接继承HttpServlet
package com.ljj.servlet; import javax.servlet.ServletException; import javax.servlet.ServletOutputStream; import javax.servlet.http.HttpServlet; import javax.servlet.http.HttpServletRequest; import javax.servlet.http.HttpServletResponse; import java.io.IOException; import java.io.PrintWriter; //继承HttpServlet public class HelloServlet extends HttpServlet { //由于get或者post只是请求实现的不同的方式,可以相互调用,因为业务逻辑都一样 @Override protected void doGet(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException { //ServletOutputStream outputStream = resp.getOutputStream(); PrintWriter writer = resp.getWriter();//响应流 writer.print("Hello,Servlet"); } @Override protected void doPost(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException { super.doPost(req, resp); } }
-
-
编写Servlet的映射
- 为什么需要映射:我们写的是JAVA程序,但是要通过浏览器访问,而浏览器需要连接web服务器,所以我们需要在web服务中注册我们写的Servlet,还需给他一个浏览器能访问的路径。
-
配置Tomcat
-
注意:配置项目发布的路径就可以了
[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-50FLKqIS-1634477384985)(JavaWeb.assets/image-20211007140300153.png)]
-
-
启动测试:
- [外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-qilnoeuf-1634477384987)(JavaWeb.assets/image-20211007140939266.png)]
-
成功!!
5、Servlet原理
5.1原理图
[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-z4Gv343Y-1634477384989)(JavaWeb.assets/image-20211008213702406.png)]
5.2Mapping 问题
-
一个Servlet请求可以指定一个映射路径
-
<servlet-mapping> <servlet-name>hello</servlet-name> <url-pattern>/hello</url-pattern> </servlet-mapping>
-
-
一个Servlet可以指定多个多个映射路径
<servlet-mapping> <servlet-name>hello</servlet-name> <url-pattern>/hello</url-pattern> </servlet-mapping> <servlet-mapping> <servlet-name>hello</servlet-name> <url-pattern>/hello1</url-pattern> </servlet-mapping> <servlet-mapping> <servlet-name>hello</servlet-name> <url-pattern>/hello2</url-pattern> </servlet-mapping>
-
一个Servlet可以指定指定通用路径
<servlet-mapping> <servlet-name>hello</servlet-name> <url-pattern> /hello/* </url-pattern> //localhost:8080/s2/hello/随意 </servlet-mapping>
-
一个Servlet可以指定默认路径
<servlet-mapping>
<servlet-name>hello</servlet-name>
<url-pattern>*.ljj</url-pattern> //localhost:8080/s2/(随意).ljj
</servlet-mapping>
- 优先级问题
- 指定了固有的映射路径优先级最高,如果找不到就会走默认的处理请求
6.5、ServletContext
1、共享数据
web容器在启动的时候,它会为每个web程序都创建一个对应的ServletContext对象,它代表了当前的web应用:
-
共享数据
我在这个Servlet中保存的数据,可以在另外一个servlet中得到
[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-ZbrWDLwG-1634477384990)(JavaWeb.assets/image-20211009174429184.png)]
-
放置数据的类
package com.ljj.Servlet; import javax.servlet.ServletContext; import javax.servlet.ServletException; import javax.servlet.http.HttpServlet; import javax.servlet.http.HttpServletRequest; import javax.servlet.http.HttpServletResponse; import java.io.IOException; public class HelloServlet extends HttpServlet { @Override protected void doGet(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException { ServletContext context = this.getServletContext(); String username = "李嘉俊";//数据 context.setAttribute("username",username);//将一个数据保存在了ServletContext中 System.out.println("hello"); } @Override protected void doPost(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException { super.doPost(req, resp); } }
-
读取数据的类
package com.ljj.Servlet; import javax.servlet.ServletContext; import javax.servlet.ServletException; import javax.servlet.http.HttpServlet; import javax.servlet.http.HttpServletRequest; import javax.servlet.http.HttpServletResponse; import java.io.IOException; public class GetServlet extends HttpServlet { @Override protected void doGet(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException { ServletContext context = this.getServletContext(); String username = (String) context.getAttribute("username");//强转 resp.setContentType("text/html"); resp.setCharacterEncoding("utf-8"); resp.getWriter().print("名字:"+ username); } @Override protected void doPost(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException { super.doPost(req, resp); } }
-
xml配置
<!DOCTYPE web-app PUBLIC "-//Sun Microsystems, Inc.//DTD Web Application 2.3//EN" "http://java.sun.com/dtd/web-app_2_3.dtd" > <web-app> <display-name>Archetype Created Web Application</display-name> <servlet> <servlet-name>hello</servlet-name> <servlet-class>com.ljj.Servlet.HelloServlet</servlet-class> </servlet> <servlet-mapping> <servlet-name>hello</servlet-name> <url-pattern>/hello</url-pattern> </servlet-mapping> <servlet> <servlet-name>getc</servlet-name> <servlet-class>com.ljj.Servlet.GetServlet</servlet-class> </servlet> <servlet-mapping> <servlet-name>getc</servlet-name> <url-pattern>/getc</url-pattern> </servlet-mapping> </web-app>
-
测试访问结果
2、获取初始化参数
<!--配置一些web应用的初始化参数-->
<context-param>
<param-name>url</param-name>
<param-value>jdbc:mysql://localhost:3306/mybatis</param-value>
</context-param>
public class ServletDemo03 extends HttpServlet {
@Override
protected void doGet(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {
ServletContext context = this.getServletContext();
String url = context.getInitParameter("url");
resp.getWriter().print(url);
}
3、请求转发
public class ServletDmoe04 extends HttpServlet {
@Override
protected void doGet(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {
//ServletContext的应用
ServletContext context = this.getServletContext();
System.out.println("进入ServletDmoe04");
//RequestDispatcher requestDispatcher = context.getRequestDispatcher("/geturl");//转发的请求路径
context.getRequestDispatcher("/geturl").forward(req,resp);//调用forward实现请求转发:转发到/geturl页面
}
[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-7pKos0EQ-1634477384992)(JavaWeb.assets/image-20211009190249046.png)]
4、读取资源文件
Properties类
- 在java目录下新建properties
- 在resources目录下新建properties
发现:都被打包到同一路径下:classes,我们俗称这个路径为classpath
思路:需要一个文件流:
username = root
password=123456
public class ServletDemo05 extends HttpServlet {
@Override
protected void doGet(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {
InputStream is = this.getServletContext().getResourceAsStream("/WEB-INF/classes/db.properties");
Properties prop = new Properties();
prop.load(is);
String username = prop.getProperty("username");
String password = prop.getProperty("password");
resp.getWriter().print(username+ ":" + password);
}
访问测试结果。
6.6、HttpServletResponse
web服务器接收到客户端的http请求,针对这个请求、分别创建一个代表请求的HttpServletRequest对象,还有一个代表响应的一个HttpServletResponse;
- 如果要获取客户端请求过来的参数:找HttpServletRequest
- 如果要给客户端相应一些信息:找HttpServletResponse
1、简单分类
负责向浏览器发送数据的方法
-
ServletOutputStream getOutputStream() throws IOException; PrintWriter getWriter() throws IOException;
负责向浏览器发送响应头的方法
void setCharacterEncoding(String var1);
void setContentLength(int var1);
void setContentLengthLong(long var1);
void setContentType(String var1)
2、常见应用
- 向浏览器输出消息
- 下载文件
- 要获取下载文件的路径
- 下载的文件名是啥?
- 想办法让浏览器能够支持下载我们需要的东西
- 获取下载文件的输入流
- 创建缓冲区
- 获取OutputStream对象
- 将FileOutputStream流写入到buffer缓冲区
- 使用OutputStream将缓冲区中的数据输出到客户端
public class FileServlet extends HttpServlet {
@Override
protected void doGet(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {
// 1. 要获取下载文件的路径
// C:\Users\ljj\Desktop\JAVA\javaweb-03\Response\target\Response\WEB-INF\classes\1.png
String realPath = "C:\\Users\\ljj\\Desktop\\JAVA\\javaweb-03\\Response\\target\\Response\\WEB-INF\\classes\\1.png";
System.out.println("下载文件的路径:"+ realPath);
// 2. 下载的文件名是啥?
String filename = realPath.substring(realPath.lastIndexOf("\\") + 1);
// 3. 想办法让浏览器能够支持下载我们需要的东西
resp.setHeader("Content-Disposition","attachment;filename"+ URLEncoder.encode(filename,"UTF-8"));
// 4. 获取下载文件的输入流
FileInputStream in = new FileInputStream(realPath);
// 5. 创建缓冲区
int len = 0;
byte[] buffer = new byte[1024];
// 6. 获取OutputStream对象
ServletOutputStream out = resp.getOutputStream();
// 7. 将FileOutputStream流写入到buffer缓冲区,使用OutputStream将缓冲区中的数据输出到客户端
while((len=in.read(buffer))>0){
out.write(buffer,0,len);
}
// 8. 关闭流
in.close();
out.close();
}
3、验证码功能
验证怎么来的?
- 前端实现
- 后端实现,需要用到java的图片类,生成一个图片
public class ImageServlet extends HttpServlet {
@Override
protected void doGet(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {
//如何让浏览器5s自动刷新一次
resp.setHeader("refresh","3");
//在内存中创建一个图片
BufferedImage image = new BufferedImage(80,20,BufferedImage.TYPE_INT_RGB);
//得到图片
Graphics2D pen = (Graphics2D) image.getGraphics();//笔
pen.setColor(Color.white);
pen.fillRect(0,0,80,20);//背景颜色
//给图片写数据
pen.setColor(Color.BLUE);
pen.setFont(new Font(null,Font.BOLD,20));
pen.drawString(makeNum(),0,20);
//告诉浏览器,这个请求用图片的方式打开
resp.setContentType("image/jpeg");
//网站存在缓存,不让浏览器缓存
resp.setDateHeader("expires",-1);
resp.setHeader("Cache-Control","no-cache");
resp.setHeader("Pragma","no-cache");
//把图片写给浏览器
ImageIO.write(image,"jpg", resp.getOutputStream());
}
//生成随机数
private String makeNum(){
Random random = new Random();
String num = random.nextInt(9999) + "";
StringBuffer stringBuffer = new StringBuffer();
for (int i = 0; i < 4-num.length(); i++) {
stringBuffer.append("0");
}
String s = stringBuffer.toString() + num;
return num;
}
4、实现重定向
常见场景:
- 用户登录
public class RedirectServlet extends HttpServlet {
@Override
protected void doGet(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {
//重定向
resp.sendRedirect("/Resp/img");
}
面试题:请你聊聊重定向和转发的区别?
相同点:
- 页面都会实现跳转
不同点
- 请求转发的时候,url不会发生变化
- 重定向是,url地址会发生变化
6.7、HttpServletRequest
HttpServletRequest代表客户端的请求,用户通过HTTP协议访问服务器,HTTP请求中的所有信息会被封装到HttpServletRequest,通过这个HttpServletRequest方法,获得客户端的所有信息。
1、获取前端传递的参数
[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-J8byLCvh-1634477384994)(JavaWeb.assets/image-20211010164218800.png)]
2、请求转发
public class LoginServlet extends HttpServlet {
@Override
protected void doGet(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {
req.setCharacterEncoding("utf-8");
resp.setCharacterEncoding("utf-8");
String username = req.getParameter("username");
String password = req.getParameter("password");
String[] hobbys = req.getParameterValues("hobbys");
System.out.println("=======================================");
System.out.println(username);
System.out.println(password);
System.out.println(Arrays.toString(hobbys));
System.out.println("=======================================");
//通过请求转发
req.getRequestDispatcher("/Success.jsp").forward(req,resp);
}