The tasks: I have one or more desktop/laptop machines with varying local time zones (because the persons using them are actually in different time zones, or because the one person using them travels). I also have a number of servers configured in some random time zones. (It could be the time zone where they are physically located, or the time zone of the person who installed it, or UTC for neutrality.)
Now what I would like to have happen is that if I log in using SSH
from a desktop to a server, I see time on that server in my local time
zone. For things like ls -l
, for example. Obviously, this
illusion
will never be perfect. Nothing (except something very
complicated) will adjust the time stamps in the syslog output, for
example. But the ls -l
case in particular seems to come up a lot,
to check how long ago was this file modified.
This should be completely doable in principle, because you can set the
TZ
environment variable to any time zone you like, and it will be
used for things like ls -l
. But how do you get the TZ
setting
from here to there?
First, you have to make the remote SSH server accept the TZ
environment variable. At least on Debian, this is not done by
default. So make a setting like this in /etc/ssh/sshd_config
:
# Allow client to pass locale environment variables
AcceptEnv LANG LC_* TZ
You also need to make the equivalent setting on the client side,
either in /etc/ssh/ssh_config
or in ~/.ssh/config
:
SendEnv LANG LC_* TZ
Which leaves the question, how do you get your local time zone into
the TZ
variable to pass to the remote server? The actual time zone
configuration is the file /etc/localtime
, which belongs to glibc.
In current Debian, this is (normally) a copy of some file under
/usr/share/zoneinfo/
. In the distant past, it was a symlink, which
would have made things easier, but now it's a copy, so you don't know
where it came from. But the name of the time zone is also written to
/etc/timezone
, so you can use that.
The format of the TZ
environment variable can be found in the glibc
documentation. If you skip past most of the text, you will see the
relevant parts:
The third format looks like this:
:CHARACTERS
Each operating system interprets this format differently; in the GNU C library, CHARACTERS is the name of a file which describes the time zone.
So what you could do is set
TZ=":$(cat /etc/timezone)"
Better yet, for hopping through multiple SSH hosts in particular, make sure to preserve an already set TZ:
TZ=${TZ:-":$(cat /etc/timezone)"}
And finally, how does one hook this into ssh
? The best I could
think of is a shell alias:
alias ssh='TZ=${TZ:-":$(cat /etc/timezone)"} ssh'
Now this set up has a number of flaws, including:
Possibly only works between Linux (Debian?) hosts.
Only works if available time zone names match.
Only works when calling
ssh
from the shell.
But it practice it has turned out to be quite useful.
Comments? Improvements? Better ideas?
Related thoughts:
With this system in hand, I have resorted to setting the time zone on most servers to UTC, since I will see my local time zone automatically.
Important for the complete server localization illusion: some ideas on dealing with locales on remote hosts.