timely 0.5.0 → 0.6.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- checksums.yaml +4 -4
 - data/.rubocop.yml +22 -2
 - data/.travis.yml +0 -6
 - data/CHANGELOG.md +6 -0
 - data/Gemfile +2 -0
 - data/Rakefile +6 -4
 - data/gemfiles/rails5.gemfile +4 -2
 - data/gemfiles/rails6.gemfile +3 -1
 - data/lib/timely/date.rb +6 -2
 - data/lib/timely/date_chooser.rb +29 -30
 - data/lib/timely/date_range.rb +17 -19
 - data/lib/timely/date_time.rb +3 -1
 - data/lib/timely/rails/calendar_tag.rb +3 -3
 - data/lib/timely/rails/date.rb +3 -1
 - data/lib/timely/rails/date_group.rb +24 -24
 - data/lib/timely/rails/date_range_validity_module.rb +8 -6
 - data/lib/timely/rails/date_time.rb +5 -3
 - data/lib/timely/rails/extensions.rb +12 -37
 - data/lib/timely/rails/period.rb +14 -12
 - data/lib/timely/rails/season.rb +14 -33
 - data/lib/timely/rails/time.rb +7 -3
 - data/lib/timely/rails.rb +2 -0
 - data/lib/timely/railtie.rb +2 -0
 - data/lib/timely/range.rb +4 -2
 - data/lib/timely/string.rb +4 -2
 - data/lib/timely/time.rb +7 -3
 - data/lib/timely/time_since.rb +5 -3
 - data/lib/timely/trackable_date_set.rb +21 -21
 - data/lib/timely/version.rb +3 -1
 - data/lib/timely/week_days.rb +14 -16
 - data/lib/timely.rb +2 -0
 - data/rails/init.rb +2 -0
 - data/spec/calendar_tag_spec.rb +11 -10
 - data/spec/date_chooser_spec.rb +67 -62
 - data/spec/date_group_spec.rb +18 -15
 - data/spec/date_range_spec.rb +29 -19
 - data/spec/date_spec.rb +3 -1
 - data/spec/extensions_spec.rb +5 -9
 - data/spec/rails/date_spec.rb +5 -3
 - data/spec/rails/date_time_spec.rb +9 -7
 - data/spec/rails/period_spec.rb +2 -0
 - data/spec/rails/time_spec.rb +6 -4
 - data/spec/schema.rb +4 -3
 - data/spec/season_spec.rb +23 -26
 - data/spec/spec_helper.rb +3 -1
 - data/spec/support/coverage_loader.rb +3 -1
 - data/spec/temporal_patterns_spec.rb +5 -5
 - data/spec/time_since_spec.rb +6 -4
 - data/spec/time_spec.rb +6 -4
 - data/spec/trackable_date_set_spec.rb +20 -18
 - data/spec/week_days_spec.rb +24 -22
 - data/timely.gemspec +20 -18
 - metadata +32 -20
 - data/spec/string_spec.rb +0 -14
 
    
        data/lib/timely/rails/season.rb
    CHANGED
    
    | 
         @@ -1,34 +1,22 @@ 
     | 
|
| 
      
 1 
     | 
    
         
            +
            # frozen_string_literal: true
         
     | 
| 
      
 2 
     | 
    
         
            +
             
     | 
| 
       1 
3 
     | 
    
         
             
            module Timely
         
     | 
| 
       2 
4 
     | 
    
         
             
              class Season < ActiveRecord::Base
         
     | 
| 
       3 
     | 
    
         
            -
             
     | 
| 
       4 
     | 
    
         
            -
                if ::ActiveRecord::VERSION::MAJOR >= 4
         
     | 
| 
       5 
     | 
    
         
            -
                  has_many :date_groups, lambda { order(:start_date) }, :dependent => :destroy, :class_name => 'Timely::DateGroup'
         
     | 
| 
       6 
     | 
    
         
            -
                else
         
     | 
| 
       7 
     | 
    
         
            -
                  has_many :date_groups, :order => :start_date, :dependent => :destroy, :class_name => 'Timely::DateGroup'
         
     | 
| 
       8 
     | 
    
         
            -
                end
         
     | 
| 
       9 
     | 
    
         
            -
             
     | 
| 
      
 5 
     | 
    
         
            +
                has_many :date_groups, -> { order(:start_date) }, dependent: :destroy, class_name: 'Timely::DateGroup', inverse_of: :season
         
     | 
| 
       10 
6 
     | 
    
         | 
| 
       11 
7 
     | 
    
         
             
                accepts_nested_attributes_for :date_groups,
         
     | 
| 
       12 
     | 
    
         
            -
             
     | 
| 
       13 
     | 
    
         
            -
             
     | 
| 
      
 8 
     | 
    
         
            +
                                              reject_if: proc { |attributes| attributes['start_date'].blank? },
         
     | 
| 
      
 9 
     | 
    
         
            +
                                              allow_destroy: true
         
     | 
| 
       14 
10 
     | 
    
         | 
| 
       15 
11 
     | 
    
         
             
                validate :validate_dates_specified
         
     | 
| 
       16 
12 
     | 
    
         | 
| 
       17 
13 
     | 
    
         
             
                def validate_dates_specified
         
     | 
| 
       18 
     | 
    
         
            -
                  errors.add(:base,  
     | 
| 
      
 14 
     | 
    
         
            +
                  errors.add(:base, 'No dates specified') if date_groups.blank?
         
     | 
| 
       19 
15 
     | 
    
         
             
                  errors.empty?
         
     | 
| 
       20 
16 
     | 
    
         
             
                end
         
     | 
| 
       21 
17 
     | 
    
         | 
| 
       22 
18 
     | 
    
         
             
                def includes_date?(date)
         
     | 
| 
       23 
     | 
    
         
            -
                  date_groups.any?{|dg| dg.includes_date?(date)}
         
     | 
| 
       24 
     | 
    
         
            -
                end
         
     | 
| 
       25 
     | 
    
         
            -
             
     | 
| 
       26 
     | 
    
         
            -
                def has_gaps?
         
     | 
| 
       27 
     | 
    
         
            -
                  last_date = nil
         
     | 
| 
       28 
     | 
    
         
            -
                  date_groups.each do |dg|
         
     | 
| 
       29 
     | 
    
         
            -
                    return true if last_date && dg.start_date != last_date + 1
         
     | 
| 
       30 
     | 
    
         
            -
                  end
         
     | 
| 
       31 
     | 
    
         
            -
                  false
         
     | 
| 
      
 19 
     | 
    
         
            +
                  date_groups.any? { |dg| dg.includes_date?(date) }
         
     | 
| 
       32 
20 
     | 
    
         
             
                end
         
     | 
| 
       33 
21 
     | 
    
         | 
| 
       34 
22 
     | 
    
         
             
                def dates
         
     | 
| 
         @@ -46,11 +34,11 @@ module Timely 
     | 
|
| 
       46 
34 
     | 
    
         
             
                end
         
     | 
| 
       47 
35 
     | 
    
         | 
| 
       48 
36 
     | 
    
         
             
                def boundary_start
         
     | 
| 
       49 
     | 
    
         
            -
                  date_groups.map(&:start_date). 
     | 
| 
      
 37 
     | 
    
         
            +
                  date_groups.map(&:start_date).min
         
     | 
| 
       50 
38 
     | 
    
         
             
                end
         
     | 
| 
       51 
39 
     | 
    
         | 
| 
       52 
40 
     | 
    
         
             
                def boundary_end
         
     | 
| 
       53 
     | 
    
         
            -
                  date_groups.map(&:end_date). 
     | 
| 
      
 41 
     | 
    
         
            +
                  date_groups.map(&:end_date).max
         
     | 
| 
       54 
42 
     | 
    
         
             
                end
         
     | 
| 
       55 
43 
     | 
    
         | 
| 
       56 
44 
     | 
    
         
             
                def within_boundary?(date)
         
     | 
| 
         @@ -60,30 +48,23 @@ module Timely 
     | 
|
| 
       60 
48 
     | 
    
         
             
                def deep_clone
         
     | 
| 
       61 
49 
     | 
    
         
             
                  # Use clone until it is removed in AR 3.1, then dup is the same
         
     | 
| 
       62 
50 
     | 
    
         
             
                  method = ActiveRecord::Base.instance_methods(false).include?(:clone) ? :clone : :dup
         
     | 
| 
       63 
     | 
    
         
            -
                  cloned =  
     | 
| 
      
 51 
     | 
    
         
            +
                  cloned = send(method)
         
     | 
| 
       64 
52 
     | 
    
         
             
                  date_groups.each do |dg|
         
     | 
| 
       65 
53 
     | 
    
         
             
                    cloned.date_groups.build(dg.send(method).attributes)
         
     | 
| 
       66 
54 
     | 
    
         
             
                  end
         
     | 
| 
       67 
55 
     | 
    
         
             
                  cloned
         
     | 
| 
       68 
56 
     | 
    
         
             
                end
         
     | 
| 
       69 
57 
     | 
    
         | 
| 
       70 
     | 
    
         
            -
                def self.build_season_for(dates=[])
         
     | 
| 
       71 
     | 
    
         
            -
                  season = Season.new
         
     | 
| 
       72 
     | 
    
         
            -
                  date_groups = dates.map do |date|
         
     | 
| 
       73 
     | 
    
         
            -
                    DateGroup.new(:start_date => date, :end_date => date)
         
     | 
| 
       74 
     | 
    
         
            -
                  end
         
     | 
| 
       75 
     | 
    
         
            -
                  season.date_groups = date_groups
         
     | 
| 
       76 
     | 
    
         
            -
                  season
         
     | 
| 
       77 
     | 
    
         
            -
                end
         
     | 
| 
       78 
     | 
    
         
            -
             
     | 
| 
       79 
58 
     | 
    
         
             
                def to_s
         
     | 
| 
       80 
59 
     | 
    
         
             
                  name.presence || Timely::DateRange.to_s(boundary_start, boundary_end)
         
     | 
| 
       81 
60 
     | 
    
         
             
                end
         
     | 
| 
       82 
61 
     | 
    
         | 
| 
       83 
     | 
    
         
            -
                 
     | 
| 
      
 62 
     | 
    
         
            +
                alias audit_name to_s
         
     | 
| 
       84 
63 
     | 
    
         | 
| 
       85 
64 
     | 
    
         
             
                def string_of_date_groups
         
     | 
| 
       86 
     | 
    
         
            -
                  date_groups.map 
     | 
| 
      
 65 
     | 
    
         
            +
                  date_groups.map  do |dg|
         
     | 
| 
      
 66 
     | 
    
         
            +
                    "#{dg.start_date.to_s(:short)} - #{dg.end_date.to_s(:short)}"
         
     | 
| 
      
 67 
     | 
    
         
            +
                  end.to_sentence
         
     | 
| 
       87 
68 
     | 
    
         
             
                end
         
     | 
| 
       88 
69 
     | 
    
         
             
              end
         
     | 
| 
       89 
70 
     | 
    
         
             
            end
         
     | 
    
        data/lib/timely/rails/time.rb
    CHANGED
    
    | 
         @@ -1,18 +1,22 @@ 
     | 
|
| 
      
 1 
     | 
    
         
            +
            # frozen_string_literal: true
         
     | 
| 
      
 2 
     | 
    
         
            +
             
     | 
| 
       1 
3 
     | 
    
         
             
            module Timely
         
     | 
| 
       2 
4 
     | 
    
         
             
              module Rails
         
     | 
| 
       3 
5 
     | 
    
         
             
                module Time
         
     | 
| 
       4 
6 
     | 
    
         
             
                  def on_date(year, month = nil, day = nil)
         
     | 
| 
       5 
7 
     | 
    
         
             
                    if year.is_a?(Date)
         
     | 
| 
       6 
8 
     | 
    
         
             
                      date = year
         
     | 
| 
       7 
     | 
    
         
            -
                      year 
     | 
| 
      
 9 
     | 
    
         
            +
                      year = date.year
         
     | 
| 
      
 10 
     | 
    
         
            +
                      month = date.month
         
     | 
| 
      
 11 
     | 
    
         
            +
                      day = date.day
         
     | 
| 
       8 
12 
     | 
    
         
             
                    end
         
     | 
| 
       9 
13 
     | 
    
         | 
| 
       10 
     | 
    
         
            -
                    raise ArgumentError,  
     | 
| 
      
 14 
     | 
    
         
            +
                    raise ArgumentError, 'Year, month, and day needed' unless [year, month, day].all?
         
     | 
| 
       11 
15 
     | 
    
         | 
| 
       12 
16 
     | 
    
         
             
                    ::Time.zone.local(year, month, day, hour, min, sec)
         
     | 
| 
       13 
17 
     | 
    
         
             
                  end
         
     | 
| 
       14 
18 
     | 
    
         | 
| 
       15 
     | 
    
         
            -
                   
     | 
| 
      
 19 
     | 
    
         
            +
                  alias on on_date
         
     | 
| 
       16 
20 
     | 
    
         
             
                end
         
     | 
| 
       17 
21 
     | 
    
         
             
              end
         
     | 
| 
       18 
22 
     | 
    
         
             
            end
         
     | 
    
        data/lib/timely/rails.rb
    CHANGED
    
    
    
        data/lib/timely/railtie.rb
    CHANGED
    
    
    
        data/lib/timely/range.rb
    CHANGED
    
    | 
         @@ -1,11 +1,13 @@ 
     | 
|
| 
      
 1 
     | 
    
         
            +
            # frozen_string_literal: true
         
     | 
| 
      
 2 
     | 
    
         
            +
             
     | 
| 
       1 
3 
     | 
    
         
             
            module Timely
         
     | 
| 
       2 
4 
     | 
    
         
             
              module Range
         
     | 
| 
       3 
5 
     | 
    
         
             
                def to_date_range
         
     | 
| 
       4 
     | 
    
         
            -
                  DateRange.new( 
     | 
| 
      
 6 
     | 
    
         
            +
                  DateRange.new(first, last)
         
     | 
| 
       5 
7 
     | 
    
         
             
                end
         
     | 
| 
       6 
8 
     | 
    
         | 
| 
       7 
9 
     | 
    
         
             
                def days_from(date = Date.today)
         
     | 
| 
       8 
     | 
    
         
            -
                  (date +  
     | 
| 
      
 10 
     | 
    
         
            +
                  (date + first)..(date + last)
         
     | 
| 
       9 
11 
     | 
    
         
             
                end
         
     | 
| 
       10 
12 
     | 
    
         
             
              end
         
     | 
| 
       11 
13 
     | 
    
         
             
            end
         
     | 
    
        data/lib/timely/string.rb
    CHANGED
    
    | 
         @@ -1,3 +1,5 @@ 
     | 
|
| 
      
 1 
     | 
    
         
            +
            # frozen_string_literal: true
         
     | 
| 
      
 2 
     | 
    
         
            +
             
     | 
| 
       1 
3 
     | 
    
         
             
            module Timely
         
     | 
| 
       2 
4 
     | 
    
         
             
              module String
         
     | 
| 
       3 
5 
     | 
    
         
             
                # fmt e.g. '%d/%m/%Y'
         
     | 
| 
         @@ -12,12 +14,12 @@ module Timely 
     | 
|
| 
       12 
14 
     | 
    
         
             
                  else
         
     | 
| 
       13 
15 
     | 
    
         
             
                    ::Date.new(*::Date._parse(self, false).values_at(:year, :mon, :mday))
         
     | 
| 
       14 
16 
     | 
    
         
             
                  end
         
     | 
| 
       15 
     | 
    
         
            -
                rescue NoMethodError, ArgumentError 
     | 
| 
      
 17 
     | 
    
         
            +
                rescue NoMethodError, ArgumentError
         
     | 
| 
       16 
18 
     | 
    
         
             
                  raise DateFormatException, "Date #{self} is invalid or not formatted correctly."
         
     | 
| 
       17 
19 
     | 
    
         
             
                end
         
     | 
| 
       18 
20 
     | 
    
         
             
              end
         
     | 
| 
       19 
21 
     | 
    
         | 
| 
       20 
     | 
    
         
            -
              class DateFormatException <  
     | 
| 
      
 22 
     | 
    
         
            +
              class DateFormatException < RuntimeError; end
         
     | 
| 
       21 
23 
     | 
    
         
             
            end
         
     | 
| 
       22 
24 
     | 
    
         | 
| 
       23 
25 
     | 
    
         
             
            class String
         
     | 
    
        data/lib/timely/time.rb
    CHANGED
    
    | 
         @@ -1,16 +1,20 @@ 
     | 
|
| 
      
 1 
     | 
    
         
            +
            # frozen_string_literal: true
         
     | 
| 
      
 2 
     | 
    
         
            +
             
     | 
| 
       1 
3 
     | 
    
         
             
            module Timely
         
     | 
| 
       2 
4 
     | 
    
         
             
              module Time
         
     | 
| 
       3 
5 
     | 
    
         
             
                def on_date(year, month = nil, day = nil)
         
     | 
| 
       4 
6 
     | 
    
         
             
                  if year.is_a?(Date)
         
     | 
| 
       5 
7 
     | 
    
         
             
                    date = year
         
     | 
| 
       6 
     | 
    
         
            -
                    year 
     | 
| 
      
 8 
     | 
    
         
            +
                    year = date.year
         
     | 
| 
      
 9 
     | 
    
         
            +
                    month = date.month
         
     | 
| 
      
 10 
     | 
    
         
            +
                    day = date.day
         
     | 
| 
       7 
11 
     | 
    
         
             
                  end
         
     | 
| 
       8 
12 
     | 
    
         | 
| 
       9 
     | 
    
         
            -
                  raise ArgumentError,  
     | 
| 
      
 13 
     | 
    
         
            +
                  raise ArgumentError, 'Year, month, and day needed' unless [year, month, day].all?
         
     | 
| 
       10 
14 
     | 
    
         | 
| 
       11 
15 
     | 
    
         
             
                  ::Time.local(year, month, day, hour, min, sec)
         
     | 
| 
       12 
16 
     | 
    
         
             
                end
         
     | 
| 
       13 
17 
     | 
    
         | 
| 
       14 
     | 
    
         
            -
                 
     | 
| 
      
 18 
     | 
    
         
            +
                alias on on_date
         
     | 
| 
       15 
19 
     | 
    
         
             
              end
         
     | 
| 
       16 
20 
     | 
    
         
             
            end
         
     | 
    
        data/lib/timely/time_since.rb
    CHANGED
    
    | 
         @@ -1,15 +1,17 @@ 
     | 
|
| 
      
 1 
     | 
    
         
            +
            # frozen_string_literal: true
         
     | 
| 
      
 2 
     | 
    
         
            +
             
     | 
| 
       1 
3 
     | 
    
         
             
            module Timely
         
     | 
| 
       2 
4 
     | 
    
         
             
              module TimeSince
         
     | 
| 
       3 
5 
     | 
    
         
             
                def seconds_since
         
     | 
| 
       4 
     | 
    
         
            -
                  ::DateTime.now.to_i -  
     | 
| 
      
 6 
     | 
    
         
            +
                  ::DateTime.now.to_i - to_i
         
     | 
| 
       5 
7 
     | 
    
         
             
                end
         
     | 
| 
       6 
8 
     | 
    
         | 
| 
       7 
9 
     | 
    
         
             
                def minutes_since
         
     | 
| 
       8 
     | 
    
         
            -
                  seconds_since/60
         
     | 
| 
      
 10 
     | 
    
         
            +
                  seconds_since / 60
         
     | 
| 
       9 
11 
     | 
    
         
             
                end
         
     | 
| 
       10 
12 
     | 
    
         | 
| 
       11 
13 
     | 
    
         
             
                def hours_since
         
     | 
| 
       12 
     | 
    
         
            -
                  minutes_since/60
         
     | 
| 
      
 14 
     | 
    
         
            +
                  minutes_since / 60
         
     | 
| 
       13 
15 
     | 
    
         
             
                end
         
     | 
| 
       14 
16 
     | 
    
         
             
              end
         
     | 
| 
       15 
17 
     | 
    
         
             
            end
         
     | 
| 
         @@ -1,3 +1,5 @@ 
     | 
|
| 
      
 1 
     | 
    
         
            +
            # frozen_string_literal: true
         
     | 
| 
      
 2 
     | 
    
         
            +
             
     | 
| 
       1 
3 
     | 
    
         
             
            require 'set'
         
     | 
| 
       2 
4 
     | 
    
         | 
| 
       3 
5 
     | 
    
         
             
            # Track a set of dates (usually a range)
         
     | 
| 
         @@ -40,22 +42,20 @@ module Timely 
     | 
|
| 
       40 
42 
     | 
    
         
             
                  @dates_to_do = @dates.dup
         
     | 
| 
       41 
43 
     | 
    
         
             
                end
         
     | 
| 
       42 
44 
     | 
    
         | 
| 
       43 
     | 
    
         
            -
                def self.new_for_date(date, opts={})
         
     | 
| 
      
 45 
     | 
    
         
            +
                def self.new_for_date(date, opts = {})
         
     | 
| 
       44 
46 
     | 
    
         
             
                  duration = opts[:duration] || 1
         
     | 
| 
       45 
47 
     | 
    
         
             
                  TrackableDateSet.new(date..(date + duration - 1))
         
     | 
| 
       46 
48 
     | 
    
         
             
                end
         
     | 
| 
       47 
49 
     | 
    
         | 
| 
       48 
     | 
    
         
            -
                #  
     | 
| 
      
 50 
     | 
    
         
            +
                # TODO: remove
         
     | 
| 
       49 
51 
     | 
    
         
             
                # Initialize from a date + duration
         
     | 
| 
       50 
     | 
    
         
            -
                def self.from_params(date_string, duration_string=nil)
         
     | 
| 
      
 52 
     | 
    
         
            +
                def self.from_params(date_string, duration_string = nil)
         
     | 
| 
       51 
53 
     | 
    
         
             
                  duration = duration_string.to_i
         
     | 
| 
       52 
     | 
    
         
            -
                  duration = 1 if duration 
     | 
| 
       53 
     | 
    
         
            -
                  new_for_date(date_string.to_date, : 
     | 
| 
      
 54 
     | 
    
         
            +
                  duration = 1 if duration.zero?
         
     | 
| 
      
 55 
     | 
    
         
            +
                  new_for_date(date_string.to_date, duration: duration)
         
     | 
| 
       54 
56 
     | 
    
         
             
                end
         
     | 
| 
       55 
57 
     | 
    
         | 
| 
       56 
     | 
    
         
            -
                 
     | 
| 
       57 
     | 
    
         
            -
                  @dates
         
     | 
| 
       58 
     | 
    
         
            -
                end
         
     | 
| 
      
 58 
     | 
    
         
            +
                attr_reader :dates
         
     | 
| 
       59 
59 
     | 
    
         | 
| 
       60 
60 
     | 
    
         
             
                # Find the set of dates which are YET to do
         
     | 
| 
       61 
61 
     | 
    
         
             
                def find_to_do
         
     | 
| 
         @@ -66,18 +66,16 @@ module Timely 
     | 
|
| 
       66 
66 
     | 
    
         
             
                def dates_done
         
     | 
| 
       67 
67 
     | 
    
         
             
                  @dates - @dates_to_do
         
     | 
| 
       68 
68 
     | 
    
         
             
                end
         
     | 
| 
       69 
     | 
    
         
            -
                 
     | 
| 
      
 69 
     | 
    
         
            +
                alias find_done dates_done
         
     | 
| 
       70 
70 
     | 
    
         | 
| 
       71 
71 
     | 
    
         
             
                # Yield each date to do
         
     | 
| 
       72 
72 
     | 
    
         
             
                def each_date_to_do
         
     | 
| 
       73 
     | 
    
         
            -
                   
     | 
| 
       74 
     | 
    
         
            -
                  @dates_to_do.sort.each{|date| yield date}
         
     | 
| 
      
 73 
     | 
    
         
            +
                  @dates_to_do.each { |date| yield date }
         
     | 
| 
       75 
74 
     | 
    
         
             
                end
         
     | 
| 
       76 
75 
     | 
    
         | 
| 
       77 
76 
     | 
    
         
             
                # Yield each date in the whole set
         
     | 
| 
       78 
77 
     | 
    
         
             
                def each_date
         
     | 
| 
       79 
     | 
    
         
            -
                   
     | 
| 
       80 
     | 
    
         
            -
                  @dates.sort.each{|date| yield date}
         
     | 
| 
      
 78 
     | 
    
         
            +
                  @dates.each { |date| yield date }
         
     | 
| 
       81 
79 
     | 
    
         
             
                end
         
     | 
| 
       82 
80 
     | 
    
         | 
| 
       83 
81 
     | 
    
         
             
                # Set dates as done
         
     | 
| 
         @@ -94,9 +92,9 @@ module Timely 
     | 
|
| 
       94 
92 
     | 
    
         
             
                  @dates_to_do.clear
         
     | 
| 
       95 
93 
     | 
    
         
             
                end
         
     | 
| 
       96 
94 
     | 
    
         | 
| 
       97 
     | 
    
         
            -
                def  
     | 
| 
      
 95 
     | 
    
         
            +
                def done_dates?(date_or_date_range)
         
     | 
| 
       98 
96 
     | 
    
         
             
                  if date_or_date_range.is_a?(Enumerable)
         
     | 
| 
       99 
     | 
    
         
            -
                    @dates_to_do.none?{|date_to_do| date_or_date_range.include?(date_to_do)}
         
     | 
| 
      
 97 
     | 
    
         
            +
                    @dates_to_do.none? { |date_to_do| date_or_date_range.include?(date_to_do) }
         
     | 
| 
       100 
98 
     | 
    
         
             
                  else
         
     | 
| 
       101 
99 
     | 
    
         
             
                    !@dates_to_do.include? date_or_date_range
         
     | 
| 
       102 
100 
     | 
    
         
             
                  end
         
     | 
| 
         @@ -112,8 +110,9 @@ module Timely 
     | 
|
| 
       112 
110 
     | 
    
         
             
                #
         
     | 
| 
       113 
111 
     | 
    
         
             
                #   action_name => Name to track
         
     | 
| 
       114 
112 
     | 
    
         
             
                #   {:job_done_when} => Block to call, passed result of yield
         
     | 
| 
       115 
     | 
    
         
            -
                def do_once(action_name, opts={})
         
     | 
| 
      
 113 
     | 
    
         
            +
                def do_once(action_name, opts = {})
         
     | 
| 
       116 
114 
     | 
    
         
             
                  return if action_applied?(action_name)
         
     | 
| 
      
 115 
     | 
    
         
            +
             
     | 
| 
       117 
116 
     | 
    
         
             
                  result = yield
         
     | 
| 
       118 
117 
     | 
    
         | 
| 
       119 
118 
     | 
    
         
             
                  job_done = opts[:job_done_when].blank? || opts[:job_done_when].call(result)
         
     | 
| 
         @@ -133,14 +132,15 @@ module Timely 
     | 
|
| 
       133 
132 
     | 
    
         
             
                def duration
         
     | 
| 
       134 
133 
     | 
    
         
             
                  @dates.size
         
     | 
| 
       135 
134 
     | 
    
         
             
                end
         
     | 
| 
       136 
     | 
    
         
            -
                 
     | 
| 
      
 135 
     | 
    
         
            +
                alias number_of_nights duration
         
     | 
| 
       137 
136 
     | 
    
         | 
| 
       138 
     | 
    
         
            -
             
     | 
| 
       139 
     | 
    
         
            -
             
     | 
| 
       140 
     | 
    
         
            -
             
     | 
| 
       141 
     | 
    
         
            -
             
     | 
| 
      
 137 
     | 
    
         
            +
                # Can't say whole_period anymore... it's not necessarily sequential dates
         
     | 
| 
      
 138 
     | 
    
         
            +
                #  def whole_period
         
     | 
| 
      
 139 
     | 
    
         
            +
                #    self.dates
         
     | 
| 
      
 140 
     | 
    
         
            +
                #  end
         
     | 
| 
       142 
141 
     | 
    
         | 
| 
       143 
142 
     | 
    
         
             
                private
         
     | 
| 
      
 143 
     | 
    
         
            +
             
     | 
| 
       144 
144 
     | 
    
         
             
                def actions_applied
         
     | 
| 
       145 
145 
     | 
    
         
             
                  @actions_applied ||= Set.new
         
     | 
| 
       146 
146 
     | 
    
         
             
                end
         
     | 
    
        data/lib/timely/version.rb
    CHANGED
    
    
    
        data/lib/timely/week_days.rb
    CHANGED
    
    | 
         @@ -1,15 +1,17 @@ 
     | 
|
| 
      
 1 
     | 
    
         
            +
            # frozen_string_literal: true
         
     | 
| 
      
 2 
     | 
    
         
            +
             
     | 
| 
       1 
3 
     | 
    
         
             
            module Timely
         
     | 
| 
       2 
4 
     | 
    
         
             
              class WeekDays
         
     | 
| 
       3 
     | 
    
         
            -
                WEEKDAY_KEYS = %i[sun mon tue wed thu fri sat]
         
     | 
| 
      
 5 
     | 
    
         
            +
                WEEKDAY_KEYS = %i[sun mon tue wed thu fri sat].freeze
         
     | 
| 
       4 
6 
     | 
    
         | 
| 
       5 
7 
     | 
    
         
             
                def self.from_range(date_range)
         
     | 
| 
       6 
8 
     | 
    
         
             
                  dates = Array(date_range)
         
     | 
| 
       7 
9 
     | 
    
         
             
                  return ALL_WEEKDAYS if dates.count >= WEEKDAY_KEYS.count
         
     | 
| 
       8 
10 
     | 
    
         | 
| 
       9 
     | 
    
         
            -
                  new(dates.each_with_object({})  
     | 
| 
      
 11 
     | 
    
         
            +
                  new(dates.each_with_object({}) do |date, result|
         
     | 
| 
       10 
12 
     | 
    
         
             
                    # e.g. {3: true, 5: true}
         
     | 
| 
       11 
13 
     | 
    
         
             
                    result[date.to_date.wday] = true
         
     | 
| 
       12 
     | 
    
         
            -
                   
     | 
| 
      
 14 
     | 
    
         
            +
                  end)
         
     | 
| 
       13 
15 
     | 
    
         
             
                end
         
     | 
| 
       14 
16 
     | 
    
         | 
| 
       15 
17 
     | 
    
         
             
                # Create a new Weekdays object
         
     | 
| 
         @@ -36,7 +38,7 @@ module Timely 
     | 
|
| 
       36 
38 
     | 
    
         
             
                  when Integer
         
     | 
| 
       37 
39 
     | 
    
         
             
                    # 4 -> 0000100 (binary) -> "0010000" (reversed string) -> {:tue => true}
         
     | 
| 
       38 
40 
     | 
    
         
             
                    weekdays.to_s(2).reverse.each_char.with_index do |char, index|
         
     | 
| 
       39 
     | 
    
         
            -
                      set_day(index, char ==  
     | 
| 
      
 41 
     | 
    
         
            +
                      set_day(index, char == '1')
         
     | 
| 
       40 
42 
     | 
    
         
             
                    end
         
     | 
| 
       41 
43 
     | 
    
         
             
                  when Hash
         
     | 
| 
       42 
44 
     | 
    
         
             
                    weekdays.each_pair do |day, value|
         
     | 
| 
         @@ -58,7 +60,7 @@ module Timely 
     | 
|
| 
       58 
60 
     | 
    
         
             
                    }
         
     | 
| 
       59 
61 
     | 
    
         
             
                  else
         
     | 
| 
       60 
62 
     | 
    
         
             
                    raise ArgumentError,
         
     | 
| 
       61 
     | 
    
         
            -
                           
     | 
| 
      
 63 
     | 
    
         
            +
                          'You must initialize with an Integer, Hash or Array'
         
     | 
| 
       62 
64 
     | 
    
         
             
                  end
         
     | 
| 
       63 
65 
     | 
    
         
             
                end
         
     | 
| 
       64 
66 
     | 
    
         | 
| 
         @@ -73,10 +75,9 @@ module Timely 
     | 
|
| 
       73 
75 
     | 
    
         | 
| 
       74 
76 
     | 
    
         
             
                def set_day(day, set)
         
     | 
| 
       75 
77 
     | 
    
         
             
                  key = day_to_index(day)
         
     | 
| 
       76 
     | 
    
         
            -
                  unless WEEKDAY_KEYS.include?(key)
         
     | 
| 
       77 
     | 
    
         
            -
             
     | 
| 
       78 
     | 
    
         
            -
                   
     | 
| 
       79 
     | 
    
         
            -
                  @weekdays[key] = [true, "true", 1, "1"].include?(set)
         
     | 
| 
      
 78 
     | 
    
         
            +
                  raise ArgumentError, "Invalid week day index #{key}" unless WEEKDAY_KEYS.include?(key)
         
     | 
| 
      
 79 
     | 
    
         
            +
             
     | 
| 
      
 80 
     | 
    
         
            +
                  @weekdays[key] = [true, 'true', 1, '1'].include?(set)
         
     | 
| 
       80 
81 
     | 
    
         
             
                end
         
     | 
| 
       81 
82 
     | 
    
         | 
| 
       82 
83 
     | 
    
         
             
                def applies_for_date?(date)
         
     | 
| 
         @@ -105,10 +106,7 @@ module Timely 
     | 
|
| 
       105 
106 
     | 
    
         
             
                # Returns array of weekday selected
         
     | 
| 
       106 
107 
     | 
    
         
             
                # e.g. [:sun, :sat]
         
     | 
| 
       107 
108 
     | 
    
         
             
                def weekdays
         
     | 
| 
       108 
     | 
    
         
            -
                   
     | 
| 
       109 
     | 
    
         
            -
                  # Ruby 1.8 returns an array for Hash#select and loses order
         
     | 
| 
       110 
     | 
    
         
            -
                  return selected.keys if selected.is_a?(Hash)
         
     | 
| 
       111 
     | 
    
         
            -
                  selected.map(&:first).sort_by { |v| WEEKDAY_KEYS.index(v) }
         
     | 
| 
      
 109 
     | 
    
         
            +
                  @weekdays.select { |_day, day_selected| day_selected }.keys
         
     | 
| 
       112 
110 
     | 
    
         
             
                end
         
     | 
| 
       113 
111 
     | 
    
         | 
| 
       114 
112 
     | 
    
         
             
                # Returns comma separated and capitalized in Sun-Sat order
         
     | 
| 
         @@ -117,7 +115,7 @@ module Timely 
     | 
|
| 
       117 
115 
     | 
    
         
             
                  days = weekdays.map { |day| day.to_s.capitalize }
         
     | 
| 
       118 
116 
     | 
    
         
             
                  last_day = days.pop
         
     | 
| 
       119 
117 
     | 
    
         | 
| 
       120 
     | 
    
         
            -
                  days.empty? ? last_day : days.join( 
     | 
| 
      
 118 
     | 
    
         
            +
                  days.empty? ? last_day : days.join(', ') + ', and ' + last_day
         
     | 
| 
       121 
119 
     | 
    
         
             
                end
         
     | 
| 
       122 
120 
     | 
    
         | 
| 
       123 
121 
     | 
    
         
             
                # 7 bits encoded in decimal number
         
     | 
| 
         @@ -126,7 +124,7 @@ module Timely 
     | 
|
| 
       126 
124 
     | 
    
         
             
                def weekdays_int
         
     | 
| 
       127 
125 
     | 
    
         
             
                  int = 0
         
     | 
| 
       128 
126 
     | 
    
         
             
                  WEEKDAY_KEYS.each.with_index do |day, index|
         
     | 
| 
       129 
     | 
    
         
            -
                    int += 2 
     | 
| 
      
 127 
     | 
    
         
            +
                    int += 2**index if @weekdays[day]
         
     | 
| 
       130 
128 
     | 
    
         
             
                  end
         
     | 
| 
       131 
129 
     | 
    
         
             
                  int
         
     | 
| 
       132 
130 
     | 
    
         
             
                end
         
     | 
| 
         @@ -143,6 +141,6 @@ module Timely 
     | 
|
| 
       143 
141 
     | 
    
         
             
                  end
         
     | 
| 
       144 
142 
     | 
    
         
             
                end
         
     | 
| 
       145 
143 
     | 
    
         | 
| 
       146 
     | 
    
         
            -
                ALL_WEEKDAYS = WeekDays.new(%w[1 1 1 1 1 1 1])
         
     | 
| 
      
 144 
     | 
    
         
            +
                ALL_WEEKDAYS = WeekDays.new(%w[1 1 1 1 1 1 1]).freeze
         
     | 
| 
       147 
145 
     | 
    
         
             
              end
         
     | 
| 
       148 
146 
     | 
    
         
             
            end
         
     | 
    
        data/lib/timely.rb
    CHANGED
    
    
    
        data/rails/init.rb
    CHANGED
    
    
    
        data/spec/calendar_tag_spec.rb
    CHANGED
    
    | 
         @@ -1,3 +1,5 @@ 
     | 
|
| 
      
 1 
     | 
    
         
            +
            # frozen_string_literal: true
         
     | 
| 
      
 2 
     | 
    
         
            +
             
     | 
| 
       1 
3 
     | 
    
         
             
            require 'spec_helper'
         
     | 
| 
       2 
4 
     | 
    
         | 
| 
       3 
5 
     | 
    
         
             
            class ActionViewTest
         
     | 
| 
         @@ -8,22 +10,21 @@ describe Timely::ActionViewHelpers do 
     | 
|
| 
       8 
10 
     | 
    
         
             
              subject { ActionViewTest.new }
         
     | 
| 
       9 
11 
     | 
    
         
             
              let(:string) { double(:string) }
         
     | 
| 
       10 
12 
     | 
    
         
             
              let(:date) { Date.new(2000, 12, 25) }
         
     | 
| 
       11 
     | 
    
         
            -
              before  
     | 
| 
      
 13 
     | 
    
         
            +
              before do
         
     | 
| 
       12 
14 
     | 
    
         
             
                expect(date).to receive(:to_s).with(:calendar).and_return('25-12-2000')
         
     | 
| 
       13 
15 
     | 
    
         
             
                expect(Timely).to receive(:current_date).and_return(date)
         
     | 
| 
       14 
     | 
    
         
            -
               
     | 
| 
      
 16 
     | 
    
         
            +
              end
         
     | 
| 
       15 
17 
     | 
    
         | 
| 
       16 
18 
     | 
    
         
             
              it 'should generate calendar tags' do
         
     | 
| 
       17 
19 
     | 
    
         
             
                expect(string).to receive(:html_safe)
         
     | 
| 
       18 
20 
     | 
    
         
             
                expect(subject).to receive(:tag).with(:input,
         
     | 
| 
       19 
     | 
    
         
            -
             
     | 
| 
       20 
     | 
    
         
            -
             
     | 
| 
       21 
     | 
    
         
            -
             
     | 
| 
       22 
     | 
    
         
            -
             
     | 
| 
       23 
     | 
    
         
            -
             
     | 
| 
       24 
     | 
    
         
            -
             
     | 
| 
       25 
     | 
    
         
            -
             
     | 
| 
       26 
     | 
    
         
            -
                ).and_return(string)
         
     | 
| 
      
 21 
     | 
    
         
            +
                                                      id: 'test',
         
     | 
| 
      
 22 
     | 
    
         
            +
                                                      class: 'datepicker',
         
     | 
| 
      
 23 
     | 
    
         
            +
                                                      size: 10,
         
     | 
| 
      
 24 
     | 
    
         
            +
                                                      maxlength: 10,
         
     | 
| 
      
 25 
     | 
    
         
            +
                                                      name: 'test',
         
     | 
| 
      
 26 
     | 
    
         
            +
                                                      type: 'text',
         
     | 
| 
      
 27 
     | 
    
         
            +
                                                      value: '25-12-2000').and_return(string)
         
     | 
| 
       27 
28 
     | 
    
         
             
                subject.calendar_tag :test
         
     | 
| 
       28 
29 
     | 
    
         
             
              end
         
     | 
| 
       29 
30 
     | 
    
         
             
            end
         
     | 
    
        data/spec/date_chooser_spec.rb
    CHANGED
    
    | 
         @@ -1,110 +1,115 @@ 
     | 
|
| 
      
 1 
     | 
    
         
            +
            # frozen_string_literal: true
         
     | 
| 
      
 2 
     | 
    
         
            +
             
     | 
| 
       1 
3 
     | 
    
         
             
            require 'spec_helper'
         
     | 
| 
       2 
4 
     | 
    
         | 
| 
       3 
5 
     | 
    
         
             
            describe Timely::DateChooser do
         
     | 
| 
       4 
6 
     | 
    
         
             
              before(:all) do
         
     | 
| 
       5 
     | 
    
         
            -
                @from =  
     | 
| 
       6 
     | 
    
         
            -
                @to =  
     | 
| 
      
 7 
     | 
    
         
            +
                @from = '01-01-2011'.to_date
         
     | 
| 
      
 8 
     | 
    
         
            +
                @to = '01-03-2011'.to_date
         
     | 
| 
       7 
9 
     | 
    
         
             
              end
         
     | 
| 
       8 
10 
     | 
    
         | 
| 
       9 
     | 
    
         
            -
              #Validation
         
     | 
| 
       10 
     | 
    
         
            -
              it  
     | 
| 
       11 
     | 
    
         
            -
                expect { Timely::DateChooser.new( 
     | 
| 
       12 
     | 
    
         
            -
                  Timely::DateChooserException, 'A Start Date is required' 
     | 
| 
      
 11 
     | 
    
         
            +
              # Validation
         
     | 
| 
      
 12 
     | 
    
         
            +
              it 'rejects blank FROM dates' do
         
     | 
| 
      
 13 
     | 
    
         
            +
                expect { Timely::DateChooser.new(from: '') }.to raise_error(
         
     | 
| 
      
 14 
     | 
    
         
            +
                  Timely::DateChooserException, 'A Start Date is required'
         
     | 
| 
      
 15 
     | 
    
         
            +
                )
         
     | 
| 
       13 
16 
     | 
    
         
             
              end
         
     | 
| 
       14 
17 
     | 
    
         | 
| 
       15 
     | 
    
         
            -
              it  
     | 
| 
       16 
     | 
    
         
            -
                expect  
     | 
| 
       17 
     | 
    
         
            -
                   
     | 
| 
       18 
     | 
    
         
            -
             
     | 
| 
      
 18 
     | 
    
         
            +
              it 'rejects TO dates later than FROM dates' do
         
     | 
| 
      
 19 
     | 
    
         
            +
                expect do
         
     | 
| 
      
 20 
     | 
    
         
            +
                  Timely::DateChooser.new(
         
     | 
| 
      
 21 
     | 
    
         
            +
                    multiple_dates: true, from: @from + 10, to: @from
         
     | 
| 
      
 22 
     | 
    
         
            +
                  )
         
     | 
| 
      
 23 
     | 
    
         
            +
                end .to raise_error(Timely::DateChooserException, 'Start Date is after End Date')
         
     | 
| 
       19 
24 
     | 
    
         
             
              end
         
     | 
| 
       20 
25 
     | 
    
         | 
| 
       21 
     | 
    
         
            -
              #Operation
         
     | 
| 
       22 
     | 
    
         
            -
              it  
     | 
| 
      
 26 
     | 
    
         
            +
              # Operation
         
     | 
| 
      
 27 
     | 
    
         
            +
              it 'returns today if client only wants single date' do
         
     | 
| 
       23 
28 
     | 
    
         
             
                expect(Timely::DateChooser.new(
         
     | 
| 
       24 
     | 
    
         
            -
                  : 
     | 
| 
      
 29 
     | 
    
         
            +
                  multiple_dates: false, from: @from
         
     | 
| 
       25 
30 
     | 
    
         
             
                ).choose_dates).to eq [@from]
         
     | 
| 
       26 
31 
     | 
    
         
             
              end
         
     | 
| 
       27 
32 
     | 
    
         | 
| 
       28 
     | 
    
         
            -
              #Test specific date of month
         
     | 
| 
       29 
     | 
    
         
            -
              it  
     | 
| 
      
 33 
     | 
    
         
            +
              # Test specific date of month
         
     | 
| 
      
 34 
     | 
    
         
            +
              it 'returns from and to as same (one) day in the case that only from date is given' do
         
     | 
| 
       30 
35 
     | 
    
         
             
                expect(Timely::DateChooser.new(
         
     | 
| 
       31 
     | 
    
         
            -
                  : 
     | 
| 
      
 36 
     | 
    
         
            +
                  multiple_dates: true, from: @from, to: ''
         
     | 
| 
       32 
37 
     | 
    
         
             
                ).choose_dates).to eq [@from]
         
     | 
| 
       33 
38 
     | 
    
         
             
              end
         
     | 
| 
       34 
39 
     | 
    
         | 
| 
       35 
     | 
    
         
            -
              it  
     | 
| 
      
 40 
     | 
    
         
            +
              it 'returns all days between from and to days in the basic case' do
         
     | 
| 
       36 
41 
     | 
    
         
             
                expect(Timely::DateChooser.new(
         
     | 
| 
       37 
     | 
    
         
            -
                  : 
     | 
| 
       38 
     | 
    
         
            -
                ).choose_dates).to eq 
     | 
| 
      
 42 
     | 
    
         
            +
                  multiple_dates: true, from: @from, to: @to
         
     | 
| 
      
 43 
     | 
    
         
            +
                ).choose_dates).to eq((@from..@to).to_a)
         
     | 
| 
       39 
44 
     | 
    
         
             
              end
         
     | 
| 
       40 
45 
     | 
    
         | 
| 
       41 
     | 
    
         
            -
              it  
     | 
| 
      
 46 
     | 
    
         
            +
              it 'returns the recurring dates within the range if this option is picked' do
         
     | 
| 
       42 
47 
     | 
    
         
             
                expect(Timely::DateChooser.new(
         
     | 
| 
       43 
     | 
    
         
            -
                  : 
     | 
| 
       44 
     | 
    
         
            -
                ).choose_dates).to eq [
         
     | 
| 
       45 
     | 
    
         
            -
                   
     | 
| 
       46 
     | 
    
         
            -
                   
     | 
| 
      
 48 
     | 
    
         
            +
                  multiple_dates: true, select: 'days', dates: '1,11,3', from: @from, to: @to
         
     | 
| 
      
 49 
     | 
    
         
            +
                ).choose_dates).to eq %w[
         
     | 
| 
      
 50 
     | 
    
         
            +
                  1-01-2011 3-01-2011 11-01-2011 1-02-2011
         
     | 
| 
      
 51 
     | 
    
         
            +
                  3-02-2011 11-02-2011 1-03-2011
         
     | 
| 
       47 
52 
     | 
    
         
             
                ].map(&:to_date)
         
     | 
| 
       48 
53 
     | 
    
         
             
              end
         
     | 
| 
       49 
54 
     | 
    
         | 
| 
       50 
     | 
    
         
            -
              it  
     | 
| 
      
 55 
     | 
    
         
            +
              it 'returns the specific dates, within or outside of the range, if this option is picked' do
         
     | 
| 
       51 
56 
     | 
    
         
             
                expect(Timely::DateChooser.new(
         
     | 
| 
       52 
     | 
    
         
            -
                  : 
     | 
| 
       53 
     | 
    
         
            -
                ).choose_dates).to eq [
         
     | 
| 
       54 
     | 
    
         
            -
                   
     | 
| 
      
 57 
     | 
    
         
            +
                  multiple_dates: true, select: 'specific_days', specific_dates: '11-01-2011, 18-02-2011, 22-06-2011', from: @from, to: @to
         
     | 
| 
      
 58 
     | 
    
         
            +
                ).choose_dates).to eq %w[
         
     | 
| 
      
 59 
     | 
    
         
            +
                  11-01-2011 18-02-2011 22-06-2011
         
     | 
| 
       55 
60 
     | 
    
         
             
                ].map(&:to_date)
         
     | 
| 
       56 
61 
     | 
    
         
             
              end
         
     | 
| 
       57 
62 
     | 
    
         | 
| 
       58 
     | 
    
         
            -
              #Test days of week, every X weeks
         
     | 
| 
       59 
     | 
    
         
            -
              it  
     | 
| 
      
 63 
     | 
    
         
            +
              # Test days of week, every X weeks
         
     | 
| 
      
 64 
     | 
    
         
            +
              it 'returns every sunday correctly' do
         
     | 
| 
       60 
65 
     | 
    
         
             
                expect(Timely::DateChooser.new(
         
     | 
| 
       61 
     | 
    
         
            -
                  : 
     | 
| 
       62 
     | 
    
         
            -
                  : 
     | 
| 
       63 
     | 
    
         
            -
                ).choose_dates).to eq [
         
     | 
| 
       64 
     | 
    
         
            -
                   
     | 
| 
       65 
     | 
    
         
            -
                   
     | 
| 
      
 66 
     | 
    
         
            +
                  multiple_dates: true, select: 'weekdays', from: @from, to: @to,
         
     | 
| 
      
 67 
     | 
    
         
            +
                  interval: { level: '1', unit: 'week' }, weekdays: { sun: true }
         
     | 
| 
      
 68 
     | 
    
         
            +
                ).choose_dates).to eq %w[
         
     | 
| 
      
 69 
     | 
    
         
            +
                  2-01-2011 9-01-2011 16-01-2011 23-01-2011 30-01-2011
         
     | 
| 
      
 70 
     | 
    
         
            +
                  06-02-2011 13-02-2011 20-02-2011 27-02-2011
         
     | 
| 
       66 
71 
     | 
    
         
             
                ].map(&:to_date)
         
     | 
| 
       67 
72 
     | 
    
         
             
              end
         
     | 
| 
       68 
73 
     | 
    
         | 
| 
       69 
     | 
    
         
            -
              it  
     | 
| 
      
 74 
     | 
    
         
            +
              it 'returns every thursday and sunday correctly' do
         
     | 
| 
       70 
75 
     | 
    
         
             
                expect(Timely::DateChooser.new(
         
     | 
| 
       71 
     | 
    
         
            -
                  : 
     | 
| 
       72 
     | 
    
         
            -
                  : 
     | 
| 
       73 
     | 
    
         
            -
                  : 
     | 
| 
       74 
     | 
    
         
            -
                ).choose_dates).to eq [
         
     | 
| 
       75 
     | 
    
         
            -
                   
     | 
| 
       76 
     | 
    
         
            -
                   
     | 
| 
       77 
     | 
    
         
            -
                   
     | 
| 
       78 
     | 
    
         
            -
                   
     | 
| 
      
 76 
     | 
    
         
            +
                  multiple_dates: true, select: 'weekdays',
         
     | 
| 
      
 77 
     | 
    
         
            +
                  interval: { level: '1', unit: 'week' },
         
     | 
| 
      
 78 
     | 
    
         
            +
                  weekdays: { sun: true, thu: true }, from: @from, to: @to
         
     | 
| 
      
 79 
     | 
    
         
            +
                ).choose_dates).to eq %w[
         
     | 
| 
      
 80 
     | 
    
         
            +
                  2-01-2011 6-01-2011 9-01-2011 13-01-2011 16-01-2011
         
     | 
| 
      
 81 
     | 
    
         
            +
                  20-01-2011 23-01-2011 27-01-2011 30-01-2011 3-02-2011
         
     | 
| 
      
 82 
     | 
    
         
            +
                  06-02-2011 10-02-2011 13-02-2011 17-02-2011 20-02-2011
         
     | 
| 
      
 83 
     | 
    
         
            +
                  24-02-2011 27-02-2011
         
     | 
| 
       79 
84 
     | 
    
         
             
                ].map(&:to_date)
         
     | 
| 
       80 
85 
     | 
    
         
             
              end
         
     | 
| 
       81 
86 
     | 
    
         | 
| 
       82 
     | 
    
         
            -
              it  
     | 
| 
      
 87 
     | 
    
         
            +
              it 'returns every 2nd thursday and sunday correctly' do
         
     | 
| 
       83 
88 
     | 
    
         
             
                expect(Timely::DateChooser.new(
         
     | 
| 
       84 
     | 
    
         
            -
                  : 
     | 
| 
       85 
     | 
    
         
            -
                  : 
     | 
| 
       86 
     | 
    
         
            -
                  : 
     | 
| 
       87 
     | 
    
         
            -
                ).choose_dates).to eq [
         
     | 
| 
       88 
     | 
    
         
            -
                   
     | 
| 
       89 
     | 
    
         
            -
                   
     | 
| 
      
 89 
     | 
    
         
            +
                  multiple_dates: true, select: 'weekdays',
         
     | 
| 
      
 90 
     | 
    
         
            +
                  interval: { level: '2', unit: 'week' },
         
     | 
| 
      
 91 
     | 
    
         
            +
                  weekdays: { sun: '1', thu: '1' }, from: @from, to: @to
         
     | 
| 
      
 92 
     | 
    
         
            +
                ).choose_dates).to eq %w[
         
     | 
| 
      
 93 
     | 
    
         
            +
                  2-01-2011 6-01-2011 16-01-2011 20-01-2011 30-01-2011
         
     | 
| 
      
 94 
     | 
    
         
            +
                  3-02-2011 13-02-2011 17-02-2011 27-02-2011
         
     | 
| 
       90 
95 
     | 
    
         
             
                ].map(&:to_date)
         
     | 
| 
       91 
96 
     | 
    
         
             
              end
         
     | 
| 
       92 
97 
     | 
    
         | 
| 
       93 
     | 
    
         
            -
              #Test correct results for every Nth week of month
         
     | 
| 
       94 
     | 
    
         
            -
              it  
     | 
| 
      
 98 
     | 
    
         
            +
              # Test correct results for every Nth week of month
         
     | 
| 
      
 99 
     | 
    
         
            +
              it 'returns every 1st Tuesday' do
         
     | 
| 
       95 
100 
     | 
    
         
             
                expect(Timely::DateChooser.new(
         
     | 
| 
       96 
     | 
    
         
            -
                  : 
     | 
| 
       97 
     | 
    
         
            -
                  : 
     | 
| 
       98 
     | 
    
         
            -
                ).choose_dates).to eq [ 
     | 
| 
      
 101 
     | 
    
         
            +
                  multiple_dates: true, select: 'weekdays', from: @from, to: @to,
         
     | 
| 
      
 102 
     | 
    
         
            +
                  interval: { level: '1', unit: 'week_of_month' }, weekdays: { tue: true }
         
     | 
| 
      
 103 
     | 
    
         
            +
                ).choose_dates).to eq %w[4-01-2011 1-02-2011 1-03-2011].map(&:to_date)
         
     | 
| 
       99 
104 
     | 
    
         
             
              end
         
     | 
| 
       100 
105 
     | 
    
         | 
| 
       101 
     | 
    
         
            -
              it  
     | 
| 
      
 106 
     | 
    
         
            +
              it 'returns every 3st Monday and Friday' do
         
     | 
| 
       102 
107 
     | 
    
         
             
                expect(Timely::DateChooser.new(
         
     | 
| 
       103 
     | 
    
         
            -
                  : 
     | 
| 
       104 
     | 
    
         
            -
                  : 
     | 
| 
       105 
     | 
    
         
            -
                  : 
     | 
| 
       106 
     | 
    
         
            -
                ).choose_dates).to eq [
         
     | 
| 
       107 
     | 
    
         
            -
                   
     | 
| 
      
 108 
     | 
    
         
            +
                  multiple_dates: true, select: 'weekdays',
         
     | 
| 
      
 109 
     | 
    
         
            +
                  interval: { level: '3', unit: 'week_of_month' },
         
     | 
| 
      
 110 
     | 
    
         
            +
                  weekdays: { mon: true, fri: true }, from: @from, to: @to
         
     | 
| 
      
 111 
     | 
    
         
            +
                ).choose_dates).to eq %w[
         
     | 
| 
      
 112 
     | 
    
         
            +
                  17-01-2011 21-01-2011 18-02-2011 21-02-2011
         
     | 
| 
       108 
113 
     | 
    
         
             
                ].map(&:to_date)
         
     | 
| 
       109 
114 
     | 
    
         
             
              end
         
     | 
| 
       110 
115 
     | 
    
         
             
            end
         
     |