package Lire::Report::Entry;

use strict;

use vars qw/ $VERSION @ISA /;

use Lire::XMLUtils qw/xml_encode/;

BEGIN {
    ($VERSION)	= '$Revision: 1.3 $' =~ m!Revision: ([.\d]+)!;
}

=pod

=head1 NAME

Lire::Report::Entry - Interface to subreport's data.

=head1 SYNOPSIS

    foreach my $name ( $entry->names ) {
	print "Name: ", $name->{content}, "\n";
    }

    foreach my $value ( $entry->values ) {
	if ( ref $value eq 'Lire::Report::Group' ) {
	    # Value is a group
	    foreach my $e ( $value->entries ) {
		print_entry( $e );
	    }
	} else {
	    print "Value: ", $value->{content}, "\n";
	}
    }

=head1 DESCRIPTION

The Lire::Report::Entry objects are used to hold the subreport's data. 

=head1 CONSTRUCTOR

=head2 new()

Creates a new empty Lire::Report::Entry. Use the add_name(), add_group() and
add_value() methods to fill this entry.

=cut

sub new {
    my $proto = shift;
    my $class = ref $proto || $proto;

    bless {
	   names	 => [],
	   values	 => [],
	  }, $class;
}

=pod

=head1 OBJECT METHODS

=head2 names()

Returns the names of the entry. This is an array of hashes. The name's
hash contains the following keys:

=over 4

=item content

That's the actual content of the name element. This contains the name
in a format suitable for display.

=item value

This contains the unformatted value of the name. For example, when the
name is a time string, this attribute will contains the time in
seconds since epoch.

=item range

For some names, the actual content express a range (time, size, etc.).
This attribute contains the length of the range.

=back

=cut

sub names {
    @{$_[0]{names}};
}

=pod

=head2 add_name( $content, [$value], [$range] )

Adds a new name to this entry. Consult the documentation of the
names() method for a description of the meaning of the various
parameters which have the same meaning as the keys with the same
name.

=cut

sub add_name {
    my ( $self, $content, $value, $range ) = @_;

    $content = "" unless defined $content;
    $value = $content unless defined $value;

    my %n = (
	     content => $content,
	     value   => $value,
	    );
    $n{range} = $range if defined $range;

    push @{$self->{names}}, \%n; 
}

=pod

=head2 values()

Returns the names of the entry. This is an array of hashes or objects. If the value is an hash, it has the following keys:

=over 4

=item content

That's the actual content of the value element. This contains the
value in a format suitable for display.

=item value

This contains the unformatted value. For example, when bytes are
displayed using "1M" or "1.1G", this will contains the value in bytes.

=item total

This is used by values that represent an average. It contains the
total which makes up the average.

=item n

This is used by values that represent an average. It contains the
total which was used in the division to compute the average.

=back

Some values are Lire::Report::Group objects when there is nested data.

=cut

sub values {
    @{$_[0]{values}};
}

=pod

=head2 add_group( $group )

Adds a new group to this entry. The $group parameter must be of type
Lire::Report::Group.

=cut

sub add_group {
    croak( "group isn't of type Lire::Report::Group" )
      unless ref $_[1] eq 'Lire::Report::Group';

    push @{$_[0]{values}}, $_[1];
}

=pod

=head2 add_value( $content, [$value], [$total], [$n] )

Adds a new value to this entry. Consult the documentation of the
values() method for a description of the meaning of the various
parameters which have the same meaning as the keys with the same
names.

=cut

sub add_value {
    my ( $self, $content, $value, $total, $n ) = @_;

    $content = "" unless defined $content;
    $value = $content unless defined $value;

    my %v = (
	     content => $content,
	     value   => $value,
	    );
    $v{total} = $total if defined $total;
    $v{n} = $n if defined $n;

    push @{$self->{values}}, \%v; 
}


sub write_report {
    my ( $self, $fh, $indent ) = @_;

    $fh ||= *STDOUT;
    my $pfx = ' ' x $indent;

    print $fh "$pfx<lire:entry>\n";

    foreach my $n ( $self->names ) {
	print $fh "$pfx <lire:name";
	print $fh ' value="', xml_encode( $n->{value} ), '"',
	  if $n->{value} ne $n->{content};
	print $fh qq! range="$n->{range}"!
	  if defined $n->{range};
	print $fh ">", xml_encode( $n->{content} ), "</lire:name>\n";
    }

    foreach my $v ( $self->values ) {
	if ( ref $v eq 'Lire::Report::Group' ) {
	    $v->write_report( $fh, $indent + 1 );
	} else {
	    print $fh "$pfx <lire:value";
	    print $fh qq! total="$v->{total}"!
	      if defined $v->{total};
	    print $fh qq! n="$v->{n}"!
	      if defined $v->{n};
	    print $fh qq! value="$v->{value}"!
	      if $v->{value} ne $v->{content};
	    print $fh ">$v->{content}</lire:value>\n";
	}
    }

    print $fh "$pfx</lire:entry>\n";
}

# keep perl happy
1;

=pod

__END__

=pod

=head1 SEE ALSO

Lire::ReportParser::ReportBuilder(3pm) Lire::Report(3pm)
Lire::Report::Subreport(3pm) Lire::Report::Section(3pm)
Lire::Report::Group(3pm)

=head1 VERSION

$Id: Entry.pm,v 1.3 2002/06/23 19:23:40 vanbaal Exp $

=head1 COPYRIGHT

Copyright (C) 2002 Stichting LogReport Foundation LogReport@LogReport.org

This file is part of Lire.

Lire is free software; you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
the Free Software Foundation; either version 2 of the License, or
(at your option) any later version.

This program is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
GNU General Public License for more details.

You should have received a copy of the GNU General Public License
along with this program (see COPYING); if not, check with
http://www.gnu.org/copyleft/gpl.html or write to the Free Software 
Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA  02111, USA.

=head1 AUTHOR

Francis J. Lacoste <flacoste@logreport.org>

=cut
