SD and OS X version script

Shane,

I’m confused. How did the script I modified work without a use framework “Appkit”? When I finish a script I always take out all the included stuff that isn’t needed so only the needed stuff would be left. My system has been if it works without it then it’s not needed. I assume later it will cause a problem at some unexpected time.

Bill

Ed,

Bill’s database does not have a lot Appkit stuff yet and my database is not complete. I’ll add this stuff to the database and post it to this discussion.

objectForKey is in Bill’s database but infoDictionary is not.

The link to “Core Foundation Keys” Jim posted is the page I use. Although I downloaded the page as a web archive to my Mac in case Apple gets rid of the web page some day. They do that from time to time.

Bill

There is nothing wrong with doing that. The question is which way would you include it. List them separately at the top so they can all be seen at once or in the code, either in the code above the line where they are used or to the right of the line, whichever works best.

Bill

They’re already listed at the top with the “use” line, but it would be helpful if they were noted with the command, before or after.

–Framework

or

–AppKit

I can see how that page would be useful to you and Shane and Jim, but wasn’t much help to me.

Ed,

The latest version of the database is A15. Is that the version you used?

I’m not sure what you are referring to. Can you include a picture in a post. Then I can fix that.

The Framework section of the database only searches Frameworks. But the class section searches all classes in the database, for all the Frameworks entered in the database. For now those frameworks are just Foundation and AppKit. The class items list all class items, for all the classes, for all the frameworks, in the database. So if you are looking for a particular class use the class section, but if you are looking for the thing that does the actual work it will be a class item. Classes are are a collection of useful things with abilities related to solving some kind of issue.

For me I mostly just search class items to find what to use. When I find something the database tell’s me what class and framework to use when typing in the command. There are times the same class item name will appear in different classes. For this case use the class item with the class that best suits your intended purpose.

The database can do this kind of stuff but you have to break it down. To start with SDBundle is a user created item listed earlier in the discussion. The creation line is listed below.

SDBundle to current application's NSBundle's bundleWithIdentifier:"com.latenightsw.ScriptDebugger6"

So to understand this command you have to understand NSBundle’s bundleWithIdentifier. If you look up NSBundle in the class part of the database you will get only class information. It will not talk about the things in the class. So to understand the line you look up bundleWithIdentifier. Now if Bill’s database was more complete it would have had bundleWithIdentifier in it and you would have got your answer. But lucky for you I know the guy who created the database so I can get him to add that. If it was in there then you could see an explanation and samples.

Bill

I’m on version 14. I must have missed the announcement for 15. Can you post a link?

[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