#!/usr/bin/perl -w

use utf8;
use strict;
use warnings;

BEGIN {
    unshift @INC, ( $ENV{'POPHOME'} || '@POPHOME@' ) . '/lib'
      unless $ENV{'KUNDE_NO_PERLPATH'};
}

use Dbase::Getopt;
use Dbase::Help qw(:readonly DoSelect qquote);

GetOptions(
    'beginn-spalte=s' => \( my $Beginn = 'beginn' ),
    'ende-spalte=s'   => \( my $Ende   = 'ende' ),
    'schluessel=s' => \( my $Schluessel = "CONCAT_WS('; ', name, seriennr)" ),
    'tabelle=s'    => \( my $Tabelle    = 'hardware' ),
    'bedingung=s'  => \( my $Where      = 'seriennr IS NOT NULL' ),
    'zeige=s'      => \(
        my $Zeige =
"CONCAT_WS( '; ', id, kunde, name, seriennr, FROM_UNIXTIME(beginn), FROM_UNIXTIME(ende) )"
    ),
);

my $where = length $Where > 0 && <<_;
	WHERE    $Where
_

DoSelect {

    my ($schluessel) = @_;
    my ( $_beginn, $_ende, $_zeige );
    DoSelect {
        my ( $beginn, $ende, $zeige ) = @_;
        if ( defined $beginn && defined $ende && $ende < $beginn ) {
            print "$Ende < $Beginn: $zeige\n";
        }
        elsif (
## Please see file perltidy.ERR
            defined $_zeige
            and (   !defined $beginn || !defined $_ende || $beginn < $_ende
                and !defined $ende   || !defined $_beginn || $ende > $_beginn
                or !defined $ende    || !defined $_beginn || $ende > $_beginn
                and !defined $beginn || !defined $_ende   || $beginn < $_ende )
          )
        {
            print "\nOverlap:\n$_zeige\n$zeige\n";
        }
        ( $_beginn, $_ende, $_zeige ) = @_;
      }
      <<_;
	SELECT   $Beginn, $Ende, $Zeige
	FROM     $Tabelle
$where	     AND $Schluessel = ${\ qquote($schluessel) }
	ORDER BY $Beginn
_

  }
  <<_;
	SELECT   $Schluessel Schluessel, COUNT(*) Anzahl
	FROM     $Tabelle
$where	GROUP BY Schluessel
	HAVING   Anzahl > 1
	ORDER BY $Beginn
_

__END__

=head1 NAME

find_overlaps - zeitlich überlappende Datensätze ausfindig machen

=head1 BESCHREIBUNG

Dieses Tool kann Tabellen mit Objekten mit Beginn- und Ende-Datum nach
Einträgen durchforsten, die sich zeitlich überlappen, und die es so also
eigentlich nicht geben dürfte.

=head1 OPTIONEN

=head2 beginn-spalte=s

Name des Datenbankfeldes, in dem das Beginn-Datum (als Unix-Timestamp) steht;
Default: C<beginn>

=head2 ende-spalte=s

Name des Datenbankfeldes, in dem das Ende-Datum (als Unix-Timestamp) steht;
Default: C<ende>

=head2 schluessel=s

SQL-Schnipsel, der eine eindeutige Zeichenkette für alle vergleichbaren Objekte
erzeugt;
Default: C<CONCAT_WS('; ', name, seriennr)>

=head2 bedingung=s

SQL-Schnipsel, der in den C<WHERE>-Teil eingebaut wird, um Datensätze
auszuschließen;
Default: C<seriennr IS NOT NULL>

=head2 tabelle=s

Datenbanktabelle, die untersucht werden soll;
Default: C<hardware>

=head2 zeige=s

SQL-Schnipsel, der angibt, welche Felder ausgegeben werden sollen;
Default: C<CONCAT_WS( '; ', id, kunde, name, seriennr, FROM_UNIXTIME(beginn), FROM_UNIXTIME(ende) )>

=head2 help|?

um (nur) diese Dokumentation anzeigen zu lassen

