]>
gitweb.pimeys.fr Git - bots/hung.git/blob - hung.py
4 # Codé par 20-100 le 23/04/12
6 # Un bot IRC qui joue au pendu
11 import socket
, ssl
, json
17 from commands
import getstatusoutput
as ex
19 # Oui, j'ai recodé ma version d'irclib pour pouvoir rattrapper les SIGHUP
20 sys
. path
. insert ( 0 , "/home/vincent/scripts/python-myirclib" )
29 def get_config_logfile ( serveur
):
30 serveurs
={ "acoeur.crans.org" : "acoeur" , "irc.crans.org" : "crans" , "localhost" : "localhost" }
31 return config
. logfile_template
%( serveurs
[ serveur
])
33 def log ( serveur
, channel
, auteur
= None , message
= None ):
34 f
= open ( get_config_logfile ( serveur
), "a" )
35 if auteur
== message
== None :
36 # alors c'est que c'est pas un channel mais juste une ligne de log
37 chain
= " %s %s " %( time
. strftime ( " %F %T" ), channel
)
39 chain
= " %s [ %s : %s ] %s " %( time
. strftime ( " %F %T" ), channel
, auteur
, message
)
41 if config
. debug_stdout
:
45 def ignore_event ( serv
, ev
):
46 """Retourne ``True`` si il faut ignorer cet évènement."""
47 for ( blackmask
, exceptmask
) in config
. blacklisted_masks
:
48 usermask
= ev
. source ()
49 if exceptmask
is None :
52 exceptit
= bool ( irclib
. mask_matches ( usermask
, exceptmask
))
53 blackit
= bool ( irclib
. mask_matches ( usermask
, blackmask
))
54 return blackit
and not exceptit
56 class UnicodeBotError ( Exception ):
58 def bot_unicode ( chain
):
61 except UnicodeDecodeError as exc
:
64 def remplace_accents ( chaine
):
66 remplacements
= { u
"á" : u
"a" , u
"à" : u
"a" , u
"â" : u
"a" , u
"ä" : u
"a" , u
"é" : u
"e" , u
"è" : u
"e" , u
"ê" : u
"e" , u
"ë" : u
"e" , u
"í" : u
"i" , u
"ì" : u
"i" , u
"î" : u
"i" , u
"ï" : u
"i" , u
"ó" : u
"o" , u
"ò" : u
"o" , u
"ô" : u
"o" , u
"ö" : u
"o" , u
"ú" : u
"u" , u
"ù" : u
"u" , u
"û" : u
"u" , u
"ü" : u
"u" , u
"ý" : u
"y" , u
"ỳ" : u
"y" , u
"ŷ" : u
"y" , u
"ÿ" : u
"y" , u
"œ" : u
"oe" , u
"æ" : u
"ae" }
67 for avant
, apres
in remplacements
. items ():
68 chaine
= chaine
. replace ( avant
, apres
)
71 def is_something ( chain
, matches
, avant
= u
".*(?:^| )" , apres
= u
"(?:$|\.| |,|;).*" , case_sensitive
= False , debug
= False ):
73 chain
= unicode ( chain
, "utf8" )
75 chain
= unicode ( chain
, "utf8" ). lower ()
76 allmatches
= "(" + "|" . join ( matches
)+ ")"
77 reg
=( avant
+ allmatches
+ apres
). lower ()
82 return is_something ( chain
, config
. tag_triggers
)
84 def is_mot ( mot
, liste
):
85 real_word
= "" . join ([ lettre
[ 0 ] for lettre
in liste
])
86 real_word
= real_word
. decode ( "utf8" ). lower ()
87 mot
= remplace_accents ( mot
. decode ( "utf8" ))
88 return mot
. startswith ( real_word
)
90 class Hung ( ircbot
. SingleServerIRCBot
):
91 def __init__ ( self
, serveur
, debug
= False ):
92 temporary_pseudo
= config
. irc_pseudo
+ str ( random
. randrange ( 10000 , 100000 ))
93 ircbot
. SingleServerIRCBot
.__ init
__ ( self
, [( serveur
, 6667 )],
94 temporary_pseudo
, "Bot irc pour jouer au pendu" , 10 )
97 self
. overops
= config
. overops
98 self
. ops
= self
. overops
+ config
. ops
99 self
. report_bugs_to
= config
. report_bugs_to
100 self
. chanlist
= config
. chanlist
101 self
. stay_channels
= config
. stay_channels
102 self
. play_channels
= config
. play_channels
103 self
. play_status
={ i
:[ None , None , None ] for i
in self
. play_channels
}
105 self
. tried_letters
={}
106 self
. quiet_channels
= config
. quiet_channels
109 def give_me_my_pseudo ( self
, serv
):
110 serv
. privmsg ( "NickServ" , "RECOVER %s %s " %( config
. irc_pseudo
, config
. irc_password
))
111 serv
. privmsg ( "NickServ" , "RELEASE %s %s " %( config
. irc_pseudo
, config
. irc_password
))
113 serv
. nick ( config
. irc_pseudo
)
115 def on_welcome ( self
, serv
, ev
):
116 self
. serv
= serv
# ça serv ira :)
117 self
. give_me_my_pseudo ( serv
)
118 serv
. privmsg ( "NickServ" , "IDENTIFY %s " %( config
. irc_password
))
119 log ( self
. serveur
, "Connected" )
121 self
. chanlist
=[ "#bot" ]
122 self
. play_channels
=[ "#bot" ]
123 for c
in self
. chanlist
:
124 log ( self
. serveur
, "JOIN %s " %(c))
127 def pourmoi ( self
, serv
, message
):
128 """renvoie (False,lemessage) ou (True, le message amputé de "pseudo: ")"""
129 pseudo
= serv
. get_nickname ()
131 if message
[: size
]== pseudo
and len ( message
)> size
and message
[ size
]== ":" :
132 return ( True , message
[ size
+ 1 :]. lstrip ( " " ))
134 return ( False , message
)
136 def on_privmsg ( self
, serv
, ev
):
137 if ignore_event ( serv
, ev
):
139 message
= ev
. arguments ()[ 0 ]
140 auteur
= irclib
. nm_to_n ( ev
. source ())
142 test
= bot_unicode ( message
)
143 except UnicodeBotError
:
144 if config
. utf8_trigger
:
145 serv
. privmsg ( auteur
, random
. choice ( config
. utf8_fail_answers
). encode ( "utf8" ))
147 message
= message
. split ()
148 cmd
= message
[ 0 ]. lower ()
151 helpmsg_default
= """Liste des commandes :
152 HELP Affiche ce message d'aide
153 SCORE Affiche ton score
154 SCORES Affiche les scores"""
156 JOIN Faire rejoindre un channel (sans paramètres, donne la liste des chans actuels)
157 LEAVE Faire quitter un channel
158 PLAY Passe un channel en mode "jouer"
159 NOPLAY Passe un channel en mode "ne pas jouer"
160 QUIET Se taire sur un channel
161 NOQUIET Opposé de QUIET
162 RELOAD Recharge la config"""
164 SAY Fais envoyer un message sur un chan ou à une personne
165 DO Me fait faire une action sur un chan
166 STAY Ignorera les prochains LEAVE pour un chan
167 NOSTAY Opposé de STAY
168 STATUS Montre l'état courant
170 helpmsg
= helpmsg_default
171 if auteur
in self
. ops
:
173 if auteur
in self
. overops
:
174 helpmsg
+= helpmsg_overops
175 for ligne
in helpmsg
. split ( " \n " ):
176 serv
. privmsg ( auteur
, ligne
)
178 if auteur
in self
. ops
:
180 if message
[ 1 ] in self
. chanlist
:
181 serv
. privmsg ( auteur
, "Je suis déjà sur %s " %( message
[ 1 ]))
183 serv
. join ( message
[ 1 ])
184 self
. chanlist
. append ( message
[ 1 ])
185 serv
. privmsg ( auteur
, "Channels : " + " " . join ( self
. chanlist
))
186 log ( self
. serveur
, "priv" , auteur
, " " . join ( message
))
188 serv
. privmsg ( auteur
, "Channels : " + " " . join ( self
. chanlist
))
192 if auteur
in self
. ops
and len ( message
)> 1 :
193 if message
[ 1 ] in self
. chanlist
:
194 if not ( message
[ 1 ] in self
. stay_channels
) or auteur
in self
. overops
:
195 self
. quitter ( message
[ 1 ], " " . join ( message
[ 2 :]))
196 self
. chanlist
. remove ( message
[ 1 ])
197 log ( self
. serveur
, "priv" , auteur
, " " . join ( message
)+ "[successful]" )
199 serv
. privmsg ( auteur
, "Non, je reste !" )
200 log ( self
. serveur
, "priv" , auteur
, " " . join ( message
)+ "[failed]" )
202 serv
. privmsg ( auteur
, "Je ne suis pas sur %s " %( message
[ 1 ]))
206 if auteur
in self
. ops
:
208 if message
[ 1 ] in self
. play_channels
:
210 self
. start_partie ( serv
, message
[ 1 ], " " . join ( message
[ 2 :]))
212 serv
. privmsg ( auteur
, "Je play déjà sur %s ." %( message
[ 1 ]))
213 log ( self
. serveur
, "priv" , auteur
, " " . join ( message
)+ "[failed]" )
215 self
. play_channels
. append ( message
[ 1 ])
216 self
. play_status
[ message
[ 1 ]]=[ None , None , None ]
217 serv
. privmsg ( auteur
, "Play channels : " + " " . join ( self
. play_channels
))
218 log ( self
. serveur
, "priv" , auteur
, " " . join ( message
)+ "[successful]" )
220 serv
. privmsg ( auteur
, "Play channels : " + " " . join ( self
. play_channels
))
224 if auteur
in self
. ops
:
226 if message
[ 1 ] in self
. play_channels
:
227 self
. play_channels
. remove ( message
[ 1 ])
228 serv
. privmsg ( auteur
, "Play channels : " + " " . join ( self
. play_channels
))
229 log ( self
. serveur
, "priv" , auteur
, " " . join ( message
)+ "[successful]" )
231 serv
. privmsg ( auteur
, "Je ne play pas sur %s ." %( message
[ 1 ]))
232 log ( self
. serveur
, "priv" , auteur
, " " . join ( message
)+ "[failed]" )
236 if auteur
in self
. overops
:
238 if message
[ 1 ] in self
. stay_channels
:
239 log ( self
. serveur
, "priv" , auteur
, " " . join ( message
)+ "[failed]" )
240 serv
. privmsg ( auteur
, "Je stay déjà sur %s ." %( message
[ 1 ]))
242 log ( self
. serveur
, "priv" , auteur
, " " . join ( message
)+ "[successful]" )
243 self
. stay_channels
. append ( message
[ 1 ])
244 serv
. privmsg ( auteur
, "Stay channels : " + " " . join ( self
. stay_channels
))
246 serv
. privmsg ( auteur
, "Stay channels : " + " " . join ( self
. stay_channels
))
250 if auteur
in self
. overops
:
252 if message
[ 1 ] in self
. stay_channels
:
253 log ( self
. serveur
, "priv" , auteur
, " " . join ( message
)+ "[successful]" )
254 self
. stay_channels
. remove ( message
[ 1 ])
255 serv
. privmsg ( auteur
, "Stay channels : " + " " . join ( self
. stay_channels
))
257 log ( self
. serveur
, "priv" , auteur
, " " . join ( message
)+ "[failed]" )
258 serv
. privmsg ( auteur
, "Je ne stay pas sur %s ." %( message
[ 1 ]))
262 elif cmd
in [ "states" , "status" ]:
263 if auteur
in self
. overops
:
264 for k
in self
. play_status
. keys ():
265 if self
. play_status
[ k
]==[ None , None , None ]:
266 serv
. privmsg ( auteur
, "None" )
268 serv
. privmsg ( auteur
, " %s : %s ( %s ) [ %s ]" %( k
, "" . join ([ str ( i
[ 0 ]) for i
in self
. play_status
[ k
][ 0 ]])
269 , self
. play_status
[ k
][ 1 ], self
. play_status
[ k
][ 2 ]))
271 if auteur
in self
. overops
:
272 log ( self
. serveur
, "priv" , auteur
, " " . join ( message
)+ "[successful]" )
277 if auteur
in self
. ops
:
279 if message
[ 1 ] in self
. quiet_channels
:
280 serv
. privmsg ( auteur
, "Je me la ferme déjà sur %s " %( message
[ 1 ]))
281 log ( self
. serveur
, "priv" , auteur
, " " . join ( message
)+ "[failed]" )
283 self
. quiet_channels
. append ( message
[ 1 ])
284 serv
. privmsg ( auteur
, "Quiet channels : " + " " . join ( self
. quiet_channels
))
285 log ( self
. serveur
, "priv" , auteur
, " " . join ( message
)+ "[successful]" )
287 serv
. privmsg ( auteur
, "Quiet channels : " + " " . join ( self
. quiet_channels
))
291 if auteur
in self
. ops
:
293 if message
[ 1 ] in self
. quiet_channels
:
294 self
. quiet_channels
. remove ( message
[ 1 ])
295 serv
. privmsg ( auteur
, "Quiet channels : " + " " . join ( self
. quiet_channels
))
296 log ( self
. serveur
, "priv" , auteur
, " " . join ( message
)+ "[successful]" )
298 serv
. privmsg ( auteur
, "Je ne me la ferme pas sur %s ." %( message
[ 1 ]))
299 log ( self
. serveur
, "priv" , auteur
, " " . join ( message
)+ "[failed]" )
303 if auteur
in self
. ops
:
305 log ( self
. serveur
, "priv" , auteur
, " " . join ( message
)+ "[successful]" )
309 if auteur
in self
. overops
and len ( message
)> 2 :
310 serv
. privmsg ( message
[ 1 ], " " . join ( message
[ 2 :]))
311 log ( self
. serveur
, "priv" , auteur
, " " . join ( message
))
312 elif len ( message
)<= 2 :
313 serv
. privmsg ( auteur
, "Syntaxe : SAY <channel> <message>" )
317 if auteur
in self
. overops
and len ( message
)> 2 :
318 serv
. action ( message
[ 1 ], " " . join ( message
[ 2 :]))
319 log ( self
. serveur
, "priv" , auteur
, " " . join ( message
))
320 elif len ( message
)<= 2 :
321 serv
. privmsg ( auteur
, "Syntaxe : DO <channel> <action>" )
324 elif cmd
in [ "score" , "scores" ]:
325 self
. send_scores ( serv
, auteur
)
329 serv
. privmsg ( auteur
, "Je n'ai pas compris. Essaye HELP…" )
331 def affiche_mot ( self
, serv
, canal
, begin
= "Mot courant" ):
332 if self
. play_status
. has_key ( canal
):
333 mot
= self
. play_status
[ canal
][ 0 ]
334 obfuskated
= " " . join ([ lettre
[ 0 ] if lettre
[ 1 ] else "_" for lettre
in mot
])
335 serv
. privmsg ( canal
, " %s : %s " %( begin
, obfuskated
))
337 def start_partie ( self
, serv
, canal
, mot
= None ):
339 mots
=[ mot
. strip () for mot
in open ( config
. dico_mots
). readlines ()]
340 defs
=[ defi
. strip () for defi
in open ( config
. dico_defs
). readlines ()]
341 indice
= random
. randrange ( 0 , len ( mots
))
342 mot
, definition
= mots
[ indice
], defs
[ indice
]
344 definition
= "(custom word)"
345 # ' et - sont considérés comme déjà devinés
347 mot
= [( lettre
, lettre
in config
. non_guess_chars
) for lettre
in list ( mot
)]
348 self
. play_status
[ canal
]=[ mot
, definition
,{}]
349 self
. tried_letters
[ canal
] = set ()
350 self
. lives
[ canal
] = config
. lives
351 self
. affiche_mot ( serv
, canal
, begin
= "Devinez" )
353 def on_pubmsg ( self
, serv
, ev
):
354 if ignore_event ( serv
, ev
):
356 auteur
= irclib
. nm_to_n ( ev
. source ())
358 message
= ev
. arguments ()[ 0 ]
360 test
= bot_unicode ( message
)
361 except UnicodeBotError
:
362 if config
. utf8_trigger
and not canal
in self
. quiet_channels
:
363 serv
. privmsg ( canal
, ( u
" %s : %s " %( auteur
, random
. choice ( config
. utf8_fail_answers
))). encode ( "utf8" ))
365 pour_moi
, message
= self
. pourmoi ( serv
, message
)
366 if pour_moi
and message
. split ()!=[]:
367 cmd
= message
. split ()[ 0 ]. lower ()
369 args
= " " . join ( message
. split ()[ 1 :])
372 if cmd
in [ "meurs" , "die" , "crève" ]:
373 if auteur
in self
. overops
:
374 log ( self
. serveur
, canal
, auteur
, message
+ "[successful]" )
377 serv
. privmsg ( canal
, " %s : crève !" %(auteur))
378 log ( self
. serveur
, canal
, auteur
, message
+ "[failed]" )
379 elif cmd
== "reload" :
380 if auteur
in self
. ops
:
381 log ( self
. serveur
, canal
, auteur
, message
+ "[successful]" )
383 elif cmd
in [ "part" , "leave" , "dégage" ]:
384 if auteur
in self
. ops
and ( not ( canal
in self
. stay_channels
)
385 or auteur
in self
. overops
):
387 log ( self
. serveur
, canal
, auteur
, message
+ "[successful]" )
388 if canal
in self
. chanlist
:
389 self
. chanlist
. remove ( canal
)
391 serv
. privmsg ( canal
, " %s : Non, je reste !" %(auteur))
392 log ( self
. serveur
, canal
, auteur
, message
+ "[failed]" )
393 elif cmd
in [ "play" , "jeu" , "encore" , "again" , "partie" , "pendu" , "game" , "mot" , "go" , "allez" ]:
394 if not canal
in self
. quiet_channels
and canal
in self
. play_channels
:
395 if self
. play_status
. has_key ( canal
):
396 if self
. play_status
[ canal
]==[ None , None , None ]:
397 self
. start_partie ( serv
, canal
)
399 self
. affiche_mot ( serv
, canal
, begin
= " %s : Rappel" %(auteur))
401 self
. play_status
[ canal
]=[ None , None , None ]
402 self
. start_partie ( serv
, canal
)
403 elif not canal
in self
. play_channels
:
404 serv
. privmsg ( canal
, " %s : pas ici…" %(auteur))
405 elif cmd
in [ "score" , "scores" , "!score" , "!scores" ]:
406 self
. send_scores ( serv
, auteur
)
407 if cmd
in [ "meur" , "meurt" , "meurre" , "meurres" ] and not canal
in self
. quiet_channels
:
408 serv
. privmsg ( canal
, ' %s : Mourir, impératif, 2ème personne du singulier : "meurs" (de rien)' %(auteur))
409 if is_tag ( message
) and not canal
in self
. quiet_channels
:
410 if auteur
in self
. ops
:
411 action
= random
. choice ( config
. tag_actions
)
412 serv
. action ( canal
, action
. encode ( "utf8" ))
413 self
. quiet_channels
. append ( canal
)
415 answer
= random
. choice ( config
. tag_answers
)
416 for ligne
in answer
. split ( " \n " ):
417 serv
. privmsg ( canal
, " %s : %s " %( auteur
, ligne
. encode ( "utf8" )))
418 # on essaye de voir si le mot fourni matche la partie en cours
420 if canal
in self
. play_channels
and self
. play_status
[ canal
][ 0 ]!= None and is_mot ( mot
, self
. play_status
[ canal
][ 0 ]):
422 # on regarde combien de lettre il manquait
423 manquait
= sum ([ not lettre
[ 1 ] for lettre
in self
. play_status
[ canal
][ 0 ]])
424 self
. add_score ({ auteur
: manquait
})
425 if self
. play_status
[ canal
][ 2 ]. has_key ( auteur
):
426 self
. play_status
[ canal
][ 2 ][ auteur
]+= manquait
428 self
. play_status
[ canal
][ 2 ][ auteur
]= manquait
429 self
. gagne ( serv
, canal
, bonus
= auteur
, bonusvalue
= manquait
)
431 elif ( cmd
in list ( "azertyuiopqsdfghjklmwxcvbn" ) and canal
in self
. play_channels
432 and self
. play_status
. has_key ( canal
) and self
. play_status
[ canal
]!=[ None , None , None ]):
434 liste
= self
. play_status
[ canal
][ 0 ]
435 listeapres
=[( lettre
[ 0 ], lettre
[ 1 ] or lettre
[ 0 ]== giv_let
) for lettre
in liste
]
436 if liste
!= listeapres
:
437 nbtrouvees
=( sum ([ lettre
[ 1 ] for lettre
in listeapres
if not lettre
[ 0 ] in "'-()" ])
438 - sum ([ lettre
[ 1 ] for lettre
in liste
if not lettre
[ 0 ] in "'-()" ]))
439 if self
. play_status
[ canal
][ 2 ]. has_key ( auteur
):
440 self
. play_status
[ canal
][ 2 ][ auteur
]+= nbtrouvees
442 self
. play_status
[ canal
][ 2 ][ auteur
] = nbtrouvees
443 self
. play_status
[ canal
][ 0 ]= listeapres
444 self
. affiche_mot ( serv
, canal
, begin
= " %s placé" %(giv_let))
446 if not giv_let
in self
. tried_letters
[ canal
]:
448 self
. lives
[ canal
] -= 1
449 if self
. lives
[ canal
] > 0 :
450 serv
. privmsg ( canal
, "Pas de %s . Plus que %s chance %s …" % ( giv_let
, self
. lives
[ canal
], "s" * ( self
. lives
[ canal
] > 1 )))
451 if self
. lives
[ canal
] == 0 :
452 serv
. privmsg ( canal
, "Pas de %s ." % ( giv_let
))
453 self
. perd ( serv
, canal
)
455 self
. tried_letters
[ canal
]. add ( giv_let
)
456 if all ([ lettre
[ 1 ] for lettre
in listeapres
]):
457 self
. gagne ( serv
, canal
)
463 def on_action ( self
, serv
, ev
):
464 if ignore_event ( serv
, ev
):
466 action
= ev
. arguments ()[ 0 ]
467 auteur
= irclib
. nm_to_n ( ev
. source ())
468 channel
= ev
. target ()
471 def on_kick ( self
, serv
, ev
):
472 auteur
= irclib
. nm_to_n ( ev
. source ())
473 channel
= ev
. target ()
474 victime
= ev
. arguments ()[ 0 ]
475 raison
= ev
. arguments ()[ 1 ]
476 if victime
== self
. nick
:
477 log ( self
. serveur
, " %s kické de %s par %s (raison : %s )" %( victime
, channel
, auteur
, raison
))
480 # on ne dit rien au rejoin
481 #l1,l2=config.kick_answers,config.kick_actions
482 #n1,n2=len(l1),len(l2)
483 #i=random.randrange(n1+n2)
485 # serv.action(channel,l2[i-n1].format(auteur).encode("utf8"))
487 # serv.privmsg(channel,l1[i].format(auteur).encode("utf8"))
490 return self
. serv
. get_nickname ()
491 nick
= property ( _getnick
)
493 def quitter ( self
, chan
, leave_message
= None ):
494 if leave_message
== None :
495 leave_message
= random
. choice ( config
. leave_messages
)
496 self
. serv
. part ( chan
, message
= leave_message
. encode ( "utf8" ))
499 quit_message
= random
. choice ( config
. quit_messages
)
500 self
. die ( msg
= quit_message
. encode ( "utf8" ))
502 def get_scores ( self
):
503 f
= open ( config
. scores_file
)
504 scores
= pickle
. load ( f
)
507 def save_scores ( self
, scores
):
508 f
= open ( config
. scores_file
, 'w' )
509 pickle
. dump ( scores
, f
)
511 def add_score ( self
, dico
):
512 scores
= self
. get_scores ()
513 for k
, v
in dico
. items ():
514 if scores
. has_key ( k
):
518 self
. save_scores ( scores
)
519 def send_scores ( self
, serv
, destinataire
):
520 scores
= self
. get_scores ()
521 scores
= scores
. items ()
522 scores
. sort ( lambda x
, y
: cmp ( x
[ 1 ], y
[ 1 ]))
524 serv
. privmsg ( destinataire
, "Scores by score : " + " ; " . join ([ " %s %s " %( k
, v
) for ( k
, v
) in scores
]) )
525 scores
. sort ( lambda x
, y
: cmp ( x
[ 0 ]. lower (), y
[ 0 ]. lower ()))
526 serv
. privmsg ( destinataire
, "Scores by pseudo : " + " ; " . join ([ " %s %s " %( k
, v
) for ( k
, v
) in scores
]) )
528 def gagne ( self
, serv
, canal
, bonus
= None , bonusvalue
= 2 ):
529 serv
. privmsg ( canal
, "Bravo !" )
530 realword
= self
. reveal_word ( serv
, canal
)
531 nlettre
= float ( len ([ l
for l
in realword
if not l
in config
. non_guess_chars
]))
532 contribs
=[ " %s : %s%%%s " %( pseudo
, str ( int ( 100 * contrib
/ nlettre
)),( "+bonus( %s )" %(bonusvalue))*( bonus
== pseudo
)) for pseudo
, contrib
in self
. play_status
[ canal
][ 2 ]. items ()]
533 contribs_score
={ pseudo
: int ( 10 * contrib
/ nlettre
) for pseudo
, contrib
in self
. play_status
[ canal
][ 2 ]. items ()}
534 self
. add_score ( contribs_score
)
535 serv
. privmsg ( canal
, "Contributions : %s " %( " " . join ( contribs
)) )
536 self
. play_status
[ canal
]=[ None , None , None ]
538 def reveal_word ( self
, serv
, canal
):
539 realword
= "" . join ([ lettre
[ 0 ] for lettre
in self
. play_status
[ canal
][ 0 ]])
540 serv
. privmsg ( canal
, "C'était %s ." % ( realword
))
541 definition
= self
. play_status
[ canal
][ 1 ]
542 serv
. privmsg ( canal
, definition
)
545 def perd ( self
, serv
, canal
):
546 serv
. privmsg ( canal
, "Pendu !" )
547 self
. reveal_word ( serv
, canal
)
548 self
. play_status
[ canal
]=[ None , None , None ]
550 def reload ( self
, auteur
= None ):
552 if auteur
in [ None , "SIGHUP" ]:
553 towrite
= "Config reloaded" + " (SIGHUP received)" *( auteur
== "SIGHUP" )
554 for to
in config
. report_bugs_to
:
555 self
. serv
. privmsg ( to
, towrite
)
556 log ( self
. serveur
, towrite
)
558 self
. serv
. privmsg ( auteur
, "Config reloaded" )
560 def start_as_daemon ( self
, outfile
):
561 sys
. stderr
= Logger ( outfile
)
565 class Logger ( object ):
566 """Pour écrire ailleurs que sur stdout"""
567 def __init__ ( self
, filename
= "hung.full.log" ):
568 self
. filename
= filename
570 def write ( self
, message
):
571 f
= open ( self
. filename
, "a" )
576 if __name__
== "__main__" :
579 print "Usage : hung.py <serveur> [--debug] [--no-output] [--daemon [--pidfile]] [--outfile]"
580 print " --outfile sans --no-output ni --daemon n'a aucun effet"
583 if "--daemon" in sys
. argv
:
584 thisfile
= os
. path
. realpath ( __file__
)
585 thisdirectory
= thisfile
. rsplit ( "/" , 1 )[ 0 ]
586 os
. chdir ( thisdirectory
)
590 if "debug" in sys
. argv
or "--debug" in sys
. argv
:
594 if "--no-output" in sys
. argv
or "--daemon" in sys
. argv
:
595 outfile
= "/var/log/bots/hung.full.log"
598 if arg
[ 0 ]. strip ( '-' ) in [ "out" , "outfile" , "logfile" ]:
600 sys
. stdout
= Logger ( outfile
)
601 serveurs
={ "a♡" : "acoeur.crans.org" , "acoeur" : "acoeur.crans.org" , "acoeur.crans.org" : "acoeur.crans.org" ,
602 "irc" : "irc.crans.org" , "crans" : "irc.crans.org" , "irc.crans.org" : "irc.crans.org" ,
603 "localhost" : "localhost" }
605 serveur
= serveurs
[ serveur
]
607 print "Server Unknown : %s " %(serveur)
609 hung
= Hung ( serveur
, debug
)
610 # Si on reçoit un SIGHUP, on reload la config
611 def sighup_handler ( signum
, frame
):
612 hung
. reload ( "SIGHUP" )
613 signal
. signal ( signal
. SIGHUP
, sighup_handler
)
615 child_pid
= os
. fork ()
618 hung
. start_as_daemon ( outfile
)
620 # on enregistre le pid de hung
621 pidfile
= "/var/run/bots/hung.pid"
624 if arg
[ 0 ]. strip ( '-' ) in [ "pidfile" ]:
626 f
= open ( pidfile
, "w" )
627 f
. write ( " %s \n " % child_pid
)