基于idea的SSM框架项目搭建
整合步骤
- 创建项目,添加jar包
- 创建包、实体类与mapper
- 添加连接数据库文件
- 添加日志文件
- 添加Spring配置文件
- 添加SpringMVC配置文件
- 修改web.xml文件
一、搭建整合环境
1.1创建表
CREATE TABLE `logs` (
`logid` int(11) NOT NULL AUTO_INCREMENT,
`username` varchar(30) CHARACTER SET utf8 COLLATE utf8_general_ci NOT NULL,
`ip` varchar(30) CHARACTER SET utf8 COLLATE utf8_general_ci NOT NULL,
`logtime` date NOT NULL,
PRIMARY KEY (`logid`) USING BTREE
) ENGINE = InnoDB AUTO_INCREMENT = 3 CHARACTER SET = utf8 COLLATE = utf8_general_ci ROW_FORMAT = Dynamic;
CREATE TABLE `users` (
`userid` int(11) NOT NULL AUTO_INCREMENT,
`username` varchar(30) CHARACTER SET utf8 COLLATE utf8_general_ci NOT NULL,
`userpwd` varchar(30) CHARACTER SET utf8 COLLATE utf8_general_ci NOT NULL,
PRIMARY KEY (`userid`) USING BTREE,
UNIQUE INDEX `username_uk`(`username`) USING BTREE
) ENGINE = InnoDB AUTO_INCREMENT = 3 CHARACTER SET = utf8 COLLATE = utf8_general_ci ROW_FORMAT = Dynamic;
1.2 创建web项目
1.3 添加jar包
1.4 创建包、实体类与Mapper
二、配置SSM整合文件
2.1 添加连接数据库的properties文件
jdbc.driver=com.mysql.jdbc.Driver
jdbc.url=jdbc:mysql://localhost:3306/ssm
jdbc.username=root
jdbc.password=xxxx
2.2 添加日志配置文件(log4j)
log4j.rootLogger=info,console
### appender.console输出到控制台 ###
log4j.appender.console=org.apache.log4j.ConsoleAppender
log4j.appender.console.layout=org.apache.log4j.PatternLayout
log4j.appender.console.layout.ConversionPattern=<%d> %5p (%F:%L) [%t] (%c) - %m%n
log4j.appender.console.Target=System.out
### appender.logfile输出到日志文件 ###
log4j.appender.logfile=org.apache.log4j.RollingFileAppender
log4j.appender.logfile.File=SysLog.log
log4j.appender.logfile.MaxFileSize=500KB
log4j.appender.logfile.MaxBackupIndex=7
log4j.appender.logfile.layout=org.apache.log4j.PatternLayout
log4j.appender.logfile.layout.ConversionPattern=<%d> %p (%F:%L) [%t] %c - %m%n
2.3 添加Spring配置文件
在整合SSM框架时,为了对Spring配置项进行清晰的管理,我们可以采用“分而治之”的方式来定义Spring配置文件。将Spring配置文件分成三份:
applicationContext-dao.xml:用来配置与Mybatis整合
applicationContext-trans.xml:用来配置Spring声明式事务管理
applicationContext-services.xml:用来配置注解扫描以及其他的Spring配置
2.3.1 配置整合Mybatis
applicationContext-dao.xml
<?xml version="1.0" encoding="UTF-8"?>
<beans xmlns="http://www.springframework.org/schema/beans"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xmlns:context="http://www.springframework.org/schema/context"
xsi:schemaLocation="http://www.springframework.org/schema/beans http://www.springframework.org/schema/beans/spring-beans.xsd
http://www.springframework.org/schema/context http://www.springframework.org/schema/context/spring-context.xsd">
<!--配置整合Mybatis-->
<!--配置解析Properties文件的工具类-->
<context:property-placeholder location="classpath:db.properties"/>
<!--配置数据源-->
<bean id="dataSource" class="org.springframework.jdbc.datasource.DriverManagerDataSource">
<property name="driverClassName" value="${jdbc.driver}"/>
<property name="url" value="${jdbc.url}"/>
<property name="username" value="${jdbc.username}"/>
<property name="password" value="${jdbc.password}"/>
</bean>
<!--配置SqlSessionFactory-->
<bean id="sqlSessionFactoryBean" class="org.mybatis.spring.SqlSessionFactoryBean">
<property name="dataSource" ref="dataSource"/>
<property name="typeAliasesPackage" value="com.sky.pojo"/>
</bean>
<!--配置MapperScannerConfigurer-->
<bean id="mapperScannerConfigurer" class="org.mybatis.spring.mapper.MapperScannerConfigurer">
<property name="basePackage" value="com.sky.mapper"/>
</bean>
</beans>
2.3.2 配置Spring声明式事务管理
<?xml version="1.0" encoding="UTF-8"?>
<!--配置声明式事务管理-->
<beans xmlns="http://www.springframework.org/schema/beans"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xmlns:aop="http://www.springframework.org/schema/aop"
xmlns:tx="http://www.springframework.org/schema/tx"
xsi:schemaLocation="http://www.springframework.org/schema/beans http://www.springframework.org/schema/beans/spring-beans.xsd
http://www.springframework.org/schema/aop http://www.springframework.org/schema/aop/spring-aop.xsd
http://www.springframework.org/schema/tx http://www.springframework.org/schema/tx/spring-tx.xsd">
<import resource="applicationContext-dao.xml"/>
<!--配置事务管理器的切面-->
<bean id="transactionManager" class="org.springframework.jdbc.datasource.DataSourceTransactionManager">
<property name="dataSource" ref="dataSource"/>
</bean>
<!--配置事务属性-->
<tx:advice id="myAdvice" transaction-manager="transactionManager">
<tx:attributes>
<tx:method name="add*" propagation="REQUIRED"/>
<tx:method name="modify*" propagation="REQUIRED"/>
<tx:method name="drop*" propagation="REQUIRED"/>
<tx:method name="userLogin" propagation="REQUIRED"/>
<tx:method name="find*" read-only="true"/>
</tx:attributes>
</tx:advice>
<!--配置切点-->
<aop:config>
<aop:pointcut id="myPointcut" expression="execution(* com.sky.service.*.*(..))"/>
<aop:advisor advice-ref="myAdvice" pointcut-ref="myPointcut"/>
</aop:config>
</beans>
2.3.3 配置注解扫描
<?xml version="1.0" encoding="UTF-8"?>
<beans xmlns="http://www.springframework.org/schema/beans"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xmlns:context="http://www.springframework.org/schema/context"
xsi:schemaLocation="http://www.springframework.org/schema/beans http://www.springframework.org/schema/beans/spring-beans.xsd
http://www.springframework.org/schema/context http://www.springframework.org/schema/context/spring-context.xsd">
<!--配置注解扫描-->
<context:component-scan base-package="com.sky.service"/>
</beans>
2.4 配置SpringMVC
springmvc.xml
<?xml version="1.0" encoding="UTF-8"?>
<beans xmlns="http://www.springframework.org/schema/beans"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xmlns:context="http://www.springframework.org/schema/context"
xmlns:mvc="http://www.springframework.org/schema/mvc"
xsi:schemaLocation="http://www.springframework.org/schema/beans http://www.springframework.org/schema/beans/spring-beans.xsd
http://www.springframework.org/schema/context http://www.springframework.org/schema/context/spring-context.xsd http://www.springframework.org/schema/mvc http://www.springframework.org/schema/mvc/spring-mvc.xsd">
<!--配置注解扫描-->
<context:component-scan base-package="com.sky.web.controller"/>
<!--配置注解驱动-->
<mvc:annotation-driven/>
<!--配置视图解析器-->
<bean class="org.springframework.web.servlet.view.InternalResourceViewResolver">
<property name="prefix" value="/WEB-INF/jsp/"/>
<property name="suffix" value=".jsp"/>
</bean>
<!--配置静态资源映射器-->
<mvc:resources mapping="/js/**" location="/WEB-INF/js/"/>
<mvc:resources mapping="/img/**" location="/WEB-INF/img/"/>
<mvc:resources mapping="/css/**" location="/WEB-INF/css/"/>
</beans>
2.5 配置web.xml文件
<?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">
<!--指定Spring配置文件的位置及名称-->
<context-param>
<param-name>contextConfigLocation</param-name>
<param-value>classpath:applicationContext-*.xml</param-value>
</context-param>
<!--配置启动Spring框架的监听器-->
<listener>
<listener-class>org.springframework.web.context.ContextLoaderListener</listener-class>
</listener>
<!--配置SpringMVC的前端控制器-->
<servlet>
<servlet-name>springmvc</servlet-name>
<servlet-class>org.springframework.web.servlet.DispatcherServlet</servlet-class>
<init-param>
<param-name>contextConfigLocation</param-name>
<param-value>classpath:springmvc.xml</param-value>
</init-param>
<load-on-startup>1</load-on-startup>
</servlet>
<servlet-mapping>
<servlet-name>springmvc</servlet-name>
<url-pattern>/</url-pattern>
</servlet-mapping>
<!--配置字符编码过滤器-->
<filter>
<filter-name>encodingFilter</filter-name>
<filter-class>org.springframework.web.filter.CharacterEncodingFilter</filter-class>
<init-param>
<param-name>encoding</param-name>
<param-value>utf-8</param-value>
</init-param>
</filter>
<filter-mapping>
<filter-name>encodingFilter</filter-name>
<url-pattern>/*</url-pattern>
</filter-mapping>
</web-app>
三、实现用户登录
3.1 创建业务层
public interface UsersService {
Users userLogin(Users users);
}
3.2 创建业务层实现类
@Service
public class UsersServiceImpl implements UsersService {
@Autowired
private UsersMapper usersMapper;
/**
* 用户登录
* @param users
* @return
*/
@Override
public Users userLogin(Users users) {
UsersExample usersExample = new UsersExample();
UsersExample.Criteria criteria = usersExample.createCriteria();
criteria.andUsernameEqualTo(users.getUsername());
criteria.andUserpwdEqualTo(users.getUserpwd());
List<Users> list = this.usersMapper.selectByExample(usersExample);
if(list.isEmpty() || list.size() <= 0) {
throw new UserNotFoundException("用户名或密码有误!");
}
return list.get(0);
}
}
3.3 创建自定义异常
/**
* 自定义异常类,用户登录时错误
* @author sky
* @create 2020-09-26 12:47
*/
public class UserNotFoundException extends RuntimeException {
public UserNotFoundException() {
}
public UserNotFoundException(String message) {
super(message);
}
public UserNotFoundException(String message, Throwable cause) {
super(message, cause);
}
}
3.4 创建用户登录控制器
/**
* 用户管理控制器
* @author sky
* @create 2020-09-26 12:53
*/
@Controller
@RequestMapping("/user")
public class UsersController {
@Autowired
private UsersService usersService;
/**
* 处理用户登录请求
* @param users
* @param session
* @return
*/
@RequestMapping("/userLogin")
public String userLogin(UsersExt users, HttpSession session, HttpServletRequest request) {
String ip = request.getRemoteAddr();
users.setIp(ip);
Users user = this.usersService.userLogin(users);
session.setAttribute("user", user);
return "redirect:/page/index";
}
}
3.5 全局异常处理器
/**
* 全局异常处理器
* @author sky
* @create 2020-09-26 12:57
*/
@ControllerAdvice
public class GlobalExceptionController {
@ExceptionHandler({com.sky.exception.UserNotFoundException.class})
public String userNotFoundExceptionHandler(Exception e, Model model) {
model.addAttribute("msg", e.getMessage());
return "login";
}
@ExceptionHandler({java.lang.Exception.class})
public String exceptionHandler(Exception e) {
return "redirect:/page/error";
}
}
3.6 创建用户登录页面
<%@ page contentType="text/html;charset=UTF-8" language="java" %>
<html>
<head>
<title>Title</title>
</head>
<body>
${msg}
<form action="/user/userLogin" method="post">
用户名:<input type="text" name="username"/><br/>
密码:<input type="password" name="userpwd"/><br/>
<input type="submit" value="OK"/>
</form>
</body>
</html>
3.7 创建异常提醒页面
<%@ page contentType="text/html;charset=UTF-8" language="java" %>
<html>
<head>
<title>Title</title>
</head>
<body>
出错了,请与管理员联系:sky@sky.com
</body>
</html>
3.8 创建页面跳转控制器
/**
* 页面跳转控制器
* @author sky
* @create 2020-09-26 13:05
*/
@Controller
public class PageController {
/**
* 请求首页
*/
@RequestMapping("/")
public String showIndex() {
return "index";
}
/**
* 处理页面跳转请求
*/
@RequestMapping("/page/{page}")
public String showPage(@PathVariable String page) {
return page;
}
}
3.9 创建判断用户是否登录的拦截器
/**
* 判断用户是否登录
* @author sky
* @create 2020-09-26 13:22
*/
public class LoginInterceptor implements HandlerInterceptor {
@Override
public boolean preHandle(HttpServletRequest request, HttpServletResponse response, Object handler) throws Exception {
HttpSession session = request.getSession();
Users user = (Users) session.getAttribute("user");
if(user == null || user.getUsername().length() >= 0) {
response.sendRedirect("/page/login");
return false;
}
return true;
}
@Override
public void postHandle(HttpServletRequest request, HttpServletResponse response, Object handler, ModelAndView modelAndView) throws Exception {
}
@Override
public void afterCompletion(HttpServletRequest request, HttpServletResponse response, Object handler, Exception ex) throws Exception {
}
}
3.10 配置拦截器
在SpringMVC配置文件中配置拦截器
<!--配置拦截器-->
<mvc:interceptors>
<mvc:interceptor>
<mvc:mapping path="/**"/>
<mvc:exclude-mapping path="/page/login"/>
<mvc:exclude-mapping path="/user/userLogin"/>
<mvc:exclude-mapping path="/page/error"/>
<bean class="com.sky.interceptor.LoginInterceptor"/>
</mvc:interceptor>
</mvc:interceptors>
四、记录用户登录日志
4.1 创建登录日志记录切面
/**
* 用户登录日记记录切面
* @author sky
* @create 2020-09-26 18:26
*/
@Aspect
@Component
public class UsersLoginLogAOP {
@Autowired
private LogsMapper logsMapper;
/**
* 配置切点
*/
@Pointcut("execution(* com.sky.service.UsersService.userLogin(..))")
public void myPointcut() {
}
/**
* 在后置通知中记录登录日记
* @param joinPoint
*/
@AfterReturning("myPointcut()")
public void userLoginLog(JoinPoint joinPoint) {
Object[] objects = joinPoint.getArgs();
UsersExt users = (UsersExt) objects[0];
Logs logs = new Logs();
logs.setLogtime(new Date());
logs.setUsername(users.getUsername());
logs.setIp(users.getIp());
this.logsMapper.insertSelective(logs);
}
}
4.2 创建Users扩展实体类
public class UsersExt extends Users {
private String ip;
public String getIp() {
return ip;
}
public void setIp(String ip) {
this.ip = ip;
}
}
4.3 修改控制器
/**
* 处理用户登录请求
* @param users
* @param session
* @return
*/
@RequestMapping("/userLogin")
public String userLogin(UsersExt users, HttpSession session, HttpServletRequest request) {
String ip = request.getRemoteAddr();
users.setIp(ip);
Users user = this.usersService.userLogin(users);
session.setAttribute("user", user);
return "redirect:/page/index";
}
4.4 配置切面
修改applicationContext-service文件
<!--配置注解扫描-->
<context:component-scan base-package="com.sky.service,com.sky.aop"/>
修改applicationContext-trans.xml文件
<aop:aspectj-autoproxy proxy-target-class="true"/>
五、项目总架构
六、运行结果
登录成功 -> 数据库记录登录信息
登录失败 -> 数据库不记录登录信息