Usuario:JoaquinFerrero/Medallero2008

De Wikipedia, la enciclopedia libre

Programa para la actualización automática del Medallero de los Juegos Olímpicos de Pekín 2008[editar]

#!/usr/bin/perl
#
# medallero.pl
#
# Joaquín Ferrero
#
# Descripción:
#  Actualización automática del medallero olímpico Pekín 2008 en Wikipedia
#
# Entrada: ninguna
# Salida:  ninguna
#
# Historial:
#   11-ago-2008 : Versión inicial
#   16-ago-2008 : Corrección de estilo, simplificación
#

## Librerías
use LWP::Simple;
use HTML::TableParser;
use MediaWiki;

## Opciones de ejecución
#use strict;                     # Restrict unsafe constructs
#use warnings;                   # Control optional warnings
#use diagnostics;                # Produce verbose warning diagnostics
no warnings;

## Constantes
my $WIKI_TEST_PAGE     = 'Wikipedia:Zona de pruebas';
my $WIKI_PEKIN08_PAGE  = 'Juegos Olímpicos de Pekín 2008';
my $WIKI_MEDALS_RESULT = 'Anexo:Medallero de los Juegos Olímpicos de Pekín 2008';
my $URL_MEDALS_RESULTS = 'http://results.beijing2008.cn/WRM/ENG/INF/GL/95A/GL0000000.shtml';
my $notice = qq(<includeonly><!-- Para cerrar la tabla en el artículo principal -->|}</includeonly><noinclude><!--
Para que automáticamente se genere una lista de sólo 10 países en el artículo principal, mover el tag "noinclude"
tras los 10 mejores países clasificados -->\n);

                                # Para hacer pruebas, cambiar esta variable a $WIKI_TEST_PAGE
                                # En producción, cambiarla por $WIKI_MEDALS_RESULT
my $wiki_page_final    = $WIKI_MEDALS_RESULT;

## Objetos
my $MediaWiki = MediaWiki->new;
my $HTML_TableParser = HTML::TableParser->new(
    [{
        id  => '2',
        row => \&process_row,
    }],
    {
        Decode     => 1,
        DecodeNBSP => 1,
        Trim       => 1,
        Chomp      => 1,
    },
);

## Conexión con Wikipedia
$MediaWiki->setup({
    'bot'  => {
            user => 'JoaquinFerrero',
            pass => 'xxxxxxxxxx',
    },
    'wiki' => {
            host => 'es.wikipedia.org',
            path => 'w',
    },
});

## Lista de los países participantes
my $wiki_page_text = $MediaWiki->text($WIKI_PEKIN08_PAGE);
die "ERROR: No encuentro la página de los Juegos" if $wiki_page_text !~ /\*\{\{BanderaOL\|/;

my %COUNTRIES;
while ($wiki_page_text =~ /BanderaOL\|(.+?)\|(...)(\|alt=.+?)?\|ed=/simog) {
    $COUNTRIES{$2} = "{{BanderaOL|$1|$2$3|ed=Pekín 2008}}";
}

## Página con los resultados oficiales
my $medals_results_page = get($URL_MEDALS_RESULTS);
die "ERROR: No conseguí los resultados de medallas" unless defined $medals_results_page;

## Procesamiento de cada fila de la tabla de resultados
my @medals_results_table;
sub process_row {
    my ( $id, $line, $columns, $udata ) = @_;
    my @columns = map { s/\s+//g; $_ } @$columns;   # Filtrar espacios

    return if $columns[0] !~ /^\d/;

    my ($country_code, $country) = split q{-}, $columns[1];
    $country = $COUNTRIES{$country_code};

    # Número de medallas, a número entero
    my @medals = map { 0 + $_ } @columns[-5 .. -2];

    push @medals_results_table, [ $columns[0], $country, @medals ];
}

## Interpretación de la tabla de resultados
$HTML_TableParser->parse( $medals_results_page );

## Inicio del medallero
my $new_wiki_medals_section  = <<"EOF_MEDALS_SECTION";
== Medallero ==
</noinclude><!--

        ATENCIÓN: La tabla se actualiza de forma automática cada 5min.

            Cualquier cambio realizado de forma manual se perderá.

-->{| {{Medallero|style=text-align:right;}}
EOF_MEDALS_SECTION

## Contenido del medallero
my $is_notice_set;
my @medals_totals;
foreach my $row (@medals_results_table) {
    if ($row->[0] > 10 and !$is_notice_set++) {
        $new_wiki_medals_section .= $notice;
    }

    $new_wiki_medals_section
        = $new_wiki_medals_section
        . "|-\n"
        . "|'''$row->[0]'''\n"
        . join( q{||align=center|}, "|align=left|$row->[1]", @{$row}[2 .. 5] )
        . "\n"
        ;

    map { $medals_totals[$_ - 2] += $row->[$_] } 2 .. 5;  # Cálculo de los totales
}

## Fin del medallero
$new_wiki_medals_section
    = $new_wiki_medals_section
    . "|-\n"
    . join(q{ || align=center| }, '!colspan=2| Total', @medals_totals) . "\n"
    . "|}\n"
    . "\n"
    ;

## Actualización de la página del medallero
$wiki_page_text = $MediaWiki->text($wiki_page_final);
die "ERROR: No conseguí la página del medallero" if not $wiki_page_text;

my $wiki_page_before = $wiki_page_text;         # Cómo era antes

if ($wiki_page_text =~ s/== Medallero ==.+?(?=^==)/$new_wiki_medals_section/sm) {
    $MediaWiki->{watch}   = 1;
    $MediaWiki->{summary} = 'Actualización automática del medallero.';

    if ($wiki_page_text ne $wiki_page_before) {
        $MediaWiki->text($wiki_page_final, $wiki_page_text);
    }
}

__END__