0

I know that I can run a local bash script on a remote host via ssh per this other question. But what about running a local awk script that receives a file as a parameter?

I've tried something like this but no luck:

ssh myuser@machine 'awk -s' < awk -f my_local_awk_script.awk "/remote/path/remote_file.txt"
Arthur Accioly
  • 801
  • 9
  • 26
  • `ssh` is not an all-purpose "run this stuff, but there, not here" interface. You would be better off copying the script to the remote host first, *then* executing the desired `awk` command. – chepner Jun 01 '21 at 18:55

2 Answers2

2

Try

ssh myuser@machine "awk -s '$(<my_local_awk_script.awk)' /remote/path/remote_file.txt"

This interpolates the exact contents of the local file as flat text into the string, so embedded single-quotes will likely cause it to explode.

My target system doesn't have the -s option for awk, so I couldn't test that.

My local file:

BEGIN{ print "Hello, " }
NR=1{print "World!"; exit; }

the output:

$: ssh sa-nextgen-jenkins.eng.rr.com "awk '$(<x)' x"
Hello,
World!

Safer - copy the file over and execute it, then delete if you need to.

$: scp x sa-nextgen-jenkins.eng.rr.com:~/x && 
>  ssh sa-nextgen-jenkins.eng.rr.com "awk -f x .bash_profile && rm ~/x"
x                                                                                                              
100%   56     0.7KB/s   00:00
Hello,
World!

so for you:

scp my_local_awk_script.awk myuser@machine:~/my_local_awk_script.awk &&
ssh myuser@machine "awk -s -f ~/<my_local_awk_script.awk /remote/path/remote_file.txt && rm ~/my_local_awk_script.awk"

Make sure you don't botch that and accidentally delete your local. You might want to put the remote in /tmp, etc.

Paul Hodges
  • 13,382
  • 1
  • 17
  • 36
  • I've tried that but didn't work. How can I specify the "-f" parameter? – Arthur Accioly Jun 01 '21 at 18:52
  • Risky, as the `awk` script itself could contain single quotes which will be exposed to the shell before `awk` ever runs. – chepner Jun 01 '21 at 18:54
  • Oh, I don't have the "awk -s" as well. I was just trying to mimic the "bash -s" of the other question! Let me try your suggestions. Thank you! – Arthur Accioly Jun 01 '21 at 19:07
  • The scp && run trick worked. I've put "-q" to avoid extra verbosity. For some reason, maybe because my script has too many lines, the first solution didn't work, but I think that it's fine. Thank you again! – Arthur Accioly Jun 01 '21 at 19:25
  • Second was the better, safer, *saner* way. First was just a quick hack to showcase a trick that might be useful in *limited* cases. :) – Paul Hodges Jun 01 '21 at 19:55
  • [Accept the solution](https://stackoverflow.com/help/someone-answers)? – Paul Hodges Jun 01 '21 at 19:56
2

Can this achieve what you expected :

ssh myuser@machine awk -s -f /dev/stdin /remote/path/remote_file.txt < my_local_awk_script.awk
Philippe
  • 20,025
  • 2
  • 23
  • 32
  • I like this better than mine. An elegant solution that does *exactly* what was requested. Bravo! It reads the `awk` script from a file - `/dev/stdin` - on the remote host, literally reading from the local copy of the original file on the local host to do so, without making copies or having to chain commands. This goes in my toolbox. :) – Paul Hodges Jun 02 '21 at 13:16
  • Only complication I see is if the script does any reads directly from stdout, which seems pretty unlikely in this case. – Paul Hodges Jun 02 '21 at 13:18
  • @PaulHodges, Indeed, if the script reads from stdin, maybe the only option is copying the script over. – Philippe Jun 02 '21 at 14:46
  • I agree, this actually works even better! Just remove the "-s". We don't need that. Thank you! – Arthur Accioly Jun 03 '21 at 20:56