2

Hello so I have been making a small cross platform script I can curl and pipe into bash and Powershell. The basic idea is the server sends a command to the interpreter and then it gives a command to redirect all output after to stdout. An example in bash is

#some commands 
aplay rick.wav
cat -
random text
that will be redirected to stdout by cat... 
bash will never see this

I would then pipe this to stdin of bash

But for Powershell I can do cat test.ps1 | iex or cat test.ps1 | powershell - But can't redirect stdin to stdout continuously in one command like cat - because cat doesn't look from stdin.

Also some side notes after trying a lot of random things it seems like there are many stdin types for Windows, one being keyboard and another being pipes

Compo
  • 36,585
  • 5
  • 27
  • 39
Jesse Taube
  • 402
  • 3
  • 11
  • As an aside: Windows doesn't come with a `cat` executable, and in PowerShell `cat` is simply an _alias_ for the [`Get-Content`](https://learn.microsoft.com/powershell/module/microsoft.powershell.management/get-content), which doesn't accept pipeline input. – mklement0 Aug 16 '21 at 20:01

1 Answers1

1

You can pipe lines of text to powershell.exe, the Windows PowerShell CLI, via -Command - (-c -), and it will interpret them one by one.

Here's an interactive demonstration from inside PowerShell; it works the same with input piped (provided via stdin) from the outside:

# Repeatedly prompt for a line of input and execute it as a PowerShell command.
# Press Ctrl-C to exit.
& { while ($true) { Read-Host } } | powershell -noprofile -c -

Note:

  • -Command - has problematic aspects, notably with commands that span multiple lines (an additional Enter keystroke / newline is then needed for the command to be recognized) and so does -File -, whose behavior is even stranger - see this answer and GitHub issue #3223.

Another demonstration, simulating outside stdin input via 2 lines piped to powershell -c -:

'get-date', 'get-item /' | powershell -noprofile -c -

The two commands are executed and their output is printed; powershell.exe then exits, because no more stdin input is available; however, with indefinite stdin input (analogous to cat - on Unix-like platforms) the PowerShell process would be kept alive indefintely too.

mklement0
  • 382,024
  • 64
  • 607
  • 775
  • Ah this does work but if I run `cat program.ps1 | iex` it requests from keyboard not from the rest of stdin – Jesse Taube Aug 17 '21 at 17:50
  • @JesseTaube, yes, `Read-Host` doesn't read from stdin (unless the script is called via PowerShell's CLI). If you want to provide stdin input from the outside, omit the `Read-Host` loop, which was only meant to _simulate_ indefinite stdin input. Please see my update. If that doesn't help, you need to clarify your use case. – mklement0 Aug 17 '21 at 18:33