home *** CD-ROM | disk | FTP | other *** search
/ Usenet 1994 January / usenetsourcesnewsgroupsinfomagicjanuary1994.iso / sources / unix / volume26 / tpage2 / tpage.pl < prev    next >
Encoding:
Perl Script  |  1992-06-12  |  9.5 KB  |  308 lines

  1. #! /usr/local/bin/perl4.019
  2.  
  3. # tpage.pl -- front-end to tpage system.
  4. #   by Tom Limoncelli, tal@warren.mentorg.com
  5. #   Copyright (c) 1992, Tom Limoncelli
  6. #   The sources can be freely copied for non-commercial use only
  7. #   and only if they are unmodified.
  8.  
  9. # Version 1.0 -- See file HISTORY for details.
  10.  
  11. ####################################################################
  12. #
  13. # Parameters that the user can set:
  14. #
  15. ####################################################################
  16.  
  17. $debug = 0;
  18. # leave that off
  19.  
  20. $MAX_WINDOW = 16;
  21. #This is the number of charactors at a time do you see on your
  22. # pager.  This is used when word-wrapping.
  23.  
  24. $MAX_MESSAGE = 160;
  25. # How many bytes can one message be.  This must be less than 250
  26. # minus the length of your PIN.  This is because each packet in the ixo
  27. # protocol must be less than 250 chars.  If you have a pager that can
  28. # receive longer messages, you'll have to modify the ixocico.c program
  29. # to handle the "packet continuation" feature.  No biggie, just 
  30. # something that I didn't feel like implementing since I can't even 
  31. # test it with my pager.
  32.  
  33. $DEFAULT_S = '/home/adm/lib/tpage/schedule';
  34. # (default: '/home/adm/lib/tpage/schedule')
  35. # If you plan on using the schedule feature, this is the file
  36. # name where beep2.pl will look for the schedule.  It must be accessable
  37. # on the machine that runs tpage.pl, not the machine that runs the
  38. # daemon (tpaged.pl).
  39.  
  40. $DEFAULT_T = '/home/adm/lib/tpage/table';
  41. # (default: '/home/adm/lib/tpage/table')
  42. # If you plan on using the table feature (that is, store a list
  43. # of people and their paging info), this is the file name where tpage.pl
  44. # will look for the data.  It must be accessable on the machine that
  45. # runs tpage.pl, not the machine that runs the daemon (tpaged.pl).
  46.  
  47. $QUEUE_DIR = '/home/adm/lib/tpage/pqueue/';
  48. # (default: '/home/adm/lib/tpage/pqueue/'
  49. # This is the directory where messages will be queued.  The trailing "/"
  50. # is required.
  51.  
  52. ####################################################################
  53. # some helping functions
  54.  
  55. require("getopts.pl");
  56.  
  57. sub strip_string {
  58.     local($s) = @_;
  59. print "DEBUG: REMOVE_CONTROLS :", $s, ":\n" if $debug;
  60.     $s =~ tr/\200-\377/\000\177/;    # remove high-bit
  61.     $s =~ tr/\000-\037\177//d;    # delete unprintables
  62.     $s =~ s/\s+/ /g;            # change groups of white space into " "
  63.     $s =~ s/^ //;                # remove spaces from the front
  64.     $s =~ s/ $//;                # remove spaces from the end
  65.     
  66. print "DEBUG: REMOVE_DONE :", $s, ":\n" if $debug;
  67.     return $s;
  68. }
  69.  
  70. ####################################################################
  71. # Here's the actual program
  72.  
  73. ####################################################################
  74. # Get the command line options.
  75.  
  76. # set the defaults
  77.  
  78. print "\n";
  79.  
  80. # -S  schedule file
  81. $opt_S = $DEFAULT_S;
  82. # -T  pager table
  83. $opt_T = $DEFAULT_T;
  84. # -U  use urgent schedule if no one is scheduled for that time.
  85. $opt_U = 0;
  86. # -d  number to dial. (first name in list only)
  87. $opt_d = "";
  88. # -p  pager id to use. (first name in list only)
  89. $opt_p = "";
  90. # -t  tee all stdin into stdout.
  91. $opt_t = 0;
  92. # -v  verbose mode.
  93. $opt_v = 0;
  94. # -m  input will be in RFC822, skip boring stuff.
  95. $opt_m = 0;
  96. # -M  like -m but also skip >-quoted text.
  97. $opt_M = 0;
  98. # -e  if it errors, send email to this person.
  99. $opt_e = "";
  100.  
  101. $line_from = "";
  102. $line_subj = "";
  103. $line_prio = "";
  104.  
  105. do Getopts('S:T:Ud:p:tvmMe:');
  106.  
  107. # get the wholist
  108. $opt_wholist = shift (@ARGV);
  109. $opt_wholist = "special" if $opt_d && $opt_p;
  110.  
  111. ####################################################################
  112. # Get the message (either on the command line or stdin; handle -t -m -M
  113.  
  114. # bunch up all the rest
  115. $opt_message = join(' ', @ARGV);
  116. print "opt_message = :$opt_message:\n" if $debug;
  117. $opt_message = &strip_string( $opt_message ) if $opt_message;
  118. print "opt_message = :$opt_message:\n" if $debug;
  119. die "$0: No message.  Cat got your tongue?" if ( $opt_message eq "" );
  120.  
  121. die "$0: Can't use -m/-M and have message on the command line"
  122.         if ($opt_m || $opt_M) && $opt_message ne '-';
  123.  
  124. # maybe get message from stdin, echoing to stdout if $opt_t;
  125. if ($opt_message eq '-') {
  126.     $opt_message = '';
  127.     # handle -m headers first
  128.     if ($opt_m) {
  129.         print "DEBUG: Doing -m work\n" if $debug;
  130.         local($line) = "";
  131.         while (<>) {
  132.             if ( /^\S/ || /^$/ ) {    # start of new header, do previous one
  133.                 $line_from = substr($line, 6) if $line =~ /^From/;
  134.                 $line_subj = substr($line, 9) if $line =~ /^Subject: /;
  135.                 $line_prio = substr($line, 10) if $line =~ /^Priority: /;
  136.                 $line = $_;
  137.             } else {
  138.                 $line .= $_;
  139.             }
  140.             last if /^$/;            # end of headers, start processing
  141.         }
  142.     }
  143.     $line_from = &strip_string( $line_from ) if $line_from;
  144.     $line_subj = &strip_string( $line_subj ) if $line_subj;
  145.     $line_prio = &strip_string( $line_prio ) if $line_prio;
  146.  
  147.     while (<>) {
  148. # -M means skip if the line is news quoted email.
  149. # a line is news quoted if it begins with one of the following:
  150. #      [white] [word] quote
  151. # where "white" is any amount of whitespace (zero or one times)
  152. # where word is any letters/numbers (userid) (zero or one times)
  153. # where quote is any of >, <, }, or {.
  154.         next if $opt_M && /^\s*\S*[\>\}\<\{]/;
  155.         print if $opt_t;
  156.         $_ = &strip_string( $_ );
  157.         $opt_message .= $_;
  158.         $opt_message .= " ";
  159.         # once we've got quite a bunch, screw the rest.
  160.         if ( length($opt_message) > ($MAX_MESSAGE * 8)) {
  161.              while (<>) { print if $opt_t; }
  162.         }
  163.     }
  164. }
  165.  
  166. ####################################################################
  167. # massage the message
  168.  
  169. if ($debug) {
  170.     print "DEBUG: pre-processed messages\n";
  171.     print "FROM=:$line_from:\n";
  172.     print "PRIO=:$line_prio:\n";
  173.     print "SUBJ=:$line_subj:\n";
  174.     print "MESS=:$opt_message:\n";
  175. }
  176.  
  177. $line_from = substr( "F: " . $line_from . ' ' x $MAX_WINDOW,
  178.         0, $MAX_WINDOW) if $line_from;        # pad to display size
  179.  
  180. $line_prio = substr( "P: " . $line_prio . ' ' x $MAX_WINDOW,
  181.         0, $MAX_WINDOW) if $line_prio;        # pad to display size
  182.  
  183. $l = $MAX_WINDOW * int ((length($line_subj)+$MAX_WINDOW+2) / $MAX_WINDOW);
  184. $line_subj = substr( "S: " . $line_subj . ' ' x $MAX_WINDOW,
  185.         0, $l) if $line_subj;        # pad to display size
  186.  
  187. $opt_message = &strip_string( $opt_message );
  188. # put it all together
  189. $the_message = substr( $line_prio . $line_from . $line_subj . $opt_message, 0, $MAX_MESSAGE);
  190.  
  191. if ($debug) {
  192.     print "DEBUG: post-processed messages\n";
  193.     print "FROM=:$line_from:\n";
  194.     print "PRIO=:$line_prio:\n";
  195.     print "SUBJ=:$line_subj:\n";
  196.     print "MESS=:$opt_message:\n";
  197.     print "COMPLETE=:$the_message:\n";
  198. }
  199.  
  200. ####################################################################
  201. # At this point we can do some more of the sanity checking.
  202.  
  203. #die "$0: Conflicting verbosity levels" if ($opt_s && ($opt_v || $opt_V));
  204. die "$0: Schedule file $opt_S can't be read/found"
  205.         unless ( ($opt_wholist eq '-') || (-r $opt_S && -r $opt_T) );
  206. die "$0: Pager table $opt_T can't be read"
  207.         unless ($opt_d && $opt_p) || ( -r $opt_T );
  208.  
  209. ####################################################################
  210. # use the schedule to fill in "who" if we need.
  211.  
  212. if ($opt_wholist eq '-') {
  213.     local($sec,$min,$hour,$mday,$mon,$year,$wday,$yday,$isdst) = localtime(time);
  214.     local($l) = $wday;
  215.     local($h) = $hour * 2 + int ($hour / 30) + 1;
  216.     local($w,$found1) = 0;
  217.  
  218. print "L = $l\n" if $debug;
  219. print "H = $h\n" if $debug;
  220. print "U = $opt_U\n" if $debug;
  221.  
  222.     # Read from schedule until you hit a line beginning with $l.
  223.     # At that point, get the char $h bytes in.  If that byte is "-",
  224.     # and $opt_U, keep going.
  225.     print "\nChecking schedule:\n\n";
  226.     open(SCHED, "<$opt_S") || die "Can't open $opt_S: $!";
  227.     while (1) {
  228.         $w = '';
  229.         while (<SCHED>) {
  230.             last if /^${l}/;
  231.         }
  232.         $w = substr($_, $h, 1);
  233.         $found1 = 1 if $w;                # we found one!
  234.         next if $opt_U && $w eq '-';
  235.         last;
  236.     }
  237.  
  238.     die "$0: Schedule doesn't have a line for this day of the week.\n" unless $found1;
  239.     die "$0: No one is assigned to be on duty at this time.\n" if $w eq '-';
  240.  
  241.     # Now search until a line begins with $w= and assign line to wholist
  242.     $opt_wholist = '';
  243.     while (<SCHED>) {
  244.         next unless /^${w}\=/;
  245.         chop( $opt_wholist = substr($_, 2) );
  246.     }
  247.     die "$0: Schedule error: No people assigned to '" . $w . "'\n" unless $opt_wholist;
  248.     close SCHED;
  249. }
  250.  
  251. ####################################################################
  252. # we we still don't know who to call, bail out.
  253.  
  254. die "$0: The schedule didn't specify anyone to call!"
  255.         unless ($opt_wholist) || ($opt_d && $opt_p);
  256. die "$0: There isn't anyone scheduled for this time of day."
  257.         if $opt_wholist eq '-';
  258.  
  259. ####################################################################
  260. # rotate through "$opt_wholist" and queue each person
  261.  
  262. $cnt = 0;
  263. foreach $who ( split(',', $opt_wholist) ) {
  264.     $cnt++;
  265.  
  266.     # look up "who"'s information
  267.     open(TABL, "<$opt_T") || die "Can't open $opt_T: $!";
  268.     while (<TABL>) {
  269.         next if /^#/;
  270.         chop;
  271.         local($name,$phonen,$phonea,$pin) = split;
  272.         if ($name eq $who) {
  273.             $opt_d = $phonea unless $opt_d;    # might have it from ARGV
  274.             $opt_p = $pin unless $opt_p;    # might have it from ARGV
  275.             print "Got $who is :$opt_d:$opt_p:\n" if $debug;
  276.             last;
  277.         }
  278.     }
  279.     close TABL;
  280.  
  281.     die "$0: We were not able to find a phone number for $who.\n" unless $opt_d;
  282.     die "$0: We were not able to find a PIN for $who.\n" unless $opt_p;
  283.  
  284.     # write into the queue the proper information.
  285.     chop( $thishost = `hostname` );
  286.     $qname = $QUEUE_DIR . "P" . $thishost . time . $cnt;
  287.     print "QUEUE=$qname\n" if $debug;
  288.     open(QU, ">$qname" ) || die "Can't open $qname for writing: $!";
  289.     print QU "A\n";
  290.     print QU $opt_d, "\n";
  291.     print QU $opt_p, "\n";
  292.     if ($opt_e eq '-') {     # '-' means send errors to $who,
  293.         print QU $who, "\n";
  294.     } else {
  295.         print QU $opt_e, "\n";
  296.     }
  297.     print QU $the_message, "\n";
  298.     print QU "X\n";
  299.     close QU;
  300.     print "Message queued for $who: $the_message\n";
  301.     
  302.     # zap the phone# and PIN so that ARGV's info only effects us once.
  303.     $opt_d = "";
  304.     $opt_p = "";
  305. }
  306.  
  307. print "\n";
  308.