Blog entry

Applescript to manually sync iphone to iTunes - 1st attempt

Setting the sync preferences in iTunes to automatic means that my iPhone is always synced whenever I drop it in its dock. However, this also means that iTunes pops up and sometimes becomes the front-most application. No problem if I'm doing nothing much but every now it distracts to the point of losing my motivation.

So I decided to switch this preference off. But then I need to remember that I have to sync manually. Which I forget. Not much gained.

So after manually switching to iTunes to press the sync button today a few times I decided I might as well do this with a script.

Googling I found:

tell application "iTunes"
   repeat with s in sources
      if (kind of s is iPod) then update s
   end repeat
end tell

(Sorry, I can't remember where I found this)

Improvement, but not much. I still need to remember when I last did a sync and then decide whether it's necessary to sync or not. I don't have that much changes, so I can settle with once every 4 hours.

Sync and backup time

iTunes stores information about syncs of your mobile devices in ~/Library/Application Support/MobileSync/Backup/. Each device gets it's own directory with a long string of hex numbers as name. Each directory contains a lot of files also with hex numbers, but also a file named Info.plist. This file contains the name of the device and the date of the last backup.

At first I assumed the backup date was the last sync date, but it turns out, it's the date your device is actually backed up. As of now I haven't been able to figure out if and where iTunes stores the date of the last sync.

So in that case, I need to set my own sync date. After much googling and experimenting I finally settled for the following apple script. This script writes a plist file in the ~/Library/Application Support/MobileSync/Backup/
called LastSyncTime.plist. If this file doesn't exist it is created with the date of the last backup for each device found in that directory.

The first line allows you to set the interval.

(*

 * Figure out the last sync time of my iPhone/iPad and sync if it's more than
 * X hours ago
 *
 * X can be set in syncInterval
 *
 * 2011/07/25
*)
property syncInterval : (4 * hours)
property backupPath : ((path to application support from user domain) & "MobileSync:Backup") as string
property syncFile : "LastSyncTime.plist"

tell application "iTunes"
	repeat with s in sources
		if (kind of s is iPod) then my updateIfNecessary(s)
	end repeat
end tell

on updateIfNecessary(myDevice)
	set deviceName to name of myDevice
	set lastSyncDate to getLastSyncDate(deviceName)
	if lastSyncDate = 0 then
		display dialog "No sync date found for " & deviceName
	else
		set nextSync to lastSyncDate + syncInterval
		set now to current date
		if now < nextSync then
			set msg to "No sync necessary"
		else
			set msg to "Sync necessary"
			tell application "iTunes" to update myDevice
			updatePlistFile(deviceName, now)
		end if
		
		display dialog "I found " & deviceName & " which is synced last on " & lastSyncDate & ¬
", next sync after " & nextSync & ", it is now " & now & " " & msg end if end updateIfNecessary -- -- Read the last sync date for this device -- on getLastSyncDate(deviceName) tell application "System Events" set propfile to ((path of folder backupPath) & syncFile) as string if not (exists file propfile) then my populatePlistFile() end if set syncDate to (value of property list item deviceName of property list file propfile) return syncDate end tell return 0 end getLastSyncDate -- -- Create a plist file and populate it with the last backup dates -- on populatePlistFile() tell application "System Events" set syncPlistFile to my createEmptyPlistfile(backupPath, syncFile) -- don't add the line below instead of "fs" in the next line, because somehow
-- it will recurse into the existing folders set fs to (every folder of folder backupPath) repeat with f in fs -- display dialog "foldername=" & name of f set propfile to ((path of f) & "Info.plist") as string set devName to (value of property list item "Device Name" of property list file propfile) set backupDate to (value of property list item "Last Backup Date" of property list file propfile)
  -- this is the backup date, not the sync date tell syncPlistFile make new property list item at end with properties ¬
{kind:date, name:devName, value:backupDate} end tell end repeat end tell end populatePlistFile -- -- create an empty plist file -- based on http://www.j-schell.de/node/316 -- on createEmptyPlistfile(filePath, fileName) tell application "System Events" set the parent_dictionary to make new property list item with properties {kind:record} -- create new property list file using the empty dictionary list item as contents set the plistfile_path to filePath & ":" & fileName set pl to make new property list file with properties {contents:parent_dictionary, name:plistfile_path} return pl end tell end createEmptyPlistfile -- -- update the sync file with the date of the last sync -- on updatePlistFile(devName, syncDate) tell application "System Events" set propfile to ((path of folder backupPath) & syncFile) as string tell property list file propfile tell contents set p to the property list item devName set value of p to syncDate end tell end tell end tell end updatePlistFile