# -*-perl-*-

# $Id: DepDB.plm,v 1.4 2004/10/13 16:06:01 thomas Exp $

# $Log: DepDB.plm,v $
# Revision 1.4  2004/10/13 16:06:01  thomas
# db version
#
# Revision 1.3  2004/07/15 21:31:03  thomas
# need FileHandle
#
# Revision 1.2  2004/06/08 14:21:34  thomas
# Change external data file format (XML reads were failing)
# Write the output XML ourselves (don't use XMLout)
#
# Revision 1.1  2004/03/22 17:38:13  thomas
# Add dependency database module
#

=head1 NAME

B<DepDB.pm> - Maintain dependency information

=head1 SYNOPSIS

  use What::DepDB;

  my $dep = new DepDB (%opts);

  my @hosts = $dep->find ();
  my @data = $dep->find ($host);
  my $text = $attrs->lock ($host);
  my $ret = $attrs->unlock ();
  my $ret = $dep->set ($host, @data);
  my $ret = $dep->drop ($host);

  my @key_names = $dep->find_index ();
  my @key_values = $dep->find_index ($host_name);
  my @hosts = $dep->find_index ($host_name, $host_value);

  $dep->save(%args);

=head1 DESCRIPTION

This module updates, queries, loads and saves a database of B<What>
dependency information.

The DepDB database associates an array of hashes with a particular key
(usually a host name).  The hashes contain information about modules
included by the host.  This module assumes no information regarding
what keys are contained in the hashes.  The module then permits
retrieving information about the key (host), as well as lookup by
either a hash attribute name or a hash attribute name and value.  By
convention, the attributes stored are:

=over 4

=item name

The value of the B<name> attribute from the B<include> directive.

=item basename

The value of the B<name> attribute with any directory and/or extension
information removed.

=item filename

The file that was ultimately found to satisfy the include.

=back

This module does not depend on any other B<What> modules.  Therefore,
it is suitable for use in programs external to B<What>.

The methods available to query and manipulate this information follow.

=over 4

=cut

package What::DepDB;

use strict;
use Text::ParseWords;
use CSL::DBs;
use CSL::Pg;
use DBI;
use Class::Phrasebook::SQL;
use Log::LogLite;

use base qw(What::MultiData);

###############################################################################
# Convert a What include_tree data structure to a DepDB data array
# Return an arrayref of DepDB data.
sub inc_2_dep {
  my $self = shift;
  my $inctree = shift;

  my $inchash = {};
  inc_2_dep_r ($inchash, $inctree);

  my (@depdata, $name, $file, $basename);
  foreach $name (sort keys %$inchash) {
    $basename = $name;
    $basename =~ s;.*/;;;
    $basename =~ s/\.xml//;
    foreach $file (keys %{$inchash->{$name}}) {
      push @depdata, {
		      name => $name,
		      basename => $basename,
		      file => $file,
		     };
    }
  }
  return @depdata;
}

# inctree is the include tree returned from What::include (or a subtree)
# (input to this function)
# inchash is a hash representation of the same data
# (output from this function)
sub inc_2_dep_r {
  my $inchash = shift;
  my $inctree = shift;
  my $file;

  exists ($inctree->{kids}) or return;
  foreach (sort keys %{$inctree->{kids}}) {
    $file = $inctree->{kids}->{$_}->{filename};
    $inchash->{$_}->{$file} = 1;
    inc_2_dep_r ($inchash, $inctree->{kids}->{$_});
  }

}


###############################################################################
# Return the array of hashes that correspond to the index entries
# to be created for the given dep data.

sub getindex {
  my $self = shift;
  my $key = shift;
  my $data = shift;

  my $index = [];

  return @$data;
}


###############################################################################

1;

# End the documentation

=back

=head1 SEE ALSO

What::Command::listincludes

What::MultiData

=cut
