遍历3个不同的JDBC结果集

时间:2019-06-17 20:17:45

标签: java resultset opencsv zipoutputstream

我正在尝试将3个不同表中的3个CSV文件压缩到单个zip文件your_files_12354627.zip中。

因此,我采用以下方法,该方法对于其中包含1个csv文件的zip文件生成效果很好。我正在尝试对多个文件执行此操作,因此我修改了以下代码(如下工作代码所示):

下面的工作代码:

public void sendMessage(String msg) throws DaoException {

    DataSource ds = null;
    Connection conn = null;
    PreparedStatement pstmt = null;
    PreparedStatement pstmtEmployee = null;
    PreparedStatement pstmtCompany = null; 
    PreparedStatement pstmBuilding = null; 

    ResultSet rs = null;
    ResultSet resultSetFirst = null;
    ResultSet resultSetSecond = null;
    ResultSet resultSetThird = null;


     String[] parts = msg.split("#");
     String requestID = parts[0].trim();
     String userName = parts[1].trim();
     String applicationName = parts[2].trim();




    try {

        ds = jdbcTemplate.getDataSource();
        conn = ds.getConnection();  

        pstmtEmployee = conn.prepareStatement(getPatientEmployeeSQL);
        pstmtEmployee.setString(1, requestID);
        resultSetFirst = pstmtEmployee.executeQuery();

        pstmtCompany = conn.prepareStatement(getCompanySQL);
        pstmtCompany.setString(1, requestID);
        resultSetSecond = pstmtCompany.executeQuery();

        pstmtBuilding = conn.prepareStatement(getBuildingSQL);
        pstmtBuilding.setString(1, requestID);
        resultSetThird = pstmtBuilding.executeQuery();




        Path dir = Paths.get("/srv/custom_users", userName);
        Files.createDirectories(dir);

        OutputStream fos = Files.newOutputStream(dir.resolve("your_files_"+ unixTimestamp +".zip"));
        BufferedOutputStream bos = new BufferedOutputStream(fos);
        ZipOutputStream zos = new ZipOutputStream(bos); 

        Path employeeFile = dir.resolve("employee_custom_file_" + unixTimestamp + ".csv");
        Path companyFile = dir.resolve("company_custom_file_" + unixTimestamp + ".csv");
        Path buildingFile = dir.resolve("building_custom_file_" + unixTimestamp + ".csv");


        ZipEntry firstEntry = new ZipEntry(employeeFile.getFileName().toString());
        zos.putNextEntry(firstEntry);
        try (CSVWriter writer = new CSVWriter(new OutputStreamWriter(zos,StandardCharsets.UTF_8)))) {
               writer.writeAll(resultSetFirst, true);
               writer.flush();
               zos.closeEntry();
        }

        /*ZipEntry secondEntry = new ZipEntry(companyFile.getFileName().toString());
        zos.putNextEntry(secondEntry);
        try (CSVWriter writer = new CSVWriter(new OutputStreamWriter(zos,StandardCharsets.UTF_8)))) {
               writer.writeAll(resultSetSecond, true);
               writer.flush();
               zos.closeEntry();
        }

        ZipEntry thirdEntry = new ZipEntry(buildingFile.getFileName().toString());
        zos.putNextEntry(thirdEntry);
        try (CSVWriter writer = new CSVWriter(new OutputStreamWriter(zos,StandardCharsets.UTF_8)))) {
               writer.writeAll(resultSetThird, true);
               writer.flush();
               zos.closeEntry();
        }*/




        zos.close();

        }
        catch(Throwable th) {
            throw new DaoException(th.getMessage(), th);
        }
        finally {
            //resource Closing statements

        }   



}

以下修改的代码:

我应该如何遍历3个不同的结果集,以便分别使用writer.writeAll(resultSetFirst, true);writer.writeAll(resultSetSecond, true);writer.writeAll(resultSetThird, true);?我试图遍历下面代码中所示的文件名,但是不确定如何在for循环内处理不同的结果集,如下所示。我已经在试图找出此循环问题的位置发表了评论。

public void sendMessage(String msg) throws DaoException {

    DataSource ds = null;
    Connection conn = null;
    PreparedStatement pstmt = null;
    PreparedStatement pstmtEmployee = null;
    PreparedStatement pstmtCompany = null; 
    PreparedStatement pstmBuilding = null; 

    ResultSet rs = null;
    ResultSet resultSetFirst = null;
    ResultSet resultSetSecond = null;
    ResultSet resultSetThird = null;


     String[] parts = msg.split("#");
     String requestID = parts[0].trim();
     String userName = parts[1].trim();
     String applicationName = parts[2].trim();




    try {

        ds = jdbcTemplate.getDataSource();
        conn = ds.getConnection();  

        pstmtEmployee = conn.prepareStatement(getPatientEmployeeSQL);
        pstmtEmployee.setString(1, requestID);
        resultSetFirst = pstmtEmployee.executeQuery();

        pstmtCompany = conn.prepareStatement(getCompanySQL);
        pstmtCompany.setString(1, requestID);
        resultSetSecond = pstmtCompany.executeQuery();

        pstmtBuilding = conn.prepareStatement(getBuildingSQL);
        pstmtBuilding.setString(1, requestID);
        resultSetThird = pstmtBuilding.executeQuery();




        Path dir = Paths.get("/srv/custom_users", userName);
        Files.createDirectories(dir);

        OutputStream fos = Files.newOutputStream(dir.resolve("your_files_"+ unixTimestamp +".zip"));
        BufferedOutputStream bos = new BufferedOutputStream(fos);
        ZipOutputStream zos = new ZipOutputStream(bos); 

        Path employeeFile = dir.resolve("employee_custom_file_" + unixTimestamp + ".csv");
        Path companyFile = dir.resolve("company_custom_file_" + unixTimestamp + ".csv");
        Path buildingFile = dir.resolve("building_custom_file_" + unixTimestamp + ".csv");


        List<String> csvFileNames = new ArrayList<String>();
             csvFileNames.add(employeeFile.getFileName().toString());
             csvFileNames.add(companyFile.getFileName().toString());
             csvFileNames.add(buildingFile.getFileName().toString());


        for (String entries : csvFileNames) {

                 ZipEntry entry = new ZipEntry(entries);
                 zos.putNextEntry(entry);

                 CSVWriter writer = new CSVWriter(new OutputStreamWriter(zos,StandardCharsets.UTF_8));
                 //How should I loop through different resultsets here so that I can make use of writer.writeAll(resultSetFirst, true);
                 // writer.writeAll(resultSetSecond, true); and writer.writeAll(resultSetThird, true); respectively?


                System.out.println("Printing entries");
                System.out.println(entries); 

             }   



        /*ZipEntry firstEntry = new ZipEntry(employeeFile.getFileName().toString());
        zos.putNextEntry(firstEntry);
        try (CSVWriter writer = new CSVWriter(new OutputStreamWriter(zos,StandardCharsets.UTF_8)))) {
               writer.writeAll(resultSetFirst, true);
               writer.flush();
               zos.closeEntry();
        }*/

        /*ZipEntry secondEntry = new ZipEntry(companyFile.getFileName().toString());
        zos.putNextEntry(secondEntry);
        try (CSVWriter writer = new CSVWriter(new OutputStreamWriter(zos,StandardCharsets.UTF_8)))) {
               writer.writeAll(resultSetSecond, true);
               writer.flush();
               zos.closeEntry();
        }

        ZipEntry thirdEntry = new ZipEntry(buildingFile.getFileName().toString());
        zos.putNextEntry(thirdEntry);
        try (CSVWriter writer = new CSVWriter(new OutputStreamWriter(zos,StandardCharsets.UTF_8)))) {
               writer.writeAll(resultSetThird, true);
               writer.flush();
               zos.closeEntry();
        }*/




        zos.close();

        }
        catch(Throwable th) {
            throw new DaoException(th.getMessage(), th);
        }
        finally {
            //resource Closing statements

        }   



}

1 个答案:

答案 0 :(得分:2)

首先,我建议您将代码分解为几种不同的方法。这里有很多重复。

对于您是要为每个文件编写一个ResultSet还是为每个文件编写三个ResultSet,我有些困惑。其中一部分是文件filefileFactsfileEncounters,在其他任何地方都没有提及。

如果要在每个条目中放置一个ResultSet,则可以使用Map将File映射到ResultSet,然后遍历Entries或Key。像......

....
  Map<String,ResultSet> dataMap = new HashMap<>();
  dataMap.put(file.getFileName().toString(),resultSetFirst);
  dataMap.put(filefacts.getFileName().toString(),resultSetSecond);
  dataMap.put(fileEncounters.getFileName().toString(),resultSetThird);

  for (Map.Entry<String,ResultSet> e : dataMap.entrySet()){
    zos.putNextEntry(new ZipEntry(e.getKey()));
    try (CSVWriter writer = new CSVWriter(new OutputStreamWriter(zos,StandardCharsets.UTF_8))){
      writer.writeAll(e.getValue(), true);
      writer.flush();
      zos.closeEntry();
    }
  }
....

但是使用一种方法可能会更容易,更清晰...

....
  makeEntry(zos,file.getFileName().toString(),resultSetFirst);
  makeEntry(zos,filefacts.getFileName().toString(),resultSetSecond);
  makeEntry(zos,fileEncounters.getFileName().toString(),resultSetThird);
....
}

private static void makeEntry(ZipOutputStream zos,String name, ResultSet res) throws SomeExceptions{
    zos.putNextEntry(new ZipEntry(name));
    try (CSVWriter writer = new CSVWriter(new OutputStreamWriter(zos,StandardCharsets.UTF_8))){
      writer.writeAll(res, true);
      writer.flush();
      zos.closeEntry();
  }
}

通过这种方法,您不必创建和填充地图(或列表)即可运行3次相同的代码。

如果您决定迭代地图以使内容更清晰/更干净,则可以/应该仍然使用一种方法:

  Map<String,ResultSet> dataMap = new HashMap<>();
  dataMap.put(file.getFileName().toString(),resultSetFirst);
  dataMap.put(filefacts.getFileName().toString(),resultSetSecond);
  dataMap.put(fileEncounters.getFileName().toString(),resultSetThird);

  for (Map.Entry<String,ResultSet> e : dataMap.entrySet()){
    makeEntry(zos, e.getKey(), e.getValue());
  }
...

寻找这样的其他领域来重构方法。一个不错的规则是,每当您认为应该剪切和粘贴代码时,就考虑创建一个方法。

请注意,实际上这些代码都没有被编译或运行