package com.ruoyi.airline.service.impl; import com.alibaba.fastjson.JSONObject; import com.ruoyi.airline.api.domain.AirLinePointVO; import com.ruoyi.airline.domain.api.IAirlineFileDomain; import com.ruoyi.airline.domain.model.AirlineFile; import com.ruoyi.airline.domain.model.kml.KmlInfo; import com.ruoyi.airline.domain.uitl.KmlFileUtils; import com.ruoyi.airline.domain.uitl.WayPointUitls; import com.ruoyi.airline.service.api.IAirlineFileService; import com.ruoyi.airline.service.convert.AirlineFileServiceConvert; import com.ruoyi.airline.service.dto.AirlineFileDTO; import com.ruoyi.common.core.exception.base.BaseException; import com.ruoyi.file.service.ISysFileService; import org.apache.commons.compress.archivers.ArchiveEntry; import org.apache.commons.compress.archivers.ArchiveInputStream; import org.apache.commons.compress.archivers.zip.ZipArchiveInputStream; import org.slf4j.Logger; import org.slf4j.LoggerFactory; import org.springframework.beans.factory.annotation.Autowired; import org.springframework.stereotype.Service; import org.springframework.web.multipart.MultipartFile; import java.io.ByteArrayInputStream; import java.io.ByteArrayOutputStream; import java.io.IOException; import java.util.List; import java.util.Objects; import java.util.Optional; import java.util.UUID; /** * 航线文件Service实现类 * * @author ruoyi * @date 2026-01-17 */ @Service public class AirlineFileServiceImpl implements IAirlineFileService { private static final Logger log = LoggerFactory.getLogger(AirlineFileServiceImpl.class); // // @Autowired // private ISysFileService iSysFileService; @Autowired private IAirlineFileDomain iAirlineFileDomain; @Override public AirlineFileDTO save(AirlineFileDTO dto) { AirlineFile model = AirlineFileServiceConvert.toModel(dto); AirlineFile result = iAirlineFileDomain.save(model); return AirlineFileServiceConvert.toDTO(result); } /** * 上传航线文件,如果是KMZ的需要转换成 waypoint 的,并且需要将 原始航线文件保存。 * 并且限制航线修改,因为暂时没做到 从waypoingt 转 KMZ * * @param file * @return */ @Override public AirlineFileDTO parseAndUplload(MultipartFile file) { KmlInfo kmlInfo = new KmlInfo(); try (ArchiveInputStream archiveInputStream = new ZipArchiveInputStream(file.getInputStream()); ByteArrayOutputStream out = new ByteArrayOutputStream()) { ArchiveEntry entry; while (!Objects.isNull(entry = archiveInputStream.getNextEntry())) { String name = entry.getName(); if (name.toLowerCase().endsWith(".kml")) { // 解KML文件 kmlInfo = KmlFileUtils.parseKml(archiveInputStream); } } if (Objects.isNull(kmlInfo)) { throw new BaseException("kmz文件内容缺失"); } String globalHeight = kmlInfo.getDocument().getFolder().getGlobalHeight(); out.write(WayPointUitls.kmz2waypoint(kmlInfo)); String fileUrl = ""; //TODO String fileUrl = iSysFileService.uploadFileByStream(UUID.randomUUID().toString(), "waypoints", out); AirlineFileDTO dto = new AirlineFileDTO(); dto.setFileUrl(fileUrl); dto.setAirVendor(""); dto.setAirType(""); // 原始文件 目录存储 // dto.setFileUrl(fileUrl); return dto; } catch (IOException e) { throw new BaseException("Waypoints文件生成失败"); } catch (Exception e) { log.error("kmz航线转换失败", e); throw new BaseException("kmz航线转换失败"); } } /** * 航点编辑,直接将大疆KMZ转换成waypoints操作,就不需要区分大疆还是拓恒了 * * @param airlineFile 航线文件dto * @return */ @Override public AirlineFileDTO createOrupdate(AirlineFileDTO airlineFile) { StringBuilder waypointBuilder = new StringBuilder("QGC WPL 110\n"); List LineDto = airlineFile.getLinePointDtoList(); // 新建字节输出流,Freemarker操作此输出流写入生成的业务文件. try (ByteArrayOutputStream out = new ByteArrayOutputStream();) { if (LineDto != null && !LineDto.isEmpty()) { for (int i = 0; i < LineDto.size(); i++) { AirLinePointVO point = LineDto.get(i); waypointBuilder.append(WayPointUitls.formatWaypointLine(point, i)).append("\n"); } // 生成文件 out.write(waypointBuilder.toString().getBytes()); ByteArrayInputStream in = new ByteArrayInputStream(out.toByteArray()); // 上传文件 String fileUrl = ""; //TODO String fileUrl = iSysFileService.uploadFileByStream(UUID.randomUUID().toString(), "waypoints", out); out.close(); in.close(); //保存航线文件数据 airlineFile.setFileUrl(fileUrl); airlineFile.setSource("airport"); airlineFile.setStatus(airlineFile.getStatus() == null ? 1 : airlineFile.getStatus()); AirlineFile model = AirlineFileServiceConvert.toModel(airlineFile); AirlineFile result = iAirlineFileDomain.save(model); return AirlineFileServiceConvert.toDTO(result); } return null; } catch (Exception e) { throw new RuntimeException(e); } } }