# Env, PATH, and requires
Script-style commands use extra fields so runners can call sibling scripts, require host tools, and control the child environment.
## `requires`
External binaries that must exist on PATH before the leaf runs:
```yaml
issue:
requires: [gh, jq, fzf]
```
Checked against jan's inherited PATH (the same PATH used to resolve `argv[0]`).
## `path` and `dependencies`
`path` is a directory prepended to `PATH` when this script (or a descendant leaf) runs. `dependencies` names **other jan scripts** whose `path` directories are prepended first (cycle-checked).
Relative `path` values are resolved against, in order: `--cwd`, the spec directory, its parent, then `JAN_SCRIPTS_ROOT`.
Directories from `path` / `dependencies` are used only for programs the host does not already provide. They cannot shadow a system `bash` / `python3` that jan already found.
## `env`
Two YAML shapes:
```yaml
# shorthand (public only; restricts child env)
env:
ISSUE_EDITOR: vim
# explicit sections
env:
public:
ISSUE_EDITOR: vim
private:
- GH_TOKEN
pass:
GH_TOKEN: github/pat
```
| `public` | Key/value pairs stored in YAML and assigned on the child |
| `private` | Names only; must already be set in the host environment; copied into the child; never read from the spec |
| `pass` | Env var name → `pass` store id. jan runs `pass <id>` and sets the **first line** of stdout |
A name cannot be both `private` and `pass`.
When any public, private, or pass entry is present, the child does **not** inherit the full parent environment. It receives:
- A small essential allowlist: `PATH`, `HOME`, `USER`, `LOGNAME`, `SHELL`, `LANG`, `LC_*`, `TERM`, `TERMINFO`, `COLORTERM`, `NO_COLOR`, `TMPDIR`/`TMP`/`TEMP`, `XDG_*`
- Private copies and `pass` values
- Public assignments
With an empty `env`, the child inherits the parent environment unchanged (aside from optional PATH prepends and package-manager injections).
`pass` requires the `pass` CLI on PATH. Missing private variables fail before spawn.
## Run-time order
1. Merge chain fields (deeper wins for public env / inputs / packages).
2. Resolve typed `--input` flags and interpolate `${{ inputs.* }}` in `env.public` and `exec.argv`.
3. Resolve transitive `dependencies` to other scripts' `path` directories.
4. Prepend those directories, then the script's own `path`, to `PATH`.
5. Ensure `packages.*` environments (see [Packages](packages.md)).
6. Fail if any `requires` binary is missing, or any `env.private` variable is unset.
7. Resolve `argv[0]` on jan's inherited PATH, then spawn.