blob: 6aa4b04333eb1b5467d2e503f84d959085c6d307 (
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
77
78
79
80
81
82
83
84
85
86
87
88
|
#lang racket/base
(require (for-syntax racket/base racket/list syntax/parse syntax/parse/lib/function-header)
irc/core irc/bot irc/users irc/storage racket/format racket/string racket/exn)
(provide define-command error-user)
(struct command-registration (signature help power action))
(define current-commands (make-parameter (make-hash)))
(define current-command-name (make-parameter #f))
(define (command-add signature action
#:help [help #f]
#:power [power 0]
#:min-interval [interv 0])
(hash-set! (current-commands)
(car signature) (command-registration signature help power action)))
(define (sufficient-power? nick wanted)
(or (= wanted 0)
(and (is-identified? nick)
(>= (user-power nick) wanted))))
(define (command-process)
(define s-exp (safe-read-string (string-join (cdr (params)))))
(when (pair? s-exp)
(parameterize ([current-command-name (car s-exp)])
(define command (hash-ref (current-commands) (current-command-name) #f))
(define required-power (command-registration-power command))
(when command
(if (sufficient-power? (source) required-power)
(begin
(log-irc-info "Executing ~a" (current-command-name))
(apply (command-registration-action command)
(cdr s-exp)))
(error-user "Insufficient power (~a required)" required-power))))))
(define (error-user . args)
(raise-user-error (current-command-name) (apply format args)))
(on (and (command-is 'PRIVMSG)
(not (source-is (current-nick)))
(not (ignored? (source))))
(with-handlers
([exn:fail:user? (λ (e) (privmsg (source) (exn->string e)))])
(command-process)))
(define-syntax (define-command stx)
(define-splicing-syntax-class single-keyword
(pattern (~seq kwname:keyword kwval:expr)))
(syntax-parse stx
[(_ fn:function-header
kw:single-keyword ...
action ...)
(with-syntax ([(kw ...)
(append* (map syntax->list (syntax->list #'(kw ...))))])
#'(command-add 'fn kw ... (lambda fn.args action ...)))]))
(define-command (list)
#:help "List all registered commands accessible to you"
(reply (~s
(for/list ([(k v) (current-commands)]
#:when (sufficient-power? (source) (command-registration-power v)))
(car (command-registration-signature v))))))
(define-command (help [command #f])
#:help "Display command argument names and description"
(if command
(let ([c (hash-ref (current-commands) command #f)])
(if c
(let* ([cr (command-registration-signature c)]
[help (command-registration-help c)])
(if help (reply (format "~s - ~a" cr help))
(reply (~s cr))))
(reply "There is no such command")))
(reply "You need to supply a command name, e.g. (help list)")))
(define-command (ignore-add nick)
#:power 2
(hash-set! (network-storage "ignore") nick #t)
(persist-network "ignore"))
(define-command (ignore-del nick)
#:power 2
(hash-remove! (network-storage "ignore") nick)
(persist-network "ignore"))
(define (ignored? nick)
(hash-has-key? (network-storage "ignore") nick))
|