Does 'run script' inhibit logging in Yosemite?

Talking about bugs, while


log "Hello, world"

correctly logs the supplied text, the following


run script "log \"Hello, world\""

does not log anything. I’m pretty sure that before OS X 10.10, both scripts would produce the same result. Is there a workaround for the latter case? I vaguely remember that AppleScript had some statements to turn logging on/off. Maybe that is what is needed here?

If you’re curious, my use case is a script that is run from the command-line: log statements are used to print output to the terminal. Starting with Yosemite, I get no output.

Hello.

I don’t know if it comforts you to know that it doesn’t work under Mavericks either. :wink:

However, this works, at least in the AppleScript Editor, I think it should work in the Terminal as well.

run script "return  \"hello world\""

Hi druido,

When you use ‘run script’ in a script, that script is not the parent. Just like when you call a shell script. Also, ‘log’ has no result:

set r to run script "log \"hello\"
return result"

It goes straight to the Script Editor.

gl,
kel

You are right. I’ve got my hands on an OS X Lion machine, and it has the same behaviour. So I’m lost. But there must be some difference, because now I’ve tested my scripts in Lion and Yosemite, and their behaviour is different. This post was my attempt at reproducing the problem with a minimal example, but, apparently, the example is not the right one.

If you want to reproduce the problem I have, you may clone https://github.com/lifepillar/ASUnit and run these commands in Terminal:

In Lion (and up to Mavericks, I believe), they give exactly the same output, but in Yosemite the second command does not output anything, although it otherwise executes correctly (I’m sure about it, because I can enable logging to the terminal and to Script Editor at the same time, and I see the output in Script Editor). I’m trying to figure out why.

Ok, here is a correct (almost) minimal example:


on logMeBaby()
	log "There are " & ((random number from 2 to 6) as text) & " elephants"
end logMeBaby

repeat 5 times
	logMeBaby()
end repeat

Save as logmebaby.applescript and try:

In Yosemite, the second command will not output anything. In Lion, and probably up to Mavericks, they are equivalent. Do you think it’s a bug?

Hi druido,

At about the time of mountain lion I think, Apple added a ui to osascript. Maybe that has something to do with it.

gl,
kel

Try this in Lion and Yosemite:

do shell script "osascript -e '
display dialog \"hello\"
'"

Before they added the ui, you had to do something like this:

delay 5
do shell script "osascript -e '
tell app \"System Events\"
display dialog \"hello\"
end tell
'"

Edited: just thought of something. Maybe you might try placing the ‘log’ in a tell block like that in Lion.

gl,
kel

No, they’re unlikely to help. They’re essentially AppleScript no-ops, left for editors to respond to.

The Apple engineer that added the interactive option to osascript for 10.10 certainly didn’t understand how OSA is designed to work (his implementation is complete garbage and wrong), so it could be he also busted some existing behaviors along the way.

OTOH, the finer details of the run script command’s operation have never been publicly documented AFAIK, in which case the way that an AS interpreter executing inside another AS interpreter handles a log command would fall under the category of ‘undefined behaviors’. If that’s the case then the previous behavior was accidental and the fact that it’s now changed is equally accidental, meaning you’re probably SOOL unless you can present Apple with a compelling argument as to why the previous behavior is vital and should be officially reinstated.

Personally though, I can’t see why you’d want to use osascript to execute a run script command to execute an AppleScript file. It has a distinct whiff to it; perhaps if you explained what you’re actually trying to achieve, a better implementation that doesn’t involve any hokey run script commands may be found.

Unlikely. All osascript does for that is intercept the ‘No user interaction allowed’ (-1713) error that’s returned when [e.g.] a display dialog command is unable access the window manager, calls TransformProcessType() to get a GUI connection, then resends the command. The OP’s problem tangles with deeper OSA arcana that I’m not going to attempt explaining as it makes my head hurt.

Hi hhas,

Thanks for getting that off my mind also. Now I can sleep maybe.

Have a good day,
kel

Ah wait, just noticed the ASUnit link. Executing unit tests would arguably would fall under ‘genuinely justifiable uses’ for the run script command, since you want each test case to run in its own isolated environment [1].

That said, ASUnit was based on my earlier ASTest library, which was some of the foulest AppleScript code ever devised, so there’s still a bunch of things that can go wrong. (With hindsight, it wasn’t the wisest way to implement an AppleScript testing framework, although AppleScript’s such an intractable basketcase when it comes to adding any sort of debugging/profiling/testing support I wouldn’t even bother.)

My gut feeling would be to flip your test runner implementation about, so instead of using run script "some-test.applescript" it uses do shell script "osascript some-test.applescript", and see how that goes.

[1] Although you’re not going to get reliable isolation nowadays anyway, not unless you run every single test as a separate process, as 10.9’s library system leaks state all over the place.

‘run script’ has its own environment just like do shell script, so why would you get logging?

I don’t understand why someone would log when it doesn’t go anywhere.

Hello.

This is a kluge, but it should always work.

on osalog(theLogStatement)
	return theLogStatement
end osalog

osalog(" today is " & (current date)'s date string)

Thanks for your comments, all interesting indeed. Below, some specific replies.

@kel1 Good to know about the UI for osascript. Putting log commands in a tell statement does not solve my problem, though.

@Shane Thanks, now I remember! You were explaining about start log and stop log in this thread: http://macscripter.net/viewtopic.php?id=42078.

@hhas You may well be right about the finer details of run script. BTW, I’d be curious to know why exactly you think that the current implementation is garbage and wrong (maybe a topic for another thread?). About ASUnit, it does not rely on run script to isolate tests. Its architecture is quite robust and, in my opinion, pretty clean and “AppleScript-ish” (to be fair, the merit goes to the original author Nir Soffer, not to me). And I might be wildly wrong (so much time has passed since I took a look at ASTest), but I think the two use significantly different approaches.

So, what is my use case? I have a sort of “makefile” AppleScript script, which I use from the command-line to execute several tasks, including running other scripts (see, for example, the test script in this file https://github.com/lifepillar/ASMake/blob/master/makefile.applescript). I naïvely believed that run script "SomeExternalScript"would be more or less equivalent to run someScriptInThisSourceFile, but by your comments I see that my understanding is superficial.

For the sake of completeness, I ended up compiling my script and loading it with load script. That is, instead of writing:

in my workhorse script, now I use something along these lines:

By doing so, the log commands that exist in SomeExternalScript still generate output in the terminal when the script above is run with osascript.

In the meantime I have had other issues with osascript (related to scripts that present some GUI), so I’m starting to think that something is indeed broken in Yosemite.