raw
trilemabot-voicer       1 ;;;; trilemabot.lisp
trilemabot-voicer 2
trilemabot-voicer 3 (in-package #:trilemabot)
trilemabot-voicer 4
trilemabot-voicer 5 ;; These are used to check that we're joining #trilema; make sure that
trilemabot-voicer 6 ;; your bot is configured accordingly if you want to use
trilemabot-voicer 7 ;; #trilema-specific functionality.
trilemabot-voicer 8 (defparameter *trilema-server* ".freenode.net")
trilemabot-voicer 9 (defparameter *trilema-channel* "#trilema")
trilemabot-voicer 10 (defparameter *trilema-deedbot-nick* "deedbot")
trilemabot-voicer 11
trilemabot-voicer 12 (defclass trilemabot (ircbot)
trilemabot-voicer 13 ((in-chan :accessor trilemabot-in-chan :initform nil)
trilemabot-voicer 14 (voiced :accessor trilemabot-voiced :initform nil)
trilemabot-voicer 15 (voice-otp-stash :accessor trilemabot-voice-otp-stash
trilemabot-voicer 16 :initarg :voice-otp-stash
trilemabot-voicer 17 :initform nil)
trilemabot-voicer 18 (inbox :accessor trilemabot-inbox
trilemabot-voicer 19 :initform nil)))
trilemabot-voicer 20
trilemabot-voicer 21 (defmethod ircbot-connect :after ((bot trilemabot))
trilemabot-voicer 22 (with-slots (connection) bot
trilemabot-voicer 23 (add-hook connection 'irc-join-message
trilemabot-voicer 24 #'(lambda (message) (trilemabot-join-channel bot message)))
trilemabot-voicer 25 (add-hook connection 'irc-part-message
trilemabot-voicer 26 #'(lambda (message) (trilemabot-part-channel bot message)))
trilemabot-voicer 27 (add-hook connection 'irc-privmsg-message
trilemabot-voicer 28 #'(lambda (message) (trilemabot-handle-privmsg bot message)))
trilemabot-voicer 29 (add-hook connection 'irc-mode-message
trilemabot-voicer 30 #'(lambda (message) (trilemabot-check-mode bot message)))))
trilemabot-voicer 31
trilemabot-voicer 32 (defmethod ircbot-disconnect :after ((bot trilemabot) &optional (quit-msg ""))
trilemabot-voicer 33 (declare (ignore quit-msg))
trilemabot-voicer 34 (with-slots (in-chan voiced) bot
trilemabot-voicer 35 (setf in-chan nil
trilemabot-voicer 36 voiced nil)))
trilemabot-voicer 37
trilemabot-voicer 38 (defmethod trilemabot-join-channel ((bot trilemabot) message)
trilemabot-voicer 39 (destructuring-bind (channel) (arguments message)
trilemabot-voicer 40 (when (and (string= (source message) (ircbot-nick bot))
trilemabot-voicer 41 (string= channel *trilema-channel*)
trilemabot-voicer 42 (search *trilema-server* (ircbot-server bot)))
trilemabot-voicer 43 (setf (trilemabot-in-chan bot) t)
trilemabot-voicer 44 (trilemabot-voice bot))))
trilemabot-voicer 45
trilemabot-voicer 46 (defmethod trilemabot-part-channel ((bot trilemabot) message)
trilemabot-voicer 47 (let ((channel (car (arguments message))))
trilemabot-voicer 48 (when (and (string= (source message) (ircbot-nick bot))
trilemabot-voicer 49 (string= channel *trilema-channel*)
trilemabot-voicer 50 (search *trilema-server* (ircbot-server bot)))
trilemabot-voicer 51 (setf (trilemabot-in-chan bot) nil
trilemabot-voicer 52 (trilemabot-voiced bot) nil))))
trilemabot-voicer 53
trilemabot-voicer 54 (defmethod trilemabot-handle-privmsg ((bot trilemabot) message)
trilemabot-voicer 55 (destructuring-bind (target message-text) (arguments message)
trilemabot-voicer 56 (when (and (string= (source message) *trilema-deedbot-nick*)
trilemabot-voicer 57 (string= target (ircbot-nick bot)))
trilemabot-voicer 58 (format *standard-output* "<~a>: ~a~%"
trilemabot-voicer 59 (source message) message-text)
trilemabot-voicer 60 (push (list :from (source message)
trilemabot-voicer 61 :time (received-time message)
trilemabot-voicer 62 :message message-text)
trilemabot-voicer 63 (trilemabot-inbox bot)))))
trilemabot-voicer 64
trilemabot-voicer 65 (defmethod trilemabot-check-mode ((bot trilemabot) message)
trilemabot-voicer 66 (when (= 3 (length (arguments message))) ; mode change for user in chan
trilemabot-voicer 67 (destructuring-bind (channel mode nick) (arguments message)
trilemabot-voicer 68 (when (and (string= channel *trilema-channel*)
trilemabot-voicer 69 (string= nick (ircbot-nick bot)))
trilemabot-voicer 70 (cond
trilemabot-voicer 71 ((or (string= mode "+o")
trilemabot-voicer 72 (string= mode "+v")) (setf (trilemabot-voiced bot) t))
trilemabot-voicer 73 ((or (string= mode "-o")
trilemabot-voicer 74 (string= mode "-v")) (setf (trilemabot-voiced bot) nil)))))))
trilemabot-voicer 75
trilemabot-voicer 76 (defmethod trilemabot-add-voice-otps ((bot trilemabot) &rest otps)
trilemabot-voicer 77 (with-slots (voice-otp-stash) bot
trilemabot-voicer 78 (setf voice-otp-stash (nconc voice-otp-stash otps))))
trilemabot-voicer 79
trilemabot-voicer 80 (defmethod trilemabot-voice ((bot trilemabot))
trilemabot-voicer 81 (with-slots (voice-otp-stash) bot
trilemabot-voicer 82 (if voice-otp-stash
trilemabot-voicer 83 (trilemabot-send-otp bot (pop voice-otp-stash))
trilemabot-voicer 84 (format *standard-output* "[trilemabot ~a@~a] No OTPs available.~%"
trilemabot-voicer 85 (ircbot-nick bot) (ircbot-server bot)))))
trilemabot-voicer 86
trilemabot-voicer 87 (defmethod trilemabot-send-up ((bot trilemabot) &optional nick)
trilemabot-voicer 88 (ircbot-send-message bot *trilema-deedbot-nick*
trilemabot-voicer 89 (make-bot-command "!!up"
trilemabot-voicer 90 (or nick (ircbot-nick bot)))))
trilemabot-voicer 91
trilemabot-voicer 92 (defmethod trilemabot-send-otp ((bot trilemabot) otp)
trilemabot-voicer 93 (ircbot-send-message bot *trilema-deedbot-nick*
trilemabot-voicer 94 (make-bot-command "!!v" otp)))
trilemabot-voicer 95
trilemabot-voicer 96 (defun make-bot-command (command &rest arguments)
trilemabot-voicer 97 "Make raw bot command string consisting of `command' and
trilemabot-voicer 98 space-separated `arguments'."
trilemabot-voicer 99 (with-output-to-string (out)
trilemabot-voicer 100 (write-string command out)
trilemabot-voicer 101 (dolist (arg arguments)
trilemabot-voicer 102 (write-string " " out)
trilemabot-voicer 103 (write-string arg out))))
trilemabot-voicer 104
trilemabot-voicer 105 (defmethod trilemabot-save-voice-otp-stash ((bot trilemabot) filespec)
trilemabot-voicer 106 (with-open-file (out filespec
trilemabot-voicer 107 :direction :output
trilemabot-voicer 108 :if-exists :supersede
trilemabot-voicer 109 :if-does-not-exist :create)
trilemabot-voicer 110 (print (trlb:trilemabot-voice-otp-stash bot) out)
trilemabot-voicer 111 (finish-output out)))
trilemabot-voicer 112
trilemabot-voicer 113 (defun make-trilemabot (server port nick password channels &optional voice-otps)
trilemabot-voicer 114 (make-instance 'trilemabot
trilemabot-voicer 115 :server server
trilemabot-voicer 116 :port port
trilemabot-voicer 117 :nick nick
trilemabot-voicer 118 :password password
trilemabot-voicer 119 :channels channels
trilemabot-voicer 120 :voice-otp-stash voice-otps))