From 1119f0d46b1bbfec787061a10f5a08f7ea6b867c Mon Sep 17 00:00:00 2001 From: Filip Tibell Date: Thu, 24 Apr 2025 22:14:03 +0200 Subject: [PATCH] Remove legacy stdin option in favor of full stdio options on process exec + adjust tests accordingly --- crates/lune-std-process/src/options/mod.rs | 16 +----- crates/lune-std-process/src/options/stdio.rs | 5 +- crates/lune-std-process/types.d.luau | 58 ++++++++++++++------ tests/process/exec/stdin.luau | 4 +- 4 files changed, 49 insertions(+), 34 deletions(-) diff --git a/crates/lune-std-process/src/options/mod.rs b/crates/lune-std-process/src/options/mod.rs index 87d72a6..f19cf26 100644 --- a/crates/lune-std-process/src/options/mod.rs +++ b/crates/lune-std-process/src/options/mod.rs @@ -118,21 +118,11 @@ impl FromLua for ProcessSpawnOptions { } /* - If we got options for stdio handling, parse those as well - note that - we accept a separate "stdin" value here for compatibility with older - scripts, but the user should preferrably pass it in the stdio table + If we got options for stdio handling, parse those as well + + This may optionally contain configuration for any or all of: stdin, stdout, stderr */ this.stdio = value.get("stdio")?; - match value.get("stdin")? { - LuaValue::Nil => {} - LuaValue::String(s) => this.stdio.stdin = Some(s.as_bytes().to_vec()), - value => { - return Err(LuaError::RuntimeError(format!( - "Invalid type for option 'stdin' - expected 'string', got '{}'", - value.type_name() - ))) - } - } Ok(this) } diff --git a/crates/lune-std-process/src/options/stdio.rs b/crates/lune-std-process/src/options/stdio.rs index 58c2c87..f5d43de 100644 --- a/crates/lune-std-process/src/options/stdio.rs +++ b/crates/lune-std-process/src/options/stdio.rs @@ -1,3 +1,4 @@ +use bstr::BString; use mlua::prelude::*; use super::kind::ProcessSpawnOptionsStdioKind; @@ -29,8 +30,8 @@ impl FromLua for ProcessSpawnOptionsStdio { LuaValue::Table(t) => { let mut this = Self::default(); - if let Some(stdin) = t.get("stdin")? { - this.stdin = stdin; + if let Some(stdin) = t.get::>("stdin")? { + this.stdin = Some(stdin.to_vec()); } if let Some(stdout) = t.get("stdout")? { diff --git a/crates/lune-std-process/types.d.luau b/crates/lune-std-process/types.d.luau index c76c9c7..ea24f99 100644 --- a/crates/lune-std-process/types.d.luau +++ b/crates/lune-std-process/types.d.luau @@ -2,27 +2,35 @@ export type OS = "linux" | "macos" | "windows" export type Arch = "x86_64" | "aarch64" export type Endianness = "big" | "little" -export type StdioKind = "default" | "inherit" | "forward" | "none" -export type StdioOptions = { - stdin: StdioKind?, - stdout: StdioKind?, - stderr: StdioKind?, -} - --[=[ - @interface CreateOptions + @interface ExecStdioKind @within Process - A dictionary of options for `process.create`, with the following available values: + Enum determining how to treat a standard input/output stream for `process.exec`. - * `cwd` - The current working directory for the process - * `env` - Extra environment variables to give to the process - * `shell` - Whether to run in a shell or not - set to `true` to run using the default shell, or a string to run using a specific shell + Can be one of the following values: + + * `default` - The default behavior, writing to the final result table only + * `inherit` - Inherit the stream from the parent process, writing to both the result table and the respective stream for the parent process + * `forward` - Forward the stream to the parent process, without writing to the result table, only respective stream for the parent process + * `none` - Do not create any input/output stream ]=] -export type CreateOptions = { - cwd: string?, - env: { [string]: string }?, - shell: (boolean | string)?, +export type ExecStdioKind = "default" | "inherit" | "forward" | "none" + +--[=[ + @interface ExecStdioOptions + @within Process + + A dictionary of stdio-specific options for `process.exec`, with the following available values: + + * `stdin` - A buffer or string to write to the stdin of the process + * `stdout` - How to treat the stdout stream from the child process - see `ExecStdioKind` for more info + * `stderr` - How to treat the stderr stream from the child process - see `ExecStdioKind` for more info +]=] +export type ExecStdioOptions = { + stdin: (buffer | string)?, + stdout: ExecStdioKind?, + stderr: ExecStdioKind?, } --[=[ @@ -40,7 +48,23 @@ export type ExecOptions = { cwd: string?, env: { [string]: string }?, shell: (boolean | string)?, - stdio: (StdioKind | StdioOptions)?, + stdio: (ExecStdioKind | ExecStdioOptions)?, +} + +--[=[ + @interface CreateOptions + @within Process + + A dictionary of options for `process.create`, with the following available values: + + * `cwd` - The current working directory for the process + * `env` - Extra environment variables to give to the process + * `shell` - Whether to run in a shell or not - set to `true` to run using the default shell, or a string to run using a specific shell +]=] +export type CreateOptions = { + cwd: string?, + env: { [string]: string }?, + shell: (boolean | string)?, } --[=[ diff --git a/tests/process/exec/stdin.luau b/tests/process/exec/stdin.luau index f85cd0b..24d11f7 100644 --- a/tests/process/exec/stdin.luau +++ b/tests/process/exec/stdin.luau @@ -10,8 +10,8 @@ local echoMessage = "Hello from child process!" -- When passing stdin to powershell on windows we must "accept" using the double newline local result = if IS_WINDOWS - then process.exec("powershell", { "echo" }, { stdin = echoMessage .. "\n\n" }) - else process.exec("xargs", { "echo" }, { stdin = echoMessage }) + then process.exec("powershell", { "echo" }, { stdio = { stdin = echoMessage .. "\n\n" } }) + else process.exec("xargs", { "echo" }, { stdio = { stdin = echoMessage } }) local resultStdout = if IS_WINDOWS then string.sub(result.stdout, #result.stdout - #echoMessage - 1)