黑马程序员技术交流社区

标题: web核心 [打印本页]

作者: liweihao5253    时间: 2019-9-6 15:56
标题: web核心
08.28
请求转发
request.getRequestDispatcher("url").forward(req,res)
知识:WEB-INF目录下的资源不能被浏览器直接访问!只能通过内部的请求转发访问!
请求转发时,请求是什么方式就一直保持该方式,doGet就一直doGet,doGet就一直doGet
域对象数据共享三个方法
    setAttribute("",Object)
    getAttribute("")
    removeAttribute("")

request域可以做数据共享
ServletContext对象也能共享数据,该对象通过request来获得:request.getServletContext()
知识:如果导入外部jar包,一定要在WEB-INF下创建lib目录,一定是lib目录!不能错,这是服务器的硬性要求

beanUtils类工具的使用
populate():(给文件)添加数据
反射 ----内省:根据属性名取得对应的方法对象并调用
注意区分对象的属性和成员变量的区别(截取get之后的方法名)
使用方法:
User user = new User();
populate(user,request.getParametersMap);
populate方法接受一个空的对象,所以需要手动new一个对象传给它

响应状态码分类
1xx:服务器接收客户端消息但未接收完成,等待一段时间后响应1xx,询问客户端是否发送完
2xx:200 成功
3xx:重定向 302(重定向)   304(访问缓存)
4xx:400(坏的请求)  客户端错误 404(找不到资源)403(没有权限)  405(请求方法不支持,参考                HttpServlet源码)
5xx:服务器错误 500(服务器内部出现异常)

常见响应头:
Content-Type
content-disposition 默认值为in-line 用来设置是不是要下载
response.setHeader("Content-Type","text/html;charset=utf-8");
response.setHeader("content-disposition","attachment filename=");

响应头和请求头的区别
请求头:发送请求时浏览器->服务器的数据
响应头:服务器处理完请求后,写回浏览器的数据

重定向
request.sendRedirect(String url);

重定向和请求跳转的区别:

区分基于服务器的绝对路径和基于浏览器的绝对路径:
返回给浏览器的需要前缀项目的逻辑路径
服务器内部调用的不需要前缀项目逻辑路径
这是因为!!
对于浏览器来说,它看到的是整个服务器,因此根路径就是服务器的根路径
但是对于Servlet来说,它只能看到他所在的Application,因此根路径是逻辑目录下的根路径
简单来说,二者视野不一样,因此根路径的定位不一样

如何动态获取项目的虚拟目录(逻辑目录)?
强烈建议使用动态方式获取项目的逻辑目录
牢记request.getContextPah()方法

补充知识:
tomcat服务器默认使用ISO-8859-1编码,因此根本不能正常处理中文,因此会显示?
注意?类乱码和其他的乱码有区别, ?类的乱码是ISO-8859-1无法处理中文导致的,其他类的乱码是因为中文字符集不一致导致的
注意,response在设置编码的时候,设置编码的语句一定要放在获得流之前!
response.setContentType("text/html;charset=utf-8") 注意这个方法做了两件事

有时候,为了让中文字符适应某些特殊要求(如http header头要求其内容必须为iso8859-1编码),可能会通过将中文字符按照字节方式来编码的情况,如
  String s_iso88591 = new String("深".getBytes("UTF-8"),"ISO8859-1"),
  这样得到的s_iso8859-1字符串实际是三个在 ISO8859-1中的字符,在将这些字符传递到目的地后,目的地程序再通过相反的方式
        String s_utf8 = new String(s_iso88591.getBytes("ISO8859-1"),"UTF-8")来得到正确的中文汉字“深”。这样就既保证了遵守协议规定、也支持中文。
这个过程相当于两层编码、两层解码

自从Tomcat5.x开始,GET和POST方法提交的信息,Tomcat采用了不同的方式来处理编码,对于POST请求,Tomcat会仍然使用request.setCharacterEncoding方法所设置的编码来处理,如果未设置,则使用默认的iso-8859-1编码。而GET请求则不同,Tomcat对GET请求并不会考虑使用request.setCharacterEncoding方法设置的编码,而会永远使用iso-8859-1编码,因此,tomcat将会使用iso-8859-1将提交的字节转换成字符串。
因此request.setCharacterEncoding()只适合post请求处理乱码

快捷键ctrl+shift+u 大小写转换
注意,使用JdbcTemplate框架的时候,JavaBean中的成员变量要使用包装类型,防止数据库取出null的时候抛异常

服务器缓存问题
通过get请求 图片 js css时会缓存
如何清除缓存问题?
请求地址不变,请求参数每次改变即可

08.29
request的几个作用:
    获取请求参数
    请求转发
    作为域对象共享数据
    获取ServletContext对象

ServletContext对象:
代表整个web应用,可以和Servlet容器通信
三个作用:
    1、作为域对象数据共享(范围是application)
    2、获取文件的MIME类型
    3、获取下载文件的真实(服务器)路径(磁盘路径,不是网络路径)

如何获取ServletContext?
request.getServletContext();
也可以通过HttpServlet提供的方法获取
this.getServletContext();

ServletContext是项目的全局单例,在tomcat启动项目之后创建

回忆 == equels hascode的区别!!

什么是MIME?
在互联网通信过程中定义的一种文件数据类型
格式:大类型/小类型 text/html         image/jpeg
例如:content-type:text/html
如何获取?
getMimeType(String file) 传入带扩展名的文件名 返回字符串
原理:
根据后缀名去web.xml中查询对应的文件类型
缺陷:无法获取文件的真实类型,无法识别伪造的后缀名文件
记住几个常见的MIME类型
text/html
application/json

ServletContext作为域对象
setAttribute
getAttribute
removeAttribute

ServletContext的域有多大?
整个Application(项目)中的数据都可以共享

ServletContext获取文件真实路径(本地磁盘路径)
方法:
getRealPath(String path) 返回一个字符串

问:src下的文件位置在哪里?
在WEB-INF/classes目录下

文件下载案例的中文文件名的问题
使用URL/BASE64进行编码

火狐使用BASE64
其他浏览器使用URL编码

注意!请求/响应 行信息 头信息不可以识别二进制字节,因此但凡是涉及到头信息和行信息的时候要使用URL编码

--------------------------------------------------
会话
一次会话可能包含多次请求和响应
一次会话:浏览器第一次给服务器资源发送请求,会话建立,直到有一方断开为止
一次会话范围内多次请求间共享数据
方式:
1、客户端会话技术 Cookie
2、服务器端会话技术 Session

Cookie 基于浏览器端的会话技术

new Cookie(String k,String v)
response.addCookie()
request.getCookies() 返回Cookie数组
IDEA可以自定义代码模板

响应头 set-cookie:
请求头 cookie:

Cookie的生存周期
默认情况下,Cookie只会存在浏览器内存中,浏览器关闭Cookie就被销毁
如何让Cookie持久化?
持久化之后会变成文件存储在用户的硬盘中
setMaxAge(int seconds)    注意,该方法只是针对某一个Cookie而不是所有Cookie
参数取值情况:
    正数代表持久化存储,并规定了Cookie的存活时间 按秒算
        负数(默认值)代表临时存储
    零 删除Cookie信息

tomcat8及以后的版本 cookie支持中文
tomcat8之前想存中文需要URL编码
建议 如果出现中文/空格/特殊字符,需要先进行URL编码!!

cookie最大4k,最多20个,只是理论值

cookie的共享范围有多大?
默认情况下,cookie只能在一个application中共享,也就是他的范围默认是 "/项目/"
如何扩大/改变范围
使用方法:setPath("/")   重新设置cookie有效路径
该方法默认是setPath("/项目的逻辑路径")

如何改变范围
使用方法:setPath(request.getContextPath()+"/user/a")

注意:Cookie的视野能看到整个服务器,所以设置path为/可以访问到整个项目,但是默认是当前application
因此cookie在设置path的时候要前缀项目的逻辑路径,可以用request.getContextPath()

如何继续扩大,让不同服务器共享
setDomain(String path) 设置cookie有效域名
如果设置一级域名相同,则多个服务器可以共享
setDomain(".baidu.com") 那么tieba.baidu.com和news.baidu.com中cookie可以共享


JS中哪个对象获取参数列表

08.31
JSP:Java Server pages
用于简化书写
JSP的页面内容由动静相结合,既有静态html元素,也有动态逻辑(Java代码)

JSP编译后的资源不在项目内部,而是在下面这个目录下
Using CATALINA_BASE:   "C:\Users\liweihao\.IntelliJIdea2018.2\system\tomcat\Tomcat_8_5_311_Lesson_8"

注意!!!JSP和Servlet有区别的地方
JSP只支持get/post/head这三种请求

JSP的9大内置对象,位于_jspservice()方法中,查看源代码

JSP脚本语法:
<% Java代码 %> :定义的java代码,位于service方法中,可以定义业务逻辑
<%!  %> :感叹号!代表声明语句。  用来定义成员变量和成员方法,建议少定义成员变量,防止出现线程安全问题
<%= Java代码 %> :定义的java代码会输出到页面上,相当于sout,如果不是个变量,会直接把java语句输出

JSP的9大内置对象:
在jsp页面内不需要获取和创建,直接能直接使用的对象
但凡是在service能直接调用的对象,都是JSP的内置对象,注意这点逻辑关系

application    -> ServletContext
session         -> HttpSession
request         -> HttpServletRequest
pageContext  -> PageContext 似乎没啥用,一个页面内还用什么域对象

前四个都是域对象
response          -> HttpServletResponse
out:            ->JspWriter 可以将数据输出到页面上,和response.getWrite().write()类似
        二者区别?前者out可以自动编码,后者write()优先于out输出
config          -> ServletConfig
page            -> Object类型 当前servlet对象
exception     -> 异常


JSP的注释问题
支持html/css/js的注释
html <!-- -->
css /* */
js //    /* */
jsp <%-- --%> 特别注意,jsp注释在页面中是看不到的

两种标签嵌套:
jsp标签嵌套html标签:

html标签嵌套jsp标签:

详解Session
一个作用:作为域对象共享数据
注意,Session的键值对为String-Object 注意和Cookie做区分
如何获取?request.getSession()
Session原理
服务器如何确保在一次会话范围内,多次获取的Session对象是同一个呢?
答:Session是依赖于Cookie的
使用JSP会自动创建Session,直接使用Servlet不会自动创建Session

所谓的一次会话,只是一个概念,无法强制确定,只能通过Cookie推断是否是一次会话

研究一下request.getSession()方法

延长Session的生命周期:
创建Cookie,键为JSESSIONID
Cookie c = new Cookie("JSESSIONID",s.getId())
c.setMaxAge(60*60);

细节
客户端关闭,服务器不关闭,两次获取的session是否是同一个?
客户端不关闭,服务器关闭,两次获取的session是否是同一个?
为了解决问题2,有了session钝化和活化的概念
钝化:服务器正常关闭之前,将session对象序列化到硬盘中
活化:在服务器启动后,将session文件反序列化到内存中
tomcat会自动完成钝化和活化

Session的钝化和活化(tomcat内部实现,但是IDEA完成不了活化操作)

Session的销毁
    服务器非正常关闭
    默认销毁时间30分钟,注意,不是Cookie销毁,而是服务器把Session回收
    自杀 session.invalidate();
如何配置session生存时间?
总web.xml在找到<session-config>,也可以在项目的web.xml中配置设定该项目的session存活时间

Session特点:
用于存储一次会话的多次请求范围内的数据,在服务器端
Session的Attribute可以存储任意类型和大小的数据

Session与Cookie的区别
存储位置
大小限制
安全性

Session(主菜) Cookie(小饼干)

只有一种情况会产生Session,就是显示调用getSession(),
因此JSP会有Session,自定义Servlet不会产生Session

找时间归纳整理一下和路径有关的视野问题

如何调试web项目?前台浏览器抓包

09.01
JSP指令 <%@  %>
作用:用于配置JSP页面,导入资源文件
格式:<%@ 指令名称 属性名1=属性值1 属性名2=属性值2 %>

三种指令:
page:配置JSP页面,导入java包
    常用属性:
    contentType="text.html;charset=gbk":等同于response.setContentType()
    pageEncoding="GBK"
    buffer="8kb"
    import=“java.util.ArrayList”
    errorPage="error.jsp":当前页面异常后,会跳转到指定页面
    isErrorPage="true":指定当前页面是错误页面
        注意:只有true的时候才能使用exception对象
        exception.getMessage();
taglib(重要):导入标签库资源(JSTL)
    常用属性:
    prefix="c" url="xxx"
    使用的时候用c冒号出来
    <c:

include(了解):页面包含的。导入页面的资源文件
    常用属性:
    file="top.jsp"

JSP支持4种注释
<%--  --%> : 可以注释所有,而且浏览器无法获得,推荐都使用<%-- --%>

JSP九大内置对象

application    -> ServletContext
session         -> HttpSession
request         -> HttpServletRequest
pageContext  -> PageContext 似乎没啥用,一个页面内还用什么域对象,可以获取其他8个对象

前四个都是域对象
response          -> HttpServletResponse
out:            ->JspWriter 可以将数据输出到页面上,和response.getWrite().write()类似
        二者区别?前者out可以自动编码,后者write()优先于out输出
config          -> ServletConfig
page            -> Object类型 当前servlet对象
exception     -> 异常

mvc 开发思想/开发模式/编程思想,千万不要叫设计模式
    其他的模式MVP MVVM
    是什么
    Model-JavaBean(实体类) 完成具体业务操作,如查询数据库,封装对象
    View-JSP/HTML 视图 展示数据
    Controller-Servlet 控制器获取客户端请求,调用模型,交给视图进行展示
    应用场景
    优点
    低耦合、方便维护、利于分工协作   

EL表达式
Expression Language
语法:${表达式}
        判断    ${ 3>4 }
        如何不让jsp解析
        1、在page指令下设置isELIgnored="true" 后期使用框架必须配置为false
        2、使用转义字符\${ 3>4 }
两个作用
    1、运算
    算数运算符 /(div)  %(mod)
    比较运算符
    逻辑运算符&&(and) ||(or) !(not)
    空运算符 empty:功能强大,用于判断字符串、集合、数组是否为null,长度是否为0
        ${empty list}
    2、取值(重点)
    el表达式只能从域对象中获取值
    语法:
    1、${域名称.键名称}
        域名称:pageScope -> pageContext
                     requestScope -> request
                     sessionScope -> session
                     applicationScope -> application(ServletContext)
    2、${键名称}:从最小的域开始查找,找到为止 底层使用request.findAttribute()
    推荐用第二种,但是要求程序设计时存键值对的时候不要在多个域存同样的键

    取基本类型
    取对象
    ${键名.属性名} (必须提供get方法)

EL隐式对象(思考一下隐式对象从哪来的?参考JSP源代码)
${pageContext.request.contextPath}        重点!!!
pageContext对象功能强大,可以获取其他8个JSP内置对象!!
动态获取虚拟目录${pageContext.request.contextPath}
重要应用!
<form action="${pageContext.request.contextPath}/loginServlet">

补充知识点:
JavaBean对象的属性和成员变量有什么区别?
属性:get/set方法后的名字
成员变量:类中定义的变量
回忆BeanUtils工具类

逻辑视图的概念:只有get方法,但是没有对应的成员变量

Date类的Month也是从0开始的


JSTL标签 JavaServer Pages Tag Library JSP标准标签库
    由Apache组织提供的开源免费的jsp标签
用于简化和替换jsp页面上的java代码(尽量不在jsp写java代码)
使用:
导入jar包 到/WEB-INF/lib
引入标签库
    <%@ taglib %>

重点学习
    <c:if
    <c:if test="${判断条件}"></c:if>       如果为真则显示标签体内容
        <c:if test="true">我是真...</c:if>
        test属性会结合EL表达式
        <c:if test="${not empty list}">遍历集合...</c:if>
        <c:if test="${number % 2 != 0}"> ${number}为奇数 </c:if>
        注意:<c:if标签没有else的情况,只能再定义一个<c:if标签
    <c:choose (相当于switch语句)

    <c:foreach  (重点!)
    两种for循环:
    1、普通for循环
    <c:foreach var="i" begin="0" end="9" step="1" varStatus="s">
        ${i} ${s.index} ${s.count}
    </c:foreach>
    2、增强for循环(更重要)
    <c:foreach var="user" items="${list}" varStatus="s">
        ${user.name}
        ${s.index} ${s.count} 注:s.count还是有用的,比如控制隔行变色
    </c:foreach>
   




欢迎光临 黑马程序员技术交流社区 (http://bbs.itheima.com/) 黑马程序员IT技术论坛 X3.2