#!/usr/bin/perl -w
use strict;
use Time::localtime;
my $version = "1.3 TEST";
if ($#ARGV > -1) {
help();
exit 1;
}
# Idee: Mailverschicken, Doku und Lockfile auslagern. Kann per ShellScript
# usw. geschehen! :-)
# Ziel: siehe test1.txt (unten)
# (alle Termine und Geburtstage usw. sortiert hintereinander)
#
# Strategie: Alle Ausgabezeilen in ein Array schreiben und sortieren:
#
# 2 Array: 1. Array: Alle Ausgabezeilen
# 2. Array: x=Zeile von Array 1, y = Datums-Differenz
#
# sortiere 2.Array nach Datums.Differenz, dann entsprechend mit x die
# Ausgabezeilen auslesen. (in foreach... sort keys...)
# 1.1.2000 Fehler korrigiert: Monatl. Termine am Monatsanfang wurden nicht
# angezeigt, wenn man am Ende des Vormonats ist.
# ----------------------------------------------------------------------
# Einrichten der benutzten Dateinamen:
my $os = "LINUX"; # "WIN9X"
my $basedir = $ENV{HOME};
my $termindaten = "$basedir/.termine";
my $mailtxt = "$basedir/.termine_mailtxt";
chomp(my $empfaenger = `whoami`); # EMail-Adresse des Empfaengers per Systemkommando ermitteln
my $lockprefix = "$basedir/.termine_"; # Lockfile zusammenbauen: .termine_ttmmjjjj
if ($os eq "WIN9X") {
$basedir = "c:\\";
$termindaten = "$basedir\\termine.txt";
$mailtxt = "$basedir\\temp\\termine_mail.txt";
#chomp(my $empfaenger = `whoami`); # EMail-Adresse des Empfaengers per Systemkommando ermitteln
$lockprefix = "$basedir\\temp\\lockfile_termine_";
}
# ----------------------------------------------------------------------
# ----------------------------------------------------------------------
# Tagesdatum ermitteln:
my $nowdate = time(); # Aktuelle Zeit auslesen
my $d_now = localtime($nowdate) -> mday;
my $m_now = 1 + localtime($nowdate) -> mon;
my $y_now = 1900 + localtime($nowdate) -> year;
my $lockfile = "$lockprefix$y_now$m_now$d_now";
# ----------------------------------------------------------------------
my $ja = 1;
my $nein = 0;
# Anpassbare Werte fuer die ausgerichtete Ausgabe:
my $einruecken = " ";
my $normlaenge = 17;
# In dieses Array werden die auszugebenden Texte geschrieben:
my @ausgabearray = (); my $ausgabecnt = -1;
my %diffhash = (); # (ausgabecnt, diff)
# Variablen zur Steuerung des Verhaltens:
my $keinmodus = 0; my $termine = 1; my $woechentlich = 2;
my $monatlich = 3; my $feiertage = 4; my $geburtstage = 5;
my $modus = $keinmodus;
# Weitere Variablen:
my $zeile = "";
my %warnliste = ();
# Hashfeld zur Berechnung der Wochentags-Abstaende:
my %revdow = ("Mo" => "1", "Di" => "2", "Mi" => "3", "Do" => "4",
"Fr" => "5", "Sa" => "6", "So" => "7");
my @Monatsname = ("????", "Januar", "Februar", "Maerz", "April", "Mai", "Juni", "Juli",
"August", "September", "Oktober", "November", "Dezember" );
my @Wochentag = ("??", "Mo", "Di", "Mi", "Do", "Fr", "Sa", "So");
# ------------------------------------------------------------------------
# JulianDate von heute berechnen:
my $jdnow = MyJulianDate($d_now, $m_now, $y_now);
my $downow = day_of_week($jdnow); # 1..7 ??
# ------------------------------------------------------------------------
# Einlesen und Verarbeiten der Termindaten:
open(INPUT, "<$termindaten") || die "Konnte Termindatei $termindaten nicht oeffnen! :-(";
while() {
chomp($zeile = $_);
# Nur Zeilen verarbeiten, die laenger als 0 sind, und nicht mit "#" anfangen:
if (!( ($zeile =~ /^\#/) || (length($zeile) == 0) )) {
if ($zeile =~ /^Termine:/) { $modus = $termine; WarndatenExtrahieren(); }
elsif ($zeile =~ /^Woechentlich:/) { $modus = $woechentlich; WarndatenExtrahieren(); }
elsif ($zeile =~ /^W.chentlich:/) { $modus = $woechentlich; WarndatenExtrahieren(); }
elsif ($zeile =~ /^Monatlich:/) { $modus = $monatlich; WarndatenExtrahieren(); }
elsif ($zeile =~ /^Feiertage:/) { $modus = $feiertage; WarndatenExtrahieren(); }
elsif ($zeile =~ /^Geburtstage:/) { $modus = $geburtstage; WarndatenExtrahieren(); }
else {
# Termin auslesen und Meldung generieren:
my $tag = substr($zeile,0,2);
my $mon = substr($zeile,3,2);
my $jar = substr($zeile,6,4);
my $txt = substr($zeile,11);
# --------------------------------------------------------------------------
if ($modus == $termine) {
if (($tag eq "xx") || ($tag eq "XX") || ($tag eq "??")) {
# Termine der Form xx.12.1999 immer ausgeben, wenn Monat und Jahr ok sind :
if (($mon == $m_now) && ($jar == $y_now)) {
my $tmp = LFill("Im $Monatsname[$mon]",$normlaenge," ");
AusgabeHinzu(0, "$tmp: $txt");
}
}
else { # Normalfall: tt.mm.jjjj
my $jdthen = MyJulianDate($tag,$mon,$jar);
my $diff = $jdnow - $jdthen;
if (DiffIstWarnDiff($diff)) {
my $tmp = LFill(MakeDiffZeitString($diff ) . " (" . WochenTag($jdthen) . ")",$normlaenge," ") . ": $txt";
AusgabeHinzu($diff, "$tmp");
# print " Ein Termin: $tag $mon $jar $jdthen $jdnow $diff \n";
}
else {
# print "Kein Termin: $tag $mon $jar $jdthen $jdnow $diff \n";
}
}
}# modus == termine
# --------------------------------------------------------------------------
elsif ($modus == $woechentlich) {
my $dowthen = $revdow{$tag};
if ($dowthen < $downow) {
my $danach = $downow - $dowthen;
my $davor = -$dowthen - 7 + $downow;
if (DiffIstWarnDiff($danach)) {
my $tmp = LFill(MakeDiffZeitString($danach). " ($tag)",$normlaenge," ") .": $txt";
AusgabeHinzu($danach, "$tmp");
}
if (DiffIstWarnDiff($davor)) {
my $tmp = LFill(MakeDiffZeitString($davor). " ($tag)",$normlaenge," ") .": $txt";
AusgabeHinzu($davor, "$tmp");
}
}
elsif ($downow == $dowthen) {
if (DiffIstWarnDiff(0)) {
my $tmp = LFill(MakeDiffZeitString(0). " ($tag)",$normlaenge," ") .": $txt";
AusgabeHinzu(0, "$tmp");
}
}
else {
my $danach = $downow + 7 - $dowthen;
my $davor = $downow - $dowthen;
if (DiffIstWarnDiff($danach)) {
my $tmp = LFill(MakeDiffZeitString($danach). " ($tag)",$normlaenge," ") .": $txt";
AusgabeHinzu($danach, "$tmp");
}
if (DiffIstWarnDiff($davor)) {
my $tmp = LFill(MakeDiffZeitString($davor). " ($tag)",$normlaenge," ") .": $txt";
AusgabeHinzu($davor, "$tmp");
}
}
}
# --------------------------------------------------------------------------
# Fehler korrigiert, Monatlicher Termin am Anfang des naechsten Monats!
# 01.01.2000
elsif ($modus == $monatlich) {
my $jdthen = MyJulianDate($tag,$m_now,$y_now); # spezielle Basteltag
my $diff = $jdnow - $jdthen;
if (DiffIstWarnDiff($diff)) {
my $tmp = LFill(MakeDiffZeitString($diff). " (" . WochenTag($jdthen). ")",$normlaenge," ") . ": $txt";
AusgabeHinzu($diff, "$tmp");
}
else {
if ($m_now < 12) { $jdthen = MyJulianDate($tag,$m_now+1,$y_now); }
else { $jdthen = MyJulianDate($tag,$m_now+1,$y_now+1); }
$diff = $jdnow - $jdthen;
if (DiffIstWarnDiff($diff)) {
my $tmp = LFill(MakeDiffZeitString($diff). " (" . WochenTag($jdthen). ")",$normlaenge," ") . ": $txt";
AusgabeHinzu($diff, "$tmp");
}
}
}
# --------------------------------------------------------------------------
elsif ($modus == $feiertage) {
my $jdthen = MyJulianDate($tag,$mon,$jar);
my $diff = $jdnow - $jdthen;
if (DiffIstWarnDiff($diff)) {
my $tmp = LFill(MakeDiffZeitString($diff). " (" . WochenTag($jdthen). ")",$normlaenge," ") . ": FEIERTAG: $txt";
AusgabeHinzu($diff, "$tmp");
}
}
# --------------------------------------------------------------------------
elsif ($modus == $geburtstage) {
my $jdthen = MyJulianDate($tag,$mon,$y_now);
my $diff = $jdnow - $jdthen;
if (DiffIstWarnDiff($diff)) {
my $tmp = LFill(MakeDiffZeitString($diff). " (" . WochenTag($jdthen). ")",$normlaenge," ") . ": *$txt";
# Alter des Geburtstagskindes berechnen:
my $alter = $y_now - $jar;
AusgabeHinzu($diff, "$tmp ($alter)");
}
}
}
} # if no comment
} # while
close(INPUT);
# Ausgaben der Termininfos:
# Sortieren der DIFF-Zeilen mit den Indizes des Ausgabearrays:
# -----------------------------------------------------------------------
# print "Liste der Ausgabezeilen:\n";
# for(my $num=0; $num <= $#ausgabearray; $num++) {
# print "$num : $ausgabearray[$num]\n";
# }
# -----------------------------------------------------------------------
# -----------------------------------------------------------------------
# print "Liste der Diffzeilen :\n";
# my $num = 0;
# foreach my $line (sort {$diffhash{$b} <=> $diffhash{$a}} keys %diffhash) {
# print "$num: $line => ". $diffhash{$line} . "\n";
# $num++;
# }
# -----------------------------------------------------------------------
# Hier erfolgt die Ausgabe der Ausgabezeilen.
# Mit einem Trick wird dafuer gesorgt, dass z.b. zwischen einem Montags- und
# einem Donnerstags-Termin 2 Leerzeilen erscheinen! :-)
my $altdiff = 0;
my $neudiff = 0;
my $first = $ja;
#666
if ($ausgabecnt < 0) {
print "Keine Termine.\n";
}
else {
print "Termine:\n\n";
foreach my $line (sort {$diffhash{$b} <=> $diffhash{$a}} keys %diffhash) {
$neudiff = $diffhash{$line};
if ($first == $ja) { $first = $nein; }
else {
while ($altdiff > $neudiff + 1) {
print "\n";
$altdiff--;
}
}
$altdiff = $neudiff;
print "$ausgabearray[$line]\n";
}
print "\n";
}
exit;
# =======================================================================
# =======================================================================
# =======================================================================
# =======================================================================
# --------------------------------------------------------
sub LFill {
my ($str, $len, $womit) = @_;
while (length($str) < $len) {
$str = "$womit$str";
}
return $str;
}
# --------------------------------------------------------
# Die folgende Function schreibt, soweit ich das jetzt noch verstehe, ;->
# alle Warn-Differenzen eienr Zeile wie "Termine: [-6 -5 -4 -3 -2 -1 0]"
# in das Array @warnliste.
# Aber warum wird kein Hash verwendet???
sub WarndatenExtrahieren {
my $pos = 0;
my $part = "";
%warnliste = ();
my ($liste) = ( $zeile =~ /.*\[(.*)\]/ ); # Alles aus [...] -> $liste
$liste = Trim($liste);
while (length($liste) > 0) {
$pos = index($liste," ");
if ($pos != -1) {
$part = Trim(substr($liste,0,$pos));
$liste = Trim(substr($liste,$pos+1));
}
else {
$part = $liste;
$liste = "";
}
$warnliste{"$part"} = 1;
} # wend
# print "Warnliste = ";
# foreach my $schnorg (keys %warnliste) {
# print "$schnorg ";
# }
# print"\n";
}
# ---------------------------------------------
sub Trim {
my ($line) = @_;
if (!defined($line)) { $line = ""; }
while ( (length($line) > 0) && (substr($line,0,1) eq " ") ) {
$line = substr($line,1);
}
while ( (length($line) > 0) && (substr($line,length($line)-1,1) eq " ") ) {
$line = substr($line,0,length($line)-2);
}
return $line;
}
# ----------------------------------------------
sub DiffIstWarnDiff {
my ($mydiff) = @_;
return defined( $warnliste{$mydiff} );
}
# ----------------------------------------------
sub MakeDiffZeitString {
my ($mydiff) = @_;
if ($mydiff == -2) { return "Uebermorgen"; }
elsif ($mydiff == -1) { return "Morgen"; }
elsif ($mydiff == 0) { return "H e u t e"; }
elsif ($mydiff == 1) { return "Gestern"; }
elsif ($mydiff < 0) { return sprintf("In %d Tagen" , -$mydiff); }
elsif ($mydiff > 0) { return sprintf("Vor %d Tagen", $mydiff); }
}
# ----------------------------------------------
sub MyJulianDate {
my ($tt,$mm,$jj) = @_;
my $JD = 0;
my $J = 0;
my $M = 0;
my $G = 0;
my $a = 0;
if ($mm < 3) {
$J = $jj - 1;
$M = $mm + 12;
}
else {
$J = $jj;
$M = $mm;
}
$a = int($J / 100);
$G = 2 - $a + int($a/4);
$JD = int(365.25 * $J) + int(30.6001*($M + 1)) + $tt + 1720995 + $G;
return $JD;
}
# --------------------------------------------------
sub day_of_week {
my ($JD) = @_;
$JD = $JD - 7 * int($JD/7);
$JD++;
return $JD;
}
# --------------------------------------------------------
sub WochenTag {
my ($JD) = @_;
return $Wochentag[day_of_week($JD)];
}
# --------------------------------------------------
sub help {
print "\n -+-- TERMIN-ERINNERER $version --+-\n\n";
print " Autor: Tjabo Kloppenburg \n";
print " Datum: Januar 2000\n";
print " Usage: termine [-h|-?]\n\n";
}
# -------------------------------------------------------------------------
sub AusgabeHinzu { my($mdiff, $mtxt) = @_;
$ausgabecnt++; $ausgabearray[$ausgabecnt] = $mtxt;
$diffhash{"$ausgabecnt"} = $mdiff;
}