Beefy Boxes and Bandwidth Generously Provided by pair Networks
Come for the quick hacks, stay for the epiphanies.

Get default login environment

by tilly (Archbishop)
on Sep 22, 2000 at 17:05 UTC ( [id://33628]=CUFP: print w/replies, xml ) Need Help??

Unix crons often run into problems with an incorrectly set environment that causes the same script which works fine for you to break when used in the cron.

Under the assumption that you don't have a bizarre default login environment (eg = in the variable names or returns in the values) and your standard shell is bash, the following snippet demonstrates how you could load the default values from your login environment into your current, without losing other values that might have been passed in your cron.

use strict; sub get_bash_login_env { local %ENV; my $env = `echo env | bash --login`; if (wantarray) { $env =~ s/\\(.)/$1/gs; return map {split /=/, $_, 2} map {split /\n/, $_} $env; } else { return $env; } } # And a demo of how to use it use Data::Dumper; %ENV = (%ENV, get_bash_login_env()); print Dumper(\%ENV);

Replies are listed 'Best First'.
RE (tilly) 1: Get default login environment
by tilly (Archbishop) on Sep 22, 2000 at 18:22 UTC
    After looking at exec's documentation I noticed a more general way to do this. You call sh, lying to it about its name. Here is a slightly more general function, does the same thing as above but does not assume you are running bash as your default shell:
    sub get_login_env { local %ENV; my $shell = shift || (getpwuid($<))[8]; my $env = `echo env | perl -e 'exec {"$shell"} -sh'`; if (wantarray) { $env =~ s/\\(.)/$1/gs; return map {split /=/, $_, 2} map {split /\n/, $_} $env; } else { return $env; } }
    And since someone asked, the reason for localizing %ENV was to clear the environment before calling the login shell. I may trust the login environment to have a sane environment, but I won't trust my current environment to be clean! :-)

    This should work on virtually any *nix with virtually any valid shell, and you can choose the shell to be an argument or take the current shell you use (your choice).

    Update: (Much later.) Hue-Bond pointed out that the missing | in the grandchild is missing here as well. Fixed.

        Actually...try this on for size:
        sub get_login_env { local %ENV; my $shell = shift || (getpwuid($<))[8]; my $env = `echo env | perl -e 'exec {"$shell"} -sh'`; if (wantarray) { my @pieces = ($env =~ m/^(.*?)=((?:[^\n\\]|\\.|\\\n)*)/gm); s/\\(.)/$1/g foreach @pieces; return @pieces; } else { return $env; } }
        Doesn't that take care of everything about how the env function encodes the environment? I tried putting = and returns into the name of environment variables and it wouldn't go...

        I edited the RE slightly. I also should note that compared to the effort of launching a Perl process that execs itself into a login shell, a few invocations of the RE engine are unlikely to do much further damage...

        UPDATE (Much later), Corion caught a silly missing | in the line that gets the environment. :-(

        UPDATE 2 (Years later), as the discussion below points out, there was a silly syntax error. Fixed. Believe it or not, I used a version of this snippet for years, but that copy had been typed separately...

        Thanks, Mr. Schwartz: that's a great shortcut. (Wow, an answer from the person who's book is on my shelf :-) Bye, Ron.
      Thanks, that's a great help. Bye, Ron.
Re: Get default login environment
by Corion (Patriarch) on Nov 14, 2006 at 09:17 UTC

    I just noticed Shell::EnvImporter, which purports to support many different shells and even has code to output unexported shell variables. It sure is longer than the snippet presented here, but if you need to support more than one (non-sh) shell, it might be helpful.

Log In?

What's my password?
Create A New User
Domain Nodelet?
Node Status?
node history
Node Type: CUFP [id://33628]
and the web crawler heard nothing...

How do I use this?Last hourOther CB clients
Other Users?
Others romping around the Monastery: (5)
As of 2024-04-15 03:42 GMT
Find Nodes?
    Voting Booth?

    No recent polls found