> For the complete documentation index, see [llms.txt](https://docs.hivel.ai/llms.txt). Markdown versions of documentation pages are available by appending `.md` to page URLs; this page is available as [Markdown](https://docs.hivel.ai/self-managed-hivel-deployment/on-premises-generic/tl-dr-on-premises.md).

# TL;DR (On-Premises)

### On-Premises Quick Deployment Guide

Deploy Hivel on your own infrastructure (bare metal, VM, or any cloud instance) using Docker for services and self-managed PostgreSQL for the database. This condensed version covers all steps without omitting any part of the process.

Refer to the [full On-Premises Setup Guide](https://docs.hivel.ai/self-managed-hivel-deployment/on-premises-generic/hivel-on-premises-deployment-guide-generic) for additional context or troubleshooting.

#### Prerequisites

{% hint style="warning" %}
Before starting, you must have:

* A host (VM, bare metal, or cloud instance): 4 vCPU, 16GB RAM or larger (roughly a t3.xlarge), Ubuntu 22.04 LTS, 50GB+ disk
* Hivel-issued AWS Access Key ID and Secret Access Key for ECR registry access
* S3 bucket path or pre-signed URL for the `hivel-onprem` installer package
* Hivel license file: `license_signed.json`

If you don't have these items, contact <support@hivel.ai> before starting.
{% endhint %}

#### Step 1: Provision the Host

**Location:** Your hypervisor, data center, or cloud console (AWS, Azure, GCP, etc.)

Create a host with:

* 4 vCPU, 16GB RAM or larger
* Ubuntu 22.04 LTS
* 50GB+ available disk storage
* Open inbound ports: 22, 80, 3000, 4317 (only while integrating Claude Code), 5432
* Record the host's **private IP address** (needed later)

Contact your Hivel representative if you expect high integration or commit volume.

#### Step 2: Install Docker, Docker Compose, AWS CLI, and PostgreSQL

**Location:** The host (via SSH)

Run:

```bash
# Update system
sudo apt update && sudo apt upgrade -y
sudo apt install -y postgresql postgresql-contrib
sudo apt install -y unzip

# Install Docker
curl -fsSL https://get.docker.com -o get-docker.sh
sudo sh get-docker.sh
sudo usermod -aG docker $USER

# Install Docker Compose
sudo curl -L "https://github.com/docker/compose/releases/latest/download/docker-compose-$(uname -s)-$(uname -m)" -o /usr/local/bin/docker-compose
sudo chmod +x /usr/local/bin/docker-compose

# Install AWS CLI (needed only for the registry pull step, next)
curl "https://awscli.amazonaws.com/awscli-exe-linux-x86_64.zip" -o "awscliv2.zip"
unzip awscliv2.zip
sudo ./aws/install

# Verify installations
docker --version
docker-compose --version
aws --version
```

Log out and back in for Docker group membership to take effect.

**Required versions:** Docker ≥ 26.0, Docker Compose ≥ 2.25.0, AWS CLI v2.x

> If `docker ps` still requires `sudo`, run `newgrp docker` or reboot, then retry.

#### Step 3: Configure AWS CLI

**Location:** The host

Run:

```bash
aws configure
# AWS Access Key ID:     [Hivel-provided access key]
# AWS Secret Access Key: [Hivel-provided secret key]
# Default region name:   ap-south-1
# Default output format: json

# Verify
aws sts get-caller-identity
```

Expect a JSON response with Account, UserId, and Arn fields. If credential errors occur, check `cat ~/.aws/credentials`.

#### Step 4: Set Up PostgreSQL and Create the `insightly` Database

**Location:** The host (or a dedicated database host for production)

For production, Hivel recommends a dedicated database host with its own backup routine. Set up regular `pg_dump` cron jobs before production.

Run:

```bash
sudo apt update
sudo apt install -y postgresql postgresql-contrib
sudo systemctl enable postgresql
sudo systemctl start postgresql
```

**Supported versions:** PostgreSQL 12, 13, 14, or 15

Set the superuser password:

```bash
sudo -u postgres psql -c "ALTER USER postgres WITH PASSWORD 'your_strong_superuser_password';"
```

Configure PostgreSQL for remote connections. Edit `/etc/postgresql/<version>/main/postgresql.conf`:

```
listen_addresses = '*'
```

Edit `/etc/postgresql/<version>/main/pg_hba.conf` to allow connections only from your host:

```
host insightly all <HOST_PRIVATE_IP>/32 scram-sha-256
```

Replace `<HOST_PRIVATE_IP>` with the private IP from Step 1. Restart and configure firewall:

```bash
sudo systemctl restart postgresql
sudo ufw allow from <HOST_PRIVATE_IP> to any port 5432
```

Create the application database:

```bash
sudo -u postgres psql -c "CREATE DATABASE insightly;"
```

Verify connectivity:

```bash
psql -h <HOST_PRIVATE_IP> -U postgres -d insightly
```

Success: you see the `insightly=#` prompt with no errors.

**Record for later:** database host/IP, port `5432`, superuser `postgres`, and the password you set.

#### Step 5: Download the Installer and Add the License File

**Location:** The host

Run:

```bash
cd /opt

aws s3 cp s3://hivel-on-prem-logs/hivel-agent-onprem-deploy/hivel-onprem.zip ./

unzip hivel-onprem.zip
cd hivel-onprem
chmod +x deploy.sh
```

Verify `ls` shows: `deploy.sh`, `config/`, `license/`, `services/`, and `scripts/` directories.

If the AWS CLI download fails with "Access Denied," confirm with Hivel support that your credentials cover both ECR and S3 read access.

Copy your license files:

<pre><code><a data-footnote-ref href="#user-content-fn-1"># Copy license files into the license directory</a>
cp license_signed.json license/
cp hivel_onprem_public.pem license/
# Verify
ls -l license/
</code></pre>

> The source page says `cp license_signed.json docker-onprem-installer/license/`, but the package you just extracted is `hivel-onprem/` (per the commands above), there is no `docker-onprem-installer/` directory.  Flagged for the docs team, the command above uses the current directory name.

#### Step 6: Test AWS ECR Access

**Location:** The host

Run:

```bash
aws ecr get-login-password --region ap-south-1 | \
  docker login --username AWS --password-stdin \
  730335373269.dkr.ecr.ap-south-1.amazonaws.com
```

Expected result: `Login Succeeded`.

If your organization prohibits direct AWS ECR access, you can mirror Hivel's images into your own private registry (Harbor, Nexus, GitLab Registry, etc.) instead, updating the `ECR_REGISTRY` and `AWS_REGION` variables in `services/vm/docker-compose.yml` and `deploy.sh`.

### Step 7: Configure the Environment File, Phase 1 (Superuser Credentials)

**Run on: the host**

```bash
cd /opt/hivel-onprem
cp config/.env.template config/.env
nano config/.env
```

Set:

```
DB_HOST=<host-running-postgres-private-ip>
DB_PORT=5432
DB_NAME=insightly
DB_USER=postgres
DB_PASSWORD='your_superuser_password'
```

> **Password rules:** Wrap passwords containing `()[]$&|;#<>*` or spaces in single quotes. Write literal `$` as `$$`. Literal single quotes are not allowed.

#### Step 8: Test the Database Connection

**Location:** The host

Run:

```bash
sudo apt update && sudo apt install -y postgresql-client

psql -h $DB_HOST -U $DB_USER -d $DB_NAME -p $DB_PORT
# or
export PGPASSWORD='your_password'
psql -h $DB_HOST -U $DB_USER -d $DB_NAME -p $DB_PORT
```

Expect: `insightly=#` prompt with no errors. Do not continue until this works.

#### Step 9: Run the Database Migration

**Location:** The host

This runs once only, before any other services start. Confirm `.env` contains Phase 1 (superuser) credentials:

```bash
cat config/.env | grep DB_USER
cat config/.env | grep DB_PASSWORD
```

Ensure Docker is ready:

```bash
sudo groupadd docker
sudo usermod -aG docker $USER
newgrp docker
docker run hello-world
```

If `docker run hello-world` still fails, log out and back in, then retry. Once Docker works, run the migration:

```bash
./deploy.sh --service flyway-migration
```

Wait 1 to 2 minutes for completion, then verify:

```bash
docker logs flyway-migration
docker inspect flyway-migration --format='{{.State.ExitCode}}'
docker ps -a | grep flyway-migration
```

Success: exit code `0`, logs showing "Successfully applied X migration(s)" and application user created, container status "Exited (0)". Do not proceed if migration failed.

#### Step 10: Switch the Environment File to Application Credentials (Phase 2)

**Location:** The host

Run:

```bash
nano config/.env
```

Update:

```
DB_USER=<user>
DB_PASSWORD='<your app-user password>'
```

The application user and default password are created automatically by flyway-migration (Hivel provides the default password separately). Change the password before production and never commit a real password to source control.

#### Step 11: Deploy All Services

**Location:** The host

Run:

```bash
cd /opt/hivel-onprem

./deploy.sh --vm            # deploy all services on this host
./deploy.sh --service auth-svc   # or deploy a specific service
```

> Contact <support@hivel.ai> for the full list of services.

Verify all services are up:

Available `deploy.sh` commands:

```bash
./deploy.sh --all       # Deploy all services on one instance
./deploy.sh --vm        # Deploy the host
./deploy.sh --service <name>  # Deploy a specific service
./deploy.sh --status    # Check status
./deploy.sh --health    # Check health
./deploy.sh --logs      # View logs
./deploy.sh --logs <service>  # View logs for one service
./deploy.sh --start     # Start services
./deploy.sh --stop      # Stop services
./deploy.sh --restart   # Restart services
./deploy.sh --update    # Pull latest images
./deploy.sh --list      # List all services
./deploy.sh --help      # Show help
```

For manual control, use Docker Compose directly instead of `deploy.sh` (advanced option).

#### Step 12: Set Up Log Rotation

**Location:** The host

Run:

```bash
sudo ./scripts/setup-log-rotation.sh

# Verify
sudo crontab -l
```

This creates `/var/log/hivel/`, adds a daily cron job at midnight, and configures 7-day log retention. Logs appear at `/var/log/hivel/<service-name>/<service-name>-YYYY-MM-DD.log`.

#### Step 13: Verify the Deployment

**Location:** The host (command line), then a browser

Run:

```bash
docker ps
./deploy.sh --health
./deploy.sh --health auth-svc

# Test service endpoints
curl http://localhost:80/health            # API Gateway
curl http://localhost:8095/health          # Auth Service
curl http://localhost:8082/hivelapi/health # Insightly Service
curl http://localhost:3000                 # UI
```

All containers should show `Up`/`healthy` and each endpoint should return a healthy response.

**In your browser,** access the app using one option:

* **Direct host IP** (testing only, no HTTPS): `http://<host-ip>:3000`
* **Your own load balancer/reverse proxy** (advanced): place one in front on ports 80 and 3000
* **Caddy with automatic HTTPS** (recommended for production): see Step 14

Deployment is complete when: all containers are healthy, all endpoints return healthy responses, the UI loads with no console errors, and at least one integration (Jira, GitHub, or GitLab) is connected and shows data after Step 15.

#### Step 14 (Optional but Recommended): Enable HTTPS with Caddy

**Locations:** DNS provider → Firewall/security group → The host

The Hivel UI serves plain HTTP on port 3000. Browsers restrict `crypto.randomUUID` (used on the sign-up page) to secure contexts (HTTPS or localhost). Accessing `http://<host-ip>:3000` directly will fail sign-up.

**In your DNS provider:**\
Create an A record pointing your subdomain (e.g., `hivel.yourcompany.com`) to the host's public/reachable IP.

**In your firewall/security group:**\
Open port 80 (for Let's Encrypt HTTP-01 validation) and port 443 (HTTPS).

**On the host via SSH:**

```bash
mkdir -p ~/caddy && cd ~/caddy
cat > Caddyfile <<'EOF'
hivel.yourcompany.com {
  reverse_proxy localhost:3000
}
EOF
docker run -d --name caddy --restart unless-stopped --network host \
  -v $(pwd)/Caddyfile:/etc/caddy/Caddyfile \
  -v caddy_data:/data \
  caddy:2

# Verify
docker logs -f caddy
```

Wait for a log line confirming the certificate was obtained. Open `https://hivel.yourcompany.com` in a browser.

> **No domain yet?** Use a self-signed certificate for testing only (never production). Replace the domain block with `tls internal`. See the full guide's HTTPS Setup with Caddy page (Option B) for details on upgrading to a real domain later.

**Manage the container later:**`docker logs -f caddy`, `docker restart caddy`, `docker stop caddy`, `docker rm -f caddy` .The app remains reachable on `:3000` directly. Certificates persist in the `caddy_data` volume.

#### Step 15: Sign Up and Connect Integrations

**Location:** A browser, against the Hivel UI

1. Go to `http://<host-ip>:3000/signup` (or your HTTPS domain).
2. Enter your email, create a password, and verify your email address.
3. Log in. You'll be redirected to the Company Profile Creation page.
4. Fill in your organization's details, select an approval method for new users, and continue.
5. On the Integration Setup page, connect the tools you need.

**Integration examples:**

* **GitLab:** your GitLab domain URL, access-token user's name and email, your GitLab access token, API version `/api/v4`. Verify under **Settings > Repository** in Hivel; you should see repositories being analyzed.
* **Jira:** your Jira URL (Cloud: `https://yourcompany.atlassian.net`), access-token user's name and email, your Jira access token, API version `/rest/api/3/`.
* **SonarQube:** your SonarQube instance URL and access token.

***

See the [Integrations page](https://docs.hivel.ai/integrations) for the full list of supported integrations.

{% content-ref url="/pages/0DjYyMycz6IX42k8sXub" %}
[Integrations](/integrations.md)
{% endcontent-ref %}

Initial data sync time depends on historical data volume. For issues, see the [full guide's Troubleshooting section](https://docs.hivel.ai/self-managed-hivel-deployment/on-premises-generic/hivel-on-premises-deployment-guide-generic/troubleshooting) or contact <support@hivel.ai>.

{% content-ref url="/pages/Xr48HHS3FdjWo2747DP9" %}
[Troubleshooting](/self-managed-hivel-deployment/on-premises-generic/hivel-on-premises-deployment-guide-generic/troubleshooting.md)
{% endcontent-ref %}

***

**Deployment complete.** See the [full On-Premises Setup Guide](https://docs.hivel.ai/self-managed-hivel-deployment/on-premises-generic/hivel-on-premises-deployment-guide-generic) for additional details.

{% columns %}
{% column width="33.33333333333333%" %} <a href="/self-managed-hivel-deployment/on-premises-generic/hivel-on-premises-deployment-guide-generic.md" class="button primary" data-icon="backward">Back to On-Premises</a>
{% endcolumn %}

{% column width="33.33333333333333%" %}

{% endcolumn %}

{% column %} <a href="/archive/generic/hivel-on-premises-deployment-guide-generic.md" class="button primary" data-icon="forward">Hivel On-Premises Deployment Guide (Generic)</a>
{% endcolumn %}
{% endcolumns %}

[^1]:
