JPA操作Mysql数据库导入导出csv
项目中需要数据库检索出的数据导出到csv文件和csv文件导入数据库的功能。
String字符串读写csv文件
(1)不使用javacsv.jar进行csv导入导出String的操作,参考Java CSV操作(导出和导入)
(2)使用javacsv.jar进行csv导入导出操作,参考java读写CSV文件的两种
这里我用的是第一种方法,代码如下。
public class CSVUtil<T> {
/**
* 导出
*
* @param file csv文件(路径+文件名),csv文件不存在会自动创建
* @param dataList 数据
* @return
*/
public static boolean exportCsv(File file, List<String> dataList) {
boolean isSucess = false;
FileOutputStream out = null;
OutputStreamWriter osw = null;
BufferedWriter bw = null;
try {
out = new FileOutputStream(file);
osw = new OutputStreamWriter(out);
bw = new BufferedWriter(osw);
if (dataList != null && !dataList.isEmpty()) {
for (String data : dataList) {
bw.append(data).append("\r");
}
}
isSucess = true;
} catch (Exception e) {
isSucess = false;
} finally {
if (bw != null) {
try {
bw.close();
bw = null;
} catch (IOException e) {
e.printStackTrace();
}
}
if (osw != null) {
try {
osw.close();
osw = null;
} catch (IOException e) {
e.printStackTrace();
}
}
if (out != null) {
try {
out.close();
out = null;
} catch (IOException e) {
e.printStackTrace();
}
}
}
return isSucess;
}
/**
* 导入
*
* @param file csv文件(路径+文件)
* @return
*/
public static List<String> importCsv(File file) {
List<String> dataList = new ArrayList<String>();
BufferedReader br = null;
try {
br = new BufferedReader(new FileReader(file));
String line = "";
while ((line = br.readLine()) != null) {
dataList.add(line);
}
} catch (Exception e) {
} finally {
if (br != null) {
try {
br.close();
br = null;
} catch (IOException e) {
e.printStackTrace();
}
}
}
return dataList;
}
/**
* @param file csv文件
* @param dataList 需导出到csv的JPA数据库查询结果,csv第一行写入的是类的属性
* @return
*/
public boolean tableExportCSV(File file, List<T> dataList) {
try {
if (dataList != null) {
FieldValueTUtil<T> fieldValueTUtil = new FieldValueTUtil<>();
T t = dataList.get(0);
StringBuilder sbName = new StringBuilder();
String[] fieldNames = null;
fieldNames = fieldValueTUtil.getFiledName(t);
for (int i = 0; i < fieldNames.length; i++) {
sbName.append(fieldNames[i]);
if (i != fieldNames.length - 1) {
sbName.append(",");
}
}
List<String> csvString = new ArrayList<>();
csvString.add(sbName.toString());
for (T tData : dataList) {
StringBuilder sbValue = new StringBuilder();
for (int i = 0; i < fieldNames.length; i++) {
String name = fieldNames[i];
Object value = fieldValueTUtil.getFieldValueByName(name, tData);
sbValue.append(value);
if (i != fieldNames.length - 1) {
sbValue.append(",");
}
}
csvString.add(sbValue.toString());
}
CSVUtil.exportCsv(file, csvString);
return true;
} else {
System.out.println("datalist is null!");
return false;
}
} catch (Exception e) {
e.printStackTrace();
System.out.println("error end!");
return false;
}
}
/**
*
* @param obj csv导入对应的类的一个实例
* @param file csv文件
* @return Object实例列表
*/
public List<Object> csvImportObjects(Object obj, File file){
List<String> csvRows = CSVUtil.importCsv(file);
List<Object> tList = new ArrayList<>();
String className = obj.getClass().getName(); //获取参数1:obj的类型名
List<String> fieldsName = Arrays.asList(csvRows.get(0).split(",")); //csv文件中第一行存储的是实例的属性名
for(int i = 1; i < csvRows.size(); i++){
List<String> values = Arrays.asList(csvRows.get(i).split(","));
//这里把values重写一遍。
// 原因:使用 Arrays.asList(arr) 转换的 List 并不能进行 add 和 remove,
// 操作Arrays.asList(arr) 返回的类型是 Aarrays$ArrayList 并不是 ArrayList,
//Aarrays$ArrayList 和 ArrayList 都继承 AbstractList,
// 但是 AbstractList 中的 add 方法和 remove 方法都是直接抛出 UnsupportedOperationException,并没有直接实现。
values = new ArrayList<String>(values);
try{
//这里必须在for循环里新建一个obj.getClass()类型的新实例,
// 若实例建在for循环外,因为定义的List<Object> tList参数Object是引用类型,
// 在tList.add()时,添加的将会是同一个值
Object object = (Object) Class.forName(className).newInstance();
object = ObjUtil.setObjectValue(object, values);
tList.add(object);
}catch (Exception e){
e.printStackTrace();
}
System.out.println();
}
System.out.println();
return tList;
}
}
exportCsv()和importCsv()方法是参考第一种方法实现的String到csv的导入导出操作。
public boolean tableExportCSV(File file, List dataList)是调用exportCsv()实现了JPA查询结果导出到csv的方法。
public List csvImportObjects(Object obj, File file)是调用了importCsv()实现了csv导入到相应类实例列表的方法。
其中的FieldValueTUtil类是获取类实例的属性和属性值的工具类。参考java获取对象属性名称、属性值
其中的ObjUtil类是通过java反射机制读写类的所有属性类型、值的工具类。参考通过java反射机制读写类的所有属性类型、值
测试代码如下:
@RunWith(SpringRunner.class)
@SpringBootTest
public class MyApplicationTest {
@Autowired
private MyClassRepository myClassRep;
@Test
public void tableDataExportCSV(){
List<MyClass> dataList = myClassRep.findAllById(0);
CSVUtil<MyClass> csvUtil = new CSVUtil<>();
boolean exportResult = csvUtil.tableExportCSV(new File("D:\\testData\\testCSV.csv"), dataList);
System.out.print(exportResult);
}
@Test
public void csvImportMyClass(){
CSVUtil<MyClass> csvUtil = new CSVUtil<>();
MyClass mc = new MyClass();
List<Object> list = csvUtil.csvImportObjects(mc, new File("D:\\testData\\testCsv.csv"));
for (Object cg : list){
myClassRep.save((MyClass) cg);
}
System.out.println();
}
}
JPA查询接口如下:
public interface MyClassRepository extends JpaRepository<MyClass, int>{
public List<MyClass> findAllById(int id);
}