Run a Temporary SSH Agent Safely from Your Shell
You will finish with an ssh-agent attached to your current shell, one private key loaded for a bounded lifetime, and a reliable cleanup command. The agent keeps private keys in memory and lets ssh use them without asking for the key passphrase on every connection.
The route
Jump straight to the step you need, or tick off Done means at the end.
Allow about ten minutes. You need the Debian or Ubuntu openssh-client package, a shell, and an existing private key whose passphrase you know. The examples use the installed OpenSSH client package version 1:9.6p1-3ubuntu13.19. They do not need root. Do not use an agent on an untrusted machine, and do not forward it casually to a host you do not control.
1. Check the installed program
Confirm which binary your shell will run and inspect the package version. These are read-only commands:
$ command -v ssh-agent
/usr/bin/ssh-agent
$ dpkg-query -W -f='${Package} ${Version}\n' openssh-client
openssh-client 1:9.6p1-3ubuntu13.19
The important forms are eval "$(ssh-agent -s)" for a Bourne-style shell, ssh-agent command for an agent tied to one child command, and ssh-agent -k to stop the agent named by SSH_AGENT_PID. The agent starts with no identities loaded.
Checkpoint
If command -v finds a wrapper or an unexpected path, stop and establish why before entering a passphrase.
2. Start the agent in this shell
Use the following command in the shell where you will run ssh:
$ eval "$(ssh-agent -s)"
Agent pid 12345
The PID is variable. The command evaluates shell assignments printed by ssh-agent, including SSH_AUTH_SOCK and SSH_AGENT_PID. Every later SSH command in this shell can then find the agent through those variables. Opening another terminal does not automatically copy this environment.
Verify the two values without exposing a private key:
$ printf 'socket: %s\npid: %s\n' "$SSH_AUTH_SOCK" "$SSH_AGENT_PID"
socket: /tmp/ssh-XXXXXXXXXX/agent.12345
pid: 12345
$ test -S "$SSH_AUTH_SOCK" && echo 'agent socket exists'
agent socket exists
The exact temporary directory and PID vary. By default the socket is under $TMPDIR, or under the system temporary directory when that variable is unavailable. It should be accessible only to your user, but root and another process running as the same user can abuse an agent socket.
3. Add one key with an expiry
Choose the key explicitly. Replace the path with the key you intend to use:
$ KEY="$HOME/.ssh/id_ed25519"
$ test -r "$KEY" && echo "key is readable"
key is readable
$ ssh-add -t 1h "$KEY"
Enter passphrase for /home/you/.ssh/id_ed25519:
Identity added: /home/you/.ssh/id_ed25519 (you@example)
-t 1h sets this identity's maximum lifetime to one hour. The agent's own -t option sets a default for identities added later, while an explicit ssh-add -t value overrides that default. Without either setting, an identity can remain until the agent exits. A lifetime is a useful guard against leaving a key loaded in a long-lived login session.
Do not paste a passphrase into a command line, a script, or a terminal recording. If the key path is wrong, fix the path rather than copying a different private key into place. Adding a key changes the agent's in-memory state, not the key file.
4. Verify what the agent holds
List public identities held by the current agent:
$ ssh-add -l
256 SHA256:REDACTED-FINGERPRINT you@example (ED25519)
The fingerprint and comment are host-specific. If the result says The agent has no identities, check that the earlier eval ran in this shell and that the key was accepted. If it says the connection to the authentication agent failed, inspect SSH_AUTH_SOCK and run test -S "$SSH_AUTH_SOCK".
For a real connection, use ordinary SSH and let it try the loaded identity:
$ ssh -o IdentitiesOnly=no [email protected]
[email protected]'s password:
Use your actual account and host in place of the obvious placeholders. A password prompt can mean that the server rejected the offered key, the account is wrong, the key is not authorised there, or the agent is not the one SSH found. It is not proof that the agent failed.
5. Remove the key when you finish
Removing the identity is a reversible, in-memory change. This removes the selected key while leaving the agent running:
$ ssh-add -d "$KEY"
Identity removed: /home/you/.ssh/id_ed25519 (you@example)
$ ssh-add -l
The agent has no identities.
To remove every identity from this agent, use ssh-add -D. That is destructive to the agent's current list, so do not run it in a shared session unless you mean to remove other loaded keys. You can add a required key again with the command from step 3.
6. Stop the agent and recover from a stale shell
When the work is complete, stop the agent created in step 2:
$ ssh-agent -k
unset SSH_AUTH_SOCK;
unset SSH_AGENT_PID;
echo Agent pid 12345 killed;
The PID is variable. This command uses SSH_AGENT_PID and prints shell commands; unlike the earlier eval it does not unset variables in your calling shell unless you evaluate its output. Finish the cleanup in the current shell with:
$ eval "$(ssh-agent -k)"
Agent pid 12345 killed
$ unset KEY
$ test -z "${SSH_AUTH_SOCK:-}" && echo 'agent environment cleared'
agent environment cleared
If the shell was closed before cleanup, its agent may still be alive until its socket or process is removed. In a new shell, do not guess a PID and kill it: first inspect the process owner and command line with ps -u "$USER" -o pid=,comm=,args= | grep '[s]sh-agent'. If you identify an abandoned agent you own, use its recorded environment in the original session where possible, or stop only that exact process with normal process-management tools. Do not kill agents belonging to another session without checking which work depends on them.
7. Keep forwarding and provider options deliberate
SSH agent forwarding lets a remote SSH session use your local agent, but the remote host can request signatures while forwarding is active. Treat a forwarded agent as a credential exposed to that host. Use ssh -A only for a host you trust and only for the duration you need; prefer a host-specific SSH configuration and remove it afterwards.
This installed ssh-agent also supports -O allow-remote-pkcs11 and -O no-restrict-websafe. They relax protections around remote provider loading or FIDO signatures. Do not add either option to a routine startup command. The default restrictions reduce the chance that forwarded access becomes access to an unrelated PKCS#11 provider or website authentication.
Do not put the agent socket in a shared directory with -a unless you have a specific ownership and permission design. Do not use -d or -D for normal shell setup: they keep the agent in the foreground, and debug mode writes diagnostics to standard error. For a one-command scope, the safer pattern is:
$ ssh-agent ssh-add -l
The agent has no identities.
That child agent exits when ssh-add -l exits, but it is not useful for a multi-command shell because its environment is not exported into the parent.
Done means
SSH_AUTH_SOCKpoints to an existing socket owned for this session.- The intended identity appears in
ssh-add -l, with a bounded lifetime where appropriate. - SSH uses the agent without copying a private key to the remote host.
- Agent forwarding is off unless the destination is trusted and the access is needed.
- Loaded identities were removed or the agent was stopped, and the shell no longer carries stale agent variables.