html/notes.pl
1 # First, add $NOTE to your /format whois line so the output is shown, for example use
2 # '/format whois {nick $0} {nickhost $1@$2}%:{whois ircname $3}%:{whois note $NOTE}' which would produce
3 # Dec 12 21:24:18 -!- vague [~vague@c-e0ebe055.14-500-64736c10.cust.bredbandsbolaget.se]
4 # Dec 12 21:24:18 -!- ircname : vague
5 # Dec 12 21:24:18 -!- note : A nice guy but can be a PITA :)
6 # ...
7 #
8 # See /notes help for more help
9 #
10 # Prerequisites:
11 # irssi 0.8.13+
12 # DBM::Deep
13 # DBI
14
15 use Irssi;
16 use DBI;
17 use Data::Dumper;
18 use DBM::Deep;
19
20 use vars qw($VERSION %IRSSI);
21
22 my $VERSION = '0.31';
23 my %IRSSI = (
24 authors => 'vague',
25 contact => 'vague!#irssi\@freenode',
26 name => 'notes',
27 description => 'Keeps notes on users and displayes the note in /whois output if the host/nick matches',
28 license => 'GPL2',
29 );
30
31 my $notes;
32 my $note_expando = '';
33 my @chatnets;
34 push @chatnets, $_->{name} for(Irssi::chatnets());
35
36 my $DEBUG_ENABLED = 1;
37 sub DEBUG { $DEBUG_ENABLED }
38
39 sub init {
40 my $filename = Irssi::settings_get_str("notes_db") || Irssi::get_irssi_dir() . "/notes.db";
41 $notes = DBM::Deep->new( $filename );
42 }
43
44 sub _print {
45 my ($msg) = @_;
46 Irssi::active_win->print($msg, Irssi::MSGLEVEL_CLIENTCRAP);
47 }
48
49 sub _error {
50 my ($msg) = @_;
51 Irssi::active_win->print($msg, Irssi::MSGLEVEL_CLIENTCRAP);
52 }
53
54 sub _debug_print {
55 return unless DEBUG;
56 my ($msg) = @_;
57 Irssi::active_win->print($msg, Irssi::MSGLEVEL_CLIENTCRAP);
58 }
59
60 sub sig_whois {
61 my ($server, $data, undef, undef) = @_;
62 my ($me, $nick, $user, $host) = split(" ", $data);
63
64 if(exists $notes->{lc $server->{tag}}->{nick}->{lc $nick}) {
65 $note_expando = $notes->{lc $server->{tag}}->{nick}->{lc $nick};
66 }
67 else {
68 my $masks = $notes->{lc $server->{tag}}->{mask};
69 while(my ($mask, $value) = each %$masks) {
70 if($server->mask_match_address(lc $mask, '*', "$nick!$user\@$host")) {
71 $note_expando = $value;
72 return;
73 }
74 }
75 }
76 }
77
78 sub expando_note {
79 my ($tmp) = $note_expando;
80 $note_expando = '';
81 return $tmp;
82 }
83
84 sub cmd_notes_add {
85 my ($args, $server, $witem) = @_;
86 my $tmpargs = [ sort {$a =~ /^-/ <=> $b !~ /^-/} split / /, $args ];
87 my @options_list = Irssi::command_parse_options('notes add', join(' ', @$tmpargs));
88
89 if(!@options_list) {
90 _error "Could not parse arguments\n" . usage();
91 return;
92 }
93
94 my @minusargs = grep {/^-/} split / /, $args;
95 my @rest = grep {!/^-/} split / /, $args;
96 my ($network, $type, $pattern);
97
98 foreach(@minusargs) {
99 s/^-//;
100 if(/nick|mask/i) {
101 $type = $_;
102 $pattern = shift @rest;
103 }
104 else {
105 if(join(' ', @chatnets) =~ /$_/i) {
106 $network = $_;
107 }
108 }
109 }
110
111 if(not defined $network) {
112 $network = Irssi::active_server()->{tag};
113 }
114
115 unless ($type || $pattern) {
116 _error "Could not parse command\n" . usage();
117 return;
118 }
119
120 $notes->{lc $network}->{lc $type}->{lc $pattern} = join ' ', @rest;
121 _print "Added $pattern to $network";
122 }
123
124 sub cmd_notes_del {
125 my ($args, $server, $witem) = @_;
126 my $tmpargs = [ sort {$a =~ /^-/ <=> $b !~ /^-/} split / /, $args ];
127 my @options_list = Irssi::command_parse_options('notes del', join(' ', @$tmpargs));
128
129 if(!@options_list) {
130 _error "Could not parse arguments\n" . usage();
131 return;
132 }
133
134 my @minusargs = grep {/^-/} split / /, $args;
135 my @rest = grep {!/^-/} split / /, $args;
136 my ($network, $type, $pattern, $purge);
137
138 foreach(@minusargs) {
139 s/^-//;
140 if(/nick|mask/i) {
141 $type = $_;
142 $pattern = shift @rest;
143 }
144 elsif(/purge/) {
145 $purge = 1;
146 }
147 else {
148 if(join(' ', @chatnets) =~ /$_/i) {
149 $network = $_;
150 }
151 }
152 }
153
154 unless ($purge || $type || $pattern) {
155 _error "Could not parse command\n" . usage();
156 return;
157 }
158
159 if($purge) {
160 if(defined $network) {
161 delete $notes->{lc $network};
162 _print "Deleted all notes in $network";
163 }
164 else {
165 $notes->clear;
166 _print "Deleted all notes";
167 }
168 }
169 else {
170 if(not defined $network) {
171 $network = Irssi::active_server()->{tag};
172 }
173
174 if(exists $notes->{lc $network}->{lc $type}->{lc $pattern}) {
175 delete $notes->{lc $network}->{lc $type}->{lc $pattern};
176 _print "Deleted $pattern from $network";
177 }
178 else {
179 _error "\u$type '$pattern' on '$network' not found";
180 }
181 }
182 }
183
184 sub cmd_notes_list {
185 my ($args, $server, $witem) = @_;
186 my $tmpargs = [ sort {$a =~ /^-/ <=> $b !~ /^-/} split / /, $args ];
187 my @options_list = Irssi::command_parse_options('notes list', join(' ', @$tmpargs));
188
189 if(!@options_list) {
190 _error "Could not parse arguments\n" . usage();
191 return;
192 }
193
194 my @minusargs = grep {/^-/} split / /, $args;
195 my @rest = grep {!/^-/} split / /, $args;
196 my ($network, $type, $pattern, $all);
197
198 foreach(@minusargs) {
199 s/^-//;
200 if(/nick|mask/i) {
201 $type = $_;
202 $pattern = shift @rest;
203 }
204 elsif(/all/) {
205 $all = 1;
206 }
207 else {
208 if(join(' ', @chatnets) =~ /$_/i) {
209 $network = $_;
210 }
211 }
212 }
213
214 if(not defined $network) {
215 $network = Irssi::active_server()->{tag};
216 }
217
218 if($all) {
219 foreach my $tag (keys %$notes) {
220 Irssi::active_win()->{active}->print("--- Notes for $tag ---");
221 my $nicks = $notes->{$tag}->{nick};
222 while(my ($nick, $value1) = each %$nicks) {
223 Irssi::active_win()->{active}->print($nick . ": " . $value1);
224 }
225 my $masks = $notes->{$tag}->{mask};
226 while(my ($hostmask, $value2) = each %$masks) {
227 Irssi::active_win()->{active}->print($hostmask . ": " . $value2);
228 }
229 }
230 }
231 else {
232 if(defined $type && defined $pattern) {
233 Irssi::active_win()->{active}->print("--- Note on $network/$pattern ---");
234 Irssi::active_win()->{active}->print($notes->{lc $network}->{lc $type}->{lc $pattern});
235 }
236 else {
237 Irssi::active_win()->{active}->print("--- Notes for $network ---");
238 my $nicks = $notes->{lc $network}->{nick};
239 while(my ($nick, $value1) = each %$nicks) {
240 Irssi::active_win()->{active}->print($nick . ": " . $value1);
241 }
242 my $masks = $notes->{lc $network}->{mask};
243 while(my ($hostmask, $value2) = each %$masks) {
244 Irssi::active_win()->{active}->print($hostmask . ": " . $value2);
245 }
246 }
247 }
248 }
249
250 sub usage {
251 return "Usage: %_/notes%_ add [-tag] -nick|-mask pattern <notes>\n" .
252 " %_/notes%_ del [-tag] -purge|(-nick|-mask pattern)\n" .
253 " %_/notes%_ list [-tag] -all|(-nick|-mask pattern)";
254 }
255
256 Irssi::command_bind('notes' => sub {
257 my ( $data, $server, $item ) = @_;
258 $data =~ s/\s+$//g;
259 Irssi::command_runsub ('notes', $data, $server, $item ) ;
260 });
261
262 Irssi::command_bind('notes add', \&cmd_notes_add);
263 Irssi::command_bind('notes del', \&cmd_notes_del);
264 Irssi::command_bind('notes list', \&cmd_notes_list);
265 Irssi::command_bind('notes help', sub { Irssi::active_win()->print(usage()); });
266
267 Irssi::command_set_options('notes add', join(' ', @chatnets) . ' nick mask');
268 Irssi::command_set_options('notes del', join(' ', @chatnets) . ' purge nick mask');
269 Irssi::command_set_options('notes list', join(' ', @chatnets) . ' all nick mask');
270
271 Irssi::settings_add_str('Notes', 'notes_db', Irssi::get_irssi_dir() . "/notes.db");
272
273 Irssi::signal_add_first('event 311', \&sig_whois);
274 Irssi::expando_create('NOTE', \&expando_note,
275 {'event 311' => 'None' });
276
277 init();