From 3c428271e00198f13791a30e154f2eccf8d33ce4 Mon Sep 17 00:00:00 2001 From: Gustavo Henke Date: Tue, 3 Sep 2024 13:01:10 +1000 Subject: [PATCH] Proper documentation Also removes the --help section from readme. It's too much. --- README.md | 241 +----------------------------- docs/README.md | 13 ++ docs/cli/configuration.md | 11 ++ docs/cli/input-handling.md | 40 +++++ docs/cli/output-control.md | 35 +++++ docs/cli/passthrough-arguments.md | 80 ++++++++++ docs/cli/prefixing.md | 147 ++++++++++++++++++ docs/cli/restarting.md | 38 +++++ docs/cli/shortcuts.md | 70 +++++++++ docs/frontend-demo.gif | Bin 108747 -> 0 bytes docs/kill-demo.gif | Bin 74586 -> 0 bytes docs/raw-demo.gif | Bin 64895 -> 0 bytes 12 files changed, 438 insertions(+), 237 deletions(-) create mode 100644 docs/README.md create mode 100644 docs/cli/configuration.md create mode 100644 docs/cli/input-handling.md create mode 100644 docs/cli/output-control.md create mode 100644 docs/cli/passthrough-arguments.md create mode 100644 docs/cli/prefixing.md create mode 100644 docs/cli/restarting.md create mode 100644 docs/cli/shortcuts.md delete mode 100644 docs/frontend-demo.gif delete mode 100644 docs/kill-demo.gif delete mode 100644 docs/raw-demo.gif diff --git a/README.md b/README.md index 86e20270..46481a76 100644 --- a/README.md +++ b/README.md @@ -54,7 +54,7 @@ tired of opening terminals and made **concurrently**. ## Usage > **Note** -> The `concurrently` command is now also available under the shorthand alias `conc`. +> The `concurrently` command is also available under the shorthand alias `conc`. The tool is written in Node.js, but you can use it to run **any** commands. @@ -73,243 +73,10 @@ In package.json, escape quotes: "start": "concurrently \"command1 arg\" \"command2 arg\"" ``` -NPM run commands can be shortened: +You can always check concurrently's flag list by running `concurrently --help`. +For the version, run `concurrently --version`. -```bash -concurrently "npm:watch-js" "npm:watch-css" "npm:watch-node" - -# Equivalent to: -concurrently -n watch-js,watch-css,watch-node "npm run watch-js" "npm run watch-css" "npm run watch-node" -``` - -NPM shortened commands also support wildcards. Given the following scripts in -package.json: - -```jsonc -{ - //... - "scripts": { - // ... - "watch-js": "...", - "watch-css": "...", - "watch-node": "..." - // ... - } - // ... -} -``` - -```bash -concurrently "npm:watch-*" - -# Equivalent to: -concurrently -n js,css,node "npm run watch-js" "npm run watch-css" "npm run watch-node" - -# Any name provided for the wildcard command will be used as a prefix to the wildcard -# part of the script name: -concurrently -n w: npm:watch-* - -# Equivalent to: -concurrently -n w:js,w:css,w:node "npm run watch-js" "npm run watch-css" "npm run watch-node" -``` - -Exclusion is also supported. Given the following scripts in package.json: - -```jsonc -{ - // ... - "scripts": { - "lint:js": "...", - "lint:ts": "...", - "lint:fix:js": "...", - "lint:fix:ts": "..." - // ... - } - // ... -} -``` - -```bash -# Running only lint:js and lint:ts -# with lint:fix:js and lint:fix:ts excluded -concurrently "npm:lint:*(!fix)" -``` - -Good frontend one-liner example [here](https://github.com/kimmobrunfeldt/dont-copy-paste-this-frontend-template/blob/5cd2bde719654941bdfc0a42c6f1b8e69ae79980/package.json#L9). - -Help: - -``` -concurrently [options] - -General - -m, --max-processes How many processes should run at once. - Exact number or a percent of CPUs available (for example "50%"). - New processes only spawn after all restart tries - of a process. [string] - -n, --names List of custom names to be used in prefix - template. - Example names: "main,browser,server" [string] - --name-separator The character to split on. Example usage: - -n "styles|scripts|server" --name-separator "|" - [default: ","] - -s, --success Which command(s) must exit with code 0 in order - for concurrently exit with code 0 too. Options - are: - - "first" for the first command to exit; - - "last" for the last command to exit; - - "all" for all commands; - - "command-{name}"/"command-{index}" for the - commands with that name or index; - - "!command-{name}"/"!command-{index}" for all - commands but the ones with that name or index. - [default: "all"] - -r, --raw Output only raw output of processes, disables - prettifying and concurrently coloring. [boolean] - --no-color Disables colors from logging [boolean] - --hide Comma-separated list of processes to hide the - output. - The processes can be identified by their name or - index. [string] [default: ""] - -g, --group Order the output as if the commands were run - sequentially. [boolean] - --timings Show timing information for all processes. - [boolean] [default: false] - -P, --passthrough-arguments Passthrough additional arguments to commands - (accessible via placeholders) instead of treating - them as commands. [boolean] [default: false] - -Prefix styling - -p, --prefix Prefix used in logging for each process. - Possible values: index, pid, time, command, name, - none, or a template. Example template: "{time}-{pid}" - [string] [default: index or name (when --names is set)] - -c, --prefix-colors Comma-separated list of chalk colors to use on - prefixes. If there are more commands than colors, the - last color will be repeated. - - Available modifiers: reset, bold, dim, italic, - underline, inverse, hidden, strikethrough - - Available colors: black, red, green, yellow, blue, - magenta, cyan, white, gray, - any hex values for colors (e.g. #23de43) or auto for - an automatically picked color - - Available background colors: bgBlack, bgRed, - bgGreen, bgYellow, bgBlue, bgMagenta, bgCyan, bgWhite - See https://www.npmjs.com/package/chalk for more - information. [string] [default: "reset"] - -l, --prefix-length Limit how many characters of the command is displayed - in prefix. The option can be used to shorten the - prefix when it is set to "command" - [number] [default: 10] - -t, --timestamp-format Specify the timestamp in moment/date-fns format. - [string] [default: "yyyy-MM-dd HH:mm:ss.SSS"] - -Input handling - -i, --handle-input Whether input should be forwarded to the child - processes. See examples for more information. - [boolean] - --default-input-target Identifier for child process to which input on - stdin should be sent if not specified at start of - input. - Can be either the index or the name of the - process. [default: 0] - -Killing other processes - -k, --kill-others Kill other processes if one exits or dies.[boolean] - --kill-others-on-fail Kill other processes if one exits with non zero - status code. [boolean] - --kill-signal Signal to send to other processes if one exits or dies. - (SIGTERM/SIGKILL, defaults to SIGTERM) [string] - -Restarting - --restart-tries How many times a process that died should restart. - Negative numbers will make the process restart forever. - [number] [default: 0] - --restart-after Delay time to respawn the process, in milliseconds. - [number] [default: 0] - -Options: - -h, --help Show help [boolean] - -v, -V, --version Show version number [boolean] - - -Examples: - - - Output nothing more than stdout+stderr of child processes - - $ concurrently --raw "npm run watch-less" "npm run watch-js" - - - Normal output but without colors e.g. when logging to file - - $ concurrently --no-color "grunt watch" "http-server" > log - - - Custom prefix - - $ concurrently --prefix "{time}-{pid}" "npm run watch" "http-server" - - - Custom names and colored prefixes - - $ concurrently --names "HTTP,WATCH" -c "bgBlue.bold,bgMagenta.bold" - "http-server" "npm run watch" - - - Auto varying colored prefixes - - $ concurrently -c "auto" "npm run watch" "http-server" - - - Mixing auto and manual colored prefixes - - $ concurrently -c "red,auto" "npm run watch" "http-server" "echo hello" - - - Configuring via environment variables with CONCURRENTLY_ prefix - - $ CONCURRENTLY_RAW=true CONCURRENTLY_KILL_OTHERS=true concurrently "echo - hello" "echo world" - - - Send input to default - - $ concurrently --handle-input "nodemon" "npm run watch-js" - rs # Sends rs command to nodemon process - - - Send input to specific child identified by index - - $ concurrently --handle-input "npm run watch-js" nodemon - 1:rs - - - Send input to specific child identified by name - - $ concurrently --handle-input -n js,srv "npm run watch-js" nodemon - srv:rs - - - Shortened NPM run commands - - $ concurrently npm:watch-node npm:watch-js npm:watch-css - - - Shortened NPM run command with wildcard (make sure to wrap it in quotes!) - - $ concurrently "npm:watch-*" - - - Exclude patterns so that between "lint:js" and "lint:fix:js", only "lint:js" - is ran - - $ concurrently "npm:*(!fix)" - - - Passthrough some additional arguments via '{}' placeholder - - $ concurrently -P "echo {1}" -- foo - # Results in: echo foo - - - Passthrough all additional arguments via '{@}' placeholder - - $ concurrently -P "npm:dev-* -- {@}" -- --watch --noEmit - # Results in something like: npm run dev-example -- --watch --noEmit - - - Passthrough all additional arguments combined into one argument via '{*}' placeholder - - $ concurrently -P "echo {*}" -- foo bar - # Results in: echo 'foo bar' - -For more details, visit https://github.com/open-cli-tools/concurrently -``` +Check out documentation and other usage examples in the [`docs` directory](./docs/README.md). ## API diff --git a/docs/README.md b/docs/README.md new file mode 100644 index 00000000..99fdcae0 --- /dev/null +++ b/docs/README.md @@ -0,0 +1,13 @@ +# Concurrently Documentation + +## CLI + +These articles cover using concurrently through CLI: + +- [Prefixing](./cli/prefixing.md) +- [Output Control](./cli/output-control.md) +- [Shortcuts](./cli/shortcuts.md) +- [Restarting Commands](./cli/restarting.md) +- [Input Handling](./cli/input-handling.md) +- [Passthrough Arguments](./cli/passthrough-arguments.md) +- [Configuration](./cli/configuration.md) diff --git a/docs/cli/configuration.md b/docs/cli/configuration.md new file mode 100644 index 00000000..53939dc6 --- /dev/null +++ b/docs/cli/configuration.md @@ -0,0 +1,11 @@ +# Configuration + +You might want to configure concurrently to always have certain flags on. +Any of concurrently's flags can be set via environment variables that are prefixed with `CONCURRENTLY_`. + +```bash +$ export CONCURRENTLY_KILL_OTHERS=true +$ export CONCURRENTLY_HANDLE_INPUT=true +# Equivalent to passing --kill-others and --handle-input +$ concurrently nodemon "echo 'hey nodemon, you won't last long'" +``` diff --git a/docs/cli/input-handling.md b/docs/cli/input-handling.md new file mode 100644 index 00000000..1bb132e6 --- /dev/null +++ b/docs/cli/input-handling.md @@ -0,0 +1,40 @@ +# Input Handling + +By default, concurrently doesn't send input to any commands it spawns.
+In the below example, typing `rs` to manually restart [nodemon](https://nodemon.io/) does nothing: + +```bash +$ concurrently "nodemon" "npm run watch-js" +rs +``` + +To turn on input handling, it's necessary to set the `--handle-input`/`-i` flag.
+This will send `rs` to the first command: + +```bash +$ concurrently --handle-input "nodemon" "npm run watch-js" +rs +``` + +To send input to a different command instead, it's possible to prefix the input with the command index, followed by a `:`.
+For example, the below sends `rs` to the second command: + +```bash +$ concurrently --handle-input "npm run watch-js" "nodemon" +1:rs +``` + +If the command has a name, it's also possible to target it using that command's name: + +```bash +$ concurrently --handle-input --names js,server "npm run watch-js" "nodemon" +server:rs +``` + +It's also possible to change the default command that receives input.
+To do this, set the `--default-input-target` flag to a command's index or name. + +```bash +$ concurrently --handle-input --default-input-target 1 "npm run watch-js" "nodemon" +rs +``` diff --git a/docs/cli/output-control.md b/docs/cli/output-control.md new file mode 100644 index 00000000..8df7b098 --- /dev/null +++ b/docs/cli/output-control.md @@ -0,0 +1,35 @@ +# Output Control + +concurrently offers a few ways to control a command's output. + +## Hiding + +A command's outputs (and all its events) can be hidden by using the `--hide` flag. + +```bash +$ concurrently --hide 0 "echo Hello there" "echo 'General Kenobi!'" +[1] General Kenobi! +[1] echo 'General Kenobi!' exited with code 0 +``` + +## Grouping + +It might be useful at times to make sure that the commands outputs are grouped together, while running them in parallel.
+This can be done with the `--group` flag. + +```bash +$ concurrently --group "echo Hello there && sleep 2 && echo 'General Kenobi!'" "echo hi Star Wars fans" +[0] Hello there +[0] General Kenobi! +[0] echo Hello there && sleep 2 && echo 'General Kenobi!' exited with code 0 +[1] hi Star Wars fans +[1] echo hi Star Wars fans exited with code 0 +``` + +## No Colors + +When piping concurrently's outputs to another command or file, you might want to force it to not use colors, as these can break the other command's parsing, or reduce the legibility of the output in non-terminal environments. + +```bash +$ concurrently -c red,blue --no-color "echo Hello there" "echo 'General Kenobi!'" +``` diff --git a/docs/cli/passthrough-arguments.md b/docs/cli/passthrough-arguments.md new file mode 100644 index 00000000..95fc077e --- /dev/null +++ b/docs/cli/passthrough-arguments.md @@ -0,0 +1,80 @@ +# Passthrough Arguments + +If you have a shortcut for running a specific combination of commands through concurrently, +you might need at some point to pass additional arguments/flags to some of these. + +For example, imagine you have in your `package.json` file scripts like this: + +```jsonc +{ + // ... + "scripts": { + "build:client": "tsc -p client", + "build:server": "tsc -p server", + "build": "concurrently npm:build:client npm:build:server" + } +} +``` + +If you wanted to run only either `build:server` or `build:client` with an additional `--noEmit` flag, +you can do so with `npm run build:server -- --watch`, for example.
+However, if you want to do that while using concurrently, as `npm run dev -- --noEmit` for example, +you might find that concurrently actually parses `--watch` as its own flag, which does nothing, +because it doesn't exist. + +To solve this, you can set the `--passthrough-arguments`/`-P` flag, which instructs concurrently to +take everything after a `--` as additional arguments that are passed through to the input commands +via a few placeholder styles: + +## Single argument + +We can modify the original `build` script to pass a single additional argument/flag to a script by using +a 1-indexed `{number}` placeholder to the command you want it to apply to: + +```jsonc +{ + // ... + "scripts": { + // ... + "build": "concurrently -P 'npm:build:client -- {1}' npm:build:server --", + "typecheck": "npm run build -- --noEmit" + } +} +``` + +With this, running `npm run typecheck` will pass `--noEmit` only to `npm run build:client`. + +## All arguments + +In the original `build` example script, you're more likely to want to pass every additional argument/flag +to your commands. This can be done with the `{@}` placeholder. + +```jsonc +{ + // ... + "scripts": { + // ... + "build": "concurrently -P 'npm:build:client -- {@}' 'npm:build:server -- {@}' --", + "typecheck": "npm run build -- --watch --noEmit" + } +} +``` + +In the above example, both `--watch` and `--noEmit` are passed to each command. + +## All arguments, combined + +If for some reason you wish to combine all additional arguments into a single one, you can do that with the `{*}` placeholder, +which wraps the arguments in quotes. + +```jsonc +{ + // ... + "scripts": { + // ... + "build": "concurrently -P 'npm:build:client -- --outDir {*}/client' 'npm:build:server -- --outDir {*}/server' -- $(date)" + } +} +``` + +In the above example, the output of the `date` command, which looks like `Sun 1 Sep 2024 23:50:00 AEST` will be passed as a single string to the `--outDir` parameter of both commands. diff --git a/docs/cli/prefixing.md b/docs/cli/prefixing.md new file mode 100644 index 00000000..6431649c --- /dev/null +++ b/docs/cli/prefixing.md @@ -0,0 +1,147 @@ +# Prefixing + +## Prefix Styles + +concurrently will by default prefix each command's outputs with a zero-based index, wrapped in square brackets: + +```bash +$ concurrently "echo Hello there" "echo 'General Kenobi!'" +[0] Hello there +[1] General Kenobi! +[0] echo Hello there exited with code 0 +[1] echo 'General Kenobi!' exited with code 0 +``` + +If you've given the commands names, they are used instead: + +```bash +$ concurrently --names one,two "echo Hello there" "echo 'General Kenobi!'" +[one] Hello there +[two] General Kenobi! +[one] echo Hello there exited with code 0 +[two] echo 'General Kenobi!' exited with code 0 +``` + +There are other prefix styles available too: + +| Style | Description | +| --------- | --------------------------------- | +| `index` | Zero-based command's index | +| `name` | The command's name | +| `command` | The command's line | +| `time` | Time of output | +| `pid` | ID of the command's process (PID) | +| `none` | No prefix | + +Any of these can be used by setting the `--prefix`/`-p` flag. For example: + +```bash +$ concurrently --prefix pid "echo Hello there" "echo 'General Kenobi!'" +[2222] Hello there +[2223] General Kenobi! +[2222] echo Hello there exited with code 0 +[2223] echo 'General Kenobi!' exited with code 0 +``` + +It's also possible to have a prefix based on a template. Any of the styles listed above can be used by wrapping it in `{}`. +Doing so will also remove the square brackets: + +```bash +$ concurrently --prefix "{index}-{pid}" "echo Hello there" "echo 'General Kenobi!'" +0-2222 Hello there +1-2223 General Kenobi! +0-2222 echo Hello there exited with code 0 +1-2223 echo 'General Kenobi!' exited with code 0 +``` + +## Prefix Colors + +By default, there are no colors applied to concurrently prefixes, and they just use whatever the terminal's defaults are. + +This can be changed by using the `--prefix-colors`/`-c` flag, which takes a comma-separated list of colors to use.
+The available values are color names (e.g. `green`, `magenta`, `gray`, etc), a hex value (such as `#23de43`), or `auto`, to automatically select a color. + +```bash +$ concurrently -c red,blue "echo Hello there" "echo 'General Kenobi!'" +``` + +
+List of available color names + +- `black` +- `blue` +- `cyan` +- `green` +- `gray` +- `magenta` +- `red` +- `white` +- `yellow` +
+ +Colors can take modifiers too. Several can be applied at once by prepending `..` and so on. + +```bash +$ concurrently -c red,bold.blue.dim "echo Hello there" "echo 'General Kenobi!'" +``` + +
+List of available modifiers + +- `reset` +- `bold` +- `dim` +- `hidden` +- `inverse` +- `italic` +- `strikethrough` +- `underline` +
+ +A background color can be set in a similary fashion. + +```bash +$ concurrently -c bgGray,red.bgBlack "echo Hello there" "echo 'General Kenobi!'" +``` + +
+List of available background color names + +- `bgBlack` +- `bgBlue` +- `bgCyan` +- `bgGreen` +- `bgGray` +- `bgMagenta` +- `bgRed` +- `bgWhite` +- `bgYellow` +
+ +## Prefix Length + +When using the `command` prefix style, it's possible that it'll be too long.
+It can be limited by setting the `--prefix-length`/`-l` flag: + +```bash +$ concurrently -p command -l 10 "echo Hello there" "echo 'General Kenobi!'" +[echo..here] Hello there +[echo..bi!'] General Kenobi! +[echo..here] echo Hello there exited with code 0 +[echo..bi!'] echo 'General Kenobi!' exited with code 0 +``` + +It's also possible that some prefixes are too short, and you want all of them to have the same length.
+This can be done by setting the `--pad-prefix` flag: + +```bash +$ concurrently -n foo,barbaz --pad-prefix "echo Hello there" "echo 'General Kenobi!'" +[foo ] Hello there +[foo ] echo Hello there exited with code 0 +[barbaz] General Kenobi! +[barbaz] echo 'General Kenobi!' exited with code 0 +``` + +> [!NOTE] +> If using the `pid` prefix style in combination with [`--restart-tries`](./restarting.md), the length of the PID might grow, in which case all subsequent lines will match the new length.
+> This might happen, for example, if the PID was 99 and it's now 100. diff --git a/docs/cli/restarting.md b/docs/cli/restarting.md new file mode 100644 index 00000000..f70a50b7 --- /dev/null +++ b/docs/cli/restarting.md @@ -0,0 +1,38 @@ +# Restarting Commands + +Sometimes it's useful to have commands that exited with a non-zero status to restart automatically.
+concurrently lets you configure how many times you wish for such a command to restart through the `--restart-tries` flag: + +```bash +$ concurrently --restart-tries 2 "exit 1" +[0] exit 1 exited with code 1 +[0] exit 1 restarted +[0] exit 1 exited with code 1 +[0] exit 1 restarted +[0] exit 1 exited with code 1 +``` + +Sometimes, it might be interesting to have commands wait before restarting.
+To do this, simply set `--restart-after` to a the number of milliseconds you'd like to delay restarting. + +```bash +$ concurrently -p time --restart-tries 1 --restart-after 3000 "exit 1" +[2024-09-01 23:43:55.871] exit 1 exited with code 1 +[2024-09-01 23:43:58.874] exit 1 restarted +[2024-09-01 23:43:58.891] exit 1 exited with code 1 +``` + +If a command is not having success spawning, you might want to instead apply an exponential back-off.
+Set `--restart-after exponential` to have commands respawn with a `2^N` seconds delay. + +```bash +$ concurrently -p time --restart-tries 3 --restart-after exponential "exit 1" + +[2024-09-01 23:49:01.124] exit 1 exited with code 1 +[2024-09-01 23:49:02.127] exit 1 restarted +[2024-09-01 23:49:02.139] exit 1 exited with code 1 +[2024-09-01 23:49:04.141] exit 1 restarted +[2024-09-01 23:49:04.157] exit 1 exited with code 1 +[2024-09-01 23:49:08.158] exit 1 restarted +[2024-09-01 23:49:08.174] exit 1 exited with code 1 +``` diff --git a/docs/cli/shortcuts.md b/docs/cli/shortcuts.md new file mode 100644 index 00000000..e95b9c00 --- /dev/null +++ b/docs/cli/shortcuts.md @@ -0,0 +1,70 @@ +# Command Shortcuts + +Package managers that execute scripts from a `package.json` file can be shortened when in concurrently.
+The following are supported: + +| Syntax | Expands to | +| --------------- | --------------------- | +| `npm: