mirror of https://github.com/elunez/eladmin
修复运维管理的一些bug
parent
d32216d513
commit
fac8e2f51e
2
LICENSE
2
LICENSE
|
@ -176,7 +176,7 @@ recommend that a file or class name and description of purpose be included on
|
||||||
the same "printed page" as the copyright notice for easier identification within
|
the same "printed page" as the copyright notice for easier identification within
|
||||||
third-party archives.
|
third-party archives.
|
||||||
|
|
||||||
Copyright 2018 Elune
|
Copyright 2018 Zheng Jie
|
||||||
|
|
||||||
Licensed under the Apache License, Version 2.0 (the "License");
|
Licensed under the Apache License, Version 2.0 (the "License");
|
||||||
you may not use this file except in compliance with the License.
|
you may not use this file except in compliance with the License.
|
||||||
|
|
|
@ -97,7 +97,7 @@ public class DatabaseController {
|
||||||
public ResponseEntity<Object> upload(@RequestBody MultipartFile file, HttpServletRequest request)throws Exception{
|
public ResponseEntity<Object> upload(@RequestBody MultipartFile file, HttpServletRequest request)throws Exception{
|
||||||
String id = request.getParameter("id");
|
String id = request.getParameter("id");
|
||||||
DatabaseDto database = databaseService.findById(id);
|
DatabaseDto database = databaseService.findById(id);
|
||||||
String fileName = "";
|
String fileName;
|
||||||
if(database != null){
|
if(database != null){
|
||||||
fileName = file.getOriginalFilename();
|
fileName = file.getOriginalFilename();
|
||||||
File executeFile = new File(fileSavePath+fileName);
|
File executeFile = new File(fileSavePath+fileName);
|
||||||
|
|
|
@ -15,9 +15,12 @@ public class DeployHistoryQueryCriteria{
|
||||||
/**
|
/**
|
||||||
* 精确
|
* 精确
|
||||||
*/
|
*/
|
||||||
@Query(blurry = "appName,ip,deployUser,deployId")
|
@Query(blurry = "appName,ip,deployUser")
|
||||||
private String blurry;
|
private String blurry;
|
||||||
|
|
||||||
|
@Query
|
||||||
|
private Long deployId;
|
||||||
|
|
||||||
@Query(type = Query.Type.BETWEEN)
|
@Query(type = Query.Type.BETWEEN)
|
||||||
private List<Timestamp> deployDate;
|
private List<Timestamp> deployDate;
|
||||||
}
|
}
|
||||||
|
|
|
@ -1,5 +1,6 @@
|
||||||
package me.zhengjie.modules.mnt.service.impl;
|
package me.zhengjie.modules.mnt.service.impl;
|
||||||
|
|
||||||
|
import me.zhengjie.exception.BadRequestException;
|
||||||
import me.zhengjie.modules.mnt.domain.App;
|
import me.zhengjie.modules.mnt.domain.App;
|
||||||
import me.zhengjie.modules.mnt.repository.AppRepository;
|
import me.zhengjie.modules.mnt.repository.AppRepository;
|
||||||
import me.zhengjie.modules.mnt.service.AppService;
|
import me.zhengjie.modules.mnt.service.AppService;
|
||||||
|
@ -57,18 +58,34 @@ public class AppServiceImpl implements AppService {
|
||||||
@Override
|
@Override
|
||||||
@Transactional(rollbackFor = Exception.class)
|
@Transactional(rollbackFor = Exception.class)
|
||||||
public AppDto create(App resources) {
|
public AppDto create(App resources) {
|
||||||
|
verification(resources);
|
||||||
return appMapper.toDto(appRepository.save(resources));
|
return appMapper.toDto(appRepository.save(resources));
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
@Transactional(rollbackFor = Exception.class)
|
@Transactional(rollbackFor = Exception.class)
|
||||||
public void update(App resources) {
|
public void update(App resources) {
|
||||||
|
verification(resources);
|
||||||
App app = appRepository.findById(resources.getId()).orElseGet(App::new);
|
App app = appRepository.findById(resources.getId()).orElseGet(App::new);
|
||||||
ValidationUtil.isNull(app.getId(),"App","id",resources.getId());
|
ValidationUtil.isNull(app.getId(),"App","id",resources.getId());
|
||||||
app.copy(resources);
|
app.copy(resources);
|
||||||
appRepository.save(app);
|
appRepository.save(app);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
private void verification(App resources){
|
||||||
|
String opt = "/opt";
|
||||||
|
String home = "/home";
|
||||||
|
if (!(resources.getUploadPath().startsWith(opt) || resources.getUploadPath().startsWith(home))) {
|
||||||
|
throw new BadRequestException("文件只能上传在opt目录或者home目录 ");
|
||||||
|
}
|
||||||
|
if (!(resources.getDeployPath().startsWith(opt) || resources.getDeployPath().startsWith(home))) {
|
||||||
|
throw new BadRequestException("文件只能部署在opt目录或者home目录 ");
|
||||||
|
}
|
||||||
|
if (!(resources.getBackupPath().startsWith(opt) || resources.getBackupPath().startsWith(home))) {
|
||||||
|
throw new BadRequestException("文件只能备份在opt目录或者home目录 ");
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
@Transactional(rollbackFor = Exception.class)
|
@Transactional(rollbackFor = Exception.class)
|
||||||
public void delete(Set<Long> ids) {
|
public void delete(Set<Long> ids) {
|
||||||
|
|
|
@ -130,13 +130,15 @@ public class DeployServiceImpl implements DeployService {
|
||||||
//判断是否第一次部署
|
//判断是否第一次部署
|
||||||
boolean flag = checkFile(executeShellUtil, app);
|
boolean flag = checkFile(executeShellUtil, app);
|
||||||
//第一步要确认服务器上有这个目录
|
//第一步要确认服务器上有这个目录
|
||||||
executeShellUtil.execute("mkdir -p " + uploadPath);
|
executeShellUtil.execute("mkdir -p " + app.getUploadPath());
|
||||||
|
executeShellUtil.execute("mkdir -p " + app.getBackupPath());
|
||||||
|
executeShellUtil.execute("mkdir -p " + app.getDeployPath());
|
||||||
//上传文件
|
//上传文件
|
||||||
msg = String.format("登陆到服务器:%s", ip);
|
msg = String.format("登陆到服务器:%s", ip);
|
||||||
ScpClientUtil scpClientUtil = getScpClientUtil(ip);
|
ScpClientUtil scpClientUtil = getScpClientUtil(ip);
|
||||||
log.info(msg);
|
log.info(msg);
|
||||||
sendMsg(msg, MsgType.INFO);
|
sendMsg(msg, MsgType.INFO);
|
||||||
msg = String.format("上传文件到服务器:%s<br>目录:%s下", ip, uploadPath);
|
msg = String.format("上传文件到服务器:%s<br>目录:%s下,请稍等...", ip, uploadPath);
|
||||||
sendMsg(msg, MsgType.INFO);
|
sendMsg(msg, MsgType.INFO);
|
||||||
scpClientUtil.putFile(fileSavePath, uploadPath);
|
scpClientUtil.putFile(fileSavePath, uploadPath);
|
||||||
if (flag) {
|
if (flag) {
|
||||||
|
@ -151,13 +153,19 @@ public class DeployServiceImpl implements DeployService {
|
||||||
//部署文件,并启动应用
|
//部署文件,并启动应用
|
||||||
String deployScript = app.getDeployScript();
|
String deployScript = app.getDeployScript();
|
||||||
executeShellUtil.execute(deployScript);
|
executeShellUtil.execute(deployScript);
|
||||||
|
sleep(3);
|
||||||
sendMsg("启动应用", MsgType.INFO);
|
sendMsg("应用部署中,请耐心等待部署结果,或者稍后手动查看部署状态", MsgType.INFO);
|
||||||
String startScript = app.getStartScript();
|
int i = 0;
|
||||||
executeShellUtil.execute(startScript);
|
boolean result = false;
|
||||||
//只有过5秒才能知道到底是不是启动成功了。
|
// 由于启动应用需要时间,所以需要循环获取状态,如果超过30次,则认为是启动失败
|
||||||
sleep(5);
|
while (i++ < 30){
|
||||||
boolean result = checkIsRunningStatus(port, executeShellUtil);
|
result = checkIsRunningStatus(port, executeShellUtil);
|
||||||
|
if(result){
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
// 休眠6秒
|
||||||
|
sleep(6);
|
||||||
|
}
|
||||||
sb.append("服务器:").append(deployDTO.getName()).append("<br>应用:").append(app.getName());
|
sb.append("服务器:").append(deployDTO.getName()).append("<br>应用:").append(app.getName());
|
||||||
sendResultMsg(result, sb);
|
sendResultMsg(result, sb);
|
||||||
executeShellUtil.close();
|
executeShellUtil.close();
|
||||||
|
@ -253,7 +261,7 @@ public class DeployServiceImpl implements DeployService {
|
||||||
|
|
||||||
private boolean checkFile(ExecuteShellUtil executeShellUtil, AppDto appDTO) {
|
private boolean checkFile(ExecuteShellUtil executeShellUtil, AppDto appDTO) {
|
||||||
String result = executeShellUtil.executeForResult("find " + appDTO.getDeployPath() + " -name " + appDTO.getName());
|
String result = executeShellUtil.executeForResult("find " + appDTO.getDeployPath() + " -name " + appDTO.getName());
|
||||||
return result.indexOf("/tcp:")>0;
|
return result.indexOf(appDTO.getName())>0;
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
@ -273,9 +281,19 @@ public class DeployServiceImpl implements DeployService {
|
||||||
sb.append("服务器:").append(deploy.getName()).append("<br>应用:").append(app.getName());
|
sb.append("服务器:").append(deploy.getName()).append("<br>应用:").append(app.getName());
|
||||||
sendMsg("下发启动命令", MsgType.INFO);
|
sendMsg("下发启动命令", MsgType.INFO);
|
||||||
executeShellUtil.execute(app.getStartScript());
|
executeShellUtil.execute(app.getStartScript());
|
||||||
//停止3秒,防止应用没有启动完成
|
|
||||||
sleep(3);
|
sleep(3);
|
||||||
boolean result = checkIsRunningStatus(app.getPort(), executeShellUtil);
|
sendMsg("应用启动中,请耐心等待启动结果,或者稍后手动查看运行状态", MsgType.INFO);
|
||||||
|
int i = 0;
|
||||||
|
boolean result = false;
|
||||||
|
// 由于启动应用需要时间,所以需要循环获取状态,如果超过30次,则认为是启动失败
|
||||||
|
while (i++ < 30){
|
||||||
|
result = checkIsRunningStatus(app.getPort(), executeShellUtil);
|
||||||
|
if(result){
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
// 休眠6秒
|
||||||
|
sleep(6);
|
||||||
|
}
|
||||||
sendResultMsg(result, sb);
|
sendResultMsg(result, sb);
|
||||||
log.info(sb.toString());
|
log.info(sb.toString());
|
||||||
executeShellUtil.close();
|
executeShellUtil.close();
|
||||||
|
@ -343,21 +361,24 @@ public class DeployServiceImpl implements DeployService {
|
||||||
stopApp(app.getPort(), executeShellUtil);
|
stopApp(app.getPort(), executeShellUtil);
|
||||||
//删除原来应用
|
//删除原来应用
|
||||||
sendMsg("删除应用", MsgType.INFO);
|
sendMsg("删除应用", MsgType.INFO);
|
||||||
//考虑到系统安全性,必须限制下操作目录
|
|
||||||
String path = "/opt";
|
|
||||||
if (!deployPath.startsWith(path)) {
|
|
||||||
throw new BadRequestException("部署路径必须在opt目录下:" + deployPath);
|
|
||||||
}
|
|
||||||
executeShellUtil.execute("rm -rf " + deployPath + FILE_SEPARATOR + resources.getAppName());
|
executeShellUtil.execute("rm -rf " + deployPath + FILE_SEPARATOR + resources.getAppName());
|
||||||
|
|
||||||
//还原应用
|
//还原应用
|
||||||
sendMsg("还原应用", MsgType.INFO);
|
sendMsg("还原应用", MsgType.INFO);
|
||||||
executeShellUtil.execute("cp -r " + backupPath + "/. " + deployPath);
|
executeShellUtil.execute("cp -r " + backupPath + "/. " + deployPath);
|
||||||
sendMsg("启动应用", MsgType.INFO);
|
sendMsg("启动应用", MsgType.INFO);
|
||||||
executeShellUtil.execute(app.getStartScript());
|
executeShellUtil.execute(app.getStartScript());
|
||||||
//只有过5秒才能知道到底是不是启动成功了。
|
sendMsg("应用启动中,请耐心等待启动结果,或者稍后手动查看启动状态", MsgType.INFO);
|
||||||
sleep(5);
|
int i = 0;
|
||||||
boolean result = checkIsRunningStatus(app.getPort(), executeShellUtil);
|
boolean result = false;
|
||||||
|
// 由于启动应用需要时间,所以需要循环获取状态,如果超过30次,则认为是启动失败
|
||||||
|
while (i++ < 30){
|
||||||
|
result = checkIsRunningStatus(app.getPort(), executeShellUtil);
|
||||||
|
if(result){
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
// 休眠6秒
|
||||||
|
sleep(6);
|
||||||
|
}
|
||||||
StringBuilder sb = new StringBuilder();
|
StringBuilder sb = new StringBuilder();
|
||||||
sb.append("服务器:").append(ip).append("<br>应用:").append(resources.getAppName());
|
sb.append("服务器:").append(ip).append("<br>应用:").append(resources.getAppName());
|
||||||
sendResultMsg(result, sb);
|
sendResultMsg(result, sb);
|
||||||
|
|
|
@ -155,7 +155,7 @@ public class SqlUtils {
|
||||||
public static String executeFile(String jdbcUrl, String userName, String password, File sqlFile) {
|
public static String executeFile(String jdbcUrl, String userName, String password, File sqlFile) {
|
||||||
Connection connection = getConnection(jdbcUrl, userName, password);
|
Connection connection = getConnection(jdbcUrl, userName, password);
|
||||||
try {
|
try {
|
||||||
batchExecute(connection, readSqlList( sqlFile));
|
batchExecute(connection, readSqlList(sqlFile));
|
||||||
} catch (Exception e) {
|
} catch (Exception e) {
|
||||||
log.error("sql脚本执行发生异常:{}",e.getMessage());
|
log.error("sql脚本执行发生异常:{}",e.getMessage());
|
||||||
return e.getMessage();
|
return e.getMessage();
|
||||||
|
|
Loading…
Reference in New Issue