#!/usr/bin/tcl
#
# Summarising module for Project Clock
#
# David Keeffe
# Raster Solutions P/L
#
# $Id: summary.tcl,v 1.3 2001/01/24 03:20:59 david Exp $

# History:
#	$Log: summary.tcl,v $
#	Revision 1.3  2001/01/24 03:20:59  david
#	added summary date ranges
#	added multiple projects
#
#	Revision 1.2  2000/06/07 02:01:10  david
#	lots of options
#
#	Revision 1.1  2000/02/21 23:07:03  david
#	Initial revision
#
#

set progname [file tail $argv0]
set progdir [file dirname $argv0]


source $progdir/getopt.tcl

set dbfile "$env(HOME)/.pclock"
set pconfig $env(HOME)/.pclockrc
set projects *
set listonly false
set summarise 1
set verbose 0
set quiet 0
set year {}
set month {}
set eyear {}
set emonth {}
set debug 0
set workday 8
set from 1
set to 31
set rawtimes 0

set usagelist {
	{h {} {output this message}}
	{x {} {increment debug level}}
	{l {} {list projects}}
	{q {} {don't print headings}}
	{r {} {just rawtimes times, no factoring}}
	{s {} {omit summaries}}
	{v {} {print daily times}}
	{f {} {start day (default 1)}}
	{t {} {end day (default last of month)}}
	{d {period} {process times for 'period' (single (m/y) or range (m/y-m/y)) }}
	{i {file} {read data from 'file'}}
}


set ufmt {Usage: %s [-hxlrs][-f day][-t day][-d range][project-name]}
	

proc usage { { fd stderr }} {
	global argv0 usagelist ufmt
	puts $fd [format $ufmt $argv0]
	puts $fd "Where -"
	foreach l $usagelist {
		puts $fd [format {	-%s %-10s : %s} [lindex $l 0] [lindex $l 1] [lindex $l 2]]
	}
}

proc getdays { date plist } {
	global days

	set result {}

	foreach p $plist {
		foreach n [array names days "$date,$p"] {
			if {[lsearch -exact $result $n] == -1} {
				lappend result $n
			}
		}
	}
	return $result
}


proc timeof { value showdays } {
	global workday
	if { $showdays } {
		set days [expr $value / ( $workday * 60 * 60 )]
		set hours [expr $value % ( $workday * 60 * 60 )]
		return "[format %2dd $days] [clock format $hours -format {%H:%M:%S} -gmt 1]"
	} else {
		return "    [clock format $value -format {%H:%M:%S} -gmt 1]"
	}
}


while { [ set err [getopt $argv "Hhdrxqlsvf:t:i:d:" opt arg] ] } {
	if { $err <  0 } {
		puts stderr "$argv0: $arg"
	} else {
		switch -exact $opt {
		H {
			usage stdout
			exit 0
		}

		h {
			usage
			exit 0
		}

		d {
			set datexx [split $arg -]
			
			if {[llength $datexx] == 1} {
				set dstr [lindex $datexx 0]
				set date [split $dstr /]
				set month [lindex $date 0]
				set year [lindex $date 1]
				set emonth {}
				set eyear {}
			} else {
				set month {epoch}
				set year {epoch}
				set emonth {eot}
				set eyear {eot}
				if {[lindex $datexx 0] != {} } {
					set dstr [lindex $datexx 0]
					set date [split $dstr /]
					set month [lindex $date 0]
					set year [lindex $date 1]
				}
				if {[lindex $datexx 1] != {} } {
					set dstr [lindex $datexx 1]
					set date [split $dstr /]
					set emonth [lindex $date 0]
					set eyear [lindex $date 1]
				}
			}

		}

		f {
			set from $arg
		}

		r {
			set rawtimes 1
		}

		t {
			set to $arg
		}

		i {
			set dbfile $arg
		}

		x {
			incr debug
		}

		l {
			set listonly true
		}

		q {
			set quiet 1
		}

		v {
			incr verbose
		}

		s {
			set summarise 0
		}

		}
	}
}

if { $debug > 1 } {
	cmdtrace on stderr
}

set argv [lrange $argv $optind end] 

set projects $argv

if { $projects == {} } {
	set projects *
}



if {[file readable $pconfig]} {
	source $pconfig
}


set now [clock seconds]

if { $month == {epoch} } {
	set month Jan
}

if { $year == {epoch} } {
	set year [clock format $now -format "%Y"]
}

if { $month == {} } {
	set month [clock format $now -format "%b"]
}

if { $year == {} } {
	set year [clock format $now -format "%Y"]
}

if { $emonth == {eot} } {
	set emonth Dec
}

if { $eyear == {eot} } {
	set eyear [clock format $now -format "%Y"]
}

if {[catch {source $dbfile} res]} {
	puts stderr "$res"
	exit 1
}

if { $listonly } {
	foreach n [array names days] {
		regsub {.*,(.*)} $n {\1} p
		set plist($p) 1
	}
	puts [join [array names plist] "\n"]
	exit 0
}

array set alldays {}
set total 0

if { $emonth != {} || $eyear != {} } {
	set tbanner "Times from $month/$year to $emonth/$eyear"
} else {
	set tbanner "Times for $month/$year"
}
if { $verbose && !$quiet } {
	puts $tbanner
	puts [format {%-15s %-20s %8s} Date Project Time]
	puts [format {%-15s-%-20s-%s} --------------- --------------------- -----------]
}

if { $emonth == {} } {
	set emonth $month
}

if { $eyear == {} } {
	set eyear $year
}


array set months_n {
Jan 1
Feb 2
Mar 3
Apr 4
May 5
Jun 6
Jul 7
Aug 8
Sep 9
Oct 10
Nov 11
Dec 12
}

foreach m [array names months_n] {
	set n_months($months_n($m)) $m
}

set start_n $months_n($month)
set end_n $months_n($emonth)
# puts stderr "START \[1\]: $start_n - END: $end_n; Y1: $year; Y2 $eyear"

set end_n [expr $end_n + (12 * ($eyear - $year))]
if { $end_n <= 0 } {
	puts stderr "$progname: start is before end!"
	exit 0
}


# puts stderr "START \[2\]: $start_n - END: $end_n"

for { set mn $start_n} { $mn <= $end_n } { incr mn } {

	set n_mn [expr (($mn-1) % 12) + 1]
	set yn [expr $year + (($mn-1) / 12)]

	# puts stderr "YEAR: $yn - nom MONTH: $n_mn"

	for {set i $from} { $i <= $to } {incr i} {
		set date "$i $n_months($n_mn) $yn"
		if {[catch {clock scan $date} actual]} {
			break
		}
		set date [clock format $actual -format "%d-%b-%Y"]
		set fdate [clock format $actual -format "%a %d-%b-%Y"]
		set matches [lsort [getdays $date $projects]] 
		if { ($verbose > 1) && $matches == {} } {
			puts [format {%s %-20s %s} $fdate "--EMPTY--" 0]
		}
		foreach n $matches {
			regsub "$date," $n {} proj
			if { $rawtimes == 0 && [info exists factor($proj)] } {
				set dd [expr int($factor($proj) * $days($n))]
			} else {
				set dd $days($n)
			}
			if {[info exists alldays($proj)]} {
				incr alldays($proj) $dd
			} else {
				set alldays($proj) $dd
			}
			incr total $dd
			if { $verbose > 1 || ( $verbose && $dd > 0 ) } {
				puts [format {%s %-20s %s} $fdate $proj [timeof $dd 0]]
			}
		}
	}
}

if { $summarise } {
	if { !$quiet } {
		if { !$verbose } {
			puts $tbanner
			puts [format {%-15s %-20s %8s} {} Project Time]
		}
		puts [format {%-15s-%-20s-%s} --------------- --------------------- -----------]
	}
	foreach n [lsort [array names alldays]] {
		puts [format {%-15s %-20s %s} {} $n [timeof $alldays($n) 1]]	
	}
	if { !$quiet } {
		puts [format {%-15s-%-20s-%s} --------------- --------------------- -----------]
		puts [format {%-15s %-20s %s} {} TOTAL [timeof $total 1]]
	}
}
