Article 9857 of comp.lang.perl:
Xref: feenix.metronet.com comp.infosystems.www:6285 comp.lang.perl:9857 rec.arts.comics.strips:2686
Newsgroups: comp.infosystems.www,comp.lang.perl,clari.net.talk,rec.arts.comics.strips
Path: feenix.metronet.com!news.utdallas.edu!wupost!galileo.cc.rochester.edu!ub!news.kei.com!sol.ctr.columbia.edu!howland.reston.ans.net!vixen.cso.uiuc.edu!news.acns.nwu.edu!news.eecs.nwu.edu!jmyers
From: [email protected] (Jennifer Myers)
Subject: ANNOUNCE: CGI Script for Dilbert
Message-ID: <[email protected]>
Sender: [email protected]
Supersedes: <[email protected]>
Organization: Northwestern University, Evanston, Illinois
Date: Mon, 17 Jan 1994 20:45:11 GMT
Lines: 398

This article supersedes the announcement of "dilbert," version 0.1.
I've been informed that the script cannot be named "dilbert" because
it is a registered trademark.  Therefore, I announce version 0.11 of
"read-comics".  Please update your version.

Thanks!

Announcing Version 0.11 of 'read-comics', a Common Gateway Interface
World Wide Web gateway to clari.feature.dilbert.

'read-comics' is a Common Gateway Interface (CGI) script for
CGI-compliant HTTP (World Wide Web) servers (e.g., NSCA httpd 1.0).
'read-comics' generates a hypertext interface to the
clari.feature.dilbert newsgroup.  It does this by querying the NNTP
server for a list of active articles in the clari.feature.dilbert
newsgroup and then generates from this, a list of hyperlinks.  When a
link is selected, the article is retrieved from the NNTP server and
then uudecoded on-the-fly.

There is a special link: http://www-server.domain/cgi-bin/read-comics?today
which will always point to the most recent comic strip.

Connecting hosts not in the specified domain are denied access.

Retrieval instructions:

   Version 0.11 of 'read-comics' is appended to the end of this article.
   The latest version of 'read-comics' may also be retrieved from the WWW as
       http://www.eecs.nwu.edu:8001/jmyers/cgi-src/read-comics
   or by anonymous ftp as
       eecs.nwu.edu:/pub/jmyers/cgi-src/read-comics

Installation:

   Configure $domain, $nntphost, and $group as appropriate.

   Put this script in your CGI bin directory.  For example, on my
      server, I have this script installed as:
      http://www.eecs.nwu.edu:8001/cgi-bin/read-comics


Acknowledgments:

   The NNTP code is adopted from code for a NNTP client written by
       Eric Young <[email protected]>
   The uudecode algorithm comes from _Programming_Perl_,
       (Wall/Schwartz), p. 198.

Revision History:

1/17/94:      Version 0.11. Changed name of script to not interfere
             with trademark restrictions. (Dilbert is a registered
             trademark of Scott Adams and United Media).

1/16/94:      Version 0.1. Initial release.

Please contact me by email if you have any difficulties installing or
using this package.

Thanks,
-Jennifer

--
<A HREF = "http://www.eecs.nwu.edu:8001/jmyers/plan.html">Jennifer Myers</A>
[email protected]

#! /bin/sh
# This is a shell archive.  Remove anything before this line, then unpack
# it by saving it into a file and typing "sh file".  To overwrite existing
# files, type "sh file -c".  You can also feed this as standard input via
# unshar, or by typing "sh <file", e.g..  If this archive is complete, you
# will see the following message at the end:
#               "End of shell archive."
# Contents:  read-comics
# Wrapped by jmyers@marigold on Mon Jan 17 14:35:00 1994
PATH=/bin:/usr/bin:/usr/ucb ; export PATH
if test -f 'read-comics' -a "${1}" != "-c" ; then
 echo shar: Will not clobber existing file \"'read-comics'\"
else
echo shar: Extracting \"'read-comics'\" \(9256 characters\)
sed "s/^X//" >'read-comics' <<'END_OF_FILE'
X#!/usr/local/bin/perl
X#
X# read-comics
X#
X# Version 0.11, (January 17, 1994)
X#
X# Author: Jennifer Myers <[email protected]>
X#
X# 'read-comics' is a Common Gateway Interface (CGI) script for CGI-compliant
X# HTTP servers (e.g., NSCA httpd 1.0).  'read-comics' generates a hypertext
X# interface to the clari.feature.dilbert newsgroup.  It does this by
X# querying the NNTP server for a list of active articles in the
X# clari.feature.dilbert newsgroup and then generates from this, a list of
X# hyperlinks.  When a link is selected, the article is retrieved from the
X# NNTP server and then uudecoded on-the-fly.
X#
X# There is a special link: http://www-server.domain/cgi-bin/read-comics?today
X# which will always point to the most recent comic strip.
X#
X# Connecting hosts not in $domain are denied access.
X#
X# Retrieval instructions:
X#
X#    The latest version of 'read-comics' may be retrieved from the WWW as
X#      http://www.eecs.nwu.edu:8001/jmyers/cgi-src/read-comics
X#    or by anonymous ftp as
X#      eecs.nwu.edu:/pub/jmyers/cgi-src/read-comics
X#
X# Installation:
X#
X#    Configure $domain, $nntphost, and $group as appropriate.
X#
X#    Put this script in your CGI bin directory.  For example, on my
X#       server, I have this script installed as:
X#       http://www.eecs.nwu.edu:8001/cgi-bin/read-comics
X#
X# Acknowledgements:
X#
X#   The NNTP code is adopted from code for a NNTP client written by
X#      Eric Young <[email protected]>
X#   The uudecode algorithm comes from _Programming_Perl_,
X#      (Wall/Schwartz), p. 198.
X#
X# Revision History:
X#
X# 1/17/94:     Version 0.11. Changed name of script to not interfere
X#              with trademark restrictions. (Dilbert is a registered
X#              trademark of Scott Adams and United Media).
X#
X# 1/16/94:     Version 0.1. Initial release.
X#
X#######################################################################
X
X# Change these variables to suit your environment.
X$domain = "nwu.edu";
X$nntphost = "news.acns.nwu.edu";
X$group = "clari.feature.dilbert";
X
X# You should not need to change anything after this line.
X$date = `/bin/date`;
X$query_string = $ENV{'QUERY_STRING'};
X$remote_host = $ENV{'REMOTE_HOST'};
X$script_name = $ENV{'SCRIPT_NAME'};
X
Xrequire 'sys/socket.ph';
X
Xif ($remote_host =~ /\.$domain$/) {
X       do startnntp("$nntphost");
X       do read_nntp_header();
X       ($first, $last) = &group_cmd();
X       do xhdr_cmd($first,$last);
X}
X
Xif ($query_string eq "") { # Make index
X       print <<"EOM";
XContent-Type: text/html
X
X       <HTML><HEAD><TITLE>read-comics, a gateway to clari.feature.dilbert
X       </TITLE></HEAD>
X       <BODY><H1>clari.feature.dilbert gateway</H1><DL><HR>
X       Please note that the <EM>Dilbert</EM> comic strip is copyrighted by
X       United Media, and you may not pass copies to others.  Access to the
X       <EM>Dilbert</EM> comic strip is restricted to hosts in the
X       <STRONG>$domain</STRONG> domain.
X       <P>See <A HREF = "ftp://ftp.clarinet.com/help/dilbert"\
X       >ftp.clarinet.com:help/dilbert</A> for more information. <HR>
XEOM
X
X       if ($remote_host =~ /\.$domain$/) { # Access permitted
X               do getlinks(@subject);
X       } else { # Deny access
X               print <<"EOM";
X               <H2>Access Restricted:</H2>
X               Your host is not recognized as belonging in the
X               <STRONG>$domain</STRONG> domain.  Copyright restrictions
X               limit our distribution of this comic strip to hosts in the
X               <STRONG>$domain</STRONG> domain. <P> <A HREF =
X               "http://www.eecs.nwu.edu:8001/jmyers/cgi-src/read-comics"\
X               ><EM>read-comics</EM></A>, a gateway to the newsgroup
X               <EM>clari.feature.dilbert</EM>, is a Common Gateway Interface
X               (<A HREF="http://hoohoo.ncsa.uiuc.edu/cgi/overview.html"\
X               >CGI</A>) script, written in <A HREF =
X               "http://www.eecs.nwu.edu:8001/perl.html">Perl</A>, which
X               queries the news server via NNTP, generates a list of
X               hyperlinked articles, and retrieves and uudecodes selected
X               articles on-the-fly.
XEOM
X       }
X
X       print <<"EOM";
X       <HR>
X       This page was automatically generated on $date <HR>
X       This script, <A HREF =
X       "http://www.eecs.nwu.edu:8001/jmyers/cgi-src/read-comics"\
X       ><EM>read-comics</EM></A>, was written by <EM><A HREF =
X       "http://www.eecs.nwu.edu:8001/jmyers/plan.html">Jennifer Myers</A>
X       </EM></BODY></HTML>
XEOM
X
X} else { # Query provided
X       if ($remote_host =~ /\.$domain$/) { # Access permitted
X               print STDOUT "Content-Type: image/gif\n\n";
X
X               if ($query_string eq "today") {
X                       $query_string = $last;
X               }
X
X               @txt=&body_cmd($query_string);
X
X               #
X               # uudecode algorithm
X               #
X               $_=shift(@txt) until ($mode,$file)=/^begin\s*(\d*)\s*(\S*)/;
X               while ($_ = shift(@txt)) {
X                       last if /^end/;
X                       next if /[a-z]/;
X                       next unless int((((ord() - 32) & 077) + 2) / 3) ==
X                               int(length() / 4);
X                       print unpack("u", $_);
X               }
X       } else { # Deny access
X
X       print <<"EOM";
XContent-Type: text/html
X
X       <HTML><HEAD><TITLE>Access Denied</TITLE></HEAD>
X       <BODY><H1>Access Denied</H1><HR>
X       Sorry!  The <EM>Dilbert</EM> comic is distributed by ClariNet.
X       Copyright restrictions limit our distribution of this comic strip to
X       hosts in the <STRONG>$domain</STRONG> domain. <P> <A HREF =
X       "http://www.eecs.nwu.edu:8001/jmyers/cgi-src/read-comics"\
X       ><EM>read-comics</EM></A>, a gateway to the newsgroup
X       <EM>clari.feature.dilbert</EM>, is a Common Gateway Interface (<A
X       HREF= "http://hoohoo.ncsa.uiuc.edu/cgi/overview.html">CGI</A>)
X       script, written in <A HREF = "http://www.eecs.nwu.edu:8001/perl.html"\
X       >Perl</A>, which queries the news server via NNTP, generates a list
X       of hyperlinked articles, and retrieves and uudecodes selected
X       articles on-the-fly. <HR> This script, <A HREF =
X       "http://www.eecs.nwu.edu:8001/jmyers/cgi-src/read-comics"\
X       ><EM>read-comics</EM></A>, was written by <EM><A HREF =
X       "http://www.eecs.nwu.edu:8001/jmyers/plan.html">Jennifer Myers</A>
X       </EM></BODY></HTML>
XEOM
X       }
X} # End of main program
X
Xsub getlinks {
X        local(@articles) = @_;
X        local(@i);
X       print STDOUT "<UL><LI><A HREF =
X               \"http:$script_name?today\"\
X               >Today's Dilbert</a> (see below for title)</UL>";
X       print STDOUT "<H2>Archived:</H2>";
X       print STDOUT "<UL>";
X        while ($_=shift(@articles)) {
X                split;
X                $num=shift(@_);
X               @subj=@_;
X               if (@subj[0] eq "Dilbert:")  {
X                       print STDOUT "<LI> <A HREF=
X                               \"http:$script_name?$num\">@subj</A>";
X               }
X        }
X       print STDOUT "</UL>";
X}
X
Xsub body_cmd {
X        local($name)=@_;
X        local(@ret);
X
X        print NNTP "BODY $name\n";
X        $_=<NNTP>;
X        if (!/^222 /)
X                {
X#               print STDOUT "body cmd problems ($name):$_";
X                do quit_cmd(1);
X                }
X        @ret=&getlines();
X        return(@ret);
X        }
X
Xsub xhdr_cmd {
X        local($a,$b)=@_;
X
X        print NNTP "XHDR Subject $a-$b\n";
X        $_=<NNTP>;
X        if (!/^221 /) {
X#               print STDOUT "xhdr cmd problems\n";
X                if (/^500 /) {
X                        do manual_xhdr_cmd($a,$b);
X                } else {
X                        do quit_cmd();
X               }
X                return;
X        }
X        @subject=&getlines();
X}
X
Xsub manual_xhdr_cmd {
X        local($a,$b)=@_;
X        local($i,@s,$j);
X
X        $#subject=$[;
X        foreach $i ($a .. $b) {
X                print NNTP "HEAD $i\n";
X                $_=<NNTP>;
X               if (/^221 /) {
X                        @s=grep(/^Subject: /,&getlines());
X#                       print STDOUT "no Subject: line in article $i\n"
X#                               if ($#s < 0);
X                        $s[0] =~ /^Subject: (.*)/;
X                        push(@subject,"$i $1");
X                } else {
X                        print "$_";
X                }
X        }
X}
X
Xsub getlines {
X        local(@ret);
X
X        while (<NNTP>) {
X                if (/^\./ && (!/^\.\./)) {
X                        chop;
X                        last;
X                }
X                s/\015//g;
X                push(@ret,$_);
X        }
X        return(@ret);
X}
X
Xsub quit_cmd {
X        local($code)=@_;
X        print NNTP "QUIT\n";
X        $_=<NNTP>;
X#       print STDOUT "close bad:$_" unless (/^205 /);
X        exit($code);
X}
X
Xsub group_cmd {
X        print NNTP "GROUP $group\n";
X        $_=<NNTP>;
X
X        split;
X        ($code,$num,$first,$last,$group)=@_;
X        if ($code != 211) {
X#               print STDOUT "group cmd problems:$_";
X                do quit_cmd(1);
X        }
X        return($first,$last);
X}
X
Xsub dokill {
X        kill(9,$child) if $child;
X}
X
Xsub startnntp {
X        local($name)=@_;
X
X        $SIG{'INT'}='dokill';
X
X        $sockaddr='Sna4x8';
X        chop($hostname=`hostname`);
X
X        ($n,$aliases,$proto)=getprotobyname('tcp');
X        ($n,$aliases,$port)=getservbyname('nntp','tcp');
X        ($n,$aliases,$type,$len,$thisaddr)=gethostbyname($hostname);
X        ($n,$aliases,$type,$len,$thataddr)=gethostbyname($name);
X        $this=pack($sockaddr,&AF_INET,0,$thisaddr);
X        $that=pack($sockaddr,&AF_INET,$port,$thataddr);
X
X        socket(NNTP,&PF_INET,&SOCK_STREAM,$proto) || die "socket: $!";
X        bind(NNTP,$this) || die "bind: $!";
X        connect(NNTP,$that) || die "connect: $!";
X
X        select(NNTP); $|=1;
X        select(STDIN); $|=1;
X        select(STDOUT); $|=1;
X}
X
Xsub read_nntp_header {
X        while (<NNTP>) {
X                last if (/^200 /);
X                last if (/^201 /);
X                exit(1) if (/^400 /);
X        }
X}
END_OF_FILE
if test 9256 -ne `wc -c <'read-comics'`; then
   echo shar: \"'read-comics'\" unpacked with wrong size!
fi
chmod +x 'read-comics'
# end of 'read-comics'
fi
echo shar: End of shell archive.
exit 0