概述
效果展
数据库设计
会员表
DROP TABLE IF EXISTS `user_type`;
CREATE TABLE `user_type` (
`userTypeId` int(11) NOT NULL AUTO_INCREMENT,
`userTypeName` varchar(255) DEFAULT NULL,
`userTypeDesc` varchar(255) DEFAULT NULL,
PRIMARY KEY (`userTypeId`)
) ENGINE=InnoDB AUTO_INCREMENT=6 DEFAULT CHARSET=utf8mb4;
用户表
DROP TABLE IF EXISTS `user`;
CREATE TABLE `user` (
`userId` int(11) NOT NULL AUTO_INCREMENT,
`username` varchar(255) DEFAULT NULL,
`password` varchar(255) DEFAULT NULL,
`phone` varchar(255) DEFAULT NULL,
`nickname` varchar(255) DEFAULT NULL,
`userImg` longtext,
`email` varchar(255) DEFAULT NULL,
`userIntroduce` longtext,
`userSex` varchar(255) DEFAULT NULL,
`signature` longtext,
`userStatus` varchar(255) DEFAULT NULL,
PRIMARY KEY (`userId`)
) ENGINE=InnoDB AUTO_INCREMENT=2 DEFAULT CHARSET=utf8mb4;
会员_用户中间表
DROP TABLE IF EXISTS `user_user_type`;
CREATE TABLE `user_user_type` (
`userId` int(11) DEFAULT NULL,
`userTypeId` int(11) DEFAULT NULL
) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4;
实体类设计
会员类型表
/**
* 会员类型
*/
@Data
public class UserType {
@TableId
private Integer userTypeId;
private String userTypeName;//名称【普通会员/黄金会员/钻石会员/至尊会员/骇客会员】
private String userTypeDesc;//详情
}
用户表
/**
* 用户
*/
@Data
public class User implements Serializable {
@TableId
private Integer userId;
private String userImg; // 头像
private String nickname; // 昵称
private String username; // 账号
private String password; // 密码
private String phone; // 手机号
private String email;//邮箱
private String userSex; // 性别
private String signature;//个性签名
private String userIntroduce;//自我介绍
private String userStatus; // 用户状态(1激活 0未激活)
}
Mapper层开发
用户mapper
public interface UserMapper extends BaseMapper<User> {
}
用户类型mapper
public interface UserTypeMapper extends BaseMapper<UserType> {
//添加用户_用户类型中间表的数据
void addUser_userType(@Param("userId") Integer userId, @Param("userTypeId") Integer userTypeId);
//删除用户_用户类型中间表的数据
void deleteUser_userType(@Param("userId") Integer userId, @Param("userTypeId") Integer userTypeId);
//根据用户id删除用户_用户类型中间表的数据
void deleteUser_userTypeByUserId(Integer userId);
//根据用户类型id删除用户_用户类型中间表的数据
void deleteUser_userTypeByUserTypeId(Integer userTypeId);
//根据用户id查询用户_用户类型中间表的专栏数据
List<UserType> findUserTypeByUserId(Integer userId);
}
用户类型mapper映射文件
<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE mapper
PUBLIC "-//mybatis.org//DTD Mapper 3.0//EN"
"http://mybatis.org/dtd/mybatis-3-mapper.dtd">
<mapper namespace="jkw.mapper.UserTypeMapper">
<insert id="addUser_userType">
INSERT INTO user_user_type
VALUES (#{userId}, #{userTypeId});
</insert>
<delete id="deleteUser_userType">
DELETE
FROM user_user_type
WHERE userId = #{userId}
and userTypeId = #{userTypeId}
</delete>
<delete id="deleteUser_userTypeByUserId" parameterType="int">
DELETE
FROM user_user_type
WHERE userId = #{userId}
</delete>
<delete id="deleteUser_userTypeByUserTypeId" parameterType="int">
DELETE
FROM user_user_type
WHERE userTypeId = #{userTypeId}
</delete>
<select id="findUserTypeByUserId" resultType="jkw.pojo.UserType" parameterType="int">
select user_type.*
from user_type
left join user_user_type
on user_user_type.userTypeId = user_type.userTypeId
where user_user_type.userId = #{userId}
</select>
</mapper>
Service层开发
UserService
public interface UserService {
void add(User user);
void update(User user);
void delete(Integer id);
User findById(Integer id);
Page<User> search(int page, int size);
List<User> findAll();
void updateStatus(Integer id);
// 注册时向redis保存手机号+验证码
void saveRegisterCheckCode(String phone, String checkCode);
// 注册时验证手机号
void registerCheckCode(String phone, String checkCode);
// 注册
void register(User user);
// 账号密码登录
String loginPassword(String username, String password);
// 手机号验证码登录时向redis保存手机号+验证码
void saveLoginCheckCode(String phone, String checkCode);
// 手机号验证码登录
String loginCheckCode(String phone, String checkCode);
// 获取登录用户
User getLoginUser(String token);
}
UserServiceImpl
package jkw.service.impl;
import com.baomidou.mybatisplus.core.conditions.query.QueryWrapper;
import com.baomidou.mybatisplus.extension.plugins.pagination.Page;
import jkw.exception.MyException;
import jkw.mapper.UserMapper;
import jkw.mapper.UserTypeMapper;
import jkw.pojo.User;
import jkw.service.UserService;
import jkw.utils.JWTUtil;
import jkw.utils.Md5Util;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.data.redis.core.RedisTemplate;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;
import java.util.List;
import java.util.concurrent.TimeUnit;
@Service
@Transactional
public class UserServiceImpl implements UserService {
@Autowired
private UserMapper userMapper;
@Autowired
private RedisTemplate redisTemplate;
@Autowired
private UserTypeMapper userTypeMapper;
@Override
public void add(User user) {
user.setPassword(Md5Util.encode(user.getPassword()));
userMapper.insert(user);
}
@Override
public void update(User user) {
User userFromData = userMapper.selectById(user.getUserId());
//判断密码是否修改[若密码为空或者密码和数据库中相等,则未修改]
if (user.getPassword().equals(userFromData.getPassword())) {
userMapper.updateById(user);
} else {
//若修改,则加密后在保存
user.setPassword(Md5Util.encode(user.getPassword()));
userMapper.updateById(user);
}
}
@Override
public void delete(Integer id) {
//先删除用户_用户类型中间表的数据
userTypeMapper.deleteUser_userTypeByUserId(id);
//删除用户
userMapper.deleteById(id);
}
@Override
public User findById(Integer id) {
return userMapper.selectById(id);
}
@Override
public Page<User> search(int page, int size) {
return userMapper.selectPage(new Page<>(page, size), null);
}
@Override
public List<User> findAll() {
return userMapper.selectList(null);
}
@Override
public void updateStatus(Integer id) {
User user = userMapper.selectById(id);
if (user.getUserStatus().equals("1")) {
user.setUserStatus("0");
userMapper.updateById(user);
} else {
user.setUserStatus("1");
userMapper.updateById(user);
}
}
@Override
public void saveRegisterCheckCode(String phone, String checkCode) {
//向redis缓存注册验证码,手机验证码过期时间设为5分钟
redisTemplate.opsForValue().set("registerCheckCode" + phone, checkCode, 300, TimeUnit.SECONDS);
}
@Override
public void registerCheckCode(String phone, String checkCode) {
//获取redis中缓存的注册验证码
String checkCodeFromRedis = (String) redisTemplate.opsForValue().get("registerCheckCode" + phone);
if (!checkCodeFromRedis.equals(checkCode)) {
throw new MyException(604, "验证码错误");
}
}
@Override
public void register(User user) {
//验证手机号是否存在
QueryWrapper<User> queryWrapper1 = new QueryWrapper<>();
queryWrapper1.eq("phone", user.getPhone());
List<User> users1 = userMapper.selectList(queryWrapper1);
if (users1 != null && users1.size() > 0) {
throw new MyException(604, "手机号已存在");
}
//验证账号是否存在
QueryWrapper<User> queryWrapper2 = new QueryWrapper<>();
queryWrapper2.eq("username", user.getPhone());
List<User> users2 = userMapper.selectList(queryWrapper2);
if (users2 != null && users2.size() > 0) {
throw new MyException(604, "账号已存在");
}
//新增用户
user.setUserStatus("1");
user.setPassword(Md5Util.encode(user.getPassword()));
userMapper.insert(user);
}
@Override
public String loginPassword(String username, String password) {
QueryWrapper<User> queryWrapper = new QueryWrapper<>();
queryWrapper.eq("username", username);
User user = userMapper.selectOne(queryWrapper);
//判断用户是否存在
if (user == null) {
throw new MyException(605, "用户不存在");
}
//判断面是否正确
boolean verify = Md5Util.verify(password, user.getPassword());
if (!verify) {
throw new MyException(605, "密码错误");
}
//登录成功,生成jwt令牌
String token = JWTUtil.token(user);
return token;
}
@Override
public void saveLoginCheckCode(String phone, String checkCode) {
//判断该手机号是否有对应的用户
QueryWrapper<User> queryWrapper = new QueryWrapper<>();
queryWrapper.eq("phone", phone);
User user = userMapper.selectOne(queryWrapper);
if (user != null) {
//向redis缓存登录验证码,手机验证码过期时间设为5分钟
redisTemplate.opsForValue().set("loginCheckCode" + phone, checkCode, 300, TimeUnit.SECONDS);
} else {
throw new MyException(605, "用户不存在");
}
}
@Override
public String loginCheckCode(String phone, String checkCode) {
//获取redis中缓存的登录验证码
String checkCodeFromRedis = (String) redisTemplate.opsForValue().get("loginCheckCode" + phone);
if (!checkCodeFromRedis.equals(checkCode)) {
throw new MyException(604, "验证码错误");
}
QueryWrapper<User> queryWrapper = new QueryWrapper<>();
queryWrapper.eq("phone", phone);
User user = userMapper.selectOne(queryWrapper);
//登录成功,生成jwt令牌
return JWTUtil.token(user);
}
@Override
public User getLoginUser(String token) {
return userMapper.selectById(JWTUtil.verifyAndGetId(token));
}
}
UserTypeService
package jkw.service;
import com.baomidou.mybatisplus.extension.plugins.pagination.Page;
import jkw.pojo.UserType;
import java.util.List;
public interface UserTypeService {
void add(UserType userType);
void update(UserType userType);
void delete(Integer id);
UserType findById(Integer id);
List<UserType> findAll();
Page<UserType> search(String search, int page, int size);
//添加用户_用户类型中间表的数据
void addUser_userType(Integer userId, Integer userTypeId);
//删除用户_用户类型中间表的数据
void deleteUser_userType(Integer userId, Integer userTypeId);
//根据用户id删除用户_用户类型中间表的数据
void deleteUser_userTypeByUserId(Integer userId);
//根据用户类型id删除用户_用户类型中间表的数据
void deleteUser_userTypeByUserTypeId(Integer userTypeId);
//根据用户id查询用户_用户类型中间表的专栏数据
List<UserType> findUserTypeByUserId(Integer userId);
}
UserTypeServiceImpl
package jkw.service.impl;
import com.baomidou.mybatisplus.core.conditions.query.QueryWrapper;
import com.baomidou.mybatisplus.extension.plugins.pagination.Page;
import jkw.exception.MyException;
import jkw.mapper.UserMapper;
import jkw.mapper.UserTypeMapper;
import jkw.pojo.User;
import jkw.service.UserService;
import jkw.utils.JWTUtil;
import jkw.utils.Md5Util;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.data.redis.core.RedisTemplate;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;
import java.util.List;
import java.util.concurrent.TimeUnit;
@Service
@Transactional
public class UserServiceImpl implements UserService {
@Autowired
private UserMapper userMapper;
@Autowired
private RedisTemplate redisTemplate;
@Autowired
private UserTypeMapper userTypeMapper;
@Override
public void add(User user) {
user.setPassword(Md5Util.encode(user.getPassword()));
userMapper.insert(user);
}
@Override
public void update(User user) {
User userFromData = userMapper.selectById(user.getUserId());
//判断密码是否修改[若密码为空或者密码和数据库中相等,则未修改]
if (user.getPassword().equals(userFromData.getPassword())) {
userMapper.updateById(user);
} else {
//若修改,则加密后在保存
user.setPassword(Md5Util.encode(user.getPassword()));
userMapper.updateById(user);
}
}
@Override
public void delete(Integer id) {
//先删除用户_用户类型中间表的数据
userTypeMapper.deleteUser_userTypeByUserId(id);
//删除用户
userMapper.deleteById(id);
}
@Override
public User findById(Integer id) {
return userMapper.selectById(id);
}
@Override
public Page<User> search(int page, int size) {
return userMapper.selectPage(new Page<>(page, size), null);
}
@Override
public List<User> findAll() {
return userMapper.selectList(null);
}
@Override
public void updateStatus(Integer id) {
User user = userMapper.selectById(id);
if (user.getUserStatus().equals("1")) {
user.setUserStatus("0");
userMapper.updateById(user);
} else {
user.setUserStatus("1");
userMapper.updateById(user);
}
}
@Override
public void saveRegisterCheckCode(String phone, String checkCode) {
//向redis缓存注册验证码,手机验证码过期时间设为5分钟
redisTemplate.opsForValue().set("registerCheckCode" + phone, checkCode, 300, TimeUnit.SECONDS);
}
@Override
public void registerCheckCode(String phone, String checkCode) {
//获取redis中缓存的注册验证码
String checkCodeFromRedis = (String) redisTemplate.opsForValue().get("registerCheckCode" + phone);
if (!checkCodeFromRedis.equals(checkCode)) {
throw new MyException(604, "验证码错误");
}
}
@Override
public void register(User user) {
//验证手机号是否存在
QueryWrapper<User> queryWrapper1 = new QueryWrapper<>();
queryWrapper1.eq("phone", user.getPhone());
List<User> users1 = userMapper.selectList(queryWrapper1);
if (users1 != null && users1.size() > 0) {
throw new MyException(604, "手机号已存在");
}
//验证账号是否存在
QueryWrapper<User> queryWrapper2 = new QueryWrapper<>();
queryWrapper2.eq("username", user.getPhone());
List<User> users2 = userMapper.selectList(queryWrapper2);
if (users2 != null && users2.size() > 0) {
throw new MyException(604, "账号已存在");
}
//新增用户
user.setUserStatus("1");
user.setPassword(Md5Util.encode(user.getPassword()));
userMapper.insert(user);
}
@Override
public String loginPassword(String username, String password) {
QueryWrapper<User> queryWrapper = new QueryWrapper<>();
queryWrapper.eq("username", username);
User user = userMapper.selectOne(queryWrapper);
//判断用户是否存在
if (user == null) {
throw new MyException(605, "用户不存在");
}
//判断面是否正确
boolean verify = Md5Util.verify(password, user.getPassword());
if (!verify) {
throw new MyException(605, "密码错误");
}
//登录成功,生成jwt令牌
String token = JWTUtil.token(user);
return token;
}
@Override
public void saveLoginCheckCode(String phone, String checkCode) {
//判断该手机号是否有对应的用户
QueryWrapper<User> queryWrapper = new QueryWrapper<>();
queryWrapper.eq("phone", phone);
User user = userMapper.selectOne(queryWrapper);
if (user != null) {
//向redis缓存登录验证码,手机验证码过期时间设为5分钟
redisTemplate.opsForValue().set("loginCheckCode" + phone, checkCode, 300, TimeUnit.SECONDS);
} else {
throw new MyException(605, "用户不存在");
}
}
@Override
public String loginCheckCode(String phone, String checkCode) {
//获取redis中缓存的登录验证码
String checkCodeFromRedis = (String) redisTemplate.opsForValue().get("loginCheckCode" + phone);
if (!checkCodeFromRedis.equals(checkCode)) {
throw new MyException(604, "验证码错误");
}
QueryWrapper<User> queryWrapper = new QueryWrapper<>();
queryWrapper.eq("phone", phone);
User user = userMapper.selectOne(queryWrapper);
//登录成功,生成jwt令牌
return JWTUtil.token(user);
}
@Override
public User getLoginUser(String token) {
return userMapper.selectById(JWTUtil.verifyAndGetId(token));
}
}
控制层开发
UserCon
package jkw.controller.back;
import com.baomidou.mybatisplus.extension.plugins.pagination.Page;
import jkw.pojo.User;
import jkw.service.UserService;
import jkw.vo.BaseResult;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.security.access.prepost.PreAuthorize;
import org.springframework.web.bind.annotation.*;
import java.util.List;
@CrossOrigin
@RequestMapping("/back/user")
@RestController
public class UserCon {
@Autowired
private UserService userService;
/**
* 新增
*
* @param user
* @return
*/
@PostMapping("/add")
@PreAuthorize("hasAnyAuthority('/user')")
public BaseResult add(User user) {
userService.add(user);
return BaseResult.ok();
}
/**
* 修改
*
* @param user
* @return
*/
@PostMapping("/update")
@PreAuthorize("hasAnyAuthority('/user')")
public BaseResult update(User user) {
userService.update(user);
return BaseResult.ok();
}
/**
* 删除
*
* @param userId
* @return
*/
@DeleteMapping("/delete")
@PreAuthorize("hasAnyAuthority('/user')")
public BaseResult delete(Integer userId) {
userService.delete(userId);
return BaseResult.ok();
}
/**
* 根据id查询
*
* @param userId
* @return
*/
@GetMapping("/findById")
@PreAuthorize("hasAnyAuthority('/user')")
public BaseResult findById(Integer userId) {
User user = userService.findById(userId);
return BaseResult.ok(user);
}
/**
* 查询所有
*
* @return
*/
@GetMapping("/findAll")
@PreAuthorize("hasAnyAuthority('/user')")
public BaseResult findAll() {
List<User> all = userService.findAll();
return BaseResult.ok(all);
}
/**
* 分页查询
*
* @param page
* @param size
* @return
*/
@GetMapping("/search")
@PreAuthorize("hasAnyAuthority('/user')")
public BaseResult search(int page, int size) {
Page<User> brandPage = userService.search(page, size);
return BaseResult.ok(brandPage);
}
/**
* 修改状态
*
* @param userId
* @return
*/
@PostMapping("/updateStatus")
@PreAuthorize("hasAnyAuthority('/user')")
public BaseResult updateStatus(Integer userId) {
userService.updateStatus(userId);
return BaseResult.ok();
}
}
FrontUserCon
package jkw.controller.front;
import jkw.pojo.User;
import jkw.service.MessageService;
import jkw.service.UserService;
import jkw.utils.RandomUtil;
import jkw.vo.BaseResult;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.web.bind.annotation.*;
@RestController
@CrossOrigin
@RequestMapping("/front/user")
public class FrontUserCon {
@Autowired
private UserService userService;
@Autowired
private MessageService messageService;
/**
* 发送注册短信
*
* @param phone 注册手机号
* @return 操作结果
*/
@GetMapping("/sendMessage")
public BaseResult sendMessage(String phone) {
// 1.生成随机四位数
String checkCode = RandomUtil.buildCheckCode(4);
// 2.发送短信
BaseResult result = messageService.sendMessage(phone, checkCode);
// 3.发送成功,将验证码保存到redis中,发送失败,返回发送结果
if (200 == result.getCode()) {
userService.saveRegisterCheckCode(phone, checkCode);
return BaseResult.ok();
} else {
return result;
}
}
/**
* 验证用户注册验证码
*
* @param phone 手机号
* @param checkCode 验证码
* @return 200验证成功,605验证码不正确
*/
@GetMapping("/registerCheckCode")
public BaseResult register(String phone, String checkCode) {
userService.registerCheckCode(phone, checkCode);
return BaseResult.ok();
}
/**
* 用户注册
*
* @param user 用户信息
* @return 注册结果
*/
@PostMapping("/register")
public BaseResult register(User user) {
userService.register(user);
return BaseResult.ok();
}
/**
* 用户名密码登录
*
* @param user 用户对象
* @return 登录结果
*/
@PostMapping("/loginPassword")
public BaseResult loginPassword(User user) {
String token = userService.loginPassword(user.getUsername(), user.getPassword());
return BaseResult.ok(token);
}
/**
* 发送登录短信验证码
*
* @param phone 手机号
* @return 操作结果
*/
@GetMapping("/sendLoginCheckCode")
public BaseResult sendLoginCheckCode(String phone) {
// 1.生成随机四位数
String checkCode = RandomUtil.buildCheckCode(4);
// 2.发送短信
BaseResult result = messageService.sendMessage(phone, checkCode);
// 3.发送成功,将验证码保存到redis中,发送失败,返回发送结果
if (200 == result.getCode()) {
userService.saveLoginCheckCode(phone, checkCode);
return BaseResult.ok();
} else {
return result;
}
}
/**
* 手机号验证码登录
*
* @param phone 手机号
* @param checkCode 验证码
* @return 登录结果
*/
@PostMapping("/loginCheckCode")
public BaseResult loginCheckCode(String phone, String checkCode) {
String token = userService.loginCheckCode(phone, checkCode);
return BaseResult.ok(token);
}
/**
* 获取登录用户
*
* @param token 令牌
* @return 用户名
*/
@GetMapping("/getUser")
public BaseResult getUser(String token) {
User u = userService.getLoginUser(token);
return BaseResult.ok(u);
}
/**
* 根据id查询
*
* @param userId
* @return
*/
@GetMapping("/findById")
public BaseResult findById(Integer userId) {
User user = userService.findById(userId);
return BaseResult.ok(user);
}
}
FrontUserTypeCon
package jkw.controller.back;
import com.baomidou.mybatisplus.extension.plugins.pagination.Page;
import jkw.pojo.UserType;
import jkw.service.UserTypeService;
import jkw.vo.BaseResult;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.security.access.prepost.PreAuthorize;
import org.springframework.web.bind.annotation.*;
import java.util.List;
@CrossOrigin
@RestController
@RequestMapping("/back/userType")
public class UserTypeCon {
@Autowired
private UserTypeService userTypeService;
/**
* 新增
*
* @param userType
* @return
*/
@PostMapping("/add")
@PreAuthorize("hasAnyAuthority('/user')")
public BaseResult add(UserType userType) {
userTypeService.add(userType);
return BaseResult.ok();
}
/**
* 修改
*
* @param userType
* @return
*/
@PostMapping("/update")
@PreAuthorize("hasAnyAuthority('/user')")
public BaseResult update(UserType userType) {
userTypeService.update(userType);
return BaseResult.ok();
}
/**
* 删除
*
* @param userTypeId
* @return
*/
@DeleteMapping("/delete")
@PreAuthorize("hasAnyAuthority('/user')")
public BaseResult delete(Integer userTypeId) {
userTypeService.delete(userTypeId);
return BaseResult.ok();
}
/**
* 根据id查询
*
* @param userTypeId
* @return
*/
@GetMapping("/findById")
@PreAuthorize("hasAnyAuthority('/user')")
public BaseResult findById(Integer userTypeId) {
UserType userType = userTypeService.findById(userTypeId);
return BaseResult.ok(userType);
}
/**
* 查询所有
*
* @return
*/
@GetMapping("/findAll")
@PreAuthorize("hasAnyAuthority('/user')")
public BaseResult findAll() {
List<UserType> all = userTypeService.findAll();
return BaseResult.ok(all);
}
/**
* 分页查询
*
* @param page
* @param size
* @return
*/
@GetMapping("/search")
@PreAuthorize("hasAnyAuthority('/user')")
public BaseResult search(String search, int page, int size) {
Page<UserType> brandPage = userTypeService.search(search, page, size);
return BaseResult.ok(brandPage);
}
/**
* 添加用户_用户类型中间表的数据
*
* @param userId
* @param userTypeId
* @return
*/
@PostMapping("/addUserType")
@PreAuthorize("hasAnyAuthority('/user')")
public BaseResult addUserType(Integer userId, Integer userTypeId) {
userTypeService.addUser_userType(userId, userTypeId);
return BaseResult.ok();
}
/**
* 删除用户_用户类型中间表的数据
*
* @param userId
* @param userTypeId
* @return
*/
@DeleteMapping("/deleteUserType")
@PreAuthorize("hasAnyAuthority('/user')")
public BaseResult deleteColumn(Integer userId, Integer userTypeId) {
userTypeService.deleteUser_userType(userId, userTypeId);
return BaseResult.ok();
}
/**
* 根据用户id查询用户_用户类型中间表的专栏数据
*
* @param userId
* @return
*/
@GetMapping("/findUserTypeByUserId")
@PreAuthorize("hasAnyAuthority('/user')")
public BaseResult findColumnByBlogId(Integer userId) {
List<UserType> userTypeByUserId = userTypeService.findUserTypeByUserId(userId);
return BaseResult.ok(userTypeByUserId);
}
}
UserTypeCon
package jkw.controller.back;
import jkw.pojo.UserType;
import jkw.service.UserTypeService;
import jkw.vo.BaseResult;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.web.bind.annotation.CrossOrigin;
import org.springframework.web.bind.annotation.GetMapping;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RestController;
import java.util.List;
@CrossOrigin
@RestController
@RequestMapping("/front/userType")
public class FrontUserTypeCon {
@Autowired
private UserTypeService userTypeService;
/**
* 查询所有
*
* @return
*/
@GetMapping("/findAll")
public BaseResult findAll() {
List<UserType> all = userTypeService.findAll();
return BaseResult.ok(all);
}
/**
* 根据用户id查询用户_用户类型中间表的专栏数据
*
* @param userId
* @return
*/
@GetMapping("/findUserTypeByUserId")
public BaseResult findColumnByBlogId(Integer userId) {
List<UserType> userTypeByUserId = userTypeService.findUserTypeByUserId(userId);
return BaseResult.ok(userTypeByUserId);
}
}
后台ui代码
会员等级
<template>
<div class="data-container">
<!--添加 start-->
<div class="data-header">
<el-input class="input" @keyup.enter="searchHandle" v-model="searchInfo" size="large"
placeholder="请输入关键字"></el-input>
<el-button @click="searchHandle" class="button" size="large" type="primary" plain>搜索</el-button>
<el-button round @click="addHander" size="large" type="primary">
<el-icon>
<DocumentAdd/>
</el-icon>
<span>新增</span>
</el-button>
</div>
<!--添加 end-->
<!--表格数据展示 start-->
<div class="data-table">
<el-table :data="dataList.list" style="width: 600px;">
<el-table-column label="id" prop="userTypeId" align="center" width="60"></el-table-column>
<el-table-column label="名称" prop="userTypeName" align="center" width="120">
<template #default="scope">
<el-tag round type="warning" >
{{ scope.row.userTypeName }}
</el-tag>
</template>
</el-table-column>
<el-table-column show-overflow-tooltip label="详情" prop="userTypeDesc" align="center"
width="200"></el-table-column>
<el-table-column label="操作" align="center" width="220">
<template #default="scope">
<el-button size="small" type="primary" @click="handleEdit(scope.$index, scope.row)">编辑</el-button>
<el-button size="small" type="danger" @click="handleDelete(scope.$index, scope.row)">删除</el-button>
</template>
</el-table-column>
</el-table>
<!--分页 start-->
<div class="page">
<el-pagination background
layout="prev,pager,next,jumper"
:default-page-size="defaultPageSize"
:total="totalData"
@current-change="currentChangeHaddler"></el-pagination>
</div>
<!--分页 end-->
</div>
<!--表格数据展示 end-->
<!--添加对话框 start-->
<el-dialog draggable destroy-on-close v-model="dialogAddVisible" title="添加" width="50%" center>
<el-form inline :model="addFormInfo" label-width="150px">
<el-form-item label="名称">
<el-input v-model="addFormInfo.userTypeName"></el-input>
</el-form-item>
<el-form-item label="详情">
<el-input type="textarea" rows="10" style="width: 500px" v-model="addFormInfo.userTypeDesc"></el-input>
</el-form-item>
</el-form>
<template #footer>
<span class="dialog-footer">
<el-button @click="dialogAddVisible = false">取消</el-button>
<el-button type="primary" @click="sureHandler">确定</el-button>
</span>
</template>
</el-dialog>
<!--添加对话框 end-->
<!--编辑对话框 start-->
<!--destroy-on-close:每次关闭对话框时直接销毁对话框,没有缓存-->
<el-dialog
draggable
destroy-on-close
v-model="dialogEditorVisible"
title="编辑"
width="50%"
center>
<el-form inline :model="editorFormInfo" label-width="150px">
<el-form-item label="名称">
<el-input v-model="editorFormInfo.userTypeName"></el-input>
</el-form-item>
<el-form-item label="详情">
<el-input type="textarea" rows="10" style="width: 500px" v-model="editorFormInfo.userTypeDesc"></el-input>
</el-form-item>
</el-form>
<template #footer>
<span class="dialog-footer">
<el-button @click="dialogEditorVisible = false">取消</el-button>
<el-button type="primary" @click="sureEditorHandler">确定</el-button>
</span>
</template>
</el-dialog>
<!--编辑对话框 end-->
</div>
</template>
<script setup>
import axios from "../../api/index.js"
import {onMounted, reactive, ref} from "vue";
import {ElMessage} from "element-plus";
//初始化分页查询数据
const dataList = reactive({
list: []
})
//初始化总条数
const totalData = ref(0)
//当前页
const currentPage = ref(1)
//初始化分页显示条数
const defaultPageSize = ref(10)
//搜索初始化状态
const searchInfo = ref("")
//添加添加对话框控制器
const dialogAddVisible = ref(false)
//初始化添加对话框状态
const addFormInfo = reactive({
userTypeName: "",
userTypeDesc: "",
})
//编辑对话框控制器
const dialogEditorVisible = ref(false)
//初始化编辑对话框状态
const editorFormInfo = reactive({
userTypeId: '',
userTypeName: "",
userTypeDesc: "",
})
/**
* 网路请求:分页查询
* */
const http = (search, page, size) => {
axios.user_type_search({
search: search,
page: page,
size: size
}).then(res => {
if (res.data.code == 200) {
dataList.list = res.data.data.records
totalData.value = res.data.data.total
} else {
ElMessage.error(res.data.message)
}
})
}
onMounted(() => {
http(searchInfo.value, currentPage.value, defaultPageSize.value)
})
/**
* 分页
*/
const currentChangeHaddler = (nowPage) => {
http(searchInfo.value, nowPage, defaultPageSize.value)
currentPage.value = nowPage
}
/**
* 搜索按钮
*/
const searchHandle = () => {
http(searchInfo.value, currentPage.value, defaultPageSize.value)
}
/**
* 添加对话框弹出事件
*/
const addHander = () => {
dialogAddVisible.value = true
}
/**
* 添加对话框 确定事件
*/
const sureHandler = () => {
axios.user_type_add({
userTypeName: addFormInfo.userTypeName,
userTypeDesc: addFormInfo.userTypeDesc,
}).then(res => {
if (res.data.code == 200) {
dialogAddVisible.value = false
http(searchInfo.value, currentPage.value, defaultPageSize.value)
} else {
ElMessage.error(res.data.message)
}
})
}
/**
* 编辑对话框 弹出事件
* */
const handleEdit = (index, row) => {
dialogEditorVisible.value = true
axios.user_type_findById({
userTypeId: row.userTypeId
}).then(res => {
if (res.data.code == 200) {
editorFormInfo.userTypeId = res.data.data.userTypeId;
editorFormInfo.userTypeName = res.data.data.userTypeName;
editorFormInfo.userTypeDesc = res.data.data.userTypeDesc;
} else {
ElMessage.error(res.data.data.message)
}
})
}
/**
* 编辑对话框 确定事件
*/
const sureEditorHandler = () => {
axios.user_type_update({
userTypeId: editorFormInfo.userTypeId,
userTypeName: editorFormInfo.userTypeName,
userTypeDesc: editorFormInfo.userTypeDesc,
}).then(res => {
if (res.data.code == 200) {
dialogEditorVisible.value = false
http(searchInfo.value, currentPage.value, defaultPageSize.value)
} else {
ElMessage.error(res.data.message)
}
})
}
/**删除 */
const handleDelete = (index, row) => {
ElMessageBox.confirm(
'确定删除么',
'删除',
{
confirmButtonText: '确定',
cancelButtonText: '取消',
type: 'warning',
}
).then(() => {
//确认删除
axios.user_type_delete({
userTypeId: row.userTypeId
}).then(res => {
if (res.data.code == 200) {
ElMessage({
type: 'success',
message: "删除成功!!!",
})
//刷新
http(searchInfo.value, currentPage.value, defaultPageSize.value)
} else {
ElMessage({
type: 'error',
message: res.data.message,
})
}
})
}).catch(error => {
ElMessage({
type: 'info',
message: "取消删除",
})
})
}
</script>
<style scoped>
.data-container {
background: linear-gradient(left, rgb(89, 234, 233) 27%, rgb(131, 231, 218) 44%, rgb(69, 150, 216) 88%);
background: -o-linear-gradient(left, rgb(89, 234, 233) 27%, rgb(131, 231, 218) 44%, rgb(69, 150, 216) 88%);
background: -ms-linear-gradient(left, rgb(89, 234, 233) 27%, rgb(131, 231, 218) 44%, rgb(69, 150, 216) 88%);
background: -moz-linear-gradient(left, rgb(89, 234, 233) 27%, rgb(131, 231, 218) 44%, rgb(69, 150, 216) 88%);
background: -webkit-linear-gradient(left, rgb(89, 234, 233) 27%, rgb(131, 231, 218) 44%, rgb(69, 150, 216) 88%);
height: 800px;
}
.data-header {
padding: 20px;
}
.data-header .input {
width: 300px;
}
.data-table {
padding: 20px;
}
.page {
position: fixed;
right: 10px;
bottom: 10px;
}
</style>
用户
<template>
<div class="data-container">
<!--添加 start-->
<div class="data-header">
<el-button round @click="addHander" size="large" type="primary">
<el-icon>
<DocumentAdd/>
</el-icon>
<span>新增</span>
</el-button>
</div>
<!--添加 end-->
<!--表格数据展示 start-->
<div class="data-table">
<el-table :data="dataList.list" style="width: 1400px;">
<el-table-column label="头像" prop="userImg" align="center">
<template #default="scope">
<img :src="scope.row.userImg" style="height:60px"/>
</template>
</el-table-column>
<el-table-column show-overflow-tooltip label="昵称" prop="nickname" align="center"
width="120"></el-table-column>
<el-table-column label="账号" prop="username" align="center" width="140"></el-table-column>
<el-table-column label="手机号" prop="phone" align="center" width="140"></el-table-column>
<el-table-column show-overflow-tooltip label="邮箱" prop="email" align="center" width="160"></el-table-column>
<el-table-column label="性别" prop="userSex" align="center" width="60"></el-table-column>
<el-table-column label="状态" prop="userStatus" align="center">
<template #default="scope">
<el-tag round :type="scope.row.userStatus == '1' ? 'success' : 'info'">
{{ scope.row.userStatus == '1' ? '激活' : '未激活' }}
</el-tag>
</template>
</el-table-column>
<el-table-column show-overflow-tooltip label="个性签名" prop="signature" align="center"></el-table-column>
<el-table-column show-overflow-tooltip label="自我介绍" prop="userIntroduce" align="center"></el-table-column>
<el-table-column label="操作" align="center" width="300">
<template #default="scope">
<!-- 会员模块 start-->
<el-popover trigger="click" placement="top" :width="300" offset="20">
<template #reference>
<el-button @click="handTypes(scope.$index, scope.row)" size="small" round type="warning">会员</el-button>
</template>
<div style="margin: 15px">
<el-button @click="handleAddType(scope.$index, scope.row)" style="margin-right: 10px" type="primary"
size="small">添加
</el-button>
<el-select v-model="choseTypeId" size="small">
<el-option v-for="item in userTypeList.list" :key="item.userTypeId"
:label="item.userTypeName"
:value="item.userTypeId">
</el-option>
</el-select>
</div>
<div>
<el-tag style="margin: 4px"
type="warning"
v-for="(item,index) in user_userTypeList.list" :key="index"
@close="handleCloseType(scope.row,item.userTypeId)"
closable round>
{{ item.userTypeName }}
</el-tag>
</div>
</el-popover>
<!-- 会员模块 end-->
<el-button size="small" type="success" @click="handleColumn(scope.$index, scope.row)">专栏</el-button>
<el-button size="small" type="primary" @click="handleEdit(scope.$index, scope.row)">编辑</el-button>
<el-button size="small" type="primary" @click="handleStatus(scope.$index, scope.row)">状态</el-button>
<el-button size="small" type="danger" @click="handleDelete(scope.$index, scope.row)">删除</el-button>
</template>
</el-table-column>
</el-table>
<!--分页 start-->
<div class="page">
<el-pagination background
layout="prev,pager,next,jumper"
:default-page-size="defaultPageSize"
:total="totalData"
@current-change="currentChangeHaddler"></el-pagination>
</div>
<!--分页 end-->
</div>
<!--表格数据展示 end-->
<!--添加对话框 start-->
<el-dialog draggable destroy-on-close v-model="dialogAddVisible" title="添加" width="70%" center>
<el-form inline :model="addFormInfo" label-width="150px">
<el-form-item label="头像">
<el-input v-model="addFormInfo.userImg"></el-input>
</el-form-item>
<el-form-item label="昵称">
<el-input v-model="addFormInfo.nickname"></el-input>
</el-form-item>
<el-form-item label="账号">
<el-input v-model="addFormInfo.username"></el-input>
</el-form-item>
<el-form-item label="密码">
<el-input v-model="addFormInfo.password"></el-input>
</el-form-item>
<el-form-item label="手机号">
<el-input v-model="addFormInfo.phone"></el-input>
</el-form-item>
<el-form-item label="邮箱">
<el-input v-model="addFormInfo.email"></el-input>
</el-form-item>
<el-form-item label="性别">
<el-input v-model="addFormInfo.userSex"></el-input>
</el-form-item>
<el-form-item label="个性签名">
<el-input type="textarea" rows="3" style="width: 800px" v-model="addFormInfo.signature"></el-input>
</el-form-item>
<el-form-item label="自我介绍">
<el-input type="textarea" rows="6" style="width: 800px" v-model="addFormInfo.userIntroduce"></el-input>
</el-form-item>
</el-form>
<template #footer>
<span class="dialog-footer">
<el-button @click="dialogAddVisible = false">取消</el-button>
<el-button type="primary" @click="sureHandler">确定</el-button>
</span>
</template>
</el-dialog>
<!--添加对话框 end-->
<!--编辑对话框 start-->
<!--destroy-on-close:每次关闭对话框时直接销毁对话框,没有缓存-->
<el-dialog
draggable
destroy-on-close
v-model="dialogEditorVisible"
title="编辑"
width="70%"
center>
<el-form inline :model="editorFormInfo" label-width="150px">
<el-form-item label="头像">
<el-input v-model="editorFormInfo.userImg"></el-input>
</el-form-item>
<el-form-item label="昵称">
<el-input v-model="editorFormInfo.nickname"></el-input>
</el-form-item>
<el-form-item label="账号">
<el-input v-model="editorFormInfo.username"></el-input>
</el-form-item>
<el-form-item label="密码">
<el-input v-model="editorFormInfo.password"></el-input>
</el-form-item>
<el-form-item label="手机号">
<el-input v-model="editorFormInfo.phone"></el-input>
</el-form-item>
<el-form-item label="邮箱">
<el-input v-model="editorFormInfo.email"></el-input>
</el-form-item>
<el-form-item label="性别">
<el-input v-model="editorFormInfo.userSex"></el-input>
</el-form-item>
<el-form-item label="个性签名">
<el-input type="textarea" rows="3" style="width: 800px" v-model="editorFormInfo.signature"></el-input>
</el-form-item>
<el-form-item label="自我介绍">
<el-input type="textarea" rows="6" style="width: 800px" v-model="editorFormInfo.userIntroduce"></el-input>
</el-form-item>
</el-form>
<template #footer>
<span class="dialog-footer">
<el-button @click="dialogEditorVisible = false">取消</el-button>
<el-button type="primary" @click="sureEditorHandler">确定</el-button>
</span>
</template>
</el-dialog>
<!--编辑对话框 end-->
</div>
</template>
<script setup>
import axios from "@/utils/request.js"
import axios2 from "../../api/index.js"
import {onMounted, reactive, ref} from "vue";
import {ElMessage} from "element-plus";
import {useRouter} from 'vue-router'
const router = useRouter()
//初始化分页查询数据
const dataList = reactive({
list: []
})
//初始化用户类型列表
const userTypeList = reactive({list: []})
//用户的类型
const user_userTypeList= reactive({list: []})
//选择的类型id
const choseTypeId=ref(0)
//初始化总条数
const totalData = ref(0)
//当前页
const currentPage = ref(1)
//初始化分页显示条数
const defaultPageSize = ref(10)
//添加添加对话框控制器
const dialogAddVisible = ref(false)
//初始化添加对话框状态
const addFormInfo = reactive({
userImg: '',
nickname: '',
username: '',
password: '',
phone: '',
email: '',
userSex: '',
signature: '',
userIntroduce: '',
userStatus: '1',
})
//编辑对话框控制器
const dialogEditorVisible = ref(false)
//初始化编辑对话框状态
const editorFormInfo = reactive({
userId: '',
userImg: '',
nickname: '',
username: '',
password: '',
phone: '',
email: '',
userSex: '',
signature: '',
userIntroduce: '',
userStatus: '',
})
/**
* 网路请求:分页查询
* */
const http = (page, size) => {
axios.get('back/user/search', {
params: {
page: page,
size: size
}
}).then(res => {
if (res.data.code == 200) {
dataList.list = res.data.data.records
totalData.value = res.data.data.total
} else {
ElMessage.error(res.data.message)
}
})
axios2.user_type_findAll().then(res => {
userTypeList.list = res.data.data
})
}
onMounted(() => {
http(currentPage.value, defaultPageSize.value)
})
/**
* 分页
*/
const currentChangeHaddler = (nowPage) => {
http(nowPage, defaultPageSize.value)
currentPage.value = nowPage
}
//专栏
const handleColumn = (index, row) => {
router.push("/blog/column/" + row.userId)
}
/**
* 添加对话框弹出事件
*/
const addHander = () => {
dialogAddVisible.value = true
}
/**
* 添加对话框 确定事件
*/
const sureHandler = () => {
axios.post('back/user/add', {
userImg: addFormInfo.userImg,
nickname: addFormInfo.nickname,
username: addFormInfo.username,
password: addFormInfo.password,
phone: addFormInfo.phone,
email: addFormInfo.email,
userSex: addFormInfo.userSex,
signature: addFormInfo.signature,
userIntroduce: addFormInfo.userIntroduce,
userStatus: addFormInfo.userStatus,
}).then(res => {
if (res.data.code == 200) {
dialogAddVisible.value = false
http(currentPage.value, defaultPageSize.value)
} else {
ElMessage.error(res.data.message)
}
})
}
/**
* 编辑对话框 弹出事件
* */
const handleEdit = (index, row) => {
dialogEditorVisible.value = true
axios.get('back/user/findById', {
params: {
userId: row.userId
}
}).then(res => {
if (res.data.code == 200) {
editorFormInfo.userId = res.data.data.userId;
editorFormInfo.userImg = res.data.data.userImg;
editorFormInfo.nickname = res.data.data.nickname;
editorFormInfo.username = res.data.data.username;
editorFormInfo.password = res.data.data.password;
editorFormInfo.phone = res.data.data.phone;
editorFormInfo.email = res.data.data.email;
editorFormInfo.userSex = res.data.data.userSex;
editorFormInfo.signature = res.data.data.signature;
editorFormInfo.userIntroduce = res.data.data.userIntroduce;
editorFormInfo.userStatus = res.data.data.userStatus;
} else {
ElMessage.error(res.data.data.message)
}
})
}
/**
* 编辑对话框 确定事件
*/
const sureEditorHandler = () => {
axios.post('back/user/update', {
userId: editorFormInfo.userId,
userImg: editorFormInfo.userImg,
nickname: editorFormInfo.nickname,
username: editorFormInfo.username,
password: editorFormInfo.password,
phone: editorFormInfo.phone,
email: editorFormInfo.email,
userSex: editorFormInfo.userSex,
signature: editorFormInfo.signature,
userIntroduce: editorFormInfo.userIntroduce,
userStatus: editorFormInfo.userStatus,
}).then(res => {
if (res.data.code == 200) {
dialogEditorVisible.value = false
http(currentPage.value, defaultPageSize.value)
} else {
//添加失败:给出提示信息(element-plus/反馈组件/message信息提示)
ElMessage.error(res.data.message)
}
})
}
/**删除 */
const handleDelete = (index, row) => {
ElMessageBox.confirm(
'确定删除么',
'删除',
{
confirmButtonText: '确定',
cancelButtonText: '取消',
type: 'warning',
}
).then(() => {
//确认删除
axios.delete("back/user/delete", {
params: {
userId: row.userId
}
}).then(res => {
if (res.data.code == 200) {
ElMessage({
type: 'success',
message: "删除成功!!!",
})
//刷新
http(currentPage.value, defaultPageSize.value)
} else {
ElMessage({
type: 'error',
message: res.data.message,
})
}
})
}).catch(error => {
ElMessage({
type: 'info',
message: "取消删除",
})
})
}
/**
* 封装查询用户拥有的会员
*/
const searchTypes = (userId) => {
axios2.user_type_findUserTypeByUserId({
userId: userId
}).then(res => {
if (res.data.code == 200) {
user_userTypeList.list = res.data.data
}
})
}
/**
* 点击类型事件
*/
const handTypes = (index, row) => {
//查询博客拥有的标签
searchTypes(row.userId)
//查询所有标签列表
axios2.user_type_findAll().then(res => {
if (res.data.code == 200) {
userTypeList.list = res.data.data
}
})
}
/**
* 添加类型
*/
const handleAddType = (index, row) => {
axios2.user_type_addUserType({
userId: row.userId,
userTypeId: choseTypeId.value
}).then(res => {
if (res.data.code == 200) {
ElMessage.success('添加成功')
//查询用户的类型
searchTypes(row.userId)
}
})
}
/**
* 删除类型
*/
const handleCloseType = (row, userTypeId) => {
axios2.user_type_deleteUserType({
userId: row.userId,
userTypeId: userTypeId,
}).then(res => {
if (res.data.code == 200) {
ElMessage.success('删除成功')
//查询用户的类型
searchTypes(row.userId)
}
})
}
/**
* 修改用户状态
*/
const handleStatus = (index, row) => {
axios.post("back/user/updateStatus", {userId: row.userId}).then(res => {
if (res.data.code == 200) {
ElMessage.success("状态已更改")
http(currentPage.value, defaultPageSize.value)
}
})
}
</script>
<style scoped>
.data-container {
background: linear-gradient(left, rgb(89, 234, 233) 27%, rgb(131, 231, 218) 44%, rgb(69, 150, 216) 88%);
background: -o-linear-gradient(left, rgb(89, 234, 233) 27%, rgb(131, 231, 218) 44%, rgb(69, 150, 216) 88%);
background: -ms-linear-gradient(left, rgb(89, 234, 233) 27%, rgb(131, 231, 218) 44%, rgb(69, 150, 216) 88%);
background: -moz-linear-gradient(left, rgb(89, 234, 233) 27%, rgb(131, 231, 218) 44%, rgb(69, 150, 216) 88%);
background: -webkit-linear-gradient(left, rgb(89, 234, 233) 27%, rgb(131, 231, 218) 44%, rgb(69, 150, 216) 88%);
height: 800px;
}
.data-header {
padding: 20px;
}
.data-table {
padding: 20px;
}
.page {
position: fixed;
right: 10px;
bottom: 10px;
}
</style>