aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--dinobot.rb76
-rw-r--r--irc.rb85
2 files changed, 115 insertions, 46 deletions
diff --git a/dinobot.rb b/dinobot.rb
index ce08b7c..ffb38f3 100644
--- a/dinobot.rb
+++ b/dinobot.rb
@@ -1,6 +1,7 @@
-require 'socket'
require 'timeout'
+require_relative 'irc'
+
module Dinobot
class Bot
attr_accessor :trigger
@@ -14,73 +15,42 @@ module Dinobot
@trigger = '!'
- @socket = nil
+ @irc = Dinobot::IRC.new(@server, @port, @nick, @pass)
@modules = Hash.new
@channels = Array.new
instance_eval(&block) if block_given?
end
- def connect
- log :info, "Connecting to #{@server}:#{@port}."
- @socket = TCPSocket.new(@server, @port)
-
- out "PASS #{@pass}" if @pass
- out "NICK #{@nick}"
- out "USER #{@nick} 0 * :#{@nick}"
+ def run
+ @irc.connect unless @irc.connected?
@channels.each do |channel|
- join channel
+ @irc.join channel
end
- end
- def connected?
- !(@socket.nil? || @socket.closed?)
- end
-
- def run
- connect unless connected?
-
- while str = @socket.gets.chomp
- log :in, str.inspect
-
- Thread.new do
- begin
- Timeout.timeout(30) do
- parse_line(str)
- end
- rescue => e
- log :error, "Error parsing line. (#{e})"
- log :indent, *e.backtrace
- end
- end
+ while str = @irc.gets
+ parse_in_new_thread(str)
end
- @socket.close
+ @irc.disconnect
log :info, 'Disconnected.'
end
- def out(str)
- return unless connected?
-
- log :out, str.inspect
- @socket.puts str
- end
-
def say(channel, message)
- out "PRIVMSG #{channel} :#{message}"
+ @irc.privmsg(channel, message)
end
def join(channel)
@channels << channel unless @channels.include?(channel)
- out "JOIN #{channel}"
+ @irc.join(channel) if @irc.connected?
end
def part(channel)
@channels.delete(channel)
- out "PART #{channel}"
+ @irc.part(channel)
end
def load_module(mod)
@@ -139,17 +109,31 @@ module Dinobot
private
+ def parse_in_new_thread(str)
+ Thread.new do
+ begin
+ Timeout.timeout(30) do
+ parse_line(str.chomp)
+ end
+ rescue => e
+ log :error, "Error parsing line. (#{e})"
+ log :indent, *e.backtrace
+ end
+ end
+ end
+
def parse_line(str)
- out str.sub('PING', 'PONG') if str =~ /^PING /
+ @irc.pong str.sub(/\APING /, 'PONG') if str =~ /\APING /
if str =~ /(\S+) PRIVMSG (\S+) :(.*)/
user, channel, message = str.scan(/(\S+) PRIVMSG (\S+) :(.*)/).first
return unless message.sub!(/^#{Regexp.escape(@trigger)}/, '')
- methods = exec_command(user, channel, message)
- ensure_valid_methods(methods)
- run_methods(methods)
+ if methods = exec_command(user, channel, message)
+ ensure_valid_methods(methods)
+ run_methods(methods)
+ end
end
end
diff --git a/irc.rb b/irc.rb
new file mode 100644
index 0000000..835694e
--- /dev/null
+++ b/irc.rb
@@ -0,0 +1,85 @@
+require 'socket'
+
+module Dinobot
+ class IRC
+ def initialize(server, port, nick, pass=nil)
+ @server = server
+ @port = port
+ @nick = nick
+ @pass = pass
+
+ @socket = nil
+ end
+
+ def connect
+ log :info, "Connecting to #{@server}:#{@port}."
+
+ @socket = TCPSocket.new(@server, @port)
+
+ puts "PASS #{@pass}" if @pass
+ puts "NICK #{@nick}"
+ puts "USER #{@nick} 0 * :#{@nick}"
+ end
+
+ def disconnect
+ @socket.close
+ end
+
+ def connected?
+ !(@socket.nil? || @socket.closed?)
+ end
+
+ def gets
+ str = @socket.gets
+
+ log :in, str.inspect
+
+ str
+ end
+
+ def puts(str)
+ log :out, str.inspect
+
+ @socket.puts str
+ end
+
+ def join(channel)
+ puts "JOIN #{channel}"
+ end
+
+ def part(channel)
+ puts "PART #{channel}"
+ end
+
+ def privmsg(channel, message)
+ puts "PRIVMSG #{channel} :#{message}"
+ end
+
+ def pong(message)
+ puts "PONG #{message}"
+ end
+
+ private
+
+ def log(type, *lines)
+ str = lines.join("\n")
+
+ case type
+ when :in
+ prefix = "\e[32m<<\e[0m "
+ when :out
+ prefix = "\e[36m>>\e[0m "
+ when :error
+ prefix = "\e[31m!!\e[0m "
+ when :info
+ prefix = "\e[33m==\e[0m "
+ when :indent
+ prefix = ' '
+ else
+ raise "unknown type specified -- #{type}"
+ end
+
+ Kernel.puts str.gsub(/^/, prefix)
+ end
+ end
+end