Index: server/trunk/web/Makefile.PL
===================================================================
--- server/trunk/web/Makefile.PL	(revision 264)
+++ server/trunk/web/Makefile.PL	(revision 265)
@@ -30,4 +30,5 @@
 requires 'Catalyst::View::TT' => '0';
 requires 'Catalyst::View::JSON' => '0';
+requires 'Catalyst::View::GD' => '0';
 requires 'Catalyst::Model::DBIC::Schema';
 requires 'Catalyst::Authentication::Store::DBIx::Class';
Index: server/trunk/web/Sophie.spec.in
===================================================================
--- server/trunk/web/Sophie.spec.in	(revision 264)
+++ server/trunk/web/Sophie.spec.in	(revision 265)
@@ -27,4 +27,5 @@
 BuildRequires: perl(Catalyst::View::TT)
 BuildRequires: perl(Catalyst::View::JSON)
+BuildRequires: perl(Catalyst::View::GD)
 BuildRequires: perl(DBIx::Class)
 BuildRequires: perl(Catalyst::Plugin::Compress::Zlib)
@@ -37,4 +38,5 @@
 BuildRequires: perl(XML::Simple)
 BuildRequires: perl(XML::RSS)
+BuildRequires: perl(GD::Graph)
 
 Requires: perl(Catalyst)
@@ -49,4 +51,6 @@
 Requires: perl(Catalyst::Plugin::Prototype)
 Requires: perl(Catalyst::View::TT)
+Requires: perl(Catalyst::View::JSON)
+Requires: perl(Catalyst::View::GD)
 Requires: perl(Catalyst::Plugin::Compress::Zlib)
 Requires: perl-Catalyst-Plugin-Server
@@ -54,4 +58,5 @@
 Requires: perl(Catalyst::Authentication::Store::DBIx::Class)
 Requires: perl(XML::RSS)
+Requires: perl(GD::Graph)
 # Requires: apache-mod_fastcgi
 # Requires: perl(FCGI)
Index: server/trunk/web/lib/Sophie.pm
===================================================================
--- server/trunk/web/lib/Sophie.pm	(revision 264)
+++ server/trunk/web/lib/Sophie.pm	(revision 265)
@@ -52,4 +52,9 @@
         xml_encoding => 'UTF-8',
         show_errors => 1,
+    },
+    'View::GD' => {
+        gd_image_type         => 'png',        # defaults to 'gif'
+        gd_image_content_type => 'images/png', # defaults to 'image/$gd_image_type'
+        gd_image_render_args  => [ 5 ],        # defaults to []
     },
 
Index: server/trunk/web/lib/Sophie/Controller/Root.pm
===================================================================
--- server/trunk/web/lib/Sophie/Controller/Root.pm	(revision 264)
+++ server/trunk/web/lib/Sophie/Controller/Root.pm	(revision 265)
@@ -110,7 +110,12 @@
 sub  end : Private {
     my ( $self, $c ) = @_;
+    if (!$c->stash->{current_view}) {
+        if (ref($c->stash->{xmlrpc}) eq 'HASH' &&
+            $c->stash->{xmlrpc}{graph}) {
+            $c->stash->{current_view} = 'GD';
+        }
+    }
     if (!$c->req->xmlrpc->method) {
         $c->forward('_end');
-    } elsif (!$c->stash->{current_view}) {
     }
     $c->stash->{data} = $c->stash->{xmlrpc};
Index: server/trunk/web/lib/Sophie/Controller/Statistics.pm
===================================================================
--- server/trunk/web/lib/Sophie/Controller/Statistics.pm	(revision 265)
+++ server/trunk/web/lib/Sophie/Controller/Statistics.pm	(revision 265)
@@ -0,0 +1,44 @@
+package Sophie::Controller::Statistics;
+use Moose;
+use namespace::autoclean;
+
+BEGIN {extends 'Catalyst::Controller'; }
+
+=head1 NAME
+
+Sophie::Controller::Statistics - Catalyst Controller
+
+=head1 DESCRIPTION
+
+Catalyst Controller.
+
+=head1 METHODS
+
+=cut
+
+
+=head2 index
+
+=cut
+
+sub index :Path :Args(0) {
+    my ( $self, $c ) = @_;
+
+    $c->response->body('Matched Sophie::Controller::Statistics in Statistics.');
+}
+
+
+=head1 AUTHOR
+
+Olivier Thauvin
+
+=head1 LICENSE
+
+This library is free software. You can redistribute it and/or modify
+it under the same terms as Perl itself.
+
+=cut
+
+__PACKAGE__->meta->make_immutable;
+
+1;
Index: server/trunk/web/lib/Sophie/Controller/Statistics/Chat.pm
===================================================================
--- server/trunk/web/lib/Sophie/Controller/Statistics/Chat.pm	(revision 265)
+++ server/trunk/web/lib/Sophie/Controller/Statistics/Chat.pm	(revision 265)
@@ -0,0 +1,79 @@
+package Sophie::Controller::Statistics::Chat;
+use Moose;
+use namespace::autoclean;
+
+BEGIN {extends 'Catalyst::Controller'; }
+
+=head1 NAME
+
+Sophie::Controller::Statistics::Chat - Catalyst Controller
+
+=head1 DESCRIPTION
+
+Catalyst Controller.
+
+=head1 METHODS
+
+=cut
+
+
+=head2 index
+
+=cut
+
+sub index :Path :Args(0) {
+    my ( $self, $c ) = @_;
+
+}
+
+sub command_graph : Local {
+    my ($self, $c) = @_;
+
+    my $graph = {
+        type => 'lines',
+        size => [ 640, 240 ],
+    };
+
+    my %data;
+    my %cmd;
+    foreach ($c->model('Base::ChatStat')->search(
+            {},
+            { order_by => [ qw(day cmd) ] })->all) {
+        $cmd{$_->cmd} = 1;
+        $data{$_->day}{$_->cmd} = $_->count;
+    }
+
+    my @days;
+    my %cmd_count;
+    foreach my $d (sort keys %data) {
+        push(@days, $d);
+        foreach (sort keys %cmd) {
+            push(@{ $cmd_count{$_} }, $data{$d}{$_} || 0);
+        }
+    }
+
+    $graph->{plot} = [
+        \@days,
+        map { $cmd_count{$_} } sort keys %cmd_count,
+    ];
+    $graph->{legend} = [ sort keys %cmd_count ];
+
+    $c->stash->{xmlrpc} = {
+        graph => $graph,
+    };
+}
+
+=head1 AUTHOR
+
+Olivier Thauvin
+
+=head1 LICENSE
+
+This library is free software. You can redistribute it and/or modify
+it under the same terms as Perl itself.
+
+=cut
+
+__PACKAGE__->meta->make_immutable;
+
+1;
Index: server/trunk/web/lib/Sophie/View/GD.pm
===================================================================
--- server/trunk/web/lib/Sophie/View/GD.pm	(revision 265)
+++ server/trunk/web/lib/Sophie/View/GD.pm	(revision 265)
@@ -0,0 +1,48 @@
+package Sophie::View::GD;
+use Moose;
+use namespace::autoclean;
+use GD::Graph;
+
+extends 'Catalyst::View::GD';
+
+=head1 NAME
+
+Sophie::View::GD - Catalyst View
+
+=head1 DESCRIPTION
+
+Catalyst View.
+
+=cut
+
+sub process {
+    my ($self, $c) = @_;
+
+    my $graph = $c->stash->{xmlrpc}{graph};
+
+    my $gdclass = 'GD::Graph::' . $graph->{type};
+    eval "require $gdclass;";
+    my $gd = $gdclass->new(@{ $graph->{size} || [ 100, 100 ]});
+
+    $gd->set(%{ $graph->{set} || {} });
+    $gd->set_legend(@{ $graph->{legend} }) if ($graph->{legend});
+
+    $c->stash->{gd_image} = $gd->plot($graph->{plot});
+
+    $self->SUPER::process($c);
+}
+
+=head1 AUTHOR
+
+Olivier Thauvin
+
+=head1 LICENSE
+
+This library is free software. You can redistribute it and/or modify
+it under the same terms as Perl itself.
+
+=cut
+
+__PACKAGE__->meta->make_immutable(inline_constructor => 0);
+
+1;
Index: server/trunk/web/root/templates/html/statistics/chat/index.html
===================================================================
--- server/trunk/web/root/templates/html/statistics/chat/index.html	(revision 265)
+++ server/trunk/web/root/templates/html/statistics/chat/index.html	(revision 265)
@@ -0,0 +1,5 @@
+<!-- $Id$ -->
+<p>Bot command usage</p>
+
+<img src="[% c.uri_for('/statistics', 'chat', 'command_graph') %]">
+
Index: server/trunk/web/t/controller_Statistics-Chat.t
===================================================================
--- server/trunk/web/t/controller_Statistics-Chat.t	(revision 265)
+++ server/trunk/web/t/controller_Statistics-Chat.t	(revision 265)
@@ -0,0 +1,10 @@
+use strict;
+use warnings;
+use Test::More;
+
+BEGIN { use_ok 'Catalyst::Test', 'Sophie' }
+BEGIN { use_ok 'Sophie::Controller::Statistics::Chat' }
+
+ok( request('/statistics/chat')->is_success, 'Request should succeed' );
+ok( request('/statistics/chat/command_graph')->is_success, 'Request should succeed' );
+done_testing();
Index: server/trunk/web/t/controller_Statistics.t
===================================================================
--- server/trunk/web/t/controller_Statistics.t	(revision 265)
+++ server/trunk/web/t/controller_Statistics.t	(revision 265)
@@ -0,0 +1,9 @@
+use strict;
+use warnings;
+use Test::More;
+
+BEGIN { use_ok 'Catalyst::Test', 'Sophie' }
+BEGIN { use_ok 'Sophie::Controller::Statistics' }
+
+ok( request('/statistics')->is_success, 'Request should succeed' );
+done_testing();
Index: server/trunk/web/t/view_GD.t
===================================================================
--- server/trunk/web/t/view_GD.t	(revision 265)
+++ server/trunk/web/t/view_GD.t	(revision 265)
@@ -0,0 +1,7 @@
+use strict;
+use warnings;
+use Test::More;
+
+BEGIN { use_ok 'Sophie::View::GD' }
+
+done_testing();
