Runcommands

Latest version: v1.0a72

Safety actively analyzes 715032 Python packages for vulnerabilities to keep your Python projects secure.

Scan your dependencies

Page 9 of 13

1.0a26

- Fixed a bug in `util.confirm()` relating to its abort-on-unconfirmed logic.
The abort logic was being triggered in practically all cases when something
wasn't confirmed (notably, in the default case where
`abort_on_unconfirmed=False`).

1.0a25

- Changed mapping operations on `Config` so that `__contains__()` no longer
looks in the `run` config and `__iter__()` no longer yields `run` config
keys. I'm not sure why I thought would be useful in the first place, but it
was tricky to get right and confusing (and causing duplicates in the output
of the `show-config` command).
- Added `--python` option to `install` command so the Python version for the
virtualenv can be specified.
- All extras are no installed when the `install` command is run. This is so
testing dependencies will be installed.
- Fixed a bootstrapping issue in `commands.py`: import `coverage.Coverage` in
the `test` command instead of globally because coverage might not be
installed yet.

1.0a24

- Fixed/simplified iteration in `Config`. The previous implementation worked on
Python 3.5 and 3.6 but not 3.3 and 3.4, causing infinite recursion on those
versions. The new implementation is simpler because it only defines
`__iter__()` instead of both `__iter__()` and `keys()`.

1.0a23

Major Changes

- Replacement commands are now called automatically when commands are called
directly. A "replacement command" is a command with the same name as an
already-defined command. When the original command is called, it will check
to see if it has been replaced and call the replacement command if it has
been. The original command implementation can always be called via
`Command.implementation()`. This is intended to mirror CLI behavior (where
only replacement commands are available) and to make it easy to swap command
implementations in wrapper commands. [NOTE: This probably needs a bit more
thought put into it and perhaps a less-magical API].
- Command default options can now be specified via a shorter config path:
`defaults.{command-name}.xyz`. The old method of using the full module path
is still supported, which may be useful when commands are replaced and the
original defaults shouldn't be applied to the replacement command. Defaults
specified via the short path are merged over defaults specified using the
module path.
- Added `Command.get_default()` to make getting at individual default options
easy.

Other Changes

- Added `use_pty` flag to `remote` command. It's passed through to the remote
runner strategy (strategies already had a `use_pty` flag).
- Added `RawConfig.update()` so that `RawConfig.__getitem__()` will be used
when updating (like `get()` and `pop()`).
- A `RawConfig` object is now always returned from `Command.get_defaults()`
instead of returning a plain `dict` when there are no defaults. This is for
consistency; not sure it has any practical/noticeable effect.
- Added `commands` to default `RunConfig` options. `commands` is populated in
`Runner` with the commands it loads and in `Command.console_script()` with
the command being wrapped.

Fixed

- When loading JSON values tolerantly (i.e., treating bad values as strings),
values are now explicitly cast to `str` to avoid returning non-string values
(in `JSONValue.loads()`).

1.0a22

- When running a subprocess via the `local` command, on `Ctrl-C` `SIGINT` is
now sent to the subprocess for handling and the `local` command is aborted
only after/if the subprocess exits. The idea is to allow interactive commands
like `less` to exit cleanly and to obviate the need for the `stty sane` hack
added in the 1.0a20 release.
- When a `local` subprocess times out, `Popen.terminate()` is now used to shut
down the subprocess instead of `.kill()`. `.terminate()` gives subprocesses
a chance to exit cleanly.
- `remote` commands are now allocated a pseudo-terminal (using `ssh -t`) when
run interactively (when `stdout` is detected to be a TTY). This is to allow
interaction with remote commands that prompt for input. TODO: Investigate
downsides.

1.0a21

- Made `Config.__contains__()` look in `run` config like `.__getitem__()` does.
- Made `Config.keys()` and `.__iter__()` yield `run` config keys.
- Made `Config.values()` yield `run` config values.
- Made `Config.items()` yield `run` config items.
- Changed all `str.format(**x)` to `str.format_map(x)` for consistency.

Page 9 of 13

© 2025 Safety CLI Cybersecurity Inc. All Rights Reserved.