Use EasyExcel para leer datos de Excel locales e importarlos a la base de datos mysql

Este artículo solo registra la lectura (read) de EasyExcel

1. ¿Qué hace EasyExcel?

Primero vea la explicación de EasyExcel:
EasyExcel es un marco de procesamiento de Excel de código abierto de Alibaba. Es un proyecto de código abierto simple que ahorra memoria para leer y escribir Excel basado en Java. La razón principal por la que EasyExcel puede reducir en gran medida el uso de la memoria es que no carga todos los datos del archivo en la memoria al mismo tiempo al analizar Excel, sino que lee los datos línea por línea del disco y los analiza uno por uno.

Dirección de fuente abierta:
dirección de github: https://github.com/alibaba/easyexcel
(todavía estoy un poco confundido con solo mirar el código, busqué videos relacionados en la estación Xiaopo y un video de Crazy God lo explicó claramente) Casi directamente Solo haz lo que dijo, por supuesto, debes hacer los cambios apropiados de acuerdo con tu situación real).

2. Antecedentes del proyecto

Un pequeño proyecto que hice necesita importar los datos de la tabla de Excel a la base de datos, pero algunas columnas de datos también contienen muchos objetos de matriz [{...},{...},{...},{...}], y aquí El contenido es para almacenarse en la base de datos como campos uno por uno, porque el trabajo manual o Excel no es realista. Así que fui a entender el uso de este marco.

Excel es el siguiente:

Nota: Excel no tiene encabezados, porque comienza a leer directamente desde la columna de parámetros correspondiente a la clase de entidad.

3. Proceso de uso específico

1. Se debe agregar la configuración pom.xml:

		 <dependency>
            <groupId>com.alibaba</groupId>
            <artifactId>easyexcel</artifactId>
            <version>2.2.6</version>
        </dependency>
        <!-- https://mvnrepository.com/artifact/com.alibaba/fastjson -->
        <dependency>
            <groupId>com.alibaba</groupId>
            <artifactId>fastjson</artifactId>
            <version>1.2.75</version>
        </dependency>

2. Hay tres pasos en el código:

  1. Crear el objeto de entidad clase Dao correspondiente a excel;
  2. Oyente de escritura: el valor predeterminado es leer Excel línea por línea, por lo que debe crear un oyente de devolución de llamada para Excel línea por línea.El oyente realiza principalmente lectura y almacenamiento;
  3. Llame al oyente: configure la ubicación de Excel, llame al oyente para leer la tabla y luego guárdelo en la base de datos

Paso 1: Crear la clase de entidad correspondiente a excel


inserte la descripción de la imagen aquí
pd: use la anotación @ExcelProperty para ilustrar la clase de entidad correspondiente a la columna correspondiente de Excel
"datos de prueba de resistencia" (debe explicarse aquí, reemplacé los 4 nombres de parámetros con los nombres correspondientes en inglés en Excel en ese momento)
inserte la descripción de la imagen aquí
Si desea La estructura de la tabla almacenada en la base de datos es diferente de la clase de entidad correspondiente a Excel (por ejemplo, si una lectura de campo es una estructura de objeto de matriz como los "datos de prueba de resistencia" en Excel en la figura anterior, entonces necesita para ser procesado y dividido en múltiples campos se puede almacenar en la base de datos por separado), entonces es necesario crear una clase adicional correspondiente a la tabla de la base de datos (ligeramente) para recibir todos los datos y almacenarlos en la base de datos.

Tablas creadas por la base de datos:inserte la descripción de la imagen aquí

Paso 2: Escriba el oyente

Implementación del oyente

/**
 * Date:2021/10/20
 * Description: excel一行一行的回调监听器
 *
 * @author ivyhu
 */
@Component
public class DemoDataListener extends AnalysisEventListener<ExcelModel> {
    
    

    @Resource
    ChargingStationMapper charingStationResistanceReportMapper;
    @Resource
    CharingStationServiceImpl charingStationServiceImpl;

    private static final Logger LOGGER = LoggerFactory.getLogger(DemoDataListener.class);

    /**
     * 有参构造
     * 如果使用了spring,请使用这个构造方法。每次创建Listener的时候需要把spring管理的类传进来
     * @param serviceImpl
     */
    public DemoDataListener(CharingStationServiceImpl serviceImpl) {
    
    
        this.charingStationServiceImpl = serviceImpl;
    }
    //无参构造
    public DemoDataListener() {
    
    
    }
    /**
     * 读取数据或执行这个invoke()方法
     * @param excelModel 类型
     * @param context    分析器
     */
    @Override
    public void invoke(ExcelModel excelModel, AnalysisContext context) {
    
    
        LOGGER.info("解析到一条数据:{}", JSON.toJSONString(excelModel));
        //最终要保存到数据库的数据
        ChargingStationModel reportModelData = new ChargingStationModel();

        String productModelNum = "";
        String itemNo = "";
        Double groundResistance = 0.0;
        Double insulationResistance = 0.0;
        Byte type = 0;
        Integer singlePilePower = 0;
        /**
         * 获取excel表中充电设施产品信息
         */
        String str1 = excelModel.getInfoData();
        JSONArray array1 = JSON.parseArray(str1);
        //如果不为空,就解析[{},{},{},{}]类型的数组对象并获取值
        if (!ObjectUtils.isEmpty(array1)) {
    
    
            for (Object obj : array1) {
    
    
                JSONObject jsonObject = (JSONObject) obj;
                ChargingStationInfoDataExcelModel infoExcelModel = JSONObject.parseObject(String.valueOf((JSONObject) obj), ChargingStationInfoDataExcelModel.class);
                type = infoExcelModel.getType();
                singlePilePower = infoExcelModel.getSinglePilePower();
            }
        }
        /**
         * 获取excel表中电阻测试数据
         */
        String str = excelModel.getResistanceData();
        JSONArray array = JSON.parseArray(str);
        //电阻测试数据不为空,就解析[{},{},{},{}]类型的数组对象并获取值
        if (!ObjectUtils.isEmpty(array)) {
    
    
            for (Object obj : array) {
    
    
                JSONObject jsonObject = (JSONObject) obj;
                ChargingStationResistanceDataExcelModel reportModel = JSONObject.parseObject(String.valueOf((JSONObject) obj), ChargingStationResistanceDataExcelModel.class);
                productModelNum = reportModel.getProductModelNum();
                itemNo = reportModel.getItemNo();
                groundResistance = reportModel.getGroundResistance();
                insulationResistance = reportModel.getInsulationResistance();
                //插入数据到数据库
                reportModelData = new ChargingStationModel(excelModel.getReportNo(), excelModel.getModelNum(), productModelNum, itemNo, groundResistance, insulationResistance, type, singlePilePower,
                        excelModel.getOutputVoltageControlErrorOfCharger(), excelModel.getOutputCurrentControlErrorOfCharger(), excelModel.getActiveStopChargeTestOutputCurrentStopRate(), excelModel.getPassiveStopChargeTestOutputCurrentStopRate(),
                        excelModel.getChargerOutputCurrentAdjustmentTimeAbove20A(), excelModel.getChargerOutputCurrentAdjustmentTimeUnder20A(), excelModel.getImpulseCurrent());
                saveData(reportModelData);
            }
        }
    }

    /**
     * 所有数据解析完成了 都会来调用
     *
     * @param context
     */
    @Override
    public void doAfterAllAnalysed(AnalysisContext context) {
    
    

        // 这里也要保存数据,确保最后遗留的数据也存储到数据库
        /*saveData();*/
        LOGGER.info("所有数据解析完成!");
    }

    /**
     * 加上存储数据库
     */
    private void saveData(ChargingStationModel resistanceReportModel) {
    
    
        //调用mapper插入数据库
        charingStationServiceImpl.save(resistanceReportModel);
    }


}

Paso 3: llamar al oyente para leer datos
1. Capa de controlador

@RestController
@Controller
@RequestMapping("/product/charging_station")
public class ChargingStationController {
    
    

    @Resource
    CharingStationService charingStationService;
    /**
     * 提取excel表格数据的接口
     */
    @PostMapping()
    public void saveExcel(){
    
    
        charingStationService.saveData();
    	}
    }

2. Capa de servicio

@Service
public class CharingStationServiceImpl implements CharingStationService {
    
    

    @Resource
    ChargingStationMapper chargingStationMapper;
    @Resource
    ExcelUtil excelUtil;
    @Resource
    ChargingStationAcceptanceValueMapper chargingStationAcceptanceValueMapper;

    /**
     * 调用读取excel数据的方法
     */
    @Override
    public void saveData() {
    
    
        excelUtil.excelRead();
    }

3. Entrada de escucha
Establezca la dirección del archivo, el nombre del archivo y la clase de entidad correspondiente a Excel

@Component
public class ExcelUtil {
    
    

    @Autowired
    private CharingStationServiceImpl charingStationServiceImpl;
    /**
     * 最简单的读
     * 1. 创建excel对应的实体对象 ExcelModel
     * 2. 由于默认一行行的读取excel,所以需要创建excel一行一行的回调监听器,参照{@link DemoDataListener}
     * 3. 直接读即可
     */
    private static final Logger LOGGER = LoggerFactory.getLogger(ExcelUtil.class);
    
    //文件位置
    String PATH = "D:\\excelTest\\";


    public void excelRead() {
    
    

        // 有个很重要的点 DemoDataListener 不能被spring管理,要每次读取excel都要new,然后里面用到spring可以构造方法传进去
        String fileName = PATH + "充电桩验收测试数据.xlsx";
        // 这里 需要指定读用哪个class去读,然后读取第一个sheet 文件流会自动关闭
        EasyExcel.read(fileName, ExcelModel.class, new DemoDataListener(charingStationServiceImpl)).sheet().doRead();

    }
}

Puntos de conocimiento en este artículo:

  1. Convierta Json, analice el objeto de matriz de tipo [{},{},{},{}] para obtener un solo contenido dentro
JSONObject jsonObject = (JSONObject) obj;
ChargingStationResistanceDataExcelModel reportModel = JSONObject.parseObject(String.valueOf((JSONObject) obj);
  1. Use la anotación @Component para entregar las entradas de DemoDataListener y listener a Spring para administrar
@Component
public class DemoDataListener extends AnalysisEventListener<ExcelModel> {
    
    
...
}
  1. Configurar la ubicación del archivo para ser leído
//文件位置
    String PATH = "D:\\excelTest\\";

    public void excelRead() {
    
    

        // 有个很重要的点 DemoDataListener 不能被spring管理,要每次读取excel都要new,然后里面用到spring可以构造方法传进去
        String fileName = PATH + "充电桩验收测试数据.xlsx";

        // 这里 需要指定读用哪个class去读,然后读取第一个sheet 文件流会自动关闭
        EasyExcel.read(fileName, ExcelModel.class, new DemoDataListener(charingStationServiceImpl)).sheet().doRead();

    }

pd: se informaron algunos errores al comienzo de la operación:

  1. El asignador informa un puntero nulo. Dos posibilidades, verifiqué y descubrí que una se debe a que DemoDataListener y la clase de entrada del oyente no se inyectan en Spring, por lo que no se puede encontrar el bean y se debe usar @Component. La segunda es que no se pasa la llamada del modelo de Spring mvc, pero se aplica la prueba unitaria @Test en el marco de código abierto para ejecutar.
  2. No se pudo leer el archivo porque no se eliminó la columna del encabezado.

Este artículo es solo un pequeño registro del pequeño novato, si hay un error, ¡corríjame!

Supongo que te gusta

Origin blog.csdn.net/Ivy_Xinxxx/article/details/121036543
Recomendado
Clasificación