The main script - calendar.pl
#!/usr/bin/perl -Tw
use strict;
use CGI;
# Set PATH to cal
#########################
$ENV{'PATH'} = '/usr/bin';
# The directory to store entries for dates
#########################
my $date_dir = "dates/";
my $cgi = new CGI;
my $cal_prog = '/usr/bin/cal';
# A style sheet
#########################
my $cal_style= <<"EOT";
<!--
A { text-decoration: none; }
A.visited { color: #0000ff; }
h3 { font-size: 10px; }
.wd { color: #ffffff; }
.highlight {
color: #ff0000;
font-weight: bold;
}
-->
EOT
# Colors for the backgrounds
##########################
my $month_bg_color='#ff0000';
my $week_bg_color='#0000ff';
my $date_bg_color='#e0e0e0';
my $year = 2000;
my $num_of_months = 12;
# The number of months shown per row
##########################
my $months_per_row = 3;
print $cgi->header(),
$cgi->start_html(
-title=>'Calendar',
-BGCOLOR=>'#ffffff',
-style=>{-code=>$cal_style}
);
print $cgi->h1('Calendar for the year '. $year);
print '<table cellspacing=5 cellpadding=0 border=0><tr valign="top">';
# A table for all months
############################
my $row_count = 1;
for(;$row_count <= $num_of_months ; $row_count++){
open(CAL,"$cal_prog -m $row_count $year |") ||
die "Cannot open CAL: $!\n";
my @month = <CAL>;
close(CAL);
print '<td bgcolor="',$date_bg_color,'">';
my $month_name = splice(@month,0,1);
$month_name =~ s/^\s+(\w+) \d+$/$1/g;
my $days = splice(@month,0,1);
# A table for each of the months
###################################
print '<table cellspacing=0 cellpadding=0 border=0>',
'<tr><td bgcolor="',
$month_bg_color,
'" colspan=7>',
$cgi->h3($month_name),
'</td></tr>',
'<tr>';
# Mo Tu We Th Fr Sa Su
###############################
my @day_names = split(" ",$days);
foreach(@day_names){
print '<td class="wd" bgcolor="' . $week_bg_color . '">',$_,'<
+/td>';
}
# Start spitting out the dates
###############################
foreach(@month){
s/[^\d] /\-\- /g;
s/ (\d)( |\n)/0$1$2/g;
print '<tr>';
my @dates = split(/ /g, $_);
foreach(@dates){
unless(/^--/){
s/\n$//;
chomp($month_name);
my $date_file = $date_dir . $month_name . $_;
my @date_stats = stat($date_file);
# Check for entries per date, if any highlight it
+
#################################################
if( -e $date_file && $date_stats[7] > 0){
print '<td><a class="highlight" href="showDate.pl?
+month=',
$month_name,
'&date=',$_,'">',$_;
}
else{
print '<td><a href="showDate.pl?month=',
$month_name,
'&date=',$_,'">',$_;
}
print '</a> </td>';
}
else{
print '<td>--</td>';
}
}
print '</td></tr>';
}
print '</table>';
print '</td>';
if($row_count % $months_per_row == 0){
print '</tr><tr valign="top">';
}
}
print '</tr></table>';
print $cgi->end_html;
The script for wieving daily events - showDate.pl
#!/usr/bin/perl
use strict;
use Fcntl;
use CGI;
my $cgi = new CGI;
my $date_dir = 'dates/';
# Check month & date params
###############################
unless($cgi->param('month') =~ /\w+/ && $cgi->param('date') =~ /\d{2}/
+){
die "Invalid parameters!\n";
}
my $date_file = $date_dir . $cgi->param('month') . $cgi->param('date')
+;
my $file_identifier = '### CALENDAR.PL DATE FILE ' . $cgi->param('mont
+h') . $cgi->param('date');
# Style sheet
#########################
my $cal_style= <<"EOT";
<!--
.wd { color: #ffffff; }
.action {
text-decoration: none;
font-size: 8px;
}
-->
EOT
# Some color settings
##########################
my $time_bg_color = '#ff0000';
my $entry_bg_color = '#efefef';
my $alt_entry_bg_color = '#c0c0c0';
print $cgi->header(),
$cgi->start_html(
-title=>'Calendar',
-BGCOLOR=>'#ffffff',
-style=>{ -code=>$cal_style },
);
print $cgi->h2(
'Entries for ',
$cgi->param('month'),'-',
$cgi->param('date'),'-2000',
);
# Read in old entries if any
#############################
my(@entries);
if(-e $date_file){
sysopen(ENTRIES,$date_file,O_RDONLY) ||
die "Cannot open $date_file: $!\n";
flock(ENTRIES,1);
@entries = <ENTRIES>;
close(ENTRIES);
}
# Check to see if requested date file is valid
################################################
unless(splice(@entries,0,1) eq $file_identifier){
die "Not a valid date file!\n";
}
print '<table cellspacing=1 cellpadding=0 border=0><tr>';
# Start day at $time_count
##########################
my $time_count = 8;
for(;$time_count < 25; $time_count++){
print '<tr><td class="wd" bgcolor="',
$time_bg_color,
'"> ',
$time_count,
':00 </td>';
# A different coloring for each line
######################################
print '<td width=400';
if($time_count & 1){
print ' bgcolor="',
$entry_bg_color,
'"> ';
}
else{
print ' bgcolor="',
$alt_entry_bg_color,
'"> ';
}
foreach(@entries){
if(/^$time_count:([^\n].+)/){
print $1 . ' ';
}
}
print '</td><td';
if($time_count & 1){
print ' bgcolor="',
$entry_bg_color,
'"> ';
}
else{
print ' bgcolor="',
$alt_entry_bg_color,
'"> ';
}
# A link to add an entry
###############################
print '[<a class="action" href="alterDate.pl?date=',
$cgi->param('date'),
'&month=',
$cgi->param('month'),
'&time=',
$time_count,
'&action=add">ADD ENTRY</a> |';
# ..and to remove one
print '<a class="action" href="alterDate.pl?date=',
$cgi->param('date'),
'&month=',
$cgi->param('month'),
'&time=',
$time_count,
'&action=rem"> REMOVE</a>] ';
print '</tr>';
}
print '</table>';
print $cgi->p;
print '<a href="calendar.pl">Back to the calendar</a>';
print $cgi->end_html;
And finally, the script for adding and removing stuff - alterDate.pl
#!/usr/bin/perl
use CGI;
use strict;
use Fcntl;
my $cgi = new CGI;
my $date_dir = 'dates/';
# Check month, date & time params
###############################
unless($cgi->param('month') =~ /\w+/ && $cgi->param('date') =~ /\d{2}/
+ && $cgi->param('time') =~ /\d{1,2}/){
die "Invalid parameters!\n";
}
my $date_file = $date_dir . $cgi->param('month') . $cgi->param('date')
+;
my $file_identifier = '### CALENDAR.PL DATE FILE ' . $cgi->param('mont
+h') . $cgi->param('date');
my $new_entry;
my $redirect = 'showDate.pl?month=' . $cgi->param('month') . '&date='
+. $cgi->param('date');
# If we just added an entry write it and bounce back
#######################################################
if($cgi->param('action') eq 'Add new entry'){
sysopen(DATE_FILE,$date_file, O_RDWR | O_CREAT,0666) ||
die "Cannot open $date_file: $!\n";
flock(DATE_FILE,2);
my @old_entries = <DATE_FILE>;
# Check to see if requested date file is valid
################################################
unless(splice(@old_entries,0,1) eq $file_identifier){
die "Not a valid date file!\n";
}
seek(DATE_FILE, 0, 0);
truncate(DATE_FILE, 0);
$new_entry = $cgi->param('time') . ":" . $cgi->param('entry');
push(@old_entries,$new_entry);
print DATE_FILE $file_identifier
foreach(@old_entries){
unless(/^\s$/){
print DATE_FILE $_ . "\n";
}
}
close(DATE_FILE);
print $cgi->redirect($redirect);
}
# Remove an entry
###############################
elsif($cgi->param('action') eq 'rem'){
sysopen(DATE_FILE,$date_file,O_RDWR) ||
die "Cannot open $date_file: $!\n";
flock(DATE_FILE,2);
my(@old_entries,@new_entries);
@old_entries = <DATE_FILE>;
# Check to see if requested date file is valid
################################################
unless(splice(@old_entries,0,1) eq $file_identifier){
die "Not a valid date file!\n";
}
my $time = $cgi->param('time');
while(@old_entries){
unless(/^$time:.+/){
push(@new_entries,$_);
}
}
seek(DATE_FILE, 0, 0);
truncate(DATE_FILE, 0);
print DATE_FILE $file_identifier;
foreach(@new_entries){
unless(/^\s$/){
print DATE_FILE $_ . "\n";
}
}
close(DATE_FILE);
print $cgi->redirect($redirect);
}
# The form to add an entry
#################################
else{
print $cgi->header(),
$cgi->start_html(
-title=>'Add entry',
-BGCOLOR=>'#ffffff',
);
print $cgi->h2(
$cgi->param('month'),'-',
$cgi->param('date'),'-2000 at',
$cgi->param('time'),':00',
);
print $cgi->start_form(
-action=>'alterDate.pl',
-method=>'post',
);
print $cgi->p,
"Enter text:",
$cgi->br,
$cgi->textfield(
-name=>'entry',
-size=>'40',
),
$cgi->p,
$cgi->submit(
-value=>'Add new entry',
-name=>'action',
),
'<input type="hidden" name="time" value="' . $cgi->param('time
+') . '">',
'<input type="hidden" name="month" value="' . $cgi->param('mon
+th') . '">',
'<input type="hidden" name="date" value="' . $cgi->param('date
+') . '">';
print $cgi->end_form();
print $cgi->end_html();
}
Some TODO:
- See post below for security issues..
- A choice for either 12- or 24-hour formats (currently 24)
- Substitute <table> -stuff with $cgi->table() stuff (once I get the hang of it .. :)
- Allow users to modify existing entries
|