Пример #1
0
 def main(self, args, env = {}):
   if not len(args): return ''
   link = self.google.search(args + ['site:animenewsnetwork.com'])
   if len(link):
     if len(link[1]): return gib.ircstr("{0} - ´B{1}´N").format(link[0], link[1])
     else: return str(link[0])
   else: return gib.ircstr("'´I{0}´N' did not return anything.").format(' '.join(args))
Пример #2
0
  def main(self, args, env = {}):
    user = ''
    if len(args) and args[0] and self.userre.match(args[0]): user = args[0]
    if not user and 'nick' in env:
      nick = env['nick'].GetNick()
      if len(args) == 2 and args[0] == '.set':
        if self.userre.match(args[1]): return self.set_nick(nick, args[1])
        else: return gib.ircstr('´I{0}´N is not a valid last.fm username.').format(args[1])
      if len(args) == 1 and args[0] == '.unset': return self.unset_nick(nick)
      user = self.get_nick(nick)
      if not user and self.userre.match(nick): user = nick
    if not user: return gib.ircstr("Invalid user ´I{0}´N").format(args[0] if len(args[0]) else env['nick'].GetNick())
    last_track = self.get_last_track(user)
    if 'error' in last_track:
      if last_track['error'] == 'not found': return gib.ircstr("´I{0}´N not found").format(user)
      elif last_track['error'] == 'no records': return gib.ircstr("´I{0}´N never played anything").format(user)
      else: return
    time = last_track['time']
    time = (self.pretty_date(time) + ' ') if time != 0 else ''
    tags = last_track['tags'][:3]
    tags = (gib.ircstr('´C7´B´B') + gib.ircstr('´N, ´C7´B´B').join(tags) + gib.N) if len(tags) else 'no tags'
    loved = gib.ircstr('´C4♥´N ') if last_track['loved'] else ''
    play = self.ordn(last_track['userplaycount'])
    album = (gib.ircstr('[´C13´B´B') + last_track['album'].title + gib.ircstr('´N] ')) if last_track['album'] else ''

    resp = gib.ircstr('´C11{0}´N {1} listening to "´C10´B{2}´N" {3}by ´C12´B{4}´N {5}{6}for the {7} time, {8} plays by {9} listeners. ({10})')
    resp = resp.format(user, 'was' if time != '' else 'is', last_track['track'], loved, last_track['artist'], album, time, play, last_track['globalplaycount'], last_track['listeners'], tags)
#    if type(time) == int and time == 0:
#      resp = gib.ircstr('´C11´I{0}´N is currently listening to "´C10´B{1}´N" by ´C12´I{2}´N{3} {4}for the {5} time, {6} global plays by {7} listeners. ({8})')
#      resp = resp.format(user, last_track['track'], last_track['artist'], album, loved, play, last_track['globalplaycount'], last_track['listeners'], tags)
#    else:
#      resp = gib.ircstr('´C11´I{0}´N was listening to "´C10´B{1}´N" by ´C12´I{2}´N{3} {4}about {5} for the {6} time, {7} global plays by {8} listeners. ({9})')
#      resp = resp.format(user, last_track['track'], last_track['artist'], album, loved, time, play, last_track['globalplaycount'], last_track['listeners'], tags)
    return resp
Пример #3
0
 def main(self, args, env = {}):
   if not len(args): return ''
   link = self.search(args)
   if len(link):
     if len(link[1]): return gib.ircstr("{0} - ´B{1}´N").format(link[0], link[1])
     else: return str(link[0])
   else: return gib.ircstr("'´I{0}´N' did not match any documents.").format(' '.join(args))
Пример #4
0
 def main(self, args, env = {}):
   if not len(args): return ''
   link = self.google.search(args + ['site:anidb.net'])
   if len(link):
     if len(link[1]): return gib.ircstr("{0} - ´B{1}´N").format(link[0], link[1].replace(' - AniDB', ''))
     else: return str(link[0])
   else: return gib.ircstr("'´I{0}´N' did not return anything.").format(' '.join(args))
Пример #5
0
 def main(self, args, env={}):
     if not len(args): return ''
     link = self.google.search(args + ['site:mangaupdates.com/series.html'])
     if len(link):
         page = self.google.open_page(link[0])
         page = b''.join(page.readlines()).decode('utf-8', 'ignore')
         html = lxml.html.document_fromstring(page)
         rating = self.get_rating(html)
         volumes = self.get_volumes(html)
         description = self.get_description(html)
         name = [str(link[0])]
         if not volumes in (None, ""):
             name.append(gib.ircstr('´C6´B´B' + volumes + '´N'))
         if not rating in (None, ""):
             name.append(gib.ircstr('´C7´B´B' + rating + '´N'))
         if not link[1] in (None, ""):
             name.append(
                 gib.ircstr('´B' +
                            link[1].replace('Baka-Updates Manga - ', '') +
                            '´N'))
         name = ' :: '.join(name)
         if not description in (None, ""): name = [name, description]
         return name
     else:
         return gib.ircstr("'´I{0}´N' did not return anything.").format(
             ' '.join(args))
Пример #6
0
class RDNS:
    command = ".rdns"
    help = gib.ircstr(
        "´Iipaddress´N | Returns the reverse DNS entry for the IP.")
    shelp = gib.ircstr("´Iip´N")

    google = None

    def __init__(self):
        self.google = google.Google()

    def main(self, args, env={}):
        if not len(args): return ''
        host = socket.gethostbyaddr(args[0])[0]
        if host.find('://') == -1: host = "http://{0}/".format(host)
        page = urlopen(
            Request(
                host, None, {
                    'User-Agent':
                    "Mozilla/5.0 (Windows NT 6.2; WOW64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/29.0.1547.2 Safari/537.36"
                }))
        try:
            title = self.google.get_title(page)
        except:
            title = gib.ircstr("´ITimeout´N")
        return gib.ircstr("{0} | ´B{1}´N{2}").format(
            args[0], host, (" - " + title) if len(title) else '')
Пример #7
0
 def main(self, args, env = {}):
   if not len(args): return ''
   host = socket.gethostbyaddr(args[0])[0]
   if host.find('://') == -1: host = "http://{0}/".format(host)
   page = urlopen(Request(host, None, {'User-Agent':"Mozilla/5.0 (Windows NT 6.2; WOW64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/29.0.1547.2 Safari/537.36"}))
   try: title = self.google.get_title(page)
   except: title = gib.ircstr("´ITimeout´N")
   return gib.ircstr("{0} | ´B{1}´N{2}").format(args[0], host, (" - " + title) if len(title) else '')
Пример #8
0
 def main(self, args, env={}):
     if not len(args): return ''
     link = self.google.search(args + ['site:animenewsnetwork.com'])
     if len(link):
         if len(link[1]):
             return gib.ircstr("{0} - ´B{1}´N").format(link[0], link[1])
         else:
             return str(link[0])
     else:
         return gib.ircstr("'´I{0}´N' did not return anything.").format(
             ' '.join(args))
Пример #9
0
 def main(self, args, env = {}):
   if not len(args): return ''
   link = self.google.search(args + ['site:bato.to'])
   if len(link):
     rating = self.get_rating(link[0])
     name = [str(link[0])]
     if len(rating): name.append(gib.ircstr('´C7´B´B' + rating + '´N'))
     if len(link[1]): name.append(gib.ircstr('´B' + link[1].split('- Scanlations ')[0].split(' - Comic ')[0] + '´N'))
     name = ' :: '.join(name)
     return name
   else: return gib.ircstr("'´I{0}´N' did not return anything.").format(' '.join(args))
Пример #10
0
 def main(self, args, env={}):
     if not len(args): return ''
     link = self.search(args)
     if len(link):
         if len(link[1]):
             return gib.ircstr("{0} - ´B{1}´N").format(link[0], link[1])
         else:
             return str(link[0])
     else:
         return gib.ircstr("'´I{0}´N' did not match any documents.").format(
             ' '.join(args))
Пример #11
0
 def unset_nick(self, ircnick):
   if self.sqlc:
     irc = self.sqlc.execute('SELECT * FROM nicks WHERE irc = ?', (ircnick,)).fetchall()
     if len(irc):
       self.sqlc.execute('DELETE FROM nicks WHERE irc = ?', (ircnick,))
       self.sql.commit()
       return gib.ircstr('´I{0}´N is not linked with ´I{1}´N anymore.').format(ircnick, irc[0][1])
     else:
       return gib.ircstr('´I{0}´N is not currently linked with any last.fm username.')
   else:
     return ''
Пример #12
0
 def main(self, args, env={}):
     if not len(args): return ''
     link = self.google.search(args + ['site:anidb.net'])
     if len(link):
         if len(link[1]):
             return gib.ircstr("{0} - ´B{1}´N").format(
                 link[0], link[1].replace(' - AniDB', ''))
         else:
             return str(link[0])
     else:
         return gib.ircstr("'´I{0}´N' did not return anything.").format(
             ' '.join(args))
Пример #13
0
class WAlpha:
  command = ".wa"
  help = gib.ircstr("´Iquery´N | Queries WolframAlpha.")
  shelp = gib.ircstr("´Iquery´N")

  client = None

  def __init__(self):
    self.client = wolframalpha.Client("KEY")

  def main(self, args, env = {}):
    if not len(args): return ''
    num = 10 if 'nick' in env and env['nick'].GetHost() == 'Potatoe.Developer.AnimeBytes' else 5
    r = self.query(' '.join(args), num)
    if len(r):
      pods = [gib.ircstr('´C7´B') + r.pop(0)[1] + gib.ircstr('´N :: ')]
      for s in r:
        if len(pods[-1]) + len(s[0]) + len(s[1]) >= 400: pods.append('')
        pods[-1] += gib.ircstr('[ ´C10') + s[0] + gib.ircstr(': ´N') + s[1] + ' ]'
#        if len(pods[-1]) >= 400: pods.append('')
      pods = list(filter(None, pods))
#      if 'nick' in env and env['nick'].GetHost() != 'Potatoe.Developer.AnimeBytes': pods = pods[0:1]
      pods = pods[0:1]
      return pods
    else:
      return 'No results!'

  def query(self, query, num = 5):
    global ret
    res = self.client.query(query)
    ret = []
    for p in res.pods:
      if p.text: ret.append([p.title, ' || '.join([self.clean_wa(c.text) for c in p if c.text])])
      if len(ret) > num: break
#    for r in res.results:
#      if len(ret) == 4: break
#      ret.append(gib.B + r.text + gib.N)
#    if len(ret) < 4:
#      for p in res.pods:
#        if len(ret) == 4: break
#        ret.append(gib.I + p.text + gib.N)
    return ret

  def clean_wa(self, toclean):
    return ' '.join(toclean.replace('\n  | ', ' ').replace('\n', ' - ').split()) \
           .replace(' )', ')').replace('( ', '(').rstrip(' | ').replace(' | ', ', ') \
           .replace(' ~~ ', ' ≒ ').replace('~~ ', '~').replace('>=', '≥').replace('<=', '≤') \
           .replace('=>', '⇒').replace(r'\:2224', '∤').replace('(for all)', ' ∀ ') \
           .replace(' element ', ' ∈ ').replace('(not element)', ' ∉ ') \
           .replace(r'\:2115', 'ℕ').replace(r'\:2124', 'ℤ').replace(r'\:211a', 'ℚ').replace(r'\:211d', 'ℝ').replace(r'\:2102', 'ℂ') \
           .strip()
Пример #14
0
    def main(self, args, env={}):
        user = ''
        if len(args) and args[0] and self.userre.match(args[0]): user = args[0]
        if not user and 'nick' in env:
            nick = env['nick'].GetNick()
            if len(args) == 2 and args[0] == '.set':
                if self.userre.match(args[1]):
                    return self.set_nick(nick, args[1])
                else:
                    return gib.ircstr(
                        '´I{0}´N is not a valid last.fm username.').format(
                            args[1])
            if len(args) == 1 and args[0] == '.unset':
                return self.unset_nick(nick)
            user = self.get_nick(nick)
            if not user and self.userre.match(nick): user = nick
        if not user:
            return gib.ircstr("Invalid user ´I{0}´N").format(
                args[0] if len(args[0]) else env['nick'].GetNick())
        last_track = self.get_last_track(user)
        if 'error' in last_track:
            if last_track['error'] == 'not found':
                return gib.ircstr("´I{0}´N not found").format(user)
            elif last_track['error'] == 'no records':
                return gib.ircstr("´I{0}´N never played anything").format(user)
            else:
                return
        time = last_track['time']
        time = (self.pretty_date(time) + ' ') if time != 0 else ''
        tags = last_track['tags'][:3]
        tags = (gib.ircstr('´C7´B´B') + gib.ircstr('´N, ´C7´B´B').join(tags) +
                gib.N) if len(tags) else 'no tags'
        loved = gib.ircstr('´C4♥´N ') if last_track['loved'] else ''
        play = self.ordn(last_track['userplaycount'])
        album = (gib.ircstr('[´C13´B´B') + last_track['album'].title +
                 gib.ircstr('´N] ')) if last_track['album'] else ''

        resp = gib.ircstr(
            '´C11{0}´N {1} listening to "´C10´B{2}´N" {3}by ´C12´B{4}´N {5}{6}for the {7} time, {8} plays by {9} listeners. ({10})'
        )
        resp = resp.format(user, 'was' if time != '' else 'is',
                           last_track['track'], loved, last_track['artist'],
                           album, time, play, last_track['globalplaycount'],
                           last_track['listeners'], tags)
        #    if type(time) == int and time == 0:
        #      resp = gib.ircstr('´C11´I{0}´N is currently listening to "´C10´B{1}´N" by ´C12´I{2}´N{3} {4}for the {5} time, {6} global plays by {7} listeners. ({8})')
        #      resp = resp.format(user, last_track['track'], last_track['artist'], album, loved, play, last_track['globalplaycount'], last_track['listeners'], tags)
        #    else:
        #      resp = gib.ircstr('´C11´I{0}´N was listening to "´C10´B{1}´N" by ´C12´I{2}´N{3} {4}about {5} for the {6} time, {7} global plays by {8} listeners. ({9})')
        #      resp = resp.format(user, last_track['track'], last_track['artist'], album, loved, time, play, last_track['globalplaycount'], last_track['listeners'], tags)
        return resp
Пример #15
0
 def set_nick(self, ircnick, lfmnick):
   if self.sqlc:
     old = self.sqlc.execute('SELECT * FROM nicks WHERE irc = ?', (ircnick,)).fetchall()
     all = self.sqlc.execute('SELECT * FROM nicks WHERE lastfm = ?', (lfmnick,)).fetchall()
     if len(old):
       self.sqlc.execute('UPDATE nicks SET lastfm = ? WHERE irc = ?', (lfmnick, ircnick))
     else:
       self.sqlc.execute('INSERT INTO nicks VALUES (?, ?)', (ircnick, lfmnick))
     self.sql.commit()
     if not (ircnick, lfmnick) in all: all.append((ircnick, lfmnick))
     all = [e[0] for e in all]
     all = gib.ircstr('´N, ´I').join(all)
     return gib.ircstr('´I{0}´N is now linked with ´I{1}´N.').format(lfmnick, all)
   else:
     return ''
Пример #16
0
 def main(self, args, env={}):
     if not len(args): return ''
     link = self.google.search(args + ['site:bato.to'])
     if len(link):
         rating = self.get_rating(link[0])
         name = [str(link[0])]
         if len(rating): name.append(gib.ircstr('´C7´B´B' + rating + '´N'))
         if len(link[1]):
             name.append(
                 gib.ircstr('´B' + link[1].split('- Scanlations ')[0].split(
                     ' - Comic ')[0] + '´N'))
         name = ' :: '.join(name)
         return name
     else:
         return gib.ircstr("'´I{0}´N' did not return anything.").format(
             ' '.join(args))
Пример #17
0
 def main(self, args, env={}):
     if not len(args): return ''
     host = socket.gethostbyaddr(args[0])[0]
     if host.find('://') == -1: host = "http://{0}/".format(host)
     page = urlopen(
         Request(
             host, None, {
                 'User-Agent':
                 "Mozilla/5.0 (Windows NT 6.2; WOW64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/29.0.1547.2 Safari/537.36"
             }))
     try:
         title = self.google.get_title(page)
     except:
         title = gib.ircstr("´ITimeout´N")
     return gib.ircstr("{0} | ´B{1}´N{2}").format(
         args[0], host, (" - " + title) if len(title) else '')
Пример #18
0
  def main(self, args, env = {}):
    if not len(args): return ''
    num = 10 if 'nick' in env and env['nick'].GetHost() == 'Potatoe.Developer.AnimeBytes' else 5
    r = self.query(' '.join(args), num)
    if len(r):
      pods = [gib.ircstr('´C7´B') + r.pop(0)[1] + gib.ircstr('´N :: ')]
      for s in r:
        if len(pods[-1]) + len(s[0]) + len(s[1]) >= 400: pods.append('')
        pods[-1] += gib.ircstr('[ ´C10') + s[0] + gib.ircstr(': ´N') + s[1] + ' ]'
#        if len(pods[-1]) >= 400: pods.append('')
      pods = list(filter(None, pods))
#      if 'nick' in env and env['nick'].GetHost() != 'Potatoe.Developer.AnimeBytes': pods = pods[0:1]
      pods = pods[0:1]
      return pods
    else:
      return 'No results!'
Пример #19
0
class Batoto:
    command = ".btt"
    help = gib.ircstr("´Isearchterm´N | Searches on Bato.to.")
    shelp = gib.ircstr("´Iquery´N")

    google = None

    def __init__(self):
        self.google = google.Google()

    def main(self, args, env={}):
        if not len(args): return ''
        link = self.google.search(args + ['site:bato.to'])
        if len(link):
            rating = self.get_rating(link[0])
            name = [str(link[0])]
            if len(rating): name.append(gib.ircstr('´C7´B´B' + rating + '´N'))
            if len(link[1]):
                name.append(
                    gib.ircstr('´B' + link[1].split('- Scanlations ')[0].split(
                        ' - Comic ')[0] + '´N'))
            name = ' :: '.join(name)
            return name
        else:
            return gib.ircstr("'´I{0}´N' did not return anything.").format(
                ' '.join(args))

    def get_rating(self, url):
        if not len(url): return ''
        page = self.google.open_page(url)
        page = b''.join(page.readlines())
        try:
            page = page.decode('utf8')
        except UnicodeDecodeError:
            try:
                page = zlib.decompress(page, 15 + 32)
            except:
                return ''
        html = lxml.html.document_fromstring(page)
        rating = html.xpath('//div[contains(@class, "rating")]')
        if len(rating) > 0:
            rating = rating[0].text_content().split('(')[1].split(
                'votes')[0] + ' votes'
            return rating
        else:
            return ''
Пример #20
0
 def unset_nick(self, ircnick):
     if self.sqlc:
         irc = self.sqlc.execute('SELECT * FROM nicks WHERE irc = ?',
                                 (ircnick, )).fetchall()
         if len(irc):
             self.sqlc.execute('DELETE FROM nicks WHERE irc = ?',
                               (ircnick, ))
             self.sql.commit()
             return gib.ircstr(
                 '´I{0}´N is not linked with ´I{1}´N anymore.').format(
                     ircnick, irc[0][1])
         else:
             return gib.ircstr(
                 '´I{0}´N is not currently linked with any last.fm username.'
             )
     else:
         return ''
Пример #21
0
 def set_nick(self, ircnick, lfmnick):
     if self.sqlc:
         old = self.sqlc.execute('SELECT * FROM nicks WHERE irc = ?',
                                 (ircnick, )).fetchall()
         all = self.sqlc.execute('SELECT * FROM nicks WHERE lastfm = ?',
                                 (lfmnick, )).fetchall()
         if len(old):
             self.sqlc.execute('UPDATE nicks SET lastfm = ? WHERE irc = ?',
                               (lfmnick, ircnick))
         else:
             self.sqlc.execute('INSERT INTO nicks VALUES (?, ?)',
                               (ircnick, lfmnick))
         self.sql.commit()
         if not (ircnick, lfmnick) in all: all.append((ircnick, lfmnick))
         all = [e[0] for e in all]
         all = gib.ircstr('´N, ´I').join(all)
         return gib.ircstr('´I{0}´N is now linked with ´I{1}´N.').format(
             lfmnick, all)
     else:
         return ''
Пример #22
0
class VNDB:
    command = ".vndb"
    help = gib.ircstr("´Isearchterm´N | Searches on VNDB.")
    shelp = gib.ircstr("´Iquery´N")

    google = None

    def __init__(self):
        self.google = google.Google()

    def main(self, args, env={}):
        if not len(args): return ''
        link = self.google.search(args + ['site:vndb.org'])
        if len(link):
            if len(link[1]):
                return gib.ircstr("{0} - ´B{1}´N").format(link[0], link[1])
            else:
                return str(link[0])
        else:
            return "'´I{0}´N' did not return anything.".format(' '.join(args))
Пример #23
0
class ANN:
    command = ".ann"
    help = gib.ircstr("´Isearchterm´N | Searches on AnimeNewsNetwork.")
    shelp = gib.ircstr("´Iquery´N")

    google = None

    def __init__(self):
        self.google = google.Google()

    def main(self, args, env={}):
        if not len(args): return ''
        link = self.google.search(args + ['site:animenewsnetwork.com'])
        if len(link):
            if len(link[1]):
                return gib.ircstr("{0} - ´B{1}´N").format(link[0], link[1])
            else:
                return str(link[0])
        else:
            return gib.ircstr("'´I{0}´N' did not return anything.").format(
                ' '.join(args))
Пример #24
0
 def rebuildindices(self):
   global L, modules, Modules, commands, help
   commands = {}
   help = gib.ircstr("´B.help´N [´Icmd´N]")
   for mod in modules:
     try:
       help += ', ' + gib.B + Modules[mod].command + gib.N + ' ' + Modules[mod].shelp
       commands[Modules[mod].command] = mod
     except Exception as e:
       L.log(L.ERROR, "Exception rebuilding indices for " + mod + ": " + str(e), self.GetSavePath() + "/modules.log")
       traceback.print_exc(file = open(self.GetSavePath() + "/traceback.log", "a"))
       pass
Пример #25
0
class MAL:
    command = ".mal"
    help = gib.ircstr("´Isearchterm´N | Searches on MyAnimeList.")
    shelp = gib.ircstr("´Iquery´N")

    google = None

    def __init__(self):
        self.google = google.Google()

    def main(self, args, env={}):
        if not len(args): return ''
        link = self.google.search(args + ['site:myanimelist.net'])
        if len(link):
            if len(link[1]):
                return gib.ircstr("{0} - ´B{1}´N").format(
                    link[0], link[1].replace(' - MyAnimeList.net', ''))
            else:
                return str(link[0])
        else:
            return gib.ircstr("'´I{0}´N' did not return anything.".format(
                ' '.join(args)))
Пример #26
0
 def rebuildindices(self):
     global L, modules, Modules, commands, help
     commands = {}
     help = gib.ircstr("´B.help´N [´Icmd´N]")
     for mod in modules:
         try:
             help += ', ' + gib.B + Modules[
                 mod].command + gib.N + ' ' + Modules[mod].shelp
             commands[Modules[mod].command] = mod
         except Exception as e:
             L.log(
                 L.ERROR,
                 "Exception rebuilding indices for " + mod + ": " + str(e),
                 self.GetSavePath() + "/modules.log")
             traceback.print_exc(
                 file=open(self.GetSavePath() + "/traceback.log", "a"))
             pass
Пример #27
0
import gib
import logger

L = logger.Logger()
L.setloglevel(L.INFO)
L.setlogpath(filepath + '/GIB.log')
L.log(L.INFO, 'STARTED')

modules = {
    'google', 'anidb', 'ann', 'vndb', 'vgmdb', 'mal', 'trans', 'lastfm', 'wa',
    'mangaupdates', 'batoto'
}
modules = dict.fromkeys(modules, '')
Modules = modules
commands = {}
help = gib.ircstr("´B.help´N [´Icmd´N]")
# So that we can just import them by name of the script
sys.path.append(filepath + '/gib/')
for mod in modules:
    try:
        del sys.modules[mod]
    except KeyError:
        pass
    modules[mod] = importlib.import_module(mod)
    try:
        Modules[mod] = getattr(modules[mod], modules[mod].name)()
        help += ', ' + gib.B + Modules[mod].command + gib.N + ' ' + Modules[
            mod].shelp
        commands[Modules[mod].command] = mod
    except Exception as e:
        L.log(L.ERROR, str(e))
Пример #28
0
  def OnChanMsg(self, nick, channel, message):
    global L, modules, Modules, commands, help

    # Get some basic stuff
    net = self.GetNetwork()
    me = net.GetNick()
    msg = message.s
    msglst = msg.split()
    nik = nick.GetNick()
    try:  # It's either a znc.CChan or a znc.CNick, everything else we just don't accept
      chan = channel.GetName() if type(channel) is znc.CChan else channel.GetNick()
    except Exception:
      return znc.CONTINUE

    if nik == "Satsuki":
      return znc.CONTINUE
    if (self.use_channel_blacklist and chan in self.channel_blacklist) \
    or (self.use_channel_whitelist and not chan in self.channel_whitelist):
      return znc.CONTINUE

    # Some anti-flooding procedures. Not the best, but it works vOv
    if msglst[0] in commands:
      #if not (nik in self.user_whitelist
      permstr = channel.FindNick(nik).GetPermStr() if type(channel) is znc.CChan else ''
      if not (self.abure.sub('\\1', nick.GetHost()) in self.user_whitelist or nik in self.user_whitelist) \
      and all(permstr.find(p) < 0 for p in ['~', '&', '@', '%']):
        if use_user_whitelist:
          return znc.CONTINUE
        currenttime = time.mktime(time.gmtime())
        if currenttime-self.cooldown[0] < 90:
          return znc.CONTINUE
        if currenttime-self.cooldown[-1] < 5:
          return znc.CONTINUE
        if currenttime <= self.cooluntil:
          return znc.CONTINUE
        if all(t >= currenttime-45 for t in self.cooldown):
          self.cooluntil = currenttime + 300
          self.put_msg(chan, 'Yamete! >///<')
          L.log(L.INFO, chan + " flooded by " + nik + ", msg: " + msg, self.GetSavePath() + "/modules.log")
        self.cooldown.append(currenttime)
        if len(self.cooldown) > 5:
          self.cooldown.pop(0)
        if self.cooluntil > currenttime:
          return znc.CONTINUE
        if currenttime-self.cooldown[0] < 90:
          self.put_msg(chan, 'Yamete! >///<')
        if currenttime-self.cooldown[-1] < 5:
          self.put_msg(chan, 'Yamete! >///<')

    if msglst[0] == '.help' \
    or (msglst[0].lower() in [me.lower(), 'sawako', 'sadako'] and msglst[1].lower() == 'help') \
    or (msglst[0].lower() in ['hi', 'hello', 'yo', 'hey'] and msglst[1].lower() in [me.lower(), 'sawako', 'sadako']):
      if msglst[0].lower() in ['hi', 'hello', 'yo', 'hey']:
        greeting = random.choice(['Hi', 'Hello', '今日は', 'Konnichiwa'])
        self.put_msg(channel.GetName(), greeting + ' ' + nik + '!')
      if msglst[0] == '.help':
        args = msglst[1:]
      else:
        args = msglst[2:]
      if not len(args):
        self.put_notice(nik, 'Possible commands: ' + help)
        self.put_notice(nik, gib.ircstr('For more details: ´B/msg ' + me + ' help´N'))
        return znc.CONTINUE
      if args[0] in commands:
        mod = Modules[commands[args[0]]]
        self.put_notice(nik, gib.B + mod.command + gib.N + ' ' + mod.help)
        return znc.CONTINUE

    if msglst[0] in commands:
      cmd = msglst[0]
      mod = commands[cmd]
      mod = Modules[mod]
      args = msglst[1:]
      now = time.time()
      ret = ''
      chan = channel.GetName()
      chan = (chan[:12] + (chan[12:] and '..')).ljust(14)
      L.log(L.INFO, chan + " call: " + cmd + ", args: " + str(args), self.GetSavePath() + "/modules.log")
      try:
        env = {'nick': nick, 'channel': channel, 'self': self}
        ret = mod.main(args, env)
        if len(ret):
          if 'c' in str(channel.GetModeString()):
            ret = self.colorre.sub('', ret)
          self.put_msg(channel, ret)
      except Exception as e:
        L.log(L.ERROR, chan + " error: " + str(e), self.GetSavePath() + "/modules.log")
        traceback.print_exc(file = open(self.GetSavePath() + "/traceback.log", "a"))
      L.log(L.INFO, chan + " finish: " + cmd + ", (" + str(int((time.time() - now) * 1000)) + "ms)", self.GetSavePath() + "/modules.log")
      return znc.CONTINUE

    return znc.CONTINUE
Пример #29
0
class Google:
    command = ".g"
    help = gib.ircstr("´Isearchterm´N | Does a quick google search.")
    shelp = gib.ircstr("´Iquery´N")
    resultre = re.compile('<h3 class="r"[^>]*><a href="([^"]+)"[^>]+>(.+)</a>')
    tire = re.compile('<title>(.*)</title>')
    htmlparser = html.parser.HTMLParser()
    apiKey = ''

    class HTMLStripper(html.parser.HTMLParser):
        class HTMLP(html.parser.HTMLParser):
            _data = ""

            def handle_data(self, data):
                self._data += str(data)

            def r(self):
                self._data = ""
                self.reset()

        htmlp = HTMLP()

        def strip(self, data):
            self.htmlp.feed(str(data))
            self.htmlp.close()
            nudes = self.htmlp._data
            self.htmlp.r()
            return nudes

    htmlstripper = HTMLStripper()

    class RedirectHandler(HTTPRedirectHandler):
        def http_error_403(self, req, fp, code, msg, headers):
            return 0

        def http_error_503(self, req, fp, code, msg, headers):
            return 0

        def http_error_302(self, req, fp, code, msg, headers):
            result = HTTPRedirectHandler.http_error_302(
                self, req, fp, code, msg, headers)
            result.status = code
            return result

        def http_error_302(self, req, fp, code, msg, headers):
            result = HTTPRedirectHandler.http_error_302(
                self, req, fp, code, msg, headers)
            result.status = code
            return result

    def main(self, args, env={}):
        if not len(args): return ''
        link = self.search(args)
        if len(link):
            if len(link[1]):
                return gib.ircstr("{0} - ´B{1}´N").format(link[0], link[1])
            else:
                return str(link[0])
        else:
            return gib.ircstr("'´I{0}´N' did not match any documents.").format(
                ' '.join(args))

    def search(self, query):
        response = self.open_page(
            "http://www.google.com/search?ie=UTF-8&oe=UTF-8&sourceid=navclient&complete=0&hl=en&q={0}"
            .format('+'.join([quote_plus(s) for s in query])))
        link = [response.url, '']
        found = True
        match = ''
        if link[0].find('google.com/search') != -1 or link[0].find(
                'google.de/search') != -1:
            found = False
            pagestr = ''
            for line in iter(response.readline, b''):
                line = line.decode('utf8')
                pagestr += line
                if line.find('<h3 class="r">') != -1:
                    match = line.split('</h3>')[0]
                    found = True
                    break
            if found and len(match):
                match = self.resultre.search(match)
                link[0] = self.htmlparser.unescape(match.group(1))
                link[1] = self.htmlstripper.strip(
                    self.htmlparser.unescape(match.group(2)))


# Since we retrieve the title from Google we don't need to look it up again (with the chance of the page actually blocking us or similar)
#        if len(link[0]) and link[0]!=html.parser.HTMLParser().unescape(match): link[1] = self.get_title(opener.open(Request(link[0], None, {"User-Agent":"Mozilla/5.0 (Windows NT 6.2; WOW64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/29.0.1547.2 Safari/537.36"})))
            else:
                link = [self.shorten(link[0]), self.get_title(pagestr)]
        else:
            link = [link[0], self.get_title(response)]
        return link

    def shorten(self, longUrl):
        data = "{{'longUrl': '{0}', 'key': '{1}'}}".format(
            longUrl.replace("'", r"\'"), self.apiKey).encode('utf8')
        headers = {
            "Content-Length": len(data),
            "Content-Type": "application/json"
        }
        req = Request('https://www.googleapis.com/urlshortener/v1/url', data,
                      headers)
        page = urlopen(req)
        page = b''.join(page.readlines()).decode('utf8')
        page = json.loads(page)
        return page["id"] if ("id" in page and page["id"] != "") else longUrl

    def open_page(self, url):
        req = Request(
            url, None, {
                "User-Agent":
                "Mozilla/5.0 (Windows NT 6.1; WOW64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/40.0.2214.91 Safari/537.36"
            })
        opener = build_opener(self.RedirectHandler())
        return opener.open(req)

    def get_title(self, page, max_title_length=128):
        err = False
        try:
            page = b''.join(page.readlines())
            try:
                page = page.decode('utf8')
            except UnicodeDecodeError:
                try:
                    page = zlib.decompress(page, 15 + 32)
                except zlib.error:
                    err = True
        except:
            if not isinstance(page, str): err = True
        if not err:
            title = self.tire.search(page.replace('\n', ''))
            title = title.groups()[0] if title and len(
                title.groups()) > 0 else ''
        else:
            title = ''
        return title if len(
            title) < max_title_length else title[0:max_title_length - 1]
Пример #30
0
class BakaUpdates:
    command = ".mu"
    help = gib.ircstr("´Isearchterm´N | Searches manga on Baka-Updates.")
    shelp = gib.ircstr("´Iquery´N")

    google = None

    class HTMLStripper(html.parser.HTMLParser):
        class HTMLP(html.parser.HTMLParser):
            _data = ""

            def handle_starttag(self, tag, attrs):
                if tag == "br":
                    if self._data[-1] != " ":
                        self._data += " "

            def handle_data(self, data):
                self._data += str(data)

            def r(self):
                self._data = ""
                self.reset()

        htmlp = HTMLP()

        def strip(self, data):
            self.htmlp.feed(str(data))
            self.htmlp.close()
            nudes = self.htmlp._data
            self.htmlp.r()
            return nudes

    htmlstripper = HTMLStripper()

    def __init__(self):
        self.google = google.Google()

    def main(self, args, env={}):
        if not len(args): return ''
        link = self.google.search(args + ['site:mangaupdates.com/series.html'])
        if len(link):
            page = self.google.open_page(link[0])
            page = b''.join(page.readlines()).decode('utf-8', 'ignore')
            html = lxml.html.document_fromstring(page)
            rating = self.get_rating(html)
            volumes = self.get_volumes(html)
            description = self.get_description(html)
            name = [str(link[0])]
            if not volumes in (None, ""):
                name.append(gib.ircstr('´C6´B´B' + volumes + '´N'))
            if not rating in (None, ""):
                name.append(gib.ircstr('´C7´B´B' + rating + '´N'))
            if not link[1] in (None, ""):
                name.append(
                    gib.ircstr('´B' +
                               link[1].replace('Baka-Updates Manga - ', '') +
                               '´N'))
            name = ' :: '.join(name)
            if not description in (None, ""): name = [name, description]
            return name
        else:
            return gib.ircstr("'´I{0}´N' did not return anything.").format(
                ' '.join(args))

    def get_description(self, html):
        if not html: return ''
        description = html.xpath(
            '//div[@class="sCat"]/b[text()="Description"]/../following-sibling::div[@class="sContent"][1]'
        )
        if len(description) > 0:
            description = self.htmlstripper.strip(
                lxml.html.tostring(
                    description[0]).decode('utf8').strip(' \n\t\r')).replace(
                        '\n', '').replace('\r', '')
            #description = description[0].text_content().strip(' \n\t\r')
            return description if len(description) < 455 else (
                description[:450] + ' ...')
        else:
            return ''

    def get_rating(self, html):
        if not html: return ''
        rating = html.xpath(
            '//div[@class="sCat"]/b[text()="User Rating"]/../following-sibling::div[@class="sContent"][1]'
        )
        if len(rating) > 0:
            rating = rating[0].text_content().split(
                ' votes)')[0].split('\r')[0].replace('Average: ', '').replace(
                    ' / 10.0 (', ' - ') + ' votes'
            return rating
        else:
            return ''

    def get_volumes(self, html):
        if not html: return ''
        volumes = html.xpath(
            '//div[@class="sCat"]/b[text()="Status in Country of Origin"]/../following-sibling::div[@class="sContent"][1]'
        )
        if len(volumes) > 0:
            volumes = volumes[0].text_content().strip(' \n\t\r')
            return volumes
        else:
            return ''
Пример #31
0
class LastFM:
    command = ".np"
    help = gib.ircstr(
        "[´I.set´N/´I.unset´N] [´Iuser´N] | Returns last played song of ´Iuser´N (or own nick if none given). IRC nicks can be linked and unlinked with last.fm usernames respectively by calling ´I.np .set ´Blastfm-nick´N and ´I.np .unset´N. After this has been done, the linked IRC nick will not have to specify his last.fm username every time he calls ´I.np´N."
    )
    shelp = gib.ircstr("[´Iusr´N]")

    userre = re.compile('^[a-zA-Z0-9*_-]{,15}$')
    network = None
    sql = None
    sqlc = None

    def __init__(self):
        self.network = pylast.LastFMNetwork('ID', 'APIKEY')
        try:
            exists = os.path.isfile('lastfm.db')
            self.sql = sqlite3.connect('lastfm.db')
            self.sqlc = self.sql.cursor()
            if not exists:
                self.sqlc.execute(
                    'CREATE TABLE nicks (irc varchar(30), lastfm varchar(15));'
                )
                self.sql.commit()
        except:
            pass

    def main(self, args, env={}):
        user = ''
        if len(args) and args[0] and self.userre.match(args[0]): user = args[0]
        if not user and 'nick' in env:
            nick = env['nick'].GetNick()
            if len(args) == 2 and args[0] == '.set':
                if self.userre.match(args[1]):
                    return self.set_nick(nick, args[1])
                else:
                    return gib.ircstr(
                        '´I{0}´N is not a valid last.fm username.').format(
                            args[1])
            if len(args) == 1 and args[0] == '.unset':
                return self.unset_nick(nick)
            user = self.get_nick(nick)
            if not user and self.userre.match(nick): user = nick
        if not user:
            return gib.ircstr("Invalid user ´I{0}´N").format(
                args[0] if len(args[0]) else env['nick'].GetNick())
        last_track = self.get_last_track(user)
        if 'error' in last_track:
            if last_track['error'] == 'not found':
                return gib.ircstr("´I{0}´N not found").format(user)
            elif last_track['error'] == 'no records':
                return gib.ircstr("´I{0}´N never played anything").format(user)
            else:
                return
        time = last_track['time']
        time = (self.pretty_date(time) + ' ') if time != 0 else ''
        tags = last_track['tags'][:3]
        tags = (gib.ircstr('´C7´B´B') + gib.ircstr('´N, ´C7´B´B').join(tags) +
                gib.N) if len(tags) else 'no tags'
        loved = gib.ircstr('´C4♥´N ') if last_track['loved'] else ''
        play = self.ordn(last_track['userplaycount'])
        album = (gib.ircstr('[´C13´B´B') + last_track['album'].title +
                 gib.ircstr('´N] ')) if last_track['album'] else ''

        resp = gib.ircstr(
            '´C11{0}´N {1} listening to "´C10´B{2}´N" {3}by ´C12´B{4}´N {5}{6}for the {7} time, {8} plays by {9} listeners. ({10})'
        )
        resp = resp.format(user, 'was' if time != '' else 'is',
                           last_track['track'], loved, last_track['artist'],
                           album, time, play, last_track['globalplaycount'],
                           last_track['listeners'], tags)
        #    if type(time) == int and time == 0:
        #      resp = gib.ircstr('´C11´I{0}´N is currently listening to "´C10´B{1}´N" by ´C12´I{2}´N{3} {4}for the {5} time, {6} global plays by {7} listeners. ({8})')
        #      resp = resp.format(user, last_track['track'], last_track['artist'], album, loved, play, last_track['globalplaycount'], last_track['listeners'], tags)
        #    else:
        #      resp = gib.ircstr('´C11´I{0}´N was listening to "´C10´B{1}´N" by ´C12´I{2}´N{3} {4}about {5} for the {6} time, {7} global plays by {8} listeners. ({9})')
        #      resp = resp.format(user, last_track['track'], last_track['artist'], album, loved, time, play, last_track['globalplaycount'], last_track['listeners'], tags)
        return resp

    def get_last_track(self, user):
        try:
            track = self.network.get_user(user).get_now_playing()
        except pylast.WSError:
            return {'error': 'not found'}
        now = True
        time = 0
        if not track:
            now = False
            try:
                track = self.network.get_user(user).get_recent_tracks()[0]
            except IndexError:
                return {'error': 'no records'}
            time = int(track.timestamp)
            track = track.track
        album = track.get_album()
        track.username = user
        userloved = track.get_userloved()
        userplays = int(track.get_userplaycount()) + (1 if now else 0)
        plays = int(track.get_playcount())
        listeners = int(track.get_listener_count())
        t1 = track._request('track.getInfo').getElementsByTagName('toptags')
        tags = []
        if len(t1):
            t1 = t1[0].getElementsByTagName('tag')
            for tag in t1:
                tags.append(
                    tag.getElementsByTagName('name')
                    [0].childNodes[0].nodeValue)
        t2 = track.artist._request('artist.getInfo').getElementsByTagName(
            'tags')
        if len(t2):
            t2 = t2[0].getElementsByTagName('tag')
            for tag in t2:
                tags.append(
                    tag.getElementsByTagName('name')
                    [0].childNodes[0].nodeValue)
        return {
            'track': track.title,
            'artist': track.artist,
            'album': album,
            'time': time,
            'loved': userloved,
            'userplaycount': userplays,
            'globalplaycount': plays,
            'listeners': listeners,
            'tags': tags
        }

    def set_nick(self, ircnick, lfmnick):
        if self.sqlc:
            old = self.sqlc.execute('SELECT * FROM nicks WHERE irc = ?',
                                    (ircnick, )).fetchall()
            all = self.sqlc.execute('SELECT * FROM nicks WHERE lastfm = ?',
                                    (lfmnick, )).fetchall()
            if len(old):
                self.sqlc.execute('UPDATE nicks SET lastfm = ? WHERE irc = ?',
                                  (lfmnick, ircnick))
            else:
                self.sqlc.execute('INSERT INTO nicks VALUES (?, ?)',
                                  (ircnick, lfmnick))
            self.sql.commit()
            if not (ircnick, lfmnick) in all: all.append((ircnick, lfmnick))
            all = [e[0] for e in all]
            all = gib.ircstr('´N, ´I').join(all)
            return gib.ircstr('´I{0}´N is now linked with ´I{1}´N.').format(
                lfmnick, all)
        else:
            return ''

    def unset_nick(self, ircnick):
        if self.sqlc:
            irc = self.sqlc.execute('SELECT * FROM nicks WHERE irc = ?',
                                    (ircnick, )).fetchall()
            if len(irc):
                self.sqlc.execute('DELETE FROM nicks WHERE irc = ?',
                                  (ircnick, ))
                self.sql.commit()
                return gib.ircstr(
                    '´I{0}´N is not linked with ´I{1}´N anymore.').format(
                        ircnick, irc[0][1])
            else:
                return gib.ircstr(
                    '´I{0}´N is not currently linked with any last.fm username.'
                )
        else:
            return ''

    def get_nick(self, ircnick):
        if self.sqlc:
            nick = self.sqlc.execute('SELECT lastfm FROM nicks WHERE irc = ?',
                                     (ircnick, )).fetchall()
            if len(nick): return nick[0][0]
            else: return None
        else: return None

    def ordn(self, n):
        #    if n <= 10: return ['first', 'second', 'third', 'fourth', 'fifth', 'sixth', 'seventh', 'eighth', 'ninth', 'tenth'][n-1]
        #    else: return str(n)+("th" if 4<=n%100<=20 else {1:"st",2:"nd",3:"rd"}.get(n%10, "th"))
        return str(n) + ("th" if 4 <= n % 100 <= 20 else {
            1: "st",
            2: "nd",
            3: "rd"
        }.get(n % 10, "th"))

    def pretty_date(self, time=False):
        """
    Get a datetime object or a int() Epoch timestamp and return a
    pretty string like 'an hour ago', 'yesterday', '3 months ago',
    'just now', etc
    """
        now = datetime.datetime.now()
        if type(time) is int:
            diff = now - datetime.datetime.fromtimestamp(time)
        elif isinstance(time, datetime.datetime):
            diff = now - time
        elif not time:
            diff = now - now
        second_diff = diff.seconds
        day_diff = diff.days
        if day_diff < 0:
            return ''
        if day_diff == 0:
            if second_diff < 10:
                return "just now"
            if second_diff < 60:
                return str(second_diff) + " seconds ago"
            if second_diff < 120:
                return "a minute ago"
            if second_diff < 3600:
                return str(int(second_diff / 60)) + " minutes ago"
            if second_diff < 7200:
                return "an hour ago"
            if second_diff < 86400:
                return str(int(second_diff / 3600)) + " hours ago"
        if day_diff == 1:
            return "yesterday"
        if day_diff < 7:
            return str(day_diff) + " days ago"
        if day_diff < 31:
            return str(int(day_diff / 7)) + " weeks ago"
        if day_diff < 365:
            return str(int(day_diff / 30)) + " months ago"
        return str(int(day_diff / 365)) + " years ago"
Пример #32
0
try: del sys.modules['gib']
except KeyError: pass
try: del sys.modules['logger']
except KeyError: pass
import gib
import logger
L = logger.Logger()
L.setloglevel(L.INFO)
L.setlogpath(filepath + '/GIB.log')
L.log(L.INFO, 'STARTED')

modules = {'google', 'anidb', 'ann', 'vndb', 'vgmdb', 'mal', 'trans', 'lastfm', 'wa', 'mangaupdates', 'batoto'}
modules = dict.fromkeys(modules, '')
Modules = modules
commands = {}
help = gib.ircstr("´B.help´N [´Icmd´N]")
# So that we can just import them by name of the script
sys.path.append(filepath + '/gib/')
for mod in modules:
  try: del sys.modules[mod]
  except KeyError: pass
  modules[mod] = importlib.import_module(mod)
  try:
    Modules[mod] = getattr(modules[mod], modules[mod].name)()
    help += ', ' + gib.B + Modules[mod].command + gib.N + ' ' + Modules[mod].shelp
    commands[Modules[mod].command] = mod
  except Exception as e:
    L.log(L.ERROR, str(e))


class GIB(znc.Module):
Пример #33
0
    def OnChanMsg(self, nick, channel, message):
        global L, modules, Modules, commands, help

        # Get some basic stuff
        net = self.GetNetwork()
        me = net.GetNick()
        msg = message.s
        msglst = msg.split()
        nik = nick.GetNick()
        try:  # It's either a znc.CChan or a znc.CNick, everything else we just don't accept
            chan = channel.GetName(
            ) if type(channel) is znc.CChan else channel.GetNick()
        except Exception:
            return znc.CONTINUE

        if nik == "Satsuki":
            return znc.CONTINUE
        if (self.use_channel_blacklist and chan in self.channel_blacklist) \
        or (self.use_channel_whitelist and not chan in self.channel_whitelist):
            return znc.CONTINUE

        # Some anti-flooding procedures. Not the best, but it works vOv
        if msglst[0] in commands:
            #if not (nik in self.user_whitelist
            permstr = channel.FindNick(
                nik).GetPermStr() if type(channel) is znc.CChan else ''
            if not (self.abure.sub('\\1', nick.GetHost()) in self.user_whitelist or nik in self.user_whitelist) \
            and all(permstr.find(p) < 0 for p in ['~', '&', '@', '%']):
                if use_user_whitelist:
                    return znc.CONTINUE
                currenttime = time.mktime(time.gmtime())
                if currenttime - self.cooldown[0] < 90:
                    return znc.CONTINUE
                if currenttime - self.cooldown[-1] < 5:
                    return znc.CONTINUE
                if currenttime <= self.cooluntil:
                    return znc.CONTINUE
                if all(t >= currenttime - 45 for t in self.cooldown):
                    self.cooluntil = currenttime + 300
                    self.put_msg(chan, 'Yamete! >///<')
                    L.log(L.INFO,
                          chan + " flooded by " + nik + ", msg: " + msg,
                          self.GetSavePath() + "/modules.log")
                self.cooldown.append(currenttime)
                if len(self.cooldown) > 5:
                    self.cooldown.pop(0)
                if self.cooluntil > currenttime:
                    return znc.CONTINUE
                if currenttime - self.cooldown[0] < 90:
                    self.put_msg(chan, 'Yamete! >///<')
                if currenttime - self.cooldown[-1] < 5:
                    self.put_msg(chan, 'Yamete! >///<')

        if msglst[0] == '.help' \
        or (msglst[0].lower() in [me.lower(), 'sawako', 'sadako'] and msglst[1].lower() == 'help') \
        or (msglst[0].lower() in ['hi', 'hello', 'yo', 'hey'] and msglst[1].lower() in [me.lower(), 'sawako', 'sadako']):
            if msglst[0].lower() in ['hi', 'hello', 'yo', 'hey']:
                greeting = random.choice(['Hi', 'Hello', '今日は', 'Konnichiwa'])
                self.put_msg(channel.GetName(), greeting + ' ' + nik + '!')
            if msglst[0] == '.help':
                args = msglst[1:]
            else:
                args = msglst[2:]
            if not len(args):
                self.put_notice(nik, 'Possible commands: ' + help)
                self.put_notice(
                    nik,
                    gib.ircstr('For more details: ´B/msg ' + me + ' help´N'))
                return znc.CONTINUE
            if args[0] in commands:
                mod = Modules[commands[args[0]]]
                self.put_notice(nik,
                                gib.B + mod.command + gib.N + ' ' + mod.help)
                return znc.CONTINUE

        if msglst[0] in commands:
            cmd = msglst[0]
            mod = commands[cmd]
            mod = Modules[mod]
            args = msglst[1:]
            now = time.time()
            ret = ''
            chan = channel.GetName()
            chan = (chan[:12] + (chan[12:] and '..')).ljust(14)
            L.log(L.INFO, chan + " call: " + cmd + ", args: " + str(args),
                  self.GetSavePath() + "/modules.log")
            try:
                env = {'nick': nick, 'channel': channel, 'self': self}
                ret = mod.main(args, env)
                if len(ret):
                    if 'c' in str(channel.GetModeString()):
                        ret = self.colorre.sub('', ret)
                    self.put_msg(channel, ret)
            except Exception as e:
                L.log(L.ERROR, chan + " error: " + str(e),
                      self.GetSavePath() + "/modules.log")
                traceback.print_exc(
                    file=open(self.GetSavePath() + "/traceback.log", "a"))
            L.log(
                L.INFO, chan + " finish: " + cmd + ", (" +
                str(int((time.time() - now) * 1000)) + "ms)",
                self.GetSavePath() + "/modules.log")
            return znc.CONTINUE

        return znc.CONTINUE