乱码问题
响应乱码:
先要解决发送数据给服务器时的乱码
response.setCharsetEncoding("utf-8")//即让服务器以utf-8解析数据
再解决浏览器显示乱码的问题
response.setHead("Content-Type","text/html;charset=utf-8")//即给浏览器设置一个头,告诉浏览器以utf-8解析
便捷方式
response.setContentType("text/html;charset=utf-8");
请求乱码
post请求时
request.setCharacterEncoding("utf-8");
get请求时需要自己进行重新编解码
因服务器使用iso8859-1解码,即
string = new String(string.getBytes("iso8859-1"),"utf-8");
4.HttpServletRequest
请求首行的方法
String -- request.getMethod() 获得请求的方式
String -- request.getContextPath() 获得该请求相对于主机的url,即若项目为xxx/xx则获得/项目名/xxx
String -- request.getRemiteAddr() 获得请求客户端的ip
请求头的方法
String -- getHeader(name) 获得指定的请求头的value
Enumeration -- getHeaders(name) 获得指定名称header的values,封装为一个枚举类型
Eunmeration -- getHeaderNames() 获得所有请求头的name,封装为枚举类型
请求体的方法
getParameter(name)---指定name的value
String[] -- getParameterValues(name)---指定naem的多个value,用于多选框之类
Enumeration -- getParameterNames() 获得所有的请求体中name,封装为枚举类型
Map -- getParameterMap() 获得所有请求体中的数据,以键值对封装
5.BeanUtils
BeanUtils对象.population(JavaBean,parameterMap)-----将Map中的数据封装到JavaBean中
类型转换
例:转换为Date类型
DateConverter dateConverter = new DateConverter();
dateConverter.setPattern("yyyy-MM-dd");
ConvertUtils.register(dateConverter, java.util.Date.class);
6.Cookie
Cookie为服务器创建,保存在客户端的数据
底层通过response.addHeander("Set-Cookie","name=value")创建
Cookie默认存活时间为一次会话,可以通过cookie.setMaxAge(int time)设置存活时间
time<0时表示该cookie为会话级别的,=0表示追杀,>0表示手动设置存活时间,单位为s
cookie.setPath()设置cookie的路径,当要能使用此cookie,则路径必须要包括该cookie的路径
cookie.setDomain(),设置Cookie的域,看不懂,研究API
response.addCookie(cookie)----将cookie存入客户端
Cookie[] -- request.getCookies --- 获得客户端请求中的所有cookie
概念:由服务器创建保存在客户端的会话技术
创建:
便捷方式:Cookie cookie = new Cookie(String name,String value);
底层:
创建:response.addHeader("Set-Cookie","username=zhangsan");
获取:request.getHeader("Cookie");
规范:
处了IE6是20个,其余的版本和其它浏览器都是50个cookie
cookie的默认大小为4KB
获得所有Cookie:
Cookie[] cookies = request.getCookies();
Cookie的路径:它只与你归还的路径有关!默认路径为当前你访问的这个Servlet路径。
<url-pattern>/abc/AServlet</url-pattern>
那么此时cookie的默认路径是:/项目名/abc
cookie的路径就是上面那个,如果想要将之前的cookie携带到服务器,你所写的路径就不需包含/项目/abc
设置cookie路径的方法:cookie.setPath();
Cookie的生命:默认是会话级别,你可以设置cookie的生命,方法为cookie.setMaxAge();如果是会话,参数<0;如果想要是持久级别的>0;当设置=0,cookie立即杀死
Cookie的域:cookie.setDomain("/");
其它方法:
响应cookie:response.addCookie(cookie);
获取cookie的名字:cookie.getName();
获取cookie的值:cookie.getValue();
Cookie是基于Http协议的!
7.Session
Session是服务器创建,保存在服务器的数据,session为域对象,作用域为一次会话
当一次会话开始,即浏览器像服务器发送请求,由服务器手动创建一个Session,当一次会话结束,即浏览器关闭,则session的JSESSIONID会丢失,session依旧存在,session的默认存活时间为30m,在Tomcat的默认web.xml中可以修改,可以手动调用session的invalidate方法来销毁session
概念:由服务器创建并保存在服务器的会话技术
创建:
默认情况:
request.getSession(); //如果session池里面有,就返回;如果没有就创建一个新的并返回
request.getSession(true); //如果session池里面有,就返回;如果没有就创建一个新的并返回
request.getSession(false); //如果session池里面有,就返回;如果没有就返回null
如果你访问的是一个JSP页面,那么他就会为你创建一个Session
Session是依赖cookie
session的默认存活时间是30分钟,当然你也可以手动销毁session(session.invalidate())
域对象的使用:
session.setAttribute(String name,Object obj);
session.getAttribute(String name);
session.removeAttribute(String name);
获得ServletContext对象:
session.getServletContext();
三个域对象的对比:
ServletContext: 服务器启动创建关闭销毁 在整个WEB应用中都有效,范围太多,慎用(统计)
HttpSession: 默认手动调用或者访问JSP资源 在一次会话中有效。(登录)
HttpServletRequest 默认情况第一次请求,也可以配置;在一次请求中有效!
实现文件下载上传代码实现
/**
* 文件下载实现
*
* @author ZZ
*
*/
public class DownloadServlet extends HttpServlet {
private static final long serialVersionUID = 1L;
protected void doGet(HttpServletRequest request, HttpServletResponse response)
throws ServletException, IOException {
// 通过.html文件跳转,请求中包含的文件路径,通过request对象来获得路径名
String filename = request.getParameter("filename");
filename = new String(filename.getBytes("iso8859-1"), "utf-8");
/*
*设置 第一个响应头:response.setHeader("Content-Type", fileType);
* 其中fileType是文件的MIME类型 第二个头:response.addHeader("Content-Disposition",
* "attachment;filename="+filename);
* 告诉浏览器这是需要下载的一个文件,即使浏览器能够直接打开,也要给我一个下载框,filename它是文件的名称
*/
// 通过文件的相对路径名来获得文件的MIME类型
String mimeType = this.getServletContext().getMimeType(filename);
// 设置第一个头Content-Type;
response.setHeader("Content-Type", mimeType);
System.out.println(filename+"--------01");
System.out.println(request.getContextPath()+"--------03");
// 通过文件的相对路径调用servletContext的方法获取一个输入流对象is
InputStream is = this.getServletContext().getResourceAsStream(filename);
// 通过获得浏览器的信息来更改浏览器提示的信息User-Agent头中包括了浏览器的信息
String user_Agent = request.getHeader("User-Agent");
// 对浏览器进行判断,分别使用不同的乱码处理方式
if (user_Agent.contains("Firefox")) {
// 说明是火狐浏览器
filename = base64EncodeFileName(filename);
} else {
// 其它浏览器使用URL编码
filename = URLEncoder.encode(filename, "utf-8");
}
System.out.println(filename+"--------02");
// 设置第二个头Content-Disposition
response.setHeader("Content-Disposition", "attachment;filename=" + filename);
// 通过response对象来获得一个输出流os
ServletOutputStream os = response.getOutputStream();
// IO流的文件复制
int length = 0;
byte[] bytes = new byte[1024];
while ((length = is.read(bytes)) != -1) {
os.write(bytes, 0, length);
}
is.close();
os.close();
}
/**
* 9.火狐浏览器解决下载框的中文乱码方法
*
* @param fileName
* @return
*/
public static String base64EncodeFileName(String fileName) {
BASE64Encoder base64Encoder = new BASE64Encoder();
try {
return "=?UTF-8?B?" + new String(base64Encoder.encode(fileName.getBytes("UTF-8"))) + "?=";
} catch (UnsupportedEncodingException e) {
e.printStackTrace();
throw new RuntimeException(e);
}
}
protected void doPost(HttpServletRequest request, HttpServletResponse response)
throws ServletException, IOException {
doGet(request, response);
}
}
文件上传
form表单上传文件
method="post"
enctype="multipart/form-data"
public String saveProduct(HttpServletRequest request, HttpServletResponse response) throws IOException {
// 先建立一个文件工程,两个参数,一个表示存放多大后进行flush刷新,另一个表示工厂的位置
String realPath = request.getServletContext().getRealPath("/products");
// 存储10M后进行刷新
FileItemFactory factory = new DiskFileItemFactory(1024 * 1024 * 10, new File(realPath));
// 建立一个Servlet文件上传对象
ServletFileUpload fileUpload = new ServletFileUpload(factory);
// 设置文件上传大小的限制
fileUpload.setSizeMax(50 * 1024 * 1024);
Map<String, Object> map = new HashMap<String, Object>();
try {
// 获得所有提交数据组成的迭代器对象
@SuppressWarnings("unchecked")
List<FileItem> list = fileUpload.parseRequest(request);
if (list != null) {
// 说明有提交参数
Iterator<FileItem> iterator = list.iterator();
while (iterator.hasNext()) {
// 遍历这个迭代器
FileItem fileItem = iterator.next();
// 判断是否是file普通域对象
if (fileItem.isFormField()) {
// 说明是普通表单域对象
// 获得提交数据的key,即name
String name = fileItem.getFieldName();
String value = fileItem.getString("utf-8");
map.put(name, value);
} else {
// 说明文件表单域对象,进行文件上传
// 获得文件名
String filedName = fileItem.getName();
String name = fileItem.getFieldName();
// 创建文件对象
File file = new File(realPath + "/" + filedName);
map.put(name, "products/" + filedName);
// 进行写入
fileItem.write(file);
}
}
}
// 将数据存入数据库
Product product = new Product();
BeanUtils.populate(product, map);
// 存储product对象
product.setPid(UUIDUtils.getId());
product.setPflag(0);
productService.saveProduct(product);
} catch (Exception e) {
throw new RuntimeException(e);
}
return null;
}
request.getRequestDispathcer().forword和include的区别:forword是请求转发,而include是将页面放入response中返回(等同于write整个页面的数据给前台,可以利用include自己通过ajax实现ajax.load方法)
JSP学习随笔
声明一个JSP页面
<%@ page language="java" contentType="text/html; charset=UTF-8"
pageEncoding="UTF-8"%>
JSP的运行原理
先将JSP解析为.java文件,该.java就是一个Servlet类,然后编译为.class文件运行
JSP的9大内置对象
request --- HttpServletRequest
session --- HttpSession
application --- HttpServletContext
response --- HttpServletResponse
config --- HttpServletConfig
pageContext ---- pageContext
out
exception
page
JSP脚本:
<% %> :写在这个里面的内容相当于写在方法(_JspService(参数1,参数2))中的代码
<%! %> :写在这个里面的内容相当于写在类(当前jsp翻译成的java类)中的代码
<%= %> :写在这个里面的内容相当于response.getWriter.write();向浏览器输出内容
JSP注释:
<%-- --%> :JSP注释,它会影响整个页面的最终结果
// :java注释,它会影响整个页面的最终结果
<!-- --> :HTML注释,它不会影响整个页面的最终结果
EL表达式中11个内置对象
param
paramValues
header
headerValues
initParam
cookie
pageContext
pageScope
requestScope
sessionScope
applicationScope
取值时,page_scope的作用?
pageContext.getAttribute("book",pageContext.REQUEST_SCOPE);
明确指出从哪个域范围中获取属性值!!!!!上面这个它不会从page域中获取数据,而是从request域中。
如果没有指定scope,那么会根据你使用的这个域对象来找
pageContext.getAttribute("book"); //从page域中查找
如果没有指定scope,调用的是findAttribute();它会从最小的访问依次向大范围查找直到找到为止,如果找到不去更大的范围找,如果连最大范围都没找到,返回null
pageContext域对象的使用
作用域为当前页面
提供了获得其他8内置对象的方法 getXXX()
域对象方法有点特别
pageContext设置了四个int类型的属性值scope
1.PAGE_SCOPE
2.REQUEST_SCOPE
3.SESSION_SCOPE
4.APPLICATION_SCOPE
域中值的操作与其他与类似,不过多了一个参数 int scope
多了一个findAttribute(name)方法,若有多个相同name,则根据域的范围大小由小至大返回
JSP指令
静态包含
<%@ include file="src" %> --- 将指定位置的文件数据直接添加到此处,合并为一个.jsp文件
动态包含
<jsp:include page="src" flush="true|false"> flush表示是否刷新out.print数据
动态包含:先解析为.java再编译为.class文件,在合并为一个html文件
page指令:
<%@ page 属性名1:属性值1 属性名2=属性值2 %>
常用属性:
contentType: 指定MIME类型以及页面的编码
pageEncoding:指定页面编码(它和contentType至少写出一个来,那么另外一个默认就和这个的值一样,如果写2个值必须一致)
isErrorPage: 我们可以通过设置该属性来查看9大内置对象的Exception对象!
language:指定语言 java
import:当我们在jsp页面中书写了java代码,使用的 包可以使用这个属性来引入
tomcat的目录结构
bin:存放的都是一些二进制的可执行文件(sartup.bat启动tomcat,shutdown.bat停止tocmat服务器)
logs:存放所有tomcat启动的日志信息
conf:存放一些xml形式的配置文件(web.xml server.xml需要掌握的两个配置文件!)
web.xml 除了一个servlet默认处理类和session默认存活时间以外,全都是MIME类型(浏览器能够看懂)
server.xml 在这个文件中我们可以修改服务器的端口号,还有一些加载到tomcat里面运行的项目信息。
temp:存放一些临时文件,我们可以手动删除,下次启动,自动会创建这个目录。
lib:存放tomcat依赖的所有jar包。()
webapps:存放我们自己编写 的一些项目
work:如果用户访问的是一个jsp页面,那么在这个目录里面会生成对应的java文件(session的创建)