|
@@ -1,20 +1,20 @@
|
|
|
package com.mooctest.crowd.site.service.impl;
|
|
|
|
|
|
-import com.mooctest.crowd.domain.dao.CrowdTestTaskDao;
|
|
|
-import com.mooctest.crowd.domain.dao.EndPointDao;
|
|
|
-import com.mooctest.crowd.domain.domainobject.CrowdTestProject;
|
|
|
-import com.mooctest.crowd.domain.domainobject.CrowdTestTask;
|
|
|
-import com.mooctest.crowd.domain.domainobject.CrowdTestTaskStatus;
|
|
|
-import com.mooctest.crowd.domain.domainobject.DistributeType;
|
|
|
-import com.mooctest.crowd.domain.exception.BaseException;
|
|
|
-import com.mooctest.crowd.domain.exception.CrowdTestTaskNotExistException;
|
|
|
-import com.mooctest.crowd.domain.exception.UnauthorizedException;
|
|
|
+import com.alibaba.fastjson.JSON;
|
|
|
+import com.google.gson.Gson;
|
|
|
+import com.mooctest.crowd.domain.dao.*;
|
|
|
+import com.mooctest.crowd.domain.domainobject.*;
|
|
|
+import com.mooctest.crowd.domain.exception.*;
|
|
|
+import com.mooctest.crowd.domain.model.ApplicationTypePO;
|
|
|
import com.mooctest.crowd.domain.model.EndPointPO;
|
|
|
+import com.mooctest.crowd.domain.model.FieldPO;
|
|
|
import com.mooctest.crowd.domain.repository.CommonRepo;
|
|
|
import com.mooctest.crowd.domain.repository.CrowdTestProjectRepo;
|
|
|
import com.mooctest.crowd.domain.repository.CrowdTestTaskRepo;
|
|
|
import com.mooctest.crowd.domain.repository.UserRepo;
|
|
|
import com.mooctest.crowd.site.command.CrowdTestTaskCommand;
|
|
|
+import com.mooctest.crowd.site.constants.UploadType;
|
|
|
+import com.mooctest.crowd.site.data.dto.ProjectDetailsDTO;
|
|
|
import com.mooctest.crowd.site.data.dto.TaskDetailsDTO;
|
|
|
import com.mooctest.crowd.site.data.dto.TaskSquareDTO;
|
|
|
import com.mooctest.crowd.site.data.enums.ProjectType;
|
|
@@ -23,12 +23,21 @@ import com.mooctest.crowd.site.data.tfidf.TFIDFAnalyzer;
|
|
|
import com.mooctest.crowd.site.data.vo.CrowdTaskVO;
|
|
|
import com.mooctest.crowd.site.mediator.ViewMediator;
|
|
|
import com.mooctest.crowd.site.service.CrowdTaskService;
|
|
|
+import com.mooctest.crowd.site.service.UploadService;
|
|
|
import com.mooctest.crowd.site.util.GenerateFlowCodeUtil;
|
|
|
import lombok.extern.slf4j.Slf4j;
|
|
|
+import net.lingala.zip4j.exception.ZipException;
|
|
|
+import net.lingala.zip4j.model.ZipParameters;
|
|
|
+import net.lingala.zip4j.util.Zip4jConstants;
|
|
|
+import org.jetbrains.annotations.NotNull;
|
|
|
import org.springframework.beans.BeanUtils;
|
|
|
import org.springframework.beans.factory.annotation.Autowired;
|
|
|
+import org.springframework.beans.factory.annotation.Value;
|
|
|
+import org.springframework.mock.web.MockMultipartFile;
|
|
|
import org.springframework.stereotype.Service;
|
|
|
+import org.springframework.web.multipart.MultipartFile;
|
|
|
|
|
|
+import java.io.*;
|
|
|
import java.util.List;
|
|
|
import java.util.Map;
|
|
|
import java.util.Optional;
|
|
@@ -56,6 +65,15 @@ public class CrowdTaskServiceImpl implements CrowdTaskService {
|
|
|
CrowdTestTaskDao taskDao;
|
|
|
|
|
|
@Autowired
|
|
|
+ FieldDao fieldDao;
|
|
|
+
|
|
|
+ @Autowired
|
|
|
+ ApplicationTypeDao applicationTypeDao;
|
|
|
+
|
|
|
+ @Autowired
|
|
|
+ TestTypeDao testTypeDao;
|
|
|
+
|
|
|
+ @Autowired
|
|
|
private UserRepo userRepo;
|
|
|
|
|
|
@Autowired
|
|
@@ -64,6 +82,24 @@ public class CrowdTaskServiceImpl implements CrowdTaskService {
|
|
|
@Autowired
|
|
|
private CommonRepo commonRepo;
|
|
|
|
|
|
+ @Autowired
|
|
|
+ private UploadService uploadService;
|
|
|
+
|
|
|
+ @Value("${file.save.path}")
|
|
|
+ private String fileSaveRootPath;
|
|
|
+
|
|
|
+ @Value("${private.cloud.master}")
|
|
|
+ private String masterName;
|
|
|
+
|
|
|
+ @Value("${private.cloud.publish.project.id}")
|
|
|
+ private String publishProjectUserId;
|
|
|
+
|
|
|
+ @Value("${private.cloud.task.type.code}")
|
|
|
+ private String taskTypeCode;
|
|
|
+
|
|
|
+ @Value("${feature.client.oss}")
|
|
|
+ private Boolean usingOss;
|
|
|
+
|
|
|
@Override
|
|
|
public List<CrowdTaskVO> findMoreHotTasks() {
|
|
|
return viewMediator.findMoreHotTasks();
|
|
@@ -126,6 +162,10 @@ public class CrowdTaskServiceImpl implements CrowdTaskService {
|
|
|
task.create(taskCode);
|
|
|
project.addTask(task);
|
|
|
projectRepo.saveCrowdTestProject(project);
|
|
|
+
|
|
|
+// // 生成任务导出链接
|
|
|
+// String exportTaskUrl = this.exportTask(projectCode, task.getCode(), userId);
|
|
|
+// task.setExportUrl(exportTaskUrl);
|
|
|
return getTaskDetails(projectCode, taskCode, userId);
|
|
|
}
|
|
|
|
|
@@ -150,6 +190,11 @@ public class CrowdTaskServiceImpl implements CrowdTaskService {
|
|
|
updateTask.setStatus(CrowdTestTaskStatus.HAS_RELEASED);
|
|
|
updateTask.update();
|
|
|
project.removeTask(task.get());
|
|
|
+
|
|
|
+// // 重新生成任务导出链接
|
|
|
+// String exportTaskUrl = this.exportTask(projectCode, updateTask.getCode(), userId);
|
|
|
+// updateTask.setExportUrl(exportTaskUrl);
|
|
|
+
|
|
|
project.addTask(updateTask);
|
|
|
projectRepo.saveCrowdTestProject(project);
|
|
|
return getTaskDetails(projectCode, taskCode, userId);
|
|
@@ -241,5 +286,214 @@ public class CrowdTaskServiceImpl implements CrowdTaskService {
|
|
|
return TFIDFAnalyzer.getInstance().extractTagsList(taskDetails.getCrowdTaskVO().getDescription(), 20);
|
|
|
}
|
|
|
|
|
|
+ @Override
|
|
|
+ public String exportTask(String projectCode, String taskCode, Long userId) {
|
|
|
+ // 获取项目和任务的详细信息,特定任务的信息
|
|
|
+ ProjectDetailsDTO projectDetailsDTO = viewMediator.renderProjectDetails(projectRepo.getByProjectCodeAndTaskCode(projectCode, taskCode), userRepo.getByID(userId));
|
|
|
+
|
|
|
+ // 文件夹路径
|
|
|
+ String fileDirectoryPath = fileSaveRootPath + UploadType.EXPORT_TASK_FILE;
|
|
|
+ File fileDirectory = new File(fileDirectoryPath);
|
|
|
+ // 如果文件夹不存在,则新建一个
|
|
|
+ if(!fileDirectory.exists()){
|
|
|
+ fileDirectory.mkdirs();
|
|
|
+ }
|
|
|
+
|
|
|
+ // 文件路径
|
|
|
+ String fileNameCode = projectCode + "-" + taskCode;
|
|
|
+ String filePath = fileDirectoryPath + fileNameCode + ".json";
|
|
|
+ log.info("文件路径为:" + filePath);
|
|
|
+ File file = new File(filePath);
|
|
|
+ // 如果文件不存在,则新建一个
|
|
|
+ if(!file.exists()){
|
|
|
+ try {
|
|
|
+ file.createNewFile();
|
|
|
+ } catch (IOException e) {
|
|
|
+ throw new ExportTaskFileNotExistException();
|
|
|
+ }
|
|
|
+ }
|
|
|
+
|
|
|
+ // 将对象转成json字符串
|
|
|
+ String projectAndTaskJsonData = JSON.toJSONString(projectDetailsDTO);
|
|
|
+ // 将json字符串写入文件中
|
|
|
+ writerStringToFile(file, projectAndTaskJsonData);
|
|
|
+
|
|
|
+ // file是json文件,需要进行zip压缩
|
|
|
+ String downloadPath = fileDirectoryPath + fileNameCode + ".zip";
|
|
|
+ File downloadFile = new File(downloadPath);
|
|
|
+ String downloadUrl = downloadPath;
|
|
|
+ try{
|
|
|
+ log.info("----------------开始压缩文件----------------");
|
|
|
+ net.lingala.zip4j.core.ZipFile zipFile = new net.lingala.zip4j.core.ZipFile(downloadFile);
|
|
|
+ ZipParameters parameters = new ZipParameters();
|
|
|
+ parameters.setCompressionMethod(Zip4jConstants.COMP_DEFLATE);
|
|
|
+ parameters.setCompressionLevel(Zip4jConstants.DEFLATE_LEVEL_NORMAL);
|
|
|
+ zipFile.addFile(file, parameters);
|
|
|
+ log.info("----------------压缩结束-------------------");
|
|
|
+
|
|
|
+ // 将File类型转成MultipartFile类型
|
|
|
+ FileInputStream inputStream = new FileInputStream(downloadFile);
|
|
|
+ MultipartFile multipartFile = new MockMultipartFile(downloadFile.getName(), downloadFile.getName(), "", inputStream);
|
|
|
+ // 文件上传至oss
|
|
|
+ if(usingOss){
|
|
|
+ downloadUrl = uploadService.uploadTask(multipartFile, userId);
|
|
|
+ }
|
|
|
+ } catch (IOException e) {
|
|
|
+ log.info("----------copy error{}---------", e);
|
|
|
+ } catch (ZipException e) {
|
|
|
+ log.info("----------copy error{}---------", e);
|
|
|
+ }
|
|
|
+ log.info("下载链接:" + downloadUrl);
|
|
|
+ return downloadUrl;
|
|
|
+ }
|
|
|
+
|
|
|
+ /**
|
|
|
+ * 将json字符串写入文件中
|
|
|
+ * @param file
|
|
|
+ * @param projectAndTaskJsonData
|
|
|
+ */
|
|
|
+ public void writerStringToFile(File file, String projectAndTaskJsonData) {
|
|
|
+ //写入
|
|
|
+ BufferedWriter writer = null;
|
|
|
+ try {
|
|
|
+ writer = new BufferedWriter(new OutputStreamWriter(new FileOutputStream(file, false), "UTF-8"));
|
|
|
+ writer.write(projectAndTaskJsonData);
|
|
|
+ } catch (IOException e) {
|
|
|
+ e.printStackTrace();
|
|
|
+ }finally {
|
|
|
+ try {
|
|
|
+ if(writer != null){
|
|
|
+ writer.close();
|
|
|
+ }
|
|
|
+ } catch (IOException e) {
|
|
|
+ e.printStackTrace();
|
|
|
+ }
|
|
|
+ }
|
|
|
+ log.info("文件生成成功!");
|
|
|
+ }
|
|
|
+
|
|
|
+ @Override
|
|
|
+ public ProjectDetailsDTO importTask(MultipartFile file, Long userId) {
|
|
|
+ log.info("导入的文件为:" + file.getOriginalFilename());
|
|
|
+ // 将文件内容读出变成字符串
|
|
|
+ String fileString = fileToString(file);
|
|
|
+ Gson gson = new Gson();
|
|
|
+ // 将字符串序列化成对象
|
|
|
+ ProjectDetailsDTO projectDetailsDTO = gson.fromJson(fileString, ProjectDetailsDTO.class);
|
|
|
+
|
|
|
+ // 将对象VO转成CrowdTestProject
|
|
|
+ CrowdTestProject crowdTestProject = projectDetailsDTO.getProjectDetails().toCrowdTestProject();
|
|
|
+ User user = userRepo.getByIDJustInfo(userId);
|
|
|
+
|
|
|
+ // 为项目信息赋予导入的默认值
|
|
|
+ setProjectDefaultValueToPrivateCloud(crowdTestProject, user);
|
|
|
+ // 项目的剩余预算需要重新计算,根据任务报价
|
|
|
+
|
|
|
+ List<CrowdTestTask> crowdTestTaskList = projectDetailsDTO.getTaskList().stream().map(CrowdTaskVO::toCrowdTestTask).collect(Collectors.toList());
|
|
|
+ // 为任务信息赋予导入的默认值
|
|
|
+ crowdTestTaskList.forEach(crowdTestTask -> setTaskDefaultValueToPrivateCloud(crowdTestProject.getCode(), crowdTestTask));
|
|
|
+ // 所有任务花费的金额
|
|
|
+ double costPrice = crowdTestTaskList.stream().mapToDouble(CrowdTestTask::getQuotedPrice).sum();
|
|
|
+ // 为测试项目赋予测试类型、以及剩余预算
|
|
|
+ crowdTestProject.setType(crowdTestTaskList.get(0).getType());
|
|
|
+ crowdTestProject.setRestPrice(crowdTestProject.getQuotedPrice() - costPrice);
|
|
|
+ // 将任务添加到项目中
|
|
|
+ crowdTestProject.setCrowdTestTaskList(crowdTestTaskList);
|
|
|
+
|
|
|
+ projectRepo.saveCrowdTestProject(crowdTestProject);
|
|
|
+ return viewMediator.renderProjectDetails(projectRepo.getByProjectCode(crowdTestProject.getCode()), userRepo.getByID(userId));
|
|
|
+ }
|
|
|
+
|
|
|
+ /**
|
|
|
+ * 为项目信息赋予导入的默认值
|
|
|
+ * @param crowdTestProject
|
|
|
+ * @param user
|
|
|
+ */
|
|
|
+ private void setProjectDefaultValueToPrivateCloud(CrowdTestProject crowdTestProject, User user) {
|
|
|
+ // 导入私有云的项目名称以Master开头
|
|
|
+ crowdTestProject.setCode(masterName + "-" + System.currentTimeMillis() + "-" + crowdTestProject.getCode());
|
|
|
+
|
|
|
+ // 使用默认的发包用户进行发包
|
|
|
+ User publishUser = userRepo.getByIDJustInfo(Long.parseLong(publishProjectUserId));
|
|
|
+
|
|
|
+ crowdTestProject.setUserId(publishUser.getId());
|
|
|
+ crowdTestProject.setRegionalManagerId(user.getId());
|
|
|
+ crowdTestProject.setJoinCount(0);
|
|
|
+ crowdTestProject.setLinkManMobile(publishUser.getMobile());
|
|
|
+ crowdTestProject.setLinkMan(publishUser.getName());
|
|
|
+ crowdTestProject.setProjectDistributionTypeId(DistributeType.SQUARE.getId());
|
|
|
+ // 判断领域类型是否存在
|
|
|
+ Optional<FieldPO> fieldPO = fieldDao.findByName(crowdTestProject.getFieldType());
|
|
|
+ if(fieldPO.isPresent()){
|
|
|
+ crowdTestProject.setFieldType(fieldPO.get().getCode());
|
|
|
+ }else{
|
|
|
+ // 如果没有赋值为第一种测试类型
|
|
|
+ crowdTestProject.setFieldType(fieldDao.findAll().get(0).getCode());
|
|
|
+ }
|
|
|
+ // 判断应用类型是否存在
|
|
|
+ Optional<ApplicationTypePO> applicationTypePO = applicationTypeDao.findByName(crowdTestProject.getApplicationType());
|
|
|
+ if(applicationTypePO.isPresent()){
|
|
|
+ crowdTestProject.setApplicationType(applicationTypePO.get().getCode());
|
|
|
+ }else{
|
|
|
+ // 如果没有赋值为第一种测试类型
|
|
|
+ crowdTestProject.setApplicationType(applicationTypeDao.findAll().get(0).getCode());
|
|
|
+ }
|
|
|
+ }
|
|
|
+
|
|
|
+ /**
|
|
|
+ * 为任务信息赋予导入的默认值
|
|
|
+ * @param projectCode
|
|
|
+ * @param crowdTestTask
|
|
|
+ */
|
|
|
+ private void setTaskDefaultValueToPrivateCloud(String projectCode, CrowdTestTask crowdTestTask) {
|
|
|
+ crowdTestTask.setCode(masterName + "-" + System.currentTimeMillis() + "-" + crowdTestTask.getCode());
|
|
|
+ crowdTestTask.setCrowdTestProjectCode(projectCode);
|
|
|
+ crowdTestTask.setEvaluationAgencyId(null);
|
|
|
+ crowdTestTask.setDistributionType(DistributeType.SQUARE.getId());
|
|
|
+ crowdTestTask.setAcceptedCount(0);
|
|
|
+ crowdTestTask.setParticipantHasCommittedCount(0);
|
|
|
+ crowdTestTask.setFullStatus(0);
|
|
|
+ crowdTestTask.setStatus(CrowdTestTaskStatus.HAS_RELEASED);
|
|
|
+ // 判断默认的测试类型MCZC是否存在
|
|
|
+ if(testTypeDao.findByCode(taskTypeCode).isPresent()){
|
|
|
+ crowdTestTask.setType(taskTypeCode);
|
|
|
+ }else{
|
|
|
+ // 如果没有赋值为第一种测试类型
|
|
|
+ crowdTestTask.setType(testTypeDao.findAll().get(0).getCode());
|
|
|
+ }
|
|
|
+ }
|
|
|
+
|
|
|
+ /**
|
|
|
+ * 将文件内容读出变成字符串
|
|
|
+ * @param file
|
|
|
+ * @return
|
|
|
+ */
|
|
|
+ @NotNull
|
|
|
+ public String fileToString(MultipartFile file) {
|
|
|
+ if(file.isEmpty()){
|
|
|
+ throw new FileIsEmptyException();
|
|
|
+ }
|
|
|
+
|
|
|
+ // 读取文件内容
|
|
|
+ BufferedReader reader = null;
|
|
|
+ StringBuffer stringBuffer = new StringBuffer();
|
|
|
+ try {
|
|
|
+ reader = new BufferedReader(new InputStreamReader(file.getInputStream(), "UTF-8"));
|
|
|
+ String lineString;
|
|
|
+ while((lineString = reader.readLine()) != null){
|
|
|
+ stringBuffer.append(lineString);
|
|
|
+ }
|
|
|
+ if(reader != null){
|
|
|
+ reader.close();
|
|
|
+ }
|
|
|
+ } catch (UnsupportedEncodingException e) {
|
|
|
+ e.printStackTrace();
|
|
|
+ } catch (FileNotFoundException e) {
|
|
|
+ e.printStackTrace();
|
|
|
+ } catch (IOException e) {
|
|
|
+ e.printStackTrace();
|
|
|
+ }
|
|
|
+ return stringBuffer.toString();
|
|
|
+ }
|
|
|
}
|
|
|
|