Servlet简介
servlet就是sun公司开发动态web的一门技术。
Sun在这些API中提供了一个接口叫做:Servlet。如果你想开发一个Servlet程序,只需要完成两个步骤:1.编写好一个类,实现Servlet接口。2.把开发好的Java类部署到Web服务器中。
我们把实现了Servlet接口的Java程序叫做Servlet。
Servlet接口Sun公司的实现类为HttpServlet和GenericServlet。
Servlet的maven依赖
servlet
<!-- https://mvnrepository.com/artifact/javax.servlet/javax.servlet-api -->
<dependency>
<groupId>javax.servlet</groupId>
<artifactId>javax.servlet-api</artifactId>
<version>3.1.0</version>
<scope>provided</scope>
</dependency>
jsp
web.xml中是配置我们web的核心应用,需要注册servlet
为什么需要映射?我们写的是Java程序,但是需要通过浏览器访问,而浏览器需要链接web服务器,所以我们需要在web服务器中注册我们写的Servlet,并且要设置一个浏览器可以访问的路径。
1.注册servlet
2.配置servletMapping(两种方式:1.web.xml中配置 2.使用@WebServlet()注解)
<?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.xml中配置的是我们web的核心应用-->
<!-- 注册servlet-->
<servlet>
<servlet-name>hello</servlet-name>
<servlet-class>com.kuanghui.servlet.HelloServlet</servlet-class>
</servlet>
<!-- 一个servlet对应一个Mapping:映射-->
<servlet-mapping>
<servlet-name>hello</servlet-name>
<!-- 请求路径 因为servlet是一个java类,无法直接请求,所以需要给它一个路径-->
<url-pattern>/liang</url-pattern>
</servlet-mapping>
</web-app>
ServletContext
Web应用在启动的时候,它会为每个web程序都创建一个对应的ServletContext对象,它代表了当前的web应用;
作用:1.共享数据,在当前Servlet保存的数据,可以在另外一个servlet中拿到
protected void doGet(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {
ServletContext servletContext = this.getServletContext();
String username="shenyucheng";
servletContext.setAttribute("username",username);
}
@Override
protected void doGet(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {
ServletContext servletContext = this.getServletContext();
String username = (String)servletContext.getAttribute("username");
resp.getWriter().print(username);
}
获取ServletContext初始化参数
<!-- 配置一些web应用初始化参数-->
<context-param>
<param-name>url</param-name>
<param-value>jdbc:mysql://localhost:3037</param-value>
</context-param>
@Override
protected void doGet(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {
ServletContext servletContext = this.getServletContext();
String usr = servletContext.getInitParameter("url");
resp.getWriter().print(usr);
}
Servlet请求转发
请求转发时路径不会发生变化
@Override
protected void doGet(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {
ServletContext servletContext = this.getServletContext();
// 转发请求路径,调用forward方法实现请求转发
servletContext.getRequestDispatcher("/gc").forward(req,resp);
}
读取Servlet文件
发现:都被打包到了同一路径下:classes,我们俗称这个路径为classpath(类路径)
@Override
protected void doGet(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {
InputStream stream = this.getServletContext().getResourceAsStream("/WEB-INF/classes/com/kuanghui/Servlet/aa.properties");
Properties properties = new Properties();
properties.load(stream);
String username=properties.getProperty("username");
String password = properties.getProperty("password");
resp.getWriter().print(username+":"+password);
}
HttpServletResponse
web服务器接收到客户端的http请求,针对这个请求,分别创建一个代表请求的HttpServletRequest对象,代表响应的一个HttpServletResponse对象。
1.如果要获取客户端请求过来的参数,找HttpServletRequest
2.如果要给客户端响应一些信息,找HttpServletResponse
下载文件
1.要获取下载文件的路径 2.下载的文件名是什么 3.设置浏览器支持下载文件 4.获取下载文件的输入流 5.使用OutputStream将数据输出到客户端
注意,最重要的一点就是要设置响应头的参数。
Content-disposition:attachment;filename=study.jpg
@Override
protected void doGet(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {
//1.获取下载文件路径
String realPath ="D:\\Java\\Idea-project\\JavaWeb-01-Servlet\\Servlet-02\\src\\main\\resources\\study.jpg";
System.out.println(realPath);
//获取文件名
String filename = realPath.substring(realPath.lastIndexOf("\\")+1);
//设置让浏览器支持(Content-Disposition)下载我们需要的文件,中文文件名需要URLEncoder.encode方法进行编码
resp.setHeader("Content-disposition","attachment;filename="+ URLEncoder.encode(filename,"UTF-8"));
//获取下载文件的输入流
FileInputStream fileInputStream = new FileInputStream(realPath);
//获取output流
ServletOutputStream outputStream = resp.getOutputStream();
//创建缓冲区
byte[] buff=new byte[1024];
int readLen;
//读取文件
while((readLen=fileInputStream.read(buff))>0){
outputStream.write(buff,0,readLen);
}
//关闭流
fileInputStream.close();
outputStream.close();
}
文件传输
对于文件上传,浏览器在上传的过程中是将文件以流的形式提交到服务端。一般选择采用apache的开源工具common-fileupload这个文件上传组件。common-fileupload是依赖于common-io这个包,所以还需要下载这个包。
<!-- https://mvnrepository.com/artifact/commons-io/commons-io -->
<dependency>
<groupId>commons-io</groupId>
<artifactId>commons-io</artifactId>
<version>2.11.0</version>
</dependency>
<!-- https://mvnrepository.com/artifact/commons-fileupload/commons-fileupload -->
<dependency>
<groupId>commons-fileupload</groupId>
<artifactId>commons-fileupload</artifactId>
<version>1.4</version>
</dependency>
uuid:随机生成一个唯一识别的通用码。
文件上传注意事项
1.为保证服务器安全,上传的文件都应该放在外界无法直接访问的目录下,比如放在WEB-INF目录下。
2.为防止文件覆盖的现象发生,要为上传文件产生一个唯一的文件名。(uuid,md5,位运算算法)。
3.要限制上传文件的最大值。
4.限制上传文件的类型,在收到上传文件时,判断后缀名是否合法。
想要文件上传,必须先得到浏览器的支持。
<%--东西上传必须需要一个表单,让表单支持文件上传需要加一个属性,enctype="multipart/form-data"--%>
<%--get:上传文件大小有限制,只有4kb左右
post:上传文件大小没有限制--%>
<%--
action="/FileServlet"只能在idea中跑,一旦项目发布,就会跑不起来
所以需要使用 action="${pageContext.request.contextPath}/FileServlet"
${pageContext.request.contextPath}用来获取服务器当前路径
--%>
<form action="/FileServlet" enctype="multipart/form-data" method="post">
<input type="file" name="file1"><br>
<input type="submit" value="上传">|<input type="reset" value="重置">
</form>
文件上传后需要Servlet将文件写入WEB-INF下
@Override
protected void doGet(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {
//ServletFileUpload是工具包,负责处理上传的文件数据,并将表单中的每个输入项封装成一个FileItem对象中,
//使用其parseRequest(HttpServletRequest)方法可以将通过表单中每一个HTML标签提交的数据
//封装成一个FileItem对象,然后以List列表的形式返回,使用该方法处理上传文件简单易用
//1.判断上传的文件是普通表单还是带文件的表单
if(!ServletFileUpload.isMultipartContent(req)){
return;//终止方法运行,说明这是一个普通的表单,直接返回
}
//2.创建上传文件的保存路径,建议在WEB-INF路径下,安全,用户无法直接访问上传文件
String uploadPath = this.getServletContext().getRealPath("/WEB-INF/upload");
File uploadfile = new File(uploadPath);
if(!uploadfile.exists()){
uploadfile.mkdir();//如果没有上传目录,则创建上传目录
}
//3.缓存,临时文件:假如文件超过了预期的大小,我们就把他放在一个临时文件中,过几天自动删除,或者提醒
// 用户转存为永久
String tempPath = this.getServletContext().getRealPath("/WEB-INF/temp");
File tempfile = new File(tempPath);
if(!tempfile.exists()){
tempfile.mkdir();//创建临时目录
}
//处理上传文件,一般都需要通过流来获取,我们可以使用request.getInputStream(),原生态的
// 文件上传流获取十分麻烦:建议使用Apache的文件上传组件来实现,common-fileupload,它需要
// 依赖于common-fileupload,他需要依赖于commons-io组件
/*
* ServletFileUpload负责处理上传的文件数据,并将表单中的每个输入项封装成一个FileItem对象
* 在使用ServletFileUpload对象解析请求时需要DiskFileItemFactory对象
* 所以在进行解析工作前构造好DiskFileItemFactory对象
* 通过ServletFileUpload对象的构造方法或setDiskFileItemFactory()方法设置
* ServletFileUpload对象的fileItemFactory属性
*/
//1.创建DiskFileItemFactory对象,处理文件上传路径或者大小限制
DiskFileItemFactory factory = new DiskFileItemFactory();
//通过这个工厂设置一个缓冲区,当上传的文件大于这个缓冲区的时候,将他放在一个临时文件下
factory.setSizeThreshold(1024*1024);//缓存区大小为1M
factory.setRepository(tempfile);//临时目录的保存目录
//2.获取ServletFileUpload
ServletFileUpload upload = new ServletFileUpload(factory);
//upload.setFileItemFactory();
/* 非必须,但需要了解
//监听文件上传进度
upload.setProgressListener(new ProgressListener() {
public void update(long l, long l1, int i) {
System.out.println("总大小:"+l1+"已上传:"+l);
}
});
//处理乱码问题
upload.setHeaderEncoding("UTF-8");
//设置单个文件的最大值
upload.setFileSizeMax(1024*1024*10);
//设置总共能够上传文件的大小
upload.setSizeMax(1024*1024*10);*/
try {
//3.把前端请求解析,封装成一个FileItem对象
List<FileItem> fileItems = upload.parseRequest(req);
//4.遍历FileItems对象
for(FileItem fileItem:fileItems){
//判断上传的文件是普通文件还是带文件的表单
if(fileItem.isFormField()){
String name = fileItem.getFieldName();
String value = fileItem.getString();
}else {//文件
//================处理文件==============//
String filename = fileItem.getName();//相对地址
//可能名字不合法
if(filename.trim().equals("")||filename==null){
continue;
}
//文件名
String name = filename.substring(filename.lastIndexOf("/") + 1);
//后缀名
String fileExt = filename.substring(filename.lastIndexOf(".") + 1);
/*
* 如果文件后缀名fileExt不是我们所需要的
* 就直接return,不处理,告诉用户文件类型不对
* */
//可以使用UUID(唯一识别的通行码),保证文件名的唯一
//UUID.randomUUID()随机生成一个唯一识别的通用码
//网络中传输中的东西,都需要序列化
//POJO实体类 传输==>都需要把对象给序列化了,implement Serializable(标记接口) JVM会识别这个标记接口
//serialVersionUID是用来保证UUID是唯一的
String uuidPath = UUID.randomUUID().toString();
//================存放地址==============//
//文件真实存放路径
String realPath = uploadPath + "/" + uuidPath;
File realPathfile = new File(realPath);
if(!realPathfile.exists()){
realPathfile.mkdir();
}
//================文件传输==============//
//获得文件的上传流
InputStream inputStream = fileItem.getInputStream();
//创建一个文件输出流
FileOutputStream fileOutputStream = new FileOutputStream(realPathfile + "/" + filename);
//字节流,需要创建缓冲区
byte[] bytes = new byte[1024 * 1024];
//字节读取长度
int len;
while((len=inputStream.read(bytes))>0){
fileOutputStream.write(bytes,0,len);
}
//关闭流
inputStream.close();
fileOutputStream.close();
fileItem.delete();//上传成功,清除临时文件
}
}
} catch (FileUploadException e) {
throw new RuntimeException(e);
}
}
邮件收发
要在网络上实现邮件功能,必须要有专门的邮件服务器。
邮件服务器类似于现实生活中的邮局,它主要负责接收用户投递过来的邮件,并把邮件投递到邮件接收者的电子邮件中。
SMTP:发送邮件 POP3:接收邮件
使用Java发送E-mail是十分简单的,首先你应该准备JavaMail API和Java ActivationFramework
MIME(多用途互联网邮件扩展类型):在邮件中就是附件(二进制,文件,图像)
简单文件:没有附件和图片,纯文本邮件
复杂邮件:有附件和图片
简单邮件
//发送简单文件
public class MailDemo1 {
public static void main(String[] args) throws GeneralSecurityException, MessagingException {
Properties properties = new Properties();
properties.setProperty("main.host","smtp.qq.com");//设置QQ邮件服务器
properties.setProperty("main.transport.protocol","smtp");//邮件发送协议
properties.setProperty("mail.smtp.suth","true");//需要验证用户名密码
//关于QQ邮箱,还要设置SSL加密,加上以下代码即可,163邮箱不用
MailSSLSocketFactory mailSSLSocketFactory = new MailSSLSocketFactory();
mailSSLSocketFactory.setTrustAllHosts(true);
properties.put("mail.smtp.ssl.enable","true");
properties.put("mail.smtp.ssl.socketFactory",mailSSLSocketFactory);
//使用JavaMail发送的5个步骤
//1.创建定义整个应用程序所需的环境信息的Session对象
//QQ才有
Session session = Session.getDefaultInstance(properties, new Authenticator() {
@Override
protected PasswordAuthentication getPasswordAuthentication() {
return new PasswordAuthentication("112206047@qq.com", "dsajdgbasjgd");
}
});
//开启Session的debug模式,这样可以查看到程序发送Email的运行状态
session.setDebug(true);
//2.通过Session得到transport对象
Transport transport = session.getTransport();//连接和发送邮件的
//3.使用邮箱的用户名和邮箱连上邮件服务器
transport.connect("smtp.qq.com","112206047@qq.com", "dsajdgbasjgd");
//4.创建邮件:写邮件
//注意需要传递Session
MimeMessage mimeMessage = new MimeMessage(session);//需要从session中获取发送者的信息
mimeMessage.setFrom(new InternetAddress("112206047@qq.com"));//指明邮件的发件人
mimeMessage.setRecipient(Message.RecipientType.TO,new InternetAddress("2294788054@qq.com"));//指定邮件的收件人
mimeMessage.setSubject("学习Java");//邮件标题
mimeMessage.setContent("你好呀","text/html;charset=UTF-8");//文本内容
//5.发送邮件
transport.sendMessage(mimeMessage,mimeMessage.getAllRecipients());
//6.关闭连接
transport.close();
}
}
带有图片的邮件
public class MailDemo2 {
public static void main(String[] args) throws GeneralSecurityException, MessagingException {
Properties properties = new Properties();
properties.setProperty("main.host","smtp.qq.com");//设置QQ邮件服务器
properties.setProperty("main.transport.protocol","smtp");//邮件发送协议
properties.setProperty("mail.smtp.suth","true");//需要验证用户名密码
//关于QQ邮箱,还要设置SSL加密,加上以下代码即可,163邮箱不用
MailSSLSocketFactory mailSSLSocketFactory = new MailSSLSocketFactory();
mailSSLSocketFactory.setTrustAllHosts(true);
properties.put("mail.smtp.ssl.enable","true");
properties.put("mail.smtp.ssl.socketFactory",mailSSLSocketFactory);
//使用JavaMail发送的5个步骤
//1.创建定义整个应用程序所需的环境信息的Session对象
//QQ才有
Session session = Session.getDefaultInstance(properties, new Authenticator() {
@Override
protected PasswordAuthentication getPasswordAuthentication() {
return new PasswordAuthentication("112206047@qq.com", "dsajdgbasjgd");
}
});
//开启Session的debug模式,这样可以查看到程序发送Email的运行状态
session.setDebug(true);
//2.通过Session得到transport对象
Transport transport = session.getTransport();//连接和发送邮件的
//3.使用邮箱的用户名和邮箱连上邮件服务器
transport.connect("smtp.qq.com","112206047@qq.com", "dsajdgbasjgd");
//4.创建邮件:写邮件
//注意需要传递Session
MimeMessage mimeMessage = new MimeMessage(session);//需要从session中获取发送者的信息
mimeMessage.setFrom(new InternetAddress("112206047@qq.com"));//指明邮件的发件人
mimeMessage.setRecipient(Message.RecipientType.TO,new InternetAddress("2294788054@qq.com"));//指定邮件的收件人
mimeMessage.setSubject("带有图片的邮件");//邮件标题
//准备图片数据
MimeBodyPart image = new MimeBodyPart();
//图片需要经过数据处理。。。 DataHander:数据处理
DataHandler dataHandler = new DataHandler(new FileDataSource("src/resources/bz.jpg"));
image.setDataHandler(dataHandler);//在Body中放入这个处理的图片数据
image.setContentID("bz.jpg");//给图片设置一个id
//准备正文
MimeBodyPart text = new MimeBodyPart();
text.setContent("这是一封邮件正文带有<img src='cid:bz.jpg'>的邮件","text/html;charset=UTF-8");
//描述数据关系
MimeMultipart mm = new MimeMultipart();
mm.addBodyPart(text);
mm.addBodyPart(image);
mm.setSubType("related");//图片和文字
//设置到消息中,保存修改
mimeMessage.setContent(mm);//把最后编辑好的邮件放在消息中
mimeMessage.saveChanges();//保存修改
//5.发送邮件
transport.sendMessage(mimeMessage,mimeMessage.getAllRecipients());
//6.关闭连接
transport.close();
}
}
有附件和图片的邮件
public class MailDemo3 {
public static void main(String[] args) throws GeneralSecurityException, MessagingException {
Properties properties = new Properties();
properties.setProperty("main.host","smtp.qq.com");//设置QQ邮件服务器
properties.setProperty("main.transport.protocol","smtp");//邮件发送协议
properties.setProperty("mail.smtp.suth","true");//需要验证用户名密码
//关于QQ邮箱,还要设置SSL加密,加上以下代码即可,163邮箱不用
MailSSLSocketFactory mailSSLSocketFactory = new MailSSLSocketFactory();
mailSSLSocketFactory.setTrustAllHosts(true);
properties.put("mail.smtp.ssl.enable","true");
properties.put("mail.smtp.ssl.socketFactory",mailSSLSocketFactory);
//使用JavaMail发送的5个步骤
//1.创建定义整个应用程序所需的环境信息的Session对象
//QQ才有
Session session = Session.getDefaultInstance(properties, new Authenticator() {
@Override
protected PasswordAuthentication getPasswordAuthentication() {
return new PasswordAuthentication("112206047@qq.com", "dsajdgbasjgd");
}
});
//开启Session的debug模式,这样可以查看到程序发送Email的运行状态
session.setDebug(true);
//2.通过Session得到transport对象
Transport transport = session.getTransport();//连接和发送邮件的
//3.使用邮箱的用户名和邮箱连上邮件服务器
transport.connect("smtp.qq.com","112206047@qq.com", "dsajdgbasjgd");
//4.创建邮件:写邮件
//注意需要传递Session
MimeMessage mimeMessage = new MimeMessage(session);//需要从session中获取发送者的信息
mimeMessage.setFrom(new InternetAddress("112206047@qq.com"));//指明邮件的发件人
mimeMessage.setRecipient(Message.RecipientType.TO,new InternetAddress("2294788054@qq.com"));//指定邮件的收件人
mimeMessage.setSubject("带有图片的邮件");//邮件标题
//准备图片数据
MimeBodyPart image = new MimeBodyPart();
//图片需要经过数据处理。。。 DataHander:数据处理
DataHandler dataHandler = new DataHandler(new FileDataSource("src/resources/bz.jpg"));
image.setDataHandler(dataHandler);//在Body中放入这个处理的图片数据
image.setContentID("bz.jpg");//给图片设置一个id
//附件
MimeBodyPart appendix = new MimeBodyPart();
DataHandler dataHandler1 = new DataHandler(new FileDataSource("src/resources/log4j.properties"));
image.setDataHandler(dataHandler1);
image.setFileName("log4j.properties");
//准备正文
MimeBodyPart text = new MimeBodyPart();
text.setContent("这是一封邮件正文带有<img src='cid:bz.jpg'>的邮件","text/html;charset=UTF-8");
//描述数据关系
MimeMultipart mm = new MimeMultipart();
mm.addBodyPart(text);
mm.addBodyPart(image);
mm.setSubType("related");//图片和文字
//拼装好的正文内容设置为主体
MimeBodyPart contentText = new MimeBodyPart();
contentText.setContent(mm);
//拼接附件
MimeMultipart allFile = new MimeMultipart();
allFile.addBodyPart(appendix);
allFile.addBodyPart(contentText);
allFile.setSubType("mixed");
//设置到消息中,保存修改
mimeMessage.setContent(mm);//把最后编辑好的邮件放在消息中
mimeMessage.saveChanges();//保存修改
//5.发送邮件
transport.sendMessage(mimeMessage,mimeMessage.getAllRecipients());
//6.关闭连接
transport.close();
}
}
验证码功能
验证怎么来:需要用到Java的图片类,生成一个图片。
@Override
protected void doGet(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {
//如何让浏览器五秒刷新一次
resp.setHeader("refresh","5");
//在内存中创建一个图片
BufferedImage image = new BufferedImage(80,90,BufferedImage.TYPE_INT_RGB);
//得到图片,Graphic相当于一支笔
Graphics2D graphics = (Graphics2D)image.getGraphics();
//设置图片的背景颜色
graphics.setColor(Color.WHITE);
graphics.fillRect(0,0,20,80);
//给图片写数据,随机生成随机数
int ran=new Random().nextInt(1111);
String ranStr=String.valueOf(ran);
//设置验证码颜色,给图片写数据
graphics.setColor(Color.BLACK);
graphics.drawString(ranStr,0,10);
//告诉浏览器,这个请求用图片的形式打开
resp.setContentType("image/jpg");
//网站存在缓存,不让浏览器存在缓存
resp.setDateHeader("expires",-1);
resp.setHeader("Cache-Control","no-cache");
resp.setHeader("Pragma","no-cache");
//把图片写给浏览器
ImageIO.write(image, "jpg",resp.getOutputStream());
}
实现重定向
当web收到客户端请求后,他会通知客户端去访问另外一个web资源,这个过程叫做重定向
状态码为302
@Override
protected void doGet(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {
/*
* 原理
* resp.setHeader("Location","/Servlet3/index.jsp");
* resp.setStatus(302)
* */
resp.sendRedirect("/Servlet3/index.jsp");
}
重定向和转发的区别
相同点:页面都会跳转
不同点 :1.请求转发时,url地址栏不会发生变化 307 2.重定向时,url地址栏会发生变化 302
HttpServletRequest
HttpServletRequest代表客户端请求,用户通过Http协议访问浏览器,Http请求中的所有信息会被封装到HttpServletRequest中,铜鼓这个HttpServletRequest的方法,获得客户端的所有信息。
表单和Servlet结合
<form action="${pageContext.request.contextPath}/request" method="post" >
用户名:<input type="text" name="username"><br>
密码:<input type="text" name="pwd"><br>
爱好:
<input type="checkbox" name="hobby" value="女孩">女孩
<input type="checkbox" name="hobby" value="代码">代码
<input type="checkbox" name="hobby" value="唱歌">唱歌
<br>
<input type="submit">
</form>
@Override
protected void doGet(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {
System.out.println("进入请求.....");
//处理请求
String username = req.getParameter("username");
String pwd = req.getParameter("pwd");
String[] hobby = req.getParameterValues("hobby");
//请求转发 302
//req.getRequestDispatcher("/success.jsp").forward(req,resp);
//重定向 307
resp.sendRedirect("/Servlet3/success.jsp");
}
Http的常见ContentType
资源导出存在问题的解决代码
<!-- 在build中配置resources,来防止我们资源导出失败的问题-->
<build>
<resources>
<resource>
<directory>src/main/resources</directory>
<includes>
<include>**/*.properties</include>
<include>**/*.xml</include>
</includes>
</resource>
<resource>
<directory>src/main/java</directory>
<includes>
<include>**/*.properties</include>
<include>**/*.xml</include>
</includes>
</resource>
</resources>
</build>
W3C的JavaScript教程网址:JavaScript 输出 (w3school.com.cn)