5 @ISA @EXPORT_OK $cgi $dbh $freeside_uid $user
6 $conf_dir $secrets $datasrc $db_user $db_pass %callback @callback
7 $driver_name $AutoCommit
10 getsecrets cgisetotaker
13 use Carp qw(carp croak cluck);
19 @EXPORT_OK = qw(checkeuid checkruid cgisuidsetup adminsuidsetup forksuidsetup
20 getotaker dbh datasrc getsecrets driver_name myconnect );
22 $freeside_uid = scalar(getpwnam('freeside'));
24 $conf_dir = "/usr/local/etc/freeside/";
26 $AutoCommit = 1; #ours, not DBI
30 FS::UID - Subroutines for database login and assorted other stuff
34 use FS::UID qw(adminsuidsetup cgisuidsetup dbh datasrc getotaker
40 $dbh = cgisuidsetup($cgi);
46 $driver_name = driver_name;
50 Provides a hodgepodge of subroutines.
56 =item adminsuidsetup USER
58 Sets the user to USER (see config.html from the base documentation).
59 Cleans the environment.
60 Make sure the script is running as freeside, or setuid freeside.
61 Opens a connection to the database.
62 Swaps real and effective UIDs.
63 Runs any defined callbacks (see below).
64 Returns the DBI database handle (usually you don't need this).
69 $dbh->disconnect if $dbh;
75 croak "fatal: adminsuidsetup called without arguements" unless $user;
77 $user =~ /^([\w\-\.]+)$/ or croak "fatal: illegal user $user";
80 $ENV{'PATH'} ='/usr/local/bin:/usr/bin:/usr/ucb:/bin';
81 $ENV{'SHELL'} = '/bin/sh';
82 $ENV{'IFS'} = " \t\n";
85 $ENV{'BASH_ENV'} = '';
87 croak "Not running uid freeside!" unless checkeuid();
91 use FS::Schema qw(reload_dbdef);
92 reload_dbdef("/usr/local/etc/freeside/dbdef.$datasrc")
93 unless $FS::Schema::setup_hack;
95 FS::CurrentUser->load_user($user);
97 foreach ( keys %callback ) {
99 # breaks multi-database installs # delete $callback{$_}; #run once
102 &{$_} foreach @callback;
108 DBI->connect( getsecrets, { 'AutoCommit' => 0,
110 'ShowErrorStatement' => 1,
113 or die "DBI->connect error: $DBI::errstr\n";
116 =item install_callback
118 A package can install a callback to be run in adminsuidsetup by passing
119 a coderef to the FS::UID->install_callback class method. If adminsuidsetup has
120 run already, the callback will also be run immediately.
122 $coderef = sub { warn "Hi, I'm returning your call!" };
123 FS::UID->install_callback($coderef);
125 install_callback FS::UID sub {
126 warn "Hi, I'm returning your call!"
131 sub install_callback {
133 my $callback = shift;
134 push @callback, $callback;
135 &{$callback} if $dbh;
138 =item cgisuidsetup CGI_object
140 Takes a single argument, which is a CGI (see L<CGI>) or Apache (see L<Apache>)
141 object (CGI::Base is depriciated). Runs cgisetotaker and then adminsuidsetup.
147 if ( $cgi->isa('CGI::Base') ) {
148 carp "Use of CGI::Base is depriciated";
149 } elsif ( $cgi->isa('Apache') ) {
151 } elsif ( ! $cgi->isa('CGI') ) {
152 croak "fatal: unrecognized object $cgi";
155 adminsuidsetup($user);
160 Returns the CGI (see L<CGI>) object.
165 carp "warning: \$FS::UID::cgi isa Apache" if $cgi->isa('Apache');
171 Returns the DBI database handle.
181 Returns the DBI data source.
191 Returns just the driver name portion of the DBI data source.
196 return $driver_name if defined $driver_name;
197 $driver_name = ( split(':', $datasrc) )[1];
201 croak "suidsetup depriciated";
206 Returns the current Freeside user.
216 Sets and returns the CGI REMOTE_USER. $cgi should be defined as a CGI.pm
217 object (see L<CGI>) or an Apache object (see L<Apache>). Support for CGI::Base
218 and derived classes is depriciated.
223 if ( $cgi && $cgi->isa('CGI::Base') && defined $cgi->var('REMOTE_USER')) {
224 carp "Use of CGI::Base is depriciated";
225 $user = lc ( $cgi->var('REMOTE_USER') );
226 } elsif ( $cgi && $cgi->isa('CGI') && defined $cgi->remote_user ) {
227 $user = lc ( $cgi->remote_user );
228 } elsif ( $cgi && $cgi->isa('Apache') ) {
229 $user = lc ( $cgi->connection->user );
231 die "fatal: Can't get REMOTE_USER! for cgi $cgi - you need to setup ".
232 "Apache user authentication as documented in httemplate/docs/install.html";
239 Returns true if effective UID is that of the freeside user.
244 ( $> == $freeside_uid );
249 Returns true if the real UID is that of the freeside user.
254 ( $< == $freeside_uid );
257 =item getsecrets [ USER ]
259 Sets the user to USER, if supplied.
260 Sets and returns the DBI datasource, username and password for this user from
261 the `/usr/local/etc/freeside/mapsecrets' file.
266 my($setuser) = shift;
267 $user = $setuser if $setuser;
268 die "No user!" unless $user;
269 my($conf) = new FS::Conf $conf_dir;
271 if ( $conf->exists('mapsecrets') ) {
272 my($line) = grep /^\s*($user|\*)\s/, $conf->config('mapsecrets');
273 die "User $user not found in mapsecrets!" unless $line;
274 $line =~ /^\s*($user|\*)\s+(.*)$/;
276 die "Illegal mapsecrets line for user?!" unless $secrets;
278 # no mapsecrets file at all, so do the default thing
279 $secrets = 'secrets';
282 ($datasrc, $db_user, $db_pass) = $conf->config($secrets)
283 or die "Can't get secrets: $secrets: $!\n";
284 $FS::Conf::default_dir = $conf_dir. "/conf.$datasrc";
286 ($datasrc, $db_user, $db_pass);
293 Warning: this interface is (still) likely to change in future releases.
295 New (experimental) callback interface:
297 A package can install a callback to be run in adminsuidsetup by passing
298 a coderef to the FS::UID->install_callback class method. If adminsuidsetup has
299 run already, the callback will also be run immediately.
301 $coderef = sub { warn "Hi, I'm returning your call!" };
302 FS::UID->install_callback($coderef);
304 install_callback FS::UID sub {
305 warn "Hi, I'm returning your call!"
308 Old (deprecated) callback interface:
310 A package can install a callback to be run in adminsuidsetup by putting a
311 coderef into the hash %FS::UID::callback :
313 $coderef = sub { warn "Hi, I'm returning your call!" };
314 $FS::UID::callback{'Package::Name'} = $coderef;
318 Too many package-global variables.
322 No capabilities yet. When mod_perl and Authen::DBI are implemented,
323 cgisuidsetup will go away as well.
325 Goes through contortions to support non-OO syntax with multiple datasrc's.
327 Callbacks are (still) inelegant.
331 L<FS::Record>, L<CGI>, L<DBI>, config.html from the base documentation.