blob: fd6bf362d71d526fba5068a58303ba95e41d82a9 (
plain)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
|
;;;; A bot for playing rock paper scissors.
(ql:quickload :cl-ppcre)
(defpackage #:roshambot
(:use :cl)
(:import-from :granolin
:handle-event
:find-contact
:text-message-event
:send-text-message
:let-cond))
(in-package :roshambot)
;;; The logic of roshambot is something like:
;;; 1. A user indicates to the bot that they will to challenge another user to a
;;; game of roshambo "hey bot, roshambo with bob"
;;; 2. If bob is known to the bot then the bot will open a private with both the
;;; initiator, say alice, and with bob and present them with a chance to make a
;;; move or to cancel.
;;; 3. The bot then waits for both users to respond with a move or for either
;;; one of them to cancel.
;;; 4. The bot then reports the outcome of the match (winner bob, winner alice,
;;; or canceled by x) in the room in which the match was initiated.
(defstruct roshambo-match
room
challenger
challenger-state
challenged
challenged-state)
(defclass roshambot ()
((match-id
:accessor match-id
:initform 0)
(live-matches
:accessor live-matches
:initform nil)))
(defparameter +challenge-regex+
(ppcre:create-scanner "i challenge ([a-zA-Z0-9_.-]+) to roshambo"
:case-insensitive-mode t))
(defun you-wanna-piece-of-this!? (str)
"If the string communicates one user's intention to challenge another to
roshambo, returns the name of the user that has been challenged. Returns NIL otherwise."
(nth-value 1 (ppcre:scan-to-strings +challenge-regex+ str)))
(defmethod handle-event :after ((bot roshambot) (event text-message-event) &optional room-id)
(let ((text (msg-body event)))
(let-cond
(challenged (you-wanna-piece-of-this!? text)
(handle-new-challenge bot room-id (sender event) challenged)))))
(defun handle-new-challenge (bot room-id challenger challenged)
(let-cond
(direct-chat (find-contact bot challenged :like t :get-direct-room t)
)
(let-if (full-challenged (granolin::find-contact bot challenged :like t))
(make-new-challenge bot room-id challenger full-challenged)
(send-text-message client room-id
"Hey ~a, I don't know of anybody named ~a"
challenger challenged)))
|