Simulate the Enter key

Hello,

I want run the following command:

sudo sysdiagnose -v

From the Terminal, it’s necessary to press Enter.

In do shell script a message appears:
Triggering sysdiagnose programmatically from CLI with incorrect arguments. Exiting.

Is it possible to simulate the Enter key to run this command in do shell script ?

do shell script “sysdiagnose -v” with administrator privileges

Thanks.

If you don’t mind that the terminal window is showing you could use something like this.


tell application "Terminal"
	activate
	set scriptOne to "sudo sysdiagnose -v"
	set scriptTwo to "-my password-"
	tell application "System Events" to keystroke scriptOne & return
	delay 1
	tell application "System Events" to keystroke scriptTwo & return
	delay 1
	tell application "System Events" to keystroke return
end tell

Hi Titanium,

Did you figure out the solution. Im also in the same situation.

Well, as I understand from technical notes of Apple:
You can script Terminal and send a series of commands to the same window, but you can’t control an interactive tool like sysdiagnose with do shell script (that is, in the background).


tell application "Terminal" to do script "sudo sysdiagnose -v -f ~/Desktop"

This triggers sysdiagnose, but shell waits for user input (for password).
After entering the password, shell waits for user input again (for confirming to start diagnostics).
Here, with 2 rest steps, you can’t avoid GUI scripting. So, all code should be like this:


tell application "Terminal" to do script "sudo sysdiagnose -v -f ~/Desktop"
delay 1

tell application "System Events"
	set frontmost of process "Terminal" to true
	keystroke "YourPassword" & return
	delay 1
	keystroke return
end tell

If you want to avoid username and password entry for a particular command run under a particular user, you can add it to your /etc/sudoers file.

There are potential security implications, but if this is a personal computer I’d expect it’s fine, and sysdiagnose probably has low potential for abuse anyway.

https://www.tecmint.com/run-shell-scripts-with-sudo-command-in-linux/

For more security you can use the following script. Save it as run-only script or, better, as applet.


set aPassword to text returned of ¬
	(display dialog "Please, enter your password" default answer "" with hidden answer)

tell application "Terminal" to do script "sudo sysdiagnose -v -f ~/Desktop"
delay 2

tell application "System Events"
	set frontmost of process "Terminal" to true
	keystroke aPassword & return
	delay 2
	keystroke return
end tell

If you’re going to ask for a password each time it’s run, you might as well skip the terminal scripting.

set aPassword to text returned of (display dialog "Please, enter your password" default answer "" with hidden answer)

do shell script "echo " & aPassword & " | sudo -S sysdiagnose -v -f ~/Desktop"

But I wouldn’t call that a “more security” option than adding sysdiagnose to sudoers.

It’s not hard to extract a plain text password from a run-only AppleScript.

I exported KniazidisR’s script as a run-only Applescript application, as suggested. Only change was I changed the shell command to “sudo ls ~/Desktop” because I didn’t need a sysdiagnose.

I ran it once, and entered the (incorrect) password “bonkers”

Then inside the Application bundle, I opened /Pwd Test Run-Only.app/Contents/Resources/Scripts/main.scpt in TextEdit, which yields:

And as you’ll note, I bolded the password there in plain text.

Applescript saves the contents of top-level variables into the script… and if it’s a string, it saves it as plain text, which is easily accessible even on a run-only script.

So your suggested security improvement would leave the admin password hanging around in plain text on the computer.

You can avoid having the script save the password by never setting a variable to it:


do shell script "echo " & text returned of (display dialog "Please, enter your password" default answer "" with hidden answer) & " | sudo -S sysdiagnose -v -f ~/Desktop"

I tested that, and the password is not saved in the script.

If you had a longer script, not being able to save something as a variable might get annoying. You can also stop it from saving the variable contents back to the script by putting it into a handler outside the “run” (or default) handler.

shell_sysdiagnose()

on shell_sysdiagnose()
	set aPassword to the text returned of (display dialog "Please, enter your password" default answer "" with hidden answer)
	do shell script "echo " & aPassword & " |  sudo -S sysdiagnose -v -f ~/Desktop"
end shell_sysdiagnose

Depending on what an acceptable level of security is on the system in question, if you need it to run without asking for a password each time, and you don’t want to add sysdiagnose to sudoers, you can obfuscate the password in a run-only script. It would certainly be possible to reconstruct the password out of this… but it would take some really serious effort, so personally, I’d only be worried about it in the most dire security situations.

There are various ways, but I’ll just grab DJ Bazzie Wazzie’s from here:
https://stackoverflow.com/questions/14612235/protecting-an-applescript-script

Run this script with your password:

set encPass to simpleEncryption("bonkers")
return encPass

on simpleEncryption(_str)
	set x to id of _str
	repeat with c in x
		set contents of c to c + 100
	end repeat
	return string id x
end simpleEncryption

Take what it returns and plug it in for “encPass” here:

shell_sysdiagnose()

on shell_sysdiagnose()
	set encPass to ""
	set aPassword to simpleDecryption(encPass)
	do shell script "echo " & aPassword & " |  sudo -S sysdiagnose -v -f ~/Desktop"
end shell_sysdiagnose

on simpleDecryption(_str)
	set x to id of _str
	repeat with c in x
		set contents of c to c - 100
	end repeat
	return string id x
end simpleDecryption

Then save that script as run-only. The password will technically be extractable from the script, but it would take some effort to get it back out. Here’s the extractable plain text:

There are Applescripts with more advanced encryption you can Google up:
https://www.macscripter.net/viewtopic.php?id=19520
but if you actually need that in your situation, you might want to just reconsider the whole security case for what you’re doing.

Yes that’s right. Saving the script as run-only is a child’s defense. So, it is better saving it as applet.

I would only add that 100 percent protection does not exist. In 1993, I bet with one representative of a very serious software company in my country. He told me that no one has managed to break their passwords. Then I asked him for a protected copy of one expensive program ($ 1400).

I went home and ran the DEBUG command with this program (on my old Windows computer). This command provides everything in Assembler language - in machine codes. I delved into this code for 3 days and found the password request point in the code. Then I inserted a JUMP instruction at this point to bypass the code verification fragment. On the 4th day, I took the hacked copy to the owner and earned $ 500. He was surprised and asked me how I managed to find a password ?! It consists of 128 characters! I said: “I still don’t know your password. I just bypassed it …”

I tested it, and that code doesn’t work at all. Applescript execution error: “Password:Triggering sysdiagnose programmatically from CLI with incorrect arguments. Exiting.”

I tested that too, and that code doesn’t work at all too. The same execution error occurs.

As I already said above, you can’t avoid GUI scripting Terminal.app for interactive shell commands. I will repeat my code in a slightly modified form. It works without errors and is quite safe as an application:


tell application "Terminal" to do script "sudo sysdiagnose -v -f ~/Desktop"
set aPassword to display dialog "Please, enter your password" default answer "" with hidden answer

tell application "System Events"
	set frontmost of process "Terminal" to true
	keystroke (text returned of aPassword) & return
	delay 1
	keystroke return
end tell

NOTE: I don’t see any way to avoid setting the password to variable, as we need the Terminal process as frontmost.

KniazidisR,

Regarding “Applets”

Can you explain what you mean by an “Applet?” I was saving as a run-only application. From Script Editor, “Export” → File Format: Application with “Run Only” selected.

Or from Script Debugger, “Export Run-Only Script” Format: Application.

I had thought that’s what you meant by an “Applet,” it’s how I see it being used elsewhere:

https://www.macosxautomation.com/applescript/bundletools/index.html

As I stated, I “exported KniazidisR’s script as a run-only Applescript application” and the location where I found the plain-text password was “inside the Application bundle” in "/Pwd Test Run-Only.app/Contents/Resources/Scripts/main.scpt "

So I don’t understand what you’re referring to by an “Applet” if not an Applescript run-only application. Please let us know.

Regarding your error message

The reason the code doesn’t work is because I copied and pasted it from your script without testing it, and yours doesn’t work either.

Sorry, I should have tested rather than assuming prior contributors had posted working code. That was definitely a mistake.

As I noted, in my testing, I switched out the “sysdiagnose” command for an “ls” because I didn’t really want to run a bunch of sysdiagnoses, and the point of the script is to work around the requirement of entering a password for sudo, so the commands provided to sudo are irrelevant here. Well, irrelevant as long as they’re functional.

Running your script:



set aPassword to text returned of ¬
	(display dialog "Please, enter your password" default answer "" with hidden answer)

tell application "Terminal" to do script "sudo sysdiagnose -v -f ~/Desktop"
delay 2

tell application "System Events"
	set frontmost of process "Terminal" to true
	keystroke aPassword & return
	delay 2
	keystroke return
end tell

Yields a terminal window with the following contents:

So I went back to the first message… which says they want to run “sudo sysdiagnose -v.” Running that in my terminal, it just says that “-v” is an invalid argument for sysdiagnose, and sure enough, -v is not in the man page for sysdiagnose either.

Shahab’s recent post kicking off this discussion also says the error he was getting is “Triggering sysdiagnose programmatically from CLI with incorrect arguments. Exiting.”

Which isn’t surprising since we’ve all been calling sysdiagnose with incorrect arguments in our code.

If you try any of my scripts with the invalid “-v” argument removed, and just stick to valid shell commands, they work.

The “-v” argument is valid. You can see the options if you run sudo sysdiagnose -h in the Terminal:
-v Enable verbose mode to display the container information as it executes.

But I tried your scripts with removed -v option. They still throws the same error and doesn’t work. So, you still should test your suggestions before posting here, since the Apple is right here and not you.

Regarding the applet: AppleScript has applets and droplets. Applet is small application.

The presence of -v must be an environmental difference. It’s not valid on my system running 10.12.5. I mean, obviously, I pasted in the full returned text showing that the error returned with running “sudo sysdiagnose -v -f ~/Desktop” was “Unexpected option or insufficient arguments.” And the -f option is valid. I also said that simply running “sudo sysdiagnose -v” from Terminal on my computer just yields an error, so obviously it’s not valid on my system.

Your suggestion of “sudo sysdiagnose -h” also shows it’s not present on my system… “sudo sysdiagnose -h” doesn’t show it, but of course it wouldn’t since I already said it wasn’t in the man page on my system.

As for the scripts not working… that’s a pretty odd environmental difference to stop them from working without the -v on your computer (or with it, if “-v” is valid on your system).
I mean, you pasted the error you got into your message:

And that’s pretty weird that you’re getting the error “Triggering sysdiagnose programmatically from CLI with incorrect arguments” if you’re passing sysdiagnose correct arguments.

I did try all three of my scripts on my system without the -v, and they all ran fine. No errors from Applescript. The Sysdiagnose logs were all saved to the desktop correctly. The usual terminal output was returned to Applescript after the command completed for each.

Just in case there’s anyone else following along here, can anyone else reproduce KniazidisR’s error with any of my scripts, if you remove the -v argument? I’m quite curious what could possibly cause terminal to error that the command had incorrect arguments supplied if it doesn’t.

I’m still not clear on if there’s something different about what you’re referring to as an “Applet” compared to my example of saving the script as a run-only application, which was the example I gave where it saves the admin password in plain if used with your script.

Tom,

I haven’t followed this, but sysdiagnose does seem to have changed a bit. Here’s what I see in 10.15.1:

Hi, t.spoon. It seems, sysdiagnose has changed, so your snippets which works fine on your old system, doesn’t work on my Mojave operation system. I guess, it doesn’t work on Catalina too. You are absolutely right about one thing, and I was wrong: for better security you need to use the code as a handler so that AppleScript cannot save the password (as value of top-level variable) in the application’s bundle:


shell_SystemDiagnose() of me

on shell_SystemDiagnose()
	tell application "Terminal" to do script "sudo sysdiagnose -v -f ~/Desktop"
	set aPassword to display dialog "Please, enter your password" default answer "" with hidden answer
	tell application "System Events"
		set frontmost of process "Terminal" to true
		keystroke (text returned of aPassword) & return
		delay 1
		keystroke return
	end tell
end shell_SystemDiagnose

NOTE: I guess, other way is setting variable aPassword to “” (or, to whatever other then the user password) immediately after keystroke code line.

KniazidisR,

Thanks for clarifying the stored variable issue with Applescript Applications.

I got a chance to access a computer on Catalina 10.15.1.

So, with the updates to sysdiagnose with newer versions, it now needs the -u argument provided when it’s being run programmatically. The older version of sysdiagnose on my system didn’t have “-u” and could be run “headless” without any special arguments.

So this works on newer versions of MacOS, and returns the “verbose” information requested with the “-v” flag to Applescript.

set sysdiagnoseResult to do shell script "echo " & text returned of (display dialog "Please, enter your password" default answer "" with hidden answer) & " | sudo -S sysdiagnose -u -v -f ~/Desktop"

Although I’m probably missing the boat here with doing this outside a terminal window; the intention of running it with the “-v” argument is probably because the original asker was looking for live feedback as it executes.

Posting because it might be handy to someone in the future if they want to run sysdiagnose programmatically. I’m guessing in some cases where someone wants to script sysdiagnose, they would NOT want the terminal to pop up.

Well, t.spoon, thank you very much. Your last code runs perfect, and goes to my scripts library as one of the useful scripts, along with my own script (which shows the process live). I just will remove the -v option from your script.