From 4aa0c147adba951bd4acf18bb77978f52daae9fb Mon Sep 17 00:00:00 2001 From: Guido Quezada Date: Thu, 26 Nov 2020 18:15:36 -0500 Subject: [PATCH 1/3] feat: #566 Datepicker for Date out --- .../details-fields.component.html | 18 ++++++++++++++++-- .../details-fields.component.spec.ts | 8 ++++++-- .../details-fields/details-fields.component.ts | 10 +++++++++- 3 files changed, 31 insertions(+), 5 deletions(-) diff --git a/src/app/modules/shared/components/details-fields/details-fields.component.html b/src/app/modules/shared/components/details-fields/details-fields.component.html index fc4c69b08..3f0b12caa 100644 --- a/src/app/modules/shared/components/details-fields/details-fields.component.html +++ b/src/app/modules/shared/components/details-fields/details-fields.component.html @@ -72,8 +72,8 @@
- -
+ +
+ + +
+ +
diff --git a/src/app/modules/shared/components/details-fields/details-fields.component.spec.ts b/src/app/modules/shared/components/details-fields/details-fields.component.spec.ts index 1f343cc70..0728bf01c 100644 --- a/src/app/modules/shared/components/details-fields/details-fields.component.spec.ts +++ b/src/app/modules/shared/components/details-fields/details-fields.component.spec.ts @@ -67,6 +67,7 @@ describe('DetailsFieldsComponent', () => { activity_id: '', uri: '', entry_date: formatDate(new Date(), 'yyyy-MM-dd', 'en'), + departure_date: formatDate(new Date(), 'yyyy-MM-dd', 'en'), start_hour: '00:00:00', end_hour: '00:00:00', description: '', @@ -109,6 +110,7 @@ describe('DetailsFieldsComponent', () => { activity_id: 'a1', uri: 'ticketUri', entry_date: '', + departure_date: '', start_hour: '00:00:10', end_hour: '00:00:11', description: '', @@ -177,6 +179,7 @@ describe('DetailsFieldsComponent', () => { activity_id: '', uri: '', entry_date: formatDate(new Date(), 'yyyy-MM-dd', 'en'), + departure_date: formatDate(new Date(), 'yyyy-MM-dd', 'en'), start_hour: '00:00:00', end_hour: '00:00:00', description: '', @@ -213,6 +216,7 @@ describe('DetailsFieldsComponent', () => { activity_id: 'a1', uri: '', entry_date: '2020-02-05', + departure_date: '2020-02-05', start_hour: '00:00:01', end_hour: '00:01:01', description: '', @@ -287,7 +291,7 @@ describe('DetailsFieldsComponent', () => { component.goingToWorkOnThis = true; spyOn(component.saveEntry, 'emit'); - component.entryForm.setValue({ ...formValues, entry_date: '2020-06-11' }); + component.entryForm.setValue({ ...formValues, entry_date: '2020-06-11', departure_date: '2020-06-11' }); component.onSubmit(); @@ -311,7 +315,7 @@ describe('DetailsFieldsComponent', () => { spyOn(toastrServiceStub, 'error'); const futureDate = moment().add(1, 'days').format('YYYY-MM-DD'); - component.entryForm.setValue({ ...formValues, entry_date: futureDate }); + component.entryForm.setValue({ ...formValues, entry_date: futureDate, departure_date: futureDate }); component.onSubmit(); expect(toastrServiceStub.error).toHaveBeenCalled(); diff --git a/src/app/modules/shared/components/details-fields/details-fields.component.ts b/src/app/modules/shared/components/details-fields/details-fields.component.ts index 1c8e37711..909e8ded2 100644 --- a/src/app/modules/shared/components/details-fields/details-fields.component.ts +++ b/src/app/modules/shared/components/details-fields/details-fields.component.ts @@ -49,6 +49,7 @@ export class DetailsFieldsComponent implements OnChanges, OnInit { activity_id: ['', Validators.required], description: '', entry_date: '', + departure_date: '', start_hour: '', end_hour: '', uri: '', @@ -130,6 +131,7 @@ export class DetailsFieldsComponent implements OnChanges, OnInit { activity_id: this.entryToEdit.activity_id, description: this.entryToEdit.description, entry_date: this.entryToEdit.start_date ? formatDate(this.entryToEdit.start_date, 'yyyy-MM-dd', 'en') : '', + departure_date: formatDate(this.entryToEdit.end_date ? this.entryToEdit.end_date : new Date(), 'yyyy-MM-dd', 'en'), start_hour: this.entryToEdit.start_date ? formatDate(this.entryToEdit.start_date, 'HH:mm:ss', 'en') : '00:00:00', end_hour: this.entryToEdit.end_date ? formatDate(this.entryToEdit.end_date, 'HH:mm:ss', 'en') : '00:00:00', uri: this.entryToEdit.uri, @@ -148,6 +150,7 @@ export class DetailsFieldsComponent implements OnChanges, OnInit { activity_id: '', description: '', entry_date: formatDate(new Date(), 'yyyy-MM-dd', 'en'), + departure_date: formatDate(new Date(), 'yyyy-MM-dd', 'en'), start_hour: '00:00:00', end_hour: '00:00:00', uri: '', @@ -175,6 +178,10 @@ export class DetailsFieldsComponent implements OnChanges, OnInit { return this.entryForm.get('entry_date'); } + get departure_date() { + return this.entryForm.get('departure_date'); + } + get start_hour() { return this.entryForm.get('start_hour'); } @@ -195,13 +202,14 @@ export class DetailsFieldsComponent implements OnChanges, OnInit { } // start&end date same for now const entryDate = this.entryForm.value.entry_date; + const departureDate = this.entryForm.value.departure_date; const entry = { project_id: this.entryForm.value.project_id, activity_id: this.entryForm.value.activity_id, technologies: this.selectedTechnologies ? this.selectedTechnologies : [], description: this.entryForm.value.description, start_date: new Date(`${entryDate}T${this.entryForm.value.start_hour.trim()}`).toISOString(), - end_date: new Date(`${entryDate}T${this.entryForm.value.end_hour.trim()}`).toISOString(), + end_date: new Date(`${departureDate}T${this.entryForm.value.end_hour.trim()}`).toISOString(), uri: this.entryForm.value.uri, timezone_offset: new Date().getTimezoneOffset(), }; From 9e57632cefc312fb4c76407c1cba723932fa3bc4 Mon Sep 17 00:00:00 2001 From: Guido Quezada Date: Fri, 27 Nov 2020 15:05:58 -0500 Subject: [PATCH 2/3] fix: #566 Datepicker for departure date in entry form --- .../details-fields.component.html | 39 +++++++++---------- .../details-fields.component.spec.ts | 22 +++++++++++ .../details-fields.component.ts | 13 ++++--- .../pages/time-entries.component.spec.ts | 3 +- .../pages/time-entries.component.ts | 3 +- 5 files changed, 52 insertions(+), 28 deletions(-) diff --git a/src/app/modules/shared/components/details-fields/details-fields.component.html b/src/app/modules/shared/components/details-fields/details-fields.component.html index 3f0b12caa..d7c1c261a 100644 --- a/src/app/modules/shared/components/details-fields/details-fields.component.html +++ b/src/app/modules/shared/components/details-fields/details-fields.component.html @@ -86,23 +86,6 @@ />
- -
- -
- - - -
+
- -
+ +
+ +
+ +
+ + +
{ expect(toastrServiceStub.error).toHaveBeenCalled(); }); + it('when entry_date is in the future and departure_date is OK then throws an error', () => { + spyOn(toastrServiceStub, 'error'); + + const futureDate = moment().add(1, 'days').format('YYYY-MM-DD'); + const currentDate = moment().format('YYYY-MM-DD'); + component.entryForm.setValue({ ...formValues, entry_date: futureDate, departure_date: currentDate }); + component.onSubmit(); + + expect(toastrServiceStub.error).toHaveBeenCalled(); + }); + + it('when entry_date is OK and departure_date is in the future then throws an error future', () => { + spyOn(toastrServiceStub, 'error'); + + const futureDate = moment().add(1, 'days').format('YYYY-MM-DD'); + const currentDate = moment().format('YYYY-MM-DD'); + component.entryForm.setValue({ ...formValues, entry_date: currentDate, departure_date: futureDate }); + component.onSubmit(); + + expect(toastrServiceStub.error).toHaveBeenCalled(); + }); + it('should emit projectSelected event', () => { spyOn(component.projectSelected, 'emit'); const item = { diff --git a/src/app/modules/shared/components/details-fields/details-fields.component.ts b/src/app/modules/shared/components/details-fields/details-fields.component.ts index 909e8ded2..a0b276ae8 100644 --- a/src/app/modules/shared/components/details-fields/details-fields.component.ts +++ b/src/app/modules/shared/components/details-fields/details-fields.component.ts @@ -17,6 +17,7 @@ import { TechnologyState } from '../../store/technology.reducers'; import { EntryActionTypes } from './../../../time-clock/store/entry.actions'; import { SaveEntryEvent } from './save-entry-event'; import { ProjectSelectedEvent } from './project-selected-event'; +import { get } from 'lodash'; type Merged = TechnologyState & ProjectState & ActivityState & EntryState; @@ -130,10 +131,10 @@ export class DetailsFieldsComponent implements OnChanges, OnInit { project_id: this.entryToEdit.project_id, activity_id: this.entryToEdit.activity_id, description: this.entryToEdit.description, - entry_date: this.entryToEdit.start_date ? formatDate(this.entryToEdit.start_date, 'yyyy-MM-dd', 'en') : '', - departure_date: formatDate(this.entryToEdit.end_date ? this.entryToEdit.end_date : new Date(), 'yyyy-MM-dd', 'en'), - start_hour: this.entryToEdit.start_date ? formatDate(this.entryToEdit.start_date, 'HH:mm:ss', 'en') : '00:00:00', - end_hour: this.entryToEdit.end_date ? formatDate(this.entryToEdit.end_date, 'HH:mm:ss', 'en') : '00:00:00', + entry_date: formatDate(get(this.entryToEdit, 'start_date', '') , 'yyyy-MM-dd', 'en'), + departure_date: formatDate(get(this.entryToEdit, 'end_date'), 'yyyy-MM-dd', 'en'), + start_hour: formatDate(get(this.entryToEdit, 'start_date', '00:00:00'), 'HH:mm:ss', 'en'), + end_hour: formatDate(get(this.entryToEdit, 'end_date', '00:00:00'), 'HH:mm:ss', 'en'), uri: this.entryToEdit.uri, technology: '', }); @@ -200,7 +201,6 @@ export class DetailsFieldsComponent implements OnChanges, OnInit { this.toastrService.warning('Make sure to select a project and activity'); return; } - // start&end date same for now const entryDate = this.entryForm.value.entry_date; const departureDate = this.entryForm.value.departure_date; const entry = { @@ -217,7 +217,8 @@ export class DetailsFieldsComponent implements OnChanges, OnInit { delete entry.end_date; } const isEntryDateInTheFuture = moment(entryDate).isAfter(moment()); - if (isEntryDateInTheFuture) { + const isDepartureDateInTheFuture = moment(departureDate).isAfter(moment()); + if (isEntryDateInTheFuture || isDepartureDateInTheFuture) { this.toastrService.error('You cannot start a time-entry in the future'); return; } diff --git a/src/app/modules/time-entries/pages/time-entries.component.spec.ts b/src/app/modules/time-entries/pages/time-entries.component.spec.ts index de526154b..77511dae6 100644 --- a/src/app/modules/time-entries/pages/time-entries.component.spec.ts +++ b/src/app/modules/time-entries/pages/time-entries.component.spec.ts @@ -356,7 +356,8 @@ describe('TimeEntriesComponent', () => { uri : 'http://testing.is.fun', activity_id : 'sss', project_id : 'id', - start_date : new Date(new Date().setHours(0, 0, 0, 0)) + start_date : new Date(new Date().setHours(0, 0, 0, 0)), + end_date : new Date(new Date().setHours(0, 0, 0, 0)) }; state.timeEntriesDataSource.data = [ lastEntry ]; mockEntriesSelector = store.overrideSelector(getTimeEntriesDataSource, state.timeEntriesDataSource); diff --git a/src/app/modules/time-entries/pages/time-entries.component.ts b/src/app/modules/time-entries/pages/time-entries.component.ts index 3ab5eaf51..01b929fc2 100644 --- a/src/app/modules/time-entries/pages/time-entries.component.ts +++ b/src/app/modules/time-entries/pages/time-entries.component.ts @@ -126,7 +126,8 @@ export class TimeEntriesComponent implements OnInit, OnDestroy { uri : dataToUse.uri ? dataToUse.uri : '', activity_id : dataToUse.activity_id, project_id : dataToUse.project_id, - start_date : startDate + start_date : startDate, + end_date : startDate }; this.entry = entry; } From 329ab0a617665803d60101d0a65774430db7a4d0 Mon Sep 17 00:00:00 2001 From: Guido Quezada Date: Fri, 27 Nov 2020 16:02:06 -0500 Subject: [PATCH 3/3] fix: #566 refactor variables name --- .../details-fields.component.html | 12 +++---- .../details-fields.component.spec.ts | 28 +++++++-------- .../details-fields.component.ts | 36 +++++++++---------- 3 files changed, 38 insertions(+), 38 deletions(-) diff --git a/src/app/modules/shared/components/details-fields/details-fields.component.html b/src/app/modules/shared/components/details-fields/details-fields.component.html index d7c1c261a..7e3949525 100644 --- a/src/app/modules/shared/components/details-fields/details-fields.component.html +++ b/src/app/modules/shared/components/details-fields/details-fields.component.html @@ -75,13 +75,13 @@
@@ -112,13 +112,13 @@
diff --git a/src/app/modules/shared/components/details-fields/details-fields.component.spec.ts b/src/app/modules/shared/components/details-fields/details-fields.component.spec.ts index 30a28ba57..96c5cd9c6 100644 --- a/src/app/modules/shared/components/details-fields/details-fields.component.spec.ts +++ b/src/app/modules/shared/components/details-fields/details-fields.component.spec.ts @@ -66,8 +66,8 @@ describe('DetailsFieldsComponent', () => { project_name: '', activity_id: '', uri: '', - entry_date: formatDate(new Date(), 'yyyy-MM-dd', 'en'), - departure_date: formatDate(new Date(), 'yyyy-MM-dd', 'en'), + start_date: formatDate(new Date(), 'yyyy-MM-dd', 'en'), + end_date: formatDate(new Date(), 'yyyy-MM-dd', 'en'), start_hour: '00:00:00', end_hour: '00:00:00', description: '', @@ -109,8 +109,8 @@ describe('DetailsFieldsComponent', () => { project_name: 'name', activity_id: 'a1', uri: 'ticketUri', - entry_date: '', - departure_date: '', + start_date: '', + end_date: '', start_hour: '00:00:10', end_hour: '00:00:11', description: '', @@ -178,8 +178,8 @@ describe('DetailsFieldsComponent', () => { project_name: '', activity_id: '', uri: '', - entry_date: formatDate(new Date(), 'yyyy-MM-dd', 'en'), - departure_date: formatDate(new Date(), 'yyyy-MM-dd', 'en'), + start_date: formatDate(new Date(), 'yyyy-MM-dd', 'en'), + end_date: formatDate(new Date(), 'yyyy-MM-dd', 'en'), start_hour: '00:00:00', end_hour: '00:00:00', description: '', @@ -215,8 +215,8 @@ describe('DetailsFieldsComponent', () => { project_name: 'p-name', activity_id: 'a1', uri: '', - entry_date: '2020-02-05', - departure_date: '2020-02-05', + start_date: '2020-02-05', + end_date: '2020-02-05', start_hour: '00:00:01', end_hour: '00:01:01', description: '', @@ -291,7 +291,7 @@ describe('DetailsFieldsComponent', () => { component.goingToWorkOnThis = true; spyOn(component.saveEntry, 'emit'); - component.entryForm.setValue({ ...formValues, entry_date: '2020-06-11', departure_date: '2020-06-11' }); + component.entryForm.setValue({ ...formValues, start_date: '2020-06-11', end_date: '2020-06-11' }); component.onSubmit(); @@ -315,29 +315,29 @@ describe('DetailsFieldsComponent', () => { spyOn(toastrServiceStub, 'error'); const futureDate = moment().add(1, 'days').format('YYYY-MM-DD'); - component.entryForm.setValue({ ...formValues, entry_date: futureDate, departure_date: futureDate }); + component.entryForm.setValue({ ...formValues, start_date: futureDate, end_date: futureDate }); component.onSubmit(); expect(toastrServiceStub.error).toHaveBeenCalled(); }); - it('when entry_date is in the future and departure_date is OK then throws an error', () => { + it('when start_date is in the future and end_date is OK then throws an error', () => { spyOn(toastrServiceStub, 'error'); const futureDate = moment().add(1, 'days').format('YYYY-MM-DD'); const currentDate = moment().format('YYYY-MM-DD'); - component.entryForm.setValue({ ...formValues, entry_date: futureDate, departure_date: currentDate }); + component.entryForm.setValue({ ...formValues, start_date: futureDate, end_date: currentDate }); component.onSubmit(); expect(toastrServiceStub.error).toHaveBeenCalled(); }); - it('when entry_date is OK and departure_date is in the future then throws an error future', () => { + it('when start_date is OK and end_date is in the future then throws an error future', () => { spyOn(toastrServiceStub, 'error'); const futureDate = moment().add(1, 'days').format('YYYY-MM-DD'); const currentDate = moment().format('YYYY-MM-DD'); - component.entryForm.setValue({ ...formValues, entry_date: currentDate, departure_date: futureDate }); + component.entryForm.setValue({ ...formValues, start_date: currentDate, end_date: futureDate }); component.onSubmit(); expect(toastrServiceStub.error).toHaveBeenCalled(); diff --git a/src/app/modules/shared/components/details-fields/details-fields.component.ts b/src/app/modules/shared/components/details-fields/details-fields.component.ts index a0b276ae8..a24baa4ba 100644 --- a/src/app/modules/shared/components/details-fields/details-fields.component.ts +++ b/src/app/modules/shared/components/details-fields/details-fields.component.ts @@ -49,8 +49,8 @@ export class DetailsFieldsComponent implements OnChanges, OnInit { project_name: ['', Validators.required], activity_id: ['', Validators.required], description: '', - entry_date: '', - departure_date: '', + start_date: '', + end_date: '', start_hour: '', end_hour: '', uri: '', @@ -131,8 +131,8 @@ export class DetailsFieldsComponent implements OnChanges, OnInit { project_id: this.entryToEdit.project_id, activity_id: this.entryToEdit.activity_id, description: this.entryToEdit.description, - entry_date: formatDate(get(this.entryToEdit, 'start_date', '') , 'yyyy-MM-dd', 'en'), - departure_date: formatDate(get(this.entryToEdit, 'end_date'), 'yyyy-MM-dd', 'en'), + start_date: formatDate(get(this.entryToEdit, 'start_date', '') , 'yyyy-MM-dd', 'en'), + end_date: formatDate(get(this.entryToEdit, 'end_date'), 'yyyy-MM-dd', 'en'), start_hour: formatDate(get(this.entryToEdit, 'start_date', '00:00:00'), 'HH:mm:ss', 'en'), end_hour: formatDate(get(this.entryToEdit, 'end_date', '00:00:00'), 'HH:mm:ss', 'en'), uri: this.entryToEdit.uri, @@ -150,8 +150,8 @@ export class DetailsFieldsComponent implements OnChanges, OnInit { project_id: '', activity_id: '', description: '', - entry_date: formatDate(new Date(), 'yyyy-MM-dd', 'en'), - departure_date: formatDate(new Date(), 'yyyy-MM-dd', 'en'), + start_date: formatDate(new Date(), 'yyyy-MM-dd', 'en'), + end_date: formatDate(new Date(), 'yyyy-MM-dd', 'en'), start_hour: '00:00:00', end_hour: '00:00:00', uri: '', @@ -175,12 +175,12 @@ export class DetailsFieldsComponent implements OnChanges, OnInit { return this.entryForm.get('activity_id'); } - get entry_date() { - return this.entryForm.get('entry_date'); + get start_date() { + return this.entryForm.get('start_date'); } - get departure_date() { - return this.entryForm.get('departure_date'); + get end_date() { + return this.entryForm.get('end_date'); } get start_hour() { @@ -201,24 +201,24 @@ export class DetailsFieldsComponent implements OnChanges, OnInit { this.toastrService.warning('Make sure to select a project and activity'); return; } - const entryDate = this.entryForm.value.entry_date; - const departureDate = this.entryForm.value.departure_date; + const startDate = this.entryForm.value.start_date; + const endDate = this.entryForm.value.end_date; const entry = { project_id: this.entryForm.value.project_id, activity_id: this.entryForm.value.activity_id, - technologies: this.selectedTechnologies ? this.selectedTechnologies : [], + technologies: get(this, 'selectedTechnologies', []), description: this.entryForm.value.description, - start_date: new Date(`${entryDate}T${this.entryForm.value.start_hour.trim()}`).toISOString(), - end_date: new Date(`${departureDate}T${this.entryForm.value.end_hour.trim()}`).toISOString(), + start_date: new Date(`${startDate}T${this.entryForm.value.start_hour.trim()}`).toISOString(), + end_date: new Date(`${endDate}T${this.entryForm.value.end_hour.trim()}`).toISOString(), uri: this.entryForm.value.uri, timezone_offset: new Date().getTimezoneOffset(), }; if (this.goingToWorkOnThis) { delete entry.end_date; } - const isEntryDateInTheFuture = moment(entryDate).isAfter(moment()); - const isDepartureDateInTheFuture = moment(departureDate).isAfter(moment()); - if (isEntryDateInTheFuture || isDepartureDateInTheFuture) { + const isStartDateInTheFuture = moment(startDate).isAfter(moment()); + const isEndDateInTheFuture = moment(endDate).isAfter(moment()); + if (isStartDateInTheFuture || isEndDateInTheFuture) { this.toastrService.error('You cannot start a time-entry in the future'); return; }