'Autosave' script

I am trying to write a script that will save copies of all the open documents of a certain application (called “NeO”) into a certain folder. (The app has a tendency to drop data from its documents from time to time, so I’m trying to improvise an auto-save feature.) Right now I have the code below, but it doesn’t work for a couple of reasons.


set docList to every document
repeat with doc in docList
	tell application "Finder" to duplicate doc to "/users/j/documents/computer/NeO/JRR_autosaves"
end repeat

Issues:

  1. How to specify in the first line that I only want documents from the application “NeO”?
  2. How to specify the destination directory? The way the code is written now produces an error:
    “error “Can’t make "/users/j/documents/computer/NeO/JRR_autosaves" into type location reference.” number -1700 from “/users/j/documents/computer/NeO/JRR_autosaves” to location reference”

Note: NeO does not have built in scriptable functionality, otherwise I think I could use a solution such as below, telling NeO to list its own documents (which I’ve seen used for other apps such as QuarkXPress that I presume are scriptable), which would sovle issue (1):


tell application "NeO"
	set docList to every document
	repeat with doc in docList
		tell application "Finder" to duplicate doc to "/users/j/documents/computer/NeO/JRR_autosaves"
	end repeat
end tell

But when I try the above, I get an error (“error “NeO got an error: Can’t get every document.” number -1728 from every document”).

Thanks for any suggestions!

The Finder is unable to apply to files referenced by POSIX paths.

You must use HFS paths or use do shell script to duplicate the files.

You failed also to dereference doc which is not a POSIX path but a reference to such item.


set docList to every document
repeat with doc in docList
	doc's contents -- ADDED
	do shell script "cp -p " & result & space & "/users/j/documents/computer/NeO/JRR_autosaves" -- EDITED
end repeat

I didn’t tested it but I assume that it’s OK.

I don’t know the application named NEO so I can’t guess how to get the path to its documents.
I just assume that GUI scripting may give some help.

KOENIG Yvan (VALLAURIS, France) jeudi 2 mai 2013 23:47:27

Thanks for that info and suggestion, Yvan. Unfortunately, I’m still hitting an issue.

I tried this:


set docList to every document
repeat with doc in docList
	doc's contents -- ADDED
	do shell script "cp -p " & result & space & "/users/j/documents/computer/NeO/JRR_autosaves" -- EDITED
end repeat

Error Number:Can’t get every document.
-1728

Figured that’s my issue #1, with the first line of code, which you weren’t attempting to fix. so I tried to avoid that issue for the moment by restricting the script to one app (I chose TextEdit), and had open a single document called “test” to see if the code below would work:


tell application "TextEdit"
	set docList to every document
	repeat with doc in docList
		doc's contents -- ADDED
		do shell script "cp -p " & result & space & "/users/j/documents/computer/NeO/JRR_autosaves" -- EDITED
	end repeat
end tell

Got Error Number:Can’t make document “test” of application “TextEdit” into type Unicode text.
-1700

I’m guessing this is the issue you mention, that I “failed also to dereference doc which is not a POSIX path but a reference to such item”, and the line you added:
“doc’s contents”
didn’t resolve that. I’m not sure if it’s what’s needed, but I looked around at POSIX to HFS converter scripting, and I can’t seem to figure out how to apply that here, if it would offer a solution. Seems like the key is to get from the reference ‘doc’ to the actual POSIX path (and then conver to HFS).

I fear I am in over my head here…

Hello.

This looked interesting as I haven’t scripted TextEdit for a while.

I’ll just try to show you an approach.

I open the dictionary for TextEdit, and I look for Document, aha! I see that there is a path property there.

tell application "TextEdit"
	set pthLst to path of its every document
end tell

I see a bunch of documents, and some with missing value, since they’re scap and I haven’t saved them.
So I convert the list to a list who only contain text:

tell application "TextEdit"
	set pthLst to path of its every document
	set pthLst to pthLst's text
end tell

I now see that there is posix paths there.
it is time to try to save the documents to a folder.

I do try it with yours, and it works, (path changed).


tell application "TextEdit"
	set pthLst to path of its every document
	set pthLst to pthLst's text
	repeat with doc in pthLst
		doc's contents -- ADDED
		do shell script "cp -p " & result & space & "~/Desktop/Precious" -- EDITED
	end repeat
end tell

It can often pay off to look in the dictionary, and try it out in the editor and watch the results, then you also get working code in the process! :slight_smile:

P.S in Applescript, files (documents, disk items, items, and aliases ) tend to have a Posix Path property , that returns the Posix path as text, connected with them, that comes in handy when you need it.

I didn’t knew what is a document reference for NEO.

For TexteEdit, it’s a document’s name, not an entire path.
We must explicitely extract the path and, as TextEdit returns a POSIX one which may embed space characters, we must also quote it.


tell application "TextEdit"
	set docList to every document
	repeat with doc in docList
		set pDoc to doc's path -- EDITED
		# TextEdit returns a POSIX path which may embed space characters
		# So it's useful to quote it
		do shell script "cp -p " & quoted form of pDoc & space & "/users/j/documents/computer/NeO/JRR_autosaves" -- EDITED
	end repeat
end tell

I will search in my archives because I wrote a script extracting Numbers documents paths for Numbers '08 which was not scriptable.

KOENIG Yvan (VALLAURIS, France) vendredi 3 mai 2013 09:35:18

Another way to get the paths of open documents in a non-scriptable application

tell application "System Events"
	tell process "NeO"
		set documentFileURLs to value of attribute "AXDocument" of windows
	end tell
end tell

if the window is not a document window, it returns missing value.
The result list contains string representations of a file URL.

:cool:

(And why is that that sometimes you have to useApplication process and other times process?? )

One more questions, does it work without UI Scripting enabled in the preferences?

Anyways, I made this, which I tested with TextEdit, I convert the result from file url’s to plain paths.


tell application "System Events"
	tell process "NeO"
		set documentFileURLs to value of attribute "AXDocument" of windows
		set documentFileURLs to documentFileURLs's text
	end tell
end tell
set {tids, AppleScript's text item delimiters} to {AppleScript's text item delimiters, "file://localhost"}
set documentFileURLs to text items of (documentFileURLs as text)
set AppleScript's text item delimiters to tids
repeat with i from 2 to (count documentFileURLs) by 2
	do shell script "cp -p " & quoted form of item i of documentFileURLs & space & "~/Desktop/Precious"
end repeat

I’m using always just process, never had problems

file URLs could be percent escaped (e.g. %20 for space characters) so you have to unescape the string

Hello.

I’m have trouble with that, when I use the regular Applescript properties of an App that supports Applescript, then I have to use Application Processs, and therein lies the difference I get.

Here is my final stab:

# set AppleScript's text item delimiters to "" 
tell application "System Events"
	if not UI elements enabled then set UI elements enabled to true
	tell process "NeO"
		set documentFileURLs to value of attribute "AXDocument" of windows
		set documentFileURLs to documentFileURLs's text
	end tell
end tell
set {tids, AppleScript's text item delimiters} to {AppleScript's text item delimiters, "file://localhost"}
set documentFileURLs to text items of (documentFileURLs as text)
set AppleScript's text item delimiters to tids
repeat with i from 2 to (count documentFileURLs) by 2
	do shell script "cp -p " & quoted form of rawurldecode(item i of documentFileURLs) & space & "~/Desktop/Precious"
end repeat
-- DJ Bazzie Wazzie
on rawurldecode(str)
	return do shell script "/bin/echo -n " & quoted form of str & " | php -r ' echo rawurldecode(fgets(STDIN)); '"
end rawurldecode

watch processes and application processes in Script Debugger’s Explorer view.
They are synonyms. All elements in the processes list are of class application process

Hello.

You are right, my problem has actually been with trying to use id of a process, which is a an integer when it comes to a process, but either the creator code, or bundle identifier when it comes to an application (text).

Here is al little snippet, that should provide the start for figuring out which files are havining “NeO” as its default app.

It needs some rework, which is left for the OP as an excercise!

tell application "System Events"
	
	tell application process "FreeMind"
		set theDocTitle to name of its front window
		set bid to its bundle identifier
	end tell
	set pathStart to offset of "/" in theDocTitle
	set thePath to text pathStart thru -1 of theDocTitle
	
	set appPath to path to application "FreeMind" as alias
	set default application of disk item thePath to appPath
end tell