Javaweb
1、基础概念
1.1web开发:
- web
- 静态web
- html、css
- 动态web
- 技术栈:servlet/JSP、ASP、PHP
1.2web应用程序
web应用程序:可以提供浏览器访问的程序
-
URL
-
tomcat
1.3静态web
- 静态web缺点:
- Web页面无法动态更新
- 轮播图,点击特效:伪动态
- JavaScript
- 无法和数据库交互
- Web页面无法动态更新
1.4动态Web
可以与数据库交互:数据持久化
[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-1qrTkK1n-1650442133241)(01 基础.assets/image-20220302125908749.png)]
缺点:
- 假如服务器的动态web资源出现错误,需要重新编写后台程序,重新发布
- 停机维护
2、web服务器
2.1技术
ASP:微软的
php:
- 开发速度快,功能强大,挂平台,代码简单
- 无法承载大访问量的情况(局限性)
JSP/Servlet:
B/S:浏览和服务器
C/S:客户端和服务器
- 基于Java
- 可以承载三高问题
2.2web服务器
IIS(微软)
Tomcat
面向百度编程
2.3Tomcat
[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-cHwiluOt-1650442133243)(01 基础.assets/image-20220302132420348.png)]
[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-S0UVqI5p-1650442133244)(01 基础.assets/image-20220302132658775.png)]
可以配置端口号、主机的名称
tomcat默认端口号:8080
mysql:3306
http:80
https:443
默认主机名为:lacalhost->127.0.0.1
默认网站应用存放位置:webapps
面试题
[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-RnhsksIj-1650442133244)(01 基础.assets/image-20220302134042192.png)]
[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-9LutLcU6-1650442133245)(01 基础.assets/image-20220302134057916.png)]
3.4 发布一个网站
[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-4rwGA8Ip-1650442133247)(01 基础.assets/image-20220302135113942.png)]
4 HTTP
4.1、什么是HTTP
HTTP (超文本传输一个简单的请求-响应协议,它TCP之上。
HTTPS:安全的(443
4.2两个时代
- http1.0
- http/1.0:客户端可以与web服务器连接局,只能获得一个web资源,断开链接
- http2.0
- http/1.1:客户端可以与web服务器连接局,可以获得多个web资源
4.3http请求
- 客户端—发请求—服务器
[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-PmAUrL1F-1650442133248)(01 基础.assets/image-20220302140739481.png)]
[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-3TmNQDnC-1650442133250)(01 基础.assets/image-20220302141022779.png)]
- 请求行
- get、post
- 消息头
- [外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-3qcxUdJV-1650442133251)(01 基础.assets/image-20220302141454515.png)]
4.4http响应
- 服务器—响应—客户端
//百度:
Cache-Control:private //缓存控制
Connection:Keep-Alive //连接
Content-Encoding:gzip //编码
Content-Type:text/html //类型
-
响应体
Accept:告诉浏览器,它所支持的数据类型 Accept-Encoding:支持哪种编码格式 GBK UTF-8 GB2312 ISO8859-1 Accept-Language:告诉浏览器,它的语言环境 Cache-Control:缓存控制 Connection:告诉浏览器,请求完成是断开还是保持连接 HOST:主机..../. Refresh:告诉客户端,多久刷新一次; Location:让网页重新定位;
-
响应状态码
200:请求响应成功 200 3xx:请求重定向 重定向:你重新到我给你新位置去; 4xx:找不到资源 404 资源不存在; 5xx:服务器代码错误 500 502:网关错误
-
面试题
[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-QG1JSLlc-1650442133252)(01 基础.assets/image-20220302142124447.png)]
5、Maven
5.2 配置
打开maven安装目录下的conf\settings.xml 添加如下信息
<mirror>
<id>nexus-aliyun</id>
<mirrorOf>central</mirrorOf>
<name>Nexus aliyun</name>
<url>http://maven.aliyun.com/nexus/content/repositories/central/</url>
</mirror>
添加本地仓库路径:
<localRepository>E:\Environment\apache-maven-3.6.3\maven-repo</localRepository>
5.3 pom.xml的结构
5.4 web.xml中webapp版本问题
自动生成的webapp是2.6版本的,最新版的版本在tomcat中可以找到
<?xml version="1.0" encoding="UTF-8"?>
<web-app xmlns="http://xmlns.jcp.org/xml/ns/javaee"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:schemaLocation="http://xmlns.jcp.org/xml/ns/javaee
http://xmlns.jcp.org/xml/ns/javaee/web-app_4_0.xsd"
version="4.0"
metadata-complete="true">
</web-app>
5.5 maven其他
6、Servlet
6.1 HelloServlet
servlet接口sun公司提供了两个默认的实现类: httpServlet,genericServlet
- 构建一个普通的Maven项目,删掉里面的src目录,在这个项目里面建立Moudel(模块),这个空的工程就是Maven主工程;
- 在Maven父子工程中
- 父项目的pom.xml中自动生成
<!--读pom文件时,要去读modules下的子pom文件-->
<modules>
<module>HelloServlet</module>
</modules>
-
子类项目的pom.xml自动生成
<!--使子项目继承父项目的设置,避免导入重复依赖 eg:son extends parent--> <parent> <artifactId>javaweb-02-servlet</artifactId> <groupId>com.iandf</groupId> <version>1.0-SNAPSHOT</version> </parent>
-
编写一个Servlet程序
[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-6eNllxou-1650442133254)(01 基础.assets/image-20220324225842712.png)]
-
编写一个普通类,实现Servlet接口,这里我们直接继承HttpServlet(
HttpServlet实现了Servlet接口
)public class HelloServlet extends HttpServlet { @Override protected void doGet(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException { PrintWriter writer = resp.getWriter();//获取响应流 //响应流输出信息 writer.print("hello servlet"); } @Override protected void doPost(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException { doGet(req, resp); } }
-
编写servlet映射
我们编写的java程序需要被浏览器访问,而浏览器需要访问web服务器,所以我们需要在web服务器中部署servlet,给他一个访问的具体路径。所以我们在web.xml中注册servlet和servlet-mapping
<!--注册servlet--> <servlet> <servlet-name>helloServlet</servlet-name> <servlet-class>com.kuang.HelloServlet</servlet-class> </servlet> <!--每一个servlet对应一个映射--> <servlet-mapping> <servlet-name>helloServlet</servlet-name> <url-pattern>/hello</url-pattern> </servlet-mapping>
-
配置tomcat
6.2 Servlet原理
[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-YRPz7AkP-1650442133255)(01 基础.assets/image-20220324230616836.png)]
6.3 ServletContext
当web容器启动时,会创建一个servletContext对象,可以通过这个对象让servlet之间进行通信,代表当前的web应用
1. 共享数据
我们在一个Servlet中通过servlerContext对象保存(set)的数据,可以在另一个servlet通过servlerContext对象get到
public class SetServletContext extends HttpServlet {
@Override
protected void doGet(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {
ServletContext servletContext = this.getServletContext();
String name = "狂神";
resp.setContentType("text/html");
resp.setCharacterEncoding("utf-8");
servletContext.setAttribute("username",name);
}
}
public class GetServletContext extends HttpServlet {
@Override
protected void doGet(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {
ServletContext servletContext = this.getServletContext();
String username = (String) servletContext.getAttribute("username");
resp.setContentType("text/html");
resp.setCharacterEncoding("utf-8");
resp.getWriter().print("username : " + username);
}
}
先访问SetServletContext设置数据,再访问GetServletContext就可以拿到数据了。
2. 获取配置参数
String db_url = this.getServletContext().getInitParameter("db_url");
resp.getWriter().print(db_url); //获取配置参数中的db_url
3. 请求转发
note: 请求转发和重定向的区别
forward(转发):
是服务器请求资源,服务器直接访问目标地址的URL,把那个URL的响应内容读取过来,然后把这些内容再发给浏览器.浏览器根本不知道服务器发送的内容从哪里来的,因为这个跳转过程实在服务器实现的,并不是在客户端实现的所以客户端并不知道这个跳转动作,所以它的地址栏还是原来的地址.
redirect(重定向):
是服务端根据逻辑,发送一个状态码,告诉浏览器重新去请求那个地址.所以地址栏显示的是新的URL.
转发是服务器行为,重定向是客户端行为。
RequestDispatcher requestDispatcher = this.getServletContext().getRequestDispatcher("/getParams");//获取请求转发的路径
requestDispatcher.forward(req,resp);//使用forward方法将参数传给请求转发的路径,实现请求转发
[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-uw0xpqgC-1650442133257)(01 基础.assets/image-20220324231929971.png)]
4. 读取配置文件
//文件路径为tomcat生成的webapp文件夹下的资源路径/WEB-INF/classes/db.properties,第一个/代表当前项目
InputStream resourceAsStream = this.getServletContext().getResourceAsStream("/WEB-INF/classes/db.properties");
Properties properties = new Properties();
properties.load(resourceAsStream);
String username = properties.getProperty("username");
String password = properties.getProperty("password");
resp.getWriter().print(username+" :"+password);
6.4 HttpServletResponse
web服务器接收了web client的请求,生成两个对象:HttpServletResponse和HttpServletRequest
- request负责读取用户(client)请求的信息
- response负责把数据传给浏览器
文件下载的案例
protected void doGet(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {
//获取文件路径
String filePath = "D:\\ForStrong_java\\javaweb\\javaweb-02-servlet\\ServletHttpResponse\\target\\classes\\1.jpg";
//获取文件名
String fileName = filePath.substring(filePath.lastIndexOf("\\") + 1);
//获取文件输入流
BufferedInputStream bufferedInputStream = new BufferedInputStream(new FileInputStream(filePath));
//获取向浏览器的输出流
BufferedOutputStream bufferedOutputStream = new BufferedOutputStream(resp.getOutputStream());
//让浏览器知道我们要下载文件,需要设置头,让浏览器支持。中文文件名URLEncoder.encode编码,否则有可能乱码
resp.addHeader("Content-Disposition", "attachment;filename=" + URLEncoder.encode(fileName,"utf-8"));
//向浏览器输出数据
byte[] buffer = new byte[1024];
int len = 0;
while ((len = bufferedInputStream.read(buffer))>0){
bufferedOutputStream.write(buffer,0,len);
}
//关闭流
bufferedInputStream.close();
bufferedOutputStream.close();
}
验证码功能
-
前端实现
-
后端实现
protected void doGet(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {
//写一张图片
BufferedImage bufferedImage = new BufferedImage(80,20,BufferedImage.TYPE_INT_RGB);//需要一张画板
Graphics graphics = bufferedImage.getGraphics();//需要一只画笔
//设置背景
graphics.setColor(Color.white);//设置颜色
graphics.fillRect(0,0,80,20);
//设置内容
graphics.setColor(Color.blue);
graphics.setFont(new Font(null,Font.ITALIC,20));
graphics.drawString(Objects.requireNonNull(makeNum()),0,20);
//告诉浏览器,这个请求用图片的方式打开
resp.setContentType("image/jpeg");
//网站存在缓存,不让浏览器缓存
resp.setDateHeader("expires",-1);
resp.setHeader("Cache-Control","no-cache");
resp.setHeader("Pragma","no-cache");
//给这个响应设置三秒刷新一次,且把缓存机制关掉
resp.setHeader("refresh","3");
//将这张图片写入浏览器
ImageIO.write(bufferedImage,"jpg",resp.getOutputStream());
}
实现重定向
//参数为:项目名/地址名
resp.sendRedirect("/r/img");
<%--action:这里提交的路径,需要寻找到项目的路径--%>
<%--${pageContext.request.contextPath}代表当前的项目--%>
<form action="${pageContext.request.contextPath}/redirect" method="get">
username <input name="username" type="text"> <br>
password: <input name="password" type="password"> <br>
<input type="submit">
</form>
protected void doGet(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {
String username = req.getParameter("username");
String password = req.getParameter("password");
System.out.println(username +": "+password);
//参数为:项目名/地址名
resp.sendRedirect("/ServletHttpResponse/success.jsp");
}
[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-MgMjmvVd-1650442133258)(01 基础.assets/image-20220325215247913.png)]
6.5 HttpServletResquest
request获取请求的数据,并请求转发
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[] hobbies = req.getParameterValues("hobbies");
System.out.println(username);
System.out.println(password);
System.out.println(Arrays.toString(hobbies));
//请求转发
req.getRequestDispatcher("/success.jsp").forward(req,resp);
}
<form action="${pageContext.request.contextPath}/login" method="post">
username <input name="username" type="text"> <br>
password: <input name="password" type="password"> <br>
hobbies:
<input name="hobbies" type="checkbox" value="女孩">女孩
<input name="hobbies" type="checkbox" value="代码">代码
<input name="hobbies" type="checkbox" value="电影">电影
<input name="hobbies" type="checkbox" value="爬山">爬山
<input type="submit">
</form>
7、Cookies Seesion
7.1、会话
会话:用户打开一个浏览器,点击了很多超链接,访问多个web资源,关闭浏览器,这个过程可以称之为会话;
有状态会话:一个同学来过教室,下次再来教室,我们会知道这个同学,曾经来过,称之为有状态会话;
一个网站,怎么证明你来过?
客户端 服务端
- 服务端给客户端一个 信件,客户端下次访问服务端带上信件就可以了; cookie
- 服务器登记你来过了,下次你来的时候我来匹配你; seesion
7.2、保存会话的两种技术
cookie
- 客户端技术 (响应,请求)
session
-
服务器技术,利用这个技术,可以保存用户的会话信息? 我们可以把信息或者数据放在Session中!
常见网站:网站登录之后,你下次不用再登录了,第二次访问直接就上去了!
7.3 cookie
- 由服务器创建一个cookie,并设置数据和属性,再由服务器发送给客户端,客户端在本地保存该cookie
//服务器给客户端设置cookie
Cookie time_cookie = new Cookie("lastTime",System.currentTimeMillis()+"");
time_cookie.setMaxAge(24*60*60);//设置cookie的存活时间,0代表删除cookie,负数代表不会保存该cookie,正数以秒为单位
resp.addCookie(time_cookie);
- 下次访问时带上该cookie,服务器就能知道你先前来过,并可以通过cookie获取数据
//服务器获取客户端的cookie
Cookie[] cookies = req.getCookies();
PrintWriter writer = resp.getWriter();
for (Cookie cookie : cookies) {
if (cookie.getName().equals("lastTime")) {
writer.print("上次登陆时间为: ");
writer.print(new SimpleDateFormat().format(new Date(Long.valueOf(cookie.getValue()))));
7.4 seesion
- 由request对象获取session,如果没有则创建session,在session中保存数据,服务器把sessionID以cookie的形式发送给客户端
/* Returns the current session associated with this request,
or if the request does not have a session, creates one.*/
HttpSession session = req.getSession();
String sessionId = session.getId();
if (session.isNew()){
resp.getWriter().print("session创建完成,sessionID为 :"+sessionId);
}else {
resp.getWriter().print("session已经在服务器中存在,sessionID为 :"+sessionId);
}
//给session设置数据
session.setAttribute("person",new Person("huangaa",202160211));
- 服务器把sessionID以cookie的形式发送给客户端,相当于这段代码
//每个用户对应一个session,服务器会把sessionID保存在JSESSIONID的Cookie中发送给客户端,存活时间是这次会话(expiry = -1),浏览器退出则删除
Cookie cookie = new Cookie("JSESSIONID",sessionId);
cookie.setMaxAge(-1);
resp.addCookie(cookie);
- session的存活时间可以在web.xml中进行配置
<session-config>
<!--以分钟为单位-->
<session-timeout>1</session-timeout>
</session-config>
- 下次请求时,客户端会把该cookie带上,服务器可以通过该cookie获取session,再通过session获取数据,如果将该cookie在客户端移除,服务器端将拿不到这个session。所以服务端的session的实现对客户端的cookie有依赖关系的
HttpSession session = req.getSession();
Person person = (Person) session.getAttribute("person");
resp.getWriter().print(person.toString());
- 删除session
HttpSession session = req.getSession();
session.invalidate();
7.5 cookie和seesion的相同点和不同点
**相同点: **
- cookie和session都是为了解决http协议无状态的特征。
区别:
- cookie数据是存放在客户端本地的,session数据是存放在服务器的,但是服务端的session的实现对客户端的cookie有依赖关系的;
- cookie不是很安全,别人可以分析存放在本地的COOKIE并进行COOKIE欺骗,考虑到安全应当使用session;
- session会在一段时间内存放在服务器,如果session过多,会导致服务器压力过大,性能降低。如果考虑服务器性能方面应该使用cookie
- cookie的大小是有限制的
- 一个用户在一个站点上可以有多个cookie,但是只有一个session
8、JSP
8.1 JSP原理探究
在C:\Users\IANDF\AppData\Local\JetBrains\IntelliJIdea2020.1\tomcat\Unnamed_javaweb-04-jsp\work\Catalina\localhost\jsp_01\org\apache\jsp有
[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-t8nmdnNX-1650442133259)(01 基础.assets/3HQJ9ANbdXKoyks.png)]
说明xxx.jsp文件最终都会被服务器转换成xxx.java,xxx.class文件。
- index_jsp类结构
public final class index_jsp extends org.apache.jasper.runtime.HttpJspBase
public abstract class HttpJspBase extends HttpServlet
index_jsp继承了HttpJspBase,查看HttpJspBase源码可以得到HttpJspBase继承自HttpServlet
这说明jsp最终会装换成servlet
- JSP和servlet一样,有以上的生命周期
- _jspService()中的部分对象,这些对象可以在jsp文件中直接使用
final javax.servlet.jsp.PageContext pageContext;//页面上下文
javax.servlet.http.HttpSession session = null;//session
final javax.servlet.ServletContext application;//ServletContext,代表整个web网站
final javax.servlet.ServletConfig config;//ServletConfig 配置对象
javax.servlet.jsp.JspWriter out = null;//out等同于resp.getWriter()
final java.lang.Object page = this;//当前页面
- _jspService()中的执行语句
response.setContentType("text/html");
pageContext = _jspxFactory.getPageContext(this, request, response,
null, true, 8192, true);
_jspx_page_context = pageContext;
application = pageContext.getServletContext();
config = pageContext.getServletConfig();
session = pageContext.getSession();
out = pageContext.getOut();
_jspx_out = out;
out.write("<html>\n");
out.write("<body>\n");
out.write("<h2>Hello World!</h2>\n");
out.write("</body>\n");
out.write("</html>\n");
所有的html代码都以out.write(xxx)的形式输出
8.2 JSP语法
1. jsp表达式
<%--<%= 变量或者表达式%>--%>
<%=new SimpleDateFormat("hh:mm:ss").format(new Date(System.currentTimeMillis())) %>
2. jsp声明(全局变量和全局函数),默认生成在_jspService()中
<%!
static {
System.out.println("该类已被访问");
}
private int globalVar = 0;
public int getGlobalVar(){
return globalVar;
}
%>
3.jsp脚本片段
<%for (int i = 0; i < 5; i++) {
out.println(getGlobalVar());
%>
<h1>hello world <%= i%></h1>
<% } %>
8.3 JSP指令
<%@page args.... %>
<%@include file=""%>
<%--@include会将两个页面合二为一--%>
<%@include file="common/header.jsp"%>
<h1>网页主体</h1>
<%@include file="common/footer.jsp"%>
<hr>
<%--jSP标签
jsp:include:拼接页面,本质还是三个java文件
--%>
<jsp:include page="/common/header.jsp"/>
<h1>网页主体</h1>
<jsp:include page="/common/footer.jsp"/>
8.4 9大内置对象和其作用域
PageContext 存东西
Request 存东西
Response
Session 存东西
Application 【SerlvetContext】 存东西
config 【SerlvetConfig】
out
page (不用了解)
exception
四大作用域
存数据
public static final int PAGE_SCOPE = 1;
public static final int REQUEST_SCOPE = 2;
public static final int SESSION_SCOPE = 3;
public static final int APPLICATION_SCOPE = 4;
<%--存数据--%>
<%
pageContext.setAttribute("pageContextName","pageContext");//保存的数据在当前页面有效
request.setAttribute("requestName","request");//保存的数据在一次请求中有效,请求转发也会携带这个数据
session.setAttribute("sessionName","session");//保存的数据在一次会话中有效,从打开浏览器到关闭浏览器
application.setAttribute("applicationName","application");//保存的数据在服务器中有效,从打开服务器到关闭服务器
%>
源码中存数据做的事情
public void setAttribute (String name,Object attribute,int scope){
switch (scope) {
case PAGE_SCOPE:
mPage.put (name, attribute);
break;
case REQUEST_SCOPE:
mRequest.put (name, attribute);
break;
case SESSION_SCOPE:
mSession.put (name, attribute);
break;
case APPLICATION_SCOPE:
mApp.put (name, attribute);
break;
default:
throw new IllegalArgumentException ("Bad scope " + scope);
}
}
取数据,从作用域最小的开始找,如果存的时候有Key是同名的,数据将会取不出来
<%
String pageContextName = (String) pageContext.findAttribute("pageContextName");
String requestName = (String) request.getAttribute("requestName");
String sessionName = (String) session.getAttribute("sessionName");
String applicationName = (String) application.getAttribute("applicationName");
%>
源码如下
//从作用域最小的开始找
public Object findAttribute (String name){
if (mPage.containsKey (name)) {
return mPage.get (name);
}
else if (mRequest.containsKey (name)) {
return mRequest.get (name);
}
else if (mSession.containsKey (name)) {
return mSession.get (name);
}
else if (mApp.containsKey (name)) {
return mApp.get (name);
}
else {
return null;
}
}
8.5 JSTL标签、EL表达式
第一步就是添加依赖
<!-- https://mvnrepository.com/artifact/javax.servlet/jstl -->
<dependency>
<groupId>javax.servlet</groupId>
<artifactId>jstl</artifactId>
<version>1.2</version>
</dependency>
<!-- https://mvnrepository.com/artifact/taglibs/standard -->
<dependency>
<groupId>taglibs</groupId>
<artifactId>standard</artifactId>
<version>1.1.2</version>
</dependency>
EL表达式:${}
- 获取数据
- 执行运算
- 获取web开发的常用对象
[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-QYGFh6zN-1650442133260)(01 基础.assets/4AFQB6f9bIVwYyx.png)]
测试代码
<%--
跳转到coreif.isp页面参数为:username=param.username
完整路径为http://localhost:8080/jsp/coreif.jsp?username=admin
--%>
<form action="coreif.jsp" method="get">
<%--
EL表达式获取表单中的数据
${param.参数名}
--%>
<input type="text" name="username" value="${param.username}">
<input type="submit" value="登录">
</form>
<%--判断如果提交的用户名是管理员,则登录成功--%>
<c:if test="${param.username=='admin'}" var="isAdmin">
<c:out value="管理员欢迎您!"/>
</c:if>
<%--自闭合标签--%>
<c:out value="${isAdmin}"/>
9、JavaBean
实体类
JavaBean有特定的写法:
- 必须要有一个无参构造
- 属性必须私有化
- 必须有对应的get/set方法
一般用来和数据库的字段做映射 ORM
ORM:对象关系映射
- 表–>类
- 字段–>属性
- 行记录–>对象
class People{
private int id;
private String name;
private String adress
}
10、 MVC架构
什么是mvc: Model view Controller 模型、视图、控制器
11、Filter
11.1 Filter用法
- 让java类实现javax.servlet.Filter接口,重写方法
public class CharacterEncodingFilter implements Filter {
//初始化:web服务器启动,就已经初始化了,随时等待过滤对象出现!
public void init(FilterConfig filterConfig) throws ServletException {
System.out.println("CharacterEncodingFilter 初始化");
}
//Chain:链
/*
* 1.过滤中的所有代码,在过滤特定请求的时候都会执行
* 2.必须要让过滤器继续同行
* chain.doFilter(request,response);
* */
public void doFilter(ServletRequest request, ServletResponse response, FilterChain filterChain) throws IOException, ServletException {
request.setCharacterEncoding("utf-8");
response.setCharacterEncoding("utf-8");
response.setContentType("text/html;charset=UTF-8");
System.out.println("CharacterEncodingFilter执行前");
filterChain.doFilter(request,response);//让我们的请求继续走,如果不写,程序到这就被拦截停止!
System.out.println("CharacterEncodingFilter执行后");
}
//销毁:web服务器关闭的时候,过滤会销毁
public void destroy() {
System.out.println("CharacterEncodingFilter销毁");
}
}
- 在web.xml文件中配置filter
<filter>
<filter-name>CharacterEncodingFilter</filter-name>
<filter-class>com.dong.filter.CharacterEncodingFilter</filter-class>
</filter>
<!-- 只要是/servlet的任何请求,都会经过这个过滤器-->
<!-- <url-pattern>/*</url-pattern> -->
<filter-mapping>
<filter-name>CharacterEncodingFilter</filter-name>
<url-pattern>/servlet/*</url-pattern>
</filter-mapping>
12、 监听器
监听器应用,实现登录业务
用户点击登录按钮 -->判断用户名是否是admin->成功或者失败的页面
note:
判断操作在loginservlet中完成,成功就往Session中保存一条数据并跳转到success页面,失败跳转到error页面
不能直接访问success页面,使用过滤器完成
13、JDBC
JDBC(Java database connect):Java连接数据库!
需要jar包的支持:
- java.sql
- javax.sql
- mysql-conneter-java…连接驱动(必须要导入)
13.1 创建SQL(表和内容)
CREATE TABLE `jdbc`.`users`(
`id` int(4) UNSIGNED ZEROFILL not NULL auto_increment COMMENT '学号',
`name` VARCHAR(40),
`password` VARCHAR(40),
email varchar(60),
birthday DATE,
PRIMARY KEY(`id`)
)ENGINE=INNODB DEFAULT charset=utf8;
INSERT INTO users(id,`name`,`password`,email,birthday)
VALUES(1,'张三','123456','555@qq.com','2000-01-01');
INSERT INTO users(id,`name`,`password`,email,birthday)
VALUES(2,'李四','123456','333@qq.com','2000-01-01');
INSERT INTO users(id,`name`,`password`,email,birthday)
VALUES(3,'王五','123456','222@qq.com','2000-01-01');
13.2 在xml导入SQL -jar包依赖
<dependencies>
<dependency>
<groupId>mysql</groupId>
<artifactId>mysql-connector-java</artifactId>
<version>5.1.47</version>
</dependency>
</dependencies>
13.3 在idea中连接数据库
13.4 编写jdbc
固定步骤:
1.加载驱动
2.连接数据库,代表数据库
3.向数据库发送SQL的对象Statement:CRUD
4.编写sql(根据业务,不同的SQL)
5.执行SQL
6.关闭连接
public class TestJdbc {
public static void main(String[] args) throws ClassNotFoundException, SQLException {
//获取配置信息
String url="jdbc:mysql://localhost:3306/jdbc?useUnicode=true&characterEncoding=utf-8";
String username="root";
String password="123456";
//1.加载驱动
Class.forName("com.mysql.jdbc.Driver");
//2.连接数据库
Connection connection = DriverManager.getConnection(url, username, password);
//3.向数据库发送sql的对象statement:CRUD
Statement statement = connection.createStatement();
PreparedStatement preparedStatement = connection.prepareStatement(sql);预编译,先编写SQL,在这个时候把sql放进去
//4.编写sql语句
String sql="select * from users";
//5.查询sql语句,返回result结果集
ResultSet resultSet = statement.executeQuery(sql);
while (resultSet.next()){
System.out.println("id"+resultSet.getObject("id"));
System.out.println("name"+resultSet.getObject("name"));
System.out.println("password"+resultSet.getObject("password"));
System.out.println("email"+resultSet.getObject("email"));
System.out.println("birthday"+resultSet.getObject("birthday"));
}
//6.查询结束,关闭资源
resultSet.close();
statement.close();
connection.close();
}
}
//受影响的行数,增删改都用executeUpdate(sql)
int i = statement.executeUpdate(sql);
13.5 预编译sql
public class TestJdbc2 {
public static void main(String[] args) throws Exception {
//获取配置信息
String url="jdbc:mysql://localhost:3306/jdbc?useUnicode=true&characterEncoding=utf-8";
String username="root";
String password="123456";
//1.加载驱动
Class.forName("com.mysql.jdbc.Driver");
//2.连接数据库
Connection connection = DriverManager.getConnection(url, username, password);
//3.编写sql语句
String sql="insert into users(id, name, password, email, birthday) values(?,?,?,?,?)";
//4.预编译
PreparedStatement preparedStatement = connection.prepareStatement(sql);
preparedStatement.setInt(1,4);//给第一个?占位符赋值为1
preparedStatement.setString(2,"赵六");
preparedStatement.setString(3,"123456");
preparedStatement.setString(4,"1395950933@qq.com");
preparedStatement.setDate(5,new Date(new java.util.Date().getTime()));
//5.执行SQL
int i = preparedStatement.executeUpdate();
if(i>0){
System.out.println("插入成功!");
}
//6.关闭数据库
preparedStatement.close();
connection.close();
}
}
13.6 事务
要么都成功,要么都失败!
ACID原则:保证数据的安全
//开启十五
//事务提交 commit()
//事务回滚 rollback()
//关闭事务
[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-455IZqvZ-1650442133261)(01 基础.assets/image-20220401083326007.png)]
Junit单元测试
依赖:
<dependency>
<groupId>junit</groupId>
<artifactId>junit</artifactId>
<version>4.12</version>
</dependency>
@Test注解只有在方法上有效