;;; erc-bans.el --- Erc ban bits ;; Copyright (C) 2004 Free Software Foundation, Inc. ;; Author: Mark Triggs ;; This file is free software; you can redistribute it and/or modify ;; it under the terms of the GNU General Public License as published by ;; the Free Software Foundation; either version 2, or (at your option) ;; any later version. ;; This file is distributed in the hope that it will be useful, ;; but WITHOUT ANY WARRANTY; without even the implied warranty of ;; MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the ;; GNU General Public License for more details. ;; You should have received a copy of the GNU General Public License ;; along with GNU Emacs; see the file COPYING. If not, write to ;; the Free Software Foundation, Inc., 59 Temple Place - Suite 330, ;; Boston, MA 02111-1307, USA. ;;; Commentary: ;; ;;; Code: (defvar erc-got-banlist-hook '()) (make-local-variable 'erc-got-banlist-hook) ;;;;;;;;;;;;; ;; Commands (defun erc-cmd-BANLIST () "List the current channel's banlist" (do-once 'erc-got-banlist-hook `(lambda () (cond (erc-channel-banlist (let ((header (format "%-30s %s" "Banned" "By"))) (erc-display-line (erc-propertize header 'face 'erc-notice-face) 'active)) (dolist (ban erc-channel-banlist) (erc-display-line (format "%-30s %s" (car ban) (cadr ban)) 'active))) (t (erc-display-line (erc-make-notice (format "No bans for %s\n" ,(erc-default-target))) 'active) )))) (erc-fetch-banlist)) (defun erc-cmd-BAN (nick) "Ban a user" (let* ((tgt (erc-default-target)) (banhost (erc-mst-get-host nick))) (when (and banhost tgt) (erc-send-command (format "MODE %s +b *!*@%s" tgt banhost))) t)) (defun erc-cmd-KB (nick &rest reason) "Kick and ban someone" (erc-cmd-BAN nick) (apply 'erc-cmd-KICK nick nil reason) t) (setq erc-nick-popup-alist (cons '("Kick+Ban" erc-cmd-KB (concat nick " " (read-string (concat "Kick+Ban " nick ", reason: ")))) erc-nick-popup-alist)) (defun erc-cmd-MUB () "Unban everyone on the current channel." (do-once 'erc-got-banlist-hook `(lambda () (dolist (ban erc-channel-banlist) (erc-send-command (format "MODE %s -b %s" ,(erc-default-target) (car ban)))))) (erc-fetch-banlist)) ;;;;;;;;;;; ;;; Utils (defun erc-fetch-banlist () (setq erc-channel-banlist '()) (erc-send-command (format "MODE %s b" (erc-default-target)))) (defun erc-mst-get-host (nick) "Get the host of some nickname (blocks)" (flet ((user-host (nick) (erc-server-user-host (car (gethash nick erc-channel-users))))) (or (ignore-errors (user-host nick)) (let (host) (with-current-buffer (erc-server-buffer) (erc-once-with-server-event 352 '(progn (setq host (nth 3 (erc-response.command-args parsed))) t))) (erc-send-command (format "WHO %s" nick) nil) (do ((i 0 (1+ i))) ((or host (> i 30))) (accept-process-output) (sleep-for 0.1)) host)))) ;;;;;;;;;;;;;;;;;;; ;;; Backend stuff ;; Blank the banlist on join (add-hook 'erc-join-hook (lambda () (set (make-local-variable 'erc-channel-banlist) '()))) ;; Ban gathering (add-hook 'erc-server-367-functions (lambda (proc parsed) (let ((channel (nth 1 (erc-response.command-args parsed))) (banmask (nth 2 (erc-response.command-args parsed))) (banned-by (nth 3 (erc-response.command-args parsed)))) (erc-with-buffer (channel proc) (pushnew (list banmask banned-by) erc-channel-banlist :test 'equal))) t)) ;; End of ban list (add-hook 'erc-server-368-functions (lambda (proc parsed) (let ((channel (nth 1 (erc-response.command-args parsed)))) (erc-with-buffer (channel proc) (run-hooks 'erc-got-banlist-hook))) t)) (provide 'erc-bans) ;;; erc-bans.el ends here