Мариян обнови решението на 21.12.2015 17:02 (преди около 9 години)
+module LazyMode
+ class Date
+ attr_accessor :year, :month, :day
+ def initialize(date)
+ split_date = date.split "-"
+ @year = split_date[0].to_i
+ @month = split_date[1].to_i
+ @day = split_date[2].to_i
+ end
+
+ def -(date)
+ self_in_days = year * 12 * 30 + month * 30 + day
+ date_in_days = date.year * 12 * 30 + date.month * 30 + date.day
+ self_in_days - date_in_days
+ end
+
+ def <(date)
+ self - date < 0
+ end
+
+ def to_s
+ "%04d-%02d-%02d" % [@year, @month, @day]
+ end
+ end
+
+ class Note
+ attr_accessor :header, :file_name, :body, :status, :tags, :scheduled, :notes
+
+ def initialize(header, file_name, status, tags)
+ @header = header
+ @file_name = file_name
+ @status = status
+ @tags = tags
+ end
+ end
+
+ class File
+ attr_accessor :name, :notes
+
+ def initialize(name, notes)
+ @name = name.dup
+ @notes = notes
+ end
+
+ def daily_agenda(date)
+ Agenda.new(self, date, 1)
+ end
+
+ def weekly_agenda(date)
+ Agenda.new(self, date, 7)
+ end
+ end
+
+ class NoteBuilder
+ def initialize(file_name, header = nil, tags = nil)
+ @notes = []
+ @file_name = file_name
+ @header = header
+ @tags = tags
+ @status = :topostpone
+ @body = ""
+ end
+
+ def status(symbol)
+ @status = symbol
+ end
+
+ def body(text)
+ @body = text
+ end
+
+ def scheduled(date)
+ @scheduled = date
+ end
+
+ def note(header, *tags, &block)
+ @notes << NoteBuilder.new(@file_name, header, tags).build(&block)
+ end
+
+ def build(&block)
+ instance_eval &block
+ note = Note.new(@header, @file_name, @status, @tags)
+ note.body = @body
+ note.scheduled = @scheduled
+ note.notes = @notes
+ note
+ end
+ end
+
+ class Agenda
+ DAYS_IN_LETTERS = {"d" => 1, "w" => 7, "m" => 30}
+
+ # TODO add filters to "where"
+ def initialize(notes_holder, date = nil, day_difference = nil, **filters)
+ @notes = flatten(notes_holder)#.each { |note| note.date = date }
+ filter(filters) if date.nil?
+ if date.nil?
+ #filter(**filters)
+ else
+ #check_date(date, day_difference)
+ end
+ end
+
+ def where(**filters)
+ Agenda.new(self, **filters)
+ end
+
+ #private
+ def flatten(note_array)
+ if note_array.notes == []
+ note_array
+ else
+ #note_array.reduce([]) { |array, note| array + flatten(note) }
+ end
+ end
+
+ def parse_scheduled(schedule)
+ split_schedule = schedule.split " "
+ days = 0
+ unless split_schedule[1].nil?
+ matches = split_schedule[1].match /\+(\d+)([dwm])/
+ days = matches[1].to_i * DAYS_IN_LETTERS[matches[2]]
+ end
+ [Date.new(split_schedule[0]), days]
+ end
+
+ def filter(**filters)
+ # TODO
+ end
+
+ def check_date(date, day_difference)
+ @notes.keep_if do |note|
+ note_date, note_delta = parse_scheduled(note.schedule)
+ (@date - note_date) % note_delta < @day_difference
+ end
+ end
+ end
+
+ def self.create_file(file_name, &block)
+ File.new(file_name, NoteBuilder.new(file_name).build(&block).notes)
+ end
+end