package com.ruoyi.airline.service.impl; 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.domain.R; import com.ruoyi.common.core.exception.base.BaseException; import com.ruoyi.system.api.RemoteFileService; 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.IOException; import java.util.List; import java.util.Objects; 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 RemoteFileService remoteFileService; @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());) { 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(); R fileUrl = remoteFileService.uploadFileByData(UUID.randomUUID().toString(), "waypoints", WayPointUitls.kmz2waypoint(kmlInfo)); AirlineFileDTO dto = new AirlineFileDTO(); dto.setFileUrl(fileUrl.getData()); dto.setAirVendor(""); dto.setAirType(""); 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操作此输出流写入生成的业务文件. 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"); } // 上传文件 R fileUrl = remoteFileService.uploadFileByData(UUID.randomUUID().toString(), "waypoints", waypointBuilder.toString()); //保存航线文件数据 airlineFile.setFileUrl(fileUrl.getData()); 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; } }