Usuario:Chixpy/PyWikipediaBot/estadisticas.py
Ir a la navegación
Ir a la búsqueda
#!/usr/bin/python # -*- coding: utf-8 -*- #Un intento cutre para conseguir las estadísticas de las páginas, debería funcionar para cualquier familia #Todo está manual porque hay que hacerlo a través de api.php y Special:Statistics?action=raw #pyWikipediabot lo hace a través de las páginas y wikia tiene el límite hasta 1000 en la página de [[special:longpages]] #La verdad es que para lo único que uso Pywikipediabot es para obtener el listado de lenguajes y escribir en la página #Para páginas largas: http://inciclopedia.wikia.com/api.php?action=query&list=allpages&aplimit=500&apminsize=1000&format=phpfm #php es la forma más compacta (phpfm para verlo en el explorador), lo hace de 500 en 500 porque solo los sysops pueden 5000 #ATENCION: USO EXCESIVO DE BLOQUES TRY...EXCEPT XD XD XD XD XD XD from __future__ import division import re import codecs import wikipedia from urllib import urlopen, quote OtrasWikis = { "Inciclopedia": ["es", "inciclopedia.wikia.com", "/index.php", "/api.php"], "Frikipedia": ["fk", "www.frikipedia.es", "/index.php", "/api.php"], # "Wikipediars": ["wprs", "www.wikipediars.com", "/index.php", "/api.php"], } class BasicBot: def __init__(self): self.TotalArticulos = 0 self.TotalFicheros = 0 self.TotalPaginas = 0 self.TotalEdiciones = 0 self.TotalUsuarios = 0 self.TotalActivos = 0 self.TotalAdministradores = 0 self.ArticulosActual = 0 # Para guardar temporalmente el número de artículos de la wiki que estamos recorriendo self.AnadirOtrasWikis = True self.site = wikipedia.getSite() self.texto = "" def run(self): # Pone el sumario wikipedia.setAction(u"Actualizando estadísticas") self.treat() def _EscribirCabecera(self): self.texto += u"{| {{tablabonita|alineación=col1cen|text-align:right; font-size: 90%;}}\n" self.texto += u"|-\n!|Leng<br />\n!|Edic<br />\n!|Pág<br />\n!|Ed/Pg<br />\n!|Art<br />\n!|%<br />\n!|Fich<br />\n" self.texto += u"!|Fch/Art<br />\n!|Usu<br />\n!|Act<br />\n!|Adm<br />\n" self.texto += u"!|>64k<br />\n!|%<br />\n!|>32kb<br />\n!|%<br />\n!|>16kb<br />\n!|%<br />\n" self.texto += u"!|>8k<br />\n!|%<br />\n!|>4kb<br />\n!|%<br />\n" def _EscribirTotales(self): self.texto += u"\n{| {{tablabonita|alineación=|text-align: center;}}\n" self.texto += u"|-\n!|Lenguaje\n!|Ediciones\n!|Páginas\n!|Artículos\n!|Ficheros\n!|Usuarios\n!|Activos\n!|Administradores\n" self.texto += u"|-\n||TOTAL\n" self.texto += u"||%d\n" % (self.TotalEdiciones) self.texto += u"||%d\n" % (self.TotalPaginas) self.texto += u"||%d\n" % (self.TotalArticulos) self.texto += u"||%d\n" % (self.TotalFicheros) self.texto += u"||%d\n" % (self.TotalUsuarios) self.texto += u"||%d\n" % (self.TotalActivos) self.texto += u"||%d\n" % (self.TotalAdministradores) self.texto += u"|}\n----\n" def _LeerEstadisticas(self, URLBase, Path): # Expresiones regulares para extraer los datos # Expresion1 incluye "activesers" mientras que Expresion2 no # He hecho un montón de pruebas para unirlas poniendo (?:activeusers=(?P<activeusers>.*);)? pero no rula Expresion1 = r"total=(?P<total>.*);good=(?P<good>.*);views=(?P<views>.*);edits=(?P<edits>.*);users=(?P<users>.*);activeusers=(?P<activeusers>.*);admins=(?P<admins>.*);images=(?P<images>.*);jobs=(?P<jobs>.*)" Expresion2 = r"total=(?P<total>.*);good=(?P<good>.*);views=(?P<views>.*);edits=(?P<edits>.*);users=(?P<users>.*);admins=(?P<admins>.*);images=(?P<images>.*);jobs=(?P<jobs>.*)" try: Estadisticas = urlopen(u'http://%s%s?title=Special:Statistics&action=raw' % (URLBase, Path)).read() except: return False wikipedia.output(Estadisticas) # Probamos con Expresion1 (con Activeusers) param = re.search(Expresion1, Estadisticas) try: Articulos = int(param.group('good')) except: # Probamos sin activeusers param = re.search(Expresion2, Estadisticas) try: Articulos = int(param.group('good')) except: # Ops, algo falló return False self.ArticulosActual = Articulos Ediciones = int(param.group('edits')) Paginas = int(param.group('total')) Ficheros = int(param.group('images')) Admin = int(param.group('admins')) Usuarios = int(param.group('users')) try: Activos = int(param.group('activeusers')) except: Activos = 0 # Escribimos los datos self.texto += u"||%d\n" % (Ediciones) self.texto += u"||%d\n" % (Paginas) temp = u"||%3.2f\n" % (Ediciones / Paginas) self.texto += temp.replace(".", ",") self.texto += u"||%d\n" % (Articulos) temp = u"||%3.2f\n" % (Articulos * 100 / Paginas) self.texto += temp.replace(".", ",") self.texto += u"||%d\n" % (Ficheros) temp = u"||%3.2f\n" % (Ficheros / Articulos) self.texto += temp.replace(".", ",") self.texto += u"||%d\n" % (Usuarios) self.texto += u"||%d\n" % (Activos) self.texto += u"||%d\n" % (Admin) # Actualizamos acumuladores self.TotalArticulos += Articulos self.TotalFicheros += Ficheros self.TotalPaginas += Paginas self.TotalEdiciones += Ediciones self.TotalUsuarios += Usuarios self.TotalActivos += Activos self.TotalAdministradores += Admin return True def _LeerPaginasLargas(self, URLBase, APIPath): # Un poco cutre hacerlo de esta forma... # Habría que mejorarlo mucho Expresion1 = r"\"apfrom\";s:[0-9]*:\"(?P<sig>.*)\";\}\}" Expresion2 = r"\"allpages\";a:(?P<paginas>.*):\{[i\}]" for i in [65535, 32767, 16383, 8191, 4095]: # for i in [8191]: wikipedia.output(u"Buscando páginas de más de %d bytes" % i) Contador = 0 try: Estadisticas = urlopen(u'http://%s%s?action=query&list=allpages&aplimit=500&apminsize=%d&format=php' % (URLBase, APIPath, i)).read() except: return False Fin = False while not Fin: param = re.search(Expresion1, Estadisticas) try: Siguiente = quote(param.group(u"sig")) wikipedia.output(u"Leido hasta: %s" % Siguiente) try: Estadisticas = urlopen(u'http://%s%s?action=query&list=allpages&aplimit=500&apminsize=%d&format=php&apfrom=%s' % (URLBase, APIPath, i, Siguiente)).read() except: return False Contador += 500 except: try: param = re.search(Expresion2, Estadisticas) Contador += int(param.group(u"paginas")) except: return False Fin = True self.texto += u"||%d\n" % (Contador) temp = u"||%3.2f\n" % (Contador * 100 / self.ArticulosActual ) self.texto += temp.replace(".", ",") wikipedia.output(u"--> %d páginas encontradas" % Contador); return True def treat(self): self._EscribirCabecera() # Datos de las wikis Uncyclopedia for i in self.site.languages(): # for i in ["es"]: self.ArticulosActual = 0 wikipedia.output(u"\n>>> \03{yellow}%s\03{default} - \03{lightpurple}%s\03{default} <<<" % (i, self.site.family.langs[i])) wikipedia.output(u'http://%s%s?title=Special:Statistics&action=raw' % (self.site.family.langs[i], self.site.family.path(i))) # Nueva fila para la wiki self.texto += u"|-\n||[[:%s:]]\n" % i if not self._LeerEstadisticas(self.site.family.langs[i], self.site.family.path(i)): self.texto += u"||\n||\n||\n||\n||\n||\n||\n||\n||\n||\n||\n||\n||\n||\n||\n||\n||\n||\n||\n||\n" #Fila vacía wikipedia.output(u'ERROR -> Al acceder a [[special:Statistics]]') continue if not self._LeerPaginasLargas(self.site.family.langs[i], self.site.family.apipath(i)): # self.texto += u"||\n||\n||\n||\n||\n||\n||\n||\n||\n||\n" #Fila vacía wikipedia.output(u'ERROR -> Al acceder al API') #Cerramos tabla self.texto += u"\n|}\n" # Escribimos los totales self._EscribirTotales() # Ahora lo hacemos con las wikis listadas al principio if self.AnadirOtrasWikis: self.TotalArticulos = 0 self.TotalFicheros = 0 self.TotalPaginas = 0 self.TotalEdiciones = 0 self.TotalUsuarios = 0 self.TotalActivos = 0 self.TotalAdministradores = 0 self.ArticulosActual = 0 self._EscribirCabecera() for i in OtrasWikis: self.ArticulosActual = 0 wikipedia.output(u"\n>>> \03{yellow}%s\03{default} - \03{lightpurple}%s\03{default} <<<" % (i, OtrasWikis[i][1])) wikipedia.output(u'http://%s%s?title=Special:Statistics&action=raw' % (OtrasWikis[i][1], OtrasWikis[i][2])) # Nueva fila para la wiki self.texto += u"|-\n||[[%s|%s]]\n" % (i, OtrasWikis[i][0]) if not self._LeerEstadisticas(OtrasWikis[i][1], OtrasWikis[i][2]): self.texto += u"||\n||\n||\n||\n||\n||\n||\n||\n||\n||\n||\n||\n||\n||\n||\n||\n||\n||\n||\n||\n" #Fila vacía wikipedia.output(u'ERROR -> Al acceder a [[special:Statistics]]') continue if not self._LeerPaginasLargas(OtrasWikis[i][1], OtrasWikis[i][3]): # self.texto += u"||\n||\n||\n||\n||\n||\n||\n||\n||\n||\n" #Fila vacía wikipedia.output(u'ERROR -> Al acceder al API') self.texto += u"|}\n" self._EscribirTotales() self.texto += u"===Leyenda===\n" self.texto += u";Leng\n" self.texto += u":Lenguaje de la wiki\n" self.texto += u";Edic\n" self.texto += u":Número total de ediciones\n" self.texto += u";Pág\n" self.texto += u":Número total de páginas creadas\n" self.texto += u";Ed/Pg\n" self.texto += u":Ediciones por página\n" self.texto += u";Art\n" self.texto += u":Número de artículos (En el espacio principal, con un enlace y no se que otra restricción)\n" self.texto += u";%\n" self.texto += u":Porcentaje de artículos sobre el total de páginas\n" self.texto += u";Fich\n" self.texto += u":Número de ficheros (imágenes, sonidos, etc) subidos a la wiki\n" self.texto += u";Fch/Art\n" self.texto += u":Número de ficheros por artículos (es decir, más o menos el número de imágenes en cada artículo)\n" self.texto += u";Usu\n" self.texto += u":Número de usuarios\n" self.texto += u";Act\n" self.texto += u":Número de usuarios activos (-1 es que tienen desactivado algo seguramente)\n" self.texto += u";Adm\n" self.texto += u":Número de administradores\n" self.texto += u";>64kb, %\n" self.texto += u":Artículos de más de 64kb y su porcentaje sobre el total\n" self.texto += u";>32kb, %\n" self.texto += u":Artículos de más de 32kb y su porcentaje sobre el total\n" self.texto += u";>16kb, %\n" self.texto += u":Artículos de más de 16kb y su porcentaje sobre el total\n" self.texto += u";>8k, %\n" self.texto += u":Artículos de más de 8kb y su porcentaje sobre el total\n" self.texto += u";>4kb, %\n" self.texto += u":Artículos de más de 4kb y su porcentaje sobre el total\n" self.texto += u"===Notas===\n" self.texto += u"La tabla ya no la hago a mano, he hecho un bot con el pywikipediabot. " self.texto += u"Así me evito tener que estar haciéndolo a mano y las posibles fallos que puda tener\n\n" self.texto += u"El kB está comparado como lo es informáticamente, es decir: 65.536B, 32.768B, 16.384B," self.texto += u"8.192B y 4096B respectivamente.\n\n" self.texto += u"Las que no tienen nada de nada... Será que está mal configurada en el bot o " self.texto += u"que ha dado error al intentar acceder\n\n" self.texto += u"Aquellas en las que no se tienen los tamaños de los artículos s que no tienen activado" self.texto += u"el api.php (Tiene que escribir <code><nowiki>$wgEnableAPI=true;<" + "/nowiki><code> en " self.texto += u"LocalSettings.php y solo lo pueden hacer quien tenga acceso al servidor donde esté instalada\n\n" self.texto += u";Para las de Wikia\n" self.texto += u"*El número de usuarios son el total de toda Wikia\n" fichero = codecs.open('salida.txt', mode='w', errors='strict', encoding='utf-8', buffering=1) fichero.write(self.texto) fichero.close page=wikipedia.Page(self.site, u"User:Chixpy/Estadistitis") try: page.put(self.texto, minorEdit = False) except wikipedia.LockedPage: wikipedia.output(u"Página bloqueada: %s" % page.aslink()) except wikipedia.EditConflict: wikipedia.output(u'Conflicto de edición: %s' % (page.title())) except wikipedia.SpamfilterError, error: wikipedia.output(u'Puto filtro anti-spam: %s - %s' % (page.title(), error.url)) def main(): bot = BasicBot() bot.run() if __name__ == "__main__": try: main() finally: wikipedia.stopme()