最近在学习狂神的javaweb系列课程,笔记分享如下
[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-HWT1pV0p-1603285419026)(/home/guos/.config/Typora/typora-user-images/image-20201012170554207.png)]
[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-KpqTvIhy-1603285419028)(file:///home/guos/.config/Typora/typora-user-images/image-20201012165023514.png?lastModify=1602492621)]
可以配置端口号
Tomcat的默认端口号: 8080
MySQL的默认端口号:3306
http默认端口号:80
https的默认端口号:443
<Connector port="8080" protocol="HTTP/1.1" connectionTimeout="20000" redirectPort="8443"/>可以配置主机的名称
默认的主机名为:localhost-> 127.0.0.1
默认的网站应用存放位置为: webspps
<Host name="localhost" appBase="webapps" unpackWARs="true" autoDeploy="true">请谈谈网站是如何进行访问的?
输入一个域名,回车
检查本机的C:\Winsows\System32\drivers\etc\hosts配置文件下有没有这个域名的映射
1)有直接返回对应ip地址,在这个地址中有我们需要访问的web程序,可以直接访问
127.0.0.1 www.qinjiang.com 2)没有:去DNS服务器找,找到的话就返回,找不到就找不到:
[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-qnq7CqhZ-1603285419030)(/home/guos/.config/Typora/typora-user-images/image-20201012172111249.png)]
将自己写的网站,放到服务器(Tomcat)中指定的应用文件夹(webapps)下,就可以通过 localhost:8080/kuangsudy/ 进行访问;
网站应该有的结构
[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-EwqZYntZ-1603285419031)(/home/guos/.config/Typora/typora-user-images/image-20201012182026126.png)]
超文本传输协议,是一个基于请求与响应,无状态的,应用层的协议,常基于TCP/IP协议传输数据,互联网上应用最为广泛的一种网络协议,所有的WWW文件都必须遵守这个标准。设计HTTP的初衷是为了提供一种发布和接收HTML页面的方法。
文本: html, 字符串超文本:图片、音乐、视频、定位、地图端口号:80https: 安全的
端口:443基于HTTP协议,通过SSL或TLS提供加密处理数据、验证对方身份以及数据完整性保护
客户端–发请求–服务器
[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-gOxdi4zi-1603285419032)(/home/guos/.config/Typora/typora-user-images/image-20201012190350843.png)]
[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-Yeuk5wk5-1603285419034)(/home/guos/.config/Typora/typora-user-images/image-20201012184433869.png)]
[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-b6H5V9Px-1603285419034)(/home/guos/.config/Typora/typora-user-images/image-20201012191518329.png)]
200: 请求响应成功
3×× :请求重定向
重定向: 重新到给的新位置去404: 找不到资源
资源不存在
5××:服务器代码错误
常见面试题:
当你在浏览器的地址栏输入地址并回车的一瞬间到页面能够展示出来,经历了什么
Servlet是由Web服务器调用,具体流程如下:
[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-GNLiYOe9-1603285419035)(/home/guos/桌面/笔记/JavaWeb.assets/image-20201015191724931.png)]
在web.xml中注册Servlet
<!--注册Servlet--> <servlet> <servlet-name>helloServlet</servlet-name> <servlet-class>com.guo.servlet.HelloServlet</servlet-class> </servlet>把实现了Servlet接口的Java程序叫做Servlet
构建一个普通的maven项目,删掉其中的src目录,在里面建立一个个model就是一个个项目,这个空的工程就是maven的主工程;
关于maven父子工程的理解:
父项目中会有
<modules> <module>servlet-01</module> </modules>子项目中会有
<parent> <artifactId>javaweb-02-maven</artifactId> <groupId>com.guo</groupId> <version>1.0-SNAPSHOT</version> </parent>父项目中的jar包子项目可以直接使用
java原型: son extends fatherMaven 环境优化
修改web.xml为最新的 将maven环境构建完整 4.新建包com.guo.servlet 在下面建类HelloServlet, 实现HttpServlet类,重写其中的doGet(),doSet方法
public class HelloServlet extends HttpServlet { @Override protected void doGet(HttpServletRequest req, HttpServletResponse response) throws ServletException, IOException { // 响应的类型: html response.setContentType("text/html"); response.setCharacterEncoding("utf-8"); // 获取响应的输出流 PrintWriter out = response.getWriter(); out.println("<html>"); out.println("<head>"); out.println("<title>Hello Servlet!</title>"); out.println("</head>"); out.println("<body>"); out.println("<h1>Hello Servlet!</h1>"); out.println("</body>"); out.println("</html>"); } @Override protected void doPost(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException { doGet(req, resp); } }在web.xml中配置servlet映射
<!--web.xml是配置web的核心应用--> <!--注册Servlet--> <servlet> <servlet-name>helloServlet</servlet-name> <servlet-class>com.guo.servlet.HelloServlet</servlet-class> </servlet> <!--一个servlet对应一个映射: Mapping--> <servlet-mapping> <servlet-name>helloServlet</servlet-name> <!--请求路径--> <!--请求地址: localhost:8080/项目名/guo--> <url-pattern>/hello</url-pattern> </servlet-mapping>6.配置Tomcat,启动并输入地址就可以访问到 HelloServlet在网页的输出
一个Servlet可以指定一个映射路径
<servlet-mapping> <servlet-name>helloServlet</servlet-name> <!--请求路径--> <!--请求地址: localhost:8080/项目名/guo--> <url-pattern>/guo</url-pattern> </servlet-mapping>一个Servlet可以指定多个映射路径
<servlet-mapping> <servlet-name>helloServlet</servlet-name> <!--请求路径--> <!--请求地址: localhost:8080/项目名/guo--> <url-pattern>/guo</url-pattern> </servlet-mapping> <!--多个映射路径--> <servlet-mapping> <servlet-name>helloServlet</servlet-name> <url-pattern>/guos</url-pattern> </servlet-mapping>一个Servlet可以指定通用映射路径,通用映射路径下在guo/后面输入任意字符都可以访问该网页
<!--通用映射路径--> <servlet-mapping> <servlet-name>helloServlet</servlet-name> <url-pattern>guo/*</url-pattern> </servlet-mapping>默认请求路径
<!--默认映射路径--> <servlet-mapping> <servlet-name>helloServlet</servlet-name> <url-pattern>/*</url-pattern> </servlet-mapping>指定一些后缀或者前缀等
<!--可以自己定义后缀实现请求映射 注意点,*前面不能加映射路径--> <servlet-mapping> <servlet-name>helloServlet</servlet-name> <url-pattern>*.guoshuai</url-pattern> </servlet-mapping>web容器在启动的时候,它会为每个web程序都创建一个ServletContext对象,它代表了当前的应用。
在这个Servlet中保存的数据,在另一个Servlet中可以拿到
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中(以键值对的形式) } } 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 { doGet(req, resp); } }properties
在java目录下新建properties在resources路径下发现: 都打包在了同一个路径下:classes, 我们俗称这个路径为classpath
[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-25MpFJml-1603285419036)(/home/guos/桌面/笔记/JavaWeb.assets/image-20201016215051671.png)]
思路: 需要一个文件流
username=root password=123 protected void doGet(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException { InputStream is = this.getServletContext().getResourceAsStream("/WEB-INF/classes/db.properties"); //配置文件(db.properties)在编译生成的文件中的路径 Properties prop = new Properties(); prop.load(is); // 加载文件流 String username = prop.getProperty("username"); // 获取属性 String password = prop.getProperty("password"); resp.getWriter().print("username: "+username+'\n'+"pwd: "+ password); }访问测试即可;
该类中方法的组成:
负责向浏览器发送数据的方法;负责向浏览器发送响应头的方法;响应状态码下载文件
向浏览器输出消息;
resp.getWriter().print("username: "+username+'\n'+"pwd: "+ password);下载文件
获取下载文件的路径获取下载文件名设置使浏览器支持我们要下载的东西获取下载文件的输入流创建缓冲区获取OutputSteam对象将FileOutputSteam流写入到buffer缓冲区使用OutputSteam将缓冲区的数据输出到客户端验证码功能
验证怎么来的?
前端实现后端实现,需要用到Java的图片类,产生一个图片实现重定向
[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-ZDRZbQpd-1603285419036)(/home/guos/桌面/笔记/JavaWeb.assets/image-20201017132913998.png)]
一个web资源收到客户端请求后,他会通知客户端去访问另一个web资源。这个过程叫做重定向;
常见场景
用户登录 resp.sendRedirect("image");// 重定向测试:
protected void doGet(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException { /* 重定向的原理: resp.setHeader("Location", "image"); resp.setStatus(302);*/ resp.sendRedirect("image");// 重定向 }面试题:请你聊聊重定向和转发的区别?
相同点:
页面都会跳转不同点:
请求转发时,URL地址栏不会发生变化;重定向URL会发生变化。重定向的编码为302, 请求转发编码307HttpServletRequest 代表客户端的一个请求,用户通过HTTP协议访问服务器,请求中的所有信息会被封装到HttpServletRequest, 通过HttpServletRequest的方法获取客户端的所有信息。
1 获取前端参数
2 请求转发
cookie
客户端技术(响应、请求)session
服务器技术,利用这个技术可以保存用户的会话信息,我们可以把信息或者数据放在session中常见问题:
在网站上第一次登录后,第二次打开自动登录
从请求中拿到Cookie;
服务器响应给客户端cookie;
Cookie[] cookies = req.getCookies(); //返回数组,这里说明Cookie可能存在多个 cookie.getName(); // 获得cookie中的key cookie.getValue(); //获得cookie中的value new Cookie("time", System.currentTimeMillis()+""); // 新建一个cookie cookie.setMaxAge(24*60*60); // 设置有效期 resp.addCookie(cookie); // 给客户端响应一个cookie什么是Session?
服务器会给每个用户创建一个Session对象;
一个Session独占一个浏览器,只要浏览器没有关闭,Session就存在;
用户登录之后整个网站都可以访问
[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-yhADa1b0-1603285419037)(/home/guos/桌面/笔记/JavaWeb.assets/image-20201017214757557.png)]
Session和Cookie的区别:
cookie是把用户的数据写给用户的浏览器,浏览器保存Session是把用户的数据写到用户独占的Session中,服务器端保存(保存重要的信息,减少服务器资源的浪费)session对象由服务创建;使用场景:
保存一个登录用户的信息;购物车信息;在整个网站中经常会使用的数据,我们将它保存在session中使用Session
@Override protected void doGet(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException { req.setCharacterEncoding("utf-8"); resp.setCharacterEncoding("utf-8"); resp.setContentType("/text/html"); //得到Session HttpSession session = req.getSession(); // 给Session中存东西 session.setAttribute("name", "郭帅"); // 获取Session的id String id = session.getId(); //判断Session是否新创建 if(session.isNew()){ resp.getWriter().write("session创建成功, ID:"+id); }else{ resp.getWriter().write("session已经在服务器中存在了, ID:"+id); } }会话自动过期:web.xml配置
<!--设置session的默认失效时间--> <session-config> <!--15分钟后session自动失效--> <session-timeout>15</session-timeout> </session-config>Java Server Pages: Java服务端页面,也和Servlet一样,用于动态web技术
最大的特点:
写Jsp就像在写HTML区别: HTML只能给用户提供静态数据;JSP页面可以嵌入Java代码,为用户提供动态数据;[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-nCHg9N4M-1603285419038)(/home/guos/桌面/笔记/JavaWeb.assets/image-20201018161435612.png)]
在Jsp页面中:
只要是Java代码就会原封不动输出;
如果是HTML代码,就会转化为以下格式,输出到前端
out.write("<html>\r\n");jsp有自己的扩充语法,Java的所有语法都支持;
JSP表达式
<%--jsp表达式 作用: 将程序的输出,输出到客户端 <%=变量或表达式%> --%> <%=new java.util.Date()%>jsp脚本片段
<%--Jsp脚本片段--%> <% int sum = 0; for (int i=0; i<100; i++){ sum+=i; } out.print("<h1> Sum= "+sum+"</h1>"); %>jsp声明
<%! static{ System.out.println(); } private int globalVar=0; public void guo{ System.out.println(); } %>jsp声明: 会被编译掉JSP生成的Java类中! 其他的,就会被谁生成到_javaService方法中!
在JSP中嵌入Java代码即可;
实体类
JavaBean有特定的写法:
必须有无参构造属性必须私有化必须有对应的get/set方法一般用来和数据库的字段做映射 ORM;
ORM: 对象关系映射
表–>类字段->属性行记录->对象什么是MVC: Model View Controller (模型,视图,控制器)
[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-LvFeQXLq-1603285419038)(/home/guos/桌面/笔记/JavaWeb.assets/image-20201018184419470.png)]
用户直接访问控制层,控制层就可以直接操作数据库;
Servlet-->CRUD-->数据库 弊端: 程序十分臃肿,不利于维护; servlet代码中: 处理请求、响应、视图跳转、处理JDBC、处理业务代码、处理逻辑代码[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-9b6qa9vc-1603285419040)(/home/guos/桌面/笔记/JavaWeb.assets/image-20201018190257519.png)]
说明:
Dao层是什么?
Service是业务层,Dao是数据访问层,这样的分层是基于MVC架构来说的,分层的主要作用是解耦。对于Spring这样的框架,(View\Web)表示层调用控制层(Controller),控制层调用业务层(Service),业务层调用数据访问层(Dao)。具体起来,Dao的作用是封装对数据库的访问:增删改查,不涉及业务逻辑,只是达到按某个条件获得指定数据的要求; 而Service,则是专注业务逻辑,对于其中需要的数据库操作,都通过Dao去实现;Model
业务处理: 业务逻辑(Service)数据访问层: CRUD(Dao)View
展示数据提供链接,发起Servlet请求Controller
接收用户请求(req:请求参数,Session信息…)交给业务层处理对应的代码控制视图跳转 举例 登录操作在MVC架构中的解释: 用户登录-->Controller接收用户的登录请求-->处理用户的请求(接收用户的登录参数,用户名,密码)-->交给业务层处理登录业务(判断用户名、密码是否正确-->Dao层查询用户名和密码是否正确-->数据库Filter: 过滤器,用来过滤网站的数据;
处理中文乱码登录验证[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-pwA5JTqg-1603285419040)(/home/guos/桌面/笔记/JavaWeb.assets/image-20201018193808624.png)]
新建一个javaweb项目;
编写过滤器
导包不要错,Filter实现 javax.servlet.Filter这个接口;
代码实现,重写对应的方法即可
public class CharacterEncodingFilter implements Filter { @Override // 初始化: web服务器一旦启动就初始化完成,随时等待过滤对象的出现 public void init(FilterConfig filterConfig) throws ServletException { System.out.println("过滤器参数初始化"); } @Override // 1.doFilter中的所有代码,在过滤特定请求时都会执行 // 2.必须要让过滤器继续通行 public void doFilter(ServletRequest servletRequest, ServletResponse servletResponse, FilterChain filterChain) throws IOException, ServletException { servletRequest.setCharacterEncoding("UTF-8"); servletResponse.setCharacterEncoding("UTF-8"); servletResponse.setContentType("text/html;charset=UTF-8"); System.out.println("过滤器执行前"); filterChain.doFilter(servletRequest, servletResponse); //让我们的请求继续走,如果不写,程序在这里就会被拦截 System.out.println("过滤器执行后"); } @Override // web服务器关闭时,过滤自动销毁 public void destroy() { System.out.println("过滤器销毁"); } }在web.xml中配置Filter
<filter> <filter-name>filter</filter-name> <filter-class>com.guo.filter.CharacterEncodingFilter</filter-class> </filter> <filter-mapping> <filter-name>filter</filter-name> <url-pattern>/show/*</url-pattern> </filter-mapping>