最近在用java写一个备份数据库的服务:
代码如下:
// 备份命令
StringBuilder cmd = new StringBuilder().append("mysqldump ")
.append("--no-tablespaces ")
.append("-h").append(ip)
.append(" -u").append(userName)
.append(" -p").append(password)
// 排除MySQL备份表
.append(" --ignore-table ").append(database_name).append(".mysql_backups ")
.append(database_name)
.append(" > ").append(absoultePath);
// 判断文件是否保存成功
if (!FileUtil.exists(filePath)) {
FileUtils.forceMkdir(new File(filePath));
throw new RuntimeException("备份失败,文件保存异常,请查看文件内容后重新尝试!");
}
// 获取操作系统名称
String osName = System.getProperty("os.name").toLowerCase();
String[] command = new String[0];
if (Constants.isSystem(osName)) {
// Windows
command = new String[]{"cmd", "/c", String.valueOf(cmd)};
} else {
// Linux
command = new String[]{"/bin/sh", "-c", String.valueOf(cmd)};
}
log.info("数据库备份命令为:{}", cmd);
// 获取Runtime实例
Process process = null;
try {
//有可能发生执行命令的时候发生错误,参考这个文章:https://www.cnblogs.com/A121/p/17806596.html
//主要是mysql8默认的密码插件是aching_sha2_password,而我们默认的是mysql_native_password,所以可能会存在问题
//如果发现执行错误的话,就检查下这个问题
process = Runtime.getRuntime().exec(command);
if (process.waitFor() == 0) {
log.info("Mysql 数据库备份成功,备份文件名:{}", mysqlFileName);
}else{
log.error("执行命令行错误,脚本运行不成功,请检查。");
}
} catch (Exception e) {
e.printStackTrace();
}
执行到
process = Runtime.getRuntime().exec(command);
process变量会显示not exited,死活不成功,后面排查发现在容器执行mysqldump -h -p -u这个命令导出整库的时候会发现这个错误:
错误提示:The server requested authentication method unknown to the client [caching_sha2_password]
让我想起来数据库我使用的是mysql8,所以按照这个文章进行修改:
mysql> use mysql;
mysql> select host,user,select_priv,plugin from user;
+---------------+------------------+-------------+-----------------------+
| host | user | select_priv | plugin |
+---------------+------------------+-------------+-----------------------+
| % | root | N | caching_sha2_password |
| localhost | mysql.infoschema | Y | caching_sha2_password |
| localhost | mysql.session | N | caching_sha2_password |
| localhost | mysql.sys | N | caching_sha2_password |
| localhost | robot | Y | caching_sha2_password |
+---------------+------------------+-------------+-----------------------+
7 rows in set (0.00 sec)
mysql> alter user 'root'@'%' identified with mysql_native_password by '123456';
Query OK, 0 rows affected (0.04 sec)
mysql> flush privileges;
Query OK, 0 rows affected (0.02 sec)
再执行上面的代码就可以了,大家一定要注意这个mysql8默认的密码登录模式引起的代码问题。
All comments