patternjavascriptMinor
HumanDate for easier date calculations
Viewed 0 times
datecalculationshumandateforeasier
Problem
I need to calculate some dates like yesterday, this week/month, last three/ten days etc.
To make it a little bit easier and don't think about the
Examples:
```
console.log('day: ' + new HumanDate().day());
console.log('month: ' + new HumanDate().month());
console.log('year: ' + new HumanDate().year());
console.log('day of week: ' + new HumanDate().dayOfWeek());
console.log('yesterday: ' + new HumanDate().day(-1).day());
console.log('next month: ' + new HumanDate().month(1).toJSDate());
console.log('last month: ' + new HumanDate().month(-1).toJSDate());
console.log('beginning of the week: ' + new HumanDate().beginningOfTheWeek().toJSDate());
console.log('end of the week: ' + new HumanDate().endOfTheWeek().toJSDate());
console.log('beginning of the month: ' + new HumanDate().beginningOfTheMonth().toJSDate());
console.log('end of the week: ' + new HumanDate().endOfTheWee
To make it a little bit easier and don't think about the
Date weirdness all the time I created this helper:var HumanDate = function() {
var date = new Date();
this.day = function(numOfDays) {
if (numOfDays === undefined) {
return date.getDate();
}
else {
date.setDate(date.getDate() + numOfDays);
return this;
}
};
this.month = function(month) {
if (month === undefined) {
return date.getMonth() + 1;
}
else {
date.setMonth(date.getMonth() + month);
return this;
}
};
this.year = function() {
return date.getFullYear();
};
this.dayOfWeek = function() {
var dayOfWeek = date.getDay();
return dayOfWeek === 0 ? dayOfWeek + 1 : dayOfWeek;
};
this.beginningOfTheWeek = function() {
return this.day(-this.dayOfWeek() + 1);
}
this.endOfTheWeek = function() {
return this.day(7 - this.dayOfWeek());
}
this.beginningOfTheMonth = function() {
return this.day(-this.day() + 1);
}
this.endOfTheMonth = function() {
return this.day(7 - this.dayOfWeek());
}
this.toJSDate = function(format) {
return date;
}
};Examples:
```
console.log('day: ' + new HumanDate().day());
console.log('month: ' + new HumanDate().month());
console.log('year: ' + new HumanDate().year());
console.log('day of week: ' + new HumanDate().dayOfWeek());
console.log('yesterday: ' + new HumanDate().day(-1).day());
console.log('next month: ' + new HumanDate().month(1).toJSDate());
console.log('last month: ' + new HumanDate().month(-1).toJSDate());
console.log('beginning of the week: ' + new HumanDate().beginningOfTheWeek().toJSDate());
console.log('end of the week: ' + new HumanDate().endOfTheWeek().toJSDate());
console.log('beginning of the month: ' + new HumanDate().beginningOfTheMonth().toJSDate());
console.log('end of the week: ' + new HumanDate().endOfTheWee
Solution
Some thoughts:
For example, this usage seems very confusing:
Consider naming like
For example:
Could more clearly be written as:
Here there is no need for
- I find your method naming to be really confusing. To me, if I called methods named
.day(),.month(),year(), etc. I would be expecting methods named in this manner to behave more like a getter than a setter.
For example, this usage seems very confusing:
new HumanDate().day(-1).day()Consider naming like
modifyDay(), modifyMonth(), etc.- You have unnecessary
elseconditions.
For example:
if (numOfDays === undefined) {
return date.getDate();
}
else {
date.setDate(date.getDate() + numOfDays);
return this;
}Could more clearly be written as:
if (numOfDays === undefined) {
return date.getDate();
}
date.setDate(date.getDate() + numOfDays);
return this;Here there is no need for
else since if returns.- The
dayOfWeek()method looks odd. Why convert Sunday to Monday in all cases?
toJSDate()seems like an odd name for a function. The word "to" tends to connote cases where some casting or data transformation might take place. Here you are just returning the underlying date Object. Maybe justgetDateObj()or something more descriptive of what is happening. Of course, the caller can always just access the.dateproperty of the object to get the same result.
- I think some of the logic you are applying to try force you week to start on a certain day, might best be something you want to specify in configuration on instantiation, or via more appropriate specificity around methods that deal with work week constructs. Just totally re-mapping the days returned by underlying
Dateobject seems to sort of hide this away from the caller.
- I think that perhaps you might need to look at the time component here as well. To me, if I am trying to get the beginning of a week or month, I would be expecting to get 00:00:00 as the time component. On the other hand, if maybe the methods were named something like
modifyToBeginningOfMonth()perhaps the current behavior would be more expected.
- Consider passing the
Dateobject dependency in the constructor. Right now you limit this class to only working with Date object for current timestamp. If you took aDateobject as parameter, you could set thisDateobject on yourHumanDateobject as is currently done, but allow the caller to fully utilize the capabilities ofDateto set the timestamp to whatever they want to start with. This also makes the dependency of this class really clear.
- You might give consideration to defining this class more as an extension of the underlying
Dateclass. That way you can eliminate needing to wrap underlying date properties and methods.
Code Snippets
new HumanDate().day(-1).day()if (numOfDays === undefined) {
return date.getDate();
}
else {
date.setDate(date.getDate() + numOfDays);
return this;
}if (numOfDays === undefined) {
return date.getDate();
}
date.setDate(date.getDate() + numOfDays);
return this;Context
StackExchange Code Review Q#140775, answer score: 2
Revisions (0)
No revisions yet.