Common Coding Patterns

The sections in this topic describe common coding patterns that you likely use in your plugin, along with a code sample. Where possible, we also provide a link to one of our plugins as an additional example.

To throw an error from your command, first add the error message to your messages Markdown file. Use a H1 header as a key name for the error name. We suggest you follow the Salesforce CLI style convention of prefacing error names with error and warnings with warning. For example:

Load the message into your command with the Messages.loadMessages method and throw it using message.createError. This code example builds on the sample hello world command.

When a user runs the command and runs into the error, it's automatically prefaced with Error:, such as:

Error: Invalid Username: doesnt@work.org

The Messages class also contains the createWarning and createInfo methods for warnings and informational output.

When a CLI command encounters an error, it usually returns an exit code of 1. If you don't include any error handling code in your command, oclif handles the error and its default exit code is 1. Similarly, a successful command execution returns a 0 exit code by default.

You can use a different exit code if you want. You must, however, use only those codes that Salesforce CLI isn't currently using, or are reserved for its future use. This table shows these error codes.

Error CodeDescription
0The command executed successfully.
1The command didn't execute successfully.
2oclif detected errors, typically issues with flags.
3 - 9Reserved for future use by Salesforce CLI.
10TypeErrors, which are typically problems in client code.
11 - 19Reserved for future use by Salesforce CLI.
20GACKs, which are problems in Salesforce server code.
21 - 29Reserved for future use by Salesforce CLI.
68Partial success, such as deploying only some requested metadata.
69Request still in progress, or the request timed out.
130The command received a termination signal, such as the user pressing Ctrl+C.

SfCommand contains a prompt method that encapsulates the inquirer library. See the inquirer's documentation for different types of questions you can construct.

This code example show how to change the run() method in the sample hello world command to ask the user a question and change the output based on the answer.

SfCommand exposes a spinner class that you can use to put spinners on the terminal if your command takes a while to complete. These spinners are automatically suppressed if the --json flag is present.

This code example shows how to change the run() method in the sample hello world command to sleep for a short time, and then show the word Loading... and a spinner while it sleeps.

SfCommand exposes a progress class that you can use to put progress bars on the terminal. These progress bars are automatically suppressed if the --json flag is present.

This code example show how to change the run() method in the sample hello world command to sleep for a short time, but show the words Hello World Progress and a progress bar while it sleeps.

You can easily create and use configuration files using the ConfigFile class from @salesforce/core. The configuration file is located in the global .sfdx directory if isGlobal equals true. Otherwise it's located in your local project directory.

This code sample shows how to create a global configuration file called myConfigFilename.json, located in the global .sfdx directory. The example then shows how to set a key called myKey to the value myvalue.

sf uses configuration variables to set CLI defaults, such as your default org (target-org) or the API version you want the CLI to use (org-api-version). You set and get configuration variables with the sf config set|get commands. You can define your own custom configuration variable that is also managed by the sf config commands.

This example adds a Boolean configuration variable called do-awesome-things. First create a file in your plugin called configMeta.ts with code similar to this:

Then update the package.json file in the top-level directory of your plugin and add a configMeta property to the oclif section, like this:

You can then set the new configuration variable like this: