
September 09, 2026
11 min read
By Kokil Thapa | Last reviewed: September 2026
Production outages rarely announce themselves. You notice them when a client calls or a payment webhook fails. Monitoring with Prometheus and Grafana: Complete Setup gives you a pull-based metrics stack that watches CPU, memory, HTTP latency, queue depth, and database health before users feel pain. Prometheus collects time-series data. Grafana turns it into dashboards and alerts. This guide walks through a production-ready install on Ubuntu 24.04 for the PHP and Laravel stacks I maintain daily.
What does Monitoring with Prometheus and Grafana: Complete Setup include?
A complete stack has four layers. Prometheus pulls metrics from exporters and your app. Alertmanager routes firing alerts. Grafana queries Prometheus for charts. Node Exporter exposes host stats. This differs from push tools like NetData, which you can read about in our NetData zero-config monitoring guide.
Prometheus uses a pull model. It requests /metrics endpoints on a fixed interval. That keeps apps simple. They expose numbers; Prometheus handles storage and queries. Grafana never talks to exporters directly. It always queries Prometheus through PromQL.
Core components at a glance
- Prometheus server — scrapes targets, evaluates alert rules, stores time-series data on disk.
- Exporters — translate system or app state into Prometheus text format.
- Grafana — dashboards, variables, and optional unified alerting.
- Alertmanager — deduplicates, groups, and routes notifications.
- Service discovery — optional; static configs work fine for small fleets.
How do you install Prometheus and Grafana on Ubuntu?
Start on a dedicated monitoring VM or the same server you watch. Separate hosts reduce blast radius. For sister sites on shared EC2, I run one Prometheus instance per environment. Use a non-root user and systemd units for clean restarts after deploys.
Install Prometheus 3.x
- Create a system user and directories:
sudo useradd --no-create-home --shell /usr/sbin/nologin prometheus
sudo mkdir -p /etc/prometheus /var/lib/prometheus
sudo chown prometheus:prometheus /etc/prometheus /var/lib/prometheus Download the latest stable release from the official Prometheus download page. Extract binaries to /usr/local/bin/.
curl -LO https://github.com/prometheus/prometheus/releases/download/v3.2.1/prometheus-3.2.1.linux-amd64.tar.gz
tar xvf prometheus-3.2.1.linux-amd64.tar.gz
sudo cp prometheus-3.2.1.linux-amd64/prometheus /usr/local/bin/
sudo cp prometheus-3.2.1.linux-amd64/promtool /usr/local/bin/ Create /etc/prometheus/prometheus.yml:
global:
scrape_interval: 15s
evaluation_interval: 15s
alerting:
alertmanagers:
- static_configs:
- targets: ['localhost:9093']
rule_files:
- /etc/prometheus/rules/*.yml
scrape_configs:
- job_name: 'prometheus'
static_configs:
- targets: ['localhost:9090']
- job_name: 'node'
static_configs:
- targets: ['app1.example.com:9100', 'app2.example.com:9100']
- job_name: 'mysql'
static_configs:
- targets: ['db.example.com:9104'] Add a systemd unit at /etc/systemd/system/prometheus.service:
[Unit]
Description=Prometheus
After=network-online.target
[Service]
User=prometheus
Group=prometheus
ExecStart=/usr/local/bin/prometheus \
--config.file=/etc/prometheus/prometheus.yml \
--storage.tsdb.path=/var/lib/prometheus \
--web.listen-address=127.0.0.1:9090
Restart=always
[Install]
WantedBy=multi-user.target Bind Prometheus to localhost. Put Nginx or Apache in front with TLS. Our Let's Encrypt and Certbot HTTPS guide covers the certificate side.
Install Grafana 11.x
sudo apt-get install -y apt-transport-https software-properties-common
sudo add-apt-repository "deb https://packages.grafana.com/oss/deb stable main"
wget -q -O - https://packages.grafana.com/gpg.key | sudo apt-key add -
sudo apt-get update
sudo apt-get install grafana
sudo systemctl enable --now grafana-server Grafana listens on port 3000 by default. Change the admin password on first login. Add Prometheus as a data source at Configuration → Data sources → Prometheus with URL http://127.0.0.1:9090.
Which exporters should you scrape for a Laravel production stack?
Host metrics alone miss app-level failures. A server can show 30% CPU while every queue job stalls. Layer exporters so you see the full picture from metal to business logic.
Node Exporter on every app server
curl -LO https://github.com/prometheus/node_exporter/releases/download/v1.9.0/node_exporter-1.9.0.linux-amd64.tar.gz
tar xvf node_exporter-1.9.0.linux-amd64.tar.gz
sudo cp node_exporter-1.9.0.linux-amd64/node_exporter /usr/local/bin/
sudo useradd --no-create-home node_exporter
sudo tee /etc/systemd/system/node_exporter.service <<'EOF'
[Unit]
Description=Node Exporter
[Service]
User=node_exporter
ExecStart=/usr/local/bin/node_exporter --web.listen-address=127.0.0.1:9100
Restart=always
[Install]
WantedBy=multi-user.target
EOF
sudo systemctl enable --now node_exporter Watch node_memory_MemAvailable_bytes, node_filesystem_avail_bytes, and rate(node_cpu_seconds_total[5m]). Disk full errors kill Laravel logs and MySQL before CPU spikes.
MySQL, Redis, and Nginx exporters
For MySQL 9.7 or 8.4 LTS, run mysqld_exporter with a read-only monitoring user. Point it at port 9104. Redis 8.10 uses redis_exporter on 9121. Nginx needs the stub_status module plus nginx-prometheus-exporter.
On booking platforms like Adventure Third Pole Trek, queue backlog and DB connection counts matter more than raw CPU. Tie those metrics to user-facing symptoms.
Application metrics from Laravel
Install promphp/prometheus_client_php or expose a custom /metrics route behind IP allowlisting. Track HTTP request duration histograms, failed login counts, and queue job failures. Validate the route with our JSON formatter tool when debugging structured log payloads alongside metrics.
Never expose /metrics publicly without auth. Scrape over VPN or private network only. Prometheus should reach the target; the internet should not.
How do Prometheus and Grafana compare to other monitoring tools?
Teams often ask whether to adopt Prometheus or stick with Nagios, NetData, or a SaaS APM. Each fits a different ops maturity and team size.
| Tool | Model | Best for | Trade-off |
|---|---|---|---|
| Prometheus + Grafana | Pull, PromQL, self-hosted | Multi-service fleets, custom metrics, alert tuning | You operate storage, upgrades, and HA yourself |
| Nagios | Push/check scripts | Simple up/down checks, legacy shops | Weak time-series; clunky dashboards |
| NetData | Push, per-host agent | Fast visibility on one server | Harder to centralise across many hosts |
| SaaS APM (Datadog, etc.) | Agent + cloud | Teams without ops headcount | Cost scales with hosts; Rs 15,000+/month (~USD 110) adds up |
For ongoing server support contracts, Prometheus wins when you already run GitLab CI and Deployer. Metrics sit beside the same infrastructure you patch weekly. Read our Prometheus and Grafana full monitoring stack article for a lighter single-server variant.
How do you build Grafana dashboards and Prometheus alert rules?
Dashboards without alerts are vanity. Alerts without runbooks wake people at 2 AM for nothing. Start with four golden signals: latency, traffic, errors, and saturation.
Import community dashboards first
Grafana.com hosts dashboard IDs you can import. Use 1860 for Node Exporter Full, 7362 for MySQL overview, and 11835 for Redis. Tweak panel thresholds to match your hardware. A 2 GB VPS behaves differently from a 16 GB production node.
Write alert rules that page humans sparingly
Store rules in /etc/prometheus/rules/alerts.yml:
groups:
- name: host_alerts
rules:
- alert: HostDown
expr: up{job="node"} == 0
for: 2m
labels:
severity: critical
annotations:
summary: "Node exporter down on {{ $labels.instance }}"
- alert: DiskSpaceLow
expr: node_filesystem_avail_bytes{mountpoint="/"} / node_filesystem_size_bytes{mountpoint="/"} < 0.10
for: 5m
labels:
severity: warning
annotations:
summary: "Less than 10% disk free on {{ $labels.instance }}"
- alert: HighErrorRate
expr: rate(http_requests_total{status=~"5.."}[5m]) / rate(http_requests_total[5m]) > 0.05
for: 3m
labels:
severity: critical
annotations:
summary: "5xx rate above 5% on {{ $labels.instance }}" Install Alertmanager and point Prometheus at it. Route severity=critical to SMS or phone. Send warnings to Slack only. Full routing patterns live in our Alertmanager alerting guide.
Validate before you trust a dashboard
Run load tests or trigger a known failure. Confirm the graph moves and the alert fires within your for window. I've seen teams deploy Grafana panels that query the wrong job label for months. Use promtool check rules and promtool test rules in CI.
What production mistakes break Prometheus and Grafana setups?
Most failures I debug are config issues, not Prometheus bugs. The stack is stable when you respect retention, security, and label cardinality.
Cardinality explosions
Never put user IDs or order IDs in metric labels. Each unique label combination creates a new time series. A burst of label values can OOM Prometheus in minutes. Keep labels to environment, service, endpoint, and status code.
Scrape targets behind firewalls
Prometheus must reach each exporter. If your app servers sit behind UFW, allow port 9100 from the monitoring host IP only. Document the rule alongside SSH hardening from our SSH key-only auth guide.
Forgetting retention and backups
Default TSDB retention is 15 days. Set --storage.tsdb.retention.time=30d if disk allows. Prometheus data is not a backup. Pair metrics with nightly DB dumps covered in our automated server backups guide.
After every Deployer symlink swap, confirm PHP-FPM and queue workers still expose metrics. Opcache resets should not break scrape paths. Our Laravel queues with Redis production guide pairs well with queue-depth alerts.
For legal-tech portals like Notary Nepal, uptime during business hours matters most. Set maintenance windows in Alertmanager so planned deploys do not page the team. Document who responds and what "rollback" means.
Enterprise clients evaluating enterprise application development often ask for observability in the SOW. Prometheus plus Grafana satisfies that without locking you into proprietary agents.
Key Takeaways
- Install Prometheus on a dedicated or co-located host; bind it to localhost and reverse-proxy Grafana with TLS.
- Scrape Node Exporter, database exporters, and a secured Laravel
/metricsroute — host CPU alone is not enough. - Import Grafana dashboard 1860 first, then add alert rules for
up==0, disk space, and 5xx error rates. - Keep label cardinality low; never expose metrics endpoints to the public internet.
- Pair the stack with log review, backups, and a runbook — dashboards detect problems, they do not fix them.
- Validate rules with
promtooland test alerts before trusting them overnight.
People Also Ask
Do Prometheus and Grafana work with Laravel 13?
Yes. Laravel 13 runs on PHP 8.3 or higher. Expose metrics via a package or custom route. Scrape it like any other target. Framework version does not change the Prometheus pull model.
How much RAM does Prometheus need?
Budget 1–2 GB for a small fleet of five targets with moderate cardinality. High-cardinality apps need 4 GB or more. Watch TSDB head blocks with prometheus_tsdb_head_series.
Can Grafana send alerts without Alertmanager?
Grafana has built-in alerting that can notify Slack or email. For Prometheus-native rules, Alertmanager remains the standard. Many teams use both: Prometheus rules for infra, Grafana alerts for business KPIs.
Is Prometheus free for commercial use?
Yes. Prometheus and Grafana OSS are open source under Apache 2.0. You pay for compute, storage, and the time to operate them. Grafana Labs also sells Enterprise tiers with SSO and reporting if you outgrow OSS.
Ship observability before the next outage
Monitoring with Prometheus and Grafana: Complete Setup is not a weekend side project. It is baseline infrastructure for any Laravel or WordPress fleet you expect to run past launch day. Start with one app server, Node Exporter, and three alert rules. Expand to MySQL, Redis, and custom app metrics as traffic grows.
If you want the stack designed, installed, and tied into your existing Ubuntu server monitoring workflow, contact us for a scoped setup. You can also browse testing and optimization services or see live platforms in the portfolio. For related reading, see API monitoring with Prometheus and Grafana and Grafana dashboards practical guide. Strong metrics turn 3 AM guesswork into a five-minute fix.
Frequently Asked Questions
0 Comments
Leave a comment
Your email is not published. Comments appear once they have been read. Sign in to have your details filled in.

