### Start Development Server Source: https://github.com/fosrl/docs/blob/main/packages/docusaurus/docs/09-development.md Start the local development server for Pangolin. ```bash npm run dev ``` -------------------------------- ### Run Fossorial Quick Installer Source: https://context7.com/fosrl/docs/llms.txt Download and execute the installer script on a Linux VPS to set up the full Fossorial stack. The installer interactively prompts for necessary configuration details. ```bash # Download and run the installer as root on Ubuntu/Debian (AMD64) wget https://github.com/fosrl/pangolin/releases/latest/download/installer_linux_amd64 -O installer chmod +x installer sudo ./installer ``` ```bash # The installer prompts for: # 1. Base domain (e.g., example.com) # 2. Dashboard domain (e.g., pangolin.example.com) # 3. Let's Encrypt email # 4. Whether to install Gerbil for tunneling # 5. Security flags (invite-only signup, org creation) # 6. Optional SMTP email configuration ``` ```bash # After installation, complete admin setup at: # https://pangolin.example.com/auth/initial-setup ``` ```bash # Reset admin credentials at any time: docker exec -it pangolin pangctl set-admin-credentials \ --email "admin@example.com" \ --password "Password123!" ``` -------------------------------- ### Run Pangolin Installer Source: https://github.com/fosrl/docs/blob/main/packages/docusaurus/docs/02-Getting Started/03-quick-install.md Execute the downloaded installer script with root privileges to begin the Pangolin installation process. Ensure you are in the directory where the installer was downloaded. ```bash sudo ./installer ``` -------------------------------- ### Install Project Dependencies Source: https://github.com/fosrl/docs/blob/main/README.md Run this command to install all necessary project dependencies. ```bash $ npm i ``` -------------------------------- ### Example Docker Compose for Pangolin and PostgreSQL Source: https://github.com/fosrl/docs/blob/main/packages/docusaurus/docs/03-Pangolin/08-Database/02-postgres.md This Docker Compose file sets up a PostgreSQL database and Pangolin service. It includes a health check for the database to ensure it's ready before Pangolin starts. Note: Using `latest` tags is not recommended for production environments. ```yaml name: pangolin services: pangolin: image: fosrl/pangolin:postgresql-latest # Not advised to use `latest` in production container_name: pangolin restart: unless-stopped depends_on: postgres: condition: service_healthy volumes: - ./config:/app/config healthcheck: test: ["CMD", "curl", "-f", "http://localhost:3001/api/v1/"] interval: "10s" timeout: "10s" retries: 15 # ... other services ... postgres: image: postgres:17 container_name: postgres restart: unless-stopped environment: POSTGRES_USER: postgres POSTGRES_PASSWORD: postgres volumes: - ./config/postgres:/var/lib/postgresql/data healthcheck: test: ["CMD-SHELL", "pg_isready -U postgres"] interval: 10s timeout: 5s retries: 5 ``` -------------------------------- ### Example Pangolin Configuration Source: https://github.com/fosrl/docs/blob/main/packages/docusaurus/docs/03-Pangolin/02-Configuration/02-config.md This is an example configuration file for Pangolin. Customize these settings for your specific needs. ```yaml app: dashboard_url: "https://pangolin.example.com" log_level: "info" save_logs: false domains: domain1: base_domain: "example.com" cert_resolver: "letsencrypt" server: external_port: 3000 internal_port: 3001 next_port: 3002 secret: "d28@a2b.2HFTe2bMtZHGneNYgQFKT2X4vm4HuXUXBcq6aVyNZjdGt6Dx-_A@9b3y" traefik: cert_resolver: "letsencrypt" http_entrypoint: "web" https_entrypoint: "websecure" gerbil: start_port: 51820 base_endpoint: "pangolin.example.com" email: smtp_host: "host.hoster.net" smtp_port: 587 smtp_user: "no-reply@example.com" smtp_pass: "aaaaaaaaaaaaaaaaaa" no_reply: "no-reply@example.com" flags: require_email_verification: true disable_signup_without_invite: true disable_user_create_org: true allow_raw_resources: true allow_base_domain_resources: true ``` -------------------------------- ### Install CrowdSec Repositories Source: https://github.com/fosrl/docs/blob/main/packages/docusaurus/docs/08-Community Guides/02-crowdsec.md Run this command to install the CrowdSec repositories on your system. ```bash curl -s https://install.crowdsec.net | sudo sh ``` -------------------------------- ### Start Local Development Server Source: https://github.com/fosrl/docs/blob/main/README.md Starts a local development server. Changes are reflected live without server restarts. ```bash $ npm run start ``` -------------------------------- ### Install NPM Dependencies Source: https://github.com/fosrl/docs/blob/main/packages/docusaurus/docs/09-development.md Install all necessary package dependencies for the project using npm. ```bash npm install ``` -------------------------------- ### Start Prometheus Container Source: https://github.com/fosrl/docs/blob/main/packages/docusaurus/docs/08-Community Guides/04-metrics.md Start the Prometheus Docker container using Docker Compose. ```bash sudo docker conpose up -d ``` -------------------------------- ### Install CrowdSec Firewall Bouncer Source: https://context7.com/fosrl/docs/llms.txt Installs CrowdSec and the firewall bouncer for host protection. Requires `curl` and `sudo` privileges. After installation, an API key must be generated and configured. ```bash # CrowdSec is installable via the Pangolin installer (select during setup) # or added manually to docker-compose.yml # After installation, add firewall bouncer for SSH/host protection: curl -s https://install.crowdsec.net | sudo sh sudo apt install crowdsec-firewall-bouncer-iptables # Create API key for the firewall bouncer: docker exec -it crowdsec cscli bouncers add vps-firewall # Copy the key, then edit: nano /etc/crowdsec/bouncers/crowdsec-firewall-bouncer.yaml systemctl restart crowdsec-firewall-bouncer ``` -------------------------------- ### Install and Run Newt CLI Source: https://github.com/fosrl/docs/blob/main/packages/docusaurus/docs/02-Getting Started/05-quick-setup.md Use wget to download the Newt binary on Linux and then execute the command with your specific IDs and endpoint to connect your site. ```bash ./newt \ --id 31frd0uzbjvp721 \ --secret h51mmlknrvrwv8s4r1i210azhumt6isgbpyavxodibx1k2d6 \ --endpoint https://example.com ``` -------------------------------- ### Run Olm with CLI Arguments Source: https://github.com/fosrl/docs/blob/main/packages/docusaurus/docs/06-Olm/01-overview.md Example of how to run the Olm client using command-line arguments for ID, secret, and endpoint. ```bash olm \ --id 31frd0uzbjvp721 \ --secret h51mmlknrvrwv8s4r1i210azhumt6isgbpyavxodibx1k2d6 \ --endpoint https://example.com ``` -------------------------------- ### Start Docker Compose Services Source: https://github.com/fosrl/docs/blob/main/packages/docusaurus/docs/04-Newt/02-install.md Start all services defined in your docker-compose.yml file in detached mode. ```bash docker compose up -d ``` -------------------------------- ### Bypass Rule Examples (Path Matching) Source: https://context7.com/fosrl/docs/llms.txt Examples of path matching patterns for creating bypass rules. Wildcards like '*' match within a single segment. ```yaml # Rule evaluation is top-to-bottom by priority. # Rule types: "allow" (bypass auth) or "deny" (block request) # Path matching examples (wildcard * matches within one segment): # /api/* — all paths under /api/ # /blog/* — e.g., /blog/post-1 # *admin* — any segment containing "admin" # /api/* — allow API access for mobile apps # Common app bypass rules: # Jellyfin iOS: /system/info/public # Immich: /api/* AND /.well-known/immich # Nextcloud: /remote.php/* /status.php /.well-known/* /ocs/* # Home Assistant: /api/* /auth/* /frontend_latest/* /local/* # Vaultwarden: /api/* /identity/* /wl/* # DENY: /admin/* # Radarr/Sonarr: /api/* # Matrix/Synapse: /_matrix/* /_synapse/client/* # IP/CIDR bypass (allow home IP without login): # IP: 192.168.1.1 (single address, equivalent to /32 CIDR) # CIDR: 192.168.1.0/24 (entire subnet) # CIDR: 0.0.0.0/0 (all IPv4 — use with caution) ``` -------------------------------- ### Configure and Start WireGuard Tunnel Source: https://github.com/fosrl/docs/blob/main/packages/docusaurus/docs/02-Getting Started/05-quick-setup.md On a Linux client, save the provided WireGuard configuration to a file (e.g., wg0.conf) and use wg-quick to bring the tunnel up. ```bash wg-quick up ./wg0.conf ``` -------------------------------- ### Install Go Dependencies Source: https://github.com/fosrl/docs/blob/main/packages/docusaurus/docs/05-Gerbil/02-developer-guide.md Download all required Go dependencies for the Gerbil project. This command ensures that all necessary external packages are available. ```bash go mod download ``` -------------------------------- ### Install Badger via Docker Commands Source: https://github.com/fosrl/docs/blob/main/packages/docusaurus/docs/07-Badger/01-overview.md Alternatively, configure the Badger plugin using command-line arguments when running Traefik in Docker. ```yaml command: - "--experimental.plugins.badger.modulename=github.com/fosrl/badger" - "--experimental.plugins.badger.version=v1.2.0" ``` -------------------------------- ### Install Badger via Traefik Static Configuration Source: https://github.com/fosrl/docs/blob/main/packages/docusaurus/docs/07-Badger/01-overview.md Configure the Badger plugin in Traefik's static configuration file to enable its functionality. ```yaml experimental: plugins: badger: modulename: github.com/fosrl/badger version: v1.2.0 ``` -------------------------------- ### Newt Client Command-Line Execution Source: https://context7.com/fosrl/docs/llms.txt These examples demonstrate how to run the Newt client binary with various options. It includes basic execution, using mTLS client certificates, and integrating with the Docker socket for container discovery. ```bash # Run as a binary ./newt \ --id 31frd0uzbjvp721 \ --secret h51mmlknrvrwv8s4r1i210azhumt6isgbpyavxodibx1k2d6 \ --endpoint https://pangolin.example.com \ --log-level INFO # With mTLS client certificate ./newt \ --id 31frd0uzbjvp721 \ --secret h51mmlknrvrwv8s4r1i210azhumt6isgbpyavxodibx1k2d6 \ --endpoint https://pangolin.example.com \ --tls-client-cert ./client.p12 # With Docker socket integration (enables container discovery in Pangolin UI) ./newt \ --id 31frd0uzbjvp721 \ --secret h51mmlknrvrwv8s4r1i210azhumt6isgbpyavxodibx1k2d6 \ --endpoint https://pangolin.example.com \ --docker-socket /var/run/docker.sock ``` -------------------------------- ### Badger middleware configuration example Source: https://context7.com/fosrl/docs/llms.txt Illustrates the configuration parameters for the Badger middleware, including API base URL and cookie/query parameter names for authentication tokens. This configuration is typically auto-injected by Pangolin. ```yaml # Badger middleware config (auto-injected by Pangolin into Traefik dynamic config) # Reference only — do NOT add manually: apiBaseUrl: "http://pangolin:3001/api/v1" userSessionCookieName: "p_session_token" resourceSessionCookieName: "resource_session" accessTokenQueryParam: "p_token" ``` -------------------------------- ### Install Newt to PATH Source: https://github.com/fosrl/docs/blob/main/packages/docusaurus/docs/04-Newt/02-install.md Move the Newt binary to a directory included in your system's PATH for global access. This may require root privileges. ```bash mv ./newt /usr/local/bin ``` -------------------------------- ### Fossorial Manual Docker Compose Setup Source: https://context7.com/fosrl/docs/llms.txt Manually deploy the Pangolin stack using Docker Compose. This method provides explicit control over the configuration files and services. ```yaml # docker-compose.yml name: pangolin services: pangolin: image: fosrl/pangolin:latest container_name: pangolin restart: unless-stopped volumes: - ./config:/app/config healthcheck: test: ["CMD", "curl", "-f", "http://localhost:3001/api/v1/"] interval: "10s" timeout: "10s" retries: 15 networks: - pangolin gerbil: image: fosrl/gerbil:latest container_name: gerbil restart: unless-stopped depends_on: pangolin: condition: service_healthy cap_add: - NET_ADMIN - SYS_MODULE sysctls: - net.ipv4.ip_forward=1 - net.ipv4.conf.all.src_valid_mark=1 - net.ipv6.conf.all.forwarding=1 command: - --reachableAt=http://gerbil:3003 - --generateAndSaveKeyTo=/var/config/key - --remoteConfig=http://pangolin:3001/api/v1/gerbil/get-config - --reportBandwidthTo=http://pangolin:3001/api/v1/gerbil/receive-bandwidth volumes: - ./config:/var/config ports: - 51820:51820/udp # WireGuard - 21820:21820/udp # Newt clients - 443:443 - 80:80 networks: - pangolin traefik: image: traefik:v3.3.4 container_name: traefik restart: unless-stopped network_mode: "service:gerbil" depends_on: pangolin: condition: service_healthy volumes: - ./config/traefik:/etc/traefik:ro - ./config/letsencrypt:/letsencrypt networks: pangolin: driver: bridge ``` ```bash # Start the stack sudo docker compose up -d # View logs sudo docker compose logs -f ``` -------------------------------- ### Get Site Prerequisites Source: https://github.com/fosrl/docs/blob/main/packages/docusaurus/docs/03-Pangolin/07-API/02-Routes/return-pre-requisite-data-for-creating-a-site-such-as-the-exit-node-subnet-newt-credentials-etc.api.mdx Fetches the data needed to configure a new site, such as available exit nodes, subnet information, and Newt authentication details. ```APIDOC ## GET /org/{orgId}/pick-site-defaults ### Description Return pre-requisite data for creating a site, such as the exit node, subnet, Newt credentials, etc. ### Method GET ### Endpoint /org/{orgId}/pick-site-defaults ### Parameters #### Path Parameters - **orgId** (string) - Required - The organization ID. ``` -------------------------------- ### Install CrowdSec Firewall Bouncer (Debian/Ubuntu) Source: https://github.com/fosrl/docs/blob/main/packages/docusaurus/docs/08-Community Guides/02-crowdsec.md Install the IPTables firewall bouncer package on Debian/Ubuntu systems. ```bash sudo apt install crowdsec-firewall-bouncer-iptables ``` -------------------------------- ### Build Olm Container Image Source: https://github.com/fosrl/docs/blob/main/packages/docusaurus/docs/06-Olm/01-overview.md Command to build the Docker container image for Olm. Requires Docker to be installed. ```bash make ``` -------------------------------- ### Fetch All Organizations using Root API Key Source: https://context7.com/fosrl/docs/llms.txt Example curl command to list all organizations using the root API key. Ensure the API key format is correct. ```bash # Swagger UI available at: # https://api.example.com/v1/docs # API key format: . # Example: fm779dfwyhc237x.6gubrijowftfj6cykx77qbsdfkhfregplam74ent # Root API key (server admin only) — can create/delete orgs: curl -X GET "https://api.example.com/v1/org" \ -H "Authorization: Bearer fm779dfwyhc237x.6gubrijowftfj6cykx77qbsdfkhfregplam74ent" ``` -------------------------------- ### Create Scoped API Key for Organization Source: https://context7.com/fosrl/docs/llms.txt Example curl command to create a new API key for an organization. This key can then have specific actions assigned to it. ```bash # PUT /org/{orgId}/apikey curl -X PUT "https://api.example.com/v1/org/home-lab/apikey" \ -H "Authorization: Bearer " \ -H "Content-Type: application/json" \ -d '{ "name": "ci-deploy-key" }' ``` -------------------------------- ### Create Organization using Root API Key Source: https://context7.com/fosrl/docs/llms.txt Example curl command to create a new organization. Requires a root API key and specifies organization details like ID, name, and subnet. ```bash # PUT /org curl -X PUT "https://api.example.com/v1/org" \ -H "Authorization: Bearer " \ -H "Content-Type: application/json" \ -d '{ "orgId": "home-lab", "name": "Home Lab", "subnet": "100.89.0.0/24" }' # Expected response: # { # "data": { # "orgId": "home-lab", # "name": "Home Lab", # "subnet": "100.89.0.0/24" # } # } ``` -------------------------------- ### Create HTTP Resource on a Site Source: https://context7.com/fosrl/docs/llms.txt Example curl command to create an HTTP resource (e.g., a web service) on a specific site within an organization. It can be configured with a subdomain and protocol. ```bash # PUT /org/{orgId}/site/{siteId}/resource — HTTP resource on a subdomain curl -X PUT "https://api.example.com/v1/org/home-lab/site/1/resource" \ -H "Authorization: Bearer " \ -H "Content-Type: application/json" \ -d '{ "name": "Jellyfin", "subdomain": "jellyfin", "siteId": 1, "http": true, "protocol": "https", "domainId": "domain1" }' ``` -------------------------------- ### Configure Traefik to Expose Integration API Source: https://context7.com/fosrl/docs/llms.txt Traefik dynamic configuration to expose the Integration API at `https://api.example.com/v1`, including HTTPS redirection and TLS setup. ```yaml # config/traefik/dynamic_config.yml — expose at https://api.example.com/v1 http: middlewares: redirect-to-https: redirectScheme: scheme: https routers: int-api-router-redirect: rule: "Host(`api.example.com`)" service: int-api-service entryPoints: [web] middlewares: [redirect-to-https] int-api-router: rule: "Host(`api.example.com`)" service: int-api-service entryPoints: [websecure] tls: certResolver: letsencrypt services: int-api-service: loadBalancer: servers: - url: "http://pangolin:3003" ``` -------------------------------- ### Create Raw TCP Resource on a Site Source: https://context7.com/fosrl/docs/llms.txt Example curl command to create a raw TCP resource (e.g., a game server) on a specific site within an organization. It requires specifying the protocol and proxy port. ```bash # Raw TCP resource on a fixed port (e.g., Minecraft server): curl -X PUT "https://api.example.com/v1/org/home-lab/site/1/resource" \ -H "Authorization: Bearer " \ -H "Content-Type: application/json" \ -d '{ "name": "Minecraft", "siteId": 1, "http": false, "protocol": "tcp", "proxyPort": 25565 }' ``` -------------------------------- ### Get Client Defaults Source: https://github.com/fosrl/docs/blob/main/packages/docusaurus/docs/03-Pangolin/07-API/02-Routes/return-pre-requisite-data-for-creating-a-client.api.mdx Retrieves default values and configurations needed to create a client, often used to pre-populate forms or set initial parameters. ```APIDOC ## GET /site/{siteId}/pick-client-defaults ### Description Return pre-requisite data for creating a client. ### Method GET ### Endpoint /site/{siteId}/pick-client-defaults ### Parameters #### Path Parameters - **siteId** (string) - Required - The identifier for the site. ### Request Example ```json { "example": "request body" } ``` ### Response #### Success Response (200) - **field1** (type) - Description #### Response Example ```json { "example": "response body" } ``` ``` -------------------------------- ### Download Official Ban Page HTML Source: https://github.com/fosrl/docs/blob/main/packages/docusaurus/docs/08-Community Guides/02-crowdsec.md Use this command to download the official example ban.html file. Place this file in your Traefik configuration directory. ```bash wget https://raw.githubusercontent.com/maxlerebourg/crowdsec-bouncer-traefik-plugin/refs/heads/main/ban.html ``` -------------------------------- ### Pangolin Application Configuration (config/config.yml) Source: https://context7.com/fosrl/docs/llms.txt This is a comprehensive example of the main configuration file for the Pangolin application. It covers settings for the dashboard, server, domains, Traefik, Gerbil, rate limits, email, and feature flags. ```yaml app: dashboard_url: "https://pangolin.example.com" log_level: "info" # debug | info | warn | error save_logs: true log_failed_attempts: true # useful for CrowdSec/Fail2ban server: external_port: 3000 # public-facing API internal_port: 3001 # internal/Gerbil-facing API next_port: 3002 # Next.js frontend integration_port: 3003 # REST Integration API (optional) internal_hostname: "pangolin" session_cookie_name: "p_session_token" resource_access_token_param: "p_token" resource_access_token_headers: id: "P-Access-Token-Id" token: "P-Access-Token" resource_session_request_param: "p_session_request" secret: "d28@a2b.2HFTe2bMtZHGneNYgQFKT2X4vm4HuXUXBcq6aVyNZjdGt6Dx-_A@9b3y" trust_proxy: 1 dashboard_session_length_hours: 720 resource_session_length_hours: 720 cors: origins: ["https://pangolin.example.com"] methods: ["GET", "POST", "PUT", "DELETE", "PATCH"] allowed_headers: ["X-CSRF-Token", "Content-Type"] credentials: true domains: domain1: base_domain: "example.com" cert_resolver: "letsencrypt" prefer_wildcard_cert: false traefik: http_entrypoint: "web" https_entrypoint: "websecure" cert_resolver: "letsencrypt" prefer_wildcard_cert: false additional_middlewares: [] # e.g., ["crowdsec"] gerbil: start_port: 51820 base_endpoint: "pangolin.example.com" use_subdomain: false subnet_group: "100.89.0.0/16" block_size: 24 site_block_size: 30 rate_limits: global: window_minutes: 1 max_requests: 100 email: smtp_host: "smtp.example.com" smtp_port: 587 smtp_user: "no-reply@example.com" smtp_pass: "smtppassword" # or set env EMAIL_SMTP_PASS no_reply: "no-reply@example.com" smtp_secure: false smtp_tls_reject_unauthorized: true flags: require_email_verification: true disable_signup_without_invite: true disable_user_create_org: false allow_raw_resources: true # enable TCP/UDP resources allow_base_domain_resources: false enable_integration_api: true # Optional PostgreSQL (use image: fosrl/pangolin:postgresql-latest) # postgres: # connection_string: postgresql://user:password@postgres:5432/pangolin orgs: block_size: 24 subnet_group: "10.0.0.0/8" ``` -------------------------------- ### Download Official Captcha Page HTML Source: https://github.com/fosrl/docs/blob/main/packages/docusaurus/docs/08-Community Guides/02-crowdsec.md Use this command to download the official example captcha.html file. Place this file in your Traefik configuration directory. ```bash wget https://raw.githubusercontent.com/maxlerebourg/crowdsec-bouncer-traefik-plugin/refs/heads/main/captcha.html ``` -------------------------------- ### Create WireGuard Site within Organization Source: https://context7.com/fosrl/docs/llms.txt Example curl command to create a new site of type 'wireguard' within an organization. Requires the public key of the WireGuard client and a subnet. ```bash # Create a WireGuard site (bring your own WG client): curl -X PUT "https://api.example.com/v1/org/home-lab/site" \ -H "Authorization: Bearer " \ -H "Content-Type: application/json" \ -d '{ "name": "office-wireguard", "type": "wireguard", "pubKey": "wg-public-key-base64==", "subnet": "100.89.0.1/30" }' ``` -------------------------------- ### Assign Actions to Organization API Key Source: https://context7.com/fosrl/docs/llms.txt Example curl command to assign specific actions (e.g., createResource, listSites) to an organization's API key. Requires the root API key. ```bash # Then set specific allowed actions on the key: # POST /org/{orgId}/apikey/{apiKeyId}/actions curl -X POST "https://api.example.com/v1/org/home-lab/apikey//actions" \ -H "Authorization: Bearer " \ -H "Content-Type: application/json" \ -d '{ "actions": ["createResource", "updateResource", "deleteResource", "listSites"] }' ``` -------------------------------- ### Prometheus Configuration for Scraping Services Source: https://github.com/fosrl/docs/blob/main/packages/docusaurus/docs/08-Community Guides/04-metrics.md Create a prometheus.yml file to configure Prometheus scrape jobs. This example defines scrape intervals and targets for Prometheus itself, Traefik, and Crowdsec. ```yaml global: scrape_interval: 15s evaluation_interval: 15s scrape_configs: - job_name: "prometheus" static_configs: - targets: ["localhost:9090"] - job_name: traefik static_configs: - targets: ["172.17.0.1:8082"] - job_name: crowdsec static_configs: - targets: ["172.17.0.1:6060"] ``` -------------------------------- ### Manage Olm Windows Service Source: https://github.com/fosrl/docs/blob/main/packages/docusaurus/docs/06-Olm/01-overview.md Commands for managing the Olm Windows service, including installation, starting, stopping, status checks, and removal. ```bash # Install the service olm.exe install # Start the service olm.exe start # Stop the service olm.exe stop # Check service status olm.exe status # Remove the service olm.exe remove # Run in debug mode (console output) with our without id & secret olm.exe debug # Show help olm.exe help ``` -------------------------------- ### Traefik Configuration Files Structure Source: https://github.com/fosrl/docs/blob/main/packages/docusaurus/docs/02-Getting Started/04-Manual Install Guides/02-unraid.md This structure outlines the necessary Traefik configuration files within the Pangolin appdata directory. Ensure these files are present before proceeding with Traefik setup. ```bash pangolin/ ├─ config/ │ ├─ config.yml │ ├─ letsencrypt/ │ ├─ traefik/ │ │ ├─ dynamic_config.yml │ │ ├─ traefik_config.yml ``` -------------------------------- ### Deploy Project to Production Source: https://github.com/fosrl/docs/blob/main/README.md Deploys the project to the production environment using SSH. ```bash $ npx sst deploy --stage prod ``` -------------------------------- ### Get a Resource Source: https://github.com/fosrl/docs/blob/main/packages/docusaurus/docs/03-Pangolin/07-API/02-Routes/get-a-resource.api.mdx Retrieves a specific resource by its ID. ```APIDOC ## GET /resource/{resourceId} ### Description Retrieves a specific resource by its ID. ### Method GET ### Endpoint /resource/{resourceId} ### Parameters #### Path Parameters - **resourceId** (string) - Required - The unique identifier of the resource to retrieve. ``` -------------------------------- ### Run Gerbil standalone with local configuration Source: https://context7.com/fosrl/docs/llms.txt Execute Gerbil as a binary, specifying configuration paths, network interfaces, and listening ports. Ensure the necessary ports are open. ```bash # Run as a binary (standalone with local config) ./gerbil \ --reachableAt=http://gerbil:3003 \ --generateAndSaveKeyTo=/var/config/key \ --remoteConfig=http://pangolin:3001/api/v1/gerbil/get-config \ --reportBandwidthTo=http://pangolin:3001/api/v1/gerbil/receive-bandwidth \ --interface=wg0 \ --listen=3003 \ --log-level=INFO ``` -------------------------------- ### Get an organization Source: https://github.com/fosrl/docs/blob/main/packages/docusaurus/docs/03-Pangolin/07-API/02-Routes/get-an-organization.api.mdx Retrieves details for a specific organization using its ID. ```APIDOC ## GET /org/{orgId} ### Description Retrieves details for a specific organization using its ID. ### Method GET ### Endpoint /org/{orgId} ### Parameters #### Path Parameters - **orgId** (string) - Required - The unique identifier of the organization. ``` -------------------------------- ### Build Olm Binary Locally Source: https://github.com/fosrl/docs/blob/main/packages/docusaurus/docs/06-Olm/01-overview.md Command to build the Olm binary locally. Requires Go 1.23.1 or later. ```bash make local ``` -------------------------------- ### Get Resource Email Whitelist Source: https://github.com/fosrl/docs/blob/main/packages/docusaurus/docs/03-Pangolin/07-API/02-Routes/get-the-whitelist-of-emails-for-a-specific-resource.api.mdx Fetches the email whitelist for a specified resource. ```APIDOC ## GET /resource/{resourceId}/whitelist ### Description Get the whitelist of emails for a specific resource. ### Method GET ### Endpoint /resource/{resourceId}/whitelist ### Parameters #### Path Parameters - **resourceId** (string) - Required - The identifier of the resource for which to retrieve the email whitelist. ``` -------------------------------- ### Pangolin CLI: Access and Admin Credentials Management Source: https://context7.com/fosrl/docs/llms.txt Demonstrates how to access the Pangolin CLI tool within its container using `docker exec` and how to reset or set administrative credentials. ```bash # Access via docker exec docker exec -it pangolin pangctl --help # Reset or set admin credentials docker exec -it pangolin pangctl set-admin-credentials \ --email "admin@example.com" \ --password "NewSecurePassword123!" ``` -------------------------------- ### Get a site by siteId Source: https://github.com/fosrl/docs/blob/main/packages/docusaurus/docs/03-Pangolin/07-API/02-Routes/get-a-site-by-site-id.api.mdx Retrieves details of a specific site using its unique identifier. ```APIDOC ## GET /site/{siteId} ### Description Retrieves details of a specific site using its unique identifier. ### Method GET ### Endpoint /site/{siteId} ### Parameters #### Path Parameters - **siteId** (number) - Required - The unique identifier of the site. ``` -------------------------------- ### Get an IDP by its IDP ID Source: https://github.com/fosrl/docs/blob/main/packages/docusaurus/docs/03-Pangolin/07-API/02-Routes/get-an-idp-by-its-idp-id.api.mdx Fetches an IDP resource using its unique identifier. ```APIDOC ## GET /idp/{idpId} ### Description Get an IDP by its IDP ID. ### Method GET ### Endpoint /idp/{idpId} ### Parameters #### Path Parameters - **idpId** (number) - Optional - Description not provided ``` -------------------------------- ### Get a target by ID Source: https://github.com/fosrl/docs/blob/main/packages/docusaurus/docs/03-Pangolin/07-API/02-Routes/get-a-target.api.mdx Retrieves the details of a specific target using its unique identifier. ```APIDOC ## GET /target/{targetId} ### Description Retrieves the details of a specific target using its unique identifier. ### Method GET ### Endpoint /target/{targetId} ### Parameters #### Path Parameters - **targetId** (string) - Required - The unique identifier of the target. ``` -------------------------------- ### Start the Docker Compose Stack Source: https://github.com/fosrl/docs/blob/main/packages/docusaurus/docs/02-Getting Started/06-how-to-update.md Restarts the stack with the updated Docker images in detached mode. ```bash sudo docker compose up -d ``` -------------------------------- ### Get User in Organization Source: https://github.com/fosrl/docs/blob/main/packages/docusaurus/docs/03-Pangolin/07-API/02-Routes/get-a-user-in-an-organization.api.mdx Retrieves a user's information given their organization and user IDs. ```APIDOC ## GET /org/{orgId}/user/{userId} ### Description Get a user in an organization. ### Method GET ### Endpoint /org/{orgId}/user/{userId} ### Parameters #### Path Parameters - **userId** (string) - Required - The ID of the user to retrieve. - **orgId** (string) - Required - The ID of the organization the user belongs to. ### Response #### Success Response (200) - **field1** (type) - Description ``` -------------------------------- ### Troubleshooting: Check Docker Info Source: https://github.com/fosrl/docs/blob/main/packages/docusaurus/docs/08-Community Guides/05-homeassistant.md Verify Docker accessibility within the Home Assistant OS environment. ```shell docker info ``` -------------------------------- ### Get Client by Client ID Source: https://github.com/fosrl/docs/blob/main/packages/docusaurus/docs/03-Pangolin/07-API/02-Routes/get-a-client-by-its-client-id.api.mdx Retrieves a client's information using their unique identifier. ```APIDOC ## GET /org/{orgId}/client/{clientId} ### Description Get a client by its client ID. ### Method GET ### Endpoint /org/{orgId}/client/{clientId} ### Parameters #### Path Parameters - **clientId** (string) - Required - The unique identifier of the client. - **orgId** (string) - Optional - The identifier of the organization. ### Response #### Success Response (200) - **client** (object) - Details of the client. ``` -------------------------------- ### Docker Compose File Source: https://github.com/fosrl/docs/blob/main/packages/docusaurus/docs/02-Getting Started/04-Manual Install Guides/01-docker-compose.md Defines the services for Pangolin, Traefik, and Gerbil in a Docker Compose setup. ```yaml version: "3.8" services: pangolin: image: ghcr.io/fossorial/pangolin:latest container_name: pangolin restart: unless-stopped ports: - "8080:8080" volumes: - ./config/config.yml:/app/config.yml - ./config/db:/app/db - ./config/key:/app/key - ./config/letsencrypt:/app/letsencrypt - ./config/logs:/app/logs networks: - traefik traefik: image: traefik:v2.10 container_name: traefik restart: unless-stopped command: - "--api.insecure=true" - "--providers.docker=true" - "--entrypoints.web.address=:80" - "--entrypoints.websecure.address=:443" - "--certificatesresolvers.myresolver.acme.tlschallenge=true" - "--certificatesresolvers.myresolver.acme.storage=/letsencrypt/acme.json" - "--log.level=INFO" - "--accesslog=true" - "--api.dashboard=true" - "--providers.file.directory=/etc/traefik/dynamic_conf/" - "--providers.file.watch=true" ports: - "80:80" - "443:443" - "8080:8080" volumes: - ./config/letsencrypt:/letsencrypt - ./config/traefik/dynamic_config.yml:/etc/traefik/dynamic_conf/dynamic_config.yml - /var/run/docker.sock:/var/run/docker.sock:ro networks: - traefik gerbil: image: ghcr.io/fossorial/gerbil:latest container_name: gerbil restart: unless-stopped volumes: - ./config/key:/app/key networks: - traefik networks: traefik: name: traefik ``` -------------------------------- ### Get a site by orgId and niceId Source: https://github.com/fosrl/docs/blob/main/packages/docusaurus/docs/03-Pangolin/07-API/02-Routes/get-a-site-by-org-id-and-nice-id-nice-id-is-a-readable-id-for-the-site-and-unique-on-a-per-org-basis.api.mdx Fetches a site's details using its organization ID and its unique nice ID. ```APIDOC ## GET /org/{orgId}/site/{niceId} ### Description Get a site by orgId and niceId. NiceId is a readable ID for the site and unique on a per org basis. ### Method GET ### Endpoint /org/{orgId}/site/{niceId} ### Parameters #### Path Parameters - **orgId** (string) - Required - The unique identifier for the organization. - **niceId** (string) - Required - A readable and unique identifier for the site within the organization. ### Request Example ```json { "example": "request body" } ``` ### Response #### Success Response (200) - **field1** (type) - Description #### Response Example ```json { "example": "response body" } ``` ``` -------------------------------- ### Traefik Static Configuration Source: https://github.com/fosrl/docs/blob/main/packages/docusaurus/docs/02-Getting Started/04-Manual Install Guides/02-unraid.md This is the static configuration for Traefik, defining entry points and providers. Ensure this matches your Traefik setup. ```yaml ``` -------------------------------- ### Add Newt Add-on Repository Source: https://github.com/fosrl/docs/blob/main/packages/docusaurus/docs/08-Community Guides/05-homeassistant.md Add the GitHub repository URL to your Home Assistant Add-on Store. ```text https://github.com/Ferdinand99/home-assistant-newt-addon ``` ```text https://git.opland.net/Ferdinand99/home-assistant-newt-addon/ ``` -------------------------------- ### Run Gerbil with Localhost Config Source: https://github.com/fosrl/docs/blob/main/packages/docusaurus/docs/09-development.md Run the Gerbil binary, configuring it to use the local Pangolin development server for configuration and bandwidth reporting. Ensure the Gerbil binary is executable and specify the output path for the generated key. ```bash ./gerbil \ --remoteConfig http://localhost:3001/api/v1/gerbil/get-config \ --reportBandwidthTo http://localhost:3001/api/v1/gerbil/receive-bandwidth \ --generateAndSaveKeyTo=/var/key \ --reachableAt=http://localhost:3003 ``` -------------------------------- ### Pangolin API Health Check Source: https://context7.com/fosrl/docs/llms.txt Perform a simple GET request to the root of the API to check if the Pangolin API server is running. ```bash curl -X GET "https://api.example.com/v1/" # 200 OK — server is running ``` -------------------------------- ### Traefik Dynamic Configuration Source: https://github.com/fosrl/docs/blob/main/packages/docusaurus/docs/02-Getting Started/04-Manual Install Guides/02-unraid.md This is the dynamic configuration for Traefik, typically used for routers, services, and middleware. Ensure this matches your Traefik setup. ```yaml ``` -------------------------------- ### Enable Clients on Newt Site Source: https://github.com/fosrl/docs/blob/main/packages/docusaurus/docs/03-Pangolin/07-clients.md When configuring your Newt site, use the `--accept-clients` flag or set the `ACCEPT_CLIENTS=true` environment variable to allow it to accept incoming client connections. ```bash newt --accept-clients ``` -------------------------------- ### Docker Healthcheck Pattern Source: https://context7.com/fosrl/docs/llms.txt This is an example of a Docker healthcheck command pattern used internally to test the Pangolin API server's liveness. ```bash # Docker healthcheck pattern used internally: # test: ["CMD", "curl", "-f", "http://localhost:3001/api/v1/"] ``` -------------------------------- ### Read Pangolin Auth Headers in FastAPI Source: https://context7.com/fosrl/docs/llms.txt Example FastAPI endpoint to retrieve user authentication headers like Remote-User, Remote-Email, and Remote-Name. ```python from fastapi import Request @app.get("/dashboard") async def dashboard(request: Request): user = request.headers.get("Remote-User") # e.g., "john.doe" email = request.headers.get("Remote-Email") # e.g., "john@example.com" name = request.headers.get("Remote-Name") # e.g., "John Doe" return {"user": user, "email": email, "name": name} ``` -------------------------------- ### View Available Pangolin CLI Commands Source: https://github.com/fosrl/docs/blob/main/packages/docusaurus/docs/03-Pangolin/06-pangolin-cli.md Run this command to display a list of all available commands for the pangctl CLI. ```bash docker exec -it pangolin pangctl --help ``` -------------------------------- ### Make iptables NAT Rules Persistent (Ubuntu/Debian) Source: https://github.com/fosrl/docs/blob/main/packages/docusaurus/docs/03-Pangolin/07-clients.md Install iptables-persistent and save the current iptables rules to ensure they are applied after reboot on Ubuntu/Debian systems. ```bash # Install iptables-persistent sudo apt install iptables-persistent # Save current rules sudo iptables-save > /etc/iptables/rules.v4 ``` -------------------------------- ### Invite User to Organization Source: https://context7.com/fosrl/docs/llms.txt Use this command to invite a new user to your organization by providing their email and desired role ID. ```bash # Invite a user to an organization curl -X POST "https://api.example.com/v1/org/home-lab/invite" \ -H "Authorization: Bearer " \ -H "Content-Type: application/json" \ -d '{ "email": "alice@example.com", "roleId": "member" }' ``` -------------------------------- ### Build Newt with Nix Flake Source: https://github.com/fosrl/docs/blob/main/packages/docusaurus/docs/04-Newt/01-overview.md Build the Newt project using a Nix flake. The binary will be located at `./result/bin/newt`. A development shell is available with `nix develop`. ```bash nix build ``` -------------------------------- ### Configure NAT with nftables Source: https://github.com/fosrl/docs/blob/main/packages/docusaurus/docs/03-Pangolin/07-clients.md Set up NAT rules using nftables to masquerade traffic from the WireGuard interface, allowing external networks to return traffic to the VPN server. Ensure 'eth0' is replaced with your primary network interface name. ```bash # Create a basic NAT table sudo nft add table nat # Add postrouting chain for masquerading sudo nft add chain nat postrouting { type nat hook postrouting priority 100 \; } # Masquerade traffic from WireGuard interface to external network sudo nft add rule nat postrouting oifname "eth0" masquerade ``` -------------------------------- ### Build Gerbil Application Source: https://github.com/fosrl/docs/blob/main/packages/docusaurus/docs/05-Gerbil/02-developer-guide.md Build the Gerbil application. You can choose to build it using Docker for a containerized environment or directly with Go. ```bash docker build -t gerbil . ``` ```bash go build -o gerbil main.go ``` -------------------------------- ### Wildcard Certificate in acme.json Source: https://github.com/fosrl/docs/blob/main/packages/docusaurus/docs/03-Pangolin/02-Configuration/03-wildcard-certs.md Example of how a wildcard certificate is represented in the acme.json file after successful generation. Note the "*.example.com" in the main domain. ```json { "Certificates": [ { "domain": { "main": "*.example.com" }, "certificate": "...", "key": "...", "Store": "default" } ] } ``` -------------------------------- ### Generate and Push SQLite Schema Source: https://github.com/fosrl/docs/blob/main/packages/docusaurus/docs/09-development.md Generate the database schema and push it to the database. ```bash npm run db:sqlite:generate ``` ```bash npm run db:sqlite:push ``` -------------------------------- ### Create Site Source: https://context7.com/fosrl/docs/llms.txt Creates a new site (network node) within an organization. Sites can connect via Newt, WireGuard, or local network. ```APIDOC ## PUT /org/{orgId}/site ### Description Creates a new site (network node) within an organization. Sites can connect via Newt, WireGuard, or local network. ### Method PUT ### Endpoint /org/{orgId}/site ### Parameters #### Path Parameters - **orgId** (string) - Required - The ID of the organization to create the site in. #### Request Body - **name** (string) - Required - The name of the site. - **type** (string) - Required - The type of site connection (e.g., "newt", "wireguard", "local"). - **pubKey** (string) - Optional - The public key for WireGuard sites. - **subnet** (string) - Optional - The subnet for WireGuard sites. ### Request Example ```bash # Newt site curl -X PUT "https://api.example.com/v1/org/home-lab/site" \ -H "Authorization: Bearer " \ -H "Content-Type: application/json" \ -d '{ "name": "raspberry-pi-cluster", "type": "newt" }' # WireGuard site curl -X PUT "https://api.example.com/v1/org/home-lab/site" \ -H "Authorization: Bearer " \ -H "Content-Type: application/json" \ -d '{ "name": "office-wireguard", "type": "wireguard", "pubKey": "wg-public-key-base64==", "subnet": "100.89.0.1/30" }' ``` ### Response #### Success Response (200) - **data** (object) - Details of the created site. - **siteId** (integer) - The unique identifier for the site. - **name** (string) - The name of the site. - **type** (string) - The type of site connection. - **newtId** (string) - Optional - The Newt ID for Newt sites. - **secret** (string) - Optional - The secret for configuring Newt on the remote site. ```