Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Get the first and last day of current month in Go/Golang?

Tags:

date

time

go

I'm trying to get the first and last day of the current month. You can add days and hours but not the month, which I was thinking of subtracting one day from the next month to get the last day of this month. Something like this:

package main

import (
    "fmt"
    "time"
)

func main() {

    date := time.Now()
    nextMonth := date.Add(time.Month)
    LastDay := nextMonth.Add(-time.Hour * 24)

    fmt.Println(LastDay)

}
like image 329
vinniyo Avatar asked Apr 24 '16 23:04

vinniyo


5 Answers

time.Month is a type, not a value, so you can't Add it. Also, your logic is wrong because if you add a month and subtract a day, you aren't getting the end of the month, you're getting something in the middle of next month. If today is 24 April, you'll get 23 May.

The following code will do what you're looking for:

package main

import (
    "time"
    "fmt"
)

func main() {
    now := time.Now()
    currentYear, currentMonth, _ := now.Date()
    currentLocation := now.Location()

    firstOfMonth := time.Date(currentYear, currentMonth, 1, 0, 0, 0, 0, currentLocation)
    lastOfMonth := firstOfMonth.AddDate(0, 1, -1)

    fmt.Println(firstOfMonth)
    fmt.Println(lastOfMonth)
}

Playground link

like image 168
Amit Kumar Gupta Avatar answered Oct 21 '22 12:10

Amit Kumar Gupta


The @Apin's answer is dangerous because the now lib makes many wrong assumptions (it bit me in the foot too).
The now lib doesn't consider daylight saving times and many other things: https://github.com/jinzhu/now/issues/13

This is how I'm doing it:

t := time.Now()
firstday := time.Date(t.Year(), t.Month(), 1, 0, 0, 0, 0, time.Local)
lastday := firstday.AddDate(0, 1, 0).Add(time.Nanosecond * -1)
like image 28
gabs Avatar answered Oct 21 '22 12:10

gabs


Not sure when AddDate(...) was added to time.Time, but quite possibly it was added after this question had its prime time :)

Here's another way to achieving the same with time.Time.AddDate(...) -

func BeginningOfMonth(date time.Time)  (time.Time) {
    return date.AddDate(0, 0, -date.Day() + 1)
}

func EndOfMonth(date time.Time) (time.Time) {
    return date.AddDate(0, 1, -date.Day())
}

Then you could use today := time.Now() and pass it over to one/both of the functions like so - eom := EndOfMonth(today) to get the appropriate date.

If time, DST and such are important, it should be pretty straightforward to ornament those details on top of it once you get the date.

Finally, here's a playground link where you can play around with it - https://play.golang.org/p/DxnGuqh6g4k

like image 28
Shreyas Avatar answered Oct 21 '22 12:10

Shreyas


You can use now library, it really simple :

now.BeginningOfMonth()    // 2013-11-01 00:00:00 Fri
now.EndOfMonth()          // 2013-11-30 23:59:59.999999999 Sat

Please take a look here for detail : https://github.com/jinzhu/now

like image 22
Apin Avatar answered Oct 21 '22 11:10

Apin


I would do it like this:

// LastDayOfMonth returns 28-31 - the last day in the month of the time object
// passed in to the function
func LastDayOfMonth(t time.Time) int {
    firstDay := time.Date(t.Year(), t.Month(), 1, 0, 0, 0, 0, time.UTC)
    lastDay := firstDay.AddDate(0, 1, 0).Add(-time.Nanosecond)
    return lastDay.Day()
}

a

like image 5
Richard Knop Avatar answered Oct 21 '22 11:10

Richard Knop