Todos os comandos do seu gerenciador de senhas, do uso diário à emergência. O nome de um item pode ser só um pedaço do título: pfm get conta acha contabo.com.
Every command of your password manager, from daily use to emergencies. An item's name can be just part of its title: pfm get deep finds deepseek.com.
Começar
Uma vez por notebook. O cofre fica em ~/.local/share/passforme, cifrado.
pfm init criar o cofre
Pede a frase mestra (pelo menos 12 caracteres) e mostra o Emergency Kit: a Secret Key, que começa com SB1-. Uma frase de palavras é mais fácil de lembrar que uma senha aleatória, e o gerador sugere uma.
Anote a frase mestra e a Secret Key em papel e guarde longe do notebook. Sem as duas não há recuperação: o cofre é cifrado no seu aparelho, e ninguém mais tem a chave.
pfm register URL ligar a um servidor (opcional)
Sem servidor, o pfm funciona só neste notebook. Com um passforme-server seu, o cofre sincroniza entre aparelhos, e o servidor só guarda o cofre cifrado. O registro pede um convite de uso único, gerado no servidor.
pfm register https://pfm.example.com
Uso diário
Copiar, consultar e ver. Tudo o que vai para o clipboard se apaga sozinho em 30 segundos.
Tab completa comandos, opções e tipos
Toda opção tem um nome só, por extenso: --username, --generate, --symbols. Para não digitar tudo, use Tab: pfm add x --us + Tab vira --username, e --kind + Tab lista os tipos. Uma forma curta antiga, como -u, responde com o nome novo.
Para ligar, acrescente esta linha ao seu ~/.bashrc:
source <(passforme completions bash)
Também há scripts para zsh, fish, elvish e powershell:
Copia o segredo principal do item: a senha de um login, o número de um cartão, o PIN de um PIN.
Opção
O que faz
--field username
copia o usuário
--field url
copia o endereço
--field totp
copia o código 2FA de agora
--field cvv, --field pin, --field number…
copia um campo pelo nome; um nome errado lista os que existem
--attachment NOME
salva um anexo no diretório atual, ou onde --output mandar; nunca sobrescreve
pfm get contabo
pfm get contabo --field username # copia o usuário
pfm get contabo --field url # copia o endereço
pfm get github --field totp # copia o código 2FA de agora
pfm get nubank --field cvv
pfm get proton-recovery --attachment proton-recovery.txt --output ~/Desktop # salva o anexo numa pasta
pfm list ver todos os itens
Tabela com título, tipo, usuário, URL e o que mais cada item guarda: campos extras, 2FA, quantos códigos de recuperação restam, quantos arquivos anexados, e se programas podem ler o item. Nunca mostra senhas.
pfm list
pfm list | grep -i kimi # filtrar
pfm show NOME ver um item inteiro
Todos os campos, com os segredos como ********. Com --reveal, mostra os segredos na tela. Os anexos aparecem como Attachment: nome (tamanho): é ali que você vê o nome exato para o get --attachment.
pfm show nubank # segredos escondidos
pfm show nubank --reveal # segredos na tela
pfm totp NOME código 2FA
Mostra o código de 6 dígitos de agora e por quantos segundos ele vale. Para copiar: pfm get NOME --field totp. O segredo do 2FA entra com pfm edit NOME --totp.
pfm totp github # mostra o código
pfm get github --field totp # copia o código
pfm codes NOME código de recuperação
Copia o próximo código ainda não usado e o marca como usado. Avisa quando restam dois ou menos. Com --list, mostra todos e quais já foram usados (na tela, em texto puro). Para cadastrar os códigos, ver códigos de recuperação.
pfm codes openai # copia o próximo e marca como usado
pfm codes openai --list # todos, com (used) nos usados
Não há como desmarcar um código: rode pfm codes só na hora de usar. Marcar ao copiar é o lado seguro do erro: no pior caso sobra um código a menos, e nunca um já gasto volta para a lista. Se precisar refazer a lista, cole os códigos de novo com pfm edit NOME --codes.
Cadastrar
Uma senha nova gerada na hora, uma senha que já existe, ou várias de uma vez.
pfm add NOME cadastrar um item
Sem --generate, pede a senha duas vezes, para conferir. Use assim para guardar uma senha que você não quer trocar.
deixa programas (scripts, agentes de IA) lerem o item (ver Agente)
Com --generate valem as opções do gerador: --symbols, --length 16, --words 6… Sem --generate, elas dão erro, em vez de serem ignoradas.
pfm add contabo.com --username root --url https://contabo.com --generate # conta nova
pfm add roteador --username admin --url http://192.168.1.1 # senha que já existe
pfm add banco.com --generate --symbols # com símbolos
pfm add app.com --generate --length 16 # site que limita o tamanho
pfm add-many várias de uma vez
Pede label, senha, label, senha… até um Enter vazio. A frase mestra é pedida uma vez e cada item é salvo na hora: parar no meio não perde nada. A senha colada não aparece na tela. Bom para trazer senhas de outro gerenciador; depois complete cada item com pfm edit.
pfm add-many # Label: github.com, a senha, Label: … Enter vazio termina
pfm edit github.com --username voce@exemplo.com --url https://github.com # completar depois
Login sem senha código por SMS, entrar com Google
Para o site que entra pelo celular ou pela conta Google, cadastre sem --generate e, quando ele pedir o segredo, aperte Enter sem digitar nada: o item fica sem senha. Vale cadastrar mesmo assim, porque daqui a um ano o difícil é lembrar como você entrava.
--username: o número de celular ou o e-mail usado. No login pelo Google, o e-mail da conta Google, porque com várias contas é fácil esquecer qual foi.
Notas: o método ("login com Google", "código por SMS"). O add não tem opção de notas: acrescente com pfm edit NOME --notes e termine o texto com Ctrl-D numa linha vazia.
Códigos de recuperação: se o site tiver 2FA e oferecer códigos de backup, guarde-os num item próprio do tipo recovery-codes.
Se um dia o site passar a pedir senha, gere uma no item que já existe com pfm edit NOME --generate.
pfm add ifood.com.br --username "+55 51 9xxxx-xxxx" --url https://ifood.com.br # Enter vazio no segredo
pfm edit ifood --notes # escreva o método; Ctrl-D termina
pfm add "ifood codes" --kind recovery-codes # códigos de backup do 2FA
pfm edit ifood --generate # se passar a pedir senha
Tipos de item
pfm add NOME --kind TIPO pergunta os campos do tipo, um por vez; Enter pula o campo. pfm kinds lista os tipos no terminal. --username, --url e --file só valem nos tipos que têm esse campo, e --generate só em login, wifi e bank, cujo segredo é uma senha: um PIN, um cartão ou uma frase de cripto gerados não fariam sentido.
Tipo
Para quê
get copia
login (padrão)
site ou app: usuário, senha, URLs, 2FA
a senha
note
texto livre
—
recovery-codes
códigos de backup; um por linha ao colar, linha vazia termina (exemplos)
use pfm codes
recovery-phrase
frase de recuperação de uma conta (Proton…); confere o BIP-39 quando for um
as palavras
security-questions
perguntas e respostas de segurança
--field "a pergunta"
pin
celular, alarme, cadeado
o PIN
api-key
chave de API ou token: o nome dela no site, a validade
a chave
crypto-seed
frase da carteira; confere o checksum do BIP-39
as palavras
ssh-key
chave SSH ou GPG, lida com --file
a chave privada
card
titular, número (confere o dígito), validade MM/AA, CVV, PIN
o número
bank
agência, conta, senhas do app e de transação, chave Pix
pfm add "wifi casa" --kind wifi --generate # a senha da rede, gerada
pfm add itau --kind bank
pfm add cpf --kind document
pfm add "gov.br perguntas" --kind security-questions # pergunta → resposta, até uma pergunta vazia
pfm add "anotações servidor" --kind note # texto livre; Ctrl-D numa linha vazia termina
pfm add jetbrains --kind license
pfm kinds # lista os tipos e os campos de cada um
Frase de cripto e número de cartão são conferidos na hora. Se houver palavra trocada ou dígito errado, o pfm avisa e pergunta antes de salvar, enquanto o papel ainda está na sua mão.
pfm add NOME --kind api-key guardar uma chave de API
O add pergunta um campo por vez, nesta ordem, e Enter pula qualquer um. O Key name já é perguntado aqui: não precisa de --set-field. A conta e a URL também podem ir no comando, com --username e --url, e aí ele pergunta só o resto.
Campo
O que vai nele
Account
a conta da qual a chave saiu, em geral o e-mail. É o username do item, com outro nome. Se a chave vazar, ele diz em qual conta revogá-la.
Key name
o nome que você deu à chave no site, como meu-notebook: com várias chaves na mesma conta, diz qual revogar
Key
a chave, colada; não aparece na tela
URL
o painel onde a chave foi criada
Expires
a validade; vazio se não expira
Com --agent, programas (scripts, agentes de IA) podem ler a chave (ver Agente). Use só se um programa vai ler a chave; para copiar e colar você mesmo, deixe sem, e ela nunca passa pelo agente. Na configuração deles, use o título inteiro: deepseek casaria também com o login deepseek.com.
pfm add "deepseek api key" --kind api-key --username voce@exemplo.com --url https://platform.deepseek.com # conta e URL no comando
pfm add "deepseek api key" --kind api-key --agent # chave que um programa vai ler
pfm get "deepseek api key" # copia a chave
pfm get "deepseek api key" --field account # copia o e-mail da conta
pfm edit "deepseek api key" --password # trocar por uma chave nova
pfm edit "deepseek api key" --set-field "Key name" # mudar o nome depois, ou num item criado antes do campo existir
pfm get "deepseek api key" --field "key name" # copia só o nome
Várias chaves na mesma conta: um item por chave, com o nome dela também no título, como deepseek api key notebook e deepseek api key servidor. Assim o get, o list e a configuração dos programas diferenciam uma da outra só pelo título.
Um serviço, vários logins um item para cada login
Alguns serviços têm um login para o app e outro para a API, como o Kimi: o chat em kimi.ai entra pelo telefone, e a plataforma de API em platform.kimi.ai entra por e-mail ou Google. Cadastre um item para cada login, cada um com o seu username, e a chave num terceiro item.
Com vários itens começando por "kimi", pfm get kimi responde "matches several items" e lista os itens. Use o título exato, que sempre ganha, ou um pedaço que só um título tenha.
Duas contas no Zoho, no Google ou na AWS são dois itens, cada um com o seu usuário e a sua senha. Ponha no título o que diferencia uma da outra (pessoal, trabalho, o domínio), para o get achar a certa.
Se é o mesmo login, com a mesma senha, e a conta tem outros e-mails (o de cadastro, um alias, o de recuperação), o --username fica com o que você digita para entrar, e os outros vão em campos extras. O nome do campo é livre: Alias, Signup email, Recovery email, o que fizer sentido para você.
Campos extras só existem no edit: cadastre primeiro, acrescente depois. Se o outro e-mail entra com outra senha, é outro login, e vira outro item.
pfm add "zoho.com empresa" --username voce@empresa.com --url https://www.zoho.com --generate # o e-mail com que você entra
pfm get "zoho.com empresa" --field "signup email" # copia o campo
pfm edit "zoho.com empresa" --rm-field "Signup email" # remove o campo
pfm add NOME --kind recovery-codes códigos de recuperação e o arquivo
Os códigos de backup do 2FA (OpenAI, GitHub, Google…). O tipo pergunta a conta e a URL, que também podem vir no comando, e então os códigos: cole todos, um por linha, e termine com uma linha vazia. Código com espaço no meio vale. Não aparecem na tela.
Se o site deu um arquivo com os códigos, anexe-o com edit --attach, como cópia do original. Mesmo assim os códigos ficam no item, porque o pfm codes usa os do item.
pfm get "openai recovery codes" --attachment openai-recovery-codes.txt --output ~/Desktop # devolve o arquivo
pfm edit github --codes # códigos dentro de um login, ou trocar por um lote novo
Gerou códigos novos no site? pfm edit NOME --codes --attach ARQUIVO_NOVO troca os códigos e anexa o arquivo novo; --rm-attachment tira o antigo. Depois apague o arquivo de ~/Downloads.
pfm add NOME --kind recovery-phrase frase e arquivo de recuperação
Serviços como o Proton dão uma frase de recuperação (12 palavras) e às vezes um arquivo de recuperação. O tipo recovery-phrase pergunta a conta, a URL e as palavras. Se a frase tem o tamanho de uma frase BIP-39 (12, 15, 18, 21 ou 24 palavras), o pfm a confere: uma palavra trocada ou digitada errada aparece na hora. Frases de outro formato são guardadas como foram digitadas.
O arquivo vai como anexo, cifrado dentro do item, com edit --attach. Os anexos de um item somam no máximo 512 KiB: o cofre inteiro viaja a cada sincronização, então só cabem arquivos pequenos.
pfm add proton-recovery --kind recovery-phrase # conta, URL e as 12 palavras
pfm edit proton-recovery --attach ~/Downloads/proton-recovery.txt # guarda o arquivo no item
pfm get proton-recovery # copia as palavras
pfm get proton-recovery --attachment proton-recovery.txt --output ~/Downloads # devolve o arquivo
pfm edit proton-recovery --rm-attachment proton-recovery.txt # remove o anexo
O get --attachment nunca sobrescreve um arquivo e grava legível só por você. Depois de guardar o arquivo no pfm, apague a cópia de ~/Downloads.
Alterar e apagar
pfm edit NOME mudar um item
Muda só o que você pedir; a senha continua a mesma, a menos que use --generate ou --password.
Opção
O que faz
--title NOVO
renomeia
--username USUÁRIO
troca o usuário
--url / --rm-url
acrescenta / remove um endereço
--password
digita uma senha nova
--generate
gera uma senha nova e copia; só em itens login, wifi e bank
--totp
cola o segredo do 2FA (texto ou link otpauth://)
--notes
escreve notas; termina com Ctrl+D
--set-field NOME
cria ou troca um campo visível
--set-secret-field NOME
cria ou troca um campo oculto
--rm-field NOME
remove um campo
--codes
substitui os códigos de recuperação
--attach ARQUIVO
guarda um arquivo pequeno no item; um de mesmo nome é substituído
--rm-attachment NOME
remove um anexo
--kind TIPO
muda o tipo, sem perder dados
--agent / --no-agent
liga ou desliga o acesso de programas
pfm edit deepseek --url https://chat.deepseek.com --url https://deepseek.com # endereços num item que já existe; a senha fica
pfm edit contabo --generate # trocou a senha no site
pfm edit github --totp # ativou o 2FA
pfm edit alarme --kind pin
pfm edit contabo --title contabo.com # renomeia
pfm edit contabo --username novo@exemplo.com # troca o usuário
pfm edit deepseek --rm-url https://deepseek.com # remove um endereço
pfm edit roteador --password # digita a senha nova, duas vezes
pfm edit contabo --generate --symbols --length 20 # gera com as regras do site
pfm edit ifood --notes # notas; Ctrl-D numa linha vazia termina, vazio apaga
pfm edit nubank --set-secret-field "Senha do app" # campo oculto, digitado sem eco
pfm edit nubank --rm-field "Senha do app" # remove o campo
pfm edit "deepseek api key" --agent # programas podem ler; --no-agent desfaz
Anexos arquivos pequenos dentro de um item
Arquivo de recuperação, códigos em .txt, um PDF com as palavras: edit --attach guarda o arquivo dentro do item, e get --attachment devolve. Até 512 KiB somando os anexos de um item; um anexo com o mesmo nome substitui o anterior.
O anexo é cifrado sempre, junto com o resto do item: no cofre do notebook, no .bak, no servidor e no histórico dele, e na sincronização. Programas (o agente) nunca recebem anexos. Ele só fica em texto puro em dois lugares, os dois por ação sua: o arquivo original, até você apagar, e a cópia que o get --attachment grava (legível só por você, nunca sobrescreve nada). O servidor vê só o tamanho aproximado do item, nunca o conteúdo nem o nome do arquivo.
Nenhuma opção é ignorada: se uma não fizer sentido no comando, o pfm recusa antes de pedir qualquer coisa. Frase e caracteres não se misturam: --words não aceita --length, --symbols, --no-… nem --avoid-ambiguous. No add e no edit, todas as opções do gerador precisam de --generate.
Sessão e segurança
Sessão automática
Digitou a frase mestra uma vez, os próximos comandos não pedem de novo. Trava em 15 minutos sem uso, quando a tela bloqueia, quando o notebook suspende, ou com pfm lock. Só vale para comandos digitados no terminal.
Para mudar o tempo, crie ~/.config/passforme/config com uma linha:
session = 1h # ou 30m; "off" pede a frase sempre
pfm lock travar agora
Fecha a sessão e esvazia o agente. Bom antes de emprestar o notebook ou sair de perto.
pfm lock
pfm status ver o estado
Se a sessão está aberta e por quanto tempo, se o agente está ativo e com quais itens, e o servidor de sincronização. Não recebe nome de item.
pfm status
pfm passwd trocar a frase mestra
Recifra o cofre com uma chave nova. A Secret Key continua a mesma. Anote a frase nova no Emergency Kit. Com servidor, os outros aparelhos pedem a frase nova na próxima sincronização.
pfm passwd # frase atual, depois a nova duas vezes
Agente (programas)
Programas (scripts, agentes de IA) não usam a sessão. Eles só leem os itens que você marcar, e nada mais do cofre.
Comando
O que faz
pfm edit openrouter --agent
marca o item para programas
pfm unlock
entrega os itens marcados ao agente por 8 horas
pfm unlock --for forever
até travar, reiniciar ou sair da sessão
pfm unlock --for 2h gemini
só os itens citados, pelo tempo dado
pfm get NOME --stdout
o que o programa chama para ler o valor
pfm edit "deepseek api key" --agent # 1. marcar
pfm unlock --for 8h # 2. liberar, com a frase mestra
pfm get "deepseek api key" --stdout # 3. o que o programa roda
DEEPSEEK_API_KEY="$(pfm get 'deepseek api key' --stdout)" ./meu-script # num script
pfm status # o que o agente guarda e por quanto tempo
pfm lock # esvazia o agente agora
Sem agente liberado, o get --stdout fora de um terminal falha na hora, em vez de ficar esperando uma frase que ninguém vai digitar.
Sincronização
Acontece sozinha a cada add, edit, rm e codes. Se o servidor estiver fora do ar, a mudança fica no notebook e sobe na próxima vez. O servidor só guarda o cofre cifrado.
Comando
Quando usar
pfm sync
forçar a troca com o servidor
pfm register URL
ligar o cofre a um servidor vazio
pfm init
criar um cofre novo
pfm sync # depois de mudar algo em outro aparelho
pfm status # mostra a qual servidor está ligado
Item editado nos dois aparelhos ao mesmo tempo: fica a versão do servidor e a sua vira "título (conflict)". Nada digitado se perde.
Emergência
Notebook quebrou, foi roubado ou trocou? O cofre volta inteiro do seu servidor, com o Emergency Kit.
pfm login URL configurar um aparelho novo
Pede a Secret Key (começa com SB1-) e a frase mestra, as duas do Emergency Kit, e baixa o cofre.
pfm login https://pfm.example.com
Sem a Secret Key e a frase não há recuperação: nem o servidor consegue abrir o cofre. Por isso o Emergency Kit fica em papel, guardado longe do notebook.
Nenhum comando com esse termo.
Getting started
Once per laptop. The vault lives in ~/.local/share/passforme, encrypted.
pfm init create the vault
Asks for the master phrase (at least 12 characters) and shows the Emergency Kit: the Secret Key, which starts with SB1-. A phrase of words is easier to remember than a random password, and the generator suggests one.
pfm generate --words 6 --lang en # a master phrase suggestion
pfm init
Write the master phrase and the Secret Key on paper and keep it away from the laptop. Without both there is no recovery: the vault is encrypted on your device, and nobody else has the key.
pfm register URL link to a server (optional)
Without a server, pfm works on this laptop only. With your own passforme-server, the vault syncs between devices, and the server keeps only the encrypted vault. Registering takes a single-use invite, made on the server.
pfm register https://pfm.example.com
Daily use
Copy, look up, view. Anything copied to the clipboard is cleared by itself after 30 seconds.
Tab completes commands, options and kinds
Every option has a single, spelled-out name: --username, --generate, --symbols. To avoid typing it all, press Tab: pfm add x --us + Tab becomes --username, and --kind + Tab lists the kinds. An old short form such as -u answers with its new name.
To turn it on, add this line to your ~/.bashrc:
source <(passforme completions bash)
There are scripts for zsh, fish, elvish and powershell too:
Copies the item's main secret: a login's password, a card's number, a PIN's PIN.
Option
What it does
--field username
copies the username
--field url
copies the address
--field totp
copies the current 2FA code
--field cvv, --field pin, --field number…
copies a field by name; a wrong name lists the ones that exist
--attachment NAME
saves an attachment in the current directory, or where --output says; never overwrites
pfm get contabo
pfm get contabo --field username # copies the username
pfm get contabo --field url # copies the address
pfm get github --field totp # copies the current 2FA code
pfm get visa --field cvv
pfm get proton-recovery --attachment proton-recovery.txt --output ~/Desktop # saves the attachment in a folder
pfm list see every item
A table with title, kind, username, URL and what else each item holds: extra fields, 2FA, how many recovery codes are left, how many files are attached, and whether programs may read it. Never shows passwords.
pfm list
pfm list | grep -i kimi # filter
pfm show NAME see a whole item
Every field, with secrets as ********. With --reveal, the secrets are shown on screen. Attachments show as Attachment: name (size): that is where you find the exact name for get --attachment.
pfm show visa # secrets hidden
pfm show visa --reveal # secrets on screen
pfm totp NAME 2FA code
Shows the current 6-digit code and how many seconds it is still valid. To copy it: pfm get NAME --field totp. The 2FA secret goes in with pfm edit NAME --totp.
pfm totp github # shows the code
pfm get github --field totp # copies the code
pfm codes NAME recovery code
Copies the next unused code and marks it used. Warns when two or fewer are left. With --list, shows them all and which were used (on screen, in plain text). To add the codes, see recovery codes.
pfm codes openai # copies the next one and marks it used
pfm codes openai --list # all of them, (used) on the used ones
A code cannot be unmarked: run pfm codes only when you are about to use one. Marking on copy errs on the safe side: at worst you are one code short, and a spent code never comes back to the list. To rebuild the list, paste the codes again with pfm edit NAME --codes.
Adding
A new password generated on the spot, a password you already have, or many at once.
pfm add NAME add an item
Without --generate, it asks for the password twice, to check it. Use it this way to keep a password you don't want to change.
pfm add router --username admin --url http://192.168.1.1 # a password you already have
pfm add bank.com --generate --symbols # with symbols
pfm add app.com --generate --length 16 # a site that limits the length
pfm add-many many at once
Asks for label, password, label, password… until an empty Enter. The master phrase is asked once and every item is saved right away: stopping halfway loses nothing. A pasted password is not shown. Handy for bringing passwords over from another manager; fill in each item afterwards with pfm edit.
pfm add-many # Label: github.com, the password, Label: … an empty Enter finishes
pfm edit github.com --username you@example.com --url https://github.com # fill in later
Passwordless login SMS code, sign in with Google
For a site you enter through your phone or your Google account, add it without --generate and, when it asks for the secret, press Enter without typing anything: the item is saved without a password. It is still worth adding, because a year from now the hard part is remembering how you signed in.
--username: the phone number or email you used. For Google sign-in, the Google account's email, since with several accounts it is easy to forget which one.
Notes: the method ("sign in with Google", "SMS code"). add has no notes option: add them with pfm edit NAME --notes and finish the text with Ctrl-D on an empty line.
Recovery codes: if the site has 2FA and offers backup codes, keep them in an item of their own, of kind recovery-codes.
If the site ever starts asking for a password, generate one on the existing item with pfm edit NAME --generate.
pfm add uber.com --username "+1 555 010 0199" --url https://uber.com # empty Enter for the secret
pfm edit uber --notes # write the method; Ctrl-D finishes
pfm edit uber --generate # if it starts asking for a password
Kinds of item
pfm add NAME --kind KIND asks for the kind's fields one by one; Enter skips a field. pfm kinds lists the kinds in the terminal. --username, --url and --file only apply to kinds that have that field, and --generate only to login, wifi and bank, whose secret is a password: a generated PIN, card or recovery phrase would make no sense.
Kind
For
get copies
login (default)
a site or app: username, password, URLs, 2FA
the password
note
free text
—
recovery-codes
backup codes; one per line when pasting, an empty line finishes (examples)
use pfm codes
recovery-phrase
an account's recovery phrase (Proton…); BIP-39 checked when it is one
the words
security-questions
security questions and answers
--field "the question"
pin
phone, alarm, lock
the PIN
api-key
an API key or token: its name on the site, its expiry
the key
crypto-seed
a wallet's recovery phrase; checks the BIP-39 checksum
the words
ssh-key
an SSH or GPG key, read with --file
the private key
card
cardholder, number (check digit), expiry MM/YY, CVV, PIN
pfm add "bank questions" --kind security-questions # question → answer, until an empty question
pfm add "server notes" --kind note # free text; Ctrl-D on an empty line finishes
pfm add jetbrains --kind license
pfm kinds # lists the kinds and each one's fields
Recovery phrases and card numbers are checked as you type them. A swapped word or a wrong digit makes pfm warn you and ask before saving, while the paper is still in your hand.
pfm add NAME --kind api-key keep an API key
add asks for one field at a time, in this order, and Enter skips any of them. The key name is asked here already: no --set-field needed. The account and the URL can also come on the command line, with --username and --url, and then it asks only for the rest.
Field
What goes in it
Account
the account the key came from, usually the email. It is the item's username under another name. If the key leaks, it tells you where to revoke it.
Key name
the name you gave the key on the site, such as john-laptop: with several keys on one account, it tells which to revoke
Key
the key, pasted; it is not shown
URL
the dashboard where the key was created
Expires
the expiry; empty if it doesn't expire
With --agent, programs (scripts, AI agents) can read the key (see Agent). Use it only if a program will read the key; to copy and paste it yourself, leave it off, and the key never goes through the agent. In their configuration, use the whole title: deepseek would also match the deepseek.com login.
pfm add "deepseek api key" --kind api-key # asks for account, key name, key, URL, expiry
pfm add "deepseek api key" --kind api-key --username you@example.com --url https://platform.deepseek.com # account and URL on the command line
pfm add "deepseek api key" --kind api-key --agent # a key a program will read
pfm get "deepseek api key" # copies the key
pfm get "deepseek api key" --field account # copies the account's email
pfm edit "deepseek api key" --password # replace it with a new key
pfm edit "deepseek api key" --set-field "Key name" # change the name later, or on an item made before the field existed
pfm get "deepseek api key" --field "key name" # copies just the name
Several keys on one account: one item per key, with its name in the title too, such as deepseek api key laptop and deepseek api key server. Then get, list and the programs' configuration tell them apart by title alone.
One service, several logins one item per login
Some services have one login for the app and another for the API, like Kimi: the chat at kimi.ai signs in by phone, and the API platform at platform.kimi.ai by email or Google. Add one item per login, each with its own username, and the key in a third item.
With several items starting with "kimi", pfm get kimi answers "matches several items" and lists them. Use the exact title, which always wins, or a part only one title has.
Several accounts on one service one item per account
Two Zoho, Google or AWS accounts are two items, each with its own username and password. Put what tells them apart in the title (personal, work, the domain), so get finds the right one.
If it is the same login, with the same password, and the account has other emails (the signup one, an alias, the recovery one), --username holds the one you type to sign in, and the others go in extra fields. The field name is free: Alias, Signup email, Recovery email, whatever makes sense to you.
Extra fields exist only in edit: add the item first, then the fields. If the other email signs in with another password, it is another login, and another item.
pfm add "zoho.com company" --username you@company.com --url https://www.zoho.com --generate # the email you sign in with
pfm edit "zoho.com company" --set-field "Signup email" # asks for the value, visibly
pfm get "zoho.com company" --field "signup email" # copies the field
pfm edit "zoho.com company" --rm-field "Signup email" # removes the field
pfm add NAME --kind recovery-codes recovery codes and their file
A site's 2FA backup codes (OpenAI, GitHub, Google…). The kind asks for the account and the URL, which can also come on the command line, and then the codes: paste them all, one per line, and finish with an empty line. A code with a space in it is fine. They are not shown.
If the site gave you a file with the codes, attach it with edit --attach as a copy of the original. The codes still go in the item, since pfm codes uses the item's.
pfm add "openai recovery codes" --kind recovery-codes --username you@example.com --url https://openai.com # paste; an empty line finishes
pfm get "openai recovery codes" --attachment openai-recovery-codes.txt --output ~/Desktop # gives the file back
pfm edit github --codes # codes inside a login, or a new batch
Made new codes on the site? pfm edit NAME --codes --attach NEW_FILE replaces the codes and attaches the new file; --rm-attachment removes the old one. Then delete the file in ~/Downloads.
pfm add NAME --kind recovery-phrase recovery phrase and file
Services such as Proton give a recovery phrase (12 words) and sometimes a recovery file. The recovery-phrase kind asks for the account, the URL and the words. If the phrase has the length of a BIP-39 phrase (12, 15, 18, 21 or 24 words), pfm checks it: a swapped or mistyped word shows at once. Phrases of any other form are kept as typed.
The file goes in as an attachment, encrypted inside the item, with edit --attach. An item's attachments add up to 512 KiB at most: the whole vault travels on every sync, so only small files fit.
pfm add proton-recovery --kind recovery-phrase # account, URL and the 12 words
pfm edit proton-recovery --attach ~/Downloads/proton-recovery.txt # keeps the file in the item
pfm get proton-recovery # copies the words
pfm get proton-recovery --attachment proton-recovery.txt --output ~/Downloads # gives the file back
pfm edit proton-recovery --rm-attachment proton-recovery.txt # removes the attachment
get --attachment never overwrites a file and writes it readable by you only. Once the file is in pfm, delete the copy in ~/Downloads.
Editing and deleting
pfm edit NAME change an item
Changes only what you ask for; the password stays the same unless you use --generate or --password.
Option
What it does
--title NEW
renames it
--username USER
changes the username
--url / --rm-url
adds / removes an address
--password
type a new password
--generate
generates a new password and copies it; only on login, wifi and bank items
--totp
paste the 2FA secret (text or otpauth:// link)
--notes
write notes; finish with Ctrl+D
--set-field NAME
creates or changes a visible field
--set-secret-field NAME
creates or changes a hidden field
--rm-field NAME
removes a field
--codes
replaces the recovery codes
--attach FILE
keeps a small file in the item; one with the same name is replaced
--rm-attachment NAME
removes an attachment
--kind KIND
changes the kind, losing nothing
--agent / --no-agent
turns program access on or off
pfm edit deepseek --url https://chat.deepseek.com --url https://deepseek.com # addresses on an existing item; the password stays
pfm edit contabo --generate # changed the password on the site
pfm edit github --totp # turned on 2FA
pfm edit alarm --kind pin
pfm edit contabo --title contabo.com # renames it
pfm edit contabo --username new@example.com # changes the username
pfm edit deepseek --rm-url https://deepseek.com # removes an address
pfm edit router --password # type the new password, twice
pfm edit contabo --generate --symbols --length 20 # generate by the site's rules
pfm edit uber --notes # notes; Ctrl-D on an empty line finishes, empty removes them
pfm edit chase --rm-field "App password" # removes the field
pfm edit "deepseek api key" --agent # programs may read it; --no-agent undoes it
Attachments small files inside an item
A recovery file, codes in a .txt, a PDF with the words: edit --attach keeps the file inside the item, and get --attachment gives it back. Up to 512 KiB for all of an item's attachments; an attachment with the same name replaces the old one.
An attachment is always encrypted, together with the rest of the item: in the laptop's vault, in its .bak, on the server and in its history, and during sync. Programs (the agent) never receive attachments. It is in plain text in two places only, both by your doing: the original file, until you delete it, and the copy get --attachment writes (readable by you only, never overwriting anything). The server sees only the item's rough size, never the content or the file's name.
rm ~/Downloads/proton-recovery.pdf # once attached, delete the original
pfm rm NAME delete an item
Asks you to type the title back, to confirm. With a synced vault, the item goes from the other devices too.
pfm rm router # type the title to confirm
Generator
The default is the Contabo style: 29 letters and digits, 173 bits. Nothing that breaks in a form, and a double-click selects all of it.
pfm generate generate only, without saving
Option
What it does
--symbols
with symbols
--length N
length, from 4 to 1024
--no-digits, --no-uppercase, --no-lowercase
leaves out digits, uppercase or lowercase
--avoid-ambiguous
leaves out look-alike characters: l, 1, O, 0
--words N
a phrase of N words instead of characters
--lang pt-br, --lang en
language of the words; only with --words
--separator X
what goes between the words (default -); only with --words
--copy
copies instead of printing
pfm generate # Tguod41e8MFOYKBFPF30bSxnxeIkE
pfm generate --words 6 --lang en # unused-tingly-snowless-…
pfm generate --length 6 --no-lowercase --no-uppercase # a 6-digit PIN
pfm generate --symbols --length 20 # a site that demands a symbol and allows 20
pfm generate --avoid-ambiguous # to read and type by hand
pfm generate --words 5 --separator " " # words separated by spaces
pfm generate --copy # copies without showing it
No option is ignored: if one makes no sense in the command, pfm refuses it before asking for anything. Phrases and characters don't mix: --words takes no --length, --symbols, --no-… or --avoid-ambiguous. In add and edit, every generator option needs --generate.
Session and security
Session automatic
Type the master phrase once, and the next commands don't ask again. It locks after 15 minutes unused, when the screen locks, when the laptop suspends, or with pfm lock. It only applies to commands typed in a terminal.
To change the time, create ~/.config/passforme/config with one line:
session = 1h # or 30m; "off" always asks
pfm lock lock now
Closes the session and empties the agent. Good before lending the laptop or walking away.
pfm lock
pfm status see the state
Whether the session is open and for how long, whether the agent is running and with which items, and the sync server. It takes no item name.
pfm status
pfm passwd change the master phrase
Re-encrypts the vault under a new key. The Secret Key stays the same. Write the new phrase on the Emergency Kit. With a server, the other devices ask for the new phrase on their next sync.
pfm passwd # the current phrase, then the new one twice
Agent (programs)
Programs (scripts, AI agents) don't use the session. They only read the items you mark, and nothing else in the vault.
Command
What it does
pfm edit openrouter --agent
marks the item for programs
pfm unlock
hands the marked items to the agent for 8 hours
pfm unlock --for forever
until you lock, reboot or log out
pfm unlock --for 2h gemini
only the items named, for the time given
pfm get NAME --stdout
what the program calls to read the value
pfm edit "deepseek api key" --agent # 1. mark it
pfm unlock --for 8h # 2. release it, with the master phrase
pfm get "deepseek api key" --stdout # 3. what the program runs
DEEPSEEK_API_KEY="$(pfm get 'deepseek api key' --stdout)" ./my-script # in a script
pfm status # what the agent holds and for how long
pfm lock # empties the agent now
With no agent released, get --stdout outside a terminal fails at once, instead of waiting for a phrase nobody will type.
Sync
Happens by itself on every add, edit, rm and codes. If the server is down, the change stays on the laptop and goes up next time. The server only keeps the encrypted vault.
Command
When to use it
pfm sync
force an exchange with the server
pfm register URL
link the vault to an empty server
pfm init
create a new vault
pfm sync # after changing something on another device
pfm status # shows which server it is linked to
An item edited on two devices at once: the server's version stays and yours becomes "title (conflict)". Nothing typed is lost.
Emergency
Laptop broken, stolen or replaced? The vault comes back whole from your server, with the Emergency Kit.
pfm login URL set up a new device
Asks for the Secret Key (it starts with SB1-) and the master phrase, both from the Emergency Kit, and downloads the vault.
pfm login https://pfm.example.com
Without the Secret Key and the phrase there is no recovery: not even the server can open the vault. That is why the Emergency Kit stays on paper, kept away from the laptop.