{"record":{"id":"b46fdcea483b5801","repo":"laurent22/joplin","slug":"reading-commands-from-standard-input-is-only-avail","errorCode":null,"errorMessage":"Reading commands from standard input is only available in CLI mode.","messagePattern":"Reading commands from standard input is only available in CLI mode\\.","errorType":"exception","errorClass":"Error","httpStatus":null,"severity":"error","filePath":"packages/app-cli/app/command-batch.ts","lineNumber":45,"sourceCode":"\n\tpublic description() {\n\t\treturn _('Runs the commands contained in the text file. There should be one command per line.');\n\t}\n\n\tprivate streamCommands_ = async function*(filePath: string) {\n\t\tconst processLines = function*(lines: string) {\n\t\t\tconst commandLines = splitCommandBatch(lines);\n\n\t\t\tfor (const command of commandLines) {\n\t\t\t\tif (!command.trim()) continue;\n\t\t\t\tyield splitCommandString(command.trim());\n\t\t\t}\n\t\t};\n\n\t\tif (filePath === '-') { // stdin\n\t\t\t// Iterating over standard input conflicts with the CLI app's GUI.\n\t\t\tif (app().hasGui()) {\n\t\t\t\tthrow new Error(_('Reading commands from standard input is only available in CLI mode.'));\n\t\t\t}\n\n\t\t\tfor await (const lines of iterateStdin('command> ')) {\n\t\t\t\tyield* processLines(lines);\n\t\t\t}\n\t\t} else {\n\t\t\tconst data = await readFile(filePath, 'utf-8');\n\t\t\tyield* processLines(data);\n\t\t}\n\t};\n\n\tpublic async action(options: Options) {\n\t\tlet lastError;\n\t\tfor await (const command of this.streamCommands_(options['file-path'])) {\n\t\t\ttry {\n\t\t\t\tawait app().refreshCurrentFolder();\n\t\t\t\tawait app().execCommand(command);\n\t\t\t} catch (error) {","sourceCodeStart":27,"sourceCodeEnd":63,"githubUrl":"https://github.com/laurent22/joplin/blob/2654b33620775080d1d59c552259d41e33dad3d2/packages/app-cli/app/command-batch.ts#L27-L63","documentation":"The 'batch' command reads a command script from a file or, when the path is '-', from standard input. Because the interactive terminal GUI also reads from stdin, reading commands from stdin conflicts with the GUI; if app().hasGui() is true the command throws 'Reading commands from standard input is only available in CLI mode.'. The message is i18n-translated.","triggerScenarios":"Running 'batch -' (or piping commands into stdin) while inside the interactive terminal GUI, where stdin is already owned by the GUI input loop.","commonSituations":"Piping a command list ('echo ... | joplin batch -') in a mode where the terminal GUI is active; running batch from a keybinding inside the GUI.","solutions":["Write the commands to a file and run 'batch <file>' instead of stdin.","Run in pure CLI mode (no terminal GUI) when piping via stdin.","Use the data API or a single 'exec' call instead of batch stdin in GUI mode."],"exampleFix":"# before\n#   echo 'ls' | joplin batch -    # inside terminal GUI -> throws\n# after\n#   printf 'ls\\n' > /tmp/cmds.txt && joplin batch /tmp/cmds.txt","handlingStrategy":"validation","validationCode":"if (filePath === '-' && app().hasGui()) {\n  throw new Error('Stdin batch input requires CLI mode; write to a file instead.');\n}","typeGuard":null,"tryCatchPattern":null,"preventionTips":["Prefer a script file over stdin for batch in any environment that may have a GUI.","Detect hasGui() before piping commands via stdin.","Use the data API for programmatic multi-command runs in GUI mode."],"tags":["cli","batch-command","stdin","gui-mode","i18n"],"backgroundTag":null,"analyzedSha":"2654b33620775080d1d59c552259d41e33dad3d2","analyzedAt":"2026-08-12T14:26:46.263Z","schemaVersion":2},"datasetVersion":"2026-08-12T18:17:37.767Z"}