Commit 17b75a20 sunke

启动时只加载未被取消(隐藏)的任务,放上小车时,如果任务已被取消,直接NG

出库,入库,发料时如果通知Qisda失败,自动进行重发
修复分过盘的料入库时从紧急出料口出的问题
1 个父辈 c9cde554
...@@ -20,6 +20,11 @@ public class DataLog extends BaseMongoBean /*implements Comparable<DataLog>*/ { ...@@ -20,6 +20,11 @@ public class DataLog extends BaseMongoBean /*implements Comparable<DataLog>*/ {
* 是否是单盘出库(联电指出库项目,默认为false即默认批量出库) * 是否是单盘出库(联电指出库项目,默认为false即默认批量出库)
*/ */
private boolean singleOut = false; private boolean singleOut = false;
/**
* 是否停止向Qisda发料(已经发送过E状态的任务)
*/
private boolean stopSendToQisda = false;
/** /**
* 所属料仓 * 所属料仓
*/ */
...@@ -311,6 +316,18 @@ public class DataLog extends BaseMongoBean /*implements Comparable<DataLog>*/ { ...@@ -311,6 +316,18 @@ public class DataLog extends BaseMongoBean /*implements Comparable<DataLog>*/ {
return StorageConstants.OP_STATUS.CANCEL.name().equals(status); return StorageConstants.OP_STATUS.CANCEL.name().equals(status);
} }
/**
* 是否停止向Qisda发送消息
*/
public boolean isStopSendToQisda() {
return stopSendToQisda;
}
public void setStopSendToQisda(boolean stopSendToQisda) {
this.stopSendToQisda = stopSendToQisda;
}
public boolean isExecuting(){ public boolean isExecuting(){
return StorageConstants.OP_STATUS.EXECUTING.name().equals(status); return StorageConstants.OP_STATUS.EXECUTING.name().equals(status);
} }
......
...@@ -111,16 +111,18 @@ public class DataLogDaoImpl extends AbstractMongoDao implements IDataLogDao { ...@@ -111,16 +111,18 @@ public class DataLogDaoImpl extends AbstractMongoDao implements IDataLogDao {
@Override @Override
public List<DataLog> findUnFinishedTasks(String executingHSerial){ public List<DataLog> findUnFinishedTasks(String executingHSerial){
Criteria c = Criteria.where("appendInfo.hSerial").is(executingHSerial).and("lessSendReel").is(false).and("status").nin(StorageConstants.OP_STATUS.FINISHED.name(),StorageConstants.OP_STATUS.CANCEL.name()); //Criteria c = Criteria.where("appendInfo.hSerial").is(executingHSerial).and("lessSendReel").is(false).and("status").nin(StorageConstants.OP_STATUS.FINISHED.name(),StorageConstants.OP_STATUS.CANCEL.name());
Criteria c = Criteria.where("status").nin(StorageConstants.OP_STATUS.FINISHED.name(),StorageConstants.OP_STATUS.CANCEL.name()).and("stopSendToQisda").is(false);
Query query = Query.query(c); Query query = Query.query(c);
List<DataLog> unFinishedTasks = findByQuery(query); List<DataLog> unFinishedTasks = findByQuery(query);
if(unFinishedTasks == null){ if(unFinishedTasks == null){
unFinishedTasks = new ArrayList<>(); unFinishedTasks = new ArrayList<>();
} }
List<DataLog> unExecuteTasks = findUnExecuteTasks(executingHSerial); // List<DataLog> unExecuteTasks = findUnExecuteTasks(executingHSerial);
for (DataLog unExecuteTask : unExecuteTasks) { // for (DataLog unExecuteTask : unExecuteTasks) {
unFinishedTasks.add(unExecuteTask); // unFinishedTasks.add(unExecuteTask);
} // }
return unFinishedTasks; return unFinishedTasks;
} }
......
...@@ -202,7 +202,30 @@ public final class DateUtil { ...@@ -202,7 +202,30 @@ public final class DateUtil {
} }
public static void main(String args[]) throws Exception { public static void main(String args[]) throws Exception {
List<Date> list = new ArrayList<>();
Calendar c = Calendar.getInstance();
c.set(Calendar.DAY_OF_YEAR,5);
list.add(c.getTime());
c.set(Calendar.DAY_OF_YEAR,3);
list.add(c.getTime());
c.set(Calendar.DAY_OF_YEAR,2);
list.add(c.getTime());
c.set(Calendar.DAY_OF_YEAR,1);
list.add(c.getTime());
c.set(Calendar.DAY_OF_YEAR,4);
list.add(c.getTime());
list.sort(new Comparator<Date>() {
@Override
public int compare(Date o1, Date o2) {
//按优先级排序,如果没有优先级,使用
return o1.compareTo(o2);
}
});
for (Date date : list) {
System.out.println(DateUtil.toDateString(date));
}
} }
} }
...@@ -4,6 +4,7 @@ import com.google.common.base.Strings; ...@@ -4,6 +4,7 @@ import com.google.common.base.Strings;
import com.google.common.collect.Lists; import com.google.common.collect.Lists;
import com.myproject.bean.qisda.AppendInfo; import com.myproject.bean.qisda.AppendInfo;
import com.myproject.bean.qisda.DiffInfo; import com.myproject.bean.qisda.DiffInfo;
import com.myproject.bean.qisda.QisdaApiRequest;
import com.myproject.bean.update.Barcode; import com.myproject.bean.update.Barcode;
import com.myproject.bean.update.DataLog; import com.myproject.bean.update.DataLog;
import com.myproject.bean.update.qisda.DNInfo; import com.myproject.bean.update.qisda.DNInfo;
...@@ -11,6 +12,7 @@ import com.myproject.bean.update.qisda.DNItem; ...@@ -11,6 +12,7 @@ import com.myproject.bean.update.qisda.DNItem;
import com.myproject.bean.update.qisda.OutItem; import com.myproject.bean.update.qisda.OutItem;
import com.myproject.exception.ApiException; import com.myproject.exception.ApiException;
import com.myproject.exception.ValidateException; import com.myproject.exception.ValidateException;
import com.myproject.webapp.controller.webService.QisdaCache;
import org.apache.logging.log4j.LogManager; import org.apache.logging.log4j.LogManager;
import org.apache.logging.log4j.Logger; import org.apache.logging.log4j.Logger;
...@@ -353,12 +355,16 @@ public class QisdaApi { ...@@ -353,12 +355,16 @@ public class QisdaApi {
paramMap.put("location",location); paramMap.put("location",location);
paramMap.put("userName",USER_NAME); paramMap.put("userName",USER_NAME);
log.info("纯入库操作完成时通知Qisda接口(VMILocationIn):reelID=" + reelID + "&location="+location); log.info("纯入库操作完成时通知Qisda接口(VMILocationIn):reelID=" + reelID + "&location="+location);
QisdaApiRequest apiRequest = new QisdaApiRequest("纯入库",paramMap,reelID,url);
try { try {
String result = HttpHelper.postParam(url,paramMap); String result = HttpHelper.postParam(url,paramMap);
log.info(reelID + "纯入库操作完成时通知Qisda接口(VMILocationIn)返回:" + result); log.info(reelID + "纯入库操作完成时通知Qisda接口(VMILocationIn)返回:" + result);
} catch (ApiException e) { QisdaCache.removeFailedRequest(apiRequest);
return;
} catch (Exception e) {
log.error(reelID + "纯入库操作完成时通知Qisda接口(VMILocationIn)出错",e); log.error(reelID + "纯入库操作完成时通知Qisda接口(VMILocationIn)出错",e);
} }
QisdaCache.addFailedRequest(apiRequest);
} }
/** /**
...@@ -371,7 +377,7 @@ public class QisdaApi { ...@@ -371,7 +377,7 @@ public class QisdaApi {
materialInfoMap.put("dnOrFacility",barcode.getAppendInfo().getDnOrFacility());//DN单号或者是厂别 materialInfoMap.put("dnOrFacility",barcode.getAppendInfo().getDnOrFacility());//DN单号或者是厂别
materialInfoMap.put("reelID",barcode.getBarcode());//料卷ID materialInfoMap.put("reelID",barcode.getBarcode());//料卷ID
materialInfoMap.put("partNum",barcode.getPartNumber());//料号 materialInfoMap.put("partNum",barcode.getPartNumber());//料号
materialInfoMap.put("qty",barcode.getAmount() + "");//数量 materialInfoMap.put("qty",barcode.getInitialAmount() + "");//数量
materialInfoMap.put("lifeCycle",barcode.getLifeCycle());//生命周期 materialInfoMap.put("lifeCycle",barcode.getLifeCycle());//生命周期
String productCode = DateUtil.toDateString(barcode.getProduceDate(),"yyyyMMdd"); String productCode = DateUtil.toDateString(barcode.getProduceDate(),"yyyyMMdd");
materialInfoMap.put("productCode",productCode);//生产日期 materialInfoMap.put("productCode",productCode);//生产日期
...@@ -388,12 +394,17 @@ public class QisdaApi { ...@@ -388,12 +394,17 @@ public class QisdaApi {
paramMap.put("materialInfo",materialInfo); paramMap.put("materialInfo",materialInfo);
paramMap.put("userName",USER_NAME); paramMap.put("userName",USER_NAME);
log.info("DN单收料或Facility收料通知Qisda接口(VMIMateriaReceive):" + materialInfo); log.info("DN单收料或Facility收料通知Qisda接口(VMIMateriaReceive):" + materialInfo);
QisdaApiRequest apiRequest = new QisdaApiRequest("收料入库",paramMap,barcode.getBarcode(),url);
try { try {
String result = HttpHelper.postParam(url,paramMap); String result = HttpHelper.postParam(url,paramMap);
log.info("DN单收料或Facility收料["+barcode.getBarcode()+"]接口返回:" + result); log.info("DN单收料或Facility收料["+barcode.getBarcode()+"]接口返回:" + result);
} catch (ApiException e) { QisdaCache.removeFailedRequest(apiRequest);
return;
} catch (Exception e) {
log.error("DN单收料或Facility收料接口出错",e); log.error("DN单收料或Facility收料接口出错",e);
} }
QisdaCache.addFailedRequest(apiRequest);
} }
...@@ -401,7 +412,7 @@ public class QisdaApi { ...@@ -401,7 +412,7 @@ public class QisdaApi {
* 出仓完成时通知 * 出仓完成时通知
* @param materialInfoMap * @param materialInfoMap
*/ */
public static void VMILocationOut(Map<String, Object> materialInfoMap){ public static void VMILocationOut(String reelId, Map<String, Object> materialInfoMap){
String url = "http://10.85.17.233/ESMTCommonInterface/CommonService.asmx/VMILocationOut"; String url = "http://10.85.17.233/ESMTCommonInterface/CommonService.asmx/VMILocationOut";
String materialInfo = JsonUtil.toJsonStr(materialInfoMap); String materialInfo = JsonUtil.toJsonStr(materialInfoMap);
...@@ -409,13 +420,16 @@ public class QisdaApi { ...@@ -409,13 +420,16 @@ public class QisdaApi {
paramMap.put("materialInfo",materialInfo); paramMap.put("materialInfo",materialInfo);
paramMap.put("userName",USER_NAME); paramMap.put("userName",USER_NAME);
log.info("出仓完成时通知Qisda:materialInfo=" + materialInfo); log.info("出仓完成时通知Qisda:materialInfo=" + materialInfo);
QisdaApiRequest apiRequest = new QisdaApiRequest("出仓",paramMap,reelId,url);
try { try {
String result = HttpHelper.postParam(url,paramMap); String result = HttpHelper.postParam(url,paramMap);
log.info("出仓完成时通知Qisda(VMILocationOut)返回:" + result); log.info("出仓完成时通知Qisda(VMILocationOut)返回:" + result);
} catch (ApiException e) { QisdaCache.removeFailedRequest(apiRequest);
return;
} catch (Exception e) {
log.error("出仓完成时通知Qisda(VMILocationOut)接口出错",e); log.error("出仓完成时通知Qisda(VMILocationOut)接口出错",e);
} }
QisdaCache.addFailedRequest(apiRequest);
} }
...@@ -473,13 +487,16 @@ public class QisdaApi { ...@@ -473,13 +487,16 @@ public class QisdaApi {
paramMap.put("materialInfo",materialInfo); paramMap.put("materialInfo",materialInfo);
paramMap.put("userName",USER_NAME); paramMap.put("userName",USER_NAME);
log.info("物料放上小车时通知Qisda:materialInfo=" + materialInfo); log.info("物料放上小车时通知Qisda:materialInfo=" + materialInfo);
QisdaApiRequest apiRequest = new QisdaApiRequest("发料",paramMap,task.getBarcode(),url);
try { try {
String result = HttpHelper.postParam(url,paramMap); String result = HttpHelper.postParam(url,paramMap);
log.info(task.getBarcode() + "物料放上小车时通知Qisda(VMIMateriaRecAss)返回:" + result); log.info(task.getBarcode() + "物料放上小车时通知Qisda(VMIMateriaRecAss)返回:" + result);
} catch (ApiException e) { QisdaCache.removeFailedRequest(apiRequest);
return;
} catch (Exception e) {
log.error(task.getBarcode() + "物料放上小车时通知Qisda(VMIMateriaRecAss)接口出错",e); log.error(task.getBarcode() + "物料放上小车时通知Qisda(VMIMateriaRecAss)接口出错",e);
} }
QisdaCache.addFailedRequest(apiRequest);
} }
......
...@@ -66,13 +66,18 @@ public class DifferentInventoryController extends BaseController { ...@@ -66,13 +66,18 @@ public class DifferentInventoryController extends BaseController {
public String dnIn(HttpServletRequest request) throws ApiException { public String dnIn(HttpServletRequest request) throws ApiException {
String file = request.getParameter("file"); String file = request.getParameter("file");
Map<String,DiffInfo> qisdaReelMap = null; Map<String,DiffInfo> qisdaReelMap = new HashMap<>();
if(!Strings.isNullOrEmpty(file)){ if(!Strings.isNullOrEmpty(file)){
log.info("开始比对:" + file); log.info("开始比对:" + file);
qisdaReelMap = readQisda(file); qisdaReelMap = readQisda(file);
}else{ }else{
log.info("开始与Qisda比对库存"); try {
qisdaReelMap = QisdaApi.getInventory(); log.info("开始与Qisda比对库存");
qisdaReelMap = QisdaApi.getInventory();
}catch (Exception e){
log.info("获取Qisda库存出错:",e);
}
} }
List<StoragePos> posList = storagePosManager.findNotEmpty(); List<StoragePos> posList = storagePosManager.findNotEmpty();
......
...@@ -66,16 +66,25 @@ public class OutInfoCache { ...@@ -66,16 +66,25 @@ public class OutInfoCache {
@Autowired @Autowired
protected IComponentManager componentManager; protected IComponentManager componentManager;
private boolean isProcessTimer = false;
/** /**
* 定时器,每3秒执行一次 * 定时器,每3秒执行一次
*/ */
public void runTimer(){ public void runTimer(){
if(!dataCache.getSettings().isStopJob()){ if(!isProcessTimer){
updateMustExeOutInfo(); isProcessTimer = true;
executeBindTask(); try {
executeOutTask(); if(!dataCache.getSettings().isStopJob()){
updateMustExeOutInfo();
executeBindTask();
executeOutTask();
}
}catch (Exception e){
log.error("需求单定时器执行出错:",e);
}finally {
isProcessTimer = false;
}
} }
} }
/** /**
...@@ -98,23 +107,25 @@ public class OutInfoCache { ...@@ -98,23 +107,25 @@ public class OutInfoCache {
if(cutItem.isCutMaterial()){ if(cutItem.isCutMaterial()){
int preBindQty = cutItem.getLockQty(); int preBindQty = cutItem.getLockQty();
if(!isCutReelIn){ if(!isCutReelIn){
//不是分完盘入库的,需要先进行预绑定
preBindQty = cutItem.getLockQty() + barcode.getAmount(); preBindQty = cutItem.getLockQty() + barcode.getAmount();
} if(preBindQty > cutItem.getQty()){
if(preBindQty >= cutItem.getQty()){ int reelRemainNum = barcode.cutCount(cutItem);
int reelRemainNum = barcode.cutCount(cutItem); if(reelRemainNum > 0){
if(reelRemainNum > 0){ //母盘还有剩余,说明该需求slot已经满足
//母盘还有剩余,说明该需求slot已经满足 preBindQty = cutItem.getQty();
preBindQty = cutItem.getQty(); }else {
}else { //母盘正好用完或全部用完也达不到需求量,此母盘绑定slot后,需要继续寻找其他盘进行绑定
//母盘正好用完或全部用完也达不到需求量,此母盘绑定slot后,需要继续寻找其他盘进行绑定 preBindQty = preBindQty + barcode.getAmount();
preBindQty = preBindQty + barcode.getAmount(); }
} }
} cutItem.setLockQty(preBindQty);
cutItem.setLockQty(preBindQty); soseqCache.udpateTotalPreLockQty(cutItem,preBindQty);
soseqCache.udpateTotalPreLockQty(cutItem,preBindQty);
log.info("\t分盘料["+barcode.getBarcode()+"]绑定到Soseq=["+cutItem.getSoseq()+"]So=["+cutItem.getSo()+"]的["+cutItem.getSlotlocation()+"] 数量:" + preBindQty +"/" + cutItem.getQty()); log.info("\t分盘料["+barcode.getBarcode()+"]绑定到Soseq=["+cutItem.getSoseq()+"]So=["+cutItem.getSo()+"]的["+cutItem.getSlotlocation()+"] 数量:" + preBindQty +"/" + cutItem.getQty());
}
if(!barcode.hasCutInfo()){ if(!barcode.hasCutInfo()){
//没有分盘信息,可以直接绑定 //没有分盘信息,可以直接绑定
barcode.realBindItem(cutItem); barcode.realBindItem(cutItem);
......
...@@ -55,7 +55,7 @@ public class MainTimer { ...@@ -55,7 +55,7 @@ public class MainTimer {
qisdaCache.initRfidDnMap(); qisdaCache.initRfidDnMap();
InquiryShelfBean.initShelfMap(); InquiryShelfBean.initShelfMap();
QisdaCache.initApiRequestMap();
outInfoCache.loadUnEndOutInfos(); outInfoCache.loadUnEndOutInfos();
......
...@@ -344,10 +344,10 @@ public class QisdaApiController extends BaseController { ...@@ -344,10 +344,10 @@ public class QisdaApiController extends BaseController {
materialInfoMap.put("slotserial", slotlocation + ""); materialInfoMap.put("slotserial", slotlocation + "");
log.info(barcode.getBarcode() + "发送分盘料信息:" + cutItem); log.info(barcode.getBarcode() + "发送分盘料信息:" + cutItem);
QisdaApi.VMILocationOut(materialInfoMap); QisdaApi.VMILocationOut(barcode.getBarcode(),materialInfoMap);
} }
}else{ }else{
QisdaApi.VMILocationOut(materialInfoMap); QisdaApi.VMILocationOut(barcode.getBarcode(), materialInfoMap);
} }
} }
......
...@@ -94,7 +94,7 @@ public class QisdaBindService { ...@@ -94,7 +94,7 @@ public class QisdaBindService {
*/ */
private void preBindReel(OutItem outItem){ private void preBindReel(OutItem outItem){
if(!outItem.isCutMaterial()){ if(!outItem.isCutMaterial()){
log.info("预绑定非分盘料:So=["+outItem.getSo()+"]hSerial=["+outItem.gethSerial()+"]+refno=["+outItem.getRefno()+"]的slot"+outItem.getSlotlocation()+"]pn=["+outItem.getPn()+"]当前预绑定数量["+outItem.getLockQty()+"/"+outItem.getQty()+"]"); log.info("预绑定非分盘料:So=["+outItem.getSo()+"]hSerial=["+outItem.getSourceName()+"]pn=["+outItem.getPn()+"]当前预绑定数量["+outItem.getLockQty()+"/"+outItem.getQty()+"]");
while (true){ while (true){
StoragePos pos = storagePosDao.findNoBindMinQty(outItem.getPn(), outItem.getFacility()); StoragePos pos = storagePosDao.findNoBindMinQty(outItem.getPn(), outItem.getFacility());
if(pos == null){ if(pos == null){
...@@ -104,7 +104,7 @@ public class QisdaBindService { ...@@ -104,7 +104,7 @@ public class QisdaBindService {
int dbQty = pos.getBarcode().getAmount(); int dbQty = pos.getBarcode().getAmount();
int lockQty = outItem.getLockQty(); int lockQty = outItem.getLockQty();
int newLockQty = lockQty + dbQty; int newLockQty = lockQty + dbQty;
log.info("\t预绑定["+pos.getBarcode().getBarcode()+"]到So=["+outItem.getSo()+"]hSerial=["+outItem.gethSerial()+"]refno=["+outItem.getRefno()+"]的["+outItem.getSlotlocation()+"] 数量:" + newLockQty +"/" + outItem.getQty()); log.info("\t预绑定["+pos.getBarcode().getBarcode()+"]到hSerial=["+outItem.getSourceName()+"] 数量:" + newLockQty +"/" + outItem.getQty());
Barcode barcode = pos.getBarcode(); Barcode barcode = pos.getBarcode();
// AppendInfo appendInfo = barcode.getAppendInfo(); // AppendInfo appendInfo = barcode.getAppendInfo();
// appendInfo.sethSerial(outItem.gethSerial()); // appendInfo.sethSerial(outItem.gethSerial());
...@@ -126,7 +126,7 @@ public class QisdaBindService { ...@@ -126,7 +126,7 @@ public class QisdaBindService {
StoragePos needToUnBindPos = storagePosDao.findSurplusPreBindReel(outItem.getSoseq(), outItem.getSlotlocation(), surplusQty, barcode.getProduceDateStr()); StoragePos needToUnBindPos = storagePosDao.findSurplusPreBindReel(outItem.getSoseq(), outItem.getSlotlocation(), surplusQty, barcode.getProduceDateStr());
if(needToUnBindPos != null){ if(needToUnBindPos != null){
int unbindAmount = needToUnBindPos.getBarcode().getAmount(); int unbindAmount = needToUnBindPos.getBarcode().getAmount();
log.info("找到与最大料盘["+barcode.getBarcode()+"]相同日期["+barcode.getProduceDateStr()+"]与超绑数量["+surplusQty+"]接近的料盘["+needToUnBindPos.getBarcode().getBarcode()+"]数量为["+unbindAmount+"]解除预绑定"); log.info(outItem.getSourceName() + "找到与最大料盘["+barcode.getBarcode()+"]相同日期["+barcode.getProduceDateStr()+"]与超绑数量["+surplusQty+"]接近的料盘["+needToUnBindPos.getBarcode().getBarcode()+"]数量为["+unbindAmount+"]解除预绑定");
storagePosDao.unbindReel(needToUnBindPos); storagePosDao.unbindReel(needToUnBindPos);
newLockQty = newLockQty - unbindAmount; newLockQty = newLockQty - unbindAmount;
outItem.setLockQty(newLockQty); outItem.setLockQty(newLockQty);
...@@ -166,7 +166,7 @@ public class QisdaBindService { ...@@ -166,7 +166,7 @@ public class QisdaBindService {
} }
if(!barcode.hasCutInfo()){ if(!barcode.hasCutInfo()){
log.info("\t第一轮绑定分盘料["+barcode.getBarcode()+"]绑定到So=["+outItem.getSo()+"]hSerial=["+outItem.gethSerial()+"]refno=["+outItem.getRefno()+"]的["+outItem.getSlotlocation()+"] 数量:" + totalLockQty +"/" + outItem.getQty()); log.info("\t第一轮绑定分盘料["+barcode.getBarcode()+"]绑定到So=["+outItem.getSo()+"]hSerial=["+outItem.getSourceName()+"] 数量:" + totalLockQty +"/" + outItem.getQty());
//没有分盘信息,可以直接绑定 //没有分盘信息,可以直接绑定
// AppendInfo appendInfo = barcode.getAppendInfo(); // AppendInfo appendInfo = barcode.getAppendInfo();
// appendInfo.sethSerial(outItem.gethSerial()); // appendInfo.sethSerial(outItem.gethSerial());
...@@ -228,7 +228,7 @@ public class QisdaBindService { ...@@ -228,7 +228,7 @@ public class QisdaBindService {
//母盘正好用完或全部用完也达不到需求量,此母盘绑定slot后,继续寻找其他盘进行绑定 //母盘正好用完或全部用完也达不到需求量,此母盘绑定slot后,继续寻找其他盘进行绑定
lockQty = lockQty + barcode.getAmount(); lockQty = lockQty + barcode.getAmount();
} }
log.info("\t分盘料["+barcode.getBarcode()+"]绑定到Soseq=["+outItem.getSoseq()+"]So=["+outItem.getSo()+"]hSerial=["+outItem.gethSerial()+"]refno=["+outItem.getRefno()+"]的["+outItem.getSlotlocation()+"] 数量:" + lockQty +"/" + outItem.getQty()); log.info("\t分盘料["+barcode.getBarcode()+"]绑定到So=["+outItem.getSo()+"]hSerial=["+outItem.getSourceName()+"]数量:" + lockQty +"/" + outItem.getQty());
if(!barcode.hasCutInfo()){ if(!barcode.hasCutInfo()){
//没有分盘信息,可以直接绑定 //没有分盘信息,可以直接绑定
// AppendInfo appendInfo = barcode.getAppendInfo(); // AppendInfo appendInfo = barcode.getAppendInfo();
...@@ -320,7 +320,7 @@ public class QisdaBindService { ...@@ -320,7 +320,7 @@ public class QisdaBindService {
unbindSurplusReel(outItem); unbindSurplusReel(outItem);
//首盘,如果此站位一盘也没有,查找是否有同工单不同站位的PN,如果有,抢一盘过来 //首盘,如果此站位一盘也没有,查找是否有同工单不同站位的PN,如果有,抢一盘过来
log.info("So=["+outItem.getSo()+"]hSerial=["+outItem.gethSerial()+"]+refno=["+outItem.getRefno()+"]的slot"+outItem.getSlotlocation()+"]pn=["+outItem.getPn()+"]真实绑定结束,当前数量:"+outItem.getSendQty()+"+"+ outItem.getRealLockQty() +"/" + outItem.getQty()); log.info("So=["+outItem.getSo()+"]hSerial=["+outItem.getSourceName()+"]pn=["+outItem.getPn()+"]真实绑定结束,当前数量:"+outItem.getSendQty()+"+"+ outItem.getRealLockQty() +"/" + outItem.getQty());
} }
} }
...@@ -338,7 +338,7 @@ public class QisdaBindService { ...@@ -338,7 +338,7 @@ public class QisdaBindService {
StoragePos needToUnBindPos = storagePosDao.findSurplusBindReel(outItem.getSoseq(), outItem.getSlotlocation(), surplusQty, maxQtyBindReelBarcode.getProduceDateStr()); StoragePos needToUnBindPos = storagePosDao.findSurplusBindReel(outItem.getSoseq(), outItem.getSlotlocation(), surplusQty, maxQtyBindReelBarcode.getProduceDateStr());
if(needToUnBindPos != null){ if(needToUnBindPos != null){
int unbindAmount = needToUnBindPos.getBarcode().getAmount(); int unbindAmount = needToUnBindPos.getBarcode().getAmount();
log.info("找到与最大料盘["+maxQtyBindReelBarcode.getBarcode()+"]相同日期["+maxQtyBindReelBarcode.getProduceDateStr()+"]与超绑数量["+surplusQty+"]接近的料盘["+needToUnBindPos.getBarcode().getBarcode()+"]数量为["+unbindAmount+"]解除绑定"); log.info(outItem.getSourceName() + "找到与最大料盘["+maxQtyBindReelBarcode.getBarcode()+"]相同日期["+maxQtyBindReelBarcode.getProduceDateStr()+"]与超绑数量["+surplusQty+"]接近的料盘["+needToUnBindPos.getBarcode().getBarcode()+"]数量为["+unbindAmount+"]解除绑定");
storagePosDao.unbindReel(needToUnBindPos); storagePosDao.unbindReel(needToUnBindPos);
int newRealLockQty = outItem.getRealLockQty() - unbindAmount; int newRealLockQty = outItem.getRealLockQty() - unbindAmount;
outItem.setRealLockQty(newRealLockQty); outItem.setRealLockQty(newRealLockQty);
...@@ -375,14 +375,14 @@ public class QisdaBindService { ...@@ -375,14 +375,14 @@ public class QisdaBindService {
if(Strings.isNotBlank(oldBindSlotStr)){ if(Strings.isNotBlank(oldBindSlotStr)){
int oldBindSlot = Integer.valueOf(oldBindSlotStr); int oldBindSlot = Integer.valueOf(oldBindSlotStr);
if(oldBindSlot > 0){ if(oldBindSlot > 0){
log.error("\t真实绑定"+outItem.getSlotlocation() + "的pn=["+outItem.getPn()+"]facility = "+outItem.getFacility()+"时 "+barcode.getBarcode()+" 已被soseq=["+oldBindSoSeq+"]slot=["+oldBindSlot+"]绑定"); log.error("\t真实绑定"+outItem.getSlotlocation() + "的pn=["+outItem.getPn()+"]facility = "+outItem.getFacility()+"时 "+barcode.getBarcode()+" 已被soseq=["+oldBindSoSeq+"_"+oldBindSlot+"]绑定");
return null; return null;
} }
} }
String oldPreBindSlot = oldBindAppendInfo.getPreBindSlot(); String oldPreBindSlot = oldBindAppendInfo.getPreBindSlot();
if(Strings.isNotBlank(oldPreBindSlot)){ if(Strings.isNotBlank(oldPreBindSlot)){
int oldSlotSeq = Integer.valueOf(oldPreBindSlot); int oldSlotSeq = Integer.valueOf(oldPreBindSlot);
log.info("预绑定oldsoseq=["+oldBindSoSeq+"]oldpreslot=["+oldPreBindSlot+"]物料["+barcode.getBarcode()+"],更新其预绑定数量"); log.info("预绑定oldsoseq=["+oldBindSoSeq+"_"+oldPreBindSlot+"]物料["+barcode.getBarcode()+"],更新其预绑定数量");
OutItem oldCutOutItem = soseqCache.getCutOutItem(oldBindSoSeq, oldSlotSeq); OutItem oldCutOutItem = soseqCache.getCutOutItem(oldBindSoSeq, oldSlotSeq);
int oldTotalPreBindQty = oldCutOutItem.getLockQty(); int oldTotalPreBindQty = oldCutOutItem.getLockQty();
oldTotalPreBindQty = oldTotalPreBindQty - dbQty; oldTotalPreBindQty = oldTotalPreBindQty - dbQty;
...@@ -393,7 +393,7 @@ public class QisdaBindService { ...@@ -393,7 +393,7 @@ public class QisdaBindService {
int realLockQty = outItem.getRealLockQty(); int realLockQty = outItem.getRealLockQty();
int newRealLockQty = realLockQty + dbQty; int newRealLockQty = realLockQty + dbQty;
log.info("\t真实绑定["+barcode.getBarcode()+"]到So=["+outItem.getSo()+"]hSerial=["+outItem.gethSerial()+"]refno=["+outItem.getRefno()+"]的["+outItem.getSlotlocation()+"] 绑定数量:" + outItem.getRealLockQty() +"/" + outItem.getQty()); log.info("\t真实绑定["+barcode.getBarcode()+"]到So=["+outItem.getSo()+"]hSerial=["+outItem.getSourceName()+"] 绑定数量:" + outItem.getRealLockQty() +"/" + outItem.getQty());
barcode.realBindItem(outItem); barcode.realBindItem(outItem);
pos.setBarcode(barcode); pos.setBarcode(barcode);
storagePosDao.save(pos); storagePosDao.save(pos);
...@@ -502,7 +502,7 @@ public class QisdaBindService { ...@@ -502,7 +502,7 @@ public class QisdaBindService {
String hSerial = outItem.gethSerial(); String hSerial = outItem.gethSerial();
int reelQty = barcode.getAmount(); int reelQty = barcode.getAmount();
String oldSlot = appendInfo.getBindSlot(); String oldSlot = appendInfo.getBindSlot();
log.info("首盘需求单["+hSerial+"]站位["+outItem.getSlotlocation()+"]缺料,从站位["+oldSlot+"]绑定料盘中抢夺料盘"+barcode.getBarcode()+"["+reelQty+"]进行绑定"); log.info("首盘需求单["+outItem.getSourceName()+"]缺料,从站位["+oldSlot+"]绑定料盘中抢夺料盘"+barcode.getBarcode()+"["+reelQty+"]进行绑定");
OutItem oldItem = outItemDao.findItem(hSerial,Integer.valueOf(oldSlot)); OutItem oldItem = outItemDao.findItem(hSerial,Integer.valueOf(oldSlot));
if(oldItem != null){ if(oldItem != null){
//不是预绑定的物料 //不是预绑定的物料
......
package com.myproject.webapp.controller.webService; package com.myproject.webapp.controller.webService;
import com.google.common.base.Strings;
import com.google.common.collect.Lists;
import com.google.common.collect.Maps;
import com.myproject.bean.CodeBean;
import com.myproject.bean.json.InventoryItem;
import com.myproject.bean.json.PlateSizeBean;
import com.myproject.bean.qisda.InquiryShelfBean; import com.myproject.bean.qisda.InquiryShelfBean;
import com.myproject.bean.qisda.QisdaApiRequest;
import com.myproject.bean.qisda.ShelfInfo; import com.myproject.bean.qisda.ShelfInfo;
import com.myproject.bean.update.*; import com.myproject.bean.update.*;
import com.myproject.bean.update.qisda.CacheInfo; import com.myproject.bean.update.qisda.CacheInfo;
...@@ -14,6 +9,8 @@ import com.myproject.bean.update.qisda.DNInfo; ...@@ -14,6 +9,8 @@ import com.myproject.bean.update.qisda.DNInfo;
import com.myproject.bean.update.qisda.DNItem; import com.myproject.bean.update.qisda.DNItem;
import com.myproject.dao.mongo.qisda.ICacheInfoDao; import com.myproject.dao.mongo.qisda.ICacheInfoDao;
import com.myproject.dao.mongo.qisda.IDNItemDao; import com.myproject.dao.mongo.qisda.IDNItemDao;
import com.myproject.exception.ApiException;
import com.myproject.util.HttpHelper;
import org.apache.logging.log4j.LogManager; import org.apache.logging.log4j.LogManager;
import org.apache.logging.log4j.Logger; import org.apache.logging.log4j.Logger;
import org.springframework.beans.factory.annotation.Autowired; import org.springframework.beans.factory.annotation.Autowired;
...@@ -48,6 +45,11 @@ public class QisdaCache { ...@@ -48,6 +45,11 @@ public class QisdaCache {
private static String HSERIAL_SHELF_MAP_KEY = "hSerialShelfMap"; private static String HSERIAL_SHELF_MAP_KEY = "hSerialShelfMap";
/** /**
* 重发消息key
*/
private static String FAILED_REQUEST_MAP_KEY = "failedRequestMap";
/**
* 当前正在执行的工单需求单(首盘,补料),未完成时,其他工单需求单不可执行 * 当前正在执行的工单需求单(首盘,补料),未完成时,其他工单需求单不可执行
*/ */
private static String currentOrderHSerial; private static String currentOrderHSerial;
...@@ -58,6 +60,82 @@ public class QisdaCache { ...@@ -58,6 +60,82 @@ public class QisdaCache {
private static Map<String, DNInfo> rfidDnMap; private static Map<String, DNInfo> rfidDnMap;
/** /**
* 需要重新向佳世达发送的指令列表
*/
private static Map<String, QisdaApiRequest> failedRequestMap;
private static boolean isProcessTimer = false;
/**
* 定时器,每10秒执行一次
*/
public static void runTimer(){
if(!isProcessTimer){
isProcessTimer = true;
try {
sendFailedRequest();
}catch (Exception e){
log.error("发送失败请求定时器执行出错:"+e.getMessage());
}finally {
isProcessTimer = false;
}
}
}
/**
* 获取失败列表,进行定时发送
*/
private static void sendFailedRequest() throws ApiException {
List<QisdaApiRequest> failedList = new ArrayList<>();
failedList.addAll(failedRequestMap.values());
failedList.sort(new Comparator<QisdaApiRequest>() {
@Override
public int compare(QisdaApiRequest o1, QisdaApiRequest o2) {
return o1.getDate().compareTo(o2.getDate()) ;
}
});
for (QisdaApiRequest apiRequest : failedList) {
log.info("重发通知指令[" + apiRequest.getMapKey() + "]到Qisda");
String result = HttpHelper.postParam(apiRequest.getUrl(),apiRequest.getParamMap());
log.info("重发通知指令[" + apiRequest.getMapKey() + "]到Qisda返回:" + result);
QisdaCache.removeFailedRequest(apiRequest);
}
}
/**
* 加载请求指令信息
*/
public static void initApiRequestMap(){
if(failedRequestMap == null){
failedRequestMap = new ConcurrentHashMap<>();
CacheInfo cacheInfo = cacheInfoDao.getCacheInfo(FAILED_REQUEST_MAP_KEY);
if(cacheInfo != null){
Map<String, QisdaApiRequest> dbFailedRequestMap = (Map<String, QisdaApiRequest>) cacheInfo.getCacheValue();
failedRequestMap.putAll(dbFailedRequestMap);
log.info("当前发送通知失败指令:" + failedRequestMap);
}
}
}
public static void addFailedRequest(QisdaApiRequest apiRequest){
String mapKey = apiRequest.getMapKey();
if(failedRequestMap.get(mapKey) == null){
log.info(mapKey + "通知指令发送到Qisda失败,加入到缓存");
failedRequestMap.put(apiRequest.getMapKey(), apiRequest);
}
}
public static void removeFailedRequest(QisdaApiRequest apiRequest){
String mapKey = apiRequest.getMapKey();
if(failedRequestMap.get(mapKey) == null){
log.info(mapKey + "通知指令发送到Qisda成功,从缓存中移除");
failedRequestMap.remove(apiRequest.getMapKey());
}
}
/**
* 保存料架缓存信息 * 保存料架缓存信息
* @param hSerialShelfMap * @param hSerialShelfMap
*/ */
...@@ -72,18 +150,22 @@ public class QisdaCache { ...@@ -72,18 +150,22 @@ public class QisdaCache {
Map<String,Map<String,ShelfInfo>> hSerialShelfMap = new ConcurrentHashMap<>(); Map<String,Map<String,ShelfInfo>> hSerialShelfMap = new ConcurrentHashMap<>();
CacheInfo cacheInfo = cacheInfoDao.getCacheInfo(HSERIAL_SHELF_MAP_KEY); CacheInfo cacheInfo = cacheInfoDao.getCacheInfo(HSERIAL_SHELF_MAP_KEY);
if(cacheInfo != null){ if(cacheInfo != null){
hSerialShelfMap = (Map<String,Map<String,ShelfInfo>>) cacheInfo.getCacheValue(); Map<String, Map<String, ShelfInfo>> dbShelfMap = (Map<String, Map<String, ShelfInfo>>) cacheInfo.getCacheValue();
hSerialShelfMap.putAll(dbShelfMap);
} }
return hSerialShelfMap; return hSerialShelfMap;
} }
/**
* 初始化DN单绑定缓存信息
*/
public void initRfidDnMap(){ public void initRfidDnMap(){
if(rfidDnMap == null){ if(rfidDnMap == null){
CacheInfo cacheInfo = cacheInfoDao.getCacheInfo(RFID_DN_MAP_KEY); CacheInfo cacheInfo = cacheInfoDao.getCacheInfo(RFID_DN_MAP_KEY);
if(cacheInfo == null){ rfidDnMap = new ConcurrentHashMap<>();
rfidDnMap = new ConcurrentHashMap<>(); if(cacheInfo != null){
}else{ Map<String, DNInfo> dbRfidDnMap = (Map<String, DNInfo>) cacheInfo.getCacheValue();
rfidDnMap = (Map<String, DNInfo>) cacheInfo.getCacheValue(); rfidDnMap.putAll(dbRfidDnMap);
log.info("当前收料绑定:" + rfidDnMap); log.info("当前收料绑定:" + rfidDnMap);
} }
} }
......
...@@ -122,6 +122,10 @@ public class QisdaDeviceController extends BaseController { ...@@ -122,6 +122,10 @@ public class QisdaDeviceController extends BaseController {
if(task.isFinished()){ if(task.isFinished()){
String msg = "条码["+barcode.getBarcode()+"]的任务已完成,不返回尺寸信息"; String msg = "条码["+barcode.getBarcode()+"]的任务已完成,不返回尺寸信息";
return ResultBean.newErrorResult(104, msg); return ResultBean.newErrorResult(104, msg);
}else if(task.isStopSendToQisda()){
//被取消的出库任务,不可再放上料架
String msg = "条码["+barcode.getBarcode()+"]的任务已被取消,不返回尺寸信息";
return ResultBean.newErrorResult(107, msg);
}else { }else {
String hSerial = task.getAppendInfo().gethSerial(); String hSerial = task.getAppendInfo().gethSerial();
String executingHSerial = QisdaCache.getCurrentOrderHSerial(); String executingHSerial = QisdaCache.getCurrentOrderHSerial();
...@@ -133,10 +137,9 @@ public class QisdaDeviceController extends BaseController { ...@@ -133,10 +137,9 @@ public class QisdaDeviceController extends BaseController {
boolean secondRobtoSame = isSameTask(barcode,secondRobotTask); boolean secondRobtoSame = isSameTask(barcode,secondRobotTask);
if (firstRobtoSame || secondRobtoSame){ if (firstRobtoSame || secondRobtoSame){
String msg = "机器人正在将料盘["+barcode.getBarcode()+"]的放上料架,不返回尺寸信息"; String msg = "机器人正在将料盘["+barcode.getBarcode()+"]的放上料架,不返回尺寸信息";
return ResultBean.newErrorResult(106, msg); return ResultBean.newErrorResult(107, msg);
} }
} }
} }
updateScanTask(robotIndex, task); updateScanTask(robotIndex, task);
......
...@@ -554,7 +554,7 @@ public class StorageDataController extends BaseController { ...@@ -554,7 +554,7 @@ public class StorageDataController extends BaseController {
if(dataCache.getSettings().isStopOut()){ if(dataCache.getSettings().isStopOut()){
lineMsg = "系统更新中,暂停出入库"; lineMsg = "系统更新中,暂停出入库";
resultMap.put("result"," "); resultMap.put("result","100");
resultMap.put("msg",lineMsg); resultMap.put("msg",lineMsg);
return resultMap; return resultMap;
} }
......
...@@ -699,6 +699,7 @@ public class TaskService implements ITaskService { ...@@ -699,6 +699,7 @@ public class TaskService implements ITaskService {
taskMap.remove(task.getId()); taskMap.remove(task.getId());
String barcode = task.getBarcode(); String barcode = task.getBarcode();
if(!Strings.isNullOrEmpty(barcode)){ if(!Strings.isNullOrEmpty(barcode)){
task.setStopSendToQisda(true);
task.setStatus(StorageConstants.OP_STATUS.CANCEL.name()); task.setStatus(StorageConstants.OP_STATUS.CANCEL.name());
finishedTaskMap.put(barcode, task); finishedTaskMap.put(barcode, task);
} }
...@@ -744,9 +745,13 @@ public class TaskService implements ITaskService { ...@@ -744,9 +745,13 @@ public class TaskService implements ITaskService {
if(task != null && task.isCheckOutTask()){ if(task != null && task.isCheckOutTask()){
log.info("清除任务["+task.getBarcode()+"]"); log.info("清除任务["+task.getBarcode()+"]");
finishedTaskMap.remove(task.getBarcode()); finishedTaskMap.remove(task.getBarcode());
task.setStopSendToQisda(true);
task = dataLogDao.save(task);
//发送取消(发料)指令到佳世达 //发送取消(发料)指令到佳世达
AppendInfo taskAppendInfo = task.getAppendInfo(); AppendInfo taskAppendInfo = task.getAppendInfo();
if(taskAppendInfo.isFirstReelAction() || taskAppendInfo.isTailAction()){ if(taskAppendInfo.isFirstReelAction() || taskAppendInfo.isTailAction()){
Barcode barcode = barcodeManager.findByBarcode(task.getBarcode()); Barcode barcode = barcodeManager.findByBarcode(task.getBarcode());
log.info("["+task.getBarcode()+"]任务已出库完成,但未放上小车,发送E状态到佳世达,同时解除料架架位,发料任务完成数量+1"); log.info("["+task.getBarcode()+"]任务已出库完成,但未放上小车,发送E状态到佳世达,同时解除料架架位,发料任务完成数量+1");
OutInfo outInfo = outInfoCache.incTaskFinishNum(taskAppendInfo.gethSerial(), 0, 0); OutInfo outInfo = outInfoCache.incTaskFinishNum(taskAppendInfo.gethSerial(), 0, 0);
...@@ -1710,7 +1715,7 @@ public class TaskService implements ITaskService { ...@@ -1710,7 +1715,7 @@ public class TaskService implements ITaskService {
//记录日志,完成 task //记录日志,完成 task
task.setNum(barcode.getAmount()); task.setNum(barcode.getInitialAmount());
task.setStatus(StorageConstants.OP_STATUS.FINISHED.name()); task.setStatus(StorageConstants.OP_STATUS.FINISHED.name());
dataLogDao.save(task); dataLogDao.save(task);
......
支持 Markdown 格式
你添加了 0 到此讨论。请谨慎行事。
Finish editing this message first!