diff --git a/SAS/TMSS/frontend/tmss_webapp/src/App.js b/SAS/TMSS/frontend/tmss_webapp/src/App.js index 145f23fc69bfa1640825f360cf2c88363f4ceeac..294ed19468acfcf2970b03f7bec4508b4a353156 100644 --- a/SAS/TMSS/frontend/tmss_webapp/src/App.js +++ b/SAS/TMSS/frontend/tmss_webapp/src/App.js @@ -62,16 +62,21 @@ class App extends Component { this.menu = [ //{label: 'Dashboard', icon: 'pi pi-fw pi-home', to:'/dashboard',section: 'dashboard'}, + { label: 'Calendar', icon: 'pi pi-fw pi-calendar-times', to: '/su/timelineview/week', section: 'su/timelineview/week', isBreadCrumbVisible: false ,isDateTimeVisible:true}, { label: 'Cycle', icon: 'pi pi-fw pi-spinner', to: '/cycle', section: 'cycle', isBreadCrumbVisible: true,isDateTimeVisible:false }, + { label: 'Daily Schedule', icon: 'pi pi-fw pi-sun', to: '/constraint/view', section: 'system', isBreadCrumbVisible: false ,isDateTimeVisible:true}, { label: 'Project', icon: 'pi pi-fw pi-compass', to: '/project', section: 'project', isBreadCrumbVisible: true ,isDateTimeVisible:false}, + { label: 'Reservations', icon: 'pi pi-fw pi-book', to: '/reservation/list', section: 'system', isBreadCrumbVisible: false ,isDateTimeVisible:true}, + { label: 'Reports', icon: 'pi pi-fw pi-chart-bar', to: '/reports', section: 'reports', isBreadCrumbVisible: false ,isDateTimeVisible:false}, { label: 'Scheduling Units', icon: 'pi pi-fw pi-calendar', to: '/schedulingunit', section: 'schedulingunit', isBreadCrumbVisible: true ,isDateTimeVisible:false}, + { label: 'Stations', icon: 'pi pi-fw pi-wifi pi-rotate', to: '/station/list', section: 'system', isBreadCrumbVisible: false ,isDateTimeVisible:true}, + { label: 'System Events', icon: 'pi pi-fw pi-bolt', to: '/systemevent/list', section: 'system', isBreadCrumbVisible: false ,isDateTimeVisible:true}, { label: 'Tasks', icon: 'pi pi-fw pi-check-square', to: '/task', isBreadCrumbVisible: true ,isDateTimeVisible:false}, { label: 'Workflow', icon: 'pi pi-fw pi-sitemap', to: '/su/workflow', section: 'workflow', isBreadCrumbVisible: true,isDateTimeVisible:false }, - { label: 'Calendar', icon: 'pi pi-fw pi-calendar-times', to: '/su/timelineview/week', section: 'su/timelineview/week', isBreadCrumbVisible: false ,isDateTimeVisible:true}, - { label: 'Reports', icon: 'pi pi-fw pi-chart-bar', to: '/reports', section: 'reports', isBreadCrumbVisible: false ,isDateTimeVisible:false}, - { label: 'System Events', icon: 'pi pi-fw pi-bolt', to: '/systemevent/list', section: 'system', isBreadCrumbVisible: false ,isDateTimeVisible:true}, - { label: 'Stations', icon: 'pi pi-fw pi-wifi pi-rotate', to: '/station/list', section: 'system', isBreadCrumbVisible: false ,isDateTimeVisible:true}, - { label: 'Daily Schedule', icon: 'pi pi-fw pi-sun', to: '/constraint/view', section: 'system', isBreadCrumbVisible: false ,isDateTimeVisible:true}, + + + + ]; } diff --git a/SAS/TMSS/frontend/tmss_webapp/src/components/ViewTable.js b/SAS/TMSS/frontend/tmss_webapp/src/components/ViewTable.js index 137b84362f2be4f630888acdab9192c4fe45953b..d91fbd613d037181e1f762a9e60a152dd5a410d0 100644 --- a/SAS/TMSS/frontend/tmss_webapp/src/components/ViewTable.js +++ b/SAS/TMSS/frontend/tmss_webapp/src/components/ViewTable.js @@ -810,7 +810,7 @@ function FlatpickrRangeColumnFilter({ "plugins": [new confirmDatePlugin()] }} title={(tableToolTipsState[Header])?tableToolTipsState[Header]:"Enter the date & time range to search and press ‘Ok’ button"} - value={filterValue} + value={ filterValue} onClose={newValue => { if(newValue) { // To apply serverside filter only when the value is changed diff --git a/SAS/TMSS/frontend/tmss_webapp/src/layout/components/PageActionMenu.js b/SAS/TMSS/frontend/tmss_webapp/src/layout/components/PageActionMenu.js index 4d25da3c2ad33a3658bf7eeea6eab42021c48d07..deb600340e3ef420f5852c87aa220bd1c79305a2 100644 --- a/SAS/TMSS/frontend/tmss_webapp/src/layout/components/PageActionMenu.js +++ b/SAS/TMSS/frontend/tmss_webapp/src/layout/components/PageActionMenu.js @@ -41,20 +41,21 @@ const PageActionMenu = ({ actions, className }) => { return <div className={"page-action-menu " + className}> {(actions || []).map((action,index) => { - if (action.type === 'buttonv2') { - return ( - <Button key={action.title + '_page_header'} title={action.title || ''} - style={action.style} - icon={`pi ${action.icon}`} disabled={action.disabled} - onMouseOver={(e) => action.disabled ? '' : onButtonMouseOver(e, action)} - onFocus={(e) => action.disabled ? '' : onButtonMouseOver(e, action)} - onClick={(e) => action.disabled ? '' : onButtonClick(e, action)} - onKeyDown={(e) => action.disabled ? '' : handleOnKeyDown(e, action)} - > - </Button> - ); - } switch (action.type) { + + case 'buttonv2': + return ( + <Button key={action.title + '_page_header'} title={action.title || ''} + style={action.style} + icon={`pi ${action.icon}`} disabled={action.disabled} + onMouseOver={(e) => action.disabled ? '' : onButtonMouseOver(e, action)} + onFocus={(e) => action.disabled ? '' : onButtonMouseOver(e, action)} + onClick={(e) => action.disabled ? '' : onButtonClick(e, action)} + onKeyDown={(e) => action.disabled ? '' : handleOnKeyDown(e, action)} + > + </Button> + ); + ; case 'button': return ( <button className="p-link" key={action.title + '_page_header'} title={action.title || ''} diff --git a/SAS/TMSS/frontend/tmss_webapp/src/layout/sass/_pageheader.scss b/SAS/TMSS/frontend/tmss_webapp/src/layout/sass/_pageheader.scss index 6f036f305fddf6ee5ace33c80f19d66a3bb0d94e..e9270cf5eed49a1520b5ebbbfff5ac04a33e3ea6 100644 --- a/SAS/TMSS/frontend/tmss_webapp/src/layout/sass/_pageheader.scss +++ b/SAS/TMSS/frontend/tmss_webapp/src/layout/sass/_pageheader.scss @@ -37,6 +37,21 @@ } } + +.defaultrightpageHeader{ + margin-top: 5px; + width: 100%; +} + +.page-actionsdefaultpageHeader{ + display: flex; + justify-content: flex-end; + + button { + height: 30px; + } +} + .subsystem { font-size: 12px !important; padding: 0.3rem 0.5rem; diff --git a/SAS/TMSS/frontend/tmss_webapp/src/layout/sass/reservation.scss b/SAS/TMSS/frontend/tmss_webapp/src/layout/sass/reservation.scss index 5442a492fbfe35e2c694632c1caaa6aa98b931b0..9863b3b97081e7708accd85d0d1febdcd5b98c60 100644 --- a/SAS/TMSS/frontend/tmss_webapp/src/layout/sass/reservation.scss +++ b/SAS/TMSS/frontend/tmss_webapp/src/layout/sass/reservation.scss @@ -14,4 +14,58 @@ .p-field.p-grid, .p-formgrid.p-grid { margin-left: -2px; margin-top: 0; +} + + +.PanelBlock +{ + display: flex; + flex-direction: column; + +} +.divbox { + display: flex; + margin-bottom: 5px; +} + +.FilterPanel{ + + flex-direction: row; + .p-dropdown{ + width: 150px; + } + .p-panel-content + { + display: flex + } + + margin-right: 10px; + label { + min-width: 100px; + margin-left: 10px; + } + + label::first-child + { + margin-left: 0px; + } + + + .p-inputtext{ + padding-right: 0px; + width: 150px; + margin-right: 0px; + } + .p-button + { + margin-left: 5px; + padding: 0px; + min-width: 20px; + padding-right:7px; + padding-left:7px; + } + .p-datepicker-trigger { + margin-left: 0px !important; + } + } \ No newline at end of file diff --git a/SAS/TMSS/frontend/tmss_webapp/src/routes/Reservation/reservation.list.js b/SAS/TMSS/frontend/tmss_webapp/src/routes/Reservation/reservation.list.js index 6ab3642c1404051e0582f065348994725181fe41..0cacc3d2816357144c4c32627eef1459f5257c42 100644 --- a/SAS/TMSS/frontend/tmss_webapp/src/routes/Reservation/reservation.list.js +++ b/SAS/TMSS/frontend/tmss_webapp/src/routes/Reservation/reservation.list.js @@ -1,13 +1,13 @@ -import React, { Component } from 'react'; +import React, { Component ,useEffect} from 'react'; import _ from 'lodash'; import moment from 'moment'; import { DataTable } from 'primereact/datatable'; +import { Calendar } from 'primereact/calendar'; import { Column } from 'primereact/column'; import { Dropdown } from 'primereact/dropdown'; - -import "flatpickr/dist/flatpickr.css"; -import Flatpickr from "react-flatpickr"; -import confirmDatePlugin from "flatpickr/dist/plugins/confirmDate/confirmDate"; +import { Panel } from 'primereact/panel'; +import { Button } from 'primereact/button'; +import {InputSwitch} from 'primereact/inputswitch' import { CustomDialog } from '../../layout/components/CustomDialog'; import { appGrowl } from '../../layout/components/AppGrowl'; @@ -18,80 +18,81 @@ import PageHeader from '../../layout/components/PageHeader'; import UnitService from '../../utils/unit.converter'; import UIConstants from '../../utils/ui.constants'; import Validator from '../../utils/validator'; - -import ReservationService from '../../services/reservation.service'; +import ReservationService from '../../services/reservation.service'; import CycleService from '../../services/cycle.service'; import UtilService from '../../services/util.service'; import AuthStore from '../../authenticate/auth.store'; import AuthUtil from '../../utils/auth.util'; import AccessDenied from '../../layout/components/AccessDenied'; + import Websocket from 'react-websocket'; -export class ReservationList extends Component{ +export class ReservationList extends Component { lsKeySortColumn = "ReservationListSortData"; - constructor(props){ + constructor(props) { super(props); this.state = { validFields: {}, - fStartTime: '', // Filter Start time + fStartTime: '', fEndTime: '', // Filter End Time reservationsList: [], cycle: '', errors: {}, + syncWithCalendar : true, // Filter Start time dialog: {}, defaultcolumns: [{ - name: {name:"System Id"}, - description: {name:"Description"}, + name: { name: "System Id" }, + description: { name: "Description" }, start_time: { name: "Start Time", filter: "flatpickrDateRange", - format:UIConstants.CALENDAR_DATETIME_FORMAT + format: UIConstants.CALENDAR_DATETIME_FORMAT }, stop_time: { name: "End Time", filter: "flatpickrDateRange", - format:UIConstants.CALENDAR_DATETIME_FORMAT + format: UIConstants.CALENDAR_DATETIME_FORMAT }, - duration:{ - name:"Duration (Days HH:mm:ss)", - format:UIConstants.CALENDAR_TIME_FORMAT, + duration: { + name: "Duration (Days HH:mm:ss)", + format: UIConstants.CALENDAR_TIME_FORMAT, filter: "durationWithDaysMinMax", }, reservation_type: { - name:"Reservation Type", - filter:"select" + name: "Reservation Type", + filter: "select" }, subject: { - name:"Subject", - filter:"select" + name: "Subject", + filter: "select" }, planned: { name: "Planned", - filter:"switch" + filter: "switch" }, - stations:{ + stations: { name: "Stations", - filter:"multiselect" + filter: "multiselect" }, - fixed_time: { + fixed_time: { name: "FixedTime", - filter:"switch" + filter: "switch" }, dynamic: { name: "Dynamic", - filter:"switch" + filter: "switch" }, project_exclusive: { name: "Fixed project", - filter:"switch" + filter: "switch" }, project_id: { name: "Project", - filter:"select" + filter: "select" }, expert: { name: "Expert", - filter:"switch" + filter: "switch" }, hba_rfi: { name: "HBA-RFI", @@ -113,29 +114,29 @@ export class ReservationList extends Component{ }, actionpath: "actionpath" }], - optionalcolumns: [{ - id: {name:"ID"}, - + optionalcolumns: [{ + id: { name: "ID" }, + }], columnclassname: [{ "ID": "filter-input-50", "System Id": "filter-input-100", "Description": "filter-input-100", - "Duration (Days HH:mm:ss)":"filter-input-150", - "Reservation type":"filter-input-100", - "Subject":"filter-input-75", - "Planned":"filter-input-50", - "Stations":"filter-input-150,multi-select", - "FixedTime":"filter-input-50", - "Dynamic":"filter-input-50", - "Fixed project":"filter-input-50", - "Expert":"filter-input-50", - "HBA-RFI":"filter-input-50", - "LBA-RFI":"filter-input-50", - "Start Time":"filter-input-150", - "End Time":"filter-input-150", - "Created at":"filter-input-150", - "Updated at":"filter-input-150", + "Duration (Days HH:mm:ss)": "filter-input-150", + "Reservation type": "filter-input-100", + "Subject": "filter-input-75", + "Planned": "filter-input-50", + "Stations": "filter-input-150,multi-select", + "FixedTime": "filter-input-50", + "Dynamic": "filter-input-50", + "Fixed project": "filter-input-50", + "Expert": "filter-input-50", + "HBA-RFI": "filter-input-50", + "LBA-RFI": "filter-input-50", + "Start Time": "filter-input-150", + "End Time": "filter-input-150", + "Created at": "filter-input-150", + "Updated at": "filter-input-150", }], columnOrders: [ "ID", @@ -158,7 +159,7 @@ export class ReservationList extends Component{ "Created at", "Updated at" ], - defaultSortColumn: [{id: "System Id", desc: false}], + defaultSortColumn: [{ id: "System Id", desc: false }], isLoading: true, cycleList: [], userrole: AuthStore.getState() @@ -166,15 +167,14 @@ export class ReservationList extends Component{ this.reservationTypeOptionList = []; this.subjectsOptionList = []; this.stationList = []; - // let optionsList = new Set(); this.filterQry = ''; this.orderBy = ''; this.limit = 10; - this.offset = 0; + this.offset = 0; this.currentPageSize = 10; this.tableInstance = null; - this.reservations= []; - this.cycleList= []; + this.reservations = []; + this.cycleList = []; this.selectedRows = []; this.totalPage = 0; this.pageUpdated = true; @@ -196,78 +196,81 @@ export class ReservationList extends Component{ this.refreshReservationList = this.refreshReservationList.bind(this); this.updateReservation = this.updateReservation.bind(this); } - + async componentDidMount() { - this. setToggleBySorting(); + this.setToggleBySorting(); await this.getFilterColumns(); this.cycleList = await CycleService.getAllCycles(); this.setLocalFilters(); - await this.setState({ + this.setState({ isLoading: false, cycleList: this.cycleList, reservationsList: this.reservations, }); } + + + /** * Set Top filters when the state changed or while init the page */ setLocalFilters() { - let filters = UtilService.localStore({ type: 'get', key: "reservation_list"}); + let filters = UtilService.localStore({ type: 'get', key: "reservation_list" }); if (filters) { - let filter = _.find(filters, {'id': 'CycleId'}); + let filter = _.find(filters, { 'id': 'CycleId' }); if (filter) { - this.setState({cycle: filter.value}); + this.setState({ cycle: filter.value }); } - filter = _.find(filters, {'id': 'Start Time'}); + filter = _.find(filters, { 'id': 'Start Time' }); if (filter) { const values = filter.value; - this.setState({fStartTime: values[0]}); - } else { - this.setState({fStartTime: '', cycle: ''}); + this.setState({ fStartTime: new Date(values[0]) }); + } else { + this.setState({ fStartTime: '', cycle: '' }); } - filter = _.find(filters, {'id': 'End Time'}); + filter = _.find(filters, { 'id': 'End Time' }); if (filter) { const values = filter.value; - this.setState({fEndTime: values.length === 2 ? values[1] : values[0]}); - } else { - this.setState({fEndTime: '', cycle: ''}); + this.setState({ fEndTime: values.length === 2 ? new Date(values[1]) : new Date(values[0]) }); + } else { + this.setState({ fEndTime:undefined, cycle: '' }); } } - let filterStartTime = _.find(filters, function(filter){ - return (filter.id === 'Start Time' && filter.value.length>0); + let filterStartTime = _.find(filters, function (filter) { + return (filter.id === 'Start Time' && filter.value.length > 0); }); - let filterEndTime = _.find(filters, function(filter){ - return (filter.id === 'End Time' && filter.value.length>0) + let filterEndTime = _.find(filters, function (filter) { + return (filter.id === 'End Time' && filter.value.length > 0) }); if (!filterStartTime && !filterEndTime) { - this.setState({cycle: ''}); + this.setState({ cycle: '' }); } } - toggleBySorting=(sortData) => { + toggleBySorting = (sortData) => { UtilService.localStore({ type: 'set', key: this.lsKeySortColumn, value: sortData }); } - setToggleBySorting() { + setToggleBySorting() { let sortData = UtilService.localStore({ type: 'get', key: this.lsKeySortColumn }); - if(sortData){ - if(Object.prototype.toString.call(sortData) === '[object Array]'){ + if (sortData) { + if (Object.prototype.toString.call(sortData) === '[object Array]') { this.defaultSortColumn = sortData; } - else{ - this.defaultSortColumn = [{...sortData}]; + else { + this.defaultSortColumn = [{ ...sortData }]; } } this.defaultSortColumn = this.defaultSortColumn || []; - UtilService.localStore({ type: 'set', key: this.lsKeySortColumn, value: [...this.defaultSortColumn] }); + UtilService.localStore({ type: 'set', key: this.lsKeySortColumn, value: [...this.defaultSortColumn] }); } - - mergeResourceWithReservation ( reservation, params) { - if( params ){ + + mergeResourceWithReservation(reservation, params) { + if (params) { Object.keys(params).map((key) => ( - ['name', 'description'].indexOf(key)<0? reservation[key]= params[key] : '' - )); + ['name', 'description'].indexOf(key) < 0 ? reservation[key] = params[key] : '' + )); } return reservation; } @@ -277,30 +280,31 @@ export class ReservationList extends Component{ * Here to search use Cycle.start time as Reservation Start time and Cycle.stop time as Reservation End time */ async filterTableData(cycleValues) { - let filters = UtilService.localStore({ type: 'get', key: "reservation_list"}); - _.remove(filters, function(filter) { + let filters = UtilService.localStore({ type: 'get', key: "reservation_list" }); + _.remove(filters, function (filter) { return filter.id === 'Cycle' || filter.id === 'CycleId' || filter.id === 'Start Time' || filter.id === 'End Time'; }); if (!cycleValues) { - UtilService.localStore({ type: 'set', key: 'reservation_list', value: filters}); - await this.setState({cycle: '',fStartTime:'', fEndTime: ''}); + UtilService.localStore({ type: 'set', key: 'reservation_list', value: filters }); + this.setState({ cycle: '', fStartTime: '', fEndTime: '' }); this.setTableProperty(filters, 'Filter'); await this.fetchTableData(null); } else { - const filterCycleList = _.filter(this.cycleList, function(o) { return o.name === cycleValues }); + const filterCycleList = _.filter(this.cycleList, function (o) { return o.name === cycleValues }); if (filterCycleList) { let cycle = filterCycleList[0]; - this.setState({fStartTime: cycle['start'], fEndTime: cycle['stop']}); - let cycleFilter = [{'id': 'Cycle', value:[cycle['start'], cycle['stop']]}]; - cycleFilter.push({'id': 'CycleId', value:cycle['name']}); - cycleFilter.push({'id': 'Start Time', value:[cycle['start'], '']}); - cycleFilter.push({'id': 'End Time', value:['', cycle['stop']]}); - filters = [...cycleFilter, ...filters]; - UtilService.localStore({ type: 'set', key: 'reservation_list', value: filters}); + + this.setState({ fStartTime: new Date(cycle['start']), fEndTime: new Date(cycle['stop']) }); + let cycleFilter = [{ 'id': 'Cycle', value: [cycle['start'], cycle['stop']] }]; + cycleFilter.push({ 'id': 'CycleId', value: cycle['name'] }); + cycleFilter.push({ 'id': 'Start Time', value: [cycle['start'], ''] }); + cycleFilter.push({ 'id': 'End Time', value: ['', cycle['stop']] }); + filters = [...cycleFilter, ...filters]; + UtilService.localStore({ type: 'set', key: 'reservation_list', value: filters }); this.setTableProperty(filters, 'Filter'); await this.fetchTableData(null); } - await this.setState({cycle: cycleValues,}); + this.setState({ cycle: cycleValues, }); } this.pageUpdated = true; } @@ -309,13 +313,13 @@ export class ReservationList extends Component{ Reset the Reserved Start Datetime filter */ async resetStartDateTime() { - await this.setState({'fStartTime': ''}); - let filters = UtilService.localStore({ type: 'get', key: "reservation_list"}); - _.remove(filters, function(filter) { - let result = filter.id === 'Start Time'; + this.setState({ 'fStartTime': ''}); + let filters = UtilService.localStore({ type: 'get', key: "reservation_list" }); + _.remove(filters, function (filter) { + let result = filter.id === 'Start Time'; return result; }); - UtilService.localStore({ type: 'set', key: 'reservation_list', value: filters}); + UtilService.localStore({ type: 'set', key: 'reservation_list', value: filters }); this.setTableProperty(filters, 'Filter'); await this.fetchTableData(null); } @@ -324,13 +328,13 @@ export class ReservationList extends Component{ Reset the Reserved End Datetime filter */ async resetEndDateTime() { - await this.setState({'fEndTime': ''}); - let filters = UtilService.localStore({ type: 'get', key: "reservation_list"}); - _.remove(filters, function(filter) { - let result = filter.id === 'End Time'; + await this.setState({ 'fEndTime': '' }); + let filters = UtilService.localStore({ type: 'get', key: "reservation_list" }); + _.remove(filters, function (filter) { + let result = filter.id === 'End Time'; return result; }); - UtilService.localStore({ type: 'set', key: 'reservation_list', value: filters}); + UtilService.localStore({ type: 'set', key: 'reservation_list', value: filters }); this.setTableProperty(filters, 'Filter'); await this.fetchTableData(null); } @@ -338,8 +342,8 @@ export class ReservationList extends Component{ /** - To clear all filters above the table, it will be called from ViewTable-ClearAllFilter */ - clearAllFilter() { - this.setState({cycle: '', fStartTime: '', fEndTime: ''}); + clearAllFilter() { + this.setState({ cycle: '', fStartTime: '', fEndTime: '' }); } /** @@ -369,21 +373,21 @@ export class ReservationList extends Component{ * @param {*} value - Date Value */ async setDateRange() { - let filters = UtilService.localStore({ type: 'get', key: "reservation_list"}); - _.remove(filters, function(filter) { - let result = filter.id === 'Start Time' || filter.id === 'End Time'; + let filters = UtilService.localStore({ type: 'get', key: "reservation_list" }); + _.remove(filters, function (filter) { + let result = filter.id === 'Start Time' || filter.id === 'End Time'; return result; }); - await this.setState({cycle: ''}); - let reservedTimeFilter = [{'id': 'Start Time', value:[Validator.isEmpty(this.state.fStartTime)?'':moment(new Date(this.state.fStartTime)).format("YYYY-MM-DDTHH:mm:SS"), '']}]; - reservedTimeFilter.push({'id': 'End Time', value:['', Validator.isEmpty(this.state.fEndTime)?'':moment(new Date(this.state.fEndTime)).format("YYYY-MM-DDTHH:mm:SS")]}); - filters = [...reservedTimeFilter, ...filters]; + this.setState({ cycle: '' }); + let reservedTimeFilter = [{ 'id': 'Start Time', value: [Validator.isEmpty(this.state.fStartTime) ? '' : moment(new Date(this.state.fStartTime)).format("YYYY-MM-DDTHH:mm:SS"), ''] }]; + reservedTimeFilter.push({ 'id': 'End Time', value: ['', Validator.isEmpty(this.state.fEndTime) ? '' : moment(new Date(this.state.fEndTime)).format("YYYY-MM-DDTHH:mm:SS")] }); + filters = [...reservedTimeFilter, ...filters]; this.setTableProperty(filters, 'Filter'); - UtilService.localStore({ type: 'set', key: 'reservation_list', value: filters}); + UtilService.localStore({ type: 'set', key: 'reservation_list', value: filters }); await this.fetchTableData(null); this.pageUpdated = true; } - + /** * Set selected rows form view table * @param {Row} selectedRows - rows selected in view table @@ -396,67 +400,67 @@ export class ReservationList extends Component{ /** * Callback function to close the dialog prompted. */ - closeDialog() { - this.setState({dialogVisible: false}); + closeDialog() { + this.setState({ dialogVisible: false }); } - closeList(){ - this.props.history.length>1?this.props.history.goBack():this.props.history.push(`/su/timelineview/week`); + closeList() { + this.props.history.length > 1 ? this.props.history.goBack() : this.props.history.push(`/su/timelineview/week`); } /** * Create confirmation dialog details */ confirmDeleteReservations() { - if(this.selectedRows.length === 0) { - appGrowl.show({severity: 'info', summary: 'Select Row', detail: 'Select Reservation to delete.'}); - } else { + if (this.selectedRows.length === 0) { + appGrowl.show({ severity: 'info', summary: 'Select Row', detail: 'Select Reservation to delete.' }); + } else { let dialog = {}; dialog.type = "confirmation"; - dialog.header= "Confirm to Delete Reservation(s)"; + dialog.header = "Confirm to Delete Reservation(s)"; dialog.detail = "Do you want to delete the selected Reservation(s)?"; dialog.content = this.getReservationDialogContent; - dialog.actions = [{id: 'yes', title: 'Delete', callback: this.deleteReservations, className:'act-btn-dispose'}, - {id: 'no', title: 'Cancel', className:'act-btn-cancel', callback: this.closeDialog}]; + dialog.actions = [{ id: 'yes', title: 'Delete', callback: this.deleteReservations, className: 'act-btn-dispose' }, + { id: 'no', title: 'Cancel', className: 'act-btn-cancel', callback: this.closeDialog }]; dialog.onSubmit = this.deleteReservations; dialog.width = '55vw'; dialog.showIcon = false; - this.setState({dialog: dialog, dialogVisible: true}); + this.setState({ dialog: dialog, dialogVisible: true }); } } - /** - * Prepare Reservation(s) details to show on confirmation dialog - */ - getReservationDialogContent() { - return <> - <DataTable value={this.selectedRows} resizableColumns columnResizeMode="expand" className="card" style={{paddingLeft: '0em'}}> - <Column field="id" header="Reservation Id"></Column> - <Column field="name" header="Name"></Column> - <Column field="start_time" header="Start time"></Column> - <Column field="stop_time" header="End Time"></Column> - </DataTable> + /** + * Prepare Reservation(s) details to show on confirmation dialog + */ + getReservationDialogContent() { + return <> + <DataTable value={this.selectedRows} resizableColumns columnResizeMode="expand" className="card" style={{ paddingLeft: '0em' }}> + <Column field="id" header="Reservation Id"></Column> + <Column field="name" header="Name"></Column> + <Column field="start_time" header="Start time"></Column> + <Column field="stop_time" header="End Time"></Column> + </DataTable> </> } /** * Delete selected Reservation(s) */ - async deleteReservations() { + async deleteReservations() { let hasError = false; - for(const reservation of this.selectedRows) { - if(!await ReservationService.deleteReservation(reservation.id)) { + for (const reservation of this.selectedRows) { + if (!await ReservationService.deleteReservation(reservation.id)) { hasError = true; } } - if(hasError){ - appGrowl.show({severity: 'error', summary: 'error', detail: 'Error while deleting Reservation(s)'}); - this.setState({dialogVisible: false}); - } else { + if (hasError) { + appGrowl.show({ severity: 'error', summary: 'error', detail: 'Error while deleting Reservation(s)' }); + this.setState({ dialogVisible: false }); + } else { this.selectedRows = []; - this.setState({dialogVisible: false}); + this.setState({ dialogVisible: false }); this.componentDidMount(); - appGrowl.show({severity: 'success', summary: 'Success', detail: 'Reservation(s) deleted successfully'}); + appGrowl.show({ severity: 'success', summary: 'Success', detail: 'Reservation(s) deleted successfully' }); } } @@ -473,28 +477,28 @@ export class ReservationList extends Component{ let tempKey = key; tmpColMap['orgField'] = tempKey; tmpColMap['tmpField'] = tempKey; - if(columnDef[key]) { + if (columnDef[key]) { tmpColMap['displayName'] = columnDef[key]['name']; } this.columnMap.push(tmpColMap); //Set Enable/Disable the Filter & SortBy in each column - if(apiFilters.data.filters[tempKey]) { + if (apiFilters.data.filters[tempKey]) { columnDef[key]['disableSortBy'] = !_.includes(apiFilters.data.ordering, tempKey); columnDef[key]['disableFilters'] = false; - if( (tempKey !== 'start_time' && tempKey !== 'stop_time') && UIConstants.FILTER_MAP[apiFilters.data.filters[tempKey].type]) { + if ((tempKey !== 'start_time' && tempKey !== 'stop_time') && UIConstants.FILTER_MAP[apiFilters.data.filters[tempKey].type]) { columnDef[key]['filter'] = UIConstants.FILTER_MAP[apiFilters.data.filters[tempKey].type]; } - } else if (key === 'project_id' && apiFilters.data.filters['project']) { + } else if (key === 'project_id' && apiFilters.data.filters['project']) { columnDef[key]['disableSortBy'] = !_.includes(apiFilters.data.ordering, 'project'); columnDef[key]['disableFilters'] = false; columnDef[key]['filter'] = ''; - } else if (key === 'stations' && apiFilters.data.filters['stations_any']) { + } else if (key === 'stations' && apiFilters.data.filters['stations_any']) { columnDef[key]['disableSortBy'] = false; columnDef[key]['disableFilters'] = false; - } else if (key === 'duration' && apiFilters.data.filters['duration_min']) { + } else if (key === 'duration' && apiFilters.data.filters['duration_min']) { columnDef[key]['disableSortBy'] = !_.includes(apiFilters.data.ordering, 'duration_min'); columnDef[key]['disableFilters'] = false; - } else if (columnDef[key]['name']) { + } else if (columnDef[key]['name']) { columnDef[key]['disableSortBy'] = true; columnDef[key]['disableFilters'] = true; } @@ -509,13 +513,18 @@ export class ReservationList extends Component{ */ removeArrayIndex(arrayValue, keys) { keys.forEach(key => { - let index = arrayValue.indexOf(key) ; + let index = arrayValue.indexOf(key); if (index !== -1) { arrayValue.splice(index, 1); } }); } - + + + setsyncWithCalendar = (value) =>{ + this.setState({syncWithCalendar : value}); + + } /** * Remove column definition * @param {column definition array} arrayValue @@ -535,12 +544,12 @@ export class ReservationList extends Component{ let tmpDefaulColumns = _.cloneDeep(this.state.defaultcolumns[0]); let tmpOptionalColumns = _.cloneDeep(this.state.optionalcolumns[0]); let tmpColumnOrders = _.cloneDeep(this.state.columnOrders); - - if(apiFilters) { + + if (apiFilters) { this.getDropDownOptionList(apiFilters); tmpDefaulColumns = this.getAPIFilter(apiFilters, tmpDefaulColumns); tmpOptionalColumns = this.getAPIFilter(apiFilters, tmpOptionalColumns); - await this.setState({tmpDefaulcolumns: [tmpDefaulColumns], tmpOptionalcolumns:[tmpOptionalColumns], tmpColumnOrders: tmpColumnOrders, columnMap: this.columnMap}) + await this.setState({ tmpDefaulcolumns: [tmpDefaulColumns], tmpOptionalcolumns: [tmpOptionalColumns], tmpColumnOrders: tmpColumnOrders, columnMap: this.columnMap }) } } @@ -548,7 +557,7 @@ export class ReservationList extends Component{ * Get Status list frol filter * @param {Array} suFilters */ - getDropDownOptionList(apiFilters) { + getDropDownOptionList(apiFilters) { this.getOptions('reservation_type', apiFilters); this.getOptions('subject', apiFilters); this.stationList = []; @@ -560,10 +569,10 @@ export class ReservationList extends Component{ apiFilter.data.filters[key].choices.forEach(choice => { if (key === 'subject') { this.subjectsOptionList.push(choice.value); - } else if(key === 'reservation_type') { - this.reservationTypeOptionList.push(choice.value); - } else if (key === 'stations_any') { - this.stationList.push({name: choice.display_name, value:choice.value}); + } else if (key === 'reservation_type') { + this.reservationTypeOptionList.push(choice.value); + } else if (key === 'stations_any') { + this.stationList.push({ name: choice.display_name, value: choice.value }); } }) } @@ -575,83 +584,83 @@ export class ReservationList extends Component{ * @returns */ async fetchTableData(state) { - // await this.getFilterColumns(); + // await this.getFilterColumns(); await this.setLocalFilters(); this.filterQry = ''; this.orderBy = ''; this.pageUpdated = true; - this.setState({loadingStatus:true}); - let filters = UtilService.localStore({ type: 'get', key: "reservation_list"}); - const sortByValue = UtilService.localStore({ type: 'get', key: "ReservationListSortData"}); - if(filters.length > 0 ) { - for( const filter of filters) { + this.setState({ loadingStatus: true }); + let filters = UtilService.localStore({ type: 'get', key: "reservation_list" }); + const sortByValue = UtilService.localStore({ type: 'get', key: "ReservationListSortData" }); + if (filters.length > 0) { + for (const filter of filters) { if (filter.id === 'Start Time') { const values = filter.value; if (values[0] && values[0] !== '') { - this.filterQry += 'start_time_min='+ moment(new Date(values[0])).format("YYYY-MM-DD HH:mm:SS&"); + this.filterQry += 'start_time_min=' + moment(new Date(values[0])).format("YYYY-MM-DD HH:mm:SS&"); } if (values[1] && values[1] !== '') { - this.filterQry += 'start_time_max='+moment(new Date(values[1])).format("YYYY-MM-DD HH:mm:ss&"); + this.filterQry += 'start_time_max=' + moment(new Date(values[1])).format("YYYY-MM-DD HH:mm:ss&"); } - } else if (filter.id === 'End Time') { + } else if (filter.id === 'End Time') { const values = filter.value; if (values[0] && values[0] !== '') { - this.filterQry += 'stop_time_min='+ moment(new Date(values[0])).format("YYYY-MM-DD 00:00:00&"); + this.filterQry += 'stop_time_min=' + moment(new Date(values[0])).format("YYYY-MM-DD 00:00:00&"); } if (values[1] && values[1] !== '') { - this.filterQry += 'stop_time_max='+moment(new Date(values[1])).format("YYYY-MM-DD 23:59:59&"); + this.filterQry += 'stop_time_max=' + moment(new Date(values[1])).format("YYYY-MM-DD 23:59:59&"); } - } else if (filter.id === 'Project') { - this.filterQry += 'project='+ encodeURIComponent(filter.value) +'&' ; - } else if (filter.id === 'Stations') { - const stationFilterType = _.find(filters, {id:'stationFilterType'}); - if(filter.value.length>0) { + } else if (filter.id === 'Project') { + this.filterQry += 'project=' + encodeURIComponent(filter.value) + '&'; + } else if (filter.id === 'Stations') { + const stationFilterType = _.find(filters, { id: 'stationFilterType' }); + if (filter.value.length > 0) { const values = _.split(filter.value, ","); - for ( const value of values) { - if(stationFilterType && stationFilterType.value === 'All') { - this.filterQry += 'stations_all='+value+"&"; - } else { - this.filterQry += 'stations_any='+value+"&"; + for (const value of values) { + if (stationFilterType && stationFilterType.value === 'All') { + this.filterQry += 'stations_all=' + value + "&"; + } else { + this.filterQry += 'stations_any=' + value + "&"; } } } - } else if (filter.id === 'Duration (Days HH:mm:ss)' && filter.value !== '') { - let columnDetails = _.find(this.state.columnMap, {displayName:filter.id}); + } else if (filter.id === 'Duration (Days HH:mm:ss)' && filter.value !== '') { + let columnDetails = _.find(this.state.columnMap, { displayName: filter.id }); const values = _.split(filter.value, ","); if ((values.length === 0) || (values[0] === '' || values[0] === '0') && (values[1] === '' || values[1] === '0')) { this.filterQry += "duration_isnull=false&"; - } else { + } else { if (values[0].includes(":")) { - this.filterQry += columnDetails.orgField+"_min" +'='+UnitService.getDDDHHmmssToSecs(values[0])+'&'; + this.filterQry += columnDetails.orgField + "_min" + '=' + UnitService.getDDDHHmmssToSecs(values[0]) + '&'; } if (values[1].includes(":")) { - this.filterQry += columnDetails.orgField+"_max" +'='+UnitService.getDDDHHmmssToSecs(values[1])+'&'; + this.filterQry += columnDetails.orgField + "_max" + '=' + UnitService.getDDDHHmmssToSecs(values[1]) + '&'; } } - } else if (filter.id === 'durationNull') { - this.filterQry += "duration_isnull="+filter.value+'&'; - } else { - let columnDetails = _.find(this.state.columnMap, {displayName:filter.id}); - if(columnDetails) { - this.filterQry += columnDetails.orgField +'='+ encodeURIComponent(filter.value) +'&' + } else if (filter.id === 'durationNull') { + this.filterQry += "duration_isnull=" + filter.value + '&'; + } else { + let columnDetails = _.find(this.state.columnMap, { displayName: filter.id }); + if (columnDetails) { + this.filterQry += columnDetails.orgField + '=' + encodeURIComponent(filter.value) + '&' } - } + } } } - let sortBy = state && state.sortBy?state.sortBy[0]:(sortByValue)?sortByValue:null; + let sortBy = state && state.sortBy ? state.sortBy[0] : (sortByValue) ? sortByValue : null; if (sortBy) { this.defaultSortColumn = sortBy; - UtilService.localStore({ type: 'set', key: this.lsKeySortColumn ,value:sortBy}); - let columnDetails = _.find(this.state.columnMap, {displayName:sortBy.id}); - if(columnDetails) { - this.orderBy = 'ordering='+((sortBy.desc)?'-':'')+columnDetails.orgField; + UtilService.localStore({ type: 'set', key: this.lsKeySortColumn, value: sortBy }); + let columnDetails = _.find(this.state.columnMap, { displayName: sortBy.id }); + if (columnDetails) { + this.orderBy = 'ordering=' + ((sortBy.desc) ? '-' : '') + columnDetails.orgField; } } - this.filterQry = this.filterQry.substring(0,this.filterQry.length-1); - + this.filterQry = this.filterQry.substring(0, this.filterQry.length - 1); + this.currentPageSize = (state && state.pageSize) ? state.pageSize : this.currentPageSize; - let offset = (state && state.pageIndex) ? state.pageIndex*this.currentPageSize : 0; + let offset = (state && state.pageIndex) ? state.pageIndex * this.currentPageSize : 0; await this.getReservationList(this.filterQry, this.orderBy, this.currentPageSize, offset); return [this.state.reservationsList, this.totalPage]; } @@ -660,16 +669,16 @@ export class ReservationList extends Component{ * Get reservation list */ async getReservationList(filterQry, orderBy, limit, offset) { - const promises = [ + const promises = [ ReservationService.getReservationsWithFilter(filterQry, orderBy, limit, offset), ]; const permission = await AuthUtil.getUserRolePermission(); - this.setState({userrole: permission}); - + this.setState({ userrole: permission }); + this.reservations = []; Promise.all(promises).then(async responses => { - this.totalPage = responses[0].data?responses[0].data.count:0; - for( const response of responses[0].data.results){ + this.totalPage = responses[0].data ? responses[0].data.count : 0; + for (const response of responses[0].data.results) { let reservation = this.updateReservation(response, response); this.reservations.push(reservation); } @@ -685,24 +694,24 @@ export class ReservationList extends Component{ }); } - updateReservation (reservation, response) { - reservation = this.mergeResourceWithReservation( reservation, response.specifications_doc.activity) ; - reservation = this.mergeResourceWithReservation( reservation, response.specifications_doc.effects ); - reservation = this.mergeResourceWithReservation( reservation, response.specifications_doc.schedulability ); + updateReservation(reservation, response) { + reservation = this.mergeResourceWithReservation(reservation, response.specifications_doc.activity); + reservation = this.mergeResourceWithReservation(reservation, response.specifications_doc.effects); + reservation = this.mergeResourceWithReservation(reservation, response.specifications_doc.schedulability); reservation['reservation_type'] = reservation.type; - if (response.specifications_doc.resources.stations ) { + if (response.specifications_doc.resources.stations) { reservation['stations'] = response.specifications_doc.resources.stations.join(', '); } else { reservation['stations'] = ''; } - if(reservation.duration === null || reservation.duration === ''){ + if (reservation.duration === null || reservation.duration === '') { reservation.duration = 'Unknown'; - reservation['stop_time']= 'Unknown'; + reservation['stop_time'] = 'Unknown'; } else { reservation.duration = UnitService.getSecsToDDHHmmss(reservation.duration); - reservation['stop_time']= moment(reservation['stop_time']).format(UIConstants.CALENDAR_DATETIME_FORMAT); + reservation['stop_time'] = moment(reservation['stop_time']).format(UIConstants.CALENDAR_DATETIME_FORMAT); } - reservation['start_time']= moment(reservation['start_time']).format(UIConstants.CALENDAR_DATETIME_FORMAT); + reservation['start_time'] = moment(reservation['start_time']).format(UIConstants.CALENDAR_DATETIME_FORMAT); reservation['actionpath'] = `/reservation/view/${reservation.id}`; reservation['canSelect'] = true; return reservation; @@ -715,11 +724,11 @@ export class ReservationList extends Component{ */ getFilterOptions(id) { let options = null; - if(id && id === 'Reservation Type') { + if (id && id === 'Reservation Type') { options = this.reservationTypeOptionList; - } else if (id && id === 'Subject') { + } else if (id && id === 'Subject') { options = this.subjectsOptionList; - } else if (id === 'Stations') { + } else if (id === 'Stations') { this.stationList = _.orderBy(this.stationList, ['name'], ['asc']); return this.stationList; } @@ -730,16 +739,16 @@ export class ReservationList extends Component{ /** * Function to call wnen websocket is connected */ - onConnect() { - try{ + onConnect() { + try { console.log("WS Opened"); const userDets = localStorage.getItem("user"); if (userDets) { - this.websocket.sendMessage(JSON.stringify({"token": JSON.parse(userDets).websocket_token})); + this.websocket.sendMessage(JSON.stringify({ "token": JSON.parse(userDets).websocket_token })); console.log("Auth token submitted"); } - }catch (err) { - console.log('err',err) + } catch (err) { + console.log('err', err) } } @@ -758,7 +767,7 @@ export class ReservationList extends Component{ if (data) { console.log('received websocket data:', data) const jsonData = JSON.parse(data); - this.refreshReservationList(jsonData); + this.refreshReservationList(jsonData); } } @@ -776,184 +785,155 @@ export class ReservationList extends Component{ if (count > reservationList.length) { this.totalPage--; } - } else { - ReservationService.getReservationsWithFilter(('id='+jsonData.object_details.id+'&'+this.filterQry), this.orderBy, this.currentPageSize, this.offset).then(async (updatedReservation) => { - if (updatedReservation && updatedReservation.data.count>0) { + } else { + ReservationService.getReservationsWithFilter(('id=' + jsonData.object_details.id + '&' + this.filterQry), this.orderBy, this.currentPageSize, this.offset).then(async (updatedReservation) => { + if (updatedReservation && updatedReservation.data.count > 0) { let tmpRes = updatedReservation.data.results[0]; tmpRes = await this.updateReservation(tmpRes, _.cloneDeep(tmpRes)); if (tmpRes) { if (jsonData.action === 'create') { reservationList.push(tmpRes); this.totalPage++; - } else if (jsonData.action === 'update') { + } else if (jsonData.action === 'update') { _.remove(reservationList, function (reservation) { return reservation.id === tmpRes.id }); reservationList.push(tmpRes); } } - } else { + } else { const count = reservationList.length; _.remove(reservationList, function (reservation) { return reservation.id === jsonData.object_details.id }); if (count > reservationList.length) { this.totalPage--; } } - this.setState({reservationsList: reservationList}); + this.setState({ reservationsList: reservationList }); }); } - + break; - } + } default: { break; } } } + movetoCreate = () => { + this.props.history.push(`/reservation/create`); + } + render() { const permissions = this.state.userrole.userRolePermission.reservation; - return ( + return ( <React.Fragment> - <PageHeader location={this.props.location} title={'Reservation - List'} - actions={[{icon: 'fa-plus-square', - title:permissions.create?'Add Reservation': "Don't have permission to add new Reservation", - disabled: permissions.create? !permissions.create: true, - props : { pathname: `/reservation/create`}}, - {icon: 'fa-window-close', title:'Click to close Reservation list', type: 'button', actOn: 'click', props:{ callback: this.closeList }}]}/> - {this.state.isLoading? <AppLoader /> : (this.state.reservationsList) ? - <> - {permissions.list? - <> - <div className="p-select " style={{position: 'relative', marginTop: '-2em'}}> - <div className="p-field p-grid"> - <div className="col-lg-3 col-md-3 col-sm-12 ms-height"> - <span className="p-float-label"> - <Dropdown data-testid="cycle" id="cycle" optionLabel="name" optionValue="url" - value={this.state.cycle} - options={this.state.cycleList} - onChange={(e) => {this.filterTableData(e.value)}} - className="ms-width" - filter={true} - showClear={true} - showFilterClear={true} - tooltip="Select cycle to view reservations that start and end in the cycle (will not include those are reserved for unknown duration)" - /> - <label htmlFor="cycle" >Filter by Cycle</label> - </span> - </div> - <div className="col-lg-3 col-md-3 col-sm-6 ms-height" style={{ marginLeft: '1em'}}> - <span className="p-float-label"> - <Flatpickr data-enable-time data-input - id="fstartdate" - style={{width: '12em'}} - options={{ "inlineHideInput": true, - "wrap": true, - "enableSeconds": true, - "time_24hr": true, - "minuteIncrement": 1, - "allowInput": true, - "defaultHour": 0, - "plugins": [new confirmDatePlugin()] - }} - title="Select Reserved Between - From" - value={this.state.fStartTime} - onClose={this.setDateRange} - onChange={date => {this.setState({fStartTime :date})}} - > - <input type="text" data-input className={`p-inputtext p-component calendar-input`} placeholder="Reserved - From" /> - <button className="p-button p-component p-button-icon-only calendar-button" data-toggle - title="Click to select the date range" > - <i className="fas fa-calendar"></i> - </button> - <button className="p-button p-component p-button-icon-only calendar-reset" - onClick={this.resetStartDateTime} - title="Clear date range" > - <i className="pi pi-times" style={{color:'white', marginTop:'-2.85px'}} ></i> - </button> - </Flatpickr> - </span> - <label className={this.state.errors.fStartTime?"error":"info"} style={{position: 'relative', bottom: '27px'}}> - {this.state.errors.fStartTime ? this.state.errors.fStartTime : ""} - </label> - </div> - <div className="col-lg-3 col-md-3 col-sm-6 ms-height" style={{ marginLeft: '2em'}}> - <span className="p-float-label"> - <Flatpickr data-enable-time data-input - id="fenddate" - style={{width: '12em'}} - options={{ "inlineHideInput": true, - "wrap": true, - "enableSeconds": true, - "time_24hr": true, - "minuteIncrement": 1, - "allowInput": true, - "defaultHour": 0, - "plugins": [new confirmDatePlugin()] - }} - title="Select Reserved Between-To" - value={this.state.fEndTime} - onClose={this.setDateRange} - onChange={date => {this.setState({fEndTime :date})}} - > - <input type="text" data-input className={`p-inputtext p-component calendar-input`} placeholder="Reserved - To" /> - <button className="p-button p-component p-button-icon-only calendar-button" data-toggle - title="Click to select the date range" > - <i className="fas fa-calendar"></i> - </button> - <button className="p-button p-component p-button-icon-only calendar-reset" - onClick={this.resetEndDateTime} title="Clear date range" > - <i className="pi pi-times" style={{color:'white', marginTop:'-2.85px'}} ></i> - </button> - </Flatpickr> - </span> - <label className={this.state.errors.fEndTime?"error":"info"} style={{position: 'relative', bottom: '27px'}} > - {this.state.errors.fEndTime ? this.state.errors.fEndTime : ""} - </label> - </div> - </div> - - </div> - <div className="delete-option"> - <div > - <span className="p-float-label"> - <a href="#" onClick={permissions.delete?this.confirmDeleteReservations:()=>{}} - title={permissions.delete?"Delete selected Reservation(s)":"Don't have delete permission"}> - <i className={`fa fa-trash${permissions.delete?'':' fa-disabled'}`} aria-hidden="true" ></i> - </a> - </span> - </div> - </div> - <ViewTable - data={this.state.reservationsList} - defaultcolumns={this.state.tmpDefaulcolumns ? this.state.tmpDefaulcolumns : this.state.defaultcolumns} - optionalcolumns={this.state.tmpOptionalcolumns ? this.state.tmpOptionalcolumns : this.state.optionalcolumns} - columnclassname={this.state.columnclassname} - columnOrders={this.state.columnOrders} - defaultSortColumn={this.defaultSortColumn} - showaction="true" - paths={this.state.paths} - tablename="reservation_list" - showCSV= {true} - allowRowSelection={true} - onRowSelection = {this.onRowSelection} - toggleBySorting={(sortData) => this.toggleBySorting(sortData)} - lsKeySortColumn={this.lsKeySortColumn} - pageUpdated={this.pageUpdated} - storeFilter={true} - callBackFunction={this.fetchTableData} - showFilterOption={this.getFilterOptions} - totalPage={this.totalPage} - clearAllFuncCallback={this.clearAllFilter} // Callback function will call when the clearAllFilter called in ViewTable - tableInstanceRef={this.seTableInstanceRef} - /> - </>: <AccessDenied/>} - </> - : <div>No Reservation found </div> + <PageHeader location={this.props.location} title={'Reservation - List'} className="defaultrightpageHeader" + actions={[ + + + { + icon: 'pi-plus', + title: permissions.create ? 'Add Reservation' : "Don't have permission to add new Reservation", + disabled: permissions.create ? !permissions.create : true, + type: 'buttonv2', + actOn: 'click', + props: { callback: this.movetoCreate + + }}, + { icon: 'pi-trash', title: 'Delete selected Reservations', disabled: permissions.delete ? !permissions.delete : true , type: 'buttonv2', actOn: 'click', props: { callback:this.confirmDeleteReservations }}, + + { icon: 'pi-times', title: 'Click to close Reservation list', type: 'buttonv2', actOn: 'click', props: { callback: this.closeList } } + + + + + + + + + ]} /> + {this.state.isLoading ? <AppLoader /> : (this.state.reservationsList) ? + <> + {permissions.list ? + <> + + <Panel className="FilterPanel" header="Special Filters" > + <div className='divbox'> + <label htmlFor="cycle" >Filter by Cycle</label> + <Dropdown data-testid="cycle" id="cycle" optionLabel="name" optionValue="url" + value={this.state.cycle} + options={this.state.cycleList} + onChange={(e) => { this.filterTableData(e.value) }} + className="ms-width" + filter={true} + showClear={true} + showFilterClear={true} + tooltip="Select cycle to view reservations that start and end in the cycle (will not include those are reserved for unknown duration)" + /> + </div> + <div className='divbox'> + <label htmlFor="fstartdate" >Reserved From</label> + <Calendar id="fstartdate" showIcon + showTime + dateFormat="yy-mm-dd" + hourFormat="24" + + value={this.state.fStartTime} + onChange={(e) => this.setState({ fStartTime: e.value })} + /> + <Button onClick={this.resetStartDateTime} title="Clear date range" > <i className="pi pi-times" ></i> </Button> + </div> + <div className='divbox'> + <label htmlFor="fenddate" >Reserved To</label> + <Calendar id="fenddate" showIcon + + showTime + dateFormat="yy-mm-dd" + hourFormat="24" + value={this.state.fEndTime} + onChange={(e) => this.setState({ fEndTime: e.value })} + /> + <Button onClick={this.resetEndDateTime} title="Clear date range"> <i className="pi pi-times" ></i> </Button> + </div> + + + </Panel> + + + + + <ViewTable + data={this.state.reservationsList} + defaultcolumns={this.state.tmpDefaulcolumns ? this.state.tmpDefaulcolumns : this.state.defaultcolumns} + optionalcolumns={this.state.tmpOptionalcolumns ? this.state.tmpOptionalcolumns : this.state.optionalcolumns} + columnclassname={this.state.columnclassname} + columnOrders={this.state.columnOrders} + defaultSortColumn={this.defaultSortColumn} + showaction="true" + paths={this.state.paths} + tablename="reservation_list" + showCSV={true} + allowRowSelection={true} + onRowSelection={this.onRowSelection} + toggleBySorting={(sortData) => this.toggleBySorting(sortData)} + lsKeySortColumn={this.lsKeySortColumn} + pageUpdated={this.pageUpdated} + storeFilter={true} + callBackFunction={this.fetchTableData} + showFilterOption={this.getFilterOptions} + totalPage={this.totalPage} + clearAllFuncCallback={this.clearAllFilter} // Callback function will call when the clearAllFilter called in ViewTable + tableInstanceRef={this.seTableInstanceRef} + /> + + </> : <AccessDenied />} + </> + : <div>No Reservation found </div> } <CustomDialog type="confirmation" visible={this.state.dialogVisible} header={this.state.dialog.header} message={this.state.dialog.detail} actions={this.state.dialog.actions} content={this.state.dialog.content} width={this.state.dialog.width} showIcon={this.state.dialog.showIcon} - onClose={this.closeDialog} onCancel={this.closeDialog} onSubmit={this.state.dialog.onSubmit}/> + onClose={this.closeDialog} onCancel={this.closeDialog} onSubmit={this.state.dialog.onSubmit} /> {!this.state.isLoading && - <Websocket ref={websocket => this.websocket = websocket} url={process.env.REACT_APP_WEBSOCKET_URL} + <Websocket ref={websocket => this.websocket = websocket} url={process.env.REACT_APP_WEBSOCKET_URL} onOpen={this.onConnect} onMessage={this.handleData} onClose={this.onDisconnect} />} </React.Fragment> ); diff --git a/SAS/TMSS/frontend/tmss_webapp/src/routes/SystemEvent/system.event.list.js b/SAS/TMSS/frontend/tmss_webapp/src/routes/SystemEvent/system.event.list.js index dd4e842f1a6c961ef45d0b2d3e93abd943d39098..093fe32e6badaf342b7616920124171afb201e62 100644 --- a/SAS/TMSS/frontend/tmss_webapp/src/routes/SystemEvent/system.event.list.js +++ b/SAS/TMSS/frontend/tmss_webapp/src/routes/SystemEvent/system.event.list.js @@ -599,7 +599,7 @@ export class SystemEventList extends Component { return ( <React.Fragment> {!this.props.schedulingUnit && - <PageHeader className="defaultpageHeader" location={this.props.location} title={'System Issues - List'} + <PageHeader className="defaultrightpageHeader" location={this.props.location} title={'System Issues - List'} actions={[ {