class Doing::Items
A collection of Item
objects
Attributes
Public Class Methods
Source
# File lib/doing/items/items.rb, line 13 def initialize super @sections = [] end
Public Instance Methods
Source
# File lib/doing/items/sections.rb, line 59 def add_section(section, log: false) section = section.is_a?(Section) ? section : Section.new(section.cap_first) return if section?(section) @sections.push(section) Doing.logger.info('New section:', %("#{section}" added)) if log end
Add a new section to the sections array. Accepts either a Section
object, or a title string that will be converted into a Section
.
@param section [Section] The section to add. A String
value will be converted to Section
automatically. @param log [Boolean] Add a log message notifying the user about the creation of the section.
@return nothing
Source
# File lib/doing/items/filter.rb, line 62 def between_dates(start, finish) start = start.chronify(guess: :begin, future: false) if start.is_a?(String) finish = finish.chronify(guess: :end) if finish.is_a?(String) WWID.new.filter_items(self, opt: { date_filter: [start, finish] }) end
Filter Items
by date. String
arguments will be chronified
@param start [Time,String] Filter items after this date @param finish [Time,String] Filter items before this date
@return [Items] array of items with dates between targets
Source
# File lib/doing/items/util.rb, line 60 def dedup(match_section: true) unique = Items.new each do |item| unique.push(item) unless unique.include?(item, match_section: match_section) end unique end
Remove duplicated entries. Duplicate entries must have matching start date, title, note, and section
@return [Items] Items
array with duplicate entries removed
Source
# File lib/doing/items/util.rb, line 70 def dedup!(match_section: true) replace dedup(match_section: match_section) end
@see dedup
Source
Source
# File lib/doing/items/modify.rb, line 10 def delete_item(item, single: false) deleted = delete(item) Doing.logger.count(:deleted) Doing.logger.info('Entry deleted:', deleted.title) if single deleted end
Delete an item from the index
@param item The item
Source
# File lib/doing/items/sections.rb, line 68 def delete_section(section, log: false) return unless section?(section) raise DoingRuntimeError, 'Section not empty' if in_section(section).count.positive? @sections.each do |sect| next unless sect.title == section && in_section(sect).count.zero? @sections.delete(sect) Doing.logger.info('Removed section:', %("#{section}" removed)) if log end Doing.logger.error('Not found:', %("#{section}" not found)) end
Source
# File lib/doing/items/util.rb, line 40 def diff(items) a = clone b = items.clone a.delete_if do |item| if b.include?(item) b.delete(item) true else false end end { added: b, deleted: a } end
Return Items
containing items that don’t exist in receiver
@param items [Items] Receiver
@return [Hash] Hash
of added and deleted items
Source
# File lib/doing/items/items.rb, line 42 def find_id(id) select { |item| item.id == id }[0] end
Find an item by ID
@param id The identifier to match
Source
# File lib/doing/items/sections.rb, line 32 def guess_section(frag, distance: 2) section = nil re = frag.to_rx(distance: distance, case_type: :ignore) @sections.each do |sect| next unless sect.title =~ /#{re}/i Doing.logger.debug('Match:', %(Assuming "#{sect.title}" from "#{frag}")) section = sect break end section end
Return the best section match for a search query
@param frag The search query @param distance The distance apart characters can be (fuzziness)
@return [Section] (first) matching section object
Source
# File lib/doing/items/filter.rb, line 12 def in_section(section) sect = section.is_a?(Section) ? section.title : section if sect =~ /^all$/i dup else items = Items.new.concat(select { |item| !item.nil? && item.section == section }) items.add_section(section, log: false) items end end
Get a new Items
object containing only items in a specified section
@param section [String] section title
@return [Items] Array
of items
Source
# File lib/doing/items/items.rb, line 26 def include?(item, match_section: true) includes = false each do |other_item| if other_item.equal?(item, match_section: match_section) includes = true break end end includes end
Test if self includes Item
@param item [Item] The item to search for @param match_section [Boolean] Section
must match
@return [Boolean] True if Item
exists
Source
# File lib/doing/items/items.rb, line 51 def index_for_id(id) i = nil each_with_index do |item, idx| if item.id == id i = idx break end end i end
Return the index for an entry matching ID
@param id The identifier to match
Source
# File lib/doing/items/items.rb, line 76 def inspect sections = @sections.map { |s| "<Section:#{s.title} #{in_section(s.title).count} items>" }.join(', ') "#<Doing::Items #{count} items, #{@sections.count} sections: #{sections}>" end
@private
Source
# File lib/doing/items/filter.rb, line 32 def search(query, case_type: :smart) WWID.new.fuzzy_filter_items(self, query, case_type: case_type) end
Search Items
for a string (title and note)
@param query [String] The query @param case_type [Symbol] The case type (:smart, :sensitive, :ignore)
@return [Items] array of items matching search
Source
# File lib/doing/items/sections.rb, line 19 def section?(section) section = section.is_a?(Section) ? section.title.downcase : section.downcase @sections.map { |i| i.title.downcase }.include?(section) end
Test if section already exists
@param section [String] section title
@return [Boolean] true if section exists
Source
# File lib/doing/items/sections.rb, line 9 def section_titles @sections.map(&:title) end
List sections, title only
@return [Array] section titles
Source
# File lib/doing/items/filter.rb, line 46 def tagged(tags, bool: :and) WWID.new.filter_items(self, opt: { tag: tags, bool: bool }) end
Search items by tags
@param tags [Array,String] The tags by which to filter @param bool [Symbol] The bool with which to combine multiple tags
@return [Items] array of items matching tag filter
Source
# File lib/doing/items/items.rb, line 63 def to_s out = [] @sections.each do |section| out.push(section.original) items = in_section(section.title).sort_by { |i| [i.date, i.title] } items.reverse! if Doing.setting('doing_file_sort').normalize_order == :desc items.each { |item| out.push(item.to_s) } end out.join("\n") end
Output sections and items in Doing
file format
Source
# File lib/doing/items/modify.rb, line 23 def update_item(old_item, new_item) s_idx = index { |item| item.equal?(old_item) } raise ItemNotFound, 'Unable to find item in index, did it mutate?' unless s_idx return if fetch(s_idx).equal?(new_item) self[s_idx] = new_item Doing.logger.count(:updated) Doing.logger.info('Entry updated:', self[s_idx].title.trunc(60)) new_item end
Update an item in the index with a modified item
@param old_item The old item @param new_item The new item