Dmenu/Rofi frontend for managing Bitwarden vault using the Bitwarden CLI tool.
  • Python 97.2%
  • Roff 1.6%
  • Makefile 0.7%
  • Nix 0.5%
Find a file
Scott Hansen 984b251f8f
Update TOTP handling. Closes #24
gen_otp() required secret, period and digits to all be present in an
otpauth:// URL and returned an empty string otherwise. Bitwarden keeps the
TOTP field as it was entered, so three perfectly normal values produced no
code at all and no error: a bare base32 key (what pasting a key stores), an
otpauth:// URL from a QR code that omits the optional parameters, and a
steam:// URL. {TOTP} typed nothing and "TOTP: ******" in the view menu
yielded an empty selection.

Split the parsing into otp_params() and make everything but the secret
optional, falling back to the RFC 6238 defaults. Handle the two
non-otpauth forms, strip the spacing Bitwarden preserves in a key, and
return an empty string rather than propagating binascii.Error or a
ValueError from an algorithm hashlib doesn't know. The debug log line
carries only the exception, never the field value.

edit_totp() prefilled the secret with query_string["secret"][0], which
raised KeyError on any entry whose TOTP was a bare secret. Route it through
otp_params() so an unreadable value just prefills nothing.

Co-Authored-By: Claude Opus 5 <noreply@anthropic.com>
2026-08-24 14:14:34 -07:00
.claude Add the claude agent files 2026-08-16 11:02:35 -07:00
.github/workflows Update github actions versions 2026-08-16 11:03:08 -07:00
bwm Update TOTP handling. Closes #24 2026-08-24 14:14:34 -07:00
docs Update TOTP handling. Closes #24 2026-08-24 14:14:34 -07:00
tests Update TOTP handling. Closes #24 2026-08-24 14:14:34 -07:00
.gitignore Add claude.md file 2026-08-22 17:24:57 -07:00
bwm.1 Bump version to 0.6.0 2026-08-16 11:08:31 -07:00
bwm.1.md Bump version to 0.6.0 2026-08-16 11:08:31 -07:00
CLAUDE.md Add the claude agent files 2026-08-16 11:02:35 -07:00
config.ini.example Add wtype support 2022-04-02 17:04:20 -07:00
flake.lock Update flake.lock 2025-12-01 21:16:25 -08:00
flake.nix * Add --show and allow CLI-only usage. 2026-08-15 17:59:55 -07:00
LICENSE Update docs 2026-08-13 18:55:42 -07:00
Makefile * Add --show and allow CLI-only usage. 2026-08-15 17:59:55 -07:00
pyproject.toml * Add --show and allow CLI-only usage. 2026-08-15 17:59:55 -07:00
README.md * Add --show and allow CLI-only usage. 2026-08-15 17:59:55 -07:00

Bitwarden-menu

PyPI - Python Version PyPI GitHub contributors

Dmenu/Rofi frontend for managing Bitwarden vaults. Uses the Bitwarden CLI tool to interact with the Bitwarden database.

This project is not associated with the Bitwarden project nor 8bit Solutions LLC.

Installation

pip install --user bitwarden-menu[autotype]

Ensure ~/.local/bin is in your $PATH. Run bwm and enter your database path, keyfile path, and password.

Drop the [autotype] extra to install without pynput.

NOTE: Initial login to some servers, including vault.bitwarden.com, will require the client_secret from your account settings page. Ensure this is in your clipboard and ready to paste prior to first run. Once logged in for the first time, you will not need this value again.

For full installation documention see the [installation docs][docs/install.md].

Full Documentation

Installation - Configuration - Usage

Requirements

  1. Python 3.10+
  2. Bitwarden CLI. Ensure the bw command is in $PATH
  3. Xdg

The rest is only needed for the interactive (launcher) mode:

  1. Pynput (pip install bitwarden-menu[autotype]), or one of the alternate type libraries below
  2. Dmenu, Rofi, Wofi or Bemenu
  3. xsel or wl-copy
  4. (optional) Pinentry.
  5. (optional) xdotool, ydotool(>= 1.0.0)/wtype (for Wayland).

Features

  • Supports multiple bitwarden.com and self-hosted Vaultwarden accounts. Accounts can be switched on the fly.
  • Auto-type username and/or password on selection. Select to clipboard if desired (clipboard clears after 30 sec on X11 or after 1 paste on Wayland).
  • Supports login with 2FA code from Authenticator(TOTP), Email, or Yubikey.
  • Background process allows selectable time-out for locking the database.
  • Use a custom Keepass 2.x style auto-type sequence.
  • Type, view or edit any field.
  • Open the URL in the default web browser.
  • Non U.S. English keyboard languages and layouts supported via xdotool or ydotool/wtype (for Wayland).
  • Edit notes using terminal or gui editor.
  • Add and Delete entries
  • Rename, move, delete and add folders and collections
  • Move any item to or from an organization, including support for multiple collections.
  • Hide selected folders from the default and 'View/Type Individual entries' views.
  • Configure the characters and groups of characters used during password generation.
  • Optional Pinentry support for secure passphrase entry.
  • Add, edit and type TOTP codes.
  • Offline use: an already logged in vault can be unlocked, viewed and typed without a network connection.
  • Output any field(s) to stdout with --show, usable as a CLI-only password manager with no launcher or GUI installed. Works headless, including the initial login and 2FA.
  • Runs as a background daemon, so a vault is unlocked once rather than on every lookup. --foreground keeps it attached for troubleshooting.

License

  • MIT

Usage

bwm [-h] [-V] [-v VAULT] [-l LOGIN] [-k] [-a AUTOTYPE] [-C] [-c CONFIGPATH] [-s SEARCH] [-f FIELD] [-F]

  • Run bwm or bind to keystroke combination.
  • Enter account URL on first run.
  • Start typing to match entries.
  • Configure ~/.config/bwm/config.ini as desired.
  • More detailed usage information.
  • Screencast (Using Bemenu on Sway):

Screencast

Tests

Run tests using pytest:

# Using make (creates venv automatically)
make test

# With coverage report
make test-cov

# Or install and run directly
pip install .[test]
pytest

Development

  • To install bitwarden-menu in a venv: make

  • Build man page from Markdown source: make man

  • The version is hardcoded in bwm/__init__.py (make version or bwm -V). Anything else needing a version number reads from there.

  • Using hatch:

    • hatch shell: provies venv with editable installation.
    • hatch build && hatch publish: build and publish to Pypi.
  • Using nix:

    • nix develop: Provides development shell with all dependencies.
    • make test and hatch build/publish work as usual.
  • GitHub Action will upload to TestPyPi on each push to main. To create a GitHub and PyPi release, run make release VERSION=x.y.z (no leading v; the tag gets one). It bumps __version__, updates and rebuilds the man page, commits, and opens an editor for the annotated tag, prefilled with the version as the subject and one bullet per commit since the last tag.

      <tag name on first line, prefilled>
    
      * Release note 1
      * Release note 2
      * ...
    

    Then push the commit and tag: git push origin main --follow-tags. The GitHub Action fails the build if a pushed tag does not match __version__, so nothing mismatched can reach PyPi.

Planned features

  • Notifications for syncing status (e.g. when a sync is complete)