Posted on 03-15-2013 07:14 AM
I'm looking for a programatic way to be able to set that setting in Date & Time. Any ideas?
Posted on 03-15-2013 09:31 AM
The ability to use "Current Location" would be a great, but if it helps you as to what we do to set the timezone, I will gladly expound. We are all in the American Eastern Time Zone so I hardcode for "America/New_York"
We also have Network Time Servers at each of our locations. So to set both the timezone via command line on our images, I have a script that runs the following two commands:
systemsetup -settimezone "America/New_York"
systemsetup -setnetworktimeserver "yourntpserver.yourdomainhere.com"
So, now that we have the syntax of the commands covered, let me start the skeleton of a script for you...knowing that I lack the knowledge of how to finish this concept. If nothing else, this should give you some food for thought:
#!/bin/sh
###Variable Declaration###
#This is my main challenge. How do write a command(s) that will
#populate this variable by either pulling the network segment or
#Casper location data for a given Mac in the data base, and then how
#do we transform what is pulled from the database into something
#systemsetup understands such as 'America/New_York' or say 'Europe/Berlin'.
TimeZone="`<hoped for command the populates this variable here>`"
systemsetup -settimezone "$TimeZone"
exit 0
Hopefully some better scripters weigh in on this...and who knows...maybe there is a way to set it using "Current Location", but the man page for the systemsetup command does not cover that.
Posted on 03-15-2013 10:07 AM
Further investigation on my 10.8.3 computer yielded that the actual file being touched is /Library/Preferences/com.apple.timezone.auto.plist I wonder if it's touching other files as well.
Time to fire up PlistBuddy to try to script it.
Posted on 04-18-2013 08:28 AM
As always TEST TEST TEST in a dev environment first.
This works for me.
It only seems to do the first lookup after opening the Date & Time prefs.
#!/bin/sh
# Use "/usr/sbin/systemsetup -listtimezones" to see a list of available list time zones.
TimeZone="America/New_York"
TimeServer="time.apple.com"
############# Pause for network services #############
/bin/sleep 10
#################################################
/usr/sbin/systemsetup -setusingnetworktime off
#Set an initial time zone
/usr/sbin/systemsetup -settimezone $TimeZone
#Set specific time server
/usr/sbin/systemsetup -setnetworktimeserver $TimeServer
# enable location services
/bin/launchctl unload /System/Library/LaunchDaemons/com.apple.locationd.plist
uuid=`/usr/sbin/system_profiler SPHardwareDataType | grep "Hardware UUID" | cut -c22-57`
/usr/bin/defaults write /var/db/locationd/Library/Preferences/ByHost/com.apple.locationd.$uuid LocationServicesEnabled -int 1
/usr/sbin/chown -R _locationd:_locationd /var/db/locationd
/bin/launchctl load /System/Library/LaunchDaemons/com.apple.locationd.plist
# set time zone automatically using current location
/usr/bin/defaults write /Library/Preferences/com.apple.timezone.auto Active -bool true
/usr/sbin/systemsetup -setusingnetworktime on
/usr/sbin/systemsetup -gettimezone
/usr/sbin/systemsetup -getnetworktimeserver
exit 0
Posted on 12-18-2013 11:56 AM
Just to answer my own question here's what I've come up with, pretty or elegant? No. Effective? Seems to be.
#!/bin/bash
uuid=/usr/sbin/system_profiler SPHardwareDataType | grep "Hardware UUID" | cut -c22-57
/bin/launchctl unload /System/Library/LaunchDaemons/com.apple.locationd.plist
/usr/bin/defaults write /private/var/db/locationd/Library/Preferences/ByHost/com.apple.locationd.$uuid LocationServicesEnabled -int 1
/usr/bin/defaults write /private/var/db/locationd/Library/Preferences/ByHost/com.apple.locationd.notbackedup.$uuid LocationServicesEnabled -int 1
/usr/sbin/chown -R _locationd:_locationd /var/db/locationd
/bin/launchctl load /System/Library/LaunchDaemons/com.apple.locationd.plist
exit 0
For Auto Time Zone similar idea
#!/bin/sh /usr/bin/sudo /usr/bin/defaults write /Library/Preferences/com.apple.timezone.auto Active -bool True exit 0
Posted on 04-27-2015 04:01 PM
@ericbenfer Thanks for the TimeServer, TimeZone, Location Service on script. It was everything I needed!
Posted on 05-28-2015 12:58 PM
I was actually looking at this myself. Am I right in that this only works after opening up Date and Time? There's got to be a way to kick off the "Determining location..." portion that the System Preference pane. I'll be looking a bit more into this, but figured I'd ask.
Posted on 05-29-2015 09:01 AM
I just want to describe a few other things I tried in investigating this. I went ahead and implemented the script as is. Ran command in Terminal:
opensnoop -v
and then opened up Date and Time preferences
Lots of stuff going on but the main ones I saw were TimeZoneToAdmin, timezoned, locationd, and references to GeoKit.framework. Most of it was located in here: /System/Library/PreferencePanes/DateAndTime.prefPane/Contents/Resources/TimeZone.prefPane/Contents/Resources/timezoned.app
Unfortunately, I didn't get much further than that. Unloading and re-loading the plist doesn't seem to do much either. Tried looking at Developer documentation for anything related to timezone settings and there are references to Core Location services but I wouldn't know what to do with that at this point in time.
But here's what I discovered which I find rather interesting: if you disable and re-enable wireless it automatically re-syncs after a 2-3 seconds (this assumes it reconnects to a wireless network with an active internet connection). Doesn't work with Ethernet. I'm wondering if disabling the wireless and re-enabling the wireless as part of the script would automatically sync to the right timezone. The downside is if the computer only has a wireless connection and for whatever reason cannot reconnect to the network (and therefore the JSS) you may run into logs for the policy not completing successfully. Something to think about.
Posted on 05-29-2015 09:33 AM
Running a simple commands of:
/usr/sbin/networksetup -setairportpower en0 off
/usr/sbin/networksetup -setairportpower en0 on
This assumes your wireless is en0. If it's not, you can run this command to determine what device name is listed as:
/usr/sbin/networksetup -listallhardwareports
Alternatively you can also use the Hardware Port name too:
/usr/sbin/networksetup -setairportpower Wi-Fi off
/usr/sbin/networksetup -setairportpower Wi-Fi on
But that may differ depending on the OS you're running. I think it was AirPort at one point and may have changed in either 10.7 or 10.8 to Wi-Fi.
Anyways this is all informational. I'll personally let OS naturally detect it either on a restart which a user is bound to do or when they connect to the wireless for the first time.
Posted on 10-02-2015 08:54 AM
I found that this change would only be respected if the plist file was in xml format. Weird, huh?
This is my setup for enabling location-based time zone (Note; location services need to also be enabled, as above:
/bin/rm /Library/Preferences/com.apple.timezone.auto.plist
/usr/bin/defaults write /Library/Preferences/com.apple.timezone.auto Active -bool true
/usr/bin/plutil -convert xml1 /Library/Preferences/com.apple.timezone.auto.plist
Posted on 01-13-2016 09:48 AM
What worked for me is to create a package using composer containing the com.apple.timezone.auto.plist set to true. I then pushed this out via policy and added it to our Casper Imaging configuration.
<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE plist PUBLIC "-//Apple//DTD PLIST 1.0//EN" "http://www.apple.com/DTDs/PropertyList-1.0.dtd">
<plist version="1.0">
<dict>
<key>Active</key>
<true/>
</dict>
</plist>
Posted on 02-23-2017 02:31 PM
Thanks @ericbenfer ! Worked great for me.
Posted on 03-16-2017 10:12 AM
So the script itself works for me but the problem that I'm seeing is that this will only set the timezone to Eastern but if the person sits in the Pacific timezone then it won't update the time on the machine until after they've launched the Date & Time preference pane. Is there any way to get the time zone to set itself correctly based off their geo automatically?
Posted on 07-06-2017 02:12 PM
@cgiordano I ran into the same problem - we were previously unloading and loading the LaunchD located in /System/Library/LaunchDaemons/com.apple.locationd.plist to get the change to stick, but SIP in Sierra neutered that. Finally had some time to dig in today and found this little gem that forces the auto timezone if you've set all the other stuff properly for automatic timezone discovery and enabling Location Services.
Since the bulk of the auto timezone stuff is a shell script and the above is in Python, I just loaded it in as a heredoc after all the bash code:
/usr/bin/python << EOF
from Foundation import NSBundle
TZPP = NSBundle.bundleWithPath_("/System/Library/PreferencePanes/DateAndTime.prefPane/Contents/Resources/TimeZone.prefPane")
TimeZonePref = TZPP.classNamed_('TimeZonePref')
ATZAdminPrefererences = TZPP.classNamed_('ATZAdminPrefererences')
atzap = ATZAdminPrefererences.defaultPreferences()
pref = TimeZonePref.alloc().init()
atzap.addObserver_forKeyPath_options_context_(pref, "enabled", 0, 0)
result = pref._startAutoTimeZoneDaemon_(0x1)
EOF
Posted on 07-06-2017 02:25 PM
Hey Guys!
Correct me if I'm wrong - the issue is not that the script doesn't work anymore. It's that Location Services have to be enabled for the automatic Date & Time function to work.
I am able to enable Location Services with the following bit of stuff in a 1st run script in the most up-to-date version macOS 10.12:
hdwruid=$(/usr/sbin/system_profiler SPHardwareDataType | /usr/bin/awk '/Hardware UUID/{print $NF}')
loginfo "Hardware UUID: $hdwruid"
loginfo "enabling Location Services..."
osref=$(/usr/bin/sw_vers -productVersion | /usr/bin/awk -F. '{print $2}')
locd_osx(){
/bin/rm -rf /private/var/db/locationd/Library/Preferences/ByHost/*
/usr/bin/defaults write /private/var/db/locationd/Library/Preferences/ByHost/com.apple.locationd."$hdwruid" LocationServicesEnabled -int 1
/usr/sbin/chown -R _locationd:_locationd /private/var/db/locationd
}
locd_macos(){
osbld=$(/bin/cat /System/Library/CoreServices/SystemVersion.plist | /usr/bin/sed -n 's/^[[:space:]]//g;6p')
osnam=$(/bin/cat /System/Library/CoreServices/SystemVersion.plist | /usr/bin/sed -n 's/^[[:space:]]//g;10p')
osvrs=$(/bin/cat /System/Library/CoreServices/SystemVersion.plist | /usr/bin/sed -n 's/^[[:space:]]//g;12p')
osstr=$(echo "$osnam$osvrs/$osbld" | /usr/bin/sed 's/<[^>]*>//g')
/bin/rm -rf /private/var/db/locationd/Library/Preferences/ByHost/*
locsrvc
/usr/bin/defaults write /private/var/db/locationd/Library/Preferences/ByHost/com.apple.locationd."$hdwruid".plist LocationServicesEnabled -int 1
/usr/sbin/chown -R _locationd:_locationd /private/var/db/locationd/
/bin/chmod 600 /private/var/db/locationd/Library/Preferences/ByHost/com.apple.locationd."$hdwruid".plist
}
if [ "$osref" -le 11 ]
then
locd_osx
else
locd_macos
fi
It might be a little bit of overkill to repopulate the .plist but this has worked for me since, like, forever.
Posted on 07-06-2017 02:49 PM
Hiya @brock.walters -- the issue we had run into is that we had bundled all this up in a Self Service job for our users who are traveling, and even after enabling location services and writing to the proper plists to set timezone auto adjust (code below), we were no longer able to unload/reload the com.apple.locationd.plist to enact the change in Sierra with SIP enabled. Opening up System Preferences and selecting the Time Zone radio button in Date & Time seemed to wake the system up and force it to detect that it should be setting TZ automatically, but I had difficulty until I came across that Python code above determining a way to do this with no user interaction and no restart.
# Enable location services and enforce ownership; path is no longer UUID dependent in Sierra
/usr/bin/defaults write /var/db/locationd/Library/Preferences/ByHost/com.apple.locationd LocationServicesEnabled -int 1
/usr/bin/defaults write /var/db/locationd/Library/Preferences/ByHost/com.apple.locationd.notbackedup. LocationServicesEnabled -int 1
/usr/sbin/chown -R _locationd:_locationd /var/db/locationd
# Update Time Zone preference to auto-adjust based upon location
/usr/bin/defaults write /Library/Preferences/com.apple.timezone.auto Active -bool YES
/usr/bin/defaults write /Library/Preferences/com.apple.locationmenu ShowSystemServices -bool YES
Posted on 07-06-2017 04:05 PM
@NoahRJ That's an interesting find...What does your final script look like if you don't mind my asking?
@brock.walters My use case is the same as Noah's if we have users that travel the time zone doesn't always automatically update so forcing a check-in for the time server would seem to be the way to go. We'd rather walk them through running a policy in Self Service as opposed to having to walk them through opening the Date & Time System Preference.
Posted on 07-07-2017 07:17 AM
@cgiordano Sure thing - full script is below:
#!/bin/sh
#Get device interface for wireless
WiFiDI=$(/usr/sbin/networksetup -listallhardwareports | grep -A1 Wi-Fi | grep Device | awk '{print $2}')
#Get the version of Mac OS
OS_Version=$(sw_vers -productVersion)
if [[ $OS_Version == 10.11* ]]; then
uuid=$(/usr/sbin/system_profiler SPHardwareDataType | grep "Hardware UUID" | cut -c22-57)
#Enable location services and enforce ownership
/usr/bin/defaults write /var/db/locationd/Library/Preferences/ByHost/com.apple.locationd."$uuid" LocationServicesEnabled -int 1
/usr/bin/defaults write /var/db/locationd/Library/Preferences/ByHost/com.apple.locationd.notbackedup."$uuid" LocationServicesEnabled -int 1
/usr/sbin/chown -R _locationd:_locationd /var/db/locationd
#Update Time Zone preference to auto-adjust based upon location
/usr/bin/defaults write /Library/Preferences/com.apple.timezone.auto Active 1
/usr/bin/defaults write /Library/Preferences/com.apple.locationmenu ShowSystemServices 1
elif [[ $OS_Version == 10.12* ]]; then
#Enable location services and enforce ownership; path is no longer UUID dependent in Sierra
/usr/bin/defaults write /var/db/locationd/Library/Preferences/ByHost/com.apple.locationd LocationServicesEnabled -int 1
/usr/bin/defaults write /var/db/locationd/Library/Preferences/ByHost/com.apple.locationd.notbackedup. LocationServicesEnabled -int 1
/usr/sbin/chown -R _locationd:_locationd /var/db/locationd
#Update Time Zone preference to auto-adjust based upon location
/usr/bin/defaults write /Library/Preferences/com.apple.timezone.auto Active -bool YES
/usr/bin/defaults write /Library/Preferences/com.apple.locationmenu ShowSystemServices -bool YES
else
echo "not running macOS 10.11 or 10.12"
fi
#Wi-Fi must be powered on to determine current location
/usr/sbin/networksetup -setairportpower $WiFiDI on
#Pause to enable location services to load properly
sleep 3
#Re-enable network time
/usr/sbin/systemsetup -setusingnetworktime on
#Python code snippet to reload AutoTimeZoneDaemon
/usr/bin/python << EOF
from Foundation import NSBundle
TZPP = NSBundle.bundleWithPath_("/System/Library/PreferencePanes/DateAndTime.prefPane/Contents/Resources/TimeZone.prefPane")
TimeZonePref = TZPP.classNamed_('TimeZonePref')
ATZAdminPrefererences = TZPP.classNamed_('ATZAdminPrefererences')
atzap = ATZAdminPrefererences.defaultPreferences()
pref = TimeZonePref.alloc().init()
atzap.addObserver_forKeyPath_options_context_(pref, "enabled", 0, 0)
result = pref._startAutoTimeZoneDaemon_(0x1)
EOF
sleep 1
#Get the time from time server
/usr/sbin/systemsetup -getnetworktimeserver
#Detect the newly set timezone
/usr/sbin/systemsetup -gettimezone
exit 0
Posted on 07-07-2017 11:43 AM
Wow. That totally worked for me. The only interesting this that I found is that it said that the timezone was set to NY but then it updated the time and changed the timezone to LA which is correct since I'm sitting with this machine in Seattle. I copied and pasted your script with
sudo ./test.sh
Password:
Network Time is already on.
Network Time Server: time.apple.com
Time Zone: America/New_York
Why does it say that it's America/New_York when it then updates to America/Los_Angeles? It's not a huge deal since it's showing the correct time but just a curious thing....
Posted on 07-07-2017 11:49 AM
Hmm, try increasing the sleep time from 1 to a higher number (maybe sleep 5) toward the bottom of the script and then run again. The /usr/sbin/systemsetup -gettimezone command that detects the set timezone might jump the gun and run before the python script has had time to fully work its magic.
I use that as a check to make sure the proper timezone was set (since error codes aren't always the most forthcoming), but you don't need it for anything aside from verification.
Posted on 07-07-2017 11:56 AM
Yup. That seems to have done the trick. I also added to the script just to echo the date/time before running the script and the date/time as the last step so you can look back historically in the policy log or the machine policy log to confirm that the date/time is actually getting updated.
## Tell the time prior to the script running
echo "The current time is `date`"
## Tell the new time after everything has been updated
echo "The new, correct time is now set as `date`"
Thanks for this Noah and everyone. This is great!
Posted on 11-28-2017 06:48 AM
Just wanted to chime in and say I added an OR condition onto the 10.12 one for 10.13 and it still works great in High Sierra.
elif [[ $OS_Version == 10.12* ]] || [[ $OS_Version == 10.13* ]]; then
Thanks, @NoahRJ.
Posted on 11-30-2017 03:59 PM
So are you using this as a Self Service policy? Or automatically pushed?
Posted on 12-01-2017 05:32 AM
We’re using it in a deployment policy. For new/re-imaged/DEP’d machines. Seems to work fine just firing it at computers with Remote as well, so should be good in a mass Recurring Check-In-type policy, too. Test a bit, obviously.
Posted on 05-29-2018 03:26 PM
Anyone having success on 10.13.4? Getting errors with the python script
AttributeError: 'TimeZonePref' object has no attribute '_startAutoTimeZoneDaemon_'
Thank you all for your contributions, this thread has been hugely helpful.
Posted on 05-30-2018 05:09 AM
Hadn't run the script on a 10.13.4 machine yet, but just tested, and yeah, I'm getting the same.
I'll be able to look into it later this week, but can't say I'm very familiar with Python, so someone else may prove more helpful.
Posted on 06-25-2018 11:43 PM
Testing on 10.13.4 I also get the error mentioned by @shan3 .
Posted on 06-29-2018 07:39 AM
It's a real shame the python code no longer works on 10.13.4 and above. This was a great find, but once again apple broken something useful.
On top of this I have noticed that this code no longer works on 10.13.3/10.13.4 and newer. I'm still looking into it, but no luck. /usr/bin/defaults write /Library/Preferences/com.apple.timezone.auto Active -bool YES
this command no longer ticks the option to set time zone automatically using current location
Posted on 06-29-2018 12:57 PM
I get the opposite on 10.13.4, The box gets ticked, however the map does not show until I click on another tab
Posted on 07-02-2018 04:07 AM
@ewinterbourne I'm still getting the same problem with that command in 10.13.5, Trying to find a way around it but no joy as of yet.
Posted on 11-12-2018 12:20 PM
I have tried running this script in 10.14.1 and still getting no response from the machine when it comes to ticking the box, under Date & Time. Has anyone been able to find a resolution to this?
Posted on 11-13-2018 11:35 AM
@oartola We've been using this https://github.com/jamfprofessionalservices/Jamf-Scripts/blob/master/Set%20Time%20Zone.sh Along with a self service policy.
Posted on 01-25-2019 01:05 PM
Posted on 01-25-2019 05:04 PM
@DFree It must have been moved. Check out my Github page for the script
Posted on 02-21-2019 12:37 PM
/usr/bin/defaults write /var/db/locationd/Library/Preferences/ByHost/com.apple.locationd LocationServicesEnabled -int 1
I'm using this as part of my enrollment provisioning on DEPNotify. When the user logs in, before DEPNotify launches, the time is PST. I prompt for reboot at the end of my DEPNotify script and after reboot, the location services kicks in and the time zone is automatically set by current location. It can take a few minutes for it to kick in
Posted on 05-11-2021 12:38 PM
Create a blank package with the script below (postinstall). Then add it to your prestage enrollment.
#!/bin/bash
## configure ntp server
/bin/cat > /etc/ntp.conf << 'NEW_NTP_CONF'
server time.apple.com
NEW_NTP_CONF
## configure automatic timezone
/usr/bin/defaults write /var/db/locationd/Library/Preferences/ByHost/com.apple.locationd LocationServicesEnabled -int 1
uuid=$(/usr/sbin/system_profiler SPHardwareDataType | grep "Hardware UUID" | cut -c22-57)
/usr/bin/defaults write /var/db/locationd/Library/Preferences/ByHost/com.apple.locationd.$uuid LocationServicesEnabled -int 1
## Set date and time automatically
/usr/bin/defaults write /Library/Preferences/com.apple.timezone.auto Active -bool YES
/usr/bin/defaults write /private/var/db/timed/Library/Preferences/com.apple.timed.plist TMAutomaticTimeOnlyEnabled -bool YES
/usr/bin/defaults write /private/var/db/timed/Library/Preferences/com.apple.timed.plist TMAutomaticTimeZoneEnabled -bool YES
/usr/sbin/systemsetup -setusingnetworktime on
/usr/sbin/systemsetup -gettimezone
/usr/sbin/systemsetup -getnetworktimeserver
### Restart location services daemon (locationd)
/usr/bin/killall locationd
exit 0; ## Success
exit 1; ## Failure
Posted on 07-27-2021 03:27 AM
Modifying ByHost plist and those under /private/var/db has no effect. It doesn't toggle the checkbox in System Preferences. At least true for High Sierra, Mojave.