#!/usr/bin/perl -Tw #-----------------------------------------------------------------# # my_portal # pudge # # This software is unsupported and provided for those who # just want it. See the docs at the end of this file. # # Created: Chris Nandor (pudge@pobox.com) 09 Nov 1999 # Last Modified: Chris Nandor (pudge@pobox.com) 02 Jan 2000 #-----------------------------------------------------------------# use strict; use AnyDBM_File; use CGI ':all'; use CGI::Carp 'fatalsToBrowser'; use Data::Dumper; use Date::Parse; use Date::Format; use Fcntl; use File::Basename; use Getopt::Std; use LWP::Simple qw[mirror is_error]; use Symbol; use Time::Local; use XML::RSS; #require '/export/home/pudge/site_perl/XML/RSS.pm'; $ENV{PATH} = ''; #================== # set defaults #================== my %conf = ( prog => '/my_portal/', # $ENV{SCRIPT_NAME} admin => 'pudge@pobox.com', src => 'http://www.news.perl.org/my_portal/my_portal.plx', dir => '/opt/apache/gocho.pm.org/80/htdocs/perl.org/news/my_portal', cookieDom => '.perl.org', cookieNam => 'myPortalName', cookieExp => '+1y', cookiePath => '/my_portal', defaults => { 1 => '1,1', 10 => '2,1', 3 => '3,1', 5 => '1,2', 2 => '2,2', 7 => '3,2', 14 => '1,3', 18 => '2,3', back => '#FFFFFF', fore => '#CCCCFF', btext => '#000000', ftext => '#000000', 'link' => '#000088', vlink => '#880000', showdesc => '', save_cookie => 'CHECKED', }, ); $conf{imgurl} = "img"; $conf{imgdir} = "$conf{dir}/img"; $conf{rdfdir} = "$conf{dir}/rdf"; $conf{rdff} = "$conf{dir}/rdfs"; $conf{userf} = "$conf{dir}/users"; unless ($ENV{SERVER_SOFTWARE}) { do_cl(); exit; } tie my %rdfs, 'AnyDBM_File', $conf{rdff}, O_RDONLY, 0444 or die $!; $conf{rdfs} = \%rdfs; #================== # do main #================== while (my $cgi = new CGI) { if ($cgi->param('dumpusers')) { tie my %users, 'AnyDBM_File', $conf{userf}, O_RDWR|O_CREAT, 0644 or die $!; print header('text/plain'); print Dumper \%users; untie %users; exit; } my($user) = $cgi->cookie(-name => $conf{cookieNam}); $user ||= ''; my $prefs = get_prefs($user); my($un, $pw) = ($cgi->param('un'), $cgi->param('pw')); if ($cgi->param('dologin') && $un && $pw) { my $nuser = join '|', crypt($pw, $un), $un; my $ok = userOK($un, $pw); $user = $ok ? $nuser : ''; $prefs = get_prefs($user, ($ok ? $prefs : undef)); print myhead($cgi, $user, $prefs, 1), ($ok ? '' : <

Incorrect password for user $un

EOT display_channels($prefs); } else { ($user, $prefs) = set_config($cgi, $user, $prefs) if $cgi->param('set'); if ($cgi->param('login')) { print myhead($cgi, $user, $prefs); print show_login($user, $prefs); } elsif ($cgi->param('config')) { print myhead($cgi, $user, $prefs); print show_config($user, $prefs); } else { print myhead($cgi, $user, $prefs, 1); print display_channels($prefs); } } print myfoot(); exit; } #================== # main displays #================== sub show_login { my($user, $prefs) = @_; return <

Enter username and password to log in or create new login.

Username: Password:

EOT } sub show_config { my($user, $prefs) = @_; my $return = <
EOT foreach my $i (sort {$conf{rdfs}->{$a} cmp $conf{rdfs}->{$b}} keys %{$conf{rdfs}}) { my($c, $l) = split m/\|/, $conf{rdfs}->{$i}; my($m, $r) = split m/,/, $prefs->{$i} if exists $prefs->{$i}; my $k = 'CHECKED' if exists $prefs->{$i}; $m ||= ''; $r ||= ''; $return .= < EOT } $return .= <
Channel Column Row
$c
 
{showdesc}> Show item descriptions
{save_cookie}> Save cookie
Background color
Foreground color
Text color
Link color
Visited link color
EOT return $return; } sub display_channels { my $prefs = shift; my(%channels, $channels); for my $rdf (sort { $a->[1] <=> $b->[1] || $a->[2] <=> $b->[2] || $a->[0] <=> $b->[0] } map { [$_, split /,/, $prefs->{$_}] } grep { /^\d+$/ } keys %$prefs) { my $rss = new XML::RSS; eval { $rss->parsefile("$conf{rdfdir}/$rdf->[0].rdf") }; if ($@) { # print $@; next; } push @{$channels{$rdf->[1]}}, format_channel($rss, $prefs, $rdf->[0]); } $channels = qq[ \n]; for (grep { exists $channels{$_} } 1..3) { $channels .= join '', qq[ \n], join("\n
\n", @{$channels{$_}}), qq[ \n]; } $channels .= qq[ \n]; return $channels; } sub format_channel { my($rss, $prefs, $rdf) = @_; my($desc, $img, @items, $items, $input, $date); $img = $rss->{image}{url} && -e "$conf{imgurl}/$rdf.gif" ? qq'{image}{description}) { $img .= qq' ALT="$rss->{image}{description}"'; } elsif ($rss->{image}{title}) { $img .= qq' ALT="$rss->{image}{title}"'; } if ($rss->{image}{width} && $rss->{image}{height}) { $img .= qq' HEIGHT="$rss->{image}{height}" WIDTH="$rss->{image}{width}"'; } $img .= '>'; if ($rss->{image}{'link'}) { $img = qq[$img]; } $img = "

$img

"; } else { $img = qq[

$rss->{channel}{title}

]; } for my $item (@{$rss->{items}}) { my $i = qq[ * ] . qq[$item->{title}]; $i .= " - $item->{description}" if $prefs->{showdesc} && $item->{description}; $i .= "
"; push @items, $i; } $items = join "\n", @items; $date = $rss->{channel}{lastBuildDate} || $rss->{channel}{pubDate} || ''; my @date = $date ? gmtime timegm localtime str2time($date) : localtime(time - ((-M "$conf{rdfdir}/$rdf.rdf") * 86400)); $date = sprintf '

%s

', strftime('%B %d, %Y, %H:%M EST', @date); # $desc = $rss->{channel}{description} || ''; # $desc = "

$desc

" if $desc; $input = $rss->{textinput}{'link'} ? <

${\($rss->{textinput}{title} || '')}

EOT return < $img $items $input $date EOT } sub myhead { my($cgi, $user, $prefs, $refresh) = @_; $refresh = $refresh ? < EOT return header(get_cookie($cgi, $user, $prefs)), < My Portal $refresh EOT } sub myfoot { return <

Hosting provided by Perl Mongers

© Copyright 2000, Chris Nandor. All Rights Reserved.
Copyright of content of each channel maintained by respective owners.

EOT } #================== # data stuff #================== sub save_prefs { my($user, $prefs) = @_; tie my %users, 'AnyDBM_File', $conf{userf}, O_RDWR|O_CREAT, 0644 or die $!; $users{$user} = join '|', %$prefs, modtime => time; untie %users; } sub get_cookie { my($cgi, $user, $prefs) = @_; my %params; if ($user) { $params{-cookie} = $cgi->cookie( -name => $conf{cookieNam}, -value => $user, -domain => $conf{cookieDom}, -path => $conf{cookiePath}, $prefs->{save_cookie} ? (-expires => $conf{cookieExp}) : () ); } return %params; } sub set_config { my($cgi, $user, $prefs) = @_; $user ||= join '.', $ENV{REMOTE_ADDR}, $$, time; $user = join '', map { $_ ? chr : '' } split m/\%/, $user if $user =~ m/^\%/; for my $i (keys %$prefs) { delete $prefs->{$i} if $i =~ /^\d+$/; } # channels for ($cgi->param('channels')) { my($m, $r) = ($cgi->param("col-$_"), $cgi->param("row-$_")); $m = $m =~ /^\d+$/ ? $m : 3; $r = $r =~ /^\d+$/ ? $r : 9; $prefs->{$_} = "$m,$r"; } # color for my $c (qw(back fore btext ftext link vlink)) { my $color = $cgi->param($c); $color =~ s/^\s*(.*)\s*$/$1/; if ($color =~ /^(?:#?[0-9a-fA-F]{6}|[a-zA-Z]+)$/) { $prefs->{$c} = $color; } } # other for my $c (qw(showdesc save_cookie)) { $prefs->{$c} = $cgi->param($c); } save_prefs($user, $prefs); return($user, $prefs); } sub get_prefs { my($user, $prefs) = @_; return $conf{defaults} unless -e $conf{userf} . '.pag'; $user = join '', map { $_ ? chr : '' } split m/\%/, $user if $user =~ m/^\%/; tie my %users, 'AnyDBM_File', $conf{userf}, O_RDONLY, 0444 or die $!; return $prefs || $conf{defaults} unless $users{$user}; my %prefs = split m/\|/, $users{$user}; untie %users; for (grep !/^\d+$/, keys %{$conf{defaults}}) { $prefs{$_} = $conf{defaults}->{$_} unless exists $prefs{$_}; } return \%prefs; } sub userOK { my($un, $pw) = @_; return $conf{defaults} unless -e $conf{userf} . '.pag'; tie my %users, 'AnyDBM_File', $conf{userf}, O_RDONLY, 0444 or die $!; for my $u (keys %users) { next unless $u =~ /^(.+?)\|$un$/; if (crypt($pw, $1) ne $1) { return; } } 1; } #================== # command line stuff #================== sub fetch_rdf { my($rdf, $l) = @_; my $rc = mirror($l, "$conf{rdfdir}/$rdf.rdf"); return($rc, $l) if is_error($rc); { my $file = "$conf{rdfdir}/$rdf.rdf"; my @time = (stat $file)[8, 9]; local $^I = '.bak'; local @ARGV = $file; my $line = <>; print $line unless $line =~ /^

My Portal
[ Home | Login | Configure | Source | Feedback ]