Chanpory
Chanpory

Reputation: 3095

Rails: Is there away to get the Date object that is the closest Monday to today?

Given a date, how do I find the nearest Monday in Rails?

I know I can do things like:

Date.tomorrow Date.today

Is there something like Date.nearest :monday ?

Upvotes: 18

Views: 8734

Answers (5)

David Geere
David Geere

Reputation: 433

I know this is an old thread but it's always nice to keep it current for future seekers.

Let's assume today is say Friday the 19th of August. All I do to get my nearest Monday is this:

monday = Date.today.monday

Then from there you can go back a week or forward a week like this:

last_monday = monday.last_week
next_monday = monday.next_week

Upvotes: 10

Aleksey Shein
Aleksey Shein

Reputation: 7482

It's a little bit tricky, but not so hard to calculate.

Use ActiveSupport::DateAndTimeCalculations#end_of_week to calculate end of a week, this method accepts a start_day parameter that is used to indicate start day of the week (it's :monday by default). They even have implemented sunday method.

The trick is the following: if you want to calculate closest Monday, you may calculate it as a end of the week which starts on Tuesday (Tue => 1st day, Wed => 2nd day, ..., Mon => 7th day which is also end of the week).

So all you need to do is:

# it will return current date if today is Monday and nearest Monday otherwise
Date.today.end_of_week(:tuesday) 

Upvotes: 14

sgriffinusa
sgriffinusa

Reputation: 4221

The commercial method on the Date object will let you do this. This example will get you the next Monday.

Date.commercial(Date.today.year, 1+Date.today.cweek, 1)

If you need the next or previous Monday, whichever is closest, you can do:

Date.commercial(Date.today.year, Date.today.cwday.modulo(4)+Date.today.cweek, 1)

I can't execute this right now, so forgive me if there are syntax errors.

Upvotes: 23

Brian Deterling
Brian Deterling

Reputation: 13724

Assuming you want both directions: Date.today.beginning_of_week + 7*(Date.today.wday/5)

Upvotes: 6

iain
iain

Reputation: 16274

Untested, so you might need to finetune, but here you go:

def Date.nearest_monday
  today = Date.today
  wday  = today.wday
  if wday > 4 # over the half of the week
    today + (7 - wday) # next monday
  else
    today - (1 + wday) # previous monday
  end
end 

Upvotes: 1

Related Questions