use of org.compiere.model.MResourceType in project adempiere by adempiere.
the class CRP method scheduleForward.
private Timestamp scheduleForward(final Timestamp start, final long nodeDurationMillis, MResource r) {
MResourceType t = r.getResourceType();
// statistical interation count
int iteration = 0;
Timestamp currentDate = start;
Timestamp end = null;
long remainingMillis = nodeDurationMillis;
do {
currentDate = reasoner.getAvailableDate(r, currentDate, false);
Timestamp dayStart = t.getDayStart(currentDate);
Timestamp dayEnd = t.getDayEnd(currentDate);
// resource's availability, switch start time to the given again
if (currentDate.after(dayStart) && currentDate.before(dayEnd)) {
dayStart = currentDate;
}
// The available time at this day in milliseconds
long availableDayDuration = getAvailableDurationMillis(dayStart, dayEnd, r);
// The work can be finish on this day.
if (availableDayDuration >= remainingMillis) {
end = new Timestamp(dayStart.getTime() + remainingMillis);
remainingMillis = 0;
break;
} else // Otherwise recall with next day and the remained node duration.
{
currentDate = TimeUtil.addDays(TimeUtil.getDayBorder(currentDate, null, false), 1);
remainingMillis -= availableDayDuration;
}
iteration++;
if (iteration > p_MaxIterationsNo) {
throw new CRPException("Maximum number of iterations exceeded (" + p_MaxIterationsNo + ")" + " - Date:" + currentDate + ", RemainingMillis:" + remainingMillis);
}
} while (remainingMillis > 0);
return end;
}
use of org.compiere.model.MResourceType in project adempiere by adempiere.
the class CRP method scheduleBackward.
/**
* Calculate start date having duration and resource
* @param end end date
* @param nodeDurationMillis duration [millis]
* @param r resource
* @return start date
*/
private Timestamp scheduleBackward(final Timestamp end, final long nodeDurationMillis, MResource r) {
MResourceType t = r.getResourceType();
log.info("--> ResourceType " + t);
Timestamp start = null;
Timestamp currentDate = end;
long remainingMillis = nodeDurationMillis;
// statistical iteration count
int iteration = 0;
do {
log.info("--> end=" + currentDate);
log.info("--> nodeDuration=" + remainingMillis);
currentDate = reasoner.getAvailableDate(r, currentDate, true);
log.info("--> end(available)=" + currentDate);
Timestamp dayEnd = t.getDayEnd(currentDate);
Timestamp dayStart = t.getDayStart(currentDate);
log.info("--> dayStart=" + dayStart + ", dayEnd=" + dayEnd);
// resource's availability, switch end time to the given again
if (currentDate.before(dayEnd) && currentDate.after(dayStart)) {
dayEnd = currentDate;
}
// The available time at this day in milliseconds
long availableDayDuration = getAvailableDurationMillis(dayStart, dayEnd, r);
// The work can be finish on this day.
if (availableDayDuration >= remainingMillis) {
log.info("--> availableDayDuration >= nodeDuration true " + availableDayDuration + "|" + remainingMillis);
start = new Timestamp(dayEnd.getTime() - remainingMillis);
remainingMillis = 0;
break;
} else // Otherwise recall with previous day and the remained node duration.
{
log.info("--> availableDayDuration >= nodeDuration false " + availableDayDuration + "|" + remainingMillis);
log.info("--> nodeDuration-availableDayDuration " + (remainingMillis - availableDayDuration));
currentDate = TimeUtil.addDays(TimeUtil.getDayBorder(currentDate, null, true), -1);
remainingMillis -= availableDayDuration;
}
//
iteration++;
if (iteration > p_MaxIterationsNo) {
throw new CRPException("Maximum number of iterations exceeded (" + p_MaxIterationsNo + ")" + " - Date:" + start + ", RemainingMillis:" + remainingMillis);
}
} while (remainingMillis > 0);
log.info(" --> start=" + start + " <---------------------------------------- ");
return start;
}
use of org.compiere.model.MResourceType in project adempiere by adempiere.
the class CRPReasoner method getSQLDayRestriction.
private String getSQLDayRestriction(Timestamp dateTime, I_S_Resource r, List<Object> params) {
final MResourceType rt = MResourceType.get(getCtx(), r.getS_ResourceType_ID());
Timestamp dayStart = rt.getDayStart(dateTime);
Timestamp dayEnd = rt.getDayEnd(dateTime);
String whereClause;
//
// Case 1: The time dependent process has already begun and ends at this day.
whereClause = "(DateStartSchedule<=? AND DateFinishSchedule>=? AND DateFinishSchedule<=?)";
params.add(dayStart);
params.add(dayStart);
params.add(dayEnd);
//
// Case 2: The time dependent process begins and ends at this day.
whereClause += " OR (DateStartSchedule>=? AND DateStartSchedule<=?" + " AND DateFinishSchedule>=? AND DateFinishSchedule<=?)";
params.add(dayStart);
params.add(dayEnd);
params.add(dayStart);
params.add(dayEnd);
//
// Case 3: The time dependent process begins at this day and ends few days later.
whereClause += " OR (DateStartSchedule>=? AND DateStartSchedule<=? AND DateFinishSchedule>=?)";
params.add(dayStart);
params.add(dayEnd);
params.add(dayEnd);
//
// Case 4: The time dependent process has already begun and ends few days later.
whereClause += " OR (DateStartSchedule<=? AND DateFinishSchedule>=?)";
params.add(dayStart);
params.add(dayEnd);
return "(" + whereClause + ")";
}
use of org.compiere.model.MResourceType in project adempiere by adempiere.
the class CRPReasoner method getAvailableDate.
/**
* @param r resource
* @param dateTime
* @return next available date
*/
public Timestamp getAvailableDate(I_S_Resource r, Timestamp dateTime, boolean isScheduleBackward) {
MResourceType t = MResourceType.get(getCtx(r), r.getS_ResourceType_ID());
Timestamp date = dateTime;
ArrayList<Object> params = new ArrayList<Object>();
String whereClause;
String orderByClause;
int direction;
if (isScheduleBackward) {
whereClause = MResourceUnAvailable.COLUMNNAME_DateFrom + " <= ?";
params.add(date);
orderByClause = MResourceUnAvailable.COLUMNNAME_DateFrom + " DESC";
direction = 1;
} else {
whereClause = MResourceUnAvailable.COLUMNNAME_DateTo + " >= ?";
params.add(date);
orderByClause = MResourceUnAvailable.COLUMNNAME_DateTo;
direction = -1;
}
whereClause += " AND " + MResourceUnAvailable.COLUMNNAME_S_Resource_ID + "=? AND AD_Client_ID=?";
params.add(r.getS_Resource_ID());
params.add(r.getAD_Client_ID());
POResultSet<MResourceUnAvailable> rs = new Query(getCtx(r), MResourceUnAvailable.Table_Name, whereClause, null).setOrderBy(orderByClause).setParameters(params).scroll();
try {
while (rs.hasNext()) {
MResourceUnAvailable rua = rs.next();
if (rua.isUnAvailable(date)) {
date = TimeUtil.addDays(rua.getDateTo(), 1 * direction);
}
date = getAvailableDate(t, dateTime, isScheduleBackward);
}
} finally {
DB.close(rs);
}
//
date = getAvailableDate(t, dateTime, isScheduleBackward);
return date;
}
use of org.compiere.model.MResourceType in project adempiere by adempiere.
the class DefaultRoutingServiceImpl method calculateDuration.
public BigDecimal calculateDuration(I_AD_Workflow wf, I_S_Resource plant, BigDecimal qty) {
if (plant == null)
return Env.ZERO;
final Properties ctx = ((PO) wf).getCtx();
final MResourceType S_ResourceType = MResourceType.get(ctx, plant.getS_ResourceType_ID());
BigDecimal AvailableDayTime = new BigDecimal(S_ResourceType.getTimeSlotHours());
int AvailableDays = S_ResourceType.getAvailableDaysWeek();
double durationBaseSec = getDurationBaseSec(wf.getDurationUnit());
double durationTotal = 0.0;
MWFNode[] nodes = ((MWorkflow) wf).getNodes(false, Env.getAD_Client_ID(ctx));
for (I_AD_WF_Node node : nodes) {
// Qty independent times:
durationTotal += node.getQueuingTime();
durationTotal += node.getSetupTime();
durationTotal += node.getWaitingTime();
durationTotal += node.getMovingTime();
// Get OverlapUnits - number of units that must be completed before they are moved the next activity
double overlapUnits = qty.doubleValue();
if (node.getOverlapUnits() > 0 && node.getOverlapUnits() < overlapUnits) {
overlapUnits = node.getOverlapUnits();
}
double durationBeforeOverlap = node.getDuration() * overlapUnits;
durationTotal += durationBeforeOverlap;
}
BigDecimal requiredTime = BigDecimal.valueOf(durationTotal * durationBaseSec / 60 / 60);
// TODO: implement here, Victor's suggestion - https://sourceforge.net/forum/message.php?msg_id=5179460
// Weekly Factor
BigDecimal WeeklyFactor = new BigDecimal(7).divide(new BigDecimal(AvailableDays), 8, RoundingMode.UP);
return (requiredTime.multiply(WeeklyFactor)).divide(AvailableDayTime, 0, RoundingMode.UP);
}
Aggregations