From fc3b6024fcf0bf0394e6239639cbe31786b0cad8 Mon Sep 17 00:00:00 2001 From: ivan Date: Tue, 5 Nov 2002 20:29:57 +0000 Subject: lost? --- FS/bin/freeside-sqlradius-radacctd | 180 +++++++++++++++++++++++++++++++++++++ 1 file changed, 180 insertions(+) create mode 100644 FS/bin/freeside-sqlradius-radacctd (limited to 'FS/bin/freeside-sqlradius-radacctd') diff --git a/FS/bin/freeside-sqlradius-radacctd b/FS/bin/freeside-sqlradius-radacctd new file mode 100644 index 000000000..4e8d57c51 --- /dev/null +++ b/FS/bin/freeside-sqlradius-radacctd @@ -0,0 +1,180 @@ +#!/usr/bin/perl -Tw + +use strict; +use vars qw( $log_file $sigterm $sigint ); +use subs qw( _die _logmsg ); +use Fcntl qw(:flock); +use POSIX qw(setsid); +use Date::Format; +use IO::File; +use FS::UID qw(adminsuidsetup); +#use FS::Record qw(qsearch qsearchs); +#use FS::part_export; +#use FS::svc_acct; +#use FS::cust_svc; + +#lots of false laziness w/freeside-queued + +my $user = shift or die &usage; + +#my $pid_file = "/var/run/freeside-sqlradius-radacctd.$user.pid"; +my $pid_file = "/var/run/freeside-sqlradius-radacctd.pid"; + +&daemonize1; + +#sub REAPER { my $pid = wait; $SIG{CHLD} = \&REAPER; $kids--; } +#$SIG{CHLD} = \&REAPER; + +$sigterm = 0; +$sigint = 0; +$SIG{INT} = sub { warn "SIGINT received; shutting down\n"; $sigint++; }; +$SIG{TERM} = sub { warn "SIGTERM received; shutting down\n"; $sigterm++; }; + +my $freeside_gid = scalar(getgrnam('freeside')) + or die "can't setgid to freeside group\n"; +$) = $freeside_gid; +$( = $freeside_gid; +#if freebsd can't setuid(), presumably it can't setgid() either. grr fleabsd +($(,$)) = ($),$(); +$) = $freeside_gid; + +$> = $FS::UID::freeside_uid; +$< = $FS::UID::freeside_uid; +#freebsd is sofa king broken, won't setuid() +($<,$>) = ($>,$<); +$> = $FS::UID::freeside_uid; + +#$ENV{HOME} = (getpwuid($>))[7]; #for ssh +adminsuidsetup $user; + +$log_file= "/usr/local/etc/freeside/sqlradius-radacctd-log.". $FS::UID::datasrc; + +&daemonize2; + +$SIG{__DIE__} = \&_die; +$SIG{__WARN__} = \&_logmsg; + +warn "freeside-sqlradius-radacctd starting\n"; + +#eslaf + +#my $machine = shift or die &usage; #would need to be up higher for real +my @exports = qsearch('part_export', { 'exporttype' => 'sqlradius' } ); + +while (1) { + + my %seen = (); + foreach my $export ( @exports ) { + next if $seen{$export->option('datasrc')}++; + my $dbh = DBI->connect( + map { $export->option($_) } qw( datasrc username password ) + ) or do { + warn "can't connect to ". $export->option('datasrc'). ": ". $DBI::errstr; + next; + } + + # find old radacct position + #$lastid = 0; + + # get new radacct records + my $sth = $dbh->prepare('SELECT * FROM radacct WHERE radacctid > ?') or do { + warn "can't select in radacct table from ". $export->option('datasrc'). + ": ". $dbh->errstr; + next; + }; + + while ( my $radacct = $sth->fetchrow_arrayref({}) ) { + + my $session = new FS::session { + portnum => + svcnum => + login => + #logout => + }; + + } + + # look for updated radacct records & replace them + + } + + sleep 5; + +} + +#more false laziness w/freeside-queued + +sub usage { + die "Usage:\n\n freeside-sqlradius-radacctd user\n"; +} + +sub _die { + my $msg = shift; + unlink $pid_file if -e $pid_file; + _logmsg($msg); +} + +sub _logmsg { + chomp( my $msg = shift ); + my $log = new IO::File ">>$log_file"; + flock($log, LOCK_EX); + seek($log, 0, 2); + print $log "[". time2str("%a %b %e %T %Y",time). "] [$$] $msg\n"; + flock($log, LOCK_UN); + close $log; +} + +sub daemonize1 { + + chdir "/" or die "Can't chdir to /: $!"; + open STDIN, '/dev/null' or die "Can't read /dev/null: $!"; + defined(my $pid = fork) or die "Can't fork: $!"; + if ( $pid ) { + print "freeside-sqlradius-radacctd started with pid $pid\n"; + #logging to $log_file\n"; + exit unless $pid_file; + my $pidfh = new IO::File ">$pid_file" or exit; + print $pidfh "$pid\n"; + exit; + } + #open STDOUT, '>/dev/null' + # or die "Can't write to /dev/null: $!"; + #setsid or die "Can't start a new session: $!"; + #open STDERR, '>&STDOUT' or die "Can't dup stdout: $!"; + +} + +sub daemonize2 { + open STDOUT, '>/dev/null' + or die "Can't write to /dev/null: $!"; + setsid or die "Can't start a new session: $!"; + open STDERR, '>&STDOUT' or die "Can't dup stdout: $!"; +} + + +#eslaf + +=head1 NAME + +freeside-sqlradius-radacctd - Real-time radacct import daemon + +=head1 SYNOPSIS + + freeside-sqlradius-radacctd username + +=head1 DESCRIPTION + +Imports records from an SQL radacct table in real-time into the session +monitor. + +This enables per-minute or per-hour charges as well as the +"View active NAS ports" function. + +B is a username added by freeside-adduser. + +=head1 SEE ALSO + +session.html from the base documentation. + +=cut + -- cgit v1.2.1 From beba6672fb9c9c5769c81f8029bb88cd2bc910e9 Mon Sep 17 00:00:00 2001 From: ivan Date: Mon, 25 Apr 2005 09:33:35 +0000 Subject: pick up freeside-sqlradius-radacctd again after all these years, now it just needs to update the "seconds" field(s), finally closes: Bug#1125 --- FS/bin/freeside-sqlradius-radacctd | 202 +++++++++++++++---------------------- 1 file changed, 83 insertions(+), 119 deletions(-) (limited to 'FS/bin/freeside-sqlradius-radacctd') diff --git a/FS/bin/freeside-sqlradius-radacctd b/FS/bin/freeside-sqlradius-radacctd index 4e8d57c51..8d8e5233c 100644 --- a/FS/bin/freeside-sqlradius-radacctd +++ b/FS/bin/freeside-sqlradius-radacctd @@ -1,159 +1,116 @@ #!/usr/bin/perl -Tw use strict; -use vars qw( $log_file $sigterm $sigint ); -use subs qw( _die _logmsg ); -use Fcntl qw(:flock); -use POSIX qw(setsid); -use Date::Format; +use vars qw( @part_export ); +use subs qw(myshutdown); +use POSIX qw(:sys_wait_h); use IO::File; -use FS::UID qw(adminsuidsetup); -#use FS::Record qw(qsearch qsearchs); -#use FS::part_export; +use FS::Daemon qw(daemonize1 drop_root logfile daemonize2 sigint sigterm); +use FS::UID qw(adminsuidsetup); #forksuidsetup driver_name dbh myconnect); +use FS::Record qw(qsearch); # qsearchs); +use FS::part_export; #use FS::svc_acct; #use FS::cust_svc; -#lots of false laziness w/freeside-queued - my $user = shift or die &usage; -#my $pid_file = "/var/run/freeside-sqlradius-radacctd.$user.pid"; -my $pid_file = "/var/run/freeside-sqlradius-radacctd.pid"; - -&daemonize1; - -#sub REAPER { my $pid = wait; $SIG{CHLD} = \&REAPER; $kids--; } -#$SIG{CHLD} = \&REAPER; - -$sigterm = 0; -$sigint = 0; -$SIG{INT} = sub { warn "SIGINT received; shutting down\n"; $sigint++; }; -$SIG{TERM} = sub { warn "SIGTERM received; shutting down\n"; $sigterm++; }; - -my $freeside_gid = scalar(getgrnam('freeside')) - or die "can't setgid to freeside group\n"; -$) = $freeside_gid; -$( = $freeside_gid; -#if freebsd can't setuid(), presumably it can't setgid() either. grr fleabsd -($(,$)) = ($),$(); -$) = $freeside_gid; +#daemonize1('freeside-sqlradius-radacctd', $user); #keep unique pid files w/multi installs +daemonize1('freeside-sqlradius-radacctd'); -$> = $FS::UID::freeside_uid; -$< = $FS::UID::freeside_uid; -#freebsd is sofa king broken, won't setuid() -($<,$>) = ($>,$<); -$> = $FS::UID::freeside_uid; +drop_root(); #$ENV{HOME} = (getpwuid($>))[7]; #for ssh + adminsuidsetup $user; -$log_file= "/usr/local/etc/freeside/sqlradius-radacctd-log.". $FS::UID::datasrc; +logfile( "/usr/local/etc/freeside/sqlradius-radacctd-log.". $FS::UID::datasrc ); -&daemonize2; +daemonize2(); -$SIG{__DIE__} = \&_die; -$SIG{__WARN__} = \&_logmsg; +#-- -warn "freeside-sqlradius-radacctd starting\n"; +@part_export = + qsearch('part_export', { 'exporttype' => 'sqlradius' } ); +push @part_export, + qsearch('part_export', { 'exporttype' => 'sqlradius_withdomain' } ); -#eslaf +@part_export = grep { ! $_->option('ignore_accounting') } @part_export; -#my $machine = shift or die &usage; #would need to be up higher for real -my @exports = qsearch('part_export', { 'exporttype' => 'sqlradius' } ); +die "no sqlradius or sqlradius_withdomain exports without ignore_accounting" + unless @part_export; while (1) { - my %seen = (); - foreach my $export ( @exports ) { - next if $seen{$export->option('datasrc')}++; - my $dbh = DBI->connect( - map { $export->option($_) } qw( datasrc username password ) - ) or do { - warn "can't connect to ". $export->option('datasrc'). ": ". $DBI::errstr; - next; - } - - # find old radacct position - #$lastid = 0; - - # get new radacct records - my $sth = $dbh->prepare('SELECT * FROM radacct WHERE radacctid > ?') or do { - warn "can't select in radacct table from ". $export->option('datasrc'). - ": ". $dbh->errstr; + #fork off one kid per export (machine) + # _>{'_radacct_kid'} is an evil kludge + foreach my $part_export ( grep ! $_->{'_radacct_kid'}, @part_export ) { + + defined( my $pid = fork ) or do { + warn "WARNING: can't fork to spawn child for ". $part_export->machine; next; }; - while ( my $radacct = $sth->fetchrow_arrayref({}) ) { + if ( $pid ) { + $part_export->{'_radacct_kid'} = $pid; + warn "child $pid spawned for ". $part_export->machine; + } else { #kid time - my $session = new FS::session { - portnum => - svcnum => - login => - #logout => - }; + adminsuidsetup($user); #get our own db handle - } + until ( sigint || sigterm ) { + $part_export->update_svc_acct(); + sleep 1; + } - # look for updated radacct records & replace them + warn "child for ". $part_export->machine. " done"; + exit; + + } #eo kid } - sleep 5; + #reap up any kids that died... + &reap_kids; + myshutdown() if sigterm() || sigint(); + + sleep 5; } -#more false laziness w/freeside-queued +#-- -sub usage { - die "Usage:\n\n freeside-sqlradius-radacctd user\n"; -} +sub myshutdown { + &reap_kids; -sub _die { - my $msg = shift; - unlink $pid_file if -e $pid_file; - _logmsg($msg); -} + #kill all the kids + kill 'TERM', $_ foreach grep $_, map $_->{'_radacct_kid'}, @part_export; -sub _logmsg { - chomp( my $msg = shift ); - my $log = new IO::File ">>$log_file"; - flock($log, LOCK_EX); - seek($log, 0, 2); - print $log "[". time2str("%a %b %e %T %Y",time). "] [$$] $msg\n"; - flock($log, LOCK_UN); - close $log; + my $wait = 12; #wait up to 1 minute + while ( ( grep $_->{'_radacct_kid'}, @part_export ) && $wait-- ) { + warn "waiting for children to terminate"; + sleep 5; + &reap_kids; + } + warn "abandoning children" if grep $_->{'_radacct_kid'}, @part_export; + die "exiting"; } -sub daemonize1 { - - chdir "/" or die "Can't chdir to /: $!"; - open STDIN, '/dev/null' or die "Can't read /dev/null: $!"; - defined(my $pid = fork) or die "Can't fork: $!"; - if ( $pid ) { - print "freeside-sqlradius-radacctd started with pid $pid\n"; - #logging to $log_file\n"; - exit unless $pid_file; - my $pidfh = new IO::File ">$pid_file" or exit; - print $pidfh "$pid\n"; - exit; +sub reap_kids { + #warn "reaping kids\n"; + foreach my $part_export ( grep $_->{'_radacct_kid'}, @part_export ) { + my $pid = $part_export->{'_radacct_kid'}; + my $kid = waitpid($pid, WNOHANG); + if ( $kid > 0 ) { + $part_export->{'_radacct_kid'} = ''; + } } - #open STDOUT, '>/dev/null' - # or die "Can't write to /dev/null: $!"; - #setsid or die "Can't start a new session: $!"; - #open STDERR, '>&STDOUT' or die "Can't dup stdout: $!"; - + #warn "done reaping\n"; } -sub daemonize2 { - open STDOUT, '>/dev/null' - or die "Can't write to /dev/null: $!"; - setsid or die "Can't start a new session: $!"; - open STDERR, '>&STDOUT' or die "Can't dup stdout: $!"; +sub usage { + die "Usage:\n\n freeside-sqlradius-radacctd user\n"; } - -#eslaf - =head1 NAME freeside-sqlradius-radacctd - Real-time radacct import daemon @@ -164,17 +121,24 @@ freeside-sqlradius-radacctd - Real-time radacct import daemon =head1 DESCRIPTION -Imports records from an SQL radacct table in real-time into the session -monitor. - -This enables per-minute or per-hour charges as well as the -"View active NAS ports" function. +Imports records from an the SQL radacct tables of all sqlradius and +sqlradius_withdomain exports (except those with the ignore_accounting flag) and +updates the svc_acct.seconds for each account. Runs as a daemon and updates +the database in real-time. B is a username added by freeside-adduser. -=head1 SEE ALSO +=head1 RADIUS DATABASE CHANGES + +ALTER TABLE radacct ADD COLUMN FreesideStatus varchar(32) NULL; -session.html from the base documentation. +If you want to ignore the existing accountg records, also do: + +UPDATE TABLE radacct SET FreesideStatus = 'done' WHERE FreesideStatus IS NULL; + +=head1 SEE ALSO =cut +1; + -- cgit v1.2.1 From 22095d167d138ae7561b01d5cfbf4df5ae73a4c8 Mon Sep 17 00:00:00 2001 From: ivan Date: Tue, 3 May 2005 08:51:38 +0000 Subject: not running with elevated privs, -T not necessary --- FS/bin/freeside-sqlradius-radacctd | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) (limited to 'FS/bin/freeside-sqlradius-radacctd') diff --git a/FS/bin/freeside-sqlradius-radacctd b/FS/bin/freeside-sqlradius-radacctd index 8d8e5233c..d66c875b9 100644 --- a/FS/bin/freeside-sqlradius-radacctd +++ b/FS/bin/freeside-sqlradius-radacctd @@ -1,4 +1,4 @@ -#!/usr/bin/perl -Tw +#!/usr/bin/perl -w use strict; use vars qw( @part_export ); -- cgit v1.2.1 From 8a90e2477b53a9c1f7472a7145858b6a5765d966 Mon Sep 17 00:00:00 2001 From: ivan Date: Mon, 28 Nov 2005 17:07:50 +0000 Subject: startup freeside-sqlradius-radacctd for radiator export too --- FS/bin/freeside-sqlradius-radacctd | 7 ++++++- 1 file changed, 6 insertions(+), 1 deletion(-) (limited to 'FS/bin/freeside-sqlradius-radacctd') diff --git a/FS/bin/freeside-sqlradius-radacctd b/FS/bin/freeside-sqlradius-radacctd index d66c875b9..d75592377 100644 --- a/FS/bin/freeside-sqlradius-radacctd +++ b/FS/bin/freeside-sqlradius-radacctd @@ -4,7 +4,7 @@ use strict; use vars qw( @part_export ); use subs qw(myshutdown); use POSIX qw(:sys_wait_h); -use IO::File; +#use IO::File; use FS::Daemon qw(daemonize1 drop_root logfile daemonize2 sigint sigterm); use FS::UID qw(adminsuidsetup); #forksuidsetup driver_name dbh myconnect); use FS::Record qw(qsearch); # qsearchs); @@ -29,10 +29,15 @@ daemonize2(); #-- +#don't just look for ->can('usage_sessions'), we're sqlradius-specific +# (radiator is supposed to be setup with a radacct table) + @part_export = qsearch('part_export', { 'exporttype' => 'sqlradius' } ); push @part_export, qsearch('part_export', { 'exporttype' => 'sqlradius_withdomain' } ); +push @part_export, + qsearch('part_export', { 'exporttype' => 'radiator' } ); @part_export = grep { ! $_->option('ignore_accounting') } @part_export; -- cgit v1.2.1 From 8293ef7884a56f92681d2af8d7581dece7446560 Mon Sep 17 00:00:00 2001 From: ivan Date: Mon, 28 Nov 2005 17:12:04 +0000 Subject: update docs and error message for all three supporte exports --- FS/bin/freeside-sqlradius-radacctd | 11 ++++++----- 1 file changed, 6 insertions(+), 5 deletions(-) (limited to 'FS/bin/freeside-sqlradius-radacctd') diff --git a/FS/bin/freeside-sqlradius-radacctd b/FS/bin/freeside-sqlradius-radacctd index d75592377..324e4ab1e 100644 --- a/FS/bin/freeside-sqlradius-radacctd +++ b/FS/bin/freeside-sqlradius-radacctd @@ -41,7 +41,8 @@ push @part_export, @part_export = grep { ! $_->option('ignore_accounting') } @part_export; -die "no sqlradius or sqlradius_withdomain exports without ignore_accounting" +die "no sqlradius, sqlradius_withdomain or radiator exports without". + " ignore_accounting" unless @part_export; while (1) { @@ -126,10 +127,10 @@ freeside-sqlradius-radacctd - Real-time radacct import daemon =head1 DESCRIPTION -Imports records from an the SQL radacct tables of all sqlradius and -sqlradius_withdomain exports (except those with the ignore_accounting flag) and -updates the svc_acct.seconds for each account. Runs as a daemon and updates -the database in real-time. +Imports records from an the SQL radacct tables of all sqlradius, +sqlradius_withdomain and radiator exports (except those with the +ignore_accounting flag) and updates the svc_acct.seconds for each account. +Runs as a daemon and updates the database in real-time. B is a username added by freeside-adduser. -- cgit v1.2.1 From 4956c4ac2f2d6e95985cc26cbfd7cba57882fa12 Mon Sep 17 00:00:00 2001 From: ivan Date: Mon, 28 Nov 2005 17:13:30 +0000 Subject: in POD example, remove extra SQL that Pg doesn't need and MySQL doesn't like --- FS/bin/freeside-sqlradius-radacctd | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) (limited to 'FS/bin/freeside-sqlradius-radacctd') diff --git a/FS/bin/freeside-sqlradius-radacctd b/FS/bin/freeside-sqlradius-radacctd index 324e4ab1e..e98eaa015 100644 --- a/FS/bin/freeside-sqlradius-radacctd +++ b/FS/bin/freeside-sqlradius-radacctd @@ -140,7 +140,7 @@ ALTER TABLE radacct ADD COLUMN FreesideStatus varchar(32) NULL; If you want to ignore the existing accountg records, also do: -UPDATE TABLE radacct SET FreesideStatus = 'done' WHERE FreesideStatus IS NULL; +UPDATE radacct SET FreesideStatus = 'done' WHERE FreesideStatus IS NULL; =head1 SEE ALSO -- cgit v1.2.1