package com.fdkankan.download.service.impl; import cn.hutool.core.io.FileUtil; import cn.hutool.core.io.file.FileReader; import cn.hutool.core.io.file.FileWriter; import cn.hutool.core.thread.ThreadUtil; import cn.hutool.core.util.StrUtil; import cn.hutool.http.HttpUtil; import cn.hutool.system.oshi.OshiUtil; import com.alibaba.fastjson.JSON; import com.alibaba.fastjson.JSONObject; import com.fdkankan.common.constant.SceneVersionType; import com.fdkankan.common.exception.BusinessException; import com.fdkankan.common.util.CmdUtils; import com.fdkankan.common.util.DateExtUtil; import com.fdkankan.download.bean.ImageTypeDetail; import com.fdkankan.download.bean.LaserResultData; import com.fdkankan.download.bean.ResultData; import com.fdkankan.download.callback.ErrorCallback; import com.fdkankan.download.callback.SuccessCallback; import com.fdkankan.download.callback.SuccessLaserCallback; import com.fdkankan.download.entity.DTO.OfflineDTO; import com.fdkankan.download.httpclient.HttpClient; import com.fdkankan.download.service.IDownloadService; import com.fdkankan.download.service.ILaserService; import com.fdkankan.download.service.IScenePlusService; import com.fdkankan.download.util.DownloadUtil; import com.fdkankan.download.util.ImgUtil; import com.fdkankan.fyun.face.FYunFileServiceInterface; import jodd.util.SystemUtil; import lombok.SneakyThrows; import lombok.extern.slf4j.Slf4j; import net.lingala.zip4j.ZipFile; import net.lingala.zip4j.model.ZipParameters; import org.springframework.beans.factory.annotation.Autowired; import org.springframework.beans.factory.annotation.Value; import org.springframework.stereotype.Service; import oshi.software.os.OperatingSystem; import oshi.software.os.windows.WindowsOperatingSystem; import javax.annotation.Resource; import java.io.File; import java.nio.charset.Charset; import java.util.Collections; import java.util.Date; import java.util.List; import java.util.Map; /** * @author Xiewj * @date 2024/1/4 */ @Service @Slf4j public class LaserService implements ILaserService { @Autowired DownloadUtil downloadUtil; @Value("${laserhost}") private String host; @Resource private HttpClient httpClient; @Value("${api.offlineData}") private String offlineData; @Resource private FYunFileServiceInterface fYunFileService; @Value("${laser.bucket}") private String bucket; @Value("${path.source-local-laser}") private String sourceLocal; @Value("${path.laserschool}") private String laserschool; @Autowired IDownloadService downloadService; @Value("${download.config.resource-url}") private String resourceUrl; @Value("${download.config.laser-resource-url}") private String laserResourceUrl; @Value("${path.zip-local}") private String zipLocalFormat; @Override public String downloadHandler(String num) throws Exception { String url = host.concat(String.format(offlineData, num)); try { LaserResultData > resultData = httpClient.get(url, new SuccessLaserCallback(), new ErrorCallback()); if (resultData.getCode()==200){ OperatingSystem os = OshiUtil.getOs(); List data = resultData.getData(); data.parallelStream().forEach(datum -> { //1 json ,2下载,3深度图 ,4全景图 switch (datum.getType()) { case 1: FileUtil.writeUtf8String(JSON.toJSONStringWithDateFormat(datum.getData(), "yyyy-MM-dd HH:mm:ss").replaceAll("\\n", " ").replaceAll("\\t", " "), sourceLocal + File.separator + datum.getPath()); break; case 2: if (os instanceof WindowsOperatingSystem) { String path = datum.getKey(); if (datum.getKey().startsWith("/")) { path = path.substring(1); } List strings = fYunFileService.listRemoteFiles(bucket, path); for (String key : strings) { if (StrUtil.isEmpty(FileUtil.extName(key))) { continue; } String srcPath = key; if (!key.startsWith("/")) { srcPath = "/" + key; } downloadUtil.downloadFile(laserResourceUrl + key, sourceLocal + File.separator + num + File.separator + "www" + File.separator + num + srcPath,1); } } else { String srcPath = datum.getKey(); if ("/".equals(datum.getKey().substring(0, 1))) { srcPath = srcPath.substring(1); } fYunFileService.downloadFileByCommand(bucket, sourceLocal + datum.getPath(), srcPath); } break; case 3: // if (os instanceof WindowsOperatingSystem){ String path = datum.getKey(); if (datum.getKey().startsWith("/")) { path = path.substring(1); } List strings = fYunFileService.listRemoteFiles(bucket, path); for (String key : strings) { if (StrUtil.isEmpty(FileUtil.extName(key)) || FileUtil.extName(key).equalsIgnoreCase("ply")) { continue; } downloadUtil.downloadFile(laserResourceUrl + key, sourceLocal + File.separator + num + File.separator + "www" + File.separator + num + File.separator + "wwwroot" + File.separator + datum.getSceneCode() + File.separator + "data" + File.separator + datum.getSceneCode() + File.separator + "depthmap" + File.separator + FileUtil.getName(key),1); } // }else{ // String srcPath=datum.getKey(); // if("/".equals(datum.getKey().substring(0,1))){ // srcPath = srcPath.substring(1); // } // fYunFileService.downloadFileByCommand(bucket,sourceLocal+datum.getPath(),srcPath); // File[] deptLs = FileUtil.ls(sourceLocal+datum.getPath()); // for (File dept : deptLs) { // if (FileUtil.extName(dept).equalsIgnoreCase("ply")){ // FileUtil.del(dept); // } // } // } break; case 4: try { downloadService.cutImg(datum.getSceneCode(), sourceLocal + datum.getPath(), "4k", "tiles", SceneVersionType.V4.code()); } catch (Exception e) { throw new RuntimeException(e); } break; default: break; } }); String path=sourceLocal+File.separator+num; //处理html的编码 String htmlPath=laserschool+"www/offline.html"; if (FileUtil.exist(htmlPath)){ String copyPath=path+File.separator+"www"+File.separator; FileUtil.copy(htmlPath, copyPath, true); FileReader fileReader = new FileReader(copyPath+"offline.html"); String html = fileReader.readString(); FileWriter fileWriter=new FileWriter(copyPath+"offline.html"); fileWriter.write(html.replaceAll("@lang@","zh"),false); } String browserBatPath=laserschool+"start-browser.bat"; if (FileUtil.exist(browserBatPath)){ String copyPath=path+File.separator; FileUtil.copy(browserBatPath, copyPath, true); FileReader fileReader = new FileReader(copyPath+"start-browser.bat"); String bat = fileReader.readString(); FileWriter fileWriter=new FileWriter(copyPath+"start-browser.bat"); fileWriter.write(bat.replaceAll("@sceneCode@",num),false); } String zipPath = String.format(this.zipLocalFormat, DateExtUtil.format(new Date(), DateExtUtil.dateStyle6),num + "_laser"); File file=offlineZip(path,zipPath); log.info("生成完成路径{}",file.getAbsoluteFile()); return zipPath; } }catch (Exception e){ log.error("laser场景下载报错,num:{}", num, e); throw e; }finally { String path=sourceLocal+File.separator+num; FileUtil.del(path); } return ""; } public final static String ZIP_PATH = "cd @path && cp -f @bashOffline . && zip -u -r bashOffline.zip start-browser.bat www/ && mv -f bashOffline.zip @target"; @SneakyThrows public File offlineZip( String path,String moveZipPath) { String bashOfflinePath = laserschool + "bashOffline.zip"; File file = new File(moveZipPath); if(!file.getParentFile().exists()){ file.getParentFile().mkdirs(); } String zipCmd = ZIP_PATH; zipCmd = zipCmd.replace("@bashOffline", bashOfflinePath); zipCmd = zipCmd.replace("@target", moveZipPath); zipCmd = zipCmd.replace("@path", path); CmdUtils.callLineSh(zipCmd); if(!FileUtil.exist(moveZipPath)){ throw new RuntimeException("打包失败"); } return FileUtil.file(moveZipPath); } }