Local-first, offline password manager.
Zero cloud. Zero telemetry. Fully open-source.
Designed for security, simplicity, and complete user control.
LocalPass
Local-first, offline password manager. Zero cloud. Zero telemetry. Fully open-source.
Why LocalPass?
Most password managers rely on cloud sync, telemetry, or proprietary storage. LocalPass takes the opposite approach:
- 100% offline
- 100% local storage
- 100% open-source
- no accounts, no tracking, no vendor lock-in If you want full control over your vault — LocalPass is built for you.
Quickstart
Initialize a new vault
localpass init myvault.lp
# You'll be prompted to enter and confirm a master password
# Password strength feedback is provided
Add a new entry
localpass add myvault.lp --id 1
# You'll be prompted for master password, service, username, password (with confirmation), and notes
List all entries
localpass list myvault.lp
Show entry details
localpass show myvault.lp <entry-id>
Remove an entry
localpass remove myvault.lp <entry-id>
Check password against breaches
localpass hibp-check
# You'll be prompted to confirm the network request, then enter a password to check
Automation with JSON output
LocalPass supports scripting and automation with JSON output mode:
# Get version in JSON format
localpass --json
# Output: {"status": "ok", "version": "0.3.0", "action": "version", "data": {...}}
# Non-interactive initialization (use with caution)
localpass init new_vault.lp --yes
# List entries in JSON format
localpass --json list myvault.lp
Installation
Using pip
pip install localpass
Editable mode (for development)
git clone https://github.com/wrogistefan/LocalPass.git
cd LocalPass
pip install -e .
Key Features
- 🔒 Encrypted Vault: Uses Argon2id for key derivation and AES-GCM for encryption
- 💻 Cross-platform: Works on Windows, macOS, and Linux
- 📦 Zero Cloud: No cloud sync, no telemetry, no remote storage
- 📖 Open-Source: Fully transparent codebase under Apache License 2.0
- ✅ High Test Coverage: 90%+ test coverage with comprehensive validation (configured threshold: 89%)
- Note: 98% coverage would require extensive mocking of network errors and edge cases that are not practical for a CLI application with network operations.
- 🔧 Shell Compatibility: Verified on Windows PowerShell and Unix shells (WSL/bash)
- 🤖 Automation Support: JSON output mode and
--yesflags for scripting - 📊 Password Strength Feedback: zxcvbn-powered strength analysis with warnings and suggestions
Security Model
LocalPass follows a strict local‑first and offline‑first security philosophy. All operations happen entirely on the user's device, and no data is ever sent to external services.
- Local‑only encryption — all vault data is encrypted client‑side using Argon2id and AES‑256‑GCM.
- Offline‑first — the application works fully without network access.
- Zero cloud — no sync, no remote storage, no accounts, no telemetry.
- Deterministic security — the vault file contains everything needed to decrypt the data; nothing is stored elsewhere.
For detailed cryptographic parameters, vault format, repository types, and responsible disclosure guidelines, see:
Optional HIBP Password Check
LocalPass includes an optional, fully manual password check using the Have I Been Pwned (HIBP) k‑anonymity API.
This feature is:
- optional — disabled by default,
- manual — only executed when explicitly requested by the user,
- non‑blocking — it never prevents vault creation,
- privacy‑preserving — only the first 5 characters of the SHA‑1 hash are sent,
- philosophy‑aligned — no automatic network calls, ever.
This keeps LocalPass fully offline‑first while still offering a useful security tool for users who want it.
Project Structure
src/localpass/
├── cli.py # CLI interface
├── vault/
│ ├── crypto.py # Encryption/decryption
│ ├── models.py # Data models
│ ├── repository.py # Vault storage
│ ├── service.py # Business logic
│ └── serialization.py # JSON serialization
└── __main__.py # Entry point
Vault API
The Vault class provides the core API for managing password entries:
Methods
add_entry(entry: VaultEntry) -> None: Add a new entry to the vault.list_entries() -> List[VaultEntry]: Return a copy of all entries in the vault.get_entry_by_id(entry_id: str) -> Optional[VaultEntry]: Retrieve an entry by its unique ID, orNoneif not found.remove_entry(service: str) -> None: Remove all entries that match the specified service name.remove_entry_by_id(entry_id: str) -> None: Remove the entry with the specified unique ID. RaisesValueErrorif the entry does not exist.
Key Differences
remove_entry(service)performs a bulk removal of all entries for a given service, which is useful for cleaning up multiple accounts.remove_entry_by_id(entry_id)provides granular deletion of a single entry by its ID, intended for precise CLI operations. It ensures the entry exists before removal.
This API is designed for programmatic use and powers the LocalPass CLI.
📰 In the media
LocalPass was recently featured on Korben.info, one of the most respected French tech and privacy blogs.
"LocalPass – a 100% offline password manager for the terminal.
Zero cloud, zero telemetry, full data sovereignty."
— Korben.info
The article captured the core idea behind the project perfectly:
a simple, local‑first tool that keeps your data entirely on your machine.
LocalPass started as a small side project — something built mainly for personal use.
Thanks to this coverage, it has begun to grow beyond that, which is a huge motivation to keep improving it.
🔗 Read the article: https://korben.info/localpass-gestionnaire-mots-de-passe-offline.html
License
This project is licensed under the Apache License 2.0. See the LICENSE file for full details.