目录
1.代码生成器
1.依赖
<!-- 代码生成器 -->
<dependency>
<groupId>com.baomidou</groupId>
<artifactId>mybatis-plus-generator</artifactId>
<version>3.5.1</version>
</dependency>
<dependency>
<groupId>org.apache.velocity</groupId>
<artifactId>velocity</artifactId>
<version>1.7</version>
</dependency>
2.CodeGenerator.java
package com.example.demo.util;
import com.baomidou.mybatisplus.generator.FastAutoGenerator;
import com.baomidou.mybatisplus.generator.config.OutputFile;
import java.util.Collections;
/**
* mp代码生成器
* by 青哥哥
* @since 2022-01-26
*/
public class CodeGenerator {
public static void main(String[] args) {
generate();
}
private static void generate() {
FastAutoGenerator.create("jdbc:mysql://localhost:3306/ping?serverTimezone=GMT%2b8", "root", "123456")
.globalConfig(builder -> {
builder.author("") // 设置作者
//.enableSwagger() // 开启 swagger 模式
.fileOverride() // 覆盖已生成文件
.outputDir("D:\\java\\qingge\\src\\main\\java"); // 指定输出目录
})
.packageConfig(builder -> {
builder.parent("com.example.demo") // 设置父包名
.moduleName(null) // 设置父包模块名
.pathInfo(Collections.singletonMap(OutputFile.mapperXml, "D:\\java\\qingge\\src\\main\\resources\\mapper")); // 设置mapperXml生成路径
})
.strategyConfig(builder -> {
builder.entityBuilder().enableLombok();
// builder.mapperBuilder().enableMapperAnnotation().build();
builder.controllerBuilder().enableHyphenStyle() // 开启驼峰转连字符
.enableRestStyle(); // 开启生成@RestController 控制器
builder.addInclude("sys_user") // 设置需要生成的表名
.addTablePrefix("t_", "sys_"); // 设置过滤表前缀
})
// .templateEngine(new FreemarkerTemplateEngine()) // 使用Freemarker引擎模板,默认的是Velocity引擎模板
.execute();
}
}
3.controller.java.vm
package ${package.Controller};
import com.baomidou.mybatisplus.extension.plugins.pagination.Page;
import org.springframework.web.bind.annotation.*;
import javax.annotation.Resource;
import java.util.List;
import com.baomidou.mybatisplus.core.conditions.query.QueryWrapper;
import ${package.Service}.${table.serviceName};
import ${package.Entity}.${entity};
#if(${restControllerStyle})
import org.springframework.web.bind.annotation.RestController;
#else
import org.springframework.stereotype.Controller;
#end
#if(${superControllerClassPackage})
import ${superControllerClassPackage};
#end
/**
* <p>
* $!{table.comment} 前端控制器
* </p>
*
* @author ${author}
* @since ${date}
*/
#if(${restControllerStyle})
@RestController
#else
@Controller
#end
@RequestMapping("#if(${package.ModuleName})/${package.ModuleName}#end/#if(${controllerMappingHyphenStyle})${controllerMappingHyphen}#else${table.entityPath}#end")
#if(${kotlin})
class ${table.controllerName}#if(${superControllerClass}) : ${superControllerClass}()#end
#else
#if(${superControllerClass})
public class ${table.controllerName} extends ${superControllerClass} {
#else
public class ${table.controllerName} {
#end
@Resource
private ${table.serviceName} ${table.entityPath}Service;
// 新增或者更新
@PostMapping
public boolean save(@RequestBody ${entity} ${table.entityPath}) {
return ${table.entityPath}Service.saveOrUpdate(${table.entityPath});
}
@DeleteMapping("/{id}")
public Boolean delete(@PathVariable Integer id) {
return ${table.entityPath}Service.removeById(id);
}
@PostMapping("/del/batch")
public boolean deleteBatch(@RequestBody List<Integer> ids) {
return ${table.entityPath}Service.removeByIds(ids);
}
@GetMapping
public List<${entity}> findAll() {
return ${table.entityPath}Service.list();
}
@GetMapping("/{id}")
public ${entity} findOne(@PathVariable Integer id) {
return ${table.entityPath}Service.getById(id);
}
@GetMapping("/page")
public Page<${entity}> findPage(@RequestParam Integer pageNum,
@RequestParam Integer pageSize) {
QueryWrapper<User> queryWrapper = new QueryWrapper<>();
queryWrapper.orderByDesc("id");
return ${table.entityPath}Service.page(new Page<>(pageNum, pageSize), queryWrapper);
}
}
#end
4.swagger依赖
<!--swagger-->
<dependency>
<groupId>io.springfox</groupId>
<artifactId>springfox-boot-starter</artifactId>
<version>3.0.0</version>
</dependency>
2.Excel导入和导出
1.依赖
<dependency>
<groupId>cn.hutool</groupId>
<artifactId>hutool-all</artifactId>
<version>5.7.20</version>
</dependency>
<dependency>
<groupId>org.apache.poi</groupId>
<artifactId>poi-ooxml</artifactId>
<version>4.1.2</version>
</dependency>
2.代码
导入时要将Excel的字段名换成英文名与实体类对应,注意 id 和createTime 应该排除。在导入时弹幕有说使用 .addHeaderAlias("用户名" , "username" )。还有一种方法是在实体类的属性上的加上@Alias但是这种方法导出的时候会出现问题。
/**
* excel 导入
* @param file
* @throws Exception
*/
@PostMapping("/import")
public Boolean imp(MultipartFile file) throws Exception {
InputStream inputStream = file.getInputStream();
// 方式1:(推荐) 通过 javabean的方式读取Excel内的对象,但是要求表头必须是英文,跟javabean的属性要对应起来
ExcelReader reader = ExcelUtil.getReader(inputStream);
reader.addHeaderAlias("用户名", "username");
reader.addHeaderAlias("密码", "password");
reader.addHeaderAlias("昵称", "nickname");
reader.addHeaderAlias("邮箱", "email");
reader.addHeaderAlias("电话", "phone");
reader.addHeaderAlias("地址", "address");
reader.addHeaderAlias("创建时间", "createTime");
reader.addHeaderAlias("头像", "avatarUrl");
List<User> list = reader.readAll(User.class);
// 方式2:忽略表头的中文,直接读取表的内容
// List<List<Object>> list = reader.read(1);
// List<User> users = CollUtil.newArrayList();
// for (List<Object> row : list) {
// User user = new User();
// user.setUsername(row.get(0).toString());
// user.setPassword(row.get(1).toString());
// user.setNickname(row.get(2).toString());
// user.setEmail(row.get(3).toString());
// user.setPhone(row.get(4).toString());
// user.setAddress(row.get(5).toString());
// user.setAvatarUrl(row.get(6).toString());
// users.add(user);
// }
//
userService.saveBatch(list);
return true;
}
/**
* 导出接口
*/
@GetMapping("/export")
public void export(HttpServletResponse response) throws Exception {
// 从数据库查询出所有的数据
List<User> list = userService.list();
// 通过工具类创建writer 写出到磁盘路径
// ExcelWriter writer = ExcelUtil.getWriter(filesUploadPath + "/用户信息.xlsx");
// 在内存操作,写出到浏览器
ExcelWriter writer = ExcelUtil.getWriter(true);
//自定义标题别名
writer.addHeaderAlias("username", "用户名");
writer.addHeaderAlias("password", "密码");
writer.addHeaderAlias("nickname", "昵称");
writer.addHeaderAlias("email", "邮箱");
writer.addHeaderAlias("phone", "电话");
writer.addHeaderAlias("address", "地址");
writer.addHeaderAlias("createTime", "创建时间");
writer.addHeaderAlias("avatarUrl", "头像");
// 一次性写出list内的对象到excel,使用默认样式,强制输出标题
writer.write(list, true);
// 设置浏览器响应的格式
response.setContentType("application/vnd.openxmlformats-officedocument.spreadsheetml.sheet;charset=utf-8");
String fileName = URLEncoder.encode("用户信息", "UTF-8");
response.setHeader("Content-Disposition", "attachment;filename=" + fileName + ".xlsx");
ServletOutputStream out = response.getOutputStream();
writer.flush(out, true);
out.close();
writer.close();
}
3.JWT
1.依赖
<!-- JWT -->
<dependency>
<groupId>com.auth0</groupId>
<artifactId>java-jwt</artifactId>
<version>3.10.3</version>
</dependency>
2.TokenUtils.java工具类
import cn.hutool.core.date.DateUtil;
import cn.hutool.core.util.StrUtil;
import com.auth0.jwt.JWT;
import com.auth0.jwt.algorithms.Algorithm;
import com.example.demo.entity.User;
import com.example.demo.service.IUserService;
import org.springframework.stereotype.Component;
import org.springframework.web.context.request.RequestContextHolder;
import org.springframework.web.context.request.ServletRequestAttributes;
import javax.annotation.PostConstruct;
import javax.annotation.Resource;
import javax.servlet.http.HttpServletRequest;
import java.util.Date;
@Component
public class TokenUtils {
private static IUserService staticUserService;
@Resource
private IUserService userService;
@PostConstruct
public void setUserService() {
staticUserService = userService;
}
/**
* 生成token
*
* @return
*/
public static String genToken(String userId, String sign) {
return JWT.create().withAudience(userId) // 将 user id 保存到 token 里面,作为载荷
.withExpiresAt(DateUtil.offsetHour(new Date(), 2)) // 2小时后token过期
.sign(Algorithm.HMAC256(sign)); // 以 password 作为 token 的密钥
}
/**
* 获取当前登录的用户信息
*
* @return user对象
*/
public static User getCurrentUser() {
try {
HttpServletRequest request = ((ServletRequestAttributes) RequestContextHolder.getRequestAttributes()).getRequest();
String token = request.getHeader("token");
if (StrUtil.isNotBlank(token)) {
String userId = JWT.decode(token).getAudience().get(0);
return staticUserService.getById(Integer.valueOf(userId));
}
} catch (Exception e) {
return null;
}
return null;
}
}
3.JwtInterceptor.java拦截器
import cn.hutool.core.util.StrUtil;
import com.auth0.jwt.JWT;
import com.auth0.jwt.JWTVerifier;
import com.auth0.jwt.algorithms.Algorithm;
import com.auth0.jwt.exceptions.JWTDecodeException;
import com.auth0.jwt.exceptions.JWTVerificationException;
import com.example.demo.common.Constants;
import com.example.demo.common.CustomException;
import com.example.demo.entity.User;
import com.example.demo.service.IUserService;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.web.method.HandlerMethod;
import org.springframework.web.servlet.HandlerInterceptor;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
public class JwtInterceptor implements HandlerInterceptor {
@Autowired
private IUserService userService;
@Override
public boolean preHandle(HttpServletRequest request, HttpServletResponse response, Object handler) {
String token = request.getHeader("token");
// 如果不是映射到方法直接通过
if(!(handler instanceof HandlerMethod)){
return true;
}
// 执行认证
if (StrUtil.isBlank(token)) {
throw new CustomException(Constants.CODE_401, "无token,请重新登录");
}
// 获取 token 中的 user id
String userId;
try {
userId = JWT.decode(token).getAudience().get(0);
} catch (JWTDecodeException j) {
throw new CustomException(Constants.CODE_401, "token验证失败,请重新登录");
}
// 根据token中的userid查询数据库
User user = userService.getById(userId);
if (user == null) {
throw new CustomException(Constants.CODE_401, "用户不存在,请重新登录");
}
// 用户密码加签验证 token
JWTVerifier jwtVerifier = JWT.require(Algorithm.HMAC256(user.getUsername())).build();
try {
// 验证token
jwtVerifier.verify(token);
} catch (JWTVerificationException e) {
throw new CustomException(Constants.CODE_401, "token验证失败,请重新登录");
}
return true;
}
}
4.拦截器配置
import com.example.demo.config.interceptor.JwtInterceptor;
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;
import org.springframework.web.servlet.config.annotation.InterceptorRegistry;
import org.springframework.web.servlet.config.annotation.WebMvcConfigurer;
@Configuration
public class InterceptorConfig implements WebMvcConfigurer {
@Override
public void addInterceptors(InterceptorRegistry registry) {
registry.addInterceptor(jwtInterceptor())
// 拦截所有请求,通过判断token是否合法来决定是否需要登录
.addPathPatterns("/**")
.excludePathPatterns("/user/login", "/user/register", "/**/export", "/**/import");
}
@Bean
public JwtInterceptor jwtInterceptor() {
return new JwtInterceptor();
}
}
4.部署
1.chmod 777 +Jar包 //授权
2.nohup java -jar +包名 +& //后台运行
3.nohup.out 日志
4.cat nohup.out //查看日志命令
tailf nohup.out //查看日志命令
5.ps -ef | grep java //查看Java是否启动
6.kill 9 进程号 //关闭
7.tar -zxvf 压缩包名 // 解压
8.rm -rf 文件 // 删除 (危险命令)
安装nginx
1.yum -y install gcc-c++ zlib-devel openssl-devel libtool //安装需要的插件
2.wget http://nginx.org/download/nginx-1.14.0.tar.gz //wget +地址 下载nginx
3.tar -zxvf nginx-1.14.0.tar.gz // 解压
4.cd nginx-1.14.0
5./configure --prefix=/usr/local/nginx //配置nginx
6.make && make install //安装nginx
7.cd conf //进入nginx的conf 配置vue反向代理
8.vim nginx.conf // 进入nginx的conf 配置vue反向代理
9.配置80端口
location / {
root /home/user/server/dist; //vue包的位置
index index.html index.htm;
try_ files $uri $uri/ /index.html;
}
5.用正则去除文章里的标签
// <p>段落替换为换行
content = content.replaceAll("<p .*?>", "\r\n");
//<br><br/>替换为换行
content = content.replaceAll("<br\\s*/?>", "\r\n");
// 去掉其它的<>之间的东西
content = content.replaceAll("\\<.*?>", "");
5.Redis
依赖
<!-- Redis -->
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-data-redis</artifactId>
</dependency>
时间处理
@JsonFormat(pattern = "yyyy-MM-dd", timezone = "GMT+8")
@DateTimeFormat(pattern = "yyyy-MM-dd")
设置MySQL读未提交
set SESSION TRANSACTION ISOLATION LEVEL read UNCOMMITTED;
Excl生成sql语句的函数
=CONCATENATE("insert into sys_file_type (code,name , is_template , is_must , provider ,receiver)values("&A1&",'"&B1&"','" &C1&"','" &D1& "','" &E1& "','" &F1&"');")
minio批量下载
/**
* @description: 批量下载
* @date: 2022/8/17 16:50
* @param: filenames: 多个文件名称
* @Param: zip: 压缩包名称
* @Param: res: 响应对象
* @return: void
**/
public void batchDownload(List<String> filenames, String zip, HttpServletResponse res, HttpServletRequest req){
String tenantCode = "1";
if($.isEmpty(tenantCode)){
//tenantCode = tenantDefaultCode;
throw new MarsException(UserExceptionEnum.TENANT_NOT_EXIST.getMessage());
}
String beanName = DictConstant.FILE_CONFIG_KEY+tenantCode;
try{
MinioTemplate minio = FileTemplateManager.getMinio(beanName);
BufferedOutputStream bos = null;
bos = new BufferedOutputStream(res.getOutputStream());
ZipOutputStream out = new ZipOutputStream(bos);
for (int i = 0; i < filenames.size(); i++) {
InputStream object = minio.download(filenames.get(i));
byte buf[] = new byte[1024];
int length = 0;
res.setCharacterEncoding("utf-8");
res.setContentType("application/force-download");// 设置强制下载不打开
res.setHeader("Access-Control-Expose-Headers", "Content-Disposition");
res.setHeader("Content-Disposition", "attachment;filename=" + filenameEncoding(zip,req) + ".zip");
out.putNextEntry(new ZipEntry(filenames.get(i)));
while ((length = object.read(buf)) > 0) {
out.write(buf, 0, length);
}
}
out.close();
bos.close();
}catch (Exception e){
throw new MarsException(e.getMessage());
}
}
计算时间加减
SimpleDateFormat df = new SimpleDateFormat("yyyy-MM-dd");
//取今天日期,如果日期类型为String类型,可以使用df.parse()方法,转换为Date类型
Date date = new Date();
Calendar calendar = Calendar.getInstance();//new一个Calendar类,把Date放进去
calendar.setTime(date);
calendar.add(Calendar.DATE, 1);//实现日期加一操作,也就是明天
//控制台打印的日期为明天日期,2019-06-11
System.out.println("明天的日期为:" + df.format(calendar.getTime()));
//此时的日期为明天的日期,要实现昨天,日期应该减二
calendar.add(Calendar.DATE, -2);
System.out.println("昨天的日期为:" + df.format(calendar.getTime()));