protected virtual IEnumerable balances() { BalanceFilter filter = Filter.Current; PXView view = new Select2 <FABookBalance, InnerJoin <FixedAsset, On <FixedAsset.assetID, Equal <FABookBalance.assetID> >, InnerJoin <FADetails, On <FADetails.assetID, Equal <FABookBalance.assetID> >, LeftJoin <Account, On <Account.accountID, Equal <FixedAsset.fAAccountID> > > > >, Where <FABookBalance.depreciate, Equal <True>, And <FABookBalance.status, Equal <FixedAssetStatus.active>, And <FADetails.status, Equal <FixedAssetStatus.active> > > > >() .CreateView(this, mergeCache: PXView.MaximumRows > 1); if (filter.BookID != null) { view.WhereAnd <Where <FABookBalance.bookID, Equal <Current <BalanceFilter.bookID> > > >(); } if (filter.ClassID != null) { view.WhereAnd <Where <FixedAsset.classID, Equal <Current <BalanceFilter.classID> > > >(); } if (PXAccess.FeatureInstalled <FeaturesSet.multipleCalendarsSupport>() || filter.OrgBAccountID != null) { view.WhereAnd <Where <FixedAsset.branchID, Inside <Current <BalanceFilter.orgBAccountID> > > >(); } if (!string.IsNullOrEmpty(filter.PeriodID)) { view.WhereAnd <Where <FABookBalance.currDeprPeriod, LessEqual <Current <BalanceFilter.periodID> > > >(); } if (filter.ParentAssetID != null) { view.WhereAnd <Where <FixedAsset.parentAssetID, Equal <Current <BalanceFilter.parentAssetID> > > >(); } int startRow = PXView.StartRow; int totalRows = 0; List <PXFilterRow> newFilters = new List <PXFilterRow>(); foreach (PXFilterRow f in PXView.Filters) { if (f.DataField.ToLower() == "status") { f.DataField = "FADetails__Status"; } newFilters.Add(f); } List <object> list = view.Select(PXView.Currents, null, PXView.Searches, PXView.SortColumns, PXView.Descendings, newFilters.ToArray(), ref startRow, PXView.MaximumRows, ref totalRows); PXView.StartRow = 0; return(list); }
public virtual IEnumerable appointments() { var filter = Filter.Current; if (filter.CutOffDate == null) { return(new List <object>()); } List <object> args = new List <object>(); var commandFilter = new Select2 <FSAppointmentInventoryItem, InnerJoin <FSAppointment, On < FSAppointment.appointmentID, Equal <FSAppointmentInventoryItem.appointmentID> >, InnerJoin <FSServiceOrder, On < FSServiceOrder.sOID, Equal <FSAppointment.sOID> >, InnerJoin <Customer, On < Customer.bAccountID, Equal <FSServiceOrder.billCustomerID> >, InnerJoin <FSSrvOrdType, On < FSSrvOrdType.srvOrdType, Equal <FSAppointment.srvOrdType> >, InnerJoin <FSAppointmentDet, On < FSAppointmentDet.sODetID, Equal <FSAppointmentInventoryItem.sODetID>, And <FSAppointmentDet.appointmentID, Equal <FSAppointment.appointmentID> > >, LeftJoin <FSPostInfo, On < FSPostInfo.postID, Equal <FSAppointmentInventoryItem.postID> >, LeftJoin <FSGeoZonePostalCode, On < FSGeoZonePostalCode.postalCode, Equal <FSServiceOrder.postalCode> >, LeftJoin <FSGeoZone, On < FSGeoZone.geoZoneID, Equal <FSGeoZonePostalCode.geoZoneID> > > > > > > > > >, Where2 < Where < FSAppointmentInventoryItem.lineType, Equal <ListField_LineType_Pickup_Delivery.Pickup_Delivery>, And <FSAppointment.status, Equal <ListField_Status_Appointment.Closed>, And <FSAppointmentDet.lineType, Equal <ListField_LineType_ALL.Service> > > >, And < FSSrvOrdType.enableINPosting, Equal <True> > > >() as BqlCommand; commandFilter = commandFilter.WhereAnd(typeof(Where <FSPostInfo.postID, IsNull, Or <FSPostInfo.iNPosted, Equal <False> > >)); if (filter.CutOffDate != null) { commandFilter = commandFilter.WhereAnd(typeof(Where <FSAppointment.executionDate, LessEqual <Required <UpdateInventoryFilter.cutOffDate> > >)); args.Add(filter.CutOffDate); } if (filter.RouteDocumentID != null) { commandFilter = commandFilter.WhereAnd(typeof(Where <FSAppointment.routeDocumentID, Equal <Required <UpdateInventoryFilter.routeDocumentID> > >)); args.Add(filter.RouteDocumentID); } if (filter.AppointmentID != null) { commandFilter = commandFilter.WhereAnd(typeof(Where <FSAppointment.appointmentID, Equal <Required <UpdateInventoryFilter.appointmentID> > >)); args.Add(filter.AppointmentID); } var view = new PXView(this, true, commandFilter); var startRow = PXView.StartRow; int totalRows = 0; var results = view.Select( PXView.Currents, args.ToArray(), PXView.Searches, PXView.SortColumns, PXView.Descendings, PXView.Filters, ref startRow, PXView.MaximumRows, ref totalRows); Appointments.Cache.IsDirty = false; return(results); }
public virtual void OptimizeRoutes(RoutesOptimizationProcess graph, FSAppointmentFilter filter, List <FSAppointmentFSServiceOrder> list, PXResultset <FSAppointmentStaffMember, CSCalendar> staffSelected) { RouteOptimizerClient client = new RouteOptimizerClient(); SingleDayOptimizationInput requestBody = new SingleDayOptimizationInput(); List <FSAppointment> processList = new List <FSAppointment>(); FSSetup fsSetupRow = graph.SetupRecord.Current; requestBody.balanced = true; requestBody.vehicles = new List <Vehicle>(); requestBody.waypoints = new List <Waypoint>(); string address = string.Empty; if (staffSelected != null && staffSelected.Count == 0) { throw new PXException(PXMessages.LocalizeFormatNoPrefix(TX.Error.SELECT_AT_LEAST_ONE_STAFF_MEMBER)); } //Origin end Route location FSAddress fsAddressRow = PXSelectJoin <FSAddress, InnerJoin <FSBranchLocation, On <FSBranchLocation.branchLocationAddressID, Equal <FSAddress.addressID> > >, Where < FSBranchLocation.branchLocationID, Equal <Required <FSBranchLocation.branchLocationID> > > > .Select(graph, list[0].BranchLocationID); address = SharedFunctions.GetAddressForGeolocation(fsAddressRow.PostalCode, fsAddressRow.AddressLine1, fsAddressRow.AddressLine2, fsAddressRow.City, fsAddressRow.State, fsAddressRow.CountryID); GLocation[] results = Geocoder.Geocode(address, fsSetupRow.MapApiKey); if (results.Length == 0) { throw new PXException(PXMessages.LocalizeFormatNoPrefix(TX.Error.MAPS_FAILED_REVERSE_ADRESS, TX.TableName.BRANCH_LOCATION)); } CSCalendar csVendorCalendarRow = PXSelect <CSCalendar, Where <CSCalendar.calendarID, Equal <Required <CSCalendar.calendarID> > > > .Select(graph, fsSetupRow.CalendarID); //Driver Logic foreach (PXResult <FSAppointmentStaffMember, CSCalendar> result in staffSelected) { FSAppointmentStaffMember staffRow = (FSAppointmentStaffMember)result; CSCalendar csCalendarRow = (CSCalendar)result; Vehicle vehicleRow = new Vehicle() { name = staffRow.BAccountID.ToString(), origin = new RouteLocation() { latitude = results[0].LatLng.Latitude, longitude = results[0].LatLng.Longitude }, destination = new RouteLocation() { latitude = results[0].LatLng.Latitude, longitude = results[0].LatLng.Longitude }, tags = new List <string>() { staffRow.BAccountID.ToString() } }; TimeWindow working = graph.GetWorkingTimeWindow(staffRow.EmployeeSDEnabled == true ? csCalendarRow : csVendorCalendarRow, filter.StartDate); Break lunchBreak = graph.GetBreakWindow(fsSetupRow); if (lunchBreak != null) { vehicleRow.breaks = new List <Break>() { lunchBreak }; } if (working != null) { vehicleRow.timeWindow = working; requestBody.vehicles.Add(vehicleRow); } } if (requestBody.vehicles.Count == 0) { for (int i = 0; i < list.Count; i++) { FSAppointment fsAppointmentRow = list[i]; UpdateAppointmentHeader(fsAppointmentRow, ID.Status_ROOptimization.NOT_ABLE); graph.Appointments.Update(fsAppointmentRow); PXProcessing <FSAppointmentFSServiceOrder> .SetError(i, PXMessages.LocalizeFormatNoPrefix(TX.Error.APPOINTMENT_COULD_NOT_BE_REACH_SERVICED_NO_DRIVER_AVAILABLE)); } if (graph.Appointments.Cache.IsDirty == true) { graph.Appointments.Cache.Persist(PXDBOperation.Update); } return; } //Existing Appointment Logic if (filter.Type == ID.Type_ROOptimization.UNASSIGNED_APP && staffSelected.Count() > 0) { List <object> args = new List <object>(); BqlCommand fsAppointmentList = new Select2 <FSAppointment, InnerJoin <FSServiceOrder, On <FSServiceOrder.sOID, Equal <FSAppointment.sOID> >, InnerJoin <FSAddress, On <FSAddress.addressID, Equal <FSServiceOrder.serviceOrderAddressID> > > > >(); if (filter.BranchID != null) { fsAppointmentList = fsAppointmentList.WhereAnd(typeof(Where <FSServiceOrder.branchID, Equal <Required <FSServiceOrder.branchID> > >)); args.Add(filter.BranchID); } if (filter.BranchLocationID != null) { fsAppointmentList = fsAppointmentList.WhereAnd(typeof(Where <FSServiceOrder.branchLocationID, Equal <Required <FSServiceOrder.branchLocationID> > >)); args.Add(filter.BranchLocationID); } if (filter.StartDate != null) { fsAppointmentList = fsAppointmentList.WhereAnd(typeof(Where <FSAppointment.scheduledDateTimeBegin, GreaterEqual <Required <FSAppointment.scheduledDateTimeBegin> > >)); args.Add(filter.StartDateWithTime); } if (filter.EndDateWithTime != null) { fsAppointmentList = fsAppointmentList.WhereAnd(typeof(Where <FSAppointment.scheduledDateTimeEnd, LessEqual <Required <FSAppointment.scheduledDateTimeEnd> > >)); args.Add(filter.EndDateWithTime); } if (staffSelected != null && staffSelected.Count() > 0) { fsAppointmentList = fsAppointmentList.WhereAnd(typeof(Where <FSAppointment.primaryDriver, In <Required <FSAppointment.primaryDriver> > >)); int[] staffResult = StaffMemberFilter.Select() .RowCast <FSAppointmentStaffMember>() .Where(_ => _.Selected == true) .Select(_ => _.BAccountID) .Cast <int>() .ToArray(); args.Add(staffResult); } PXView appointmentView = new PXView(graph, true, fsAppointmentList); var fsAppointmentSet = appointmentView.SelectMulti(args.ToArray()); foreach (PXResult <FSAppointment, FSServiceOrder, FSAddress> row in fsAppointmentSet) { FSAppointment fsAppointmentRow = (FSAppointment)row; fsAddressRow = (FSAddress)row; address = SharedFunctions.GetAddressForGeolocation( fsAddressRow.PostalCode, fsAddressRow.AddressLine1, fsAddressRow.AddressLine2, fsAddressRow.City, fsAddressRow.State, fsAddressRow.CountryID); Waypoint wp = GetWaypointFromAppointment(fsSetupRow, fsAppointmentRow, address); if (wp != null) { requestBody.waypoints.Add(wp); processList.Add(fsAppointmentRow); } else { UpdateAppointmentHeader(fsAppointmentRow, ID.Status_ROOptimization.ADDRESS_ERROR); graph.Appointments.Update(fsAppointmentRow); } } } //Appointment Logic for (int i = list.Count - 1; i >= 0; i--) { bool addressError = false; try { address = SharedFunctions.GetAddressForGeolocation( list[i].PostalCode, list[i].AddressLine1, list[i].AddressLine2, list[i].City, list[i].State, list[i].CountryID); Waypoint wp = GetWaypointFromAppointment(fsSetupRow, list[i], address); if (wp != null) { requestBody.waypoints.Add(wp); processList.Add(list[i]); } else { addressError = true; } } catch { addressError = true; } if (addressError == true) { addressError = false; FSAppointment fsAppointmentRow = list[i]; UpdateAppointmentHeader(fsAppointmentRow, ID.Status_ROOptimization.ADDRESS_ERROR); graph.Appointments.Update(fsAppointmentRow); list.RemoveAt(i); PXProcessing <FSAppointmentFSServiceOrder> .SetError(i, PXMessages.LocalizeFormatNoPrefix(TX.Error.MAPS_FAILED_REVERSE_ADRESS, TX.TableName.APPOINTMENT)); } } if (graph.Appointments.Cache.IsDirty == true) { graph.Appointments.Cache.Persist(PXDBOperation.Update); } try { SingleDayOptimizationOutput responseObject = client.getSingleDayOptimization(fsSetupRow.ROWWApiEndPoint, fsSetupRow.ROWWLicensekey, requestBody); AppointmentEntry graphAppointmentEntry = PXGraph.CreateInstance <AppointmentEntry>(); for (int i = 0; i < responseObject.routes.Count; i++) { int assignedstaffID; int.TryParse(responseObject.routes[i].vehicle.name, out assignedstaffID); bool changeFlag = false; for (int j = 1; j < responseObject.routes[i].steps.Count - 1; j++) { RouteOtimizer.RouteStep currentAppointment = responseObject.routes[i].steps[j]; int appointmentID; int.TryParse(currentAppointment.waypoint.name, out appointmentID); FSAppointment fsAppointmentListRow = processList.Find(x => x.AppointmentID == appointmentID); var newBegin = convertSecToTime(currentAppointment.serviceStartTimeSec, fsAppointmentListRow.ScheduledDateTimeBegin); var newEnd = newBegin.AddSeconds(currentAppointment.departureTimeSec - currentAppointment.arrivalTimeSec); UpdateAppointmentHeader(fsAppointmentListRow, ID.Status_ROOptimization.OPTIMIZED, j, null, newBegin, newEnd); if (fsAppointmentListRow.PrimaryDriver != null) { graph.Appointments.Update(fsAppointmentListRow); changeFlag = true; } else { fsAppointmentListRow.PrimaryDriver = assignedstaffID; FSAppointment fsAppointmentRow = graphAppointmentEntry.AppointmentRecords.Current = graphAppointmentEntry.AppointmentRecords.Search <FSAppointment.refNbr>( fsAppointmentListRow.RefNbr, fsAppointmentListRow.SrvOrdType); UpdateAppointmentHeader(fsAppointmentRow, ID.Status_ROOptimization.OPTIMIZED, j, assignedstaffID, newBegin, newEnd); graphAppointmentEntry.AppointmentRecords.Update(fsAppointmentRow); FSAppointmentEmployee fsAppointmentEmployeeRow_New = new FSAppointmentEmployee() { AppointmentID = fsAppointmentRow.AppointmentID, EmployeeID = assignedstaffID }; fsAppointmentEmployeeRow_New = graphAppointmentEntry.AppointmentServiceEmployees.Insert(fsAppointmentEmployeeRow_New); graphAppointmentEntry.Save.Press(); } } if (changeFlag == true) { graph.Appointments.Cache.Persist(PXDBOperation.Update); } } foreach (OutputWaypoint wp in responseObject.unreachableWaypoints.Concat(responseObject.unreachedWaypoints).GroupBy(p => p.name).Select(g => g.First()).ToList()) { int appointmentID; int.TryParse(wp.name, out appointmentID); FSAppointment fsAppointmentRow = list.Find(x => x.AppointmentID == appointmentID); if (fsAppointmentRow != null) { for (int i = 0; i < list.Count; i++) { if (fsAppointmentRow.AppointmentID == list[i].AppointmentID) { UpdateAppointmentHeader(fsAppointmentRow, ID.Status_ROOptimization.NOT_ABLE); graph.Appointments.Update(fsAppointmentRow); PXProcessing <FSAppointmentFSServiceOrder> .SetError(i, PXMessages.LocalizeFormatNoPrefix(TX.Error.APPOINTMENT_COULD_NOT_BE_REACH_SERVICED)); } } } } graph.Appointments.Cache.Persist(PXDBOperation.Update); } catch (PXException e) { for (int i = 0; i < list.Count; i++) { FSAppointment fsAppointmentRow = list[i]; UpdateAppointmentHeader(fsAppointmentRow, ID.Status_ROOptimization.NOT_ABLE); graph.Appointments.Update(fsAppointmentRow); PXProcessing <FSAppointmentFSServiceOrder> .SetError(i, PXMessages.LocalizeFormatNoPrefix(e.Message)); } graph.Appointments.Cache.Persist(PXDBOperation.Update); } }