How to Test CLI Output in Jest & Vitest
Created: Dec 25, 2023 – Last Updated: Dec 25, 2023
Tags: CLIDigital Garden
- Questionnaire through
secco init(using enquirer (opens in a new tab))
- A “fire once and forget” mode like most CLIs
I didn’t want to test the first case as my prompts are simple and most of secco’s logic lies in the second mode. If you want to test enquirer, I can recommend reading Gleb Bahmutov’s article Unit testing CLI programs (opens in a new tab) as a starting point.
At the end of this post you should be able to write such tests:
This guide uses Vitest but you should be able to transfer it to Jest (opens in a new tab), too, as the APIs are very similar.
#Create a logs matcher
matcher.ts file in order to easily check if a word or a sequence of words is found inside the CLI output (logs).
#Create a CLI helper
invoke-cli.ts file to author a new
YourCLI helper following the builder pattern. With it you’ll run your CLI inside a specified directory and with your defined commands.
First, install the necessary dependencies:
invoke-cli.ts and add the following contents:
YourCLI builder uses execa’s (opens in a new tab) synchronous method to invoke your CLI and its arguments. Through
setCwd you’ll need to define the location where the CLI should be run. The result is a tuple of the
exitCode and the cleaned up logs.
Important: You need to define the path to your built CLI through
builtCliLocation. Alternatively you could also try using something like
ts-node to point to your source file before invoking the CLI.
You could also rewrite this helper to use execa’s Promise interface if you need to use async/await.
Inside your test you can now use it like so: