中转业务更新
This commit is contained in:
parent
a6170c3fe0
commit
e5d129219d
|
@ -1,8 +1,8 @@
|
|||
package com.haitonggauto.rtosc.dto;
|
||||
|
||||
import com.baomidou.mybatisplus.annotation.TableField;
|
||||
import com.fasterxml.jackson.annotation.JsonFormat;
|
||||
import com.haitonggauto.rtosc.common.utils.ValidationGroup;
|
||||
import com.haitonggauto.rtosc.common.validate.DependsOn;
|
||||
import com.haitonggauto.rtosc.common.validate.MoreThan;
|
||||
import io.swagger.annotations.ApiModel;
|
||||
import io.swagger.annotations.ApiModelProperty;
|
||||
|
@ -11,7 +11,6 @@ import lombok.Data;
|
|||
import javax.validation.Valid;
|
||||
import javax.validation.constraints.NotBlank;
|
||||
import javax.validation.constraints.NotNull;
|
||||
import javax.validation.constraints.Size;
|
||||
import java.io.Serializable;
|
||||
import java.math.BigDecimal;
|
||||
import java.util.Date;
|
||||
|
@ -25,6 +24,7 @@ import java.util.List;
|
|||
@Data
|
||||
@ApiModel(value = "出口进场基本表", description = "")
|
||||
@MoreThan(groups = {ValidationGroup.insert.class, ValidationGroup.update.class}, field1 = "quantity", field2 = "eachQuantity", message = "数量不得超过单票件数")
|
||||
@DependsOn(groups = {ValidationGroup.insert.class, ValidationGroup.update.class}, field1 = "natureFlagName", fields = {"transferShipId", "transferShipName", "transferVoyageId", "transferVoyage"}, message = "货物性质为“正常”时,中转船ID,中转船名,中转航次ID,中转航次为空, 否则必填")
|
||||
public class ExportInVo implements Serializable {
|
||||
|
||||
@ApiModelProperty(value = "是否直接提交审核")
|
||||
|
@ -70,6 +70,27 @@ public class ExportInVo implements Serializable {
|
|||
@ApiModelProperty(value = "航次", required = true)
|
||||
private String voyage;
|
||||
|
||||
|
||||
@NotBlank(groups = {ValidationGroup.insert.class, ValidationGroup.update.class}, message = "货物性质ID不能为空")
|
||||
@ApiModelProperty(value = "货物性质ID", required = true)
|
||||
private String natureFlag;
|
||||
|
||||
@NotBlank(groups = {ValidationGroup.insert.class, ValidationGroup.update.class}, message = "货物性质名称不能为空")
|
||||
@ApiModelProperty(value = "货物性质名称", required = true)
|
||||
private String natureFlagName;
|
||||
|
||||
@ApiModelProperty(value = "中转船ID")
|
||||
private String transferShipId;
|
||||
|
||||
@ApiModelProperty(value = "中转船名")
|
||||
private String transferShipName;
|
||||
|
||||
@ApiModelProperty(value = "中转航次ID")
|
||||
private String transferVoyageId;
|
||||
|
||||
@ApiModelProperty(value = "中转航次名")
|
||||
private String transferVoyage;
|
||||
|
||||
/**
|
||||
* 港区ID
|
||||
*/
|
||||
|
@ -160,16 +181,14 @@ public class ExportInVo implements Serializable {
|
|||
@ApiModelProperty(value = "运输方式", required = true)
|
||||
private String transportWay;
|
||||
|
||||
@NotNull(groups = {ValidationGroup.insert.class, ValidationGroup.update.class}, message = "进场开始时间不能为空")
|
||||
@ApiModelProperty(value = "进场开始时间", required = true)
|
||||
@ApiModelProperty(value = "进场开始时间")
|
||||
@JsonFormat(pattern = "yyyy-MM-dd HH:mm:ss")
|
||||
private Date beginEnterTime;
|
||||
|
||||
/**
|
||||
* 进场开始时间
|
||||
*/
|
||||
@NotNull(groups = {ValidationGroup.insert.class, ValidationGroup.update.class}, message = "进场结束时间不能为空")
|
||||
@ApiModelProperty(value = "进场结束时间", required = true)
|
||||
@ApiModelProperty(value = "进场结束时间")
|
||||
@JsonFormat(pattern = "yyyy-MM-dd HH:mm:ss")
|
||||
private Date endEnterTime;
|
||||
|
||||
|
|
|
@ -0,0 +1,32 @@
|
|||
package com.haitonggauto.rtosc.excel;
|
||||
|
||||
import com.alibaba.excel.annotation.ExcelProperty;
|
||||
import lombok.Data;
|
||||
|
||||
import javax.validation.constraints.NotBlank;
|
||||
import javax.validation.constraints.Size;
|
||||
|
||||
@Data
|
||||
public class ExportInBillSpareExcel {
|
||||
|
||||
@ExcelProperty("*船名")
|
||||
@NotBlank(message = "船名不能为空")
|
||||
private String shipName;
|
||||
|
||||
@ExcelProperty("*航次")
|
||||
@NotBlank(message = "航次不能为空")
|
||||
private String voyage;
|
||||
|
||||
@ExcelProperty("*提单号")
|
||||
@NotBlank(message = "提单号不能为空")
|
||||
private String billNo;
|
||||
|
||||
@ExcelProperty("*品牌")
|
||||
@NotBlank(message = "品牌不能为空")
|
||||
private String brand;
|
||||
|
||||
@ExcelProperty("*备件号")
|
||||
@NotBlank(message = "备件号不能为空")
|
||||
@Size(min = 17, max = 17, message = "备件号长度为17位")
|
||||
private String vin;
|
||||
}
|
|
@ -3,6 +3,9 @@ package com.haitonggauto.rtosc.excel;
|
|||
import com.alibaba.excel.annotation.ExcelProperty;
|
||||
import com.alibaba.excel.annotation.format.DateTimeFormat;
|
||||
import com.alibaba.excel.annotation.format.NumberFormat;
|
||||
import com.baomidou.mybatisplus.annotation.TableField;
|
||||
import com.haitonggauto.rtosc.common.utils.ValidationGroup;
|
||||
import com.haitonggauto.rtosc.common.validate.DependsOn;
|
||||
import io.swagger.annotations.ApiModelProperty;
|
||||
import lombok.Data;
|
||||
|
||||
|
@ -34,6 +37,7 @@ import java.util.Date;
|
|||
* 19.源类型必须是是新能源、不是新能源,否则的导入不成功
|
||||
*/
|
||||
@Data
|
||||
@DependsOn(field1 = "natureFlagName", fields = {"transferShipName", "transferVoyage"}, message = "货物性质为“正常”时,中转船ID,中转船名,中转航次ID,中转航次为空, 否则必填")
|
||||
public class ExportInPlanExcel {
|
||||
|
||||
/**
|
||||
|
@ -57,6 +61,16 @@ public class ExportInPlanExcel {
|
|||
@NotBlank(message = "航次不能为空")
|
||||
private String voyage;
|
||||
|
||||
@ExcelProperty("*货物性质")
|
||||
@NotBlank(message = "货物性质不能为空")
|
||||
private String natureFlagName;
|
||||
|
||||
@ExcelProperty("中转进口船名")
|
||||
private String transferShipName;
|
||||
|
||||
@ExcelProperty("中转进口航次")
|
||||
private String transferVoyage;
|
||||
|
||||
|
||||
/**
|
||||
* 货代
|
||||
|
|
|
@ -0,0 +1,28 @@
|
|||
package com.haitonggauto.rtosc.excel;
|
||||
|
||||
import com.alibaba.excel.annotation.ExcelProperty;
|
||||
import io.swagger.annotations.ApiModel;
|
||||
import io.swagger.annotations.ApiModelProperty;
|
||||
import lombok.Data;
|
||||
|
||||
import javax.validation.constraints.NotBlank;
|
||||
import javax.validation.constraints.Size;
|
||||
|
||||
|
||||
/**
|
||||
* 出口进场基本表
|
||||
* @TableName customer_export_in
|
||||
*/
|
||||
@Data
|
||||
@ApiModel
|
||||
public class ExportInSpareExcel {
|
||||
/**
|
||||
* 船名
|
||||
*/
|
||||
@NotBlank(message = "备件号不能为空")
|
||||
@Size(min = 17, max = 17, message = "备件号长度为17位")
|
||||
@ApiModelProperty(value = "备件号")
|
||||
@ExcelProperty("*备件号")
|
||||
private String vin;
|
||||
|
||||
}
|
|
@ -1,6 +1,7 @@
|
|||
package com.haitonggauto.rtosc.excel;
|
||||
|
||||
import com.alibaba.excel.annotation.ExcelProperty;
|
||||
import com.haitonggauto.rtosc.common.validate.DependsOn;
|
||||
import io.swagger.annotations.ApiModelProperty;
|
||||
import lombok.Data;
|
||||
|
||||
|
@ -8,6 +9,7 @@ import javax.validation.constraints.NotBlank;
|
|||
import javax.validation.constraints.Size;
|
||||
|
||||
@Data
|
||||
@DependsOn(field1 = "natureFlagName", fields = {"transferShipName", "transferVoyage"}, message = "货物性质为“正常”时,中转船ID,中转船名,中转航次ID,中转航次为空, 否则必填")
|
||||
public class ExportLoadInsideExcel {
|
||||
|
||||
@ExcelProperty("*船名")
|
||||
|
@ -18,6 +20,16 @@ public class ExportLoadInsideExcel {
|
|||
@NotBlank(message = "航次不能为空")
|
||||
private String voyage;
|
||||
|
||||
@ExcelProperty("*货物性质")
|
||||
@NotBlank(message = "货物性质不能为空")
|
||||
private String natureFlagName;
|
||||
|
||||
@ExcelProperty("中转进口船名")
|
||||
private String transferShipName;
|
||||
|
||||
@ExcelProperty("中转进口航次")
|
||||
private String transferVoyage;
|
||||
|
||||
@ExcelProperty("*港区")
|
||||
@NotBlank(message = "港区不能为空")
|
||||
private String portArea;
|
||||
|
@ -30,7 +42,7 @@ public class ExportLoadInsideExcel {
|
|||
@NotBlank(message = "品牌不能为空")
|
||||
private String brand;
|
||||
|
||||
@ExcelProperty("*目的港")
|
||||
@ExcelProperty("目的港")
|
||||
private String destPort;
|
||||
|
||||
@ExcelProperty("*车架号")
|
||||
|
|
|
@ -0,0 +1,32 @@
|
|||
package com.haitonggauto.rtosc.common.validate;
|
||||
|
||||
import javax.validation.Constraint;
|
||||
import javax.validation.Payload;
|
||||
import java.lang.annotation.*;
|
||||
|
||||
/**
|
||||
* 一个字段依赖于另一个字段
|
||||
*/
|
||||
@Target({ElementType.TYPE, ElementType.ANNOTATION_TYPE})
|
||||
@Retention(RetentionPolicy.RUNTIME)
|
||||
@Documented
|
||||
@Constraint(validatedBy = DependsOnValidator.class)
|
||||
public @interface DependsOn {
|
||||
|
||||
/**
|
||||
* 违反校验时的错误信息
|
||||
*/
|
||||
String message() default "{DependsOn.message}";
|
||||
|
||||
/**
|
||||
* 用于指定校验的条件
|
||||
*/
|
||||
Class<?>[] groups() default {};
|
||||
|
||||
Class<? extends Payload>[] payload() default {};
|
||||
|
||||
// 比较字段一
|
||||
String field1();
|
||||
// 比较字段二
|
||||
String[] fields();
|
||||
}
|
|
@ -0,0 +1,62 @@
|
|||
package com.haitonggauto.rtosc.common.validate;
|
||||
|
||||
import org.apache.commons.lang3.StringUtils;
|
||||
import org.springframework.beans.BeanWrapperImpl;
|
||||
|
||||
import javax.validation.ConstraintValidator;
|
||||
import javax.validation.ConstraintValidatorContext;
|
||||
|
||||
public class DependsOnValidator implements ConstraintValidator<DependsOn, Object> {
|
||||
// 字段一
|
||||
private String field1;
|
||||
// 字段二
|
||||
private String[] fields;
|
||||
|
||||
@Override
|
||||
public void initialize(final DependsOn constraintAnnotation) {
|
||||
field1 = constraintAnnotation.field1();
|
||||
fields = constraintAnnotation.fields();
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean isValid(final Object src, ConstraintValidatorContext context) {
|
||||
BeanWrapperImpl wrapper = new BeanWrapperImpl(src);
|
||||
|
||||
if (StringUtils.isAnyEmpty(field1, field1)) {
|
||||
return false;
|
||||
}
|
||||
|
||||
Object value1 = wrapper.getPropertyValue(field1);
|
||||
|
||||
if (value1 == null) {
|
||||
for (String field : fields) {
|
||||
String v = (String) wrapper.getPropertyValue(field);
|
||||
if (StringUtils.isNotEmpty(v)) {
|
||||
return false;
|
||||
}
|
||||
}
|
||||
return true;
|
||||
}
|
||||
|
||||
if (value1 != null) {
|
||||
if (StringUtils.equals("正常", (String)value1)) {
|
||||
for (String field : fields) {
|
||||
String v = (String) wrapper.getPropertyValue(field);
|
||||
if (StringUtils.isNotEmpty(v)) {
|
||||
return false;
|
||||
}
|
||||
}
|
||||
} else {
|
||||
for (String field : fields) {
|
||||
String v = (String) wrapper.getPropertyValue(field);
|
||||
if (StringUtils.isEmpty(v)) {
|
||||
return false;
|
||||
}
|
||||
}
|
||||
}
|
||||
return true;
|
||||
}
|
||||
|
||||
return false;
|
||||
}
|
||||
}
|
|
@ -24,6 +24,10 @@ public interface NuzarPubApi {
|
|||
@GetMapping(value = "/typeRef/domain/TRADE_TYPE")
|
||||
List<NuzarDictDTO> getTradType();
|
||||
|
||||
// 获取获物性质
|
||||
@GetMapping(value = "/typeRef/domain/GOODS_NATURE")
|
||||
List<NuzarDictDTO> getGoodsNatureList();
|
||||
|
||||
// 所有船舶
|
||||
@GetMapping(value = "/shipManage/queryAllShipManage")
|
||||
List<ShipDTO> getAllShip();
|
||||
|
@ -63,4 +67,9 @@ public interface NuzarPubApi {
|
|||
// 根据客户名称查询客户信息
|
||||
@GetMapping(value = "/customerManage/query/name")
|
||||
CompanyDTO getCompanyByName(@RequestParam("cueCnname") String cueCnname);
|
||||
|
||||
// 船舶管理下拉框模糊查询
|
||||
@GetMapping(value = "/shipManage/queryLikeShipManage")
|
||||
List<ShipDTO> getShipList(@RequestParam("key") String key, @RequestParam("query") String query, @RequestParam("spmId") String spmId
|
||||
, @RequestParam("valid") String valid, @RequestParam("vslCd") String vslCd, @RequestParam("vslCnname") String vslCnname, @RequestParam("vslEnnameList") List<String> vslEnnameList);
|
||||
}
|
||||
|
|
|
@ -12,8 +12,8 @@ import org.springframework.web.bind.annotation.RequestParam;
|
|||
|
||||
import java.util.List;
|
||||
|
||||
//@FeignClient(name = "https://rtops4.haitongauto.com/tos/shp")
|
||||
@FeignClient(name = "shipment-service")
|
||||
@FeignClient(name = "https://rtops4.haitongauto.com/tos/shp")
|
||||
//@FeignClient(name = "shipment-service")
|
||||
public interface NuzarShpApi {
|
||||
|
||||
@GetMapping("/vesselVoyages/queryVvyName")
|
||||
|
@ -24,4 +24,9 @@ public interface NuzarShpApi {
|
|||
|
||||
@PostMapping("/vesselVoyages/queryVvyListByVvNameAndSpmName")
|
||||
List<VoyageResp> queryVvyListByVvNameAndSpmName(@RequestBody List<VoyageReq> req);
|
||||
|
||||
// 获取航次
|
||||
@GetMapping("/vesselVoyages/queryByKey")
|
||||
List<VoyageResp> queryVoyageByKey(@RequestParam("ieType") String ieType, @RequestParam("key") String key, @RequestParam("pamId") String pamId, @RequestParam("spmId") String spmId
|
||||
, @RequestParam("tradeType") String tradeType);
|
||||
}
|
||||
|
|
|
@ -3,6 +3,7 @@ package com.haitonggauto.rtosc.handler;
|
|||
import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper;
|
||||
import com.haitonggauto.rtosc.api.NuzarOpenApi;
|
||||
import com.haitonggauto.rtosc.api.NuzarPubApi;
|
||||
import com.haitonggauto.rtosc.api.NuzarShpApi;
|
||||
import com.haitonggauto.rtosc.api.dto.*;
|
||||
import com.haitonggauto.rtosc.common.context.UserContext;
|
||||
import com.haitonggauto.rtosc.common.dto.DictDTO;
|
||||
|
@ -41,15 +42,15 @@ import java.util.stream.Collectors;
|
|||
@Validated
|
||||
public class DictHandler implements BaseHandler {
|
||||
|
||||
@Resource
|
||||
private LoginHandler loginHandler;
|
||||
|
||||
@Resource
|
||||
private NuzarPubApi nuzarPubApi;
|
||||
|
||||
@Resource
|
||||
private NuzarOpenApi nuzarOpenApi;
|
||||
|
||||
@Resource
|
||||
private NuzarShpApi nuzarShpApi;
|
||||
|
||||
@Resource
|
||||
private CustomerLinkmanService customerLinkmanService;
|
||||
|
||||
|
@ -446,4 +447,49 @@ public class DictHandler implements BaseHandler {
|
|||
}
|
||||
}
|
||||
|
||||
|
||||
@ApiOperation("货物性质")
|
||||
@GetMapping("/goodsNature")
|
||||
public Result<List<NuzarDictDTO>> getGoodsNature() {
|
||||
|
||||
List<NuzarDictDTO> list = nuzarPubApi.getGoodsNatureList();
|
||||
|
||||
if (CollectionUtils.isEmpty(list)) {
|
||||
return ResultUtil.success(Collections.emptyList());
|
||||
} else {
|
||||
|
||||
}
|
||||
|
||||
return ResultUtil.success(list);
|
||||
}
|
||||
|
||||
@ApiOperation("获取船名")
|
||||
@GetMapping(value = "/shipManage/queryLikeShipManage")
|
||||
public Result<List<ShipDTO>> getShipList(@RequestParam(value = "key", required = false) String key, @RequestParam(value = "query", required = false) String query, @RequestParam(value = "spmId", required = false) String spmId
|
||||
, @RequestParam(value = "valid", required = false) String valid, @RequestParam(value = "vslCd", required = false) String vslCd, @RequestParam(value = "vslCnname", required = false) String vslCnname, @RequestParam(value = "vslEnnameList", required = false) List<String> vslEnnameList) {
|
||||
List<ShipDTO> list = nuzarPubApi.getShipList(key, query, spmId, valid, vslCd, vslCnname, vslEnnameList);
|
||||
|
||||
if (CollectionUtils.isEmpty(list)) {
|
||||
return ResultUtil.success(Collections.emptyList());
|
||||
} else {
|
||||
|
||||
}
|
||||
|
||||
return ResultUtil.success(list);
|
||||
}
|
||||
|
||||
@ApiOperation("获取航次")
|
||||
@GetMapping("/vesselVoyages/queryByKey")
|
||||
public Result<List<VoyageResp>> queryVoyageByKey(@RequestParam(value = "ieType", required = false) String ieType, @RequestParam(value = "key", required = false) String key, @RequestParam(value = "pamId", required = false) String pamId, @RequestParam(value = "spmId", required = false) String spmId
|
||||
, @RequestParam(value = "tradeType", required = false) String tradeType) {
|
||||
List<VoyageResp> list = nuzarShpApi.queryVoyageByKey(ieType, key, pamId, spmId, tradeType);
|
||||
|
||||
if (CollectionUtils.isEmpty(list)) {
|
||||
return ResultUtil.success(Collections.emptyList());
|
||||
} else {
|
||||
|
||||
}
|
||||
|
||||
return ResultUtil.success(list);
|
||||
}
|
||||
}
|
||||
|
|
|
@ -683,7 +683,7 @@ public class ExportInHandler implements BaseHandler {
|
|||
entity.setVinStatus(1);
|
||||
return entity;
|
||||
}).collect(Collectors.toList());
|
||||
if (CollectionUtils.isEmpty(spares) && StringUtils.equalsAnyIgnoreCase(exportIn.getCartType(), "备件", "BJ")) {
|
||||
if (CollectionUtils.isEmpty(spares) && StringUtils.equalsAnyIgnoreCase(exportIn.getCartType(), "备件", "BJ") && StringUtils.equals("正常", exportIn.getNatureFlagName())) {
|
||||
// 出口进场计划备件条码生成的规则要变一下,BJ+年月日时分+5随机数,一共要17位
|
||||
String prefix = StringUtils.join("BJ", DateUtil.format(new Date(), "yyMMddHHmm"));
|
||||
List<String> vins = new ArrayList<>(exportIn.getQuantity());
|
||||
|
@ -931,6 +931,7 @@ public class ExportInHandler implements BaseHandler {
|
|||
*/
|
||||
@ApiOperation("编辑")
|
||||
@PostMapping("/edit")
|
||||
@Transactional(rollbackFor = {Exception.class})
|
||||
// 使用LambdaUpdateWrapper只在特定需求下做处理(推荐) 将字段修改为空值的处理方法
|
||||
public Result<String> edit(@RequestParam(required = false, defaultValue = "false") Boolean flag,
|
||||
@RequestBody @Validated(ValidationGroup.update.class) ExportInVo form) {
|
||||
|
@ -954,6 +955,7 @@ public class ExportInHandler implements BaseHandler {
|
|||
if (in.getCheckStatus() == AuditEnum.AUDIT_PASS) {
|
||||
return ResultUtil.failure(ErrorType.PARAMS_ERROR.id(), "审核通过之后不能进行编辑");
|
||||
}
|
||||
|
||||
String batchNo = in.getBatchNo();
|
||||
// 表单验证以及格式转换
|
||||
CustomerExportIn exportIn = PoMapper.instance.exportInVo2Entity(form);
|
||||
|
@ -965,6 +967,9 @@ public class ExportInHandler implements BaseHandler {
|
|||
exportIn.setCheckStatus(AuditEnum.AUDIT);
|
||||
}
|
||||
|
||||
// 判断货物性质是否发生变化
|
||||
boolean f = StringUtils.equals(in.getNatureFlagName(), exportIn.getNatureFlagName());
|
||||
|
||||
List<CustomerExportInCargo> cargos = form.getCargos().stream().map(item -> {
|
||||
CustomerExportInCargo entity = PoMapper.instance.exportInCargoVo2Entity(item);
|
||||
entity.setBrand(exportIn.getBrand());
|
||||
|
@ -997,7 +1002,7 @@ public class ExportInHandler implements BaseHandler {
|
|||
return entity;
|
||||
}).collect(Collectors.toList());
|
||||
|
||||
if (CollectionUtils.isNotEmpty(spares)) {
|
||||
if (CollectionUtils.isNotEmpty(spares) || (!f && StringUtils.equalsAnyIgnoreCase(exportIn.getCartType(), "备件", "BJ") && StringUtils.equalsAnyIgnoreCase(exportIn.getNatureFlagName(), "正常"))) {
|
||||
// 验证数量
|
||||
if (exportIn.getQuantity() < spares.size()) {
|
||||
return ResultUtil.failure(ErrorType.PROGRAM_ERROR.id(), "备件列表不能大于备件总数");
|
||||
|
@ -1103,6 +1108,11 @@ public class ExportInHandler implements BaseHandler {
|
|||
}
|
||||
}
|
||||
|
||||
// 货物性质发生变化时,需要清空表
|
||||
if (!f && StringUtils.equalsAnyIgnoreCase(exportIn.getCartType(), "备件", "BJ")) {
|
||||
customerExportInCargoService.lambdaUpdate().eq(CustomerExportInCargo::getExportInId, in.getId()).remove();
|
||||
}
|
||||
|
||||
customerService.updateExportIn(false, exportIn, cargos, times, spares);
|
||||
|
||||
return ResultUtil.success(String.valueOf(exportIn.getId()));
|
||||
|
@ -1840,7 +1850,7 @@ public class ExportInHandler implements BaseHandler {
|
|||
|
||||
List<ExportVinExcel> existData = item.getValue().stream().filter(p -> existVins.contains(p.getVin())).collect(Collectors.toList());
|
||||
if (CollectionUtils.isNotEmpty(existData)) {
|
||||
errorDataList.addAll(item.getValue().stream().map(p -> {
|
||||
errorDataList.addAll(existData.stream().map(p -> {
|
||||
JSONObject o = JSONObject.from(p);
|
||||
o.put("status", "数据已存在");
|
||||
return o;
|
||||
|
@ -1871,6 +1881,192 @@ public class ExportInHandler implements BaseHandler {
|
|||
return ResultUtil.success(errorDataList);
|
||||
}
|
||||
|
||||
@ApiOperation("备件号导入模板下载")
|
||||
@GetMapping("/temp/down/spare")
|
||||
public void tmpDownSpare(HttpServletResponse response) throws Exception {
|
||||
ExcelWriter excelWriter = null;
|
||||
OutputStream out = null;
|
||||
try {
|
||||
out = response.getOutputStream();
|
||||
|
||||
// 这里注意 有同学反应使用swagger 会导致各种问题,请直接用浏览器或者用postman
|
||||
response.setContentType("application/vnd.ms-excel");
|
||||
response.setCharacterEncoding("utf-8");
|
||||
// 这里URLEncoder.encode可以防止中文乱码 当然和easyexcel没有关系
|
||||
String fileName = URLEncoder.encode("备件号导入模板", "UTF-8");
|
||||
response.setHeader("Content-disposition", "attachment;filename=" + fileName + ".xlsx");
|
||||
|
||||
excelWriter = EasyExcel.write(out).build();
|
||||
|
||||
WriteSheet writeSheet = EasyExcel.writerSheet(0, "备件号").head(ExportInSpareExcel.class).build();
|
||||
|
||||
// 查询数据
|
||||
List<ExportInSpareExcel> rows = new ArrayList<>();
|
||||
|
||||
excelWriter.write(rows, writeSheet);
|
||||
} catch (Exception e) {
|
||||
e.printStackTrace();
|
||||
} finally {
|
||||
if (excelWriter != null) {
|
||||
excelWriter.finish();
|
||||
}
|
||||
if (out != null) {
|
||||
try {
|
||||
out.close();
|
||||
} catch (IOException e) {
|
||||
e.printStackTrace();
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@ApiOperation("备件号导入")
|
||||
@PostMapping("/import-spare")
|
||||
public Result<List<JSONObject>> importSpare(@RequestParam(required = false) @NotNull(message = "出口进场ID不能为空") Long id, MultipartFile file) throws IOException {
|
||||
CustomerExportIn exportIn = customerExportInService.getById(id);
|
||||
|
||||
List<Long> havePlans = openApi.haveShipPlan(exportIn.getVoyageId());
|
||||
if (exportIn != null && CollectionUtils.isNotEmpty(havePlans)) {
|
||||
Boolean c = havePlans.contains(exportIn.getId());
|
||||
if (c) {
|
||||
return ResultUtil.failure(ErrorType.PARAMS_ERROR.id(), "已生成装船计划,不能导入");
|
||||
}
|
||||
}
|
||||
|
||||
// 所有读取的数据
|
||||
List<ExportInSpareExcel> dataList = new ArrayList<>();
|
||||
|
||||
// 有错误的数据
|
||||
List<JSONObject> errorDataList = new ArrayList<>();
|
||||
|
||||
// 验证成功的数据
|
||||
List<JSONObject> successDataList = new ArrayList<>();
|
||||
|
||||
// 要存储的数据
|
||||
List<CustomerExportInCargo> saveCargos = new ArrayList<>();
|
||||
|
||||
EasyExcel.read(file.getInputStream(), ExportInSpareExcel.class, new ReadExcelListener<ExportInSpareExcel>() {
|
||||
@Override
|
||||
protected void saveData(List<ExportInSpareExcel> list) { // 缓存数据
|
||||
dataList.addAll(list);
|
||||
}
|
||||
}).sheet().doRead();
|
||||
|
||||
ValidatorFactory vf = Validation.buildDefaultValidatorFactory();
|
||||
Validator validator = vf.getValidator();
|
||||
|
||||
List<ExportInSpareExcel> validData = new ArrayList<>();
|
||||
|
||||
// 数据验证
|
||||
dataList.stream().forEach(item -> {
|
||||
Set<ConstraintViolation<ExportInSpareExcel>> set = validator.validate(item);
|
||||
if (CollectionUtils.isEmpty(set)) { // 验证通过的
|
||||
validData.add(item);
|
||||
} else { // 验证失败的
|
||||
JSONObject o = JSONObject.from(item);
|
||||
o.put("status", set.stream().map(p -> p.getMessage()).collect(Collectors.joining(",")));
|
||||
errorDataList.add(o);
|
||||
}
|
||||
});
|
||||
|
||||
if (CollectionUtils.isEmpty(validData)) {
|
||||
return ResultUtil.failure(ErrorType.PARAMS_ERROR.id(), "导入失败", errorDataList);
|
||||
}
|
||||
|
||||
// 是否有重复的车架号
|
||||
List<String> repeat = validData.stream().collect(Collectors.groupingBy(ExportInSpareExcel::getVin, Collectors.counting()))
|
||||
.entrySet().stream().filter(entry -> entry.getValue() > 1).map(entry -> entry.getKey()).collect(Collectors.toList());
|
||||
if (CollectionUtils.isNotEmpty(repeat)) {
|
||||
errorDataList.addAll(validData.stream().filter(p -> repeat.contains(p.getVin())).map(p -> {
|
||||
JSONObject o = JSONObject.from(p);
|
||||
o.put("status", "车架号重复");
|
||||
return o;
|
||||
}).collect(Collectors.toList()));
|
||||
return ResultUtil.failure(ErrorType.PARAMS_ERROR.id(), "导入失败", errorDataList);
|
||||
}
|
||||
|
||||
if (exportIn.getQuantity() != validData.size()) {
|
||||
errorDataList.addAll(validData.stream().map(p -> {
|
||||
JSONObject o = JSONObject.from(p);
|
||||
o.put("status", "数量不一致");
|
||||
return o;
|
||||
}).collect(Collectors.toList()));
|
||||
return ResultUtil.failure(ErrorType.PARAMS_ERROR.id(), "导入失败", errorDataList);
|
||||
}
|
||||
|
||||
List<CustomerExportInCargo> cargos = validData.stream().map(p -> {
|
||||
CustomerExportInCargo cargo = new CustomerExportInCargo();
|
||||
cargo.setExportInId(exportIn.getId());
|
||||
cargo.setBrand(exportIn.getBrand());
|
||||
cargo.setBrandId(exportIn.getBrandId());
|
||||
cargo.setCargoType(0);
|
||||
cargo.setVin(p.getVin());
|
||||
cargo.setTermcd(exportIn.getPortAreaId());
|
||||
cargo.setVinStatus(1);
|
||||
return cargo;
|
||||
}).collect(Collectors.toList());
|
||||
|
||||
List<String> vins = cargos.stream().map(p -> p.getVin()).collect(Collectors.toList());
|
||||
|
||||
// 验证哪些车架号已经存在了
|
||||
List<CustomerExportInCargo> existCargos = customerExportInCargoService.list(new LambdaQueryWrapper<CustomerExportInCargo>().in(CustomerExportInCargo::getVin, vins).ne(CustomerExportInCargo::getExportInId, exportIn.getId()));
|
||||
List<String> existVins = existCargos.stream().map(p -> p.getVin()).collect(Collectors.toList());
|
||||
|
||||
if (CollectionUtils.isNotEmpty(existCargos)) {
|
||||
// 查询出对应的港区
|
||||
List<CustomerExportIn> sList = customerExportInService.lambdaQuery().in(CustomerExportIn::getId, existCargos.stream().map(ss -> ss.getExportInId()).collect(Collectors.toList())).list();
|
||||
Map<Long, String> portAreaMap = sList.stream().collect(Collectors.toMap(CustomerExportIn::getId, CustomerExportIn::getPortAreaId));
|
||||
// 通过接口再次验证
|
||||
List<CheckVinReq> req = existCargos.stream().map(ss -> {
|
||||
CheckVinReq v = new CheckVinReq();
|
||||
v.setIsRepetition(true);
|
||||
v.setPamId(portAreaMap.get(ss.getExportInId()));
|
||||
v.setVinCode(ss.getVin());
|
||||
return v;
|
||||
}).collect(Collectors.toList());
|
||||
List<CheckVinReq> rst = shpApi.checkVinRepeat(req);
|
||||
existVins.clear();
|
||||
if (CollectionUtils.isNotEmpty(rst)) {
|
||||
// 再次过滤出重复的
|
||||
List<CheckVinReq> sCollect = rst.stream().filter(ss -> ss.getIsRepetition()).collect(Collectors.toList());
|
||||
if (CollectionUtils.isNotEmpty(sCollect)) {
|
||||
existVins.addAll(sCollect.stream().map(ss -> ss.getVinCode()).collect(Collectors.toList()));
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
List<ExportInSpareExcel> existData = validData.stream().filter(p -> existVins.contains(p.getVin())).collect(Collectors.toList());
|
||||
if (CollectionUtils.isNotEmpty(existData)) {
|
||||
errorDataList.addAll(existData.stream().map(p -> {
|
||||
JSONObject o = JSONObject.from(p);
|
||||
o.put("status", "数据已存在");
|
||||
return o;
|
||||
}).collect(Collectors.toList()));
|
||||
}
|
||||
|
||||
successDataList.addAll(validData.stream().filter(p -> !existVins.contains(p.getVin()))
|
||||
.map(p -> {
|
||||
JSONObject o = JSONObject.from(p);
|
||||
o.put("status", "数据验证成功");
|
||||
return o;
|
||||
}).collect(Collectors.toList()));
|
||||
|
||||
saveCargos.addAll(cargos.stream().filter(p -> !existVins.contains(p.getVin())).collect(Collectors.toList()));
|
||||
|
||||
if (CollectionUtils.isNotEmpty(errorDataList)) {
|
||||
errorDataList.addAll(successDataList);
|
||||
return ResultUtil.failure(ErrorType.PARAMS_ERROR.id(), "导入失败", errorDataList);
|
||||
}
|
||||
|
||||
if (CollectionUtils.isNotEmpty(saveCargos)) {
|
||||
// 删除原有的车架号
|
||||
customerExportInCargoService.lambdaUpdate().eq(CustomerExportInCargo::getExportInId, exportIn.getId()).remove();
|
||||
customerExportInCargoService.saveBatch(saveCargos);
|
||||
}
|
||||
|
||||
return ResultUtil.success(errorDataList);
|
||||
}
|
||||
|
||||
@ApiOperation("整船清单导入模板下载")
|
||||
@GetMapping("/temp/down/ship")
|
||||
public void tmpDownShip(HttpServletResponse response) throws Exception {
|
||||
|
@ -2095,7 +2291,268 @@ public class ExportInHandler implements BaseHandler {
|
|||
|
||||
List<ExportLoadExcel> existData = item.getValue().stream().filter(p -> existVins.contains(p.getVin())).collect(Collectors.toList());
|
||||
if (CollectionUtils.isNotEmpty(existData)) {
|
||||
errorDataList.addAll(item.getValue().stream().filter(p -> existVins.contains(p.getVin())).map(p -> {
|
||||
errorDataList.addAll(existData.stream().map(p -> {
|
||||
JSONObject o = JSONObject.from(p);
|
||||
o.put("status", "数据已存在, 未导入");
|
||||
return o;
|
||||
}).collect(Collectors.toList()));
|
||||
successDataList.addAll(item.getValue().stream().filter(p -> !existVins.contains(p.getVin()))
|
||||
.map(p -> {
|
||||
JSONObject o = JSONObject.from(p);
|
||||
o.put("status", "数据验证成功");
|
||||
return o;
|
||||
}).collect(Collectors.toList()));
|
||||
return;
|
||||
} else {
|
||||
successDataList.addAll(item.getValue().stream().filter(p -> !existVins.contains(p.getVin()))
|
||||
.map(p -> {
|
||||
JSONObject o = JSONObject.from(p);
|
||||
o.put("status", "数据验证成功");
|
||||
return o;
|
||||
}).collect(Collectors.toList()));
|
||||
}
|
||||
|
||||
saveCargos.addAll(cargos.stream().filter(p -> !existVins.contains(p.getVin())).collect(Collectors.toList()));
|
||||
|
||||
});
|
||||
|
||||
if (CollectionUtils.isNotEmpty(errorDataList)) {
|
||||
errorDataList.addAll(successDataList);
|
||||
return ResultUtil.failure(ErrorType.PARAMS_ERROR.id(), "导入失败", errorDataList);
|
||||
}
|
||||
|
||||
if (CollectionUtils.isNotEmpty(saveCargos)) {
|
||||
// 删除原有的车架号
|
||||
customerExportInCargoService.lambdaUpdate().in(CustomerExportInCargo::getExportInId, ids).remove();
|
||||
customerExportInCargoService.saveBatch(saveCargos);
|
||||
}
|
||||
|
||||
return ResultUtil.success(errorDataList);
|
||||
}
|
||||
|
||||
@ApiOperation("整票备件号导入模板下载")
|
||||
@GetMapping("/temp/spare/down/ship")
|
||||
public void tmpDownShipSpare(HttpServletResponse response) throws Exception {
|
||||
ExcelWriter excelWriter = null;
|
||||
OutputStream out = null;
|
||||
try {
|
||||
out = response.getOutputStream();
|
||||
|
||||
// 这里注意 有同学反应使用swagger 会导致各种问题,请直接用浏览器或者用postman
|
||||
response.setContentType("application/vnd.ms-excel");
|
||||
response.setCharacterEncoding("utf-8");
|
||||
// 这里URLEncoder.encode可以防止中文乱码 当然和easyexcel没有关系
|
||||
String fileName = URLEncoder.encode("整票备件号导入模板", "UTF-8");
|
||||
response.setHeader("Content-disposition", "attachment;filename=" + fileName + ".xlsx");
|
||||
|
||||
excelWriter = EasyExcel.write(out).build();
|
||||
|
||||
WriteSheet writeSheet = EasyExcel.writerSheet(0, "整票备件号").head(ExportInBillSpareExcel.class).build();
|
||||
|
||||
// 查询数据
|
||||
List<ExportInBillSpareExcel> rows = new ArrayList<>();
|
||||
|
||||
excelWriter.write(rows, writeSheet);
|
||||
} catch (Exception e) {
|
||||
e.printStackTrace();
|
||||
} finally {
|
||||
if (excelWriter != null) {
|
||||
excelWriter.finish();
|
||||
}
|
||||
if (out != null) {
|
||||
try {
|
||||
out.close();
|
||||
} catch (IOException e) {
|
||||
e.printStackTrace();
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@ApiOperation("整票备件号导入")
|
||||
@PostMapping("/import-to-add/spare")
|
||||
public Result<List<JSONObject>> uploadSpare(
|
||||
@ApiParam(name = "操作方式, 0为前端,1为审核端") @RequestParam(required = false, defaultValue = "0") String type,
|
||||
MultipartFile file) throws IOException {
|
||||
// 所有读取的数据
|
||||
List<ExportInBillSpareExcel> dataList = new ArrayList<>();
|
||||
|
||||
// 有错误的数据
|
||||
List<JSONObject> errorDataList = new ArrayList<>();
|
||||
|
||||
// 验证成功的数据
|
||||
List<JSONObject> successDataList = new ArrayList<>();
|
||||
|
||||
// 需要清空的
|
||||
List<Long> ids = new ArrayList<>();
|
||||
|
||||
// 要保存到数据库的数据
|
||||
List<CustomerExportInCargo> saveCargos = new ArrayList<>();
|
||||
|
||||
EasyExcel.read(file.getInputStream(), ExportLoadExcel.class, new ReadExcelListener<ExportInBillSpareExcel>() {
|
||||
@Override
|
||||
protected void saveData(List<ExportInBillSpareExcel> list) { // 保存数据
|
||||
dataList.addAll(list);
|
||||
}
|
||||
}).sheet().doRead();
|
||||
|
||||
ValidatorFactory vf = Validation.buildDefaultValidatorFactory();
|
||||
Validator validator = vf.getValidator();
|
||||
|
||||
List<ExportInBillSpareExcel> validData = new ArrayList<>();
|
||||
|
||||
// 数据验证
|
||||
dataList.stream().forEach(item -> {
|
||||
Set<ConstraintViolation<ExportInBillSpareExcel>> set = validator.validate(item);
|
||||
if (CollectionUtils.isEmpty(set)) { // 验证通过的
|
||||
validData.add(item);
|
||||
} else { // 验证失败的
|
||||
JSONObject o = JSONObject.from(item);
|
||||
o.put("status", set.stream().map(p -> p.getMessage()).collect(Collectors.joining(",")));
|
||||
errorDataList.add(o);
|
||||
}
|
||||
});
|
||||
|
||||
// 所有数据验证都不通过
|
||||
if (CollectionUtils.isEmpty(validData)) {
|
||||
return ResultUtil.failure(ErrorType.PARAMS_ERROR.id(), "导入失败", errorDataList);
|
||||
}
|
||||
|
||||
// 首先按对船名,般次,提单进行分组
|
||||
Map<String, List<ExportInBillSpareExcel>> collect = validData.stream()
|
||||
.collect(Collectors.groupingBy(item -> StringUtils.joinWith("#$#", item.getShipName(), item.getVoyage(), item.getBillNo(), item.getBrand()), Collectors.toList()));
|
||||
|
||||
collect.entrySet().forEach(item -> {
|
||||
String[] keys = StringUtils.split(item.getKey(), "#$#");
|
||||
String shipName = keys[0]; // 船名
|
||||
String voyage = keys[1]; // 航次
|
||||
String billNo = keys[2]; // 提单号
|
||||
String brand = keys[3]; // 品牌
|
||||
// 找到是否存在船名,航次,提单号的表头
|
||||
|
||||
LambdaQueryWrapper<CustomerExportIn> cQuery = new LambdaQueryWrapper<>();
|
||||
cQuery.eq(CustomerExportIn::getShipName, shipName)
|
||||
.eq(CustomerExportIn::getVoyage, voyage)
|
||||
.eq(CustomerExportIn::getBillNum, billNo)
|
||||
.eq(CustomerExportIn::getBrand, brand)
|
||||
.eq(CustomerExportIn::getCartType, "备件"); // 备件的不允许整船导入
|
||||
if (StringUtils.equals(type, "0")) {
|
||||
cQuery.and((wrapper) -> {
|
||||
wrapper.eq(CustomerExportIn::getCheckStatus, AuditEnum.SUBMIT)
|
||||
.or()
|
||||
.eq(CustomerExportIn::getCheckStatus, AuditEnum.AUDIT_REJECT);
|
||||
});
|
||||
} else {
|
||||
cQuery.and((wrapper) -> {
|
||||
wrapper.eq(CustomerExportIn::getCheckStatus, AuditEnum.AUDIT)
|
||||
.or()
|
||||
.eq(CustomerExportIn::getCheckStatus, AuditEnum.AUDIT_REJECT);
|
||||
});
|
||||
}
|
||||
|
||||
List<CustomerExportIn> exportInList = customerExportInService.list(cQuery);
|
||||
|
||||
if (CollectionUtils.isEmpty(exportInList)) { // 船名,航次等不存在
|
||||
errorDataList.addAll(item.getValue().stream().map(p -> {
|
||||
JSONObject o = JSONObject.from(p);
|
||||
o.put("status", "船名、航次、提单号、品牌不存在");
|
||||
return o;
|
||||
}).collect(Collectors.toList()));
|
||||
return;
|
||||
}
|
||||
|
||||
// 找到和本次数量一致的
|
||||
Optional<CustomerExportIn> first = exportInList.stream().filter(p -> p.getQuantity() == item.getValue().size()).findFirst();
|
||||
|
||||
CustomerExportIn exportIn = first.isPresent() ? first.get() : null;
|
||||
|
||||
if (exportIn == null) {
|
||||
errorDataList.addAll(item.getValue().stream().map(p -> {
|
||||
JSONObject o = JSONObject.from(p);
|
||||
o.put("status", "数量不一致不允许导入");
|
||||
return o;
|
||||
}).collect(Collectors.toList()));
|
||||
return;
|
||||
}
|
||||
|
||||
ids.add(exportIn.getId());
|
||||
|
||||
// 已生成装船计划,不能导入
|
||||
List<Long> havePlans = openApi.haveShipPlan(exportIn.getVoyageId());
|
||||
if (exportIn != null && CollectionUtils.isNotEmpty(havePlans)) {
|
||||
Boolean c = havePlans.contains(exportIn.getId());
|
||||
if (c) {
|
||||
errorDataList.addAll(item.getValue().stream().map(p -> {
|
||||
JSONObject o = JSONObject.from(p);
|
||||
o.put("status", "已生成装船计划,不能导入");
|
||||
return o;
|
||||
}).collect(Collectors.toList()));
|
||||
return;
|
||||
}
|
||||
}
|
||||
|
||||
if (exportIn.getCheckStatus() == AuditEnum.AUDIT_PASS) { // 审核
|
||||
errorDataList.addAll(item.getValue().stream().map(p -> {
|
||||
JSONObject o = JSONObject.from(p);
|
||||
o.put("status", "审核通过状态的不可导入");
|
||||
return o;
|
||||
}).collect(Collectors.toList()));
|
||||
return;
|
||||
}
|
||||
|
||||
if (exportIn.getEnterQuantity() != item.getValue().size()) {
|
||||
errorDataList.addAll(item.getValue().stream().map(p -> {
|
||||
JSONObject o = JSONObject.from(p);
|
||||
o.put("status", "车架号数量和实际货物数量不符合,无法导入");
|
||||
return o;
|
||||
}).collect(Collectors.toList()));
|
||||
return;
|
||||
}
|
||||
|
||||
List<CustomerExportInCargo> cargos = item.getValue().stream().map(p -> {
|
||||
CustomerExportInCargo cargo = new CustomerExportInCargo();
|
||||
cargo.setBrandId(exportIn.getBrandId());
|
||||
cargo.setBrand(exportIn.getBrand());
|
||||
cargo.setExportInId(exportIn.getId());
|
||||
cargo.setCargoType(1);
|
||||
cargo.setVin(p.getVin());
|
||||
cargo.setTermcd(exportIn.getPortAreaId());
|
||||
cargo.setVinStatus(1);
|
||||
return cargo;
|
||||
}).collect(Collectors.toList());
|
||||
|
||||
List<String> vins = cargos.stream().map(p -> p.getVin()).collect(Collectors.toList());
|
||||
|
||||
// 验证哪些车架号已经存在了
|
||||
List<CustomerExportInCargo> existCargos = customerExportInCargoService.list(new LambdaQueryWrapper<CustomerExportInCargo>().in(CustomerExportInCargo::getVin, vins).ne(CustomerExportInCargo::getExportInId, exportIn.getId()));
|
||||
List<String> existVins = existCargos.stream().map(p -> p.getVin()).collect(Collectors.toList());
|
||||
|
||||
if (CollectionUtils.isNotEmpty(existCargos)) {
|
||||
// 查询出对应的港区
|
||||
List<CustomerExportIn> sList = customerExportInService.lambdaQuery().in(CustomerExportIn::getId, existCargos.stream().map(ss -> ss.getExportInId()).collect(Collectors.toList())).list();
|
||||
Map<Long, String> portAreaMap = sList.stream().collect(Collectors.toMap(CustomerExportIn::getId, CustomerExportIn::getPortAreaId));
|
||||
// 通过接口再次验证
|
||||
List<CheckVinReq> req = existCargos.stream().map(ss -> {
|
||||
CheckVinReq v = new CheckVinReq();
|
||||
v.setIsRepetition(true);
|
||||
v.setPamId(portAreaMap.get(ss.getExportInId()));
|
||||
v.setVinCode(ss.getVin());
|
||||
return v;
|
||||
}).collect(Collectors.toList());
|
||||
List<CheckVinReq> rst = shpApi.checkVinRepeat(req);
|
||||
existVins.clear(); // 先清空
|
||||
if (CollectionUtils.isNotEmpty(rst)) {
|
||||
// 再次过滤出重复的
|
||||
List<CheckVinReq> sCollect = rst.stream().filter(ss -> ss.getIsRepetition()).collect(Collectors.toList());
|
||||
if (CollectionUtils.isNotEmpty(sCollect)) {
|
||||
existVins.addAll(sCollect.stream().map(ss -> ss.getVinCode()).collect(Collectors.toList()));
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
List<ExportInBillSpareExcel> existData = item.getValue().stream().filter(p -> existVins.contains(p.getVin())).collect(Collectors.toList());
|
||||
if (CollectionUtils.isNotEmpty(existData)) {
|
||||
errorDataList.addAll(existData.stream().map(p -> {
|
||||
JSONObject o = JSONObject.from(p);
|
||||
o.put("status", "数据已存在, 未导入");
|
||||
return o;
|
||||
|
@ -2481,9 +2938,12 @@ public class ExportInHandler implements BaseHandler {
|
|||
Map<String, DictDTO> portCountryList = new HashMap<>();
|
||||
// 货代列表
|
||||
Map<String, String> companyMap = new HashMap<>();
|
||||
|
||||
// 货物性质
|
||||
List<NuzarDictDTO> goodsNature = dictHandler.getGoodsNature().getData();
|
||||
// 车型明细缓存
|
||||
Map<String, List<DictDTO>> carDetailTypeList = new HashMap<>();
|
||||
// 航次缴存
|
||||
Map<String, List<VoyageResp>> voyageMap = new HashMap<>();
|
||||
|
||||
EasyExcel.read(file.getInputStream(), ExportInPlanExcel.class, new ReadExcelListener<ExportInPlanExcel>() {
|
||||
@Override
|
||||
|
@ -2606,6 +3066,30 @@ public class ExportInHandler implements BaseHandler {
|
|||
errorDataList.add(o);
|
||||
return;
|
||||
}
|
||||
if (goodsNature.stream().filter(p -> StringUtils.equalsIgnoreCase(p.getPtrDesc(), item.getNatureFlagName())).count() == 0) {
|
||||
JSONObject o = JSONObject.from(item);
|
||||
o.put("status", "货物性质不存在");
|
||||
errorDataList.add(o);
|
||||
return;
|
||||
}
|
||||
if (!StringUtils.equals(item.getNatureFlagName(), "正常")) {
|
||||
if (shipList.stream().filter(p -> StringUtils.equalsIgnoreCase(p.getText(), item.getTransferShipName())).count() == 0) {
|
||||
JSONObject o = JSONObject.from(item);
|
||||
o.put("status", "中转进口船名不存在");
|
||||
errorDataList.add(o);
|
||||
return;
|
||||
}
|
||||
if (!voyageMap.containsKey(item.getTransferShipName())) {
|
||||
List<VoyageResp> data = dictHandler.queryVoyageByKey(null, null, null, shipList.stream().filter(p -> StringUtils.equalsIgnoreCase(p.getText(), item.getTransferShipName())).findFirst().get().getId(), null).getData();
|
||||
voyageMap.put(item.getTransferShipName(), data);
|
||||
}
|
||||
if (voyageMap.get(item.getTransferShipName()).stream().filter(p -> StringUtils.equalsIgnoreCase(p.getVvyName(), item.getTransferVoyage())).count() == 0) {
|
||||
JSONObject o = JSONObject.from(item);
|
||||
o.put("status", "中转进口航次不存在");
|
||||
errorDataList.add(o);
|
||||
return;
|
||||
}
|
||||
}
|
||||
Date bDate = DateUtils.parseDate(StringUtils.trim(item.getBeginEnterTime()), "yyyy/MM/dd");
|
||||
if (bDate == null) {
|
||||
JSONObject o = JSONObject.from(item);
|
||||
|
@ -2683,6 +3167,11 @@ public class ExportInHandler implements BaseHandler {
|
|||
in.setApplicantId(UserContext.getUser().getUserId());
|
||||
in.setTermcd(in.getPortAreaId());
|
||||
in.setVolume(in.getLength().multiply(in.getWidth()).multiply(in.getHeight()).setScale(4, RoundingMode.HALF_UP)); // 计算体积
|
||||
in.setNatureFlag(goodsNature.stream().filter(p -> StringUtils.equalsIgnoreCase(p.getPtrDesc(), item.getNatureFlagName())).findFirst().get().getPtrCode());
|
||||
if (!StringUtils.equals(item.getNatureFlagName(), "正常")) {
|
||||
in.setTransferShipId(shipList.stream().filter(p -> StringUtils.equalsIgnoreCase(p.getText(), item.getTransferShipName())).findFirst().get().getId());
|
||||
in.setTransferVoyageId(voyageMap.get(in.getTransferShipName()).stream().filter(p -> StringUtils.equalsIgnoreCase(p.getVvyName(), item.getTransferVoyage())).findFirst().get().getVvyId());
|
||||
}
|
||||
if (in.getEnterQuantity() == null) {
|
||||
in.setEnterQuantity(in.getQuantity());
|
||||
}
|
||||
|
@ -2756,7 +3245,7 @@ public class ExportInHandler implements BaseHandler {
|
|||
|
||||
// 如果是备件自动生成条码
|
||||
// 过滤出是备件的
|
||||
item.getValue().stream().filter(ss -> StringUtils.equals(ss.getCartType(), "备件")).forEach(ss -> {
|
||||
item.getValue().stream().filter(ss -> StringUtils.equals(ss.getCartType(), "备件") && StringUtils.equals(ss.getNatureFlagName(), "正常")).forEach(ss -> {
|
||||
// 判断是否是国际中转航次ID
|
||||
String vvyId = ss.getVoyageId();
|
||||
TransitPartRequest request = new TransitPartRequest();
|
||||
|
|
|
@ -26,6 +26,7 @@ import com.haitonggauto.rtosc.common.utils.ValidationGroup;
|
|||
import com.haitonggauto.rtosc.common.utils.WrapperKit;
|
||||
import com.haitonggauto.rtosc.dto.*;
|
||||
import com.haitonggauto.rtosc.excel.*;
|
||||
import com.haitonggauto.rtosc.handler.excel.CustomCellWriteHandler;
|
||||
import com.haitonggauto.rtosc.query.CargoQuery;
|
||||
import com.haitonggauto.rtosc.query.ExportInCheckQuery;
|
||||
import com.haitonggauto.rtosc.query.ExportLoadCheckQuery;
|
||||
|
@ -1406,7 +1407,20 @@ public class ExportLoadHandler implements BaseHandler {
|
|||
String fileName = URLEncoder.encode("内贸整船车辆导入模板", "UTF-8");
|
||||
response.setHeader("Content-disposition", "attachment;filename=" + fileName + ".xlsx");
|
||||
|
||||
excelWriter = EasyExcel.write(out).build();
|
||||
//普通下拉数据
|
||||
Map<Integer, String[]> map = new HashMap<>();
|
||||
String[] isZgArray = {"是", "否"};
|
||||
map.put(3, isZgArray);
|
||||
//检查类型-子类
|
||||
Map<String, List<String>> inspNameMap = new HashMap<>();
|
||||
//检查类型-父类
|
||||
String[] proInspNameMap = new String[0];
|
||||
//问题属性
|
||||
Map<String, List<String>> probPropsNameMap = new HashMap<>();
|
||||
|
||||
excelWriter = EasyExcel.write(out)
|
||||
.registerWriteHandler(new CustomCellWriteHandler(map, proInspNameMap, inspNameMap, probPropsNameMap))
|
||||
.build();
|
||||
|
||||
WriteSheet writeSheet = EasyExcel.writerSheet(0, "内贸整船车辆导入模板").head(ExportLoadInsideExcel.class).build();
|
||||
|
||||
|
@ -1457,9 +1471,14 @@ public class ExportLoadHandler implements BaseHandler {
|
|||
List<DictDTO> shipList = dictHandler.getAllShip(null).getData();
|
||||
// 港区基础数据
|
||||
List<DictDTO> portAreaList = dictHandler.getPortAreaList(null).getData();
|
||||
// 货物性质
|
||||
List<NuzarDictDTO> goodsNature = dictHandler.getGoodsNature().getData();
|
||||
// 缓存航次信息
|
||||
Map<String, String> voyageMap = new HashMap<>();
|
||||
|
||||
// 缓存中转航次信息
|
||||
Map<String, List<VoyageResp>> transferVoyageMap = new HashMap<>();
|
||||
|
||||
EasyExcel.read(file.getInputStream(), ExportLoadInsideExcel.class, new ReadExcelListener<ExportLoadInsideExcel>() {
|
||||
@Override
|
||||
protected void saveData(List<ExportLoadInsideExcel> list) { // 保存数据
|
||||
|
@ -1541,6 +1560,31 @@ public class ExportLoadHandler implements BaseHandler {
|
|||
errorDataList.add(o);
|
||||
return;
|
||||
}
|
||||
if (goodsNature.stream().filter(p -> StringUtils.equalsIgnoreCase(p.getPtrDesc(), item.getNatureFlagName())).count() == 0) {
|
||||
JSONObject o = JSONObject.from(item);
|
||||
o.put("status", "货物性质不存在");
|
||||
errorDataList.add(o);
|
||||
return;
|
||||
}
|
||||
if (!StringUtils.equals(item.getNatureFlagName(), "正常")) {
|
||||
if (shipList.stream().filter(p -> StringUtils.equalsIgnoreCase(p.getText(), item.getTransferShipName())).count() == 0) {
|
||||
JSONObject o = JSONObject.from(item);
|
||||
o.put("status", "中转进口船名不存在");
|
||||
errorDataList.add(o);
|
||||
return;
|
||||
}
|
||||
if (!transferVoyageMap.containsKey(item.getTransferShipName())) {
|
||||
List<VoyageResp> data = dictHandler.queryVoyageByKey(null, null, null, shipList.stream().filter(p -> StringUtils.equalsIgnoreCase(p.getText(), item.getTransferShipName())).findFirst().get().getId(), null).getData();
|
||||
transferVoyageMap.put(item.getTransferShipName(), data);
|
||||
}
|
||||
if (transferVoyageMap.get(item.getTransferShipName()).stream().filter(p -> StringUtils.equalsIgnoreCase(p.getVvyName(), item.getTransferVoyage())).count() == 0) {
|
||||
JSONObject o = JSONObject.from(item);
|
||||
o.put("status", "中转进口航次不存在");
|
||||
errorDataList.add(o);
|
||||
return;
|
||||
}
|
||||
}
|
||||
|
||||
if (CollectionUtils.containsAny(list, item.getSettleCompName())) {
|
||||
JSONObject o = JSONObject.from(item);
|
||||
o.put("status", "相同提单号需保持结费单位相同");
|
||||
|
@ -1684,6 +1728,11 @@ public class ExportLoadHandler implements BaseHandler {
|
|||
exportLoad.setPortArea(item.getValue().get(0).getPortArea());
|
||||
exportLoad.setContact(item.getValue().get(0).getContact());
|
||||
exportLoad.setContactPhone(item.getValue().get(0).getContactPhone());
|
||||
exportLoad.setNatureFlag(goodsNature.stream().filter(p -> StringUtils.equalsIgnoreCase(p.getPtrDesc(), item.getValue().get(0).getNatureFlagName())).findFirst().get().getPtrCode());
|
||||
if (!StringUtils.equals(item.getValue().get(0).getNatureFlagName(), "正常")) {
|
||||
exportLoad.setTransferShipId(shipList.stream().filter(p -> StringUtils.equalsIgnoreCase(p.getText(), item.getValue().get(0).getTransferShipName())).findFirst().get().getId());
|
||||
exportLoad.setTransferVoyageId(transferVoyageMap.get(exportLoad.getTransferShipName()).stream().filter(p -> StringUtils.equalsIgnoreCase(p.getVvyName(), item.getValue().get(0).getTransferVoyage())).findFirst().get().getVvyId());
|
||||
}
|
||||
if (StringUtils.isNotEmpty(item.getValue().get(0).getDestPort())) { // 内贸目的港可以为空
|
||||
exportLoad.setDestPort(item.getValue().get(0).getDestPort());
|
||||
exportLoad.setDestPortId(portList.stream().filter(s -> StringUtils.equals(s.getText(), item.getValue().get(0).getDestPort())).findFirst().get().getId());
|
||||
|
|
|
@ -0,0 +1,214 @@
|
|||
package com.haitonggauto.rtosc.handler.excel;
|
||||
|
||||
import com.alibaba.excel.write.handler.SheetWriteHandler;
|
||||
import com.alibaba.excel.write.metadata.holder.WriteSheetHolder;
|
||||
import com.alibaba.excel.write.metadata.holder.WriteWorkbookHolder;
|
||||
import org.apache.poi.ss.usermodel.*;
|
||||
import org.apache.poi.ss.util.CellRangeAddressList;
|
||||
|
||||
import java.util.Iterator;
|
||||
import java.util.List;
|
||||
import java.util.Map;
|
||||
|
||||
public class CustomCellWriteHandler implements SheetWriteHandler {
|
||||
/**
|
||||
* 普通下拉数据
|
||||
*/
|
||||
private Map<Integer, String[]> map;
|
||||
|
||||
/**
|
||||
* 检查类型-父类
|
||||
*/
|
||||
private String[] proInspNameArray;
|
||||
|
||||
/**
|
||||
* 检查类型-子类
|
||||
*/
|
||||
private Map<String, List<String>> inspNameArray;
|
||||
|
||||
/**
|
||||
* 问题属性
|
||||
*/
|
||||
private Map<String, List<String>> probPropsNameArray;
|
||||
|
||||
public CustomCellWriteHandler(Map<Integer, String[]> map, String[] proInspNameArray, Map<String, List<String>> inspNameArray, Map<String, List<String>> probPropsNameArray) {
|
||||
this.map = map;
|
||||
this.proInspNameArray = proInspNameArray;
|
||||
this.inspNameArray = inspNameArray;
|
||||
this.probPropsNameArray = probPropsNameArray;
|
||||
}
|
||||
|
||||
@Override
|
||||
public void beforeSheetCreate(WriteWorkbookHolder writeWorkbookHolder, WriteSheetHolder writeSheetHolder) {
|
||||
|
||||
}
|
||||
|
||||
@Override
|
||||
public void afterSheetCreate(WriteWorkbookHolder writeWorkbookHolder, WriteSheetHolder writeSheetHolder) {
|
||||
// 获取第一个sheet页
|
||||
Sheet sheet = writeSheetHolder.getCachedSheet();
|
||||
// 获取sheet页的数据校验对象
|
||||
DataValidationHelper helper = sheet.getDataValidationHelper();
|
||||
// 获取工作簿对象,用于创建存放下拉数据的字典sheet数据页
|
||||
Workbook workbook = writeWorkbookHolder.getWorkbook();
|
||||
|
||||
// 普通数据,迭代索引,用于存放下拉数据的字典sheet数据页命名
|
||||
int index = 1;
|
||||
for (Map.Entry<Integer, String[]> entry : map.entrySet()) {
|
||||
|
||||
// 设置存放下拉数据的字典sheet,并把这些sheet隐藏掉,这样用户交互更友好
|
||||
String dictSheetName = "dict_hide_sheet" + index;
|
||||
Sheet dictSheet = workbook.createSheet(dictSheetName);
|
||||
// 隐藏字典sheet页
|
||||
workbook.setSheetHidden(index++, true);
|
||||
|
||||
// 设置下拉列表覆盖的行数,从第一行开始到最后一行,这里注意,Excel行的
|
||||
// 索引是从0开始的,我这边第0行是标题行,第1行开始时数据化,可根据实
|
||||
// 际业务设置真正的数据开始行,如果要设置到最后一行,那么一定注意,
|
||||
// 最后一行的行索引是1048575,千万别写成1048576,不然会导致下拉列表
|
||||
// 失效,出不来
|
||||
CellRangeAddressList infoList = new CellRangeAddressList(1, 1048575, entry.getKey(), entry.getKey());
|
||||
int rowLen = entry.getValue().length;
|
||||
for (int i = 0; i < rowLen; i++) {
|
||||
// 向字典sheet写数据,从第一行开始写,此处可根据自己业务需要,自定
|
||||
// 义从第几行还是写,写的时候注意一下行索引是从0开始的即可
|
||||
dictSheet.createRow(i).createCell(0).setCellValue(entry.getValue()[i]);
|
||||
}
|
||||
|
||||
// 设置关联数据公式,这个格式跟Excel设置有效性数据的表达式是一样的
|
||||
String refers = dictSheetName + "!$A$1:$A$" + entry.getValue().length;
|
||||
Name name = workbook.createName();
|
||||
name.setNameName(dictSheetName);
|
||||
// 将关联公式和sheet页做关联
|
||||
name.setRefersToFormula(refers);
|
||||
|
||||
// 将上面设置好的下拉列表字典sheet页和目标sheet关联起来
|
||||
DataValidationConstraint constraint = helper.createFormulaListConstraint(dictSheetName);
|
||||
setValidation(sheet, helper, constraint, infoList);
|
||||
}
|
||||
|
||||
|
||||
//检查类型-父类
|
||||
Sheet hideSheet = workbook.createSheet("site");
|
||||
workbook.setSheetHidden(workbook.getSheetIndex(hideSheet), false);
|
||||
// 将具体的数据写入到每一行中,行开头为父级区域,后面是子区域。
|
||||
int rowId = 0;
|
||||
Row proviRow = hideSheet.createRow(rowId++);
|
||||
proviRow.createCell(0).setCellValue("大类列表");
|
||||
for (int i = 0; i < proInspNameArray.length; i++) {
|
||||
Cell proviCell = proviRow.createCell(i + 1);
|
||||
proviCell.setCellValue(proInspNameArray[i]);
|
||||
}
|
||||
//检查类型-子类
|
||||
Iterator<String> keyIterator = inspNameArray.keySet().iterator();
|
||||
while (keyIterator.hasNext()) {
|
||||
String key = keyIterator.next();
|
||||
List<String> son = inspNameArray.get(key);
|
||||
|
||||
Row row = hideSheet.createRow(rowId++);
|
||||
row.createCell(0).setCellValue(key);
|
||||
for (int i = 0; i < son.size(); i++) {
|
||||
Cell cell = row.createCell(i + 1);
|
||||
cell.setCellValue(son.get(i));
|
||||
}
|
||||
// 添加名称管理器
|
||||
String range = getRange(1, rowId, son.size());
|
||||
Name name = workbook.createName();
|
||||
name.setNameName(key);
|
||||
String formula = "site!" + range;
|
||||
name.setRefersToFormula(formula);
|
||||
}
|
||||
|
||||
//问题属性
|
||||
Iterator<String> probPropsNameIterator = probPropsNameArray.keySet().iterator();
|
||||
while (probPropsNameIterator.hasNext()) {
|
||||
String key = probPropsNameIterator.next();
|
||||
List<String> son = probPropsNameArray.get(key);
|
||||
|
||||
Row row = hideSheet.createRow(rowId++);
|
||||
row.createCell(0).setCellValue(key);
|
||||
for (int i = 0; i < son.size(); i++) {
|
||||
Cell cell = row.createCell(i + 1);
|
||||
cell.setCellValue(son.get(i));
|
||||
}
|
||||
// 添加名称管理器
|
||||
String range = getRange(1, rowId, son.size());
|
||||
Name name = workbook.createName();
|
||||
name.setNameName(key);
|
||||
String formula = "site!" + range;
|
||||
name.setRefersToFormula(formula);
|
||||
}
|
||||
|
||||
///开始设置(大类小类)下拉框
|
||||
DataValidationHelper dvHelper = sheet.getDataValidationHelper();
|
||||
// 大类规则
|
||||
DataValidationConstraint expConstraint = dvHelper.createExplicitListConstraint(proInspNameArray);
|
||||
CellRangeAddressList expRangeAddressList = new CellRangeAddressList(1, 1048575, 3, 3);
|
||||
setValidation(sheet, dvHelper, expConstraint, expRangeAddressList);
|
||||
|
||||
//检查类型-子类
|
||||
// 小类规则(各单元格按个设置)
|
||||
// "INDIRECT($A$" + 2 + ")" 表示规则数据会从名称管理器中获取key与单元格 A2 值相同的数据,如果A2是浙江省,那么此处就是浙江省下面的市
|
||||
// 为了让每个单元格的公式能动态适应,使用循环挨个给公式。
|
||||
// 循环几次,就有几个单元格生效,次数要和上面的大类影响行数一一对应,要不然最后几个没对上的单元格实现不了级联
|
||||
for (int i = 2; i < inspNameArray.size() + 10; i++) {
|
||||
CellRangeAddressList rangeAddressList = new CellRangeAddressList(i-1 , i-1, 4, 4);
|
||||
DataValidationConstraint formula = dvHelper.createFormulaListConstraint("INDIRECT($D$" + i + ")");
|
||||
setValidation(sheet, dvHelper, formula, rangeAddressList);
|
||||
}
|
||||
|
||||
//问题属性
|
||||
for (int i = 2; i < probPropsNameArray.size() + 10; i++) {
|
||||
CellRangeAddressList rangeAddressList = new CellRangeAddressList(i-1 , i-1, 5, 5);
|
||||
DataValidationConstraint formula = dvHelper.createFormulaListConstraint("INDIRECT($E$" + i + ")");
|
||||
setValidation(sheet, dvHelper, formula, rangeAddressList);
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* 设置验证规则
|
||||
* @param sheet sheet对象
|
||||
* @param helper 验证助手
|
||||
* @param constraint createExplicitListConstraint
|
||||
* @param addressList 验证位置对象
|
||||
*/
|
||||
private void setValidation(Sheet sheet, DataValidationHelper helper, DataValidationConstraint constraint, CellRangeAddressList addressList) {
|
||||
DataValidation dataValidation = helper.createValidation(constraint, addressList);
|
||||
dataValidation.createErrorBox("错误提示", "您输入的内容,不符合限制条件");
|
||||
sheet.addValidationData(dataValidation);
|
||||
}
|
||||
|
||||
/**
|
||||
* @param offset 偏移量,如果给0,表示从A列开始,1,就是从B列
|
||||
* @param rowId 第几行
|
||||
* @param colCount 一共多少列
|
||||
* @return 如果给入参 1,1,10. 表示从B1-K1。最终返回 $B$1:$K$1
|
||||
* @author denggonghai 2016年8月31日 下午5:17:49
|
||||
*/
|
||||
public String getRange(int offset, int rowId, int colCount) {
|
||||
char start = (char) ('A' + offset);
|
||||
if (colCount <= 25) {
|
||||
char end = (char) (start + colCount - 1);
|
||||
return "$" + start + "$" + rowId + ":$" + end + "$" + rowId;
|
||||
} else {
|
||||
char endPrefix = 'A';
|
||||
char endSuffix = 'A';
|
||||
if ((colCount - 25) / 26 == 0 || colCount == 51) {// 26-51之间,包括边界(仅两次字母表计算)
|
||||
if ((colCount - 25) % 26 == 0) {// 边界值
|
||||
endSuffix = (char) ('A' + 25);
|
||||
} else {
|
||||
endSuffix = (char) ('A' + (colCount - 25) % 26 - 1);
|
||||
}
|
||||
} else {// 51以上
|
||||
if ((colCount - 25) % 26 == 0) {
|
||||
endSuffix = (char) ('A' + 25);
|
||||
endPrefix = (char) (endPrefix + (colCount - 25) / 26 - 1);
|
||||
} else {
|
||||
endSuffix = (char) ('A' + (colCount - 25) % 26 - 1);
|
||||
endPrefix = (char) (endPrefix + (colCount - 25) / 26);
|
||||
}
|
||||
}
|
||||
return "$" + start + "$" + rowId + ":$" + endPrefix + endSuffix + "$" + rowId;
|
||||
}
|
||||
}
|
||||
}
|
Binary file not shown.
|
@ -70,6 +70,30 @@ public class CustomerExportIn extends BaseEntity implements Serializable {
|
|||
@EsLogMean(name = "航次", title = true)
|
||||
private String voyage;
|
||||
|
||||
@TableField(value = "nature_flag")
|
||||
@ApiModelProperty(value = "货物性质ID")
|
||||
private String natureFlag;
|
||||
|
||||
@TableField(value = "nature_flag_name")
|
||||
@ApiModelProperty(value = "货物性质名称")
|
||||
private String natureFlagName;
|
||||
|
||||
@TableField(value = "transfer_ship_id")
|
||||
@ApiModelProperty(value = "中转船ID")
|
||||
private String transferShipId;
|
||||
|
||||
@TableField(value = "transfer_ship_name")
|
||||
@ApiModelProperty(value = "中转船名")
|
||||
private String transferShipName;
|
||||
|
||||
@TableField(value = "transfer_voyage_id")
|
||||
@ApiModelProperty(value = "中转航次ID")
|
||||
private String transferVoyageId;
|
||||
|
||||
@TableField(value = "transfer_voyage")
|
||||
@ApiModelProperty(value = "中转航次名")
|
||||
private String transferVoyage;
|
||||
|
||||
/**
|
||||
* 港区ID
|
||||
*/
|
||||
|
|
|
@ -76,6 +76,30 @@ public class CustomerExportLoad extends BaseEntity implements Serializable {
|
|||
@EsLogMean(name = "航次", title = true)
|
||||
private String voyage;
|
||||
|
||||
@TableField(value = "nature_flag")
|
||||
@ApiModelProperty(value = "货物性质ID")
|
||||
private String natureFlag;
|
||||
|
||||
@TableField(value = "nature_flag_name")
|
||||
@ApiModelProperty(value = "货物性质名称")
|
||||
private String natureFlagName;
|
||||
|
||||
@TableField(value = "transfer_ship_id")
|
||||
@ApiModelProperty(value = "中转船ID")
|
||||
private String transferShipId;
|
||||
|
||||
@TableField(value = "transfer_ship_name")
|
||||
@ApiModelProperty(value = "中转船名")
|
||||
private String transferShipName;
|
||||
|
||||
@TableField(value = "transfer_voyage_id")
|
||||
@ApiModelProperty(value = "中转航次ID")
|
||||
private String transferVoyageId;
|
||||
|
||||
@TableField(value = "transfer_voyage")
|
||||
@ApiModelProperty(value = "中转航次名")
|
||||
private String transferVoyage;
|
||||
|
||||
/**
|
||||
* 港区ID
|
||||
*/
|
||||
|
|
Loading…
Reference in New Issue