Published on

A cute little bug

I have been working on https://rentobase.com - a rental property management SaaS.

One of the features is the ability to record a rental income collection.

There are two important date atrributes things that you have to record:

  • the date when the rental payment goes into effect
  • the date when the rental payment becomes due.

How do you do this simplistically?

  • Validate that the start date is not in the past.
  • Validate that the end date is not in the past as well.
  • Check that the end date and start date are not the same.

What was I doing?

startDate, _ := time.Parse("2006-01-02", req.StartDate)
endDate, _ := time.Parse("2006-01-02", req.EndDate)

if startDate.Before(time.Now()) || endDate.Before(time.Now()) {
	c.JSON(http.StatusBadRequest, gin.H{"message": "Dates cannot be in the past"})
	return
}   

if startDate.After(endDate) {
	c.JSON(http.StatusBadRequest, gin.H{"message": "Start date cannot be after end date"})
	return
}

Here’s where it gets interesting. If you validate using the above code, you will get a false negative because startDate.Before(time.Now()) will return false if startDate is today.

I spent quite a chunk of my afternoon wondering why this was the case.

The fix is quite simple. Truncate the current time to midnight using time.Now().Truncate(24 * time.Hour) to compare dates at the day level rather than exact timestamps.

startDate, _ := time.Parse("2006-01-02", req.StartDate)
	endDate, _ := time.Parse("2006-01-02", req.EndDate)

	currentDate := time.Now().Truncate(24 * time.Hour)
	if startDate.Before(currentDate) {
		//throw error
		return
	}

There you have it!