SD and OS X version script

[quote=“BillKopp, post:52, topic:436”]
How did the script I modified work without a use framework “Appkit”?[/quote]

It’s probably not strictly needed in this case because the host app has already loaded it, and you’re not using any of the stuff defined in it’s bridgesupport file.

I’m not exactly sure what a use statement fully does AppleScript-wise – it’s not documented anywhere. I don’t know whether terminology gets cached at the component level or higher. And although I’d be interested to know, this is one of the places I’m quite happy to take the advice of the engineers responsible, which is always to include a use statement for every framework whose classes or methods you use. It’s no great burden, it’s a simple rule to follow, and these days hardly takes any time.

Are you allowing for the fact that the results of loading it earlier might have been cached?

There’s an argument to be made that perhaps we should just start using use framework "Cocoa", because that encapsulates Foundation and AppKit. But I think the appearance of AppKit often serves as a sort of heads-up that perhaps something a bit different is being done.

I like that.
Is there any downside to having a use framework statement even if you don’t really need it? Does it slow things down?

When ASObjC was introduced in 10.9, there was a definite pause as stuff was loaded the first time (that is, say, the first time you ran any ASObjC script in an editor). But I really haven’t noticed it since.

Terminology-wise, AppKit is very big – much bigger than Foundation – so if it’s going to show up anywhere, that’s where it’s likely to be.

I’m not sure how you can time it, though. In 10.9 it was in the order of a second or two, so it was obvious.

Shane,

I wasn’t protesting including the use statement. I just thought removing the statement was a good test that I had all the use statements I needed. Apparently that is not the case.

Bill

I’m including “use framework “AppKit””, because now that the script is done (it’s done, right?) I won’t be running it from SD, but it will live in the system’s scripts menu to be run from there as needed.

–>Script Debugger 6.0.4 (6A198) on Mac OS 10.10.4 (14E46)

(Any issues with running this stuff in Yosemite? It crashes SD if you run it too much, but outside of SD it seems OK)

use scripting additions
use framework "Foundation"
use framework "AppKit"
------------------------------------------------------------------------------
-->Script Debugger 6.0.4 (6A198) on Mac OS 10.10.4 (14E46)
set fileNameFormat to {"Copy SD ", "version and", " OSX ", "version"}
set appName to "SD"
set appId to "com.latenightsw.ScriptDebugger6"

set appNSURL to current application's NSWorkspace's sharedWorkspace()'s URLForApplicationWithBundleIdentifier:appId
set appBundle to current application's NSBundle's bundleWithURL:appNSURL
set appName to (appBundle's infoDictionary()'s objectForKey:"CFBundleName") as text
set appVer to (appBundle's infoDictionary()'s objectForKey:"CFBundleShortVersionString") as text
set appBundleVer to (appBundle's infoDictionary()'s objectForKey:"CFBundleVersion") as text
set sysVer to (current application's NSProcessInfo's processInfo()'s operatingSystemVersionString())
set sysVer to (sysVer's stringByReplacingOccurrencesOfString:("Version") withString:"Mac OS")
set sysVer to (sysVer's stringByReplacingOccurrencesOfString:("Build ") withString:"") as text
set infoString to appName & space & appVer & " (" & appBundleVer & ") on " & sysVer

set the clipboard to "-->" & infoString
set newFileName to "Copy " & infoString

set thisScript to path to me as alias

--Unnote next line and run script to set script name back to default
--set newFileName to fileNameFormat as text

tell application "Finder"
	set oldFileName to the name of thisScript
	if "Unsaved Script Debugger Document" is in oldFileName then return
	if "Untitled" is in oldFileName then return
	set nameExt to the name extension of thisScript
	set newFileName to newFileName & "." & nameExt
	if oldFileName is not newFileName then set the name of thisScript to newFileName
end tell

return the clipboard

Exactly. The issue with ASObjC in Yosemite comes from instrumenting the code, not the actual running of it.

I uploaded a new version of the ASObj-C. This is version A16. It has some stuff added since A15 but I also added a lot of stuff about bundles yesterday. Here is the link:

Bill

So, what i thought was the final, stable and robust version of this script has stopped working when run from the system scripts menu. It did work previously but doesn’t now. (There has been a reboot or two since it was shown to work)

It works just fine from SE or SD. When run from the menu it doesn’t error, it just silently fails.

After all that I may just go back to the commands using shell scripts.

use scripting additions
use framework "Foundation"
use framework "AppKit"
--> SD 6.0.4 (6A198) OSX 10.11.6 (15G1217)

set appID to "com.latenightsw.ScriptDebugger6"
set fileNameFormat to {"Copy SD ", "version and", " OSX ", "version"}

set SDBundle to current application's NSBundle's bundleWithIdentifier:appID

set SDVersion to SDBundle's infoDictionary()'s objectForKey:"CFBundleShortVersionString"
set BundleVersion to SDBundle's infoDictionary()'s objectForKey:"CFBundleVersion"

set SystemInfo to do shell script "sw_vers"
set AppleScript's text item delimiters to {":   ", return}
set SystemInfo to text items of SystemInfo
set AppleScript's text item delimiters to {""}
set SystemVersion to item 4 of SystemInfo
set SystemBuildNum to the last text item of SystemInfo

set infoString to " SD " & SDVersion & " (" & BundleVersion & ") OSX " & SystemVersion & " (" & SystemBuildNum & ")"

set the clipboard to "-->" & infoString
set newFileName to "Copy" & infoString

set thisScript to path to me as alias

--Unnote next line and run script to set script name back to default
--set newFileName to fileNameFormat as text

tell application "Finder"
   set oldFileName to the name of thisScript
   if "Unsaved Script Debugger Document" is in oldFileName then return
   if "Untitled" is in oldFileName then return
   set nameExt to the name extension of thisScript
   set newFileName to newFileName & "." & nameExt
   if oldFileName is not newFileName then set the name of thisScript to newFileName
end tell

return the clipboard

so I put the whole thing in a try / on error block and this is what I got:

Error Number: -1708

Error Message:

“missing value doesn’t understand the “infoDictionary” message.”

EDITED SCRIPT TO IMPROVE ERROR REPORTS:

These two lines trigger errors when run from the scripts menu. Below is the script with error trapping and the final result, is commented out at the bottom with the error numbers and messages.

– set SDVersion to SDBundle’s infoDictionary()'s objectForKey:“CFBundleShortVersionString”


– set BundleVersion to SDBundle’s infoDictionary()'s objectForKey:“CFBundleVersion”

–> SD 6.0.4 (6A198) OSX 10.11.6 (15G1217) (generated by running from within SD)

use scripting additions
use framework "Foundation"
use framework "AppKit"
--> SD 6.0.4 (6A198) OSX 10.11.6 (15G1217)
set allErrorMessages to {}
try
   set appID to "com.latenightsw.ScriptDebugger6"
   set fileNameFormat to {"Copy SD ", "version and", " OSX ", "version"}
   
   set SDBundle to current application's NSBundle's bundleWithIdentifier:appID
   
   try
      
      set SDVersion to SDBundle's infoDictionary()'s objectForKey:"CFBundleShortVersionString"
      
   on error errMsg number errNum
      set errorString to ("A-Error Number: " & errNum as text) & return & return & "Error Message: " & return & return & "\"" & errMsg & "\""
      
      display dialog errorString default answer errorString
      set the end of allErrorMessages to "         set SDVersion to SDBundle's infoDictionary()'s objectForKey:\"CFBundleShortVersionString\""
      set the end of allErrorMessages to "            " & errorString
      set SDVersion to "dummyText"
   end try
   try
      
      set BundleVersion to SDBundle's infoDictionary()'s objectForKey:"CFBundleVersion"
      
   on error errMsg number errNum
      set errorString to ("B-Error Number: " & errNum as text) & return & return & "Error Message: " & return & return & "\"" & errMsg & "\""
      
      display dialog errorString default answer errorString
      set the end of allErrorMessages to "      set BundleVersion to SDBundle's infoDictionary()'s objectForKey:\"CFBundleVersion\""
      set the end of allErrorMessages to "            " & errorString
      set BundleVersion to "dummyText"
   end try
   
   set SystemInfo to do shell script "sw_vers"
   set AppleScript's text item delimiters to {":   ", return}
   set SystemInfo to text items of SystemInfo
   set AppleScript's text item delimiters to {""}
   set SystemVersion to item 4 of SystemInfo
   set SystemBuildNum to the last text item of SystemInfo
   
   set infoString to " SD " & SDVersion & " (" & BundleVersion & ") OSX " & SystemVersion & " (" & SystemBuildNum & ")"
   
   set the clipboard to "-->" & infoString
   set newFileName to "Copy" & infoString
   
   set thisScript to path to me as alias
   
   --Unnote next line and run script to set script name back to default
   --set newFileName to fileNameFormat as text
   
   tell application "Finder"
      set oldFileName to the name of thisScript
      if "Unsaved Script Debugger Document" is in oldFileName then return
      if "Untitled" is in oldFileName then return
      set nameExt to the name extension of thisScript
      set newFileName to newFileName & "." & nameExt
      if oldFileName is not newFileName then set the name of thisScript to newFileName
   end tell
   -- your code goes here
on error errMsg number errNum
   set AppleScript's text item delimiters to {return}
   
   set errorString to ("Final-Error Number: " & errNum as text) & return & return & "Error Message: " & return & return & "\"" & errMsg & "\""
   set allErrorMessages to {errorString, allErrorMessages}
   display dialog errorString default answer errorString as text
   
end try
set AppleScript's text item delimiters to {return}
set errorString to ("Final-Error  Report:" & return & return & allErrorMessages as text)
display dialog errorString default answer errorString

--Final-Error  Report:
--
--         set SDVersion to SDBundle's infoDictionary()'s objectForKey:"CFBundleShortVersionString"
--            A-Error Number: -1708
--
--Error Message: 
--
--"missing value doesn’t understand the “infoDictionary” message."
--      set BundleVersion to SDBundle's infoDictionary()'s objectForKey:"CFBundleVersion"
--            B-Error Number: -1708
--
--Error Message: 
--
--"missing value doesn’t understand the “infoDictionary” message."

Ed,

The problem with using bundleWithIdentifier:, and an alternative method, are covered earlier in this thread.

Thanks, Shane, since, I’m not using SD 5 or FastScripts I didn’t think that was an issue. I’ll try what you suggested above.

Chris has pointed out to me off-forum that it fails when passed other apps’ IDs in Script Debugger 5, and from FastScripts. I have know idea why. But FWIW, here’s an alternative:

Ed,

I was wondering if you noticed do shell script “sw_vers” puts out a 3 item list and your script tries to access a forth item in the list. Earlier in the topic the line NSProcessInfo’s processInfo()'s operatingSystemVersionString() was used to get information. That returned 4 items. Now you are using “sw_vers” in a shell script and that returns a 3 item list. It’s hard to tell from the comments if you noticed that since they talk about something completely different.

I added to something to you code that causes it to run without errors. I just added a script line that generated a forth item for the list to make sure that was the only problem. It ran with no errors.

I put a comment containing 50 * characters so you can just search for multiple asterisks in the script. I can’t fix the code because I don’t know what you goal is, but if you want the fourth value you need another command or else you can just drop the forth part that works with the fourth item. That decision is up to you.

But NSProcessInfo’s processInfo()'s operatingSystemVersionString() would work in this case to get the fourth value.

use scripting additions
use framework "Foundation"
use framework "AppKit"
--> SD 6.0.4 (6A198) OSX 10.11.6 (15G1217)
set allErrorMessages to {}
try
	set appID to "com.latenightsw.ScriptDebugger6"
	set fileNameFormat to {"Copy SD ", "version and", " OSX ", "version"}
	
	set SDBundle to current application's NSBundle's bundleWithIdentifier:appID
	
	try
		
		set SDVersion to SDBundle's infoDictionary()'s objectForKey:"CFBundleShortVersionString"
		
	on error errMsg number errNum
		set errorString to ("A-Error Number: " & errNum as text) & return & return & "Error Message: " & return & return & "\"" & errMsg & "\""
		
		display dialog errorString default answer errorString
		set the end of allErrorMessages to "         set SDVersion to SDBundle's infoDictionary()'s objectForKey:\"CFBundleShortVersionString\""
		set the end of allErrorMessages to "            " & errorString
		set SDVersion to "dummyText"
	end try
	try
		
		set BundleVersion to SDBundle's infoDictionary()'s objectForKey:"CFBundleVersion"
		
	on error errMsg number errNum
		set errorString to ("B-Error Number: " & errNum as text) & return & return & "Error Message: " & return & return & "\"" & errMsg & "\""
		
		display dialog errorString default answer errorString
		set the end of allErrorMessages to "      set BundleVersion to SDBundle's infoDictionary()'s objectForKey:\"CFBundleVersion\""
		set the end of allErrorMessages to "            " & errorString
		set BundleVersion to "dummyText"
	end try
	
	set SystemInfo to do shell script "sw_vers"
	set AppleScript's text item delimiters to {":   ", return}
	set SystemInfo to text items of SystemInfo
	
	
	-- **************************************************
	-- I added this line and the script no longer errors
	set SystemInfo to SystemInfo & {"XXX"}
	
	
	
	set AppleScript's text item delimiters to {""}
	set SystemVersion to item 4 of SystemInfo
	set SystemBuildNum to the last text item of SystemInfo
	
	set infoString to " SD " & SDVersion & " (" & BundleVersion & ") OSX " & SystemVersion & " (" & SystemBuildNum & ")"
	
	set the clipboard to "-->" & infoString
	set newFileName to "Copy" & infoString
	
	set thisScript to path to me as alias
	
	--Unnote next line and run script to set script name back to default
	--set newFileName to fileNameFormat as text
	
	tell application "Finder"
		set oldFileName to the name of thisScript
		if "Unsaved Script Debugger Document" is in oldFileName then return
		if "Untitled" is in oldFileName then return
		set nameExt to the name extension of thisScript
		set newFileName to newFileName & "." & nameExt
		if oldFileName is not newFileName then set the name of thisScript to newFileName
	end tell
	-- your code goes here
on error errMsg number errNum
	set AppleScript's text item delimiters to {return}
	
	set errorString to ("Final-Error Number: " & errNum as text) & return & return & "Error Message: " & return & return & "\"" & errMsg & "\""
	set allErrorMessages to {errorString, allErrorMessages}
	display dialog errorString default answer errorString as text
	
end try
set AppleScript's text item delimiters to {return}
set errorString to ("Final-Error  Report:" & return & return & allErrorMessages as text)
display dialog errorString default answer errorString

--Final-Error  Report:
--
--         set SDVersion to SDBundle's infoDictionary()'s objectForKey:"CFBundleShortVersionString"
--            A-Error Number: -1708
--
--Error Message: 
--
--"missing value doesn’t understand the “infoDictionary” message."
--      set BundleVersion to SDBundle's infoDictionary()'s objectForKey:"CFBundleVersion"
--            B-Error Number: -1708
--
--Error Message: 
--
--"missing value doesn’t understand the “infoDictionary” message."

Bill

That’s odd, Bill, on the line that sets the TIDs the first should be a colon and a tab and the second a return character. It seems that in the back and fourth with discourse the tab is replaced by three spaces. If you use this then it fixes it.

   set AppleScript's text item delimiters to {":" & tab, return}

(FYI, the shell script to get the version was something I was using to make sure we were getting the same info from all the scripts on every machine I ran it on. You’re right, it’s not required)

Hi there,

I’m looking for the shortest way to let a script application show its own build number (not version).

I don’t understand Obj-C so this is the shortest way I found. But isn’t it possible with on line?

set SDBundle to current application's NSBundle's bundleWithIdentifier:(id of me)
set appBuild to (SDBundle's infoDictionary()'s objectForKey:"CFBundleVersion") as string

Cheers

Try this:

use AppleScript version "2.4" -- Yosemite (10.10) or later
use scripting additions
use framework "Foundation"

set SDBundle to current application's NSBundle's mainBundle()
set appBuild to (SDBundle's infoDictionary()'s objectForKey:"CFBundleVersion") as string

Thanks Mark, but that gives me a hex value and not the one stored in the field “build #” of Script Debugger.

6A### is the correct form for a Script Debugger 6 build number. Its not hex. 6A denotes Script Debugger 6, and then the digits following are a sequential build number.

Okay, so I wasn’t clear enough. I’m interested in then build # of my own script application and not from the Script Debugger. I want to show my build # in a dialog.

You can do something like this:

use AppleScript version "2.4" -- Yosemite (10.10) or later
use scripting additions
use framework "Foundation"

set theBundle to current application's NSBundle's bundleWithPath:((path to me)'s POSIX path)
set appBuild to (theBundle's infoDictionary()'s objectForKey:"CFBundleVersion") as string

Note that this will only work correctly for scripts saved as Script Applications because SD only modifies the Info.plist at runtime for this type of document. This is probably a bug when working with bundled scripts that we should resolve.

1 Like