Pillar guide · INFRASTRUCTURE · 10 min read

Installing Hermes Agent on a Linux VPS

Self-host Nous Research's open-source AI agent on Ubuntu or Debian with persistent memory, a messaging gateway and a systemd service.

Installing Hermes Agent on a Linux VPS
Illustration · HostDir Editorial

Hermes Agent is Nous Research's open-source AI agent. Run it locally and it behaves like a session-bound CLI tool. Run it on a Linux VPS and it becomes something different: an always-on agent with persistent memory, scheduled work and 16 messaging integrations including Telegram, Discord and Slack. This guide walks through provisioning a small VPS, installing the agent, configuring a model provider, attaching the messaging gateway, registering it as a systemd service, and verifying the result.

What Hermes Agent is

Hermes Agent is Nous Research's open-source AI agent. It is a Python and Node toolchain that wraps a large language model with a fixed set of capabilities: terminal access, file operations, web search, scheduled tasks, persistent memory across sessions, and a messaging gateway that exposes the agent over Telegram, Discord, Slack, WhatsApp, Signal, email and roughly a dozen other surfaces.

The model itself does not run on your machine. It lives at a provider such as OpenRouter, Anthropic, OpenAI, Nous Portal or MiniMax, or at a local Ollama or vLLM endpoint of your choosing. What runs on the VPS is the agent loop: the planner, the tool harness, the gateway and the memory store. That distinction matters because it determines the size of the box you need.

When a VPS makes sense

You can run Hermes on a laptop. Most people start there. The question is whether you want it to be available when the laptop is closed. A VPS install is appropriate when you want any of the following:

  • Always-on availability. The agent answers messages even when your machine is asleep.
  • Persistent memory across days and machines. Conversations and tools state survive reboots and laptop swaps.
  • Scheduled work. Cron-like execution of agent prompts at fixed times.
  • Messaging integrations. Telegram and Slack bots are easier to operate from a stable IP than from a laptop on a coffee-shop Wi-Fi.
  • A shared instance. A small team uses the same agent and the same memory.

If none of those apply, save the four dollars a month and run it locally. The rest of this guide assumes one or more of them do.

Provisioning the VPS

Hermes is light. For API-backed use, a 1 vCPU, 1 GB RAM, 10 GB disk VPS is enough. Practical providers and plan names at the time of writing:

  • Hetzner Cloud. CX22 plan, around 4 USD per month. Locations in Germany, Finland, the United States and Singapore.
  • Contabo. VPS S, around 5 USD per month.
  • Vultr Cloud Compute. 1 GB plan, 6 USD per month.
  • DigitalOcean Droplet. Basic 1 GB plan, 6 USD per month.

Pick the operating system carefully. Hermes requires Python 3.11 or newer. Ubuntu 22.04 LTS ships 3.10, Ubuntu 24.04 ships 3.12, Debian 12 ships 3.11. The installer can provision a newer Python via uv when the system default is too old, but starting with a modern distribution is less work. Pick Ubuntu 24.04 LTS or Debian 12 unless you have a reason otherwise.

Add your SSH public key during provisioning. Password authentication should be off from minute one.

Server operator workstation with keyboard, proof page and coffee
The Hermes operator's workstation. Keep notes on what the agent is allowed to do.

Hardening before install

Do the boring server hardening before you install anything. None of this is Hermes-specific. It is the bare minimum for any Linux box on the public internet.

Create a non-root user. Log in as root for the first time, then run:

adduser hermes --disabled-password --gecos ""
usermod -aG sudo hermes
echo "hermes ALL=(ALL) NOPASSWD:ALL" > /etc/sudoers.d/hermes
chmod 440 /etc/sudoers.d/hermes
mkdir -p /home/hermes/.ssh
cp /root/.ssh/authorized_keys /home/hermes/.ssh/
chown -R hermes:hermes /home/hermes/.ssh
chmod 700 /home/hermes/.ssh
chmod 600 /home/hermes/.ssh/authorized_keys

Log out, then log back in as hermes over SSH. The rest of the guide is done as this user, never as root.

Disable root SSH login and password authentication. Edit /etc/ssh/sshd_config:

sudo sed -i 's/^#\?PermitRootLogin.*/PermitRootLogin no/' /etc/ssh/sshd_config
sudo sed -i 's/^#\?PasswordAuthentication.*/PasswordAuthentication no/' /etc/ssh/sshd_config
sudo systemctl restart ssh

Install and configure UFW. The messaging gateway is outbound only, so the only inbound port you need is SSH.

sudo apt-get update
sudo apt-get install -y ufw
sudo ufw default deny incoming
sudo ufw default allow outgoing
sudo ufw allow ssh
sudo ufw --force enable
sudo ufw status verbose

Optionally install fail2ban to throttle SSH brute-force attempts. It is not required, but it is cheap.

sudo apt-get install -y fail2ban
sudo systemctl enable --now fail2ban

Installing Hermes Agent

With a hardened box ready, the install itself is one line. As the hermes user:

curl -fsSL https://raw.githubusercontent.com/NousResearch/hermes-agent/main/scripts/install.sh | bash
source ~/.bashrc

The script installs uv, provisions a Python 3.11+ environment, fetches the Hermes package and its Node tooling, and writes the launcher binaries into ~/.local/bin. Expect it to take around five minutes on a fresh VPS. Most of that time is pip and npm resolving dependencies; the network transfer is small.

If you would rather read the script before running it (a sensible habit for any curl-pipe-bash install):

curl -fsSL https://raw.githubusercontent.com/NousResearch/hermes-agent/main/scripts/install.sh -o /tmp/hermes-install.sh
less /tmp/hermes-install.sh
bash /tmp/hermes-install.sh

Verify the install:

hermes --version
hermes doctor

The doctor subcommand checks Python version, Node version, the model provider's reachability, and the disk and memory budget for the current model context size. If any check fails it prints the exact remediation step. Run it again after any change you are not sure about.

First-run setup

Hermes ships an interactive wizard for the first run.

hermes setup

The wizard walks you through the model provider, the model name, the toolset (terminal, file ops, web search, memory), and an optional profile name. If you intend to use OpenRouter, this is the moment to set the key:

# Either via the wizard, or directly:
mkdir -p ~/.hermes
chmod 700 ~/.hermes
echo 'OPENROUTER_API_KEY=sk-or-v1-your-key-here' >> ~/.hermes/.env
chmod 600 ~/.hermes/.env
hermes config set model.provider openrouter
hermes config set model.default anthropic/claude-sonnet-4

The .env file is the single source of truth for credentials. It is read at process start. Treat it like any other secrets file: chmod 600, no version control, no shoulder-readers.

Test the model connection with a single-shot prompt:

hermes -m "What is 2+2? Reply with just the number."

If the reply is "4" with no preamble, the model is wired up correctly. If it errors, run hermes doctor for the precise failure mode.

Before you let the agent loose on the filesystem, set approval mode to ask. The agent will pause and request confirmation before any destructive operation. You can switch this off later when you trust the prompts you have written.

hermes config set approval_mode ask

Connecting a messaging gateway

The gateway is what makes the VPS install interesting. It bridges the agent to messaging platforms, so you can talk to Hermes from your phone instead of an SSH session. Telegram is the easiest first integration because the bot setup is self-service.

A mailbox row of compartments with notes folded inside
The messaging gateway as a mail room. Messages come in, the agent decides where they go, replies fan back out.

To create a Telegram bot, message @BotFather on Telegram, send /newbot, pick a name, and copy the bot token it gives you. Then look up your own numeric user ID (any of the user-info bots will tell you, or open Telegram in a browser and read it from the URL).

Add both to the env file:

echo 'TELEGRAM_BOT_TOKEN=7123456789:AAHx-your-token-here' >> ~/.hermes/.env
echo 'TELEGRAM_ALLOWED_USERS=123456789' >> ~/.hermes/.env

The TELEGRAM_ALLOWED_USERS list is critical. Without it, anyone who finds your bot can talk to the agent on your VPS, with your model API key paying the bill. Always set it.

Optionally, point the agent at a working directory where it is allowed to create files:

mkdir -p /home/hermes/projects
echo 'MESSAGING_CWD=/home/hermes/projects' >> ~/.hermes/.env

Run the gateway in the foreground first to confirm it talks to Telegram:

hermes gateway

Open the Telegram bot in your phone and send "hello". The agent should reply within a few seconds. Press Ctrl+C in the SSH session to stop the gateway. If you see authentication errors, recheck the bot token and the allowed-users list.

Running the gateway as a systemd service

Running the gateway in the foreground is fine for testing. For real use it should be a service that starts on boot and restarts if it crashes. Hermes ships a systemd-user unit for exactly this.

hermes gateway install
systemctl --user daemon-reload
systemctl --user enable --now hermes-gateway
systemctl --user status hermes-gateway

By default, systemd-user services stop when the user logs out. To keep the gateway running after you close the SSH session, enable lingering for the user:

sudo loginctl enable-linger hermes

Watch the logs in real time:

journalctl --user -u hermes-gateway -f

The unit is a thin wrapper around hermes gateway. If you want to inspect or change it:

systemctl --user cat hermes-gateway
systemctl --user edit hermes-gateway

The override drops you into an editor where you can change the Restart= policy, the RestartSec= backoff, or add environment overrides.

Verifying the install

A working install passes four checks. Run them in order.

  1. Doctor. hermes doctor returns all green. Any single red line should be fixed before continuing.
  2. Model. hermes -m "ping" returns a response within a few seconds. If it does not, the model provider key or quota is the most likely cause.
  3. Gateway. The Telegram bot replies to a "hello" message from an allowed user. Non-allowed users are ignored silently.
  4. Service. systemctl --user is-active hermes-gateway returns active. Reboot the VPS, log back in, and re-check; the service should still be active.

If all four pass, the install is done. Bookmark this checklist; it is what you run after every update.

Backups and updates

Hermes Agent stores its memory and configuration under ~/.hermes. Back that up before any update, and on a schedule.

One-shot backup:

hermes backup
# writes ~/.hermes/backups/hermes-YYYY-MM-DD.tar.gz

Schedule a nightly backup via cron. Add the user crontab entry:

(crontab -l 2>/dev/null; echo "0 3 * * * /home/hermes/.local/bin/hermes backup") | crontab -

For real off-site copies, sync the backup directory to S3, Backblaze B2, or another VPS with rclone after the backup runs. A drive failure on the VPS provider is the threat to plan for.

To update Hermes itself:

hermes backup
hermes update
hermes --version
hermes config migrate
hermes doctor
systemctl --user restart hermes-gateway

The config migrate step rewrites any configuration keys that changed shape between versions. Skipping it sometimes works and sometimes breaks the gateway on restart. Always run it.

Troubleshooting

A short list of failures that come up most often, and the first thing to check for each.

The gateway is dead after a reboot

Confirm that you ran loginctl enable-linger hermes. Without lingering, the user's systemd instance shuts down on logout, and the boot brings the box up with no user session attached. The fix is one command and a service restart.

The model returns 401

The API key is wrong, expired or rate-limited. Re-issue from the provider dashboard, edit ~/.hermes/.env, restart the gateway. If you have multiple provider keys, check that model.provider matches the one the active key belongs to.

The bot does not reply

Either the gateway is not running, or the message came from a user not in TELEGRAM_ALLOWED_USERS. Check journalctl --user -u hermes-gateway -f while you send a message; an allowed user generates a log line, a non-allowed user generates nothing visible to a casual reader. The silence is intentional, not a bug.

Out of memory on a 1 GB VPS

You probably enabled a large model context window. The agent allocates buffers proportional to the configured context. Either drop the context window in the config, upgrade to a 2 GB plan, or add 2 GB of swap as a stopgap.

sudo fallocate -l 2G /swapfile
sudo chmod 600 /swapfile
sudo mkswap /swapfile
sudo swapon /swapfile
echo '/swapfile none swap sw 0 0' | sudo tee -a /etc/fstab

Permission denied writing to projects/

The MESSAGING_CWD path must be writable by the hermes user. The most common cause is creating the directory while logged in as root. Fix the ownership:

sudo chown -R hermes:hermes /home/hermes/projects

That is the end of the install. From here the work is in the prompts you give Hermes, the tools you let it use, and the messaging integrations you wire up next. The agent does not care which messaging platform you reach it through, so there is nothing magical about Telegram beyond it being the easiest first step. Slack, Discord and email follow the same shape: get the credential, drop it in ~/.hermes/.env, restart the gateway.

Frequently asked questions
Do I need a GPU? Read

No. Hermes Agent does not run an LLM locally by default. The model lives at a provider (OpenRouter, Anthropic, OpenAI, Nous Portal, MiniMax). The agent process is small and CPU-bound. A GPU is only relevant if you want to point Hermes at a local Ollama or vLLM endpoint, in which case the GPU belongs on that other machine, not this one.

What's the cheapest VPS that works? Read

A 1 vCPU, 1 GB RAM, 10 GB disk Linux VPS. Hetzner CX22, Contabo VPS S, Vultr Cloud Compute and similar plans land around four to five US dollars a month. Pick one with Ubuntu 22.04 LTS or 24.04 LTS, or Debian 12. Avoid distributions older than Python 3.11.

Is the messaging gateway exposed to the internet? Read

No. The gateway makes outbound connections to Telegram, Discord, Slack and the other supported platforms. You do not need to open any inbound ports. SSH (port 22) is the only inbound exception you should permit, and that is for your own administration, not the agent.

Can I use a local Ollama model? Read

Yes. Set OPENAI_BASE_URL to your Ollama endpoint and OPENAI_API_KEY to any non-empty string (Ollama ignores it). Then set LLM_MODEL to the tag you have pulled, for example llama3.1:70b. The Ollama instance does not have to live on the same VPS, and almost certainly should not given the RAM cost of a useful 70B model.

How do I rotate the model provider API key? Read

Edit ~/.hermes/.env and replace the key value, then restart the gateway with <code>systemctl --user restart hermes-gateway</code>. The agent reads the env file at process start. If you have multiple gateway instances running for separate messaging platforms, restart each one.

What happens to memory when I rebuild the VPS? Read

Run <code>hermes backup</code> before the rebuild. It writes a tarball containing the agent's persistent memory, configuration, and any custom prompts. After the install on the new box, run <code>hermes import /path/to/backup.tar.gz</code> and the agent picks up where it left off. Without a backup, the new install starts from a blank slate.

Can I run multiple gateways for different messaging platforms? Read

Yes. The gateway speaks to multiple platforms from a single process by default. If you prefer process isolation (one gateway per platform, one systemd unit per gateway), the documentation supports that pattern via per-instance config directories. For most operators a single gateway is fine.

Glossary terms used in this guide
systemd SSH UFW journalctl curl OpenRouter Anthropic Ollama VPS DNS TLS OpenAI
Continue reading
PERFORMANCE · Updated Jun 2026

Content Delivery Networks: A Complete Guide

How CDNs make the web fast, how they actually work, and how to pick one

RFC grounded
SECURITY · Updated Jun 2026

DDoS Protection: A Complete Guide

How modern attacks work, what defences actually scale, and how to choose protection

RFC grounded
INFRASTRUCTURE · Updated Jun 2026

Object storage explained: S3, R2, B2 and self-hosted MinIO

A reference for picking an object storage provider, understanding the egress trap, and knowing the parts of the S3 API that actually matter.

RFC grounded

Who Is Online

In total there are 53 users online: 0 registered, 47 guests and 6 bots.

Most users ever online was 5,555 on 17 Jul 2026, 3:23 am.

Bots: Applebot Baiduspider Other Bot Other Crawler PetalBot SemrushBot

Users active in the past 15 minutes. Total registered members: 369