This would probably work fine, alas, rn nor rrn are installed on my
workstation. (I'm using gnus)
> +---------- "Newscheck for nntp servers?" ----------
> | There is no local spool for news articles on my workstation, instead,
> | I get news from our company's nntp server. Has anyone written a
> | "newscheck" to open and properly query/parse an nntp server?
>
Lots of things were close, but nothing seemed to be precisely correct.
So I put together the following perl script from newcheck.faces
(from the faces distribution) and nntptap (from ftp.uu.net). This is
my first attempt at perl programming (ok, ok, so I'm a ways behind the
times...) and I'd love to hear about bugs and/or improvements.
Mark
Mark Warren 300 Oracle Parkway, office #423, mail #659304
warren@us.oracle.com Redwood Shores, CA 94065
(415) 506-4639 Voice or -7292 Fax Friends don't let friends run DOS
--------------------------->8 Cut Here 8<---------------------------
#!/home/mwarren/bin/perl
#
# run with the command line:
# faces -e nntpnewscheck.perl -f /home/mwarren/src2/faces/news -g +0+60
#
$cols = 2; $rows = 6;
$ZERO = $0;
$format = "%s\t%s\t%s\t%s\t%s\t%s\n";
$max = $cols * $rows;
sub usage {
die join("\n",@_) .
"\nusage: $ZERO [-h newshost] [-f check file]\n";
}
do 'getopt.pl' || die "Cannot do getopts.pl ($!)";
&Getopt('hf');
&usage("extra arguments: @ARGV") if $#ARGV > -1;
## defaults:
chop($thishost = `hostname`);
$fromhost = defined $opt_h ? $opt_h : 'oracle';
$checkfile = defined $opt_f ? $opt_f : '.newsrc-oracle';
$sockaddr = 'S n a4 x8';
@x = getprotobyname('tcp'); $proto = $x[2];
@x = getservbyname('nntp','tcp'); $port = $x[2];
sub hosttoaddr {
local($hostname) = @_;
local(@x);
if ($hostname =~ /^(\d+)+\.(\d+)\.(\d+)\.(\d+)$/) {
pack('C4', $1, $2, $3, $4);
} else {
@x = gethostbyname($hostname);
die "gethostbyname: $hostname ($!)" if $#x < 0;
$x[4];
}
}
$fromaddr = &hosttoaddr($fromhost);
$thisaddr = &hosttoaddr($thishost);
$thisproc = pack($sockaddr, 2, 0, $thisaddr);
$fromnntp = pack($sockaddr, 2, $port, $fromaddr);
$| = 1;
$FH = "nntp";
socket($FH, 2, 1, $proto) || die "$FH socket: $!";
bind($FH, $thisproc) || die "$FH bind: $!";
connect($FH, $fromnntp) || die "$FH connect: $!";
$oldfh = select($FH); $| = 1; select($oldfh);
(($_ = &get($FH)) =~ /^2/) || die "got $_ during greeting $FH";
sub put {
local($FH) = shift;
local($what) = shift;
print $FH "$what\n";
print "$FH >>> $what\n" if $verbose >= 3;
$what;
}
sub get {
local($FH) = shift;
local($what);
$what = <$FH>;
$what =~ s/\015//;
chop $what;
print "$FH >> $what\n" if $verbose >= 3;
$what;
}
#########################################################################
# Most of the new stuff is in the next two loops.
#
# Get latest article numbers for all news groups from the nntp server
&put($FH,"LIST");
while( $_ = &get($FH)){
last if /^\.$/;
next if /^2/;
($group, $high, $low, $posting) = split;
$news{$group}= $high;
}
# Get subscribed articles from $checkfile (format is assumed to be
# .newsrc format).
open checkfile;
while(<checkfile>){
($group, $articles) = split;
next if /!/; # skip unsubscribed groups
chop $group; # get rid of trailing `:' or `!'
@lastread = split(/[-,]/,$articles);
# Estimate unread articles by subtracting the last read article listed
# in $checkfile from the latest article number at the nntp server.
# Ignores intermediates.
$num = $news{$group} - $lastread[$#lastread];
$tarts += $num;
if (($n+1 < $max) && ($num > 0)) {
$n++;
$host = $abbr = $group;
$host = join('.', reverse split(/\./, $host));
$abbr =~ s/([^.])[^.]+\./$1./g;
$list .= sprintf($format, 'unknown', $host,
"$num $abbr", '', $group, '');
}
}
#
#
##########################################################################
if ($list) {
printf $format, 'news', "$fromhost", "$tarts/$n", '', '', '';
printf "Cols=%d Rows=%d\n", &lesser($n, $cols),
&lesser(($n - 1) / $cols + 1, $rows);
print $list;
} else {
printf $format, 'nonews', '', "0/0", '', '', '';
print "Cols=1 Rows=1\n";
printf $format, 'nonews', '', 'No news', '', 'No news', '';
}
sub lesser {
local($a, $b) = @_;
($a < $b) ? $a : $b;
}
exit 0;