class Irc::Bot::Journal::Storage::MongoStorage

Attributes

client[R]

Public Class Methods

new(opts={}) click to toggle source
# File lib/rbot/journal/mongo.rb, line 19
def initialize(opts={})
  Mongo::Logger.logger.level = Logger::WARN
  @uri = opts[:uri] || 'mongodb://127.0.0.1:27017/rbot'
  @client = Mongo::Client.new(@uri)
  @collection = @client['journal']
  log 'journal storage: mongodb connected to ' + @uri
  
  drop if opts[:drop]
  @collection.indexes.create_one({topic: 1})
  @collection.indexes.create_one({timestamp: 1})
end

Public Instance Methods

count(query=nil) click to toggle source

returns the number of messages that match the query

# File lib/rbot/journal/mongo.rb, line 62
def count(query=nil)
  query_cursor(query).count
end
drop() click to toggle source
# File lib/rbot/journal/mongo.rb, line 70
def drop
  @collection.drop
end
ensure_payload_index(key) click to toggle source
# File lib/rbot/journal/mongo.rb, line 31
def ensure_payload_index(key)
  @collection.indexes.create_one({'payload.'+key => 1})
end
find(query=nil, limit=100, offset=0, &block) click to toggle source
# File lib/rbot/journal/mongo.rb, line 44
def find(query=nil, limit=100, offset=0, &block)
  def to_message(document)
    JournalMessage.new(id: document['_id'],
                       timestamp: document['timestamp'].localtime,
                       topic: document['topic'],
                       payload: document['payload'].to_h)
  end

  cursor = query_cursor(query).skip(offset).limit(limit)

  if block_given?
    cursor.each { |document| block.call(to_message(document)) }
  else
    cursor.map { |document| to_message(document) }
  end
end
insert(m) click to toggle source
# File lib/rbot/journal/mongo.rb, line 35
def insert(m)
  @collection.insert_one({
    '_id' => m.id,
    'topic' => m.topic,
    'timestamp' => m.timestamp,
    'payload' => m.payload
  })
end
query_cursor(query) click to toggle source
# File lib/rbot/journal/mongo.rb, line 74
def query_cursor(query)
  unless query
    return @collection.find()
  end

  query_and = []

  # ID query OR condition
  unless query.id.empty?
    query_and << {
      '$or' => query.id.map { |_id| 
        {'_id' => _id}
      }
    }
  end

  unless query.topic.empty?
    query_and << {
      '$or' => query.topic.map { |topic|
        if topic.include?('*')
          pattern = topic.gsub('.', '\.').gsub('*', '.*')
          {'topic' => {'$regex' => pattern}}
        else
          {'topic' => topic}
        end
      }
    }
  end

  if query.timestamp[:from] or query.timestamp[:to]
    where = {}
    if query.timestamp[:from]
      where['$gte'] = query.timestamp[:from]
    end
    if query.timestamp[:to]
      where['$lte'] = query.timestamp[:to]
    end
    query_and << {'timestamp' => where}
  end

  unless query.payload.empty?
    query_and << {
      '$or' => query.payload.map { |key, value|
        key = 'payload.' + key
        {key => value}
      }
    }
  end

  @collection.find({
    '$and' => query_and
  })
end
remove(query=nil) click to toggle source
# File lib/rbot/journal/mongo.rb, line 66
def remove(query=nil)
  query_cursor(query).delete_many
end
to_message(document) click to toggle source
# File lib/rbot/journal/mongo.rb, line 45
def to_message(document)
  JournalMessage.new(id: document['_id'],
                     timestamp: document['timestamp'].localtime,
                     topic: document['topic'],
                     payload: document['payload'].to_h)
end