Blazor VPS hosting

Blazor Server hosting on UpCloud with Nginx and HTTPS

Last Update 4/11/2026

Use this guide when a small Blazor Server app needs its own Ubuntu VPS instead of a managed platform. It covers the real work: DNS, SSH, .NET, Nginx, TLS, service restarts, backups, and the ongoing cost of owning the server.

The starting point is a simple UpCloud server at approx. $3/month. That can be enough for a modest production launch, but only if you keep patching, monitoring, log rotation, and rollback habits simple and repeatable.

UpCloud promo note: you and we each receive $29 in credits. Your monthly server price is not increased by the referral link.

Quick answer

Use a VPS when control matters more than platform comfort

A small UpCloud VPS is a good fit when you want stable costs, full Linux access, custom Nginx rules, direct logs, and a deployment flow you can inspect. It is a poor fit when you do not want to patch Ubuntu, watch disk space, test backups, or debug systemd at awkward times.

Domain and DNS SSH key access Nginx with TLS You own operations

Fit check

A cheap Blazor VPS is useful only when the operating work is acceptable

The server price is not the whole decision. Count the time for updates, firewall rules, certificates, restores, logs, monitoring, and failed deploys before you choose self-hosting for a production app.

Good fit

Choose this path when you want control

  • You want full control over Nginx, systemd, SSH, logs, files, and runtime versions.
  • The app is modest enough to start on a small VPS and scale later from a snapshot or rebuild.
  • You can handle Ubuntu updates, firewall rules, certificates, backups, restores, and monitoring.
  • You need predictable monthly infrastructure costs more than managed platform convenience.
Poor fit

Choose managed hosting when operations are the risk

  • No one owns patching, backups, uptime checks, disk pressure, or incident response.
  • The app needs managed scaling, managed databases, deployment slots, and platform support from day one.
  • Non-technical teammates must deploy and recover the app without touching Linux.
  • A short outage would be more expensive than a managed hosting bill.

Before setup

Prepare domain, DNS, SSH, .NET, Nginx, and TLS decisions first

Most failed VPS launches are not caused by Blazor. They happen because DNS is not ready, SSH access is unclear, ports are blocked, the app path is improvised, or certificate setup starts before the domain points at the server.

DNS prerequisite

Point DNS before TLS

Create the A or AAAA record for the final host name before running Certbot. Certificate validation needs the public name to resolve correctly.

SSH access

Use SSH keys and a deploy user

Start with key-based access, avoid routine root uploads, and decide which user owns the app directory before the first release.

.NET runtime

Choose where publishing happens

Install the ASP.NET Core runtime on the VPS. Add the full .NET SDK only when you intentionally build or publish on the server.

Server plan

Start with the approx. $3/month server only when the app is modest

The smallest plan is a launch baseline, not a promise. It works best for low to moderate traffic, mostly static assets behind Nginx, lightweight database use elsewhere, and a team that can scale before memory or CPU pressure becomes user-visible.

Plan reference approx. $3
Use it for
Small production apps, staging apps, internal dashboards, prototypes with real users, and low-traffic content sites.
Avoid it for
Memory-heavy apps, noisy background jobs, large local databases, high traffic spikes, or teams without server maintenance time.
Upgrade signal
Scale when swap usage, CPU saturation, queue delays, or restart frequency becomes visible in logs and user timings.
01

Create the server

Choose the nearest useful region, a clean Ubuntu image, SSH keys, and the smallest plan that matches your launch risk.

02

Lock the network

Allow SSH, HTTP, and HTTPS. Keep databases, dashboards, and app ports private unless there is a specific reason.

03

Take a baseline snapshot

Snapshot the server after hardening and before the first production deploy so rebuilds are faster and less stressful.

04

Document the rebuild

Keep the DNS, package, firewall, app path, service name, and certificate steps in a short runbook.

Server setup

Patch Ubuntu, keep the public surface small, and install .NET deliberately

Start from a clean Ubuntu image. Apply updates, keep timestamps predictable, install only the packages you need, and open just SSH, HTTP, and HTTPS. The SDK is optional on the server when you publish from your workstation or CI.

Base packages

Shell
sudo apt update && sudo apt upgrade -y
sudo apt install -y curl wget unzip apt-transport-https ca-certificates gnupg
sudo timedatectl set-timezone UTC

Firewall and fail2ban

Shell
sudo apt install -y ufw fail2ban
sudo ufw default deny incoming
sudo ufw default allow outgoing
sudo ufw allow ssh
sudo ufw allow http
sudo ufw allow https
sudo ufw enable
sudo systemctl enable --now fail2ban

.NET packages

Shell
wget https://packages.microsoft.com/config/ubuntu/24.04/packages-microsoft-prod.deb -O packages-microsoft-prod.deb
sudo dpkg -i packages-microsoft-prod.deb
rm packages-microsoft-prod.deb
sudo apt update
sudo apt install -y aspnetcore-runtime-8.0

Deploy flow

Publish locally, upload predictably, and let systemd own the app process

For a small server, the safest manual deploy is simple: build a Release output, upload it to a known directory, run the app as a dedicated user, and make systemd responsible for restart behavior and logs.

Publish and upload

Shell
# Build locally
dotnet publish -c Release -o publish

# Copy to UpCloud (replace user@host)
rsync -avz --delete publish/ user@YOUR_UPCLOUD_IP:/var/www/blazor-app/releases/current/

# On the server, set ownership
sudo useradd -m -s /bin/bash blazorapp || true
sudo chown -R blazorapp:blazorapp /var/www/blazor-app

systemd service

systemd
[Unit]
Description=Blazor Server on UpCloud
After=network.target

[Service]
User=blazorapp
WorkingDirectory=/var/www/blazor-app/releases/current
ExecStart=/usr/bin/dotnet /var/www/blazor-app/releases/current/YourApp.dll --urls http://127.0.0.1:5001
Restart=always
RestartSec=5
Environment=ASPNETCORE_URLS=http://127.0.0.1:5001

[Install]
WantedBy=multi-user.target

Nginx and TLS

Put Kestrel behind Nginx and make HTTPS the only public path

Kestrel should listen on localhost. Nginx receives public traffic, redirects HTTP to HTTPS, terminates TLS, forwards the original host and protocol, and keeps the URL stable for users and search crawlers.

Nginx reverse proxy

nginx
server {
    listen 80;
    listen [::]:80;
    server_name app.example.com;
    return 301 https://$host$request_uri;
}

server {
    listen 443 ssl http2;
    listen [::]:443 ssl http2;
    server_name app.example.com;

    ssl_certificate     /etc/letsencrypt/live/app.example.com/fullchain.pem;
    ssl_certificate_key /etc/letsencrypt/live/app.example.com/privkey.pem;

    add_header Strict-Transport-Security "max-age=63072000; includeSubDomains" always;

    location / {
        proxy_pass         http://127.0.0.1:5001;
        proxy_http_version 1.1;
        proxy_set_header   Upgrade $http_upgrade;
        proxy_set_header   Connection "keep-alive";
        proxy_set_header   Host $host;
        proxy_set_header   X-Real-IP $remote_addr;
        proxy_set_header   X-Forwarded-For $proxy_add_x_forwarded_for;
        proxy_set_header   X-Forwarded-Proto $scheme;
        proxy_cache_bypass $http_upgrade;
    }
}

Certbot commands

Shell
sudo apt install -y certbot python3-certbot-nginx
sudo certbot --nginx -d app.example.com --redirect --agree-tos -m [email protected]
sudo certbot renew --dry-run

Operations

Keep costs honest by planning maintenance before traffic arrives

The monthly VPS bill is predictable. The operations cost is not unless you make it routine: maintenance windows for patching, certificate renewal checks, log rotation, disk alerts, snapshots, restore tests, and a short rollback process for failed releases.

Ubuntu updates

Patch on a schedule

Run package updates during a planned window, then check the Blazor service, Nginx status, and certificate renewal path.

Backup restores

Test restore, not just snapshot creation

Snapshots are useful only when you have restored one. Keep app files, secrets, and database backups in the recovery plan.

Server logs

Watch for quiet failures

Use journalctl, Nginx logs, disk alerts, and uptime checks so failed deploys or bot traffic do not stay invisible.

VPS scaling

Scale before users feel it

Move to a larger plan, split services, add a CDN, or clone from a snapshot before memory pressure becomes downtime.

SEO reality

Hosting helps SEO only when the basics stay stable

A VPS does not create rankings by itself. It helps when it gives you stable URLs, fast first responses, correct HTTPS redirects, clean metadata, matching JSON-LD, and fewer outages than the cheaper workaround you were using before.

01

HTTPS redirects

Redirect HTTP once, keep certificates renewing, and avoid mixed-content assets that make pages look broken.

02

Stable URLs

Use human-readable routes, keep canonical URLs consistent, and avoid deployment paths that change after every release.

03

VPS performance

Measure TTFB, cache static assets through Nginx, compress responses, and keep the first page load boringly fast.

04

SEO metadata

Keep title, H1, description, Open Graph image, Article schema, BreadcrumbList, and FAQPage schema aligned with visible content.

Automation option

Use GhostlyHosting when repeating the manual setup is the risky part

Manual setup is useful when you want to understand every moving part. If you already know the stack and want a guided repeatable deploy path, GhostlyHosting can automate the Ubuntu, Nginx, SSL, GitHub, and service-management workflow.

FAQ

Can I host Blazor Server on UpCloud for approx. $3/month?

Yes, for a modest app with careful expectations. The entry plan can handle a small launch, staging environment, or internal tool, but you still need monitoring, backups, patching, and a scale-up plan.

Do I need the full .NET SDK on the VPS?

Usually no. Install the ASP.NET Core runtime when you publish from your workstation or CI. Install the SDK only when the server intentionally builds or publishes the app.

Should Kestrel be exposed directly to the internet?

No. Bind Kestrel to localhost and expose Nginx on ports 80 and 443. Nginx handles TLS, redirects, proxy headers, and the public URL surface.

What are the biggest risks of cheap Blazor VPS hosting?

The common risks are unpatched packages, expired certificates, weak SSH hygiene, missing backups, disk pressure, noisy logs, and no one noticing when the service restarts repeatedly.

Does VPS hosting improve Blazor SEO?

Only when the setup improves fundamentals: stable HTTPS URLs, fast responses, clean metadata, matching JSON-LD, uptime, and predictable redirects. Hosting alone is not an SEO shortcut.

When should I use GhostlyHosting instead of doing this by hand?

Use manual setup to learn or audit the stack. Use GhostlyHosting when you want a repeatable Ubuntu, Nginx, SSL, GitHub, and service-management workflow after you understand the moving parts.