xCode 4, AppleScript: hide & show windows, remote script execution

OK, thanks again for your time. Here is my solution:

How to move large amounts of data between AppleScript and AppeScriptObjC:

There are some tricks being involved:

  • data is passed thru a temp file
  • data is prepared as a text form of a record list (prepareMyRecord() ) which is executed on the receiver side as
  • the temp file is used as semaphore

This is a proof of concept. It will work in most circumstances, but for implementation you should check error handling & logging. And you will have to modify the prepareMyRecord() function to match your own data structure.

Sender:



property tempItemsPath : ""
property semaFile : ""
property theRemoteApp : "~/Desktop/My\\ Remote\\ App.app"


on run
	
	set tempItemsPath to (path to temporary items folder from user domain as string)
	set semaFile to tempItemsPath & "com.myCompany.myProject.sema"
	set theResult to callRemoteProc(prepareMyRecord({car:"Toyota", bike:"Kawasaki"}), theRemoteApp, "waiting")
	display dialog theResult
	
end run


--prepare record for export
on prepareMyRecord(myParams)
	
	set theParams to "car:\"" & the car of myParams
	set theParams to theParams & "\", bike:\"" & the bike of myParams
	set theParams to theParams & "\""
	
	return theParams
	
end prepareMyRecord


-- remote calling procedure
on callRemoteProc(myParams, remoteApp, waiting)
	
	tell application "Finder"
		if not (exists file semaFile) then
			
			-- no semaFile, so no other process running.
			
			-- write sema file with all params to pass on
			try
				set fRef to (open for access (semaFile) with write permission)
				set eof of fRef to 0
				write (myParams) as «class utf8» to fRef
				close access fRef
			on error
				try
					-- if something goes wrong and the file is still open, close it
					close access fRef
				end try
				
				return "ERR: semaFile not created"
				
			end try
			
			-- call remote application
			try
				set myCMD to "open " & (the quoted form of the POSIX path of remoteApp)
				do shell script myCMD
			on error
				return "ERR: could not launch remote application"
			end try
			
			-- wait for remote application to finish if desired
			if (waiting is not "") then
				try
					repeat while (exists file semaFile)
						-- future version might have a timeout here
						delay 0.5
					end repeat
				end try
			end if
			
			return "SUCCESS"
			
		else
			return "ERR: semaFile blocked by other process"
		end if
	end tell
	
end callRemoteProc


Receiver:


property tempItemsPath : ""
property semaFile : ""


on run
	
	set tempItemsPath to (path to temporary items folder from user domain as string)
	set semaFile to tempItemsPath & "com.myCompany.myProject.sema"
	
	set theResult to getRemoteData()
	set theClass to the class of theResult as string
	
	if (theClass is "text") then
		-- we have an error
		display dialog theResult
	else
		-- we got a valid record and can extract data as necessary
		display dialog the car of theResult
	end if
	
	releaseRemoteSema(semaFile)
	
end run


-- get remote parameters from semaFile
on getRemoteData()
	tell application "Finder"
		if (exists file semaFile) then
			-- semaFile exists, so we have everything we need.
			
			-- read sema file with all params to pass on
			try
				set fRef to (open for access (semaFile))
				set myParams to (read fRef for (get eof fRef) as «class utf8»)
				close access fRef
			on error
				try
					-- if something goes wrong and the file is still open, close it
					close access fRef
				end try
				
				return "ERR: could not read semaFile"
			end try
			
			-- resolve parameters passed
			try
				set paramsRead to run script ("return {" & myParams & "}")
			on error
				return "ERR: semaFile mismatch"
			end try
			
			return paramsRead
			
		else
			return "ERR: semaFile does not exist"
		end if
	end tell
end getRemoteData


-- release waiting caller application
on releaseRemoteSema(semaFile)
	
	tell application "Finder"
		try
			delete file semaFile
		end try
	end tell
	
end releaseRemoteSema