From 42882f7cd1e0d9cf11ca8b1fa12c354cf082ab27 Mon Sep 17 00:00:00 2001 From: huababa1 <2037205722@qq.com> Date: Thu, 3 Jul 2025 15:21:22 +0800 Subject: [PATCH] =?UTF-8?q?=E3=80=90=E6=96=B0=E5=A2=9E=E3=80=91=E5=AF=BC?= =?UTF-8?q?=E5=87=BA=E5=AD=A6=E7=94=9F=E4=BD=9C=E7=AD=94mysql=E8=AE=B0?= =?UTF-8?q?=E5=BD=95?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- .../exam/controller/auto/AutoController.java | 6 +- .../autoformysql/AutoForMysqlService.java | 6 +- .../autoformysql/AutoForMysqlServiceImpl.java | 25 +++ .../service/mysql/IMysqlLocalService.java | 2 + .../service/mysql/IMysqlLocalServiceImpl.java | 19 ++ .../exam/utils/mysql/MySQLExporterUtil.java | 198 ++++++++++++++++++ 6 files changed, 254 insertions(+), 2 deletions(-) create mode 100644 src/main/java/com/example/exam/exam/utils/mysql/MySQLExporterUtil.java diff --git a/src/main/java/com/example/exam/exam/controller/auto/AutoController.java b/src/main/java/com/example/exam/exam/controller/auto/AutoController.java index 4d88af6..3c4d421 100644 --- a/src/main/java/com/example/exam/exam/controller/auto/AutoController.java +++ b/src/main/java/com/example/exam/exam/controller/auto/AutoController.java @@ -82,7 +82,11 @@ public class AutoController { public Result judgementForMysql(@RequestBody StuInfoVo stuInfoVo) throws SQLException, IOException { return Result.success(autoForMysqlService.autoForMysql(stuInfoVo)); } - + // Mysql文件 + @PostMapping("/judgementForMysqlFile") + public Result judgementForMysqlFile(@RequestBody StuInfoVo stuInfoVo) throws SQLException, IOException { + return Result.success(autoForMysqlService.autoForMysqlFile(stuInfoVo)); + } /** * 删除 本地学生的连接和库 * @param tNames diff --git a/src/main/java/com/example/exam/exam/service/autoformysql/AutoForMysqlService.java b/src/main/java/com/example/exam/exam/service/autoformysql/AutoForMysqlService.java index e018169..7ea8160 100644 --- a/src/main/java/com/example/exam/exam/service/autoformysql/AutoForMysqlService.java +++ b/src/main/java/com/example/exam/exam/service/autoformysql/AutoForMysqlService.java @@ -11,8 +11,12 @@ import java.sql.SQLException; public interface AutoForMysqlService { /** - * 自动判题 C语言 + * 自动判题 Mysql * @param stuInfoVo 学生信息 */ Double autoForMysql(StuInfoVo stuInfoVo) throws SQLException, IOException; + + + String autoForMysqlFile(StuInfoVo stuInfoVo); + } diff --git a/src/main/java/com/example/exam/exam/service/autoformysql/AutoForMysqlServiceImpl.java b/src/main/java/com/example/exam/exam/service/autoformysql/AutoForMysqlServiceImpl.java index 54f7873..dbb8107 100644 --- a/src/main/java/com/example/exam/exam/service/autoformysql/AutoForMysqlServiceImpl.java +++ b/src/main/java/com/example/exam/exam/service/autoformysql/AutoForMysqlServiceImpl.java @@ -111,4 +111,29 @@ public class AutoForMysqlServiceImpl implements AutoForMysqlService { } return score; } + + @Override + public String autoForMysqlFile(StuInfoVo stuInfoVo) { + // 1、获取到学生文件路径 + String filePath = stuInfoVo.getFilePath(); + File folder = new File(filePath); + // 2、获取到学生文件 + File[] files = folder.listFiles(); + for (File file : files) { + File csFiles = new File(file.getPath()); + String quId = csFiles.getName(); + File[] csFileList = csFiles.listFiles(); + for (File one_file : csFileList) { + String name = one_file.getName(); + if ("程序设计".equals(name)) { + File mysql_file = new File(one_file.getPath()); + ExamQuestion examQuestion = examQuestionService.selectExamQuestionByQuId(quId); + mysqlLocalService.JudgementFile( mysql_file, examQuestion); + break; + + } + } + } + return "导出成功"; + } } diff --git a/src/main/java/com/example/exam/exam/service/mysql/IMysqlLocalService.java b/src/main/java/com/example/exam/exam/service/mysql/IMysqlLocalService.java index adfe516..b62a9ca 100644 --- a/src/main/java/com/example/exam/exam/service/mysql/IMysqlLocalService.java +++ b/src/main/java/com/example/exam/exam/service/mysql/IMysqlLocalService.java @@ -16,4 +16,6 @@ public interface IMysqlLocalService { void delMysqlConnect(List tNames); SourceAndText Judgement(double sorce, File file, ExamQuestion examQuestion, String judgementStr) throws IOException, SQLException; + void JudgementFile(File mysqlFile, ExamQuestion examQuestion); + } diff --git a/src/main/java/com/example/exam/exam/service/mysql/IMysqlLocalServiceImpl.java b/src/main/java/com/example/exam/exam/service/mysql/IMysqlLocalServiceImpl.java index 7db78d9..912aaf3 100644 --- a/src/main/java/com/example/exam/exam/service/mysql/IMysqlLocalServiceImpl.java +++ b/src/main/java/com/example/exam/exam/service/mysql/IMysqlLocalServiceImpl.java @@ -10,6 +10,7 @@ import com.example.exam.exam.service.mysql.IMysqlLocalService; import com.example.exam.exam.service.mysql.vo.MysqlBooleanVo; import com.example.exam.exam.service.mysql.vo.MysqlVo; import com.example.exam.exam.utils.HtmlAppender; +import com.example.exam.exam.utils.mysql.MySQLExporterUtil; import com.example.exam.exam.utils.zip.ZipUtil; import io.micrometer.common.util.StringUtils; import jakarta.annotation.Resource; @@ -1070,6 +1071,24 @@ public class IMysqlLocalServiceImpl implements IMysqlLocalService { sourceAndText.setText(judgementStr); return sourceAndText; } + + @Override + public void JudgementFile(File mysqlFile, ExamQuestion examQuestion) { + String stuDataName=examQuestion.getTname(); + String fileStu = mysqlFile.getAbsolutePath(); + String user = "root"; + String password = ""; +// String stuAnswerPath = "D:\\Desktop\\202504211120_mysql\\71\\MYS_010_122\\考试素材\\考试素材\\Student\\db\\db_escape.myd"; + File stuDbDir = new File(fileStu, "db"); + // 设置导出文件路径(放在dbDir下) + String exportFileName = stuDataName + ".myd"; + + File exportFile = new File(stuDbDir, exportFileName); + // 执行导出 + MySQLExporterUtil exporter = new MySQLExporterUtil(stuDataName, user, password, exportFile.getAbsolutePath()); + exporter.export(); + } + public static String convertAlertToSelectWhere(String sql) { if (sql == null || sql.trim().isEmpty()) return null; diff --git a/src/main/java/com/example/exam/exam/utils/mysql/MySQLExporterUtil.java b/src/main/java/com/example/exam/exam/utils/mysql/MySQLExporterUtil.java new file mode 100644 index 0000000..3195d7b --- /dev/null +++ b/src/main/java/com/example/exam/exam/utils/mysql/MySQLExporterUtil.java @@ -0,0 +1,198 @@ +package com.example.exam.exam.utils.mysql; + +import java.io.File; +import java.io.FileWriter; +import java.io.IOException; +import java.sql.*; +import java.util.ArrayList; +import java.util.List; + + +public class MySQLExporterUtil { + private final String databaseName; + private final String jdbcUrl; + private final String user; + private final String password; + private final String outputFilePath; + + public MySQLExporterUtil(String databaseName, String user, String password,String outputFilePath) { + this.databaseName = databaseName; + this.jdbcUrl = "jdbc:mysql://localhost:6033/" + databaseName + "?useSSL=false&serverTimezone=Asia/Shanghai"; + this.user = user; + this.password = password; + this.outputFilePath = outputFilePath; + } + + public void export() { + // 确保父目录存在 + File outputFile = new File(outputFilePath); + File parentDir = outputFile.getParentFile(); + if (parentDir != null && !parentDir.exists()) { + parentDir.mkdirs(); + } + + + + try (Connection conn = DriverManager.getConnection(jdbcUrl, user, password); + FileWriter writer = new FileWriter(outputFile)) { + // 2. 如果目标文件已存在,先删除(确保是新文件) + if (outputFile.exists()) { + // 3. 清空文件内容 + try { + // 方法一:使用FileWriter(自动清空) + new FileWriter(outputFile, false).close(); // false表示覆盖模式 + } catch (IOException e) { + throw new RuntimeException("无法清空文件内容: " + outputFilePath, e); + } + } + // 连接数据库 + switchDatabase(conn); + // 导出表结构 + exportTables(conn, writer); + // 导出视图结构 + exportViews(conn, writer); + // 导出存储过程 +// exportProcedures(conn, writer); + // 导出所有触发器 +// exportTriggers(conn,writer); + writer.write("\nSET FOREIGN_KEY_CHECKS=1;\n"); + System.out.println("导出成功!文件路径: " + outputFile); + } catch (Exception e) { + e.printStackTrace(); + } + } + + private void switchDatabase(Connection conn) throws SQLException { + try (Statement stmt = conn.createStatement()) { + stmt.execute("USE " + databaseName); + } + } + + private void exportTables(Connection conn, FileWriter writer) throws SQLException, IOException { + DatabaseMetaData meta = conn.getMetaData(); + try (ResultSet tables = meta.getTables(databaseName, null, "%", new String[]{"TABLE"})) { + while (tables.next()) { + String tableName = tables.getString("TABLE_NAME"); + + writer.write(getCreateTableSQL(conn, tableName) + ";\n\n"); + exportTableData(conn, tableName, writer); + } + } + } + + private String getCreateTableSQL(Connection conn, String tableName) throws SQLException { + try (Statement stmt = conn.createStatement(); + ResultSet rs = stmt.executeQuery("SHOW CREATE TABLE " + tableName)) { + + // 获取 CREATE TABLE 语句 + String createTableSQL = rs.next() ? rs.getString("Create Table") : ""; + +// // 移除 AUTO_INCREMENT 部分 +// createTableSQL = createTableSQL.replaceAll("AUTO_INCREMENT=\\d+", ""); +// +// // 移除 ENGINE, CHARSET 和 ROW_FORMAT 部分 +// createTableSQL = createTableSQL.replaceAll("ENGINE=[^ ]+|DEFAULT CHARSET=[^ ]+|ROW_FORMAT=[^ ]+", ""); +// +// // 清理多余的空格 +// createTableSQL = createTableSQL.trim(); + + return createTableSQL; + } + } + + /** + * 导出所有触发器 + */ + private void exportTriggers(Connection conn, FileWriter writer) throws SQLException, IOException { + + List triggers = getAllTriggers(conn); + for (String trigger : triggers) { + String ddl = getTriggerDDL(conn,trigger); + writer.write(ddl + ";\n\n"); + } + } + + private void exportTableData(Connection conn, String tableName, FileWriter writer) throws SQLException, IOException { + String query = "SELECT * FROM " + tableName; + try (Statement stmt = conn.createStatement(); + ResultSet rs = stmt.executeQuery(query)) { + ResultSetMetaData metaData = rs.getMetaData(); + int columnCount = metaData.getColumnCount(); + + while (rs.next()) { + StringBuilder sb = new StringBuilder("INSERT INTO " + tableName + " ("); + for (int i = 1; i <= columnCount; i++) { + sb.append(metaData.getColumnName(i)).append(i < columnCount ? ", " : ") VALUES ("); + } + for (int i = 1; i <= columnCount; i++) { + sb.append(rs.getString(i) == null ? "NULL" : "'" + rs.getString(i).replace("'", "''") + "'") + .append(i < columnCount ? ", " : ");\n"); + } + writer.write(sb.toString()); + } + } + } + + private void exportViews(Connection conn, FileWriter writer) throws SQLException, IOException { + DatabaseMetaData meta = conn.getMetaData(); + try (ResultSet views = meta.getTables(databaseName, null, "%", new String[]{"VIEW"})) { + while (views.next()) { + String viewName = views.getString("TABLE_NAME"); + + writer.write(getCreateViewSQL(conn, viewName) + ";\n\n"); + } + } + } + + private String getCreateViewSQL(Connection conn, String viewName) throws SQLException { + try (Statement stmt = conn.createStatement(); + ResultSet rs = stmt.executeQuery("SHOW CREATE VIEW " + viewName)) { + return rs.next() ? rs.getString("Create View") : ""; + } + } + + private void exportProcedures(Connection conn, FileWriter writer) throws SQLException, IOException { + DatabaseMetaData meta = conn.getMetaData(); + try (ResultSet procedures = meta.getProcedures(databaseName, null, "%")) { + while (procedures.next()) { + String procedureName = procedures.getString("PROCEDURE_NAME"); + writer.write(getCreateProcedureSQL(conn, procedureName) + ";\n\n"); + } + } + } + + private String getCreateProcedureSQL(Connection conn, String procedureName) throws SQLException { + try (Statement stmt = conn.createStatement(); + ResultSet rs = stmt.executeQuery("SHOW CREATE PROCEDURE " + procedureName)) { + if (rs.next()) { + return rs.getString("Create Procedure"); + } + return ""; + } + } + /** + * 获取触发器的DDL语句 + */ + private String getTriggerDDL(Connection conn,String triggerName) throws SQLException { + try (Statement stmt = conn.createStatement(); + ResultSet rs = stmt.executeQuery("SHOW CREATE TRIGGER `" + triggerName + "`")) { + if (rs.next()) { + return rs.getString(3); // 创建语句在第3列 + } + } + return ""; + } + /** + * 获取所有触发器 + */ + private List getAllTriggers(Connection conn) throws SQLException { + List triggers = new ArrayList<>(); + try (Statement stmt = conn.createStatement(); + ResultSet rs = stmt.executeQuery("SHOW TRIGGERS FROM " + databaseName)) { + while (rs.next()) { + triggers.add(rs.getString("Trigger")); + } + } + return triggers; + } +}