Java Web学习笔记

什么是JavaWeb?

Java Web,是用Java技术来解决相关web互联网领域的技术栈。web包括:web服务端web客户端两部分。Java在客户端的应用有Java Applet,不过使用得很少,Java在服务器端的应用非常的丰富,比如ServletJSP、第三方框架等等。Java技术对Web领域的发展注入了强大的动力。

Internet上供外界访问的Web资源分为:静态web资源(如html 页面):指web页面中供人们浏览的数据始终是不变。动态web资源:指web页面中供人们浏览的数据是由程序产生的,不同时间点访问web页面看到的内容各不相同。静态web资源开发技术:HTML、CSS。动态web资源开发技术:JavaScript、JSP/Servlet、ASP、PHP等。在Java中,动态web资源开发技术统称为Java Web。

项目开发步骤

搭建Java Web应用的开发环境-----部署Tomcat服务器、用eclipse创建Server服务、构建Java Web项目、建立第一个JSP文件、 运行JSP文件。

第一个要点是掌握tomcat的安装和部署。在Windows系统上安装Tomcat相对简单,下载压缩包解压缩到任意目录即可(目录名称不要含有中文字符)。进入tomcat的bin目录,可以直接运行startup.bat启动tomcat服务。

第二个要点是在eclipse中添加Server服务。把tomcat与eclipse进行关联,方便eclipse管理tomcat。

第三个要点是构建Java Web项目。Web项目开发的第一步就是要建立项目。在新建Project项目时,选择Dynamic Web Project项目类型,即可创建Web项目。

第四个要点是建立的项目如何在Server中运行。选择要运行的JSP文件,单击右键,在弹出的菜单中选择Run on Server命令即可,初次运行项目时,需要配置项目在哪个Server中运行(如有多个Server)。

web后端和前端是怎么连接的?

1、web服务器(apache、tomcat等),网络协议(http、socket等),浏览器(chrome、FF、IE等)。浏览器发起建立连接请求,通过网络协议与服务器建立连接,服务器保持连接,获取浏览器想要的数据,服务器通过连接返回内容给浏览器,浏览器把数据呈现出来
2、连接的协议一般是http,也有websocket。服务器以服务的方式存在,就像外卖店,你打个电话过去,人家就把饭菜送上门来了。
3、web服务器访问数据库一样要使用网络连接,端口只是开放服务的入口而已,就像外卖的电话。

主流 Java Web 开发框架

1) Spring 框架

Spring 框架是一个轻量级的框架,渗透了 Java EE 技术的方方面面。Spring 框架是由于软件开发的复杂性而创建的,是一个开源框架。

Spring 框架的用途不仅限于服务器端的开发,从简单性、可测试性和松耦合性角度而言,绝大部分 Java 应用都可以从 Spring 框架中受益。

对 Spring 框架的几点说明:

  • 目的:解决企业应用开发的复杂性。
  • 目标:Java EE 技术更容易使用,并促进良好编程习惯的养成。
  • 功能:使用基本的 JavaBean 代替 EJB,并提供更多的企业应用功能。
  • 范围:任何 Java 应用。

Spring 框架是一个轻量级控制反转(IoC)和面向切面(AOP)的容器框架,它主要作为依赖注入容器和 AOP 实现存在,还提供了声明式事务、对 DAO 层的支持等简化开发的功能。

Spring 框架可以很方便地与 Spring MVC、Struts 2、MyBatis、Hibernate 等框架集成,其中大名鼎鼎的 SSM 集成框架指的就是基于 Spring MVC + Spring + MyBatis 的技术框架,使用这个集成框架能使应用程序更加健壮、稳固、轻巧和优雅,这也是当前流行的 Java Web 技术框架。

Spring 框架官网:https://spring.io/

2) Spring MVC 框架

Spring MVC 框架属于 SpringFrameWork 的后续产品,已经融合在 Spring Web Flow 中,是结构清晰的 MVC Model2 的实现。

Spring 框架提供了构建 Web 应用程序的全功能 MVC 模块,并且拥有高度的可配置性,支持多种视图技术。它还可以进行定制化开发,使用相当灵活。

此外,Spring 框架整合 Spring MVC 框架是无缝集成,这是一个高性能的架构模式,已越来越广泛地应用于互联网应用的开发中。当使用 Spring 框架进行 Web 开发时,可以选择 Spring MVC 框架或集成其他 MVC 的开发框架,如 Struts 1(现在一般不用)、Struts 2(一般老项目使用)等。

3) MyBatis 框架

MyBatis 框架是一个优秀的数据持久层框架,可在实体类和 SQL 语句之间建立映射关系,是一种半自动化的 ORM 实现。

Mybatis 的封装性要低于 Hibernate 框架,且性能优异、简单易学,因此应用较为广泛。

MyBatis 框架本是 Apache 的一个开源项目 iBatis,2010 年,这个项目由 Apache software foundation 迁移到 Google code,并且改名为“MyBatis”;2013 年 11 月它迁移到 Github。

“iBatis”一词来源于“internet”和“abatis”的组合,它是一个基于 Java 的持久层框架,其框架包括 SQL Maps 和 Data Access Objects(DAOs)。

MyBatis 3中文文档:https://mybatis.org/mybatis-3/zh/

4) Hibernate 框架

Hibernate 框架不仅是一个优秀的持久化框架,也是一个开放源代码的对象关系映射框架。它对 JDBC 进行了轻量级的对象封装,将 POJO 与数据库表建立映射关系,形成一个全自动的 ORM 框架。

Hibernate 框架可以自动生成 SQL 语句,且自动执行,使 Java 程序员可以随心所欲地使用对象编程思维来操纵数据库。

Hibernate 框架还可以应用在任何使用 JDBC 的场合:

  • 可以在 Java 的客户端程序使用;
  • 也可以在 Servlet/JSP 的 Web 应用中使用;
  • 最具革命意义的是,Hibernate 框架可以在应用 EJB 的 Jave EE 架构中取代 CMP,以完成数据持久化的重任。

Hibernate 框架已经成为当前主流的数据库持久化框架,并被广泛应用。

Hibernate 框架官网:http://hibernate.org/

5) Struts 2 框架

Struts 2 框架以 WebWork 的优秀设计思想为核心,吸收 Struts 框架的部分优点,提供了一个更加简洁的基于 MVC 设计模式实现的 Web 应用程序框架,它本质上相当于一个 Servlet。

在 MVC 设计模式中,Struts 2 框架作为控制器(Controller)来建立模型与视图的数据交互。

Struts 2 框架是 Struts 的下一代产品,是在 Struts 1 和 WebWork 技术的基础上进行合并的创新。它采用拦截器的机制来处理用户的请求,可使业务逻辑控制器与 Servlet API 完全脱离开,所以也可以理解是 WebWork 的更新产品。

Struts 2 框架充分利用了其他 MVC 框架的经验和教训,使整个框架更加清晰和灵活。

Struts 框架官网:https://struts.apache.org/

基本概念

web开发

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-42BEbqIT-1663510961697)(Day007_JavaWeb.assets/1655879512039.png)]

web应用程序

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-4Ks5w1Qr-1663510961699)(Day007_JavaWeb.assets/1655879636897.png)]

静态Web

  • .htm、.html,这些都是网页的后缀,如果服务器上一直存在这些东西,我们就可以直接进行读取。网络:

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-kYC5tMMj-1663510961700)(Day007_JavaWeb.assets/1655880375132.png)]

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-bvGV5VFh-1663510961700)(Day007_JavaWeb.assets/1655879840044.png)]

动态Web

页面会动态展示:“web页面展示的效果因人而异“;

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-180zgBgh-1663510961700)(Day007_JavaWeb.assets/1655880420060.png)]

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-0Eri87qB-1663510961701)(Day007_JavaWeb.assets/1655880498131.png)]

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-s1Bstcic-1663510961701)(Day007_JavaWeb.assets/1655880863170.png)]

Web服务器

技术讲解

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-BTKaZC7B-1663510961702)(Day007_JavaWeb.assets/1655885899537.png)]

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-UEFBupPU-1663510961702)(Day007_JavaWeb.assets/1655885930618.png)]

Web服务器

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-e9uj1UN7-1663510961702)(Day007_JavaWeb.assets/1655946924742.png)]

下载Tomcat:

  1. 安装或者解压
  2. 了解配置文件及目录结构
  3. 这个东西的作用

Tomcat

安装Tomcat

Tomcat官网:http://tomcat.apache.org/

采用了Tomcat 9 的版本

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-GT7MsSOy-1663510961703)(Day007_JavaWeb.assets/1655947227051.png)]

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-4FWacYdL-1663510961703)(Day007_JavaWeb.assets/1655947286705.png)]

Tomcat启动和配置

文件夹目录

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-vYEwu9VJ-1663510961703)(Day007_JavaWeb.assets/1655966390983.png)]

启动和关闭Tomcat

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-3if6jlCA-1663510961703)(Day007_JavaWeb.assets/1655966511099.png)]

启动测试:http://localhost:8080/

可能遇到的问题:

  1. Java环境变量没有配置(可能会闪退)
  2. 闪退问题:需要配置兼容性
  3. 乱码问题:配置文件中设置

配置

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-jqXIFXLy-1663510961704)(Day007_JavaWeb.assets/1655966467567.png)]

总结

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-C1XJdVwr-1663510961704)(Day007_JavaWeb.assets/1655969932331.png)]

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-glkA4hxr-1663510961704)(Day007_JavaWeb.assets/1655970213782.png)]

发布一个网站

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-xGZImW0W-1663510961705)(Day007_JavaWeb.assets/1655970695564.png)]

Http

什么是Http?

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-qx3NjGKi-1663510961705)(Day007_JavaWeb.assets/1656292438371.png)]

两个时代

  • http1.0
    • HTTP/1.0 :客户端可以与web服务器连接后,只能获得一个web资源,断开连接(烧流量)
  • http2.0
    • HTTP/1.1:客户端可以与web服务器连接后,可以获得多个web资源,不用每次请求连接

http请求

  • 客户端–发请求(Request)–服务器
  • 百度:General
Request URL: https://www.baidu.com/  //请求地址
Request Method: GET					//get方法,post方法
Status Code: 200 OK					//状态码:200
Remote Address: 14.215.177.38:443	//远端服务器地址
  • 百度:Request Headers
Accept: text/html
Accept-Encoding: gzip, deflate, br  //编码
Accept-Language: en-US,en;q=0.9,zh-CN;q=0.8,zh;q=0.7 //语言
Cache-Control: max-age=0    //缓存控制
Connection: keep-alive		//保持连接

1、请求行

  • 请求行中的请求方式:GET
  • 请求方式:GetPost,HEAD,DELETE,PUT,TRACT…
    • GET:一次请求可以携带的参数比较少,大小有限制,会在浏览器的URL地址栏显示数据内容,不安全,但高效。
    • POST:一次请求可以携带的参数没有限制,大小没有限制,不会在浏览器的URL地址栏显示数据内容,安全,但不高效。

2、消息头

Accept: //告诉服务器它所支持的数据类型
Accept-Encoding: //支持哪种编码格式:GBK,UTF-8,GB2312,ISO8859-1
Accept-Language: //告诉服务器它的语言环境
Cache-Control: //缓存控制
Connection: //告诉服务器,请求完成是断开还是保持连接
HOST: //主机

Http响应

  • 服务器–响应–客户端
  • 百度:Response Headers
Cache-Control: private						//缓存控制
Connection: keep-alive						//保持连接
Content-Encoding: gzip						//编码
Content-Type: text/html;charset=utf-8		//类型
Accept: //告诉服务器它所支持的数据类型
Accept-Encoding: //支持哪种编码格式:GBK,UTF-8,GB2312,ISO8859-1
Accept-Language: //告诉服务器它的语言环境
Cache-Control: //缓存控制
Connection: //告诉服务器,请求完成是断开还是保持连接
HOST: //主机
Refresh://告诉客户端多久刷新一次
Location//让网页重新定位;

响应体

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:网关错误

常见面试题:

二面:当你的浏览器中地址栏输入地址并回车的一瞬间到页面=能够展示回来,经历了什么?

  1. **(域名解析)**在客户端,浏览器输入地址后,首先会在windows系统文件的hosts中查找是否有对应的ip地址,如果没有则需要向DNS域名解析服务器询问该域名对应的ip地址。
  2. **(TCP三次握手)**获取相应的ip地址后,客户端与服务器端建立TCP连接(三次握手),(网络层,数据链路层,物理层)

三次握手

​ 第一次握手:客户端向服务器端发送一个SYN段,该段中包含客户端的初始序列号。

​ 第二次握手:服务器端返回客户端SYN+ACK,该端中包含服务器端的初始序列号,ACK表示,已经确定收到客户端的SYN段。

​ 第三次握手:客户端向服务器端响应一个ACK端,ACK表示,已经确定接受到服务器端的SYN段。

  1. **(建立起TCP连接后发起http请求)**客户端向服务器端发送请求,包含请求行,请求头。主要的两种请求方式(GET与POST)

–>GET:请求能够携带的参数比较少,大小有限制,会在浏览器的URL地址栏显示数据的内容,不安全,但高效。

–>POST:请求能够携带的参数没有限制,大小没有限制,不会在浏览器的URL地址栏显示数据内容,安全,但不高效。

  1. **(服务器响应http请求)**服务器处理请求,并返回响应,包含状态码,响应头,响应体。
  2. **(浏览器解析http代码)**浏览器收到响应,解析http代码渲染页面,并在浏览器页面展示出来。
  3. **(断开连接)**http1.0短连接,http1.1长连接。

Maven

为什么要学习Maven技术?

1,在 JavaWeb 开发中,需要使用大量的 jar 包,我们手动去导入:

2,如何能够让一个东西自动帮我们导入和配置这个 jar 包。

由此,Maven 诞生了!

Maven项目架构管理工具

我们目前就是用来方便导入jar包的

Maven的核心思想约定大于配置

  • 有约束,不要去违反
  • 目录结构有约定

Maven会规定好你该如何去编写我们的java代码,必须要按照这个规范来

配置环境变量

配置如下:系统环境变量,不是用户变量

  • MAVEN_HOME maven的目录(类似JAVA_HOME)
  • M2_HOME maven目录下的bin目录(以后用到,比如spring,springboot)

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-A5ulhIe2-1663510961705)(Day007_JavaWeb.assets/1656297369928.png)]

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-50WjcCk7-1663510961705)(Day007_JavaWeb.assets/1656297382545.png)]

类似 JDK,检测是否安装成功,打开cmd,输入:

mvn -version 注意:mvn来源于bin目录下的mvn

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-AzzkWoka-1663510961706)(Day007_JavaWeb.assets/1656297414457.png)]

配置阿里云镜像

镜像:mirrors

  • 作用:加速我们的下载

国内建议使用阿里云镜像 ,百度一下:Maven 阿里云镜像
放在F:\Software\apache-maven-3.8.1\conf\settings.xml<mirrors></mirrors>标签中

<mirror>
      <id>nexus-aliyun</id>
	  <mirrorOf>*,!jeecg,!jeecg-snapshots</mirrorOf>
      <name>Nexus aliyun</name>
      <url>http://maven.aliyun.com/nexus/content/groups/public/</url>
</mirror>

本地仓库

建立一个本地仓库,可以配多个

F:\Software\apache-maven-3.8.1\conf\settings.xml中找到如下信息:

Default: ${user.home}/.m2/repository  <!--默认的仓库地址-->
<localRepository>/path/to/local/repo</localRepository>

修改为:

<localRepository>D:\Java\apache-maven-3.6.3\maven-repository</localRepository>

同时,在文件夹路径下需要新建文件夹:maven-repository 作为本地仓库

创建一个idea项目

创建的是一个web应用

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-Q4bpAUub-1663510961706)(Day007_JavaWeb.assets/1656298676391.png)]

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-cOeNYd6X-1663510961706)(Day007_JavaWeb.assets/1656299215161.png)]

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-7XwDuYCC-1663510961706)(Day007_JavaWeb.assets/1656299324723.png)]

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-rjZU1zJy-1663510961707)(Day007_JavaWeb.assets/1656309725591.png)]

项目创建成功

更改Maven的配置

注意:idea项目创建成功后,看一眼Maven的配置,确定一下配置文件以及仓库的位置

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-ezwe11EW-1663510961707)(Day007_JavaWeb.assets/1656310030400.png)]

不勾选Maven模版的话会得到一个干净的Maven项目

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-sZ8HH7cs-1663510961707)(Day007_JavaWeb.assets/1656310961798.png)]

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-BK8TC1gy-1663510961707)(Day007_JavaWeb.assets/1656310885654.png)]

标志文件夹

创建的web项目src中没有放置源码的java目录,放置配置文件的resource目录,需要手动添加

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-ATaVCgcb-1663510961707)(Day007_JavaWeb.assets/1656311345519.png)]

第二种方式

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-HJbA7jiU-1663510961707)(Day007_JavaWeb.assets/1656311575998.png)]

在idea中配置tomcat

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-RLYFNBTA-1663510961708)(Day007_JavaWeb.assets/1656311802148.png)]

选择tomcat

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-0ftOpuCz-1663510961708)(Day007_JavaWeb.assets/1656313414225.png)]

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-9z6Gtxcr-1663510961708)(Day007_JavaWeb.assets/1656313719328.png)]

解决警告问题

必须要有的配置:相当于我们访问一个网站,必须要指定一个文件夹名称

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-XGsUnoAE-1663510961708)(Day007_JavaWeb.assets/1656313784533.png)]

配置完成之后启动tomcat

pom文件

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-yOUQUzsO-1663510961708)(Day007_JavaWeb.assets/1656315648143.png)]

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-5X82aLqo-1663510961708)(Day007_JavaWeb.assets/1656315997711.png)]

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-KdPNQWeT-1663510961709)(Day007_JavaWeb.assets/1656316124689.png)]

Maven高级的地方在于,他会自动导入所需jar包所依赖的相关jar包供项目使用

配置文件无法导出或生效的问题的解决方式:

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-ulTDwsp6-1663510961709)(Day007_JavaWeb.assets/1656317014188.png)]

Maven仓库的使用

地址:https://mvnrepository.com/

写一个servlet

找到tomcat的存放目录,双击打开bin目录下的startup.bat文件,启动tomcat

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-XlepG5Et-1663510961709)(Day007_JavaWeb.assets/1656321816900.png)]

进入http://localhost:8080/ 出现此页面,tomcat启动成功

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-2AVWQWhO-1663510961709)(Day007_JavaWeb.assets/1656321962270.png)]

进入webapps目录下的examples

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-SjprisFU-1663510961709)(Day007_JavaWeb.assets/1656321924380.png)]

进入http://localhost:8080/examples/servlets/helloworld.html下查看servlet例子

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-T2jVoQyF-1663510961709)(Day007_JavaWeb.assets/1656322012595.png)]

模仿官网例子写一个servlet

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-q3MPzCWf-1663510961710)(Day007_JavaWeb.assets/1656340813602.png)]

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-2u4vCsir-1663510961710)(Day007_JavaWeb.assets/1656340959699.png)]

查看响应头信息

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-iIvIUrtC-1663510961710)(Day007_JavaWeb.assets/1656341367676.png)]

在servlet中设置头部信息

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-KVwtMgRk-1663510961710)(Day007_JavaWeb.assets/1656341451888.png)]

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-5ul7IpPB-1663510961710)(Day007_JavaWeb.assets/1656341490367.png)]

servlet

什么是servlet?

  • Servlet就是sun公司开发动态web的一门技术
  • Sun在这些API中提供了一个接口Servlet,如果你想开发一个Servlet程序,只需要完成两个小步骤:
    🔺编写一个类,实现Servlet接口
    🔺把开发好的java类部署到web服务器中。
  • 把实现了Servlet接口的java程序叫做Servlet

HelloServlet

Servlet接口在Sun公司有两个默认的实现类:HttpServlet,GenericServlet

1.新建一个web项目,什么也不勾选,删掉src目录

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-OAqHtLLC-1663510961711)(Day007_JavaWeb.assets/1656343397350.png)]

查看空的pom文件

2.关于Maven父子工程的理解

在项目下新建一个子工程作为Maven的主工程,新建Moudel。

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-2iKJ0rNi-1663510961711)(Day007_JavaWeb.assets/1656384623565.png)]

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-BN2kjnYJ-1663510961711)(Day007_JavaWeb.assets/1656384792745.png)]

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-o4VPCPcZ-1663510961711)(Day007_JavaWeb.assets/1656384832528.png)]

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-FrAqNxvN-1663510961711)(Day007_JavaWeb.assets/1656343373415.png)]

3.Maven环境优化

新建一个web项目,模版勾选maven的weapps

  1. 将web.xml配置替换为最新版本
<?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>

  1. 将Maven的结构搭建完整
    • 创建java源码目录
    • 创建配置文件resources目录
    • 创建测试目录test (可选)
    • 创建完成后使目录生效

4.编写一个servlet程序

  • 新建一个包com.kuang.servlet

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-jVnASiNu-1663510961711)(Day007_JavaWeb.assets/1656343639752.png)]

  • 新建一个普通类HelloServlet,实现Servlet接口,继承HttpServlet
package com.kuang.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;

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("HelloServlet");
    }

    @Override
    protected void doPost(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {
        super.doPost(req, resp);
    }
}

5.编写Servlet的映射

为什么需要编写映射?

​ 我们写的是Java程序,但是要通过浏览器访问,而浏览器需要连接web服务器,所以我们需要在web服务中注册我们写的Servlet,还需要给他一个浏览器能够访问的路径

web.xml

<!--     注册Servlet
            servlet-class:注册哪个类,写全限定名(包名+类名)
-->
    <servlet>
        <servlet-name>hello</servlet-name>
        <servlet-class>com.kuang.servlet.HelloServlet</servlet-class>
    </servlet>
<!--    Servlet的请求路径
            url-pattern:请求的路径
-->
    <servlet-mapping>
        <servlet-name>hello</servlet-name>
        <url-pattern>/hello</url-pattern>
    </servlet-mapping>

6.配置Tomcat

注意项目发布的路径

7.启动测试

点击启动程序按钮,等待响应。

Servlet原理

Servlet是由Web服务器调用,Web服务器在收到浏览器请求之后,会进行如下图操作:

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-NNYHK6RN-1663510961712)(Day007_JavaWeb.assets/1656392290013.png)]

Mapping问题

1.一个servlet可以映射一个路径

<servlet-mapping>
        <servlet-name>hello</servlet-name>
        <url-pattern>/hello</url-pattern>
</servlet-mapping>

2.一个servlet可以映射多个路径

<servlet-mapping>
    <servlet-name>hello</servlet-name>
    <url-pattern>/hello</url-pattern>
</servlet-mapping>
<servlet-mapping>
    <servlet-name>hello</servlet-name>
    <url-pattern>/hello2</url-pattern>
</servlet-mapping>
<servlet-mapping>
    <servlet-name>hello</servlet-name>
    <url-pattern>/hello3</url-pattern>
</servlet-mapping>
<servlet-mapping>
    <servlet-name>hello</servlet-name>
    <url-pattern>/hello4</url-pattern>
</servlet-mapping>

3.一个servlet可以映射通用路径

<servlet-mapping>
    <servlet-name>hello</servlet-name>
    <url-pattern>/hello/*</url-pattern>
</servlet-mapping>

4.默认请求路径,会干掉首页,优先级较高(一般不建议这样写)

<servlet-mapping>
    <servlet-name>hello</servlet-name>
    <url-pattern>/*</url-pattern>
</servlet-mapping>

5.可以自定义后缀实现请求映射

<servlet-mapping>
    <servlet-name>hello</servlet-name>
    <url-pattern>*.jxr</url-pattern>
</servlet-mapping>

*** 前面不能加项目映射的路径**

6.优先级问题

固有的映射路径(指定的)的优先级最高,其次是默认的

<!--404-->
<servlet>
    <servlet-name>error</servlet-name>
    <servlet-class>com.jxr.servlet.ErrorServlet</servlet-class>
</servlet>
<servlet-mapping>
    <servlet-name>error</servlet-name>
    <url-pattern>/*</url-pattern>
</servlet-mapping>

public class HelloServlet extends HttpServlet {
    @Override
    protected void doGet(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {
 
        //this.getInitParameter(); 初始化参数
        //this.getServletConfig();  Servlet配置
        //this.getServletContext();  Servlet上下文
        ServletContext servletContext = this.getServletContext();
 
        System.out.println("Hello");
    }
 
}

}

ServletContext

web容器在启动的时候,它会为每个web程序都创建一个对应的ServletContext的对象,它代表了当前的web应用。

ServletContext的作用:

1.共享数据:ServletContext实现servlet之间的数据共享

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-3zoTbNRq-1663510961712)(Day007_JavaWeb.assets/1656399356918.png)]

编写一个servlet,去设置Attribute

public class HelloServlet extends HttpServlet {
    @Override
    protected void doGet(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {
 
        //this.getInitParameter(); 初始化参数
        //this.getServletConfig();  Servlet配置
        //this.getServletContext();  Servlet上下文
        ServletContext context = this.getServletContext();
 
        String username = "张三";//数据
        context.setAttribute("username",username);//将一个数据保存在ServletContext中,Attribute是个键值对形式
    }
 
}

编写另一个servlet,去获取Attribute并返回给页面

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);//将获取到的attribute写入到页面
    }
 
    @Override
    protected void doPost(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {
        doGet(req, resp);
    }
}

在web.xml中编写servlet映射

<?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">
  <servlet>
    <servlet-name>hello</servlet-name>
    <servlet-class>com.hlx.servlet.HelloServlet</servlet-class>
  </servlet>
  <servlet-mapping>
    <servlet-name>hello</servlet-name>
    <url-pattern>/hello</url-pattern>
  </servlet-mapping>
 
  <servlet>
    <servlet-name>getcontext</servlet-name>
    <servlet-class>com.hlx.servlet.GetServlet</servlet-class>
  </servlet>
  <servlet-mapping>
    <servlet-name>getcontext</servlet-name>
    <url-pattern>/getcontext</url-pattern>
  </servlet-mapping>
</web-app>

测试访问,运行服务器,如果先进入/getcontext则得到null,所以得先运行/hello再运行/getcontext

2.获取初始化参数

在web.xml里面可以设置一些参数

 <!--配置一些web应用初始化参数-->
  <context-param>
    <param-name>url</param-name>
    <param-value>jdbc:mysql//localhost:3306</param-value> //jdbc连接数据库的api
  </context-param>
 
  <servlet>
    <servlet-name>geturl</servlet-name>
    <servlet-class>com.jxr.servlet.ServletDemo03</servlet-class>
  </servlet>
  <servlet-mapping>
    <servlet-name>geturl</servlet-name>
    <url-pattern>/geturl</url-pattern>
  </servlet-mapping>

编写servlet程序

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);
    }
 
    @Override
    protected void doPost(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {
    }
}

测试运行:

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-tu1cuTW9-1663510961712)(Day007_JavaWeb.assets/1656403204398.png)]

3.请求转发

编写servlet程序用来转发页面

public class ServletDemo04 extends HttpServlet {
    @Override
    protected void doGet(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {
        ServletContext context = this.getServletContext();
        System.out.println("进入了demo04");
        RequestDispatcher requestDispatcher = context.getRequestDispatcher("/geturl");//转发的请求路径
        requestDispatcher.forward(req,resp);//调用forwa实现请求转发;
        //context.getRequestDispatcher("/geturl").forward(req,resp);一行也能完成
    }
 
    @Override
    protected void doPost(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {
    }
}

在web.xml中编写servlet映射

<servlet>
    <servlet-name>sd4</servlet-name>
    <servlet-class>com.jxr.servlet.ServletDemo04</servlet-class>
  </servlet>
  <servlet-mapping>
    <servlet-name>sd4</servlet-name>
    <url-pattern>/sd4</url-pattern>
  </servlet-mapping>

测试运行

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-5EzAc7zi-1663510961712)(Day007_JavaWeb.assets/1656403342628.png)]

注意: 这里是因为通过requestDispatcher转发的/geturl页面

转发路径不变,但是重定向路径会发生改变。

转发:

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-mohMzaWD-1663510961712)(Day007_JavaWeb.assets/1656403733340.png)]

重定向:

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-VAjqNNN2-1663510961713)(Day007_JavaWeb.assets/1656403935723.png)]

4.读取资源文件

在resources文件下建立properties

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-x4jPNh4l-1663510961713)(Day007_JavaWeb.assets/1656415176521.png)]

在db.properties中填写配置信息

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-4iikvply-1663510961713)(Day007_JavaWeb.assets/1656415204872.png)]

创建PropertiesServlet

public class PropertiesServlet extends HttpServlet{
    public void test(){
        Properties properties = new Properties();
    }
}

然后使用maven 的clear执行清除操作,target被清空,再启动tomcat,观察properties的路径

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-OCHNJXgM-1663510961713)(Day007_JavaWeb.assets/1656415758840.png)]

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-arBnxHOc-1663510961713)(Day007_JavaWeb.assets/1656415921673.png)]

注意:若在java源码目录的com.hlx.servlet的文件下创建properties,则target里没有properties,因为maven在导出资源的时候会资源过滤,就如之前博客所说的,要在pom里面配置。

<!--在build中配置resources,来防止我们资源导出失败的问题-->
    <build>
        <resources>
            <resource>
                <directory>src/main/resources</directory>
                <includes>
                    <include>**/*.properties</include>
                    <include>**/*.xml</include>
                </excludes>
                <filtering>true</filtering>
            </resource>
            <resource>
                <directory>src/main/java</directory>
                <includes>
                    <include>**/*.properties</include>
                    <include>**/*.xml</include>
                </includes>
                <filtering>true</filtering>
            </resource>
        </resources>
    </build>

记得重启idea

Properties:

1.在java目录下新建properties

2.在resources目录下新建properties

发现都被打包到同一个路径:class,我们俗称这个为classpath,即类路径

思路:需要一个文件流

public class ServletDemo05 extends HttpServlet {
    @Override
    protected void doGet(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {
        // getResourceAsStream()  把资源转换为流
        InputStream is = this.getServletContext().getResourceAsStream("/WEB-INF/classes/db.properties");//  /WEB-INF...中的/不能省略,代表的是当前项目
 
        Properties prop= new Properties();//读取properties文件
        prop.load(is); //加载文件流
        String username = prop.getProperty("username");
        String password = prop.getProperty("password");
        resp.getWriter().print(username + password);
    }
 
    @Override
    protected void doPost(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {
    }
}

启动tomcat,访问测试

HttpServletResponse

web服务器接收到客户端的http请求,针对这个请求,分别创建一个代表请求的HttpServletRequest对象,代表响应的一个HttpServletResponse对象;

如果要获取客户端请求过来的参数:找HttpServletRequest;

如果要给客户端响应一些信息:找HttpServletResponse。

方法简单分类

负责向浏览器发送数据的方法
ServletOutputStream getOutputStream() throws IOException;

PrintWriter getWriter() throws IOException;


这两个方法是ServletResponse这个接口里面的

负责向浏览器发送响应头的方法
void setCharacterEncoding(String var1);

void setContentLength(int var1);
 
void setContentLengthLong(long var1);
 
void setContentType(String var1);
 
void setDateHeader(String var1, long var2);
 
void addDateHeader(String var1, long var2);
 
void setHeader(String var1, String var2);
 
void addHeader(String var1, String var2);
 
void setIntHeader(String var1, int var2);
 
void addIntHeader(String var1, int var2);

状态码
    int SC_CONTINUE = 100;
    int SC_SWITCHING_PROTOCOLS = 101;
    int SC_OK = 200;
    int SC_CREATED = 201;
    int SC_ACCEPTED = 202;
    int SC_NON_AUTHORITATIVE_INFORMATION = 203;
    int SC_NO_CONTENT = 204;
    int SC_RESET_CONTENT = 205;
    int SC_PARTIAL_CONTENT = 206;
    int SC_MULTIPLE_CHOICES = 300;
    int SC_MOVED_PERMANENTLY = 301;
    int SC_MOVED_TEMPORARILY = 302;
    int SC_FOUND = 302;
    int SC_SEE_OTHER = 303;
    int SC_NOT_MODIFIED = 304;
    int SC_USE_PROXY = 305;
    int SC_TEMPORARY_REDIRECT = 307;
    int SC_BAD_REQUEST = 400;
    int SC_UNAUTHORIZED = 401;
    int SC_PAYMENT_REQUIRED = 402;
    int SC_FORBIDDEN = 403;
    int SC_NOT_FOUND = 404;
    int SC_METHOD_NOT_ALLOWED = 405;
    int SC_NOT_ACCEPTABLE = 406;
    int SC_PROXY_AUTHENTICATION_REQUIRED = 407;
    int SC_REQUEST_TIMEOUT = 408;
    int SC_CONFLICT = 409;
    int SC_GONE = 410;
    int SC_LENGTH_REQUIRED = 411;
    int SC_PRECONDITION_FAILED = 412;
    int SC_REQUEST_ENTITY_TOO_LARGE = 413;
    int SC_REQUEST_URI_TOO_LONG = 414;
    int SC_UNSUPPORTED_MEDIA_TYPE = 415;
    int SC_REQUESTED_RANGE_NOT_SATISFIABLE = 416;
    int SC_EXPECTATION_FAILED = 417;
    int SC_INTERNAL_SERVER_ERROR = 500;
    int SC_NOT_IMPLEMENTED = 501;
    int SC_BAD_GATEWAY = 502;
    int SC_SERVICE_UNAVAILABLE = 503;
    int SC_GATEWAY_TIMEOUT = 504;
    int SC_HTTP_VERSION_NOT_SUPPORTED = 505;

常见应用
向浏览器输出消息(之前一直在用)
public class IsLoginServlets extends HttpServlet {
	@Override
	protected void doGet(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {
    	//设置输入格式为UTF-8
    	resp.setCharacterEncoding("UTF-8");
    	//设置内容类型为html,UTF-8
    	resp.setContentType("text/html;charset=utf-8");
    	//获得打印流对象
        PrintWriter out = resp.getWriter();
        //此打印流对象可向浏览器输出信息
        out.write("Do");
        out.write(" you");
        out.write(" like");
        out.write(" wanyouxi?");
        //清理打印流
        out.flush();
        //冲洗
	}
}    

下载文件

步骤:

  1. 要获取下载文件的路径
  2. 下载的文件名是啥?
  3. 设置想办法让浏览器能够支持下载我们需要的东西
  4. 获取下载文件的输入流
  5. 创建缓冲区
  6. 获取OutputStream对象
  7. 将FileOutputStream流写入到buffer缓冲区
  8. 使用OutputStream将缓冲区中的数据输出到客户端!
public class FileServlet extends HttpServlet {
    @Override
    protected void doGet(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {
        //        1.要获取下载文件的路径
        String realPath = this.getServletContext().getRealPath("/1.png");
        System.out.println("下载文件的路径:"+ realPath);
        //        2.下载的文件名是啥?
        String fileName = realPath.substring(realPath.lastIndexOf("\\") + 1);
        //        3.设置想办法让浏览器能够支持(Content-Disposition)下载我们需要的东西
        resp.setHeader("Content-Disposition","attachment;filename="+fileName);
        //        4.获取下载文件的输入流
        FileInputStream in = new FileInputStream(realPath);
        //        5.创建缓冲区
        int len = 0;
        byte[] buffer = new byte[1024];
        //        6.获取OutputStream对象
        ServletOutputStream out = resp.getOutputStream();
        //        7.将FileOutputStream流写入到buffer缓冲区
        while ((len=in.read(buffer))>0){
            //    8.使用OutputStream将缓冲区中的数据输出到客户端!
            out.write(buffer,0,len);
        }
 
        in.close();
        out.close();
 
    }
 
    @Override
    protected void doPost(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {
 		doGet(req,resp);
    }
}

映射文件

 <servlet>
        <servlet-name>filedown</servlet-name>
        <servlet-class>com.jxr.servlet.FileServlet</servlet-class>
    </servlet>
    <servlet-mapping>
        <servlet-name>filedown</servlet-name>
        <url-pattern>/down</url-pattern>
    </servlet-mapping>

但是进入到网页中会报500错误,显示系统找不到制定的文件

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-vp7P3vec-1663510961714)(Day007_JavaWeb.assets/1656473007160.png)]

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-T5ImC0M2-1663510961714)(Day007_JavaWeb.assets/1656473033995.png)]

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-v1Nj4Ou8-1663510961714)(Day007_JavaWeb.assets/1656473051894.png)]

//        3.设置想办法让浏览器能够支持(Content-Disposition)下载我们需要的东西,使用URLEncoder.encode()可以读取中文文件名
        resp.setHeader("Content-Disposition","attachment;filename="+ URLEncoder.encode(fileName,"UTF-8"));

验证码功能

验证怎么来的?
1.前端实现
2.后端实现,需要用到Java的图片类,生产一个图片

public class ImageServlet extends HttpServlet {
    @Override
    protected void doGet(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {
 
        //如何让浏览器3秒自动刷新一次;
        resp.setHeader("refresh","3");
 
        //在内存中创建一个图片
        BufferedImage image = new BufferedImage(80,20,BufferedImage.TYPE_INT_BGR);
        //得到图片
        Graphics2D g = (Graphics2D) image.getGraphics();//2d画笔
        //设置图片的背景颜色
        g.setColor(Color.white);
        // 设置图片的填充形状为矩形
        g.fillRect(0,0,80,20);
        
        //给图片写数据
        g.setColor(Color.BLUE);  //设置颜色
        g.setFont(new Font(null,Font.BOLD,20));//字体样式,大小
        g.drawString(makeNum(),0,20);
 
        //告诉浏览器,这个请求用图片的方式打开
        resp.setContentType("image/jpg");
        //网站存在缓存,不让浏览器缓存(可以不用学)
        resp.setDateHeader("expires",-1);
        resp.setHeader("Cache-Control","no-cache");//设置缓存控制为不缓存
        resp.setHeader("Pragma","no-cahce");
 
        //把图片写给浏览器
        boolean write = ImageIO.write(image,"jpg",resp.getOutputStream());
 
    }
    //生成随机数
    private String makeNum(){
        Random random = new Random();
        String num =  random.nextInt(9999999) + "";
        StringBuffer sb = new StringBuffer();//stringbuffer是可变字符串
        for(int i = 0;i<7-num.length();i++){
            sb.append("0");
        }
        String s = sb.toString() + num;
        num = sb.toString() + num;
        return num;
    }
 
    @Override
    protected void doPost(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {
        doGet(req,resp);
    }
}

编写映射文件

 <servlet>
        <servlet-name>image</servlet-name>
        <servlet-class>com.hlx.servlet.ImageServlet</servlet-class>
    </servlet>
    <servlet-mapping>
        <servlet-name>image</servlet-name>
        <url-pattern>/image</url-pattern>
    </servlet-mapping>

实现重定向!!

B一个web资源收到客户端A请求后,B他会通知A客户端去访问另外一个web资源C,这个过程叫重定向

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-v5zefht3-1663510961714)(Day007_JavaWeb.assets/1656491512232.png)]

常见场景:

1.用户登录

使用到的方法

void sendRedirect(String var1) throws IOException;

编写servlet

public class RedirectServlet extends HttpServlet {
    @Override
    protected void doGet(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {
        /*
        resp.setHeader("Location","/r/img");
        resp.setStatus(302); // 重定向的状态码
        重定向的原理
        */
 
        // tomcat设置的初始路径为localhost:8080/r 
        resp.sendRedirect("/r/image");//重定向
    }
 
    @Override
    protected void doPost(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {
 		 doGet(req,resp);
    }
}

添加映射

 <servlet>
        <servlet-name>redirect</servlet-name>
        <servlet-class>com.jxr.servlet.RedirectServlet</servlet-class>
 </servlet>
 <servlet-mapping>
        <servlet-name>redirect</servlet-name>
        <url-pattern>/red</url-pattern>
 </servlet-mapping>

测试,进入/red之后路径会自动跳转到/image

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-p5dc39ip-1663510961714)(Day007_JavaWeb.assets/1656494781223.png)]


面试题:请你聊聊重定向和转发的区别?

相同点

页面都会实现跳转

不同点

  • 请求转发的时候,url不会产生变化 307
  • 重定向时候,url地址栏会发生变化 302
利用重定向实现登录和页面跳转
为index页面设置登录功能
<html>
<body>
<h2>Hello World!</h2>
 
<%--这里提交的路径,需要寻找到项目的路径--%>
<%--${pageContext.request.contextPath}代表当前的项目--%>
 
<form action="${pageContext.request.contextPath}/login" method="get">
    用户名:<input type="text" name="username">
    密码:<input type="password" name="password">
    <input type="submit">
</form>
</body>
</html>

编写登录成功页面

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-03HyhMQb-1663510961715)(Day007_JavaWeb.assets/1656515987326.png)]

设置相应的类和方法以及servlet映射:
public class RequestTest extends HttpServlet {
    @Override
    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);
 
        //重定向的时候一定要注意路径的问题,否则就会404
        resp.sendRedirect("/r/success.jsp");
    }
 
    @Override
    protected void doPost(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {
 
    }
}

映射:

 <servlet>
        <servlet-name>request</servlet-name>
        <servlet-class>com.jxr.servlet.RequestTest</servlet-class>
    </servlet>
    <servlet-mapping>
        <servlet-name>request</servlet-name>
        <url-pattern>/login</url-pattern>
    </servlet-mapping>

并在webapps下创建success.jsp,(记得在pom下设置资源过滤,不然target文件中没有success.jsp,会报404错误)

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-Q8PtLoDL-1663510961715)(Day007_JavaWeb.assets/1656515207291.png)]

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-AYy9Ghia-1663510961715)(Day007_JavaWeb.assets/1656515226094.png)]

HttpServletRequest

HttpServletRequest代表客户端的请求,用户通过Http协议访问服务器,HTTP请求中的所有信息会被封装到HttpServletRequest,通过这个HttpServletRequest的方法,获得客户端的所有信息。

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-lrHfMn1b-1663510961715)(Day007_JavaWeb.assets/1656515372813.png)]

Request应用:

获取前端传递的参数 ,请求转发

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-sjkNWIoc-1663510961715)(Day007_JavaWeb.assets/1656515552781.png)]

新建一个Web项目,编写程序

编写jsp文件

<%@ page contentType="text/html;charset=UTF-8" language="java" %>
<html>
<head>
    <title>登录</title>
</head>
<body>
 
<h1>登录</h1>
<div>
<%--这里表单表示的意思:以post方式提交表单,提交到login请求--%>
    <form action="${pageContext.request.contextPath}\login" method="post">
        用户名:<input type="text" name="username"> <br>
        密码:<input type="password" name="password"> <br>
        爱好:
        <input type="checkbox" name="hobbys" value="女孩">女孩
        <input type="checkbox" name="hobbys" value="代码">代码
        <input type="checkbox" name="hobbys" value="唱歌">唱歌
        <input type="checkbox" name="hobbys" value="电影">电影
 
        <br>
        <input type="submit">
    </form>
</div>
 
</body>
</html>

编写登录成功页面

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-LZlK5FQR-1663510961716)(Day007_JavaWeb.assets/1656516019461.png)]

编写servlet

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[] parameterValues = req.getParameterValues("hobbys");
       
        System.out.println("=======================");
        System.out.println(username);
        System.out.println(password);
        System.out.println(Arrays.toString(parameterValues)); // 将数组以字符串形式输出
        System.out.println("=======================");
 
        //resp.sendRedirect("/request/success.jsp");重定向
 
        //通过请求转发
        req.getRequestDispatcher("/success.jsp").forward(req,resp);//注意路径与重定向不一样 这里的  / 代表当前web应用
    }
 
    @Override
    protected void doPost(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {
        doGet(req, resp);
    }
 
}

编写映射

 <servlet>
        <servlet-name>LohinServlet</servlet-name>
        <servlet-class>com.jxr.servlet.LoginServlet</servlet-class>
    </servlet>
    <servlet-mapping>
        <servlet-name>LohinServlet</servlet-name>
        <url-pattern>/login</url-pattern>
    </servlet-mapping>

以实现登录成功后跳转,且获得登录提交信息的功能

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-xvSIFAwT-1663510961716)(Day007_JavaWeb.assets/1656515845076.png)]

Cookie和Session

会话

会话:用户打开一个浏览器,点击了很多超链接,访问多个web资源,最后关闭浏览器,整个这个过程可以称之为会话。

**有状态会话:**一个同学来过教师,下次再来教师,我们会知道这个同学曾经来过,称为有状态会话。

怎么证明你属于一个公司?

你 公司

  1. 发票 公司给你开过发票
  2. 公司登记 公司标记过你是公司职员

一个网站,怎么证明你来过?

客户端 服务端

  1. 服务端给客户端一个信件(cookie),客户端下次访问服务端带上信件(cookie)就可以了; cookie
  2. 服务器登记你来过了,下次你来的时候我来匹配你; session

保存会话的两种技术:

cookie:
客户端技术(响应、请求)

session:
服务器端技术,利用这个技术,可以保存用户的会话信息 。我们可以把信息或者数据放在Session中!

常见场景:网站登录之后,你下次不用再登录了,第二次访问直接就上去了!

Cookie:
1.从请求中拿到cookie信息

2.服务器响应给客户端cookie

保存用户上一次访问的时间

//保存用户上一次访问的时间
public class CookieDemo01 extends HttpServlet {
    @Override
    protected void doGet(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {
        //服务器,告诉你来的时间,把这个时间封装成一个信件,你下次来的时候带过来,服务器就知道你来了
 
        //解决中文乱码
        req.setCharacterEncoding("utf-8");
        resp.setCharacterEncoding("utf-8");
 
        PrintWriter out = resp.getWriter();  //返回响应给客户端
 
        //Cookie 服务器端从客户端获取
        Cookie[] cookies = req.getCookies();//这里返回数组,说明Cookie可能存在多个
 
        //判断cookies是否存在
        if(cookies!=null){
            //如果存在怎么办
            out.write("你上一次访问的时间是:");
 
            for(int i = 0;i<cookies.length;i++){
                Cookie cookie = cookies[i];
                //获取cookie的名字
                if(cookie.getName().equals("lastLoginTime")){
                    //获取cookie中的值
                    long lastLoginTime=Long.parseLong(cookie.getValue());
                    Date date = new Date(lastLoginTime);
                    out.write(String.valueOf(date));
                }
            }
        }else {
            out.write("这是你第一次访问本站");
        }
 
        //服务器给客户端响应一个cookie
        Cookie cookie = new Cookie("lastLoginTime", System.currentTimeMillis()+"");
 
        //设置cookie有效期为一天
        cookie.setMaxAge(24*60*60);
 
        resp.addCookie(cookie);
    }
 
    @Override
    protected void doPost(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {
    }
 
}

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-VPUAnwbj-1663510961716)(Day007_JavaWeb.assets/1656555222825.png)]

获得Cookie

Cookie[] cookies = req.getCookies();//获得cookie
cookie.getName();//获得cookie的key
cookie.getValue();//获得cookie的value
new Cookie(key,value);//新建一个cookie
cookie.setMaxAge();//设置cookie的有效期
resp.addCookie(cookie);//响应给客户端一个cookie

cookie:一般会保存在本地的用户目录下appdata

一个网站的cookie是否存在上限?

  • 一个Cookie只能保存一个信息
  • 一个Web站点可以给浏览器发送多个cookie,一个站点最多存放20个cookie
  • 一个Cookie的大小有限制,大概是4kb
  • 浏览器的cookie上限为300个
public class CookieDemo02 extends HttpServlet {
    @Override
    protected void doGet(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {
        //创建一个cookie,名字必须要和要删除的名字一致
        Cookie cookie = new Cookie("lastLoginTime", System.currentTimeMillis()+"");
 
        //将cookie有效期设置为0,即立刻过期
        cookie.setMaxAge(0);
 
        resp.addCookie(cookie);
    }
 
    @Override
    protected void doPost(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {
        doGet(req, resp);
    }
}

运行上段代码可以将demo1的cookie删除掉

中文数据的传递

//中文数据传递
public class CookieDemo03 extends HttpServlet {
    @Override
    protected void doGet(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {
        //解决中文乱码
        req.setCharacterEncoding("utf-8");
        resp.setCharacterEncoding("utf-8");
 
        PrintWriter out = resp.getWriter();
        //Cookie 服务器端从客户端获取
        Cookie[] cookies = req.getCookies();//这里返回数组,说明Cookie可能存在多个
        //判断cookies是否存在
        if(cookies!=null){
            //如果存在怎么办
            out.write("你上一次访问的时间是:");
 
            for(int i = 0;i<cookies.length;i++){
                Cookie cookie = cookies[i];
                //获取cookie的名字
                if(cookie.getName().equals("name")){
                    //获取cookie中的值
                    //System.out.println(cookie.getValue());
                    out.write(cookie.getValue());
                }
            }
        }else {
            out.write("这是你第一次访问本站");
        }
 
        Cookie cookie = new Cookie("name","爪哇");
        resp.addCookie(cookie);
    }
 
    @Override
    protected void doPost(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {
        doGet(req, resp);
    }
}

评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值