bitbckt-botbckt 0.1.1 → 0.2.0
Sign up to get free protection for your applications and to get access to all the features.
- data/VERSION.yml +2 -2
- data/lib/botbckt/bot.rb +6 -4
- data/lib/botbckt/commands/google.rb +4 -4
- data/lib/botbckt/commands/meme.rb +2 -2
- data/lib/botbckt/commands/ping.rb +2 -2
- data/lib/botbckt/commands/remind.rb +6 -6
- data/lib/botbckt/commands/snack.rb +2 -2
- data/lib/botbckt/commands/ticker.rb +5 -6
- data/lib/botbckt/commands.rb +9 -3
- data/lib/botbckt/irc.rb +18 -21
- data/lib/botbckt.rb +2 -0
- metadata +2 -2
data/VERSION.yml
CHANGED
data/lib/botbckt/bot.rb
CHANGED
@@ -20,6 +20,7 @@ module Botbckt #:nodoc:
|
|
20
20
|
# :port<~to_i>:: The port number of the IRC server. Required.
|
21
21
|
# :channels<Array[String]>:: An array of channels to join. Channel names should *not* include the '#' prefix. Required.
|
22
22
|
# :log<String>:: The name of a log file. Defaults to 'botbckt.log'.
|
23
|
+
# :log_level<Integer>:: The minimum severity level to log. Defaults to 1 (INFO).
|
23
24
|
#
|
24
25
|
def self.start(options)
|
25
26
|
EventMachine::run do
|
@@ -34,9 +35,9 @@ module Botbckt #:nodoc:
|
|
34
35
|
#--
|
35
36
|
# TODO: Before/after callbacks?
|
36
37
|
#++
|
37
|
-
def self.run(command, *args)
|
38
|
+
def self.run(command, sender, channel, *args)
|
38
39
|
proc = self.commands[command.to_sym]
|
39
|
-
proc ? proc.call(*args) : say(befuddled)
|
40
|
+
proc ? proc.call(sender, channel, *args) : say(befuddled, channel)
|
40
41
|
end
|
41
42
|
|
42
43
|
# Returns a random "affirmative" message. Use to acknowledge user input.
|
@@ -60,9 +61,10 @@ module Botbckt #:nodoc:
|
|
60
61
|
|
61
62
|
# ==== Parameters
|
62
63
|
# msg<String>:: A message to send to the channel
|
64
|
+
# channel<String>:: The channel to send the message. Required.
|
63
65
|
#
|
64
|
-
def self.say(msg)
|
65
|
-
Botbckt::IRC.connection.say msg
|
66
|
+
def self.say(msg, channel)
|
67
|
+
Botbckt::IRC.connection.say msg, channel
|
66
68
|
end
|
67
69
|
|
68
70
|
end
|
@@ -12,11 +12,11 @@ module Botbckt #:nodoc:
|
|
12
12
|
class Google
|
13
13
|
extend Commands
|
14
14
|
|
15
|
-
on :google do |
|
15
|
+
on :google do |sender, channel, query|
|
16
16
|
result = google(query)
|
17
|
-
say "First out of #{result.first} results:"
|
18
|
-
say result.last['titleNoFormatting']
|
19
|
-
say result.last['unescapedUrl']
|
17
|
+
say "First out of #{result.first} results:", channel
|
18
|
+
say result.last['titleNoFormatting'], channel
|
19
|
+
say result.last['unescapedUrl'], channel
|
20
20
|
end
|
21
21
|
|
22
22
|
private
|
@@ -12,7 +12,7 @@ module Botbckt #:nodoc:
|
|
12
12
|
|
13
13
|
SCALES = %w{ minute minutes second seconds hour hours }
|
14
14
|
|
15
|
-
on :remind do |
|
15
|
+
on :remind do |user, channel, reminder_string|
|
16
16
|
# Somewhat faster than #match...
|
17
17
|
reminder_string =~ /in (\d+) (\w+) with (.*)/i
|
18
18
|
num, scale, msg = $1, $2, $3
|
@@ -21,19 +21,19 @@ module Botbckt #:nodoc:
|
|
21
21
|
time = num.to_i.send(scale.to_sym).seconds
|
22
22
|
|
23
23
|
# TODO: Abstraction here, please.
|
24
|
-
remind(user.gsub(/([^!]+).*/, '\1'), msg, time)
|
24
|
+
remind(user.gsub(/([^!]+).*/, '\1'), channel, msg, time)
|
25
25
|
else
|
26
|
-
say Botbckt::Bot.befuddled
|
26
|
+
say Botbckt::Bot.befuddled, channel
|
27
27
|
end
|
28
28
|
end
|
29
29
|
|
30
30
|
private
|
31
31
|
|
32
|
-
def self.remind(user, msg, seconds) #:nodoc:
|
32
|
+
def self.remind(user, channel, msg, seconds) #:nodoc:
|
33
33
|
EventMachine::Timer.new(seconds) do
|
34
|
-
say "#{user}: #{msg}"
|
34
|
+
say "#{user}: #{msg}", channel
|
35
35
|
end
|
36
|
-
say Botbckt::Bot.ok
|
36
|
+
say Botbckt::Bot.ok, channel
|
37
37
|
end
|
38
38
|
|
39
39
|
end
|
@@ -9,22 +9,21 @@ module Botbckt #:nodoc:
|
|
9
9
|
class Ticker
|
10
10
|
extend Commands
|
11
11
|
|
12
|
-
on :ticker do |
|
13
|
-
|
12
|
+
on :ticker do |sender, channel, symbol|
|
13
|
+
stock_price symbol, channel
|
14
14
|
end
|
15
15
|
|
16
16
|
private
|
17
17
|
|
18
|
-
def self.stock_price(symbol) #:nodoc:
|
18
|
+
def self.stock_price(symbol, channel) #:nodoc:
|
19
19
|
json = open("http://www.google.com/finance/info?q=#{CGI.escape(symbol)}")
|
20
20
|
response = JSON.parse(json.read[4..-1]).first
|
21
21
|
|
22
22
|
ticker, price, change = response['t'], response['l'], response['c']
|
23
23
|
|
24
|
-
"#{ticker} - $#{price} (#{change})"
|
24
|
+
say "#{ticker} - $#{price} (#{change})", channel
|
25
25
|
rescue OpenURI::HTTPError => e
|
26
|
-
say Botbckt::Bot.befuddled
|
27
|
-
nil
|
26
|
+
say Botbckt::Bot.befuddled, channel
|
28
27
|
end
|
29
28
|
end
|
30
29
|
|
data/lib/botbckt/commands.rb
CHANGED
@@ -15,15 +15,21 @@ module Botbckt #:nodoc:
|
|
15
15
|
# proc<Proc>:: Proc to execute when the command is triggered.
|
16
16
|
# &block:: Block to execute when the command is triggered.
|
17
17
|
#
|
18
|
+
# ==== Callable args
|
19
|
+
# sender<String>:: The user and host of the triggering user. Example: botbckt!n=botbckt@unaffiliated/botbckt
|
20
|
+
# channel<String>:: The channel on which the command was triggered. Example: #ruby-lang
|
21
|
+
# *args:: Any string following the trigger in the message
|
22
|
+
#
|
18
23
|
def on(command, proc = nil, &block)
|
19
24
|
Botbckt::Bot.commands[command.to_sym] = proc || block
|
20
25
|
end
|
21
26
|
|
22
27
|
# ==== Parameters
|
23
|
-
# msg<String>:: A message to send to the channel
|
28
|
+
# msg<String>:: A message to send to the channel. Required.
|
29
|
+
# channel<String>:: The channel to send the message. Required.
|
24
30
|
#
|
25
|
-
def say(msg)
|
26
|
-
Botbckt::Bot.say(msg) if msg
|
31
|
+
def say(msg, channel)
|
32
|
+
Botbckt::Bot.say(msg, channel) if msg
|
27
33
|
end
|
28
34
|
|
29
35
|
end
|
data/lib/botbckt/irc.rb
CHANGED
@@ -4,6 +4,7 @@ module Botbckt #:nodoc:
|
|
4
4
|
#
|
5
5
|
class IRC < EventMachine::Connection
|
6
6
|
include EventMachine::Protocols::LineText2
|
7
|
+
include ActiveSupport::BufferedLogger::Severity
|
7
8
|
|
8
9
|
attr_accessor :config
|
9
10
|
cattr_accessor :connection
|
@@ -20,6 +21,7 @@ module Botbckt #:nodoc:
|
|
20
21
|
# :port<~to_i>:: The port number of the IRC server. Required.
|
21
22
|
# :channels<Array[String]>:: An array of channels to join. Channel names should *not* include the '#' prefix. Required.
|
22
23
|
# :log<String>:: The name of a log file. Defaults to 'botbckt.log'.
|
24
|
+
# :log_level<Integer>:: The minimum severity level to log. Defaults to 1 (INFO).
|
23
25
|
#
|
24
26
|
def self.connect(options)
|
25
27
|
self.connection = EM.connect(options[:server], options[:port].to_i, self, options)
|
@@ -27,25 +29,26 @@ module Botbckt #:nodoc:
|
|
27
29
|
|
28
30
|
# Use IRC.connect; this method is not for you.
|
29
31
|
#
|
32
|
+
#--
|
33
|
+
# TODO: Ensure options[:channels] is always an Array
|
34
|
+
#++
|
30
35
|
def initialize(options) #:nodoc:
|
31
36
|
self.config = OpenStruct.new(options)
|
32
37
|
|
33
|
-
@logger = ActiveSupport::BufferedLogger.new
|
38
|
+
@logger = ActiveSupport::BufferedLogger.new self.config.log || 'botbckt.log',
|
39
|
+
self.config.log_level || INFO
|
34
40
|
end
|
35
41
|
|
36
42
|
# ==== Parameters
|
37
|
-
# msg<String>:: A message to send to the channel
|
43
|
+
# msg<String>:: A message to send to the channel. Required.
|
44
|
+
# channel<String>:: The channel to send the message. Required.
|
38
45
|
#
|
39
|
-
|
40
|
-
# TODO: Handle multiple channels
|
41
|
-
#++
|
42
|
-
def say(msg)
|
46
|
+
def say(msg, channel)
|
43
47
|
msg.split("\n").each do |msg|
|
44
|
-
command "PRIVMSG", "##{
|
48
|
+
command "PRIVMSG", "##{channel}", ":#{msg}"
|
45
49
|
end
|
46
50
|
end
|
47
51
|
|
48
|
-
|
49
52
|
def post_init #:nodoc:
|
50
53
|
command "USER", [config.user]*4
|
51
54
|
command "NICK", config.user
|
@@ -53,19 +56,16 @@ module Botbckt #:nodoc:
|
|
53
56
|
config.channels.each { |channel| command("JOIN", "##{ channel }") } if config.channels
|
54
57
|
end
|
55
58
|
|
56
|
-
#--
|
57
|
-
# FIXME: Re-order commands args such that 1-2 arity commands can still access
|
58
|
-
# both sender and channel
|
59
|
-
#++
|
60
59
|
def receive_line(line) #:nodoc:
|
61
60
|
case line
|
62
61
|
when /^PING (.*)/:
|
63
62
|
command('PONG', $1)
|
64
|
-
when /^:(\S+) PRIVMSG (.*) :(~|#{Regexp.escape config.user}: )(\w+)( .*)?$/:
|
63
|
+
when /^:(\S+) PRIVMSG #(.*) :(~|#{Regexp.escape config.user}: )(\w+)( .*)?$/:
|
65
64
|
# args are optional - not all commands need/support them
|
66
|
-
args =
|
65
|
+
args = [$1, $2]
|
66
|
+
args << $5.squish if $5
|
67
67
|
|
68
|
-
# run args: command
|
68
|
+
# run args: command, sender, channel, optional args
|
69
69
|
Botbckt::Bot.run($4, *args)
|
70
70
|
else
|
71
71
|
log line
|
@@ -80,12 +80,9 @@ module Botbckt #:nodoc:
|
|
80
80
|
end
|
81
81
|
|
82
82
|
private
|
83
|
-
|
84
|
-
|
85
|
-
|
86
|
-
#++
|
87
|
-
def log(msg) #:nodoc:
|
88
|
-
@logger.add(0, msg)
|
83
|
+
|
84
|
+
def log(msg, level = INFO) #:nodoc:
|
85
|
+
@logger.add(level, msg)
|
89
86
|
end
|
90
87
|
|
91
88
|
def command(*cmd) #:nodoc:
|
data/lib/botbckt.rb
CHANGED
@@ -1,2 +1,4 @@
|
|
1
1
|
%w{ rubygems eventmachine activesupport ostruct json open-uri cgi }.each { |lib| require lib }
|
2
2
|
%w{ irc bot commands }.each { |lib| require File.dirname(__FILE__) + "/botbckt/#{ lib }" }
|
3
|
+
|
4
|
+
Botbckt::Bot.start :user => 'botbckt', :server => 'irc.freenode.net', :port => 6667, :channels => ['reno.rb']
|
metadata
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
2
2
|
name: bitbckt-botbckt
|
3
3
|
version: !ruby/object:Gem::Version
|
4
|
-
version: 0.
|
4
|
+
version: 0.2.0
|
5
5
|
platform: ruby
|
6
6
|
authors:
|
7
7
|
- Brandon Mitchell
|
@@ -9,7 +9,7 @@ autorequire:
|
|
9
9
|
bindir: bin
|
10
10
|
cert_chain: []
|
11
11
|
|
12
|
-
date: 2009-04-
|
12
|
+
date: 2009-04-28 00:00:00 -07:00
|
13
13
|
default_executable:
|
14
14
|
dependencies: []
|
15
15
|
|