后端学习第四周

后端学习第四周

Servlet

Servlet 前置知识

http

客户端和服务器之间通过请求和响应进行交互。http,超文本传输协议,是请求和响应的一种标准协议。

客户端发给服务器的格式叫“请求协议”;服务器发给客户端的格式叫“响应协议”。

书写格式:

特点:

  1. 支持客户端/服务器模式。

  2. 简单快速。

  3. 灵活。

  4. 无连接

  5. 无状态

URL:

URL是一种特殊的URI,包含了用于查找某个资源的足够的信息。

URL格式:

http://host[:port]/[abs_path]

http://IP(主机名/域名):端口/访问的资源路径

http表示要通过HTTP协议来定位网络资源;

host表示合法的Internet主机域名或者IP地址;

port 指定一个端口号,为空则使用缺省端口80;

abs_path 指定请求资源的URI;如果URL中没有给出abs_path,那么当它作为请求URI时,必须以“/”的形式给出,通常这个工作浏览器自动帮我们完成。

HTTP请求

三部分:请求行请求头请求正文

GET请求(没有请求体)

GET/.../...?unme=... HTTP/1.1 (请求行)

xxxx:xxxx

xxxxx:xxxxxx (请求头)

....:....

POST请求:

POST /.../... HTTP1.1 (请求行)

xxxx:xxxx

xxxxx:xxxxxx (请求头)

....:...

Form Data

uname:zhangsan (请求体)

HTTP响应

状态行(响应行)

消息报头(响应头)

响应体

消息头:

请求头

Referer:指明请求从哪来。例如从百度来的才算入价格。通常用来做统计工作,防盗链。

响应头

Locaton:Location响应报头域重定向新的位置。常用在更换域名的时候。

Refresh:自动跳转,可以在html实现,也可以在后台实现。

服务器

服务器等待和接受客户端的请求,以分配资源。

Tomcat服务器的安装和启动:

解压后配置JAVA_HOME路径,打开bin目录下的startup.bat,若能成功运行且打开127.0.0.1.8080时打开的是Tomcat的页面,则成功。

Tomcat目录结构

bin:启动和关闭tomcat的bat 文件

conf:配置文件server.xml该文件用于配置server相关的信息,比如tomcat启动的端口号,配置主机(Host) ; web.xml文件配置与web应用(web应用相当于一个web站点); tomcat-user.xml配置用户名密码和相关权限

lib:该目录放置运行tomcat运行需要的jar包

logs:存放日志,当我们需要查看日志的时候,巧以查询信息

webapps:放置我们的web应用

work工作目录:该目录用于存放jsp被访问后生成对应的server文件和.class文件

IDEA 配置 Tomcat

在Setting中找到"Appliction Servers",点击右侧的"+"号,选择"Tomcat Server",选定Tomcat Home路径,点击应用即可。

Servlet

Servlet是Server 与Applet的缩写,是服务端小程序的意思。要实现web开发,需要实现Servlet标准。

Servlet本质上也是Java类,但要遵循Servlet规范进行编写,没有main()方法,它的创建、使用、销毁都由Servlet容器进行管理(如Tomcat)。(言外之意:写自己的类,不用写main方法,别人自动调用)

Servlet是和HTTP协议是紧密联系的,其可以处理HTTP协议相关的所有内容。这也是Servlet应用广泛的原因之一。

提供了Servlet功能的服务器,叫做Servlet容器,其常见容器有很多,如Tomcat, Jjetty, WebLogic Server,WebSphere,JBoss 等等。

Servlet基本使用

在IDEA中创建web项目

New Project中,选择Java Enterprise,勾选Web Application(4.0),点击Next,设定Project name和Project location,点击Finish即可。

重写service方法

  • 在类名后加上extends HttpServlet。

  • Crtl + O, 选择HttpServletRequest的service方法。

设置注释,指定访问的路径

@webServlet("/ser01")

或 @webServlet(name = "Servlet01", value = "/ser01", "ser001") 以设置多个路径。

其他服务器设置

右上角下拉条选择Edit Configurations,可更改URL为更简单的地址,可取消勾选After launch或设定其他打开方式。

访问路径说明

localhost:8080/s01/ser01

localhost:本台主机

8080:端口号为8080的程序(即tomcat)

s01:服务器中的项目

ser01:项目里的资源

Servlet的实现代码

package com.join.servlet;
​
import javax.servlet.ServletException;
import javax.servlet.annotation.WebServlet;
import javax.servlet.http.HttpServlet;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import java.io.IOException;
​
/**
 * 实现Servlet
 *
 */
​
//设置注解,指定访问的路径
@WebServlet("/ser01")
​
//也可以用以下写法,但不常用
//value 和 urlPatterns 可以是数组,即多个路径可访问
//@WebServlet(name = "Servlet01", value = "/ser01")
//@WebServlet(name = "Servlet01", value = {"/ser01", "ser001"})
//@WebServlet(urlPatterns = "/ser01")
//@WebServlet(urlPatterns = {"/ser01", "/ser001"})
//@
​
public class Servlet01 extends HttpServlet {
    //继承HttpServlet类
    //重写Service方法,选择 HttpServletRequest
​
    @Override
    protected void service(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {
        //打印内容在控制台
        System.out.println("Hello Servlet!");
        //通过流输出数据到浏览器
        resp.getWriter().write("Hello Servlet!");
    }
}

其他 Servlet 实现方式

(不常用)

  1. 继承Http的父类:GenericServlet,重写Service 方法

public class Servlet02 extends GenericServlet {
​
    @Override
    public void service(ServletRequest servletRequest, ServletResponse servletResponse) throws ServletException, IOException {
        //Service 方法
    }
}
  1. 继承 GenericServlet 的总接口,实现其中的方法:

public class Servlet03 implements Servlet {
    @Override
    public void init(ServletConfig servletConfig) throws ServletException {
        
    }
​
    @Override
    public ServletConfig getServletConfig() {
        return null;
    }
​
    @Override
    public void service(ServletRequest servletRequest, ServletResponse servletResponse) throws ServletException, IOException {
        //Service 方法
    }
​
    @Override
    public String getServletInfo() {
        return null;
    }
​
    @Override
    public void destroy() {
​
    }
}
  1. 仍继承 httpServlet,但重写 doGet 和 doPost 方法

public class Servlet04 extends HttpServlet {
    @Override
    protected void doGet(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {
        //doGet方法
    }
​
    @Override
    protected void doPost(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {
        //调用doGet方法
        doGet(req, resp);
    }
}

不重写 Service 方法,但较为麻烦,不常用。

Service 方法底层也调用了 doGet 和 doPost 方法。

Servlet 生命周期

简单概括为四步:Servlet 类加载-->实例化(Servlet容器检查是否存在Servlet对象,否则执行,是则跳过,生命周期中只执行一次)-->服务-->销毁。

init 方法,在 Servlet 实例创建后执行。

service 方法,每次有请求到达某个 Servlet 方法时执行,用来处理请求(证明该 Servlet 进行服务了)。

destroy 方法,Servlet 实例销毁时进行(证明该 Servlet 实例被销毁了)。

HttpServletRequest 对象

主要作用是用来接收客户端发送过来的请求信息。

常用方法:

getRequestURL() 获取客户端发出请求时的完整URL

getRequestURI() 获取请求行中的资源名称部分(项目名称开始)

getQueryString() 获取请求行中的参数部分

getMethod() 获取客户端请求方式

getProtocol() 获取HTTP版本号

getContextPath() 获取webapp名字

    /*常用方法*/
    //获取请求时的完整路径(从http开始,到"?"前面结束)
    String url = req.getRequestURL() + "";
    System.out.println("获取请求时的完整路径:" + url);
    //获取请求时的部分路径(从项目的站点名开始,到"?"前面结束)
    String uri = req.getRequestURI();
    System.out.println("获取请求时的部分路径:" + uri);
    //获取请求时的参数字符串(从"?"后面开始,到最后的字符串)
    String queryString = req.getQueryString();
    System.out.println("获取请求时的参数字符串:" + queryString);
    //获取请求方式(GET和POST)
    String method = req.getMethod();
    System.out.println("获取请求方式:" + method);
    //获取当前协议版本(HTTP/1.1)
    String prototol = req.getProtocol();
    System.out.println("获取当前协议版本:" + prototol);
    //获取项目的站点名(项目对外访问路径)
    //上下文路径
    String webapp = req.getContextPath();
    System.out.println("获取项目的站点名:" + webapp);

控制台输出:

获取请求时的完整路径:http://localhost:8080/s01/ser05
获取请求时的部分路径:/s01/ser05
获取请求时的参数字符串:null
获取请求方式:GET
获取当前协议版本:HTTP/1.1
获取项目的站点名:/s01

获取请求的参数方法:

String getParameter(String)

String[] getParameterValues(String)

    /*获取请求的参数*/
    //获取指定名称的参数值,返回字符串(重点)
    String uname = req.getParameter("uname");
    String upwd = req.getParameter("upwd");
    System.out.println("uname:" + uname + ",upwd: " + upwd);
    //获取指定名称的参数的所有参数值,返回字符串数组(用于复选框传值)
    String[] hobbys = req.getParameterValues("hobbys");
    //判断数组是否为空
    if (hobbys != null && hobbys.length > 0) {
        for (String hobby : hobbys) {
            System.out.println("爱好:" + hobby);
        }
    }

请求乱码问题

Tomcat8 及以上版本Tomcat7 及以下版本
GET请求不会乱码,不需处理会乱码,String name = new String(req.getParameter("uname").getBytes("ISO-8859-1"), "UTF-8");(每次只能处理一个(可处理任何数据,但必须只能是本身会乱码的),不好用,且Tomcat7及以下版本不常用)
POST请求会乱码,设置服务器解析编码的格式会乱码,设置服务器解析编码的格式
解决req.setCharacterEncoding("utf-8");(只针对POST请求)req.setCharacterEncoding("utf-8");

请求转发

req.getRequestDispatcher(url).forward(req, resp);
//url 可以是
//1. 特定Servlet:"ser01"
//2. jsp文件:"login.jsp"
//3. html文件:"login.html"

特点:

  1. 服务端行为

  2. 地址栏不发生变化

  3. 从始至终都是同一次请求

  4. request数据可以共享

request作用域

从request中获取数据之后,将数据存入作用域中,然后请求转发到新的Servlet/jsp页面之后,就可以从作用域中取出数据并使用了。

方法:

//设置域对象内容
req.setAttribute(String name, String value);
//获取域对象内容
req.getAttribute(String name);
//删域对象的内容
req.removeAttribute(String name);

代码:

  1. Servlet

package com.join.servlet;
​
import javax.servlet.ServletException;
import javax.servlet.annotation.WebServlet;
import javax.servlet.http.HttpServlet;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import java.io.IOException;
import java.util.ArrayList;
import java.util.List;
​
/**
 * 测试域对象与请求转发跳转
 */
​
@WebServlet("/ser06")
public class Servlet06 extends HttpServlet {
​
    @Override
    protected void service(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {
​
        //设置域对象内容
        //数据可以是Object类型,即任何类型都行
        req.setAttribute("name", "admin");
        req.setAttribute("age", 10);
        List<String> list = new ArrayList<>();
        list.add("aaa");
        list.add("bbb");
        req.setAttribute("list", list);
​
        //请求转发跳转到jsp,并通过与对象传递数据
        req.getRequestDispatcher("index.jsp").forward(req, resp);
    }
}
  1. jsp:

<%@ page import="java.util.List" %>
<%@ page contentType="text/html;charset=UTF-8" language="java" %>
<html>
  <head>
    <title>$Title$</title>
  </head>
  <body>
  <%-- 如果要在jsp中些java代码,需要写在脚本段中 --%>
  <%
    //获取域对象,并输出
    String name = (String) request.getAttribute("name");
    System.out.println("name:" + name);
    Integer age = (Integer) request.getAttribute("age");
    System.out.println("age:" + age);
    List<String> list = (List<String>) request.getAttribute("list");
    for (int i = 0; i < list.size(); i++) {
      System.out.println(list.get(i));
    }
  %>
  </body>
</html>

控制台输出:

name:admin
age:10
aaa
bbb

HttpServletResponse 对象

HttpServletResponse的主要功能用于服务器对客户端的请求进行响应,将Web服务器处理后的结果返回给客户端。

两种形式:

getWriter()获取字符流(只能相应回字符)

getOutputStream() 获取字节流(能响应一切数据)

二者不能同时使用。

代码:

package com.join.servlet;
​
import javax.servlet.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 Servlet07 extends HttpServlet {
​
    @Override
    protected void service(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {
        
        //字符输出流
        //获取字符输出流
        PrintWriter writer = resp.getWriter();
        //输出数据
        writer.write("Hello.");
        
        //字节输出流
        //获取字节输出流
        ServletOutputStream out = resp.getOutputStream();
        //输出数据,要转为字节数组
        out.write("Hi.".getBytes());
    }
}

当然,此时浏览器页面只会输出“Hello.”,并报错。因为二者不能同时使用,他们都调用了response对象。response对象只能被使用一次。

相应乱码问题

服务器端和客户端编码格式不同导致。

要设置客户端和服务端的编码格式支持中文,且保持一致。

  1. 对于字符流响应数据(getWriter()):

原因:相应中文必定出现乱码,因为服务器端在进行编码时会默认使用ISO-8859-1格式的编码。

解决:1. 设置服务端编码格式为"UTF-8"(在流之前进行设置):resp.setCharacterEncoding("UTF-8");

2 .设置客户端的编码格式:resp.setHeader("content-tpye", "text/html;charset=UTF-8");

(其中:

setHeader:响应头。

content-tpye:相应类型

text/html:响应的MIME类型,让其中字符有html效果

charset=UTF-8:编码格式。

或:同时设置客户端和服务端的编码格式:

resp.setContentType("text/html;charset=UTF-8");

2. 对于字节流响应数据(getOutputStream()):

不会出现服务端编码的问题,但是会出现两个端编码格式不一致的问题。

所以也应该同时设置客户端和服务端的编码格式。

重定向

resp.sendRedirect(url);

特点:

  1. 服务端指导,客户端行为。

  2. 地址栏改变

  3. Location改变,

  4. 两次请求

  5. request对象不共享

  6. 故数据也无法传递

请求转发与重定向其他区别:

  1. 请求转发的地址只能是当前站点名下的资源;重定向可以任意地址,可跨域(可以跳转到百度)

Cookie 对象

Cookie是浏览器提供的一种技术,通过服务器的程序能将一些只须保存在客户端,或者在客户端进行处理的数据,放在本地的计算机上,不需要通过网络传输,因而提高网页处理的效率,并且能够减少服务器的负载,但是由于Cookie是服务器端保存在客户端的信息,所以其安全性也是很差的。例如常见的记住密码则可以通过Cookie来实现。

Cookie的创建、发送、获取

  1. 创建:直接new Cookie对象即可

  2. 发送:resp.addCookie(cookie);

  3. 获取(返回值为全部Cookie组成的Cookie数组):req.getCookies();

package com.join.servlet;
​
import javax.servlet.ServletException;
import javax.servlet.annotation.WebServlet;
import javax.servlet.http.Cookie;
import javax.servlet.http.HttpServlet;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import java.io.IOException;
​
/**
 * 1. Cookie的创建、发送
 *
 * 2. Cookie的获取
 *    返回的是Cookie数组
 */
​
@WebServlet("/ser08")
public class Servlet08 extends HttpServlet {
    @Override
    protected void service(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {
        //Cookie的创建
        Cookie cookie = new Cookie("name", "admin");
        //发送(响应)Cookie对象
        resp.addCookie(cookie);
​
        //获取Cookie数组
        Cookie[] cookies = req.getCookies();
        //判断cookies是否为空
        if(cookies != null && cookies.length > 0){
            //遍历Cookie数组
            for (Cookie c : cookies) {
                //获取Cookie的名称和值
                String name = cookie.getName();
                String value = cookie.getValue();
                System.out.println("名称:" + name + ",值:" + value);
            }
        }
    }
}

控制台输出:

名称:name,值:admin

Cookie设置到期时间

Cookie类的一个字段:maxAge控制Cookie的到期时间。可以通过setMaxAge(int time);方法设定Cookie的最大有效时间,以秒为单位。

到期时间的取值:

  1. 负整数:

表示不储存该Cookie。

该Cookie只在浏览器此次打开期间存活(即存于浏览器内存中),一旦关闭浏览器窗口,Cookie消失。Cookie对象的maxAge默认值为-1。

  1. 正整数:

表示Cookie可存活的秒数。

该Cookie在浏览器(即硬盘)中储存相应的时间,时间到后消失。

表示删除该Cookie。

该Cookie作废。如果原本浏览器已经保存这个Cookie(在浏览器内存中或在硬盘中),就删除该Cookie。

Cookie路径

假设现在发送的请求路径是“/servlet13/cookie/generate”生成的cookie,如果cookie没有设置path

默认的path是:/servlet13/cookie 以及它的子路径。

也就是说,以后只要浏览器的请求路径是/servlet13/cookie 这个路径以及这个路径下的子路径,cookie都会被发送到服务器。

Cookie几个注意点

  1. Cookie存在浏览器中。换浏览器后不会存在。

  2. Cookie不建议存中文。如果有中文,则通过URLEncoder.encode()来进行编码,获取时通过URLDecoder.decode()进行解码。

  3. 如果服务器发送了重复的Cookie,会覆盖原来的。

  4. 不同浏览器存放Cookie的上限不同(有限),且Cookie大小有限(4kb左右)。

HttpSession 对象

对于服务器而言,每一个连接到它的客户端都是一个session。servlet容器使用此接口创建HTTP客户端和HTTP服务器之间的会话。会话将保留指定的时间段,跨多个连接或来自用户的页面请求。

Session的创建和常用方法:

package com.join.servlet;
​
import javax.servlet.ServletException;
import javax.servlet.annotation.WebServlet;
import javax.servlet.http.HttpServlet;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import javax.servlet.http.HttpSession;
import java.io.IOException;
​
/**
 * Session对象的获取
 * 和常用方法
 */
​
@WebServlet("/ser09")
public class Servlet09 extends HttpServlet {
    @Override
    protected void service(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {
        
        //获取Session对象
        //如果Session存在则获取,如果不存在则创建
        HttpSession session = req.getSession();
        
        //获取Session的会话标识符
        String id = session.getId();
        System.out.println(id);
        
        //获取Session的创建时间
        //返回时间戳
        System.out.println(session.getCreationTime());
        
        //获取最后一次访问时间
        //返回时间戳
        System.out.println(session.getLastAccessedTime());
        
        //判断是否是新的Session对象
        System.out.println(session.isNew());
    }
}

Session标识符JSESSIONID

每当一次请求到达服务器,如果开启了会话(访问了Session),服务器第一步会查看是否从客户端回传一个名为JSESSIONID的cookie,如果没有则认为这是一次新的会话,会创建一个新的Session对象,并用唯一的sessionld 为此次会话做一个标志。如果有JESSIONID这个cookie回传,服务器则会根据JSESSIONID这个值去查看是否含有id为JSESSION值的session对象,如果没有则认为是一个新的会话,重新创建一个新的session对象,并标志此次会话;如果找到了相应的session对象,则认为是之前标志过的一次会话,返回该session对象,数据达到共享。

这里提到一个叫做JSESSIONID的cookie,这是一个比较特殊的cookie,当用户请求服务器时,如果访问了Session,则服务器会创建一个名为JSESSIONID,值为获取到的Session(无论是获取到的还是新创建的)的sessionld的cookie对象,并添加到response对象中,响应给客户端,有效时间为关闭浏览器。

所以 Session的底层依赖Cookie来实现。

Session域对象

Session域对象在请求转发和重定向中都可以使用

Servlet中:

package com.join.servlet;
​
import javax.servlet.ServletException;
import javax.servlet.annotation.WebServlet;
import javax.servlet.http.HttpServlet;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import javax.servlet.http.HttpSession;
import java.io.IOException;
​
/**
 * Session域对象
 */
​
@WebServlet("/ser10")
public class Servlet10 extends HttpServlet {
    @Override
    protected void service(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {
        //获取Session对象
        HttpSession session = req.getSession();
​
        //设置域对象
        session.setAttribute("uname", "admin");
        session.setAttribute("upwd", "123456");
​
        //移除Session对象
        session.removeAttribute("upwd");
​
        //重定向到jsp页面
        resp.sendRedirect("index1.jsp");
    }
}

jsp中:

<%@ page contentType="text/html;charset=UTF-8" language="java" %>
<html>
<head>
    <title>获取域对象</title>
</head>
<body>
<%
  //获取Session对象
  String name = (String) session.getAttribute("uname");
  String upwd = (String) session.getAttribute("upwd");
  //输出
  out.print("name:" + name + " upwd:" + upwd);
%>
</body>
</html>

网页输出:

name:admin upwd:null

Session对象的销毁

  1. 默认到期时间

Tomcat中Session默认存活时间为30分钟,即不操作30分钟后,销毁。期间若操作,重新计时。

可以在web.xml文件中修改该默认值

<session-config>
    <session-timeout>30<session-timeout>
</session-config>

将30改为其他数字即可修改。

  1. 自己设定到期时间

通过session.setMaxInactiveInterval(int);来修改,单位为秒。

//获取Session对象
HttpSession session = req.getSession();
//设置Session最大不活动时间
session.setMaxInactiveInterval(15);
  1. 立即销毁

可以通过session.invalidate()方法让session立刻失效。

  1. 关闭浏览器

Session底层实现依赖Cookie,Cookie默认在关闭浏览器时失效。

  1. 关闭服务器

当关闭服务器,Session销毁。

mvc

MVC是模型(Model)、视图(View)、控制器(Controller)的简写,是一种软件设计规范,是将业务逻辑、数据、显示分离的方法来组织代码。是一种架构模式。

构成:

控制器:用户在网页上单击一个 URL 路径,这对 Web 服务器来说,相当于用户发送了一个请求。而获取请求后如何解析用户的输入,并执行相关处理逻辑,最终跳转至正确的页面显示反馈结果,这些工作往往是控制层(Controller)来完成的。

模型:在请求的过程中,用户的信息被封装在 User 实体类中,该实体类在 Web 项目中属于数据模型层(Model)。

视图:在请求显示阶段,跳转的结果网页就属于视图层(View)。

主要作用:降低了视图与业务逻辑间的双向偶合。

优缺点:

优点:

  • 多视图共享一个模型,大大提高了代码的可重用性

  • MVC 三个模块相互独立,松耦合架构

  • 控制器提高了应用程序的灵活性和可配置性

  • 有利于软件工程化管理

缺点:

  • 原理复杂

  • 增加了系统结构和实现的复杂性

  • 视图对模型数据的低效率访问

JSP + JavaBean

JSP+JavaBean 模式在一定程度上实现了 MVC,即 JSP 将控制层和视图合二为一,JavaBean 为模型层。JSP+JavaBean 模式中 JSP 身兼数职,既要负责视图层的数据显示,又要负责业务流程的控制,结构较为混乱,并且也不是我们所希望的松耦合架构模式,所以当业务流程复杂的时候并不推荐使用。

Servlet + JSP + JavaBean

Servlet+JSP+JavaBean 模式的结构清晰,是一个松耦合架构模式,一般情况下,建议使用该模式。

jar包

jar包:

Java Archive File,类似zip包,区别在于jar包包含了一个 META-INF/MANIFEST.MF 文件,包含了该Jar包的版本、创建人和类搜索路径Class-Path等信息。可执行Jar包会包含Main-Class属性,表明Main方法入口,尤其是较为重要的Class-Path和Main-Class。

打jar包

  • 在File中的 Project Structure 中,点击Artifacts,选择 JAR,Empty,从而创建出一个空的jar包。

  • 之后在Name中重命名jar包,并从右侧把需要添加的模块拖入左侧jar包中,此时jar包下会包含有相应的模块,点击右下OK。

  • 在Build,Build Artfacts中,选中该包,点击Build就建好包了。

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值