Spring 的内容已经学习了三篇内容,今天算是最后一篇文章,这节内容基本上是熟悉流程,本文要实现的功能:通过web页面访问数据库,实现对数据表中的数据插入和查询;与之前内容不同的是这次要创建 web 项目,而不再是 Java 项目,此外还要简单回顾一下 jsp 的内容,接触到的新知识:如何将Spring容器对象全局唯一。
这一步我们还是继续使用上一节内容中新建的表programmer
,里面有三个字段:id
、name
和age
,很简单,这里不做具体流程展示了。
创建web项目其实和创建java项目的区别就是我们选择的模板不同,当然还是基于maven来创建的,模板选择xxx-maven-archetype-webapp
就 ok 了。
创建完成之后,目录结构会比Java项目多出来一个webapp
目录,相应的缺少了java
和resources
目录,我们手动创建即可。
在pom.xml
文件中添加依赖,不同于上节内容的是,这里需要再增加两个依赖(jsp和servlet),完整代码如下:
4.0.0
com.javafirst
spring-webapp
1.0-SNAPSHOT
war
UTF-8
1.8
1.8
junit
junit
4.11
test
mysql
mysql-connector-java
8.0.25
org.mybatis
mybatis
3.5.7
org.springframework
spring-context
5.3.14
org.mybatis
mybatis-spring
1.3.3
org.springframework
spring-tx
5.3.14
org.springframework
spring-jdbc
5.3.14
org.springframework
spring-aspects
5.3.14
com.alibaba
druid
1.2.8
javax.servlet
javax.servlet-api
3.1.0
javax.servlet.jsp
javax.servlet.jsp-api
2.3.3
src/main/java
**/*.properties
**/*.xml
false
本文在后面还会增加一个依赖,各位记得这个文件。
这里新建的实体类中的字段没有和表中字段名保持一致,就这点区别,具体代码如下:
public class Programmer {
private Integer pId;
private Integer pAge;
private String pName;
public Integer getpId() {
return pId;
}
public void setpId(Integer pId) {
this.pId = pId;
}
public Integer getpAge() {
return pAge;
}
public void setpAge(Integer pAge) {
this.pAge = pAge;
}
public String getpName() {
return pName;
}
public void setpName(String pName) {
this.pName = pName;
}
@Override
public String toString() {
return "Programmer信息:{" +
"pId=" + pId +
", pAge=" + pAge +
", pName='" + pName + '\'' +
'}';
}
}
我们要实现插入数据和查询数据,所以我们的dao只需提供两个接口即可。
public interface ProgrammerDaoNew {
int insertProgrammer(Programmer programmer);
Programmer selectProgrammerById(Integer id);
}
对应mapper文件这里依旧是分开的,位置的resources
目录下的mapper
文件夹中,具体代码如下:
insert into programmer(`name`,age) values (#{pName},#{pAge})
这个和上一节内容一样,该配置文件中要完善的内容也大致相同,其实就和前面说过一样,基本上都是流程代码:
到这里大家应该有一个感受点吧:
以上流程基本上都是环环相扣的,也就是存在顺序,你看每一个文件中都会引入上一步创建的内容,写多了,自然就顺手了。
我们的业务只有添加记录和查询记录,当然各位还可以在此基础上进行扩展,我们的接口内容如下:
public interface ProgrammerService {
int addProgrammer(Programmer programmer);
Programmer findProgrammer(Integer id);
}
其实现类中,是我们真实业务开发中需要做的工作,比较各种校验通过后才进行真正的添加记录工作等等。
public class ProgrammerServiceImpl implements ProgrammerService {
ProgrammerDaoNew programmerDao;
public void setProgrammerDao(ProgrammerDaoNew programmerDao) {
this.programmerDao = programmerDao;
}
@Override
public int addProgrammer(Programmer programmer) {
return programmerDao.insertProgrammer(programmer);
}
@Override
public Programmer findProgrammer(Integer id) {
return programmerDao.selectProgrammerById(id);
}
}
有人可能会好奇,这里的 setProgrammerDao()
方法什么时候会调用呢?其实这是Spring框架在处理,当我们在Spring的配置文件中声明了自定义的Service之后,就会自动进行设值注入,这是我们学习Spring第一节内容时掌握的知识。
其实都是样板代码,这个前面文章里也已经提到了
这里我习惯将数据源的相关配置单独提取文件,这也是主流做法,推荐大家也养成习惯,jdbc.properties
文件内容如下:
jdbc.url=jdbc:mysql://localhost:3306/spring_demo
jdbc.username=root
jdbc.password=root
到这里其实我们已经完成了基本的配置,但我们创建的是web项目,不是java项目,所以我们要进行测试的话,还需要有web页面和简单的逻辑,这就要用到我们的webapp
目录了以及jsp
知识。
我们需要两个jsp页面,一个用来录入信息和提供查询功能,也就是插入操作,页面我们提供姓名和年龄输入,然后提交就进行数据库的插入操作,这个文件名就叫register.jsp
,其代码如下:
<%@ page contentType="text/html;charset=UTF-8" language="java" %>
录入一个工程师
这个页面运行起来大概长这样:
当我们录入成功后,页面会跳转到一个成功页面,就是我们的第二个jsp页面registerSuccess.jsp
,我们不关联具体逻辑,只做简单展示,完整代码如下:
<%--
Created by studyingJava
Date: 2022/1/24
Time: 15:46
--%>
<%@ page contentType="text/html;charset=UTF-8" language="java" %>
注册成功
恭喜你,完成注册!即将为您跳转首页...
查询成功我们不做跳转页面,当前页面也不做展示,我们可以通过控制台看查询信息即可,因为我们在前面的实体类中已经重写了toString()
方法;当然各位如果感兴趣,可以自行将结果显示在页面上。
页面的请求处理和展示我们同样需要创建两个Servlet,一个用来处理录入请求,也就是post提价过来的数据,另一个处理查询操作,也就是get请求数据操作,下面是代码:
AddProgrammerServlet.java
代码如下:
/**
* desc:
* author: 推荐学java
*
* weChat: studyingJava
*/
public class AddProgrammerServlet extends HttpServlet {
@Override
protected void doPost(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {
req.setCharacterEncoding("utf-8");
// 取出表单提交过来的注册数据
String name = req.getParameter("name");
String age = req.getParameter("age");
System.out.println("提交过来的数据:" + name + age);
// 创建Spring容器 插入数据库
String config = "spring-applicationContext.xml";
ApplicationContext context = new ClassPathXmlApplicationContext(config);
ProgrammerService service = (ProgrammerService) context.getBean("programmerService");
Programmer programmer = new Programmer();
programmer.setpName(name);
programmer.setpAge(Integer.valueOf(age));
service.addProgrammer(programmer);
// 给用户反馈
req.getRequestDispatcher("/registerSuccess.jsp").forward(req, resp);
}
@Override
protected void doGet(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {
super.doGet(req, resp);
}
}
其实这里主要就是三步骤,大家可以看代码注释。
FindProgrammerServlet.java
代码如下:
/**
* desc:
* author: 推荐学java
*
* weChat: studyingJava
*/
public class FindProgrammerServlet extends HttpServlet {
@Override
protected void doPost(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {
}
@Override
protected void doGet(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {
req.setCharacterEncoding("utf-8");
// 取出表单提交过来的注册数据
String pId = req.getParameter("pId");
System.out.println("提交过来的要查询的用户ID:" + pId);
// 创建Spring容器 插入数据库
String config = "spring-applicationContext.xml";
ApplicationContext context = new ClassPathXmlApplicationContext(config);
ProgrammerService service = (ProgrammerService) context.getBean("programmerService");
Programmer programmer = service.findProgrammer(Integer.valueOf(pId));
System.out.println(programmer);
}
}
逻辑其实比较简单,细心的朋友是不是发现,我们分别在不同的 Servlet 中创建了Spring容器对象,这就是本文开头提出的需要解决的问题,继续往下看。
我们已经创建好了Servlet,现在进行配置,也就是让浏览器访问的时候能找到对应处理请求的功能承载页面,配置也比较简单,在webapp
目录下的WEB-INF
下的 web.xml
中完善内容如下:
Archetype Created Web Application
AddProgrammerServlet
com.javafirst.controller.AddProgrammerServlet
AddProgrammerServlet
/add
FindProgrammerServlet
com.javafirst.controller.FindProgrammerServlet
FindProgrammerServlet
/find
这里就是相当于入口,我们的Servlet就相当于页面,而每个页面要使用,就得现在这里注册。
到这里,我们的所有工作都已就绪,但不同于java项目的是,web项目需要部署发布才可在浏览器进行访问,关于IDEA部署web项目,这里就不多讲了,注意一点是你必须安装并配置好 JDK
和tomcat
环境。
另外有可能会遇到8080端口被占用的错误提示,导致我们的项目Service启动不起来,这里给大家一个命令查找某个端口被哪个PID(进程ID)占用?
netstat -aon | findstr 8080
找出该进程的ID,然后再通过命令将其 kill 掉:
netstat -aon | findstr 14321
然后尝试重新启动项目即可。这里的两条命令是通过命令行窗口执行的。
这就是我们需要解决前面提到的问题,使用ContextLoaderListener
监听器,该监听器是Spring框架提供的,核心操作两步:
在pom.xml
中添加依赖spring-web
在web.xml中配置context-param
标签
spring-web依赖
org.springframework
spring-web
1.2.6
在web.xml
中的配置如下:
contextConfigLocation
classpath:spring-applicationContext.xml
org.springframework.web.context.ContextLoaderListener
完成这两步配置后,接下来我们就可以使用Spring提供的工具类来修改我们的初始化Spring容器代码,具体如下:
//String config = "spring-applicationContext.xml";
//ApplicationContext context = new ClassPathXmlApplicationContext(config);
// 使用这句就替代了我们前面的使用方式
ApplicationContext context = WebApplicationContextUtils.getRequiredWebApplicationContext(getServletContext());
这样这样在多个地方获取ApplicationContext
对象,系统就不会重新创建,保证全局唯一。
Spring与MyBatis结合使用其实非常方便,很多工作都可以配置好之后专注业务开发即可这可能就是框架带来的好处
创建基于maven的Java项目和web项目流程必须会,能完善常用配置
学编程,推荐首选Java语言,小编创建了一个专注Java的原创公众号
推荐学java
,各位可以在微信搜索javaFirst
关注,一起开启Java旅途!
推荐学java——Spring事务
推荐学java——Spring集成MyBatis
推荐学java——Spring之AOP
推荐学java——Spring第一课
推荐学java——MyBatis高级
推荐学Java——第一个MyBatis程序
推荐学java——Maven初识
推荐学Java——数据表高级操作
推荐学Java——数据表操作
推荐学Java——初识数据库
推荐学Java—应该了解的前端内容
一文回顾 Java 入门知识(下)
一文回顾 Java 入门知识(中)
一文回顾 Java 入门知识(上)