#Scripts with shell_command

102 messages · Page 1 of 1 (latest)

thick furnace
#

I have a script, which fires two shell commands. The first shell command (these are ssh commands) that the script calls fires correctly. There is then a short delay (2 seconds, but I've also tried 5 and 10) and then a second shell command fires to turn off what the first one turned on. I have tried a few different commands that do the same thing, and none of them work.

HOWEVER all lines of the script work when fired manually, by selecting the "three-dot menu" and selecting "run" on the lines in question.

I have tested the ssh command from the homeassistant docker container using the advanced ssh and terminal plugin, as per this extensive post: https://community.home-assistant.io/t/sshing-from-a-command-line-sensor-or-shell-command/258731

shell_command:
  cleanup_alert: ssh sparkyvison@192.168.1.11 -i /config/.ssh/id_rsa 'mpv -loop-file /media/alerts/alert13.mp3 &'
  cleanup_alert_off: ssh sparkyvision@192.168.1.11 -i /config/.ssh/id_rsa 'pkill -f mpv'

And here is the script

sequence:
  - action: shell_command.cleanup_alert
    continue_on_error: true
    data: {}
  - delay:
      hours: 0
      minutes: 0
      seconds: 5
      milliseconds: 0
    enabled: true
  - action: shell_command.cleanup_alert_off
    continue_on_error: true
    data: {}
alias: Cleanup done alert sound
description: ""
mode: restart

At first I thought perhaps I had error codes which might be interfering, but I enabled continue_on_error to get around that.

#

Again, I've confirmed the both ssh commands work, both via "real" ssh and from the homeassistant docker container that I can switch into via the Advanced SSH and Web Terminal plugin.

The command does throw an error code of 1 into the HA console, but again, it works via the Advanced SSH and Web Terminal plugin CLI, AND it works when I manually fire that line in the script.

thick furnace
#

Bump, I guess, if that's allowed here.

thick furnace
#

I have, in fact, done further testing, asking that script to call a separate script that runs the second ssh command, and that doesn't work either. At this point it makes me think I'm misunderstanding / not writing scripts correctly.

river condor
#

I don't know much about Advanced SSH plugin but are you sure that's running in the same container and as the same user as a script command?

thick furnace
#

Pretty sure, if that guide that I followed was correct. I used

docker exec -it homeassistant bash

#

And ran the commands to make sure ssh accepted the remote server fingerprint, which it did.

river condor
#

oh wait you said the individual shell_commands work correctly?

#

missed that

thick furnace
#

They are

#

Within the script, even! They work when I run them manually.

#

The script just doesn't script.

river condor
#

what does "not working" look like?

#

did you review the Trace?

thick furnace
#

I did, the trace shows, if I'm reading it correctly, that it never gets around to firing the command.

#

I can post a screenshot in a moment.

#

(Those runs are from me manually running the lines. The command makes an alarm go off in my kitchen that annoys everyone.)

#

But, why is it waiting any amount of time more than 2 seconds?

#

There are errors from the "cleanup_alert_off" ssh command in the logs, but not the "cleanup_alert" command.

river condor
#

you can share the entire trace json. I think from that it looks like it's running both commands?

thick furnace
#

You mean this?

2025-03-10 18:19:03.303 ERROR (MainThread) [homeassistant.components.shell_command] Error running command: `ssh craig@192.168.1.11 -i /config/.ssh/id_rsa 'pkill -f mpv'`, return code: 1
#

Oh, no, you don't mean that

#

One sec

river condor
#

hmm I'm not sure. It seems like everything ran, but the first command took 18 seconds to return

#

maybe the run in background thing doesn't work there

thick furnace
#

It would’ve taken infinity to return, it only advance because I went ahead and manually ran the third line.

#

(Testing this script makes my family hate me. 🙂 )

#

A more detailed log would be very helpful here, but I’m not sure where to find one

#

Do those "running_script: false" statements suggest something?

zenith summit
#
  1. I don't think your background command does anything over ssh, you can use -f 2) then pkill with a non-existent process returns status 1
#

-f actually keeps the session running, so probably not

thick furnace
#

Background command?

zenith summit
#

mpv -loop-file /media/alerts/alert13.mp3 &

#

What are you attempting to do there?

#

the & means run the command in the background

thick furnace
#

I would like the remote system to play a sound, wait two seconds, and then stop playing that sound. I looked into doing this with a variety of media server solutions, none made as much sense as just sending a simple mpv command.

thick furnace
#

I know there are different ways to do this, but I want to be able to both turn it on and turn it off, rather than only having a play once. Loop is something I want to be able to do here.

#

Anyhow, I can remove the & and see if that does anything

zenith summit
#

I don't think the shell command is running in the background though

thick furnace
#

How do you mean?

zenith summit
#

The sequence step doesn't wait for the command to finish? I'm actually not sure there.

thick furnace
#

Oooh, as in, you think it's not advancing because it's waiting for the command to finish, so ssh is just sitting there while mpv does its thing?

zenith summit
#

Yes. It's supposed to timeout after 60 seconds

thick furnace
#

Okay. That makes some sense. Is there a way to make it execute then disconnect?

#

Could I make it a shell script on the remote machine?

zenith summit
#

Can you just do:

cleanup_alert: ssh sparkyvison@192.168.1.11 -i /config/.ssh/id_rsa 'timeout 2 mpv -loop-file /media/alerts/alert13.mp3

?

thick furnace
#

I wasn’t aware there was such a command as timeout

#

However, that doesn’t solve the use case where I would like it to loop indefinitely until it receives a command to stop

#

Or does that?

#

It does. Nevermind

zenith summit
#

You can maybe use nohup

#
cleanup_alert: ssh sparkyvison@192.168.1.11 -i /config/.ssh/id_rsa 'nohup mpv -loop-file /media/alerts/alert13.mp3 1>/dev/null 2>/dev/null &'
#

or for bash shortened to

cleanup_alert: ssh sparkyvison@192.168.1.11 -i /config/.ssh/id_rsa 'nohup mpv -loop-file /media/alerts/alert13.mp3 &>/dev/null &'
thick furnace
#

Hm, okay....first I must feed several hungry children, then I will try this 😄

thick furnace
#

Alright, hrm. The question is whether nohup will keep the ssh terminal alive.

#

Let's find out

#

@zenith summit That indeed solved the issue.

#

Thank you for the help.

To anyone coming after, scripts using ssh shell_commands need to terminate before the script will move on, regardless of script run settings.

sweet frost
#

you could probably stick the call in a separate script and call it with script.turn_on, in which case that action will run in parallel with the rest of the original script

thick furnace
#

I tried that, actually.

I have, in fact, done further testing, asking that script to call a separate script that runs the second ssh command, and that doesn't work either.

#

I also thought that would work.

#

I must say, though, that I'm a little confused as to why that method failed

#

Oh I undertand what you're saying.

  1. Call script.2_second_delay_then_fire_off_command
  2. alarm_on
#

That feels hacky 😛

zenith summit
#

One script starts the loop, the other stops it.

thick furnace
#

But in that solution, the stop script has to be started first to avoid the ssh "not listening" condition

#

I mean, it's listening, it's just waiting for the command to finish

zenith summit
#

I'm not following that logic, sorry

thick furnace
#

Sorry, my cat is head-butting my hands while I'm trying to type.

#

The issue is that once started, the script waits for the SSH shell it starts to be "done"

zenith summit
#

script.turn_on script.that_loops_mpv --> wait some time -> script.turn_on script.that_stops_mpv

thick furnace
#

So if you start a script ahead of time that has a countdown to issuing the "off" command, you can sidestep that.

#

Right, it never gets there because the scripting engine waits. At least, without nohup, which sidesteps the issue entirely.

zenith summit
#

script.turn_on does not wait

thick furnace
#

But, isn't that what nohup is solving?

zenith summit
#

How are you calling the script?

thick furnace
#

Hang on...you saw that we're solved, right?

#

Your method works

zenith summit
#

Yeah but we're talking about the other option now. We can stop if you want.

thick furnace
#

No, it's okay. I like trying to wrap my head around what I did wrong.

thick furnace
zenith summit
#

there's action: script.<name_of_script> and then action: script.turn_on

thick furnace
#

Those are separate?

zenith summit
#

The former waits, the latter does not.

#

So which are you using?

thick furnace
#

For some reason I thought continue_on_error made it not wait, but apparently I was misinformed.

sweet frost
#

It's not an error

thick furnace
#

No, I suppose it isn't

#

Anyway, I was calling the script directly.

#

So that would also be the issue

zenith summit
#

Yep

#

Also, you're still limited to a max of 60 seconds that way

thick furnace
#

Starting the looped file on the remote server makes that irrelevant, though, I don't actually need to keep the ssh connection alive that long.

#

So, in the second solution suggested here, my turn on script would use turn_on to activate another script with the ssh command?

#

Then it would continue as normal?

sweet frost
#

Yes

thick furnace
#

Scripty

#

I like altering the SSH command. It feels cleaner, somehow