<?xml version="1.0" encoding="utf-8" standalone="yes" ?>
<rss version="2.0" xmlns:atom="http://www.w3.org/2005/Atom">
  <channel>
    <title>Self-Hosted | Antoine Weill--Duflos</title>
    <link>https://antoine.weill-duflos.fr/en/tag/self-hosted/</link>
      <atom:link href="https://antoine.weill-duflos.fr/en/tag/self-hosted/index.xml" rel="self" type="application/rss+xml" />
    <description>Self-Hosted</description>
    <generator>Hugo Blox Builder (https://hugoblox.com)</generator><language>en-us</language><lastBuildDate>Mon, 13 Apr 2026 00:00:00 +0000</lastBuildDate>
    <image>
      <url>https://antoine.weill-duflos.fr/media/icon_hu_d686267daab28486.png</url>
      <title>Self-Hosted</title>
      <link>https://antoine.weill-duflos.fr/en/tag/self-hosted/</link>
    </image>
    
    <item>
      <title>Everything I Self-Host: The Full Service Catalog</title>
      <link>https://antoine.weill-duflos.fr/en/post/service-catalog/</link>
      <pubDate>Mon, 13 Apr 2026 00:00:00 +0000</pubDate>
      <guid>https://antoine.weill-duflos.fr/en/post/service-catalog/</guid>
      <description>&lt;h1&gt;&lt;/h1&gt;
&lt;p&gt;In a &lt;a href=&#34;https://antoine.weill-duflos.fr/en/post/komodo/&#34;&gt;companion post&lt;/a&gt; I covered the infrastructure and orchestration layer of my homelab. This post is the full service catalog: everything that actually runs on top of that infrastructure.&lt;/p&gt;
&lt;h2 id=&#34;productivity--data&#34;&gt;Productivity &amp;amp; Data&lt;/h2&gt;
&lt;table&gt;
  &lt;thead&gt;
      &lt;tr&gt;
          &lt;th&gt;Service&lt;/th&gt;
          &lt;th&gt;What it does&lt;/th&gt;
      &lt;/tr&gt;
  &lt;/thead&gt;
  &lt;tbody&gt;
      &lt;tr&gt;
          &lt;td&gt;&lt;strong&gt;Nextcloud&lt;/strong&gt;&lt;/td&gt;
          &lt;td&gt;File sync and collaboration&lt;/td&gt;
      &lt;/tr&gt;
      &lt;tr&gt;
          &lt;td&gt;&lt;strong&gt;Paperless&lt;/strong&gt;&lt;/td&gt;
          &lt;td&gt;Document management with OCR&lt;/td&gt;
      &lt;/tr&gt;
      &lt;tr&gt;
          &lt;td&gt;&lt;strong&gt;Grocy&lt;/strong&gt;&lt;/td&gt;
          &lt;td&gt;Grocery and household tracking&lt;/td&gt;
      &lt;/tr&gt;
      &lt;tr&gt;
          &lt;td&gt;&lt;strong&gt;Actual&lt;/strong&gt;&lt;/td&gt;
          &lt;td&gt;Budget tracking&lt;/td&gt;
      &lt;/tr&gt;
      &lt;tr&gt;
          &lt;td&gt;&lt;strong&gt;Monica&lt;/strong&gt;&lt;/td&gt;
          &lt;td&gt;Personal CRM&lt;/td&gt;
      &lt;/tr&gt;
      &lt;tr&gt;
          &lt;td&gt;&lt;strong&gt;NocoDB&lt;/strong&gt;&lt;/td&gt;
          &lt;td&gt;Database web UI (Airtable alternative)&lt;/td&gt;
      &lt;/tr&gt;
      &lt;tr&gt;
          &lt;td&gt;&lt;strong&gt;n8n&lt;/strong&gt;&lt;/td&gt;
          &lt;td&gt;Workflow automation&lt;/td&gt;
      &lt;/tr&gt;
  &lt;/tbody&gt;
&lt;/table&gt;
&lt;h2 id=&#34;media--photos&#34;&gt;Media &amp;amp; Photos&lt;/h2&gt;
&lt;table&gt;
  &lt;thead&gt;
      &lt;tr&gt;
          &lt;th&gt;Service&lt;/th&gt;
          &lt;th&gt;What it does&lt;/th&gt;
      &lt;/tr&gt;
  &lt;/thead&gt;
  &lt;tbody&gt;
      &lt;tr&gt;
          &lt;td&gt;&lt;strong&gt;Immich&lt;/strong&gt; (2 instances)&lt;/td&gt;
          &lt;td&gt;Photo management (Google Photos alternative)&lt;/td&gt;
      &lt;/tr&gt;
      &lt;tr&gt;
          &lt;td&gt;&lt;strong&gt;Jellyfin&lt;/strong&gt;&lt;/td&gt;
          &lt;td&gt;Media streaming server&lt;/td&gt;
      &lt;/tr&gt;
      &lt;tr&gt;
          &lt;td&gt;&lt;strong&gt;Kavita&lt;/strong&gt;&lt;/td&gt;
          &lt;td&gt;Ebook and manga reader&lt;/td&gt;
      &lt;/tr&gt;
      &lt;tr&gt;
          &lt;td&gt;&lt;strong&gt;Prowlarr&lt;/strong&gt;&lt;/td&gt;
          &lt;td&gt;Indexer management&lt;/td&gt;
      &lt;/tr&gt;
      &lt;tr&gt;
          &lt;td&gt;&lt;strong&gt;Strava Stats&lt;/strong&gt;&lt;/td&gt;
          &lt;td&gt;Fitness statistics dashboard&lt;/td&gt;
      &lt;/tr&gt;
  &lt;/tbody&gt;
&lt;/table&gt;
&lt;h2 id=&#34;home-automation--security&#34;&gt;Home Automation &amp;amp; Security&lt;/h2&gt;
&lt;table&gt;
  &lt;thead&gt;
      &lt;tr&gt;
          &lt;th&gt;Service&lt;/th&gt;
          &lt;th&gt;What it does&lt;/th&gt;
      &lt;/tr&gt;
  &lt;/thead&gt;
  &lt;tbody&gt;
      &lt;tr&gt;
          &lt;td&gt;&lt;strong&gt;Home Assistant&lt;/strong&gt;&lt;/td&gt;
          &lt;td&gt;Home automation hub&lt;/td&gt;
      &lt;/tr&gt;
      &lt;tr&gt;
          &lt;td&gt;&lt;strong&gt;Frigate&lt;/strong&gt;&lt;/td&gt;
          &lt;td&gt;NVR with AI object detection (&lt;a href=&#34;https://antoine.weill-duflos.fr/en/post/frigate/&#34;&gt;details&lt;/a&gt;)&lt;/td&gt;
      &lt;/tr&gt;
      &lt;tr&gt;
          &lt;td&gt;&lt;strong&gt;ESPHome&lt;/strong&gt;&lt;/td&gt;
          &lt;td&gt;IoT firmware compiler for custom sensors&lt;/td&gt;
      &lt;/tr&gt;
  &lt;/tbody&gt;
&lt;/table&gt;
&lt;h2 id=&#34;communication&#34;&gt;Communication&lt;/h2&gt;
&lt;table&gt;
  &lt;thead&gt;
      &lt;tr&gt;
          &lt;th&gt;Service&lt;/th&gt;
          &lt;th&gt;What it does&lt;/th&gt;
      &lt;/tr&gt;
  &lt;/thead&gt;
  &lt;tbody&gt;
      &lt;tr&gt;
          &lt;td&gt;&lt;strong&gt;Matrix&lt;/strong&gt;&lt;/td&gt;
          &lt;td&gt;Self-hosted messaging (Synapse)&lt;/td&gt;
      &lt;/tr&gt;
      &lt;tr&gt;
          &lt;td&gt;&lt;strong&gt;TT-RSS&lt;/strong&gt;&lt;/td&gt;
          &lt;td&gt;RSS reader&lt;/td&gt;
      &lt;/tr&gt;
  &lt;/tbody&gt;
&lt;/table&gt;
&lt;h2 id=&#34;ai--compute&#34;&gt;AI &amp;amp; Compute&lt;/h2&gt;
&lt;table&gt;
  &lt;thead&gt;
      &lt;tr&gt;
          &lt;th&gt;Service&lt;/th&gt;
          &lt;th&gt;What it does&lt;/th&gt;
      &lt;/tr&gt;
  &lt;/thead&gt;
  &lt;tbody&gt;
      &lt;tr&gt;
          &lt;td&gt;&lt;strong&gt;Ollama&lt;/strong&gt;&lt;/td&gt;
          &lt;td&gt;LLM inference on Intel Arc B580&lt;/td&gt;
      &lt;/tr&gt;
      &lt;tr&gt;
          &lt;td&gt;&lt;strong&gt;llama.cpp&lt;/strong&gt;&lt;/td&gt;
          &lt;td&gt;Vision model for Frigate scene descriptions&lt;/td&gt;
      &lt;/tr&gt;
      &lt;tr&gt;
          &lt;td&gt;&lt;strong&gt;MCP Server&lt;/strong&gt;&lt;/td&gt;
          &lt;td&gt;Obsidian vault API for AI assistants&lt;/td&gt;
      &lt;/tr&gt;
  &lt;/tbody&gt;
&lt;/table&gt;
&lt;h2 id=&#34;infrastructure&#34;&gt;Infrastructure&lt;/h2&gt;
&lt;table&gt;
  &lt;thead&gt;
      &lt;tr&gt;
          &lt;th&gt;Service&lt;/th&gt;
          &lt;th&gt;What it does&lt;/th&gt;
      &lt;/tr&gt;
  &lt;/thead&gt;
  &lt;tbody&gt;
      &lt;tr&gt;
          &lt;td&gt;&lt;strong&gt;Komodo&lt;/strong&gt;&lt;/td&gt;
          &lt;td&gt;Deployment orchestration (&lt;a href=&#34;https://antoine.weill-duflos.fr/en/post/komodo/&#34;&gt;details&lt;/a&gt;)&lt;/td&gt;
      &lt;/tr&gt;
      &lt;tr&gt;
          &lt;td&gt;&lt;strong&gt;Gitea&lt;/strong&gt;&lt;/td&gt;
          &lt;td&gt;Self-hosted Git&lt;/td&gt;
      &lt;/tr&gt;
      &lt;tr&gt;
          &lt;td&gt;&lt;strong&gt;Traefik&lt;/strong&gt;&lt;/td&gt;
          &lt;td&gt;Reverse proxy with auto TLS&lt;/td&gt;
      &lt;/tr&gt;
      &lt;tr&gt;
          &lt;td&gt;&lt;strong&gt;Authelia&lt;/strong&gt;&lt;/td&gt;
          &lt;td&gt;Single sign-on + two-factor authentication&lt;/td&gt;
      &lt;/tr&gt;
      &lt;tr&gt;
          &lt;td&gt;&lt;strong&gt;Technitium DNS&lt;/strong&gt; (x2)&lt;/td&gt;
          &lt;td&gt;Internal DNS zones (redundant)&lt;/td&gt;
      &lt;/tr&gt;
      &lt;tr&gt;
          &lt;td&gt;&lt;strong&gt;Unbound&lt;/strong&gt;&lt;/td&gt;
          &lt;td&gt;Recursive DNS resolver (on OPNsense)&lt;/td&gt;
      &lt;/tr&gt;
      &lt;tr&gt;
          &lt;td&gt;&lt;strong&gt;OPNsense&lt;/strong&gt;&lt;/td&gt;
          &lt;td&gt;Firewall, router, VPN&lt;/td&gt;
      &lt;/tr&gt;
      &lt;tr&gt;
          &lt;td&gt;&lt;strong&gt;Omada Controller&lt;/strong&gt;&lt;/td&gt;
          &lt;td&gt;WiFi access point management&lt;/td&gt;
      &lt;/tr&gt;
      &lt;tr&gt;
          &lt;td&gt;&lt;strong&gt;Dockge&lt;/strong&gt;&lt;/td&gt;
          &lt;td&gt;Docker Compose UI&lt;/td&gt;
      &lt;/tr&gt;
  &lt;/tbody&gt;
&lt;/table&gt;
&lt;h2 id=&#34;monitoring--observability&#34;&gt;Monitoring &amp;amp; Observability&lt;/h2&gt;
&lt;table&gt;
  &lt;thead&gt;
      &lt;tr&gt;
          &lt;th&gt;Service&lt;/th&gt;
          &lt;th&gt;What it does&lt;/th&gt;
      &lt;/tr&gt;
  &lt;/thead&gt;
  &lt;tbody&gt;
      &lt;tr&gt;
          &lt;td&gt;&lt;strong&gt;Prometheus&lt;/strong&gt;&lt;/td&gt;
          &lt;td&gt;Metrics collection&lt;/td&gt;
      &lt;/tr&gt;
      &lt;tr&gt;
          &lt;td&gt;&lt;strong&gt;Grafana&lt;/strong&gt;&lt;/td&gt;
          &lt;td&gt;Dashboards and visualization&lt;/td&gt;
      &lt;/tr&gt;
      &lt;tr&gt;
          &lt;td&gt;&lt;strong&gt;Uptime Kuma&lt;/strong&gt;&lt;/td&gt;
          &lt;td&gt;Service uptime monitoring&lt;/td&gt;
      &lt;/tr&gt;
      &lt;tr&gt;
          &lt;td&gt;&lt;strong&gt;cAdvisor&lt;/strong&gt; (x2)&lt;/td&gt;
          &lt;td&gt;Container resource metrics&lt;/td&gt;
      &lt;/tr&gt;
      &lt;tr&gt;
          &lt;td&gt;&lt;strong&gt;NetAlertX&lt;/strong&gt;&lt;/td&gt;
          &lt;td&gt;Network device monitoring&lt;/td&gt;
      &lt;/tr&gt;
      &lt;tr&gt;
          &lt;td&gt;&lt;strong&gt;LibreSpeed&lt;/strong&gt;&lt;/td&gt;
          &lt;td&gt;LAN speed testing&lt;/td&gt;
      &lt;/tr&gt;
      &lt;tr&gt;
          &lt;td&gt;&lt;strong&gt;MySpeed&lt;/strong&gt;&lt;/td&gt;
          &lt;td&gt;Internet speed tracking over time&lt;/td&gt;
      &lt;/tr&gt;
      &lt;tr&gt;
          &lt;td&gt;&lt;strong&gt;ntfy&lt;/strong&gt;&lt;/td&gt;
          &lt;td&gt;Push notifications&lt;/td&gt;
      &lt;/tr&gt;
      &lt;tr&gt;
          &lt;td&gt;&lt;strong&gt;Chrony + GPS&lt;/strong&gt;&lt;/td&gt;
          &lt;td&gt;Stratum 1 NTP time source&lt;/td&gt;
      &lt;/tr&gt;
  &lt;/tbody&gt;
&lt;/table&gt;
&lt;h2 id=&#34;backup--sync&#34;&gt;Backup &amp;amp; Sync&lt;/h2&gt;
&lt;table&gt;
  &lt;thead&gt;
      &lt;tr&gt;
          &lt;th&gt;Service&lt;/th&gt;
          &lt;th&gt;What it does&lt;/th&gt;
      &lt;/tr&gt;
  &lt;/thead&gt;
  &lt;tbody&gt;
      &lt;tr&gt;
          &lt;td&gt;&lt;strong&gt;Proxmox Backup Server&lt;/strong&gt;&lt;/td&gt;
          &lt;td&gt;VM and container backups&lt;/td&gt;
      &lt;/tr&gt;
      &lt;tr&gt;
          &lt;td&gt;&lt;strong&gt;Resilio Sync&lt;/strong&gt; (x2)&lt;/td&gt;
          &lt;td&gt;Cross-site file synchronization&lt;/td&gt;
      &lt;/tr&gt;
      &lt;tr&gt;
          &lt;td&gt;&lt;strong&gt;Storj&lt;/strong&gt;&lt;/td&gt;
          &lt;td&gt;Decentralized storage node&lt;/td&gt;
      &lt;/tr&gt;
  &lt;/tbody&gt;
&lt;/table&gt;
&lt;h2 id=&#34;security--access&#34;&gt;Security &amp;amp; Access&lt;/h2&gt;
&lt;table&gt;
  &lt;thead&gt;
      &lt;tr&gt;
          &lt;th&gt;Service&lt;/th&gt;
          &lt;th&gt;What it does&lt;/th&gt;
      &lt;/tr&gt;
  &lt;/thead&gt;
  &lt;tbody&gt;
      &lt;tr&gt;
          &lt;td&gt;&lt;strong&gt;Vaultwarden&lt;/strong&gt;&lt;/td&gt;
          &lt;td&gt;Bitwarden-compatible password manager&lt;/td&gt;
      &lt;/tr&gt;
      &lt;tr&gt;
          &lt;td&gt;&lt;strong&gt;Guacamole&lt;/strong&gt;&lt;/td&gt;
          &lt;td&gt;Browser-based remote desktop&lt;/td&gt;
      &lt;/tr&gt;
      &lt;tr&gt;
          &lt;td&gt;&lt;strong&gt;WireGuard&lt;/strong&gt;&lt;/td&gt;
          &lt;td&gt;VPN (on OPNsense)&lt;/td&gt;
      &lt;/tr&gt;
  &lt;/tbody&gt;
&lt;/table&gt;
&lt;h2 id=&#34;web--analytics&#34;&gt;Web &amp;amp; Analytics&lt;/h2&gt;
&lt;table&gt;
  &lt;thead&gt;
      &lt;tr&gt;
          &lt;th&gt;Service&lt;/th&gt;
          &lt;th&gt;What it does&lt;/th&gt;
      &lt;/tr&gt;
  &lt;/thead&gt;
  &lt;tbody&gt;
      &lt;tr&gt;
          &lt;td&gt;&lt;strong&gt;Matomo&lt;/strong&gt;&lt;/td&gt;
          &lt;td&gt;Privacy-respecting web analytics&lt;/td&gt;
      &lt;/tr&gt;
      &lt;tr&gt;
          &lt;td&gt;&lt;strong&gt;Whoogle&lt;/strong&gt;&lt;/td&gt;
          &lt;td&gt;Private Google search proxy&lt;/td&gt;
      &lt;/tr&gt;
  &lt;/tbody&gt;
&lt;/table&gt;
&lt;h2 id=&#34;why-self-host-all-of-this&#34;&gt;Why self-host all of this?&lt;/h2&gt;
&lt;p&gt;The obvious question is: why not just use cloud services? A few reasons:&lt;/p&gt;
&lt;p&gt;&lt;strong&gt;Data sovereignty.&lt;/strong&gt; My photos, documents, passwords, and communications stay on hardware I control. No third party is mining my data or training models on it.&lt;/p&gt;
&lt;p&gt;&lt;strong&gt;No subscriptions.&lt;/strong&gt; The total recurring cost is electricity. No monthly fees for photo storage, file sync, password management, or any of the other services that cloud providers love to charge for.&lt;/p&gt;
&lt;p&gt;&lt;strong&gt;Reliability.&lt;/strong&gt; My services don&amp;rsquo;t go down when someone else&amp;rsquo;s cloud has an outage. They also don&amp;rsquo;t get discontinued, acquired, or enshittified.&lt;/p&gt;
&lt;p&gt;&lt;strong&gt;Learning.&lt;/strong&gt; Running this infrastructure teaches you more about networking, Linux, containers, storage, and monitoring than any course ever could.&lt;/p&gt;
&lt;p&gt;The trade-off is maintenance time. But with proper orchestration (see the &lt;a href=&#34;https://antoine.weill-duflos.fr/en/post/komodo/&#34;&gt;Komodo post&lt;/a&gt;), that time is minimal. Most days, everything just runs.&lt;/p&gt;
</description>
    </item>
    
    <item>
      <title>Self-Hosted GitOps at Home: Managing 30&#43; Services with Komodo and a Proxmox Cluster</title>
      <link>https://antoine.weill-duflos.fr/en/post/komodo/</link>
      <pubDate>Mon, 13 Apr 2026 00:00:00 +0000</pubDate>
      <guid>https://antoine.weill-duflos.fr/en/post/komodo/</guid>
      <description>&lt;h1&gt;&lt;/h1&gt;
&lt;p&gt;Running a handful of self-hosted services is easy. A single &lt;code&gt;docker-compose up&lt;/code&gt; and you&amp;rsquo;re done. But at some point, &amp;ldquo;a handful&amp;rdquo; turns into 30+ stacks spread across multiple servers, and suddenly you need a real way to manage it all. That&amp;rsquo;s where my setup is today, and the most interesting part isn&amp;rsquo;t any single service: it&amp;rsquo;s the orchestration layer that ties everything together.&lt;/p&gt;
&lt;h2 id=&#34;the-problem&#34;&gt;The problem&lt;/h2&gt;
&lt;p&gt;I run a lot of services at home. Photo management, home automation, file sync, NVR with AI detection, a personal CRM, RSS reader, document management, password manager, analytics, a Matrix chat server, LLM inference&amp;hellip; the list goes on. Each one is a Docker Compose stack. Each one needs to be deployed, updated, monitored, and occasionally debugged.&lt;/p&gt;
&lt;p&gt;For a while, I managed everything manually: SSH into a server, &lt;code&gt;cd&lt;/code&gt; to the right directory, &lt;code&gt;docker compose pull &amp;amp;&amp;amp; docker compose up -d&lt;/code&gt;, check the logs. It works, but it doesn&amp;rsquo;t scale. When you&amp;rsquo;re managing services across six different hosts, you spend more time on logistics than on actually using the things you&amp;rsquo;ve built.&lt;/p&gt;
&lt;p&gt;I needed a control plane.&lt;/p&gt;
&lt;h2 id=&#34;the-hardware-a-proxmox-cluster&#34;&gt;The hardware: a Proxmox cluster&lt;/h2&gt;
&lt;p&gt;Everything runs on a &lt;strong&gt;Proxmox VE&lt;/strong&gt; cluster built from repurposed enterprise hardware:&lt;/p&gt;
&lt;table&gt;
  &lt;thead&gt;
      &lt;tr&gt;
          &lt;th&gt;Node&lt;/th&gt;
          &lt;th&gt;CPU&lt;/th&gt;
          &lt;th&gt;RAM&lt;/th&gt;
          &lt;th&gt;Role&lt;/th&gt;
      &lt;/tr&gt;
  &lt;/thead&gt;
  &lt;tbody&gt;
      &lt;tr&gt;
          &lt;td&gt;Primary&lt;/td&gt;
          &lt;td&gt;Xeon E5-2640 (12 cores @ 2.5 GHz)&lt;/td&gt;
          &lt;td&gt;32 GB&lt;/td&gt;
          &lt;td&gt;Main workloads&lt;/td&gt;
      &lt;/tr&gt;
      &lt;tr&gt;
          &lt;td&gt;Secondary&lt;/td&gt;
          &lt;td&gt;Xeon E5-2430 (12 cores @ 2.2 GHz)&lt;/td&gt;
          &lt;td&gt;24 GB&lt;/td&gt;
          &lt;td&gt;Secondary workloads&lt;/td&gt;
      &lt;/tr&gt;
  &lt;/tbody&gt;
&lt;/table&gt;
&lt;p&gt;These are old servers, the kind you can pick up for next to nothing. They&amp;rsquo;re loud, they draw power, and they have more compute than I&amp;rsquo;ll ever need. Perfect for a homelab.&lt;/p&gt;
&lt;p&gt;The cluster runs about 40 LXC containers. LXC containers are the real workhorse here: they&amp;rsquo;re lighter than VMs, boot in seconds, and give you proper isolation without the overhead of full virtualization. Most of my Docker hosts are LXC containers with a few gigs of RAM each.&lt;/p&gt;
&lt;h2 id=&#34;the-servers-who-does-what&#34;&gt;The servers: who does what&lt;/h2&gt;
&lt;p&gt;Not every LXC container runs Docker. Some run standalone services (DNS, monitoring, reverse proxy, authentication). But the Docker hosts are grouped logically in &lt;strong&gt;Komodo&lt;/strong&gt; as &amp;ldquo;servers&amp;rdquo;: each one is a lightweight LXC container dedicated to running a set of related stacks. Komodo sees six servers in total: a couple of general-purpose Docker hosts, a dedicated Home Assistant instance, a photo management host, an alerting container, and the vault.&lt;/p&gt;
&lt;p&gt;The &lt;strong&gt;vault&lt;/strong&gt; is the most interesting one. It&amp;rsquo;s actually a NAS running &lt;strong&gt;OpenMediaVault&lt;/strong&gt; with an &lt;strong&gt;Intel Arc B580&lt;/strong&gt; GPU installed. That one card handles hardware video decoding for Frigate&amp;rsquo;s camera streams, AI object detection, &lt;em&gt;and&lt;/em&gt; LLM inference via Ollama, all at the same time. I wrote about the Frigate side of this in a &lt;a href=&#34;https://antoine.weill-duflos.fr/en/post/frigate/&#34;&gt;previous post&lt;/a&gt;.&lt;/p&gt;
&lt;h2 id=&#34;enter-komodo&#34;&gt;Enter Komodo&lt;/h2&gt;
&lt;p&gt;&lt;a href=&#34;https://komo.do/&#34; target=&#34;_blank&#34; rel=&#34;noopener&#34;&gt;Komodo&lt;/a&gt; is a self-hosted deployment manager. Think of it as a lightweight alternative to Portainer or Coolify, but with a focus on managing Docker Compose stacks across multiple servers. Here&amp;rsquo;s why I picked it:&lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;&lt;strong&gt;Multi-server management from a single dashboard.&lt;/strong&gt; One UI to see and control every stack on every server.&lt;/li&gt;
&lt;li&gt;&lt;strong&gt;Git-based deployments.&lt;/strong&gt; Stacks can pull their compose files from a Git repository. Push a change, and Komodo deploys it.&lt;/li&gt;
&lt;li&gt;&lt;strong&gt;Webhook-triggered updates.&lt;/strong&gt; My self-hosted Gitea instance sends webhooks to Komodo on every push. The stack redeploys automatically.&lt;/li&gt;
&lt;li&gt;&lt;strong&gt;Auto-update for container images.&lt;/strong&gt; Komodo can poll for new images and update containers without manual intervention.&lt;/li&gt;
&lt;li&gt;&lt;strong&gt;Environment variable management.&lt;/strong&gt; Secrets and config live in Komodo, not in the Git repo.&lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;The architecture looks like this: a central &lt;strong&gt;Komodo Core&lt;/strong&gt; instance runs on one server, and a lightweight &lt;strong&gt;Komodo Periphery&lt;/strong&gt; agent runs on each remote host. The core talks to periphery agents to deploy and manage stacks. It&amp;rsquo;s simple, reliable, and doesn&amp;rsquo;t require Kubernetes.&lt;/p&gt;
&lt;h2 id=&#34;the-gitops-workflow&#34;&gt;The GitOps workflow&lt;/h2&gt;
&lt;p&gt;This is where it gets interesting. About half of my stacks are managed through Git repositories on my self-hosted &lt;strong&gt;Gitea&lt;/strong&gt; instance. The workflow:&lt;/p&gt;
&lt;ol&gt;
&lt;li&gt;I edit a &lt;code&gt;docker-compose.yml&lt;/code&gt; in a Gitea repo&lt;/li&gt;
&lt;li&gt;I push the change&lt;/li&gt;
&lt;li&gt;Gitea fires a webhook to Komodo&lt;/li&gt;
&lt;li&gt;Komodo pulls the updated compose file&lt;/li&gt;
&lt;li&gt;Komodo redeploys the stack on the target server&lt;/li&gt;
&lt;/ol&gt;
&lt;p&gt;For stacks that don&amp;rsquo;t need version-controlled compose files (simpler services), Komodo manages the files directly on the host. I can still edit them through the Komodo UI, but they aren&amp;rsquo;t backed by Git.&lt;/p&gt;
&lt;p&gt;The split is intentional. Complex stacks with multiple services, custom configs, or frequent changes live in Git. Simple single-container services are managed inline. This avoids the overhead of Git for things that don&amp;rsquo;t need it, while giving me full version history and rollback for the things that do.&lt;/p&gt;
&lt;h3 id=&#34;home-assistant-a-special-case&#34;&gt;Home Assistant: a special case&lt;/h3&gt;
&lt;p&gt;Home Assistant deserves a mention because it&amp;rsquo;s managed differently. Its entire configuration is in a Gitea repo, and Komodo watches it with both polling and webhooks. When I push a config change, Home Assistant gets the update automatically. No more SSH-ing in to edit &lt;code&gt;configuration.yaml&lt;/code&gt;.&lt;/p&gt;
&lt;h2 id=&#34;the-network-opnsense-and-vlans&#34;&gt;The network: OPNsense and VLANs&lt;/h2&gt;
&lt;p&gt;Running dozens of services on a flat network would be a security nightmare. I use &lt;strong&gt;OPNsense&lt;/strong&gt; as my firewall/router with multiple VLANs:&lt;/p&gt;
&lt;table&gt;
  &lt;thead&gt;
      &lt;tr&gt;
          &lt;th&gt;Network segment&lt;/th&gt;
          &lt;th&gt;Purpose&lt;/th&gt;
      &lt;/tr&gt;
  &lt;/thead&gt;
  &lt;tbody&gt;
      &lt;tr&gt;
          &lt;td&gt;&lt;strong&gt;Main&lt;/strong&gt;&lt;/td&gt;
          &lt;td&gt;Servers and trusted devices&lt;/td&gt;
      &lt;/tr&gt;
      &lt;tr&gt;
          &lt;td&gt;&lt;strong&gt;IoT&lt;/strong&gt;&lt;/td&gt;
          &lt;td&gt;Smart home devices (cameras, sensors, ESPHome)&lt;/td&gt;
      &lt;/tr&gt;
      &lt;tr&gt;
          &lt;td&gt;&lt;strong&gt;Lab&lt;/strong&gt;&lt;/td&gt;
          &lt;td&gt;Experimental VMs and containers&lt;/td&gt;
      &lt;/tr&gt;
      &lt;tr&gt;
          &lt;td&gt;&lt;strong&gt;WireGuard&lt;/strong&gt;&lt;/td&gt;
          &lt;td&gt;VPN access from outside&lt;/td&gt;
      &lt;/tr&gt;
  &lt;/tbody&gt;
&lt;/table&gt;
&lt;p&gt;IoT devices can&amp;rsquo;t talk to each other or to the main network directly; they can only reach the services they need (Home Assistant, Frigate). The lab network is isolated for testing. WireGuard gives me secure remote access to everything.&lt;/p&gt;
&lt;h3 id=&#34;dns-unbound--technitium&#34;&gt;DNS: Unbound + Technitium&lt;/h3&gt;
&lt;p&gt;DNS is handled by two layers working together:&lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;&lt;strong&gt;Unbound&lt;/strong&gt; runs on OPNsense itself as the primary recursive resolver. It handles upstream DNS resolution with DNSSEC validation, and it&amp;rsquo;s fast: queries are answered from cache most of the time.&lt;/li&gt;
&lt;li&gt;&lt;strong&gt;Technitium DNS&lt;/strong&gt; (running in two LXC containers for redundancy) handles internal DNS zones, so I can reach services by name instead of memorizing IPs. It also provides split-horizon DNS for services that need different answers internally vs. externally.&lt;/li&gt;
&lt;/ul&gt;
&lt;h3 id=&#34;ntp-gps-disciplined-time-with-chrony&#34;&gt;NTP: GPS-disciplined time with Chrony&lt;/h3&gt;
&lt;p&gt;One detail I&amp;rsquo;m particularly happy with: the network&amp;rsquo;s time source is a &lt;strong&gt;USB GPS receiver&lt;/strong&gt; (BN-808, u-blox M8N chipset) connected to a dedicated LXC container running &lt;strong&gt;Chrony&lt;/strong&gt;. The GPS provides Stratum 1 time to the entire network.&lt;/p&gt;
&lt;p&gt;The setup isn&amp;rsquo;t perfect: USB GPS doesn&amp;rsquo;t support PPS (Pulse Per Second), so precision is limited to about 40ms due to USB latency. Chrony compensates for this with a manual offset correction and falls back to internet NTP servers (Cloudflare, public pools) when needed. OPNsense distributes the time to all clients on the network.&lt;/p&gt;
&lt;p&gt;It&amp;rsquo;s overkill for a homelab, but there&amp;rsquo;s something satisfying about having your own GPS-disciplined time source rather than depending entirely on external NTP pools.&lt;/p&gt;
&lt;p&gt;&lt;strong&gt;Authelia&lt;/strong&gt; provides single sign-on with two-factor authentication in front of all web-facing services, with &lt;strong&gt;Traefik&lt;/strong&gt; as the reverse proxy.&lt;/p&gt;
&lt;h2 id=&#34;storage-the-vault-nas&#34;&gt;Storage: the vault NAS&lt;/h2&gt;
&lt;p&gt;The &amp;ldquo;vault&amp;rdquo; server is an &lt;strong&gt;OpenMediaVault&lt;/strong&gt; NAS that does double duty as a compute node. It has 8 drives, one NVMe for the OS and 7 HDDs ranging from 2 TB to 16 TB:&lt;/p&gt;
&lt;table&gt;
  &lt;thead&gt;
      &lt;tr&gt;
          &lt;th&gt;Drive&lt;/th&gt;
          &lt;th&gt;Model&lt;/th&gt;
          &lt;th&gt;Capacity&lt;/th&gt;
      &lt;/tr&gt;
  &lt;/thead&gt;
  &lt;tbody&gt;
      &lt;tr&gt;
          &lt;td&gt;NVMe&lt;/td&gt;
          &lt;td&gt;WD BLACK SN770&lt;/td&gt;
          &lt;td&gt;500 GB (boot)&lt;/td&gt;
      &lt;/tr&gt;
      &lt;tr&gt;
          &lt;td&gt;HDD 1&lt;/td&gt;
          &lt;td&gt;Seagate IronWolf&lt;/td&gt;
          &lt;td&gt;10 TB&lt;/td&gt;
      &lt;/tr&gt;
      &lt;tr&gt;
          &lt;td&gt;HDD 2&lt;/td&gt;
          &lt;td&gt;WD&lt;/td&gt;
          &lt;td&gt;10 TB&lt;/td&gt;
      &lt;/tr&gt;
      &lt;tr&gt;
          &lt;td&gt;HDD 3&lt;/td&gt;
          &lt;td&gt;WD&lt;/td&gt;
          &lt;td&gt;12 TB&lt;/td&gt;
      &lt;/tr&gt;
      &lt;tr&gt;
          &lt;td&gt;HDD 4&lt;/td&gt;
          &lt;td&gt;WD Green&lt;/td&gt;
          &lt;td&gt;2 TB&lt;/td&gt;
      &lt;/tr&gt;
      &lt;tr&gt;
          &lt;td&gt;HDD 5&lt;/td&gt;
          &lt;td&gt;WD Red&lt;/td&gt;
          &lt;td&gt;2 TB&lt;/td&gt;
      &lt;/tr&gt;
      &lt;tr&gt;
          &lt;td&gt;HDD 6&lt;/td&gt;
          &lt;td&gt;Seagate IronWolf Pro&lt;/td&gt;
          &lt;td&gt;16 TB&lt;/td&gt;
      &lt;/tr&gt;
      &lt;tr&gt;
          &lt;td&gt;HDD 7&lt;/td&gt;
          &lt;td&gt;HGST Deskstar NAS&lt;/td&gt;
          &lt;td&gt;6 TB&lt;/td&gt;
      &lt;/tr&gt;
  &lt;/tbody&gt;
&lt;/table&gt;
&lt;p&gt;A mix of whatever drives I had or found on sale. The beauty of my storage setup is that it doesn&amp;rsquo;t care about uniformity.&lt;/p&gt;
&lt;h3 id=&#34;the-nested-mergerfs-architecture&#34;&gt;The nested mergerfs architecture&lt;/h3&gt;
&lt;p&gt;Storage is organized in layers using &lt;strong&gt;mergerfs&lt;/strong&gt; pools:&lt;/p&gt;
&lt;ol&gt;
&lt;li&gt;
&lt;p&gt;&lt;strong&gt;A parity-protected pool&lt;/strong&gt;: a mergerfs pool combining 3 btrfs-formatted drives. These drives are protected by &lt;strong&gt;SnapRAID&lt;/strong&gt; parity (the 16 TB Seagate acts as the parity drive).&lt;/p&gt;
&lt;/li&gt;
&lt;li&gt;
&lt;p&gt;&lt;strong&gt;A main pool&lt;/strong&gt;: a super-pool that merges the parity-protected pool with an additional direct drive into one large namespace. This is where Immich stores photos, Kavita stores books, and Frigate stores video clips.&lt;/p&gt;
&lt;/li&gt;
&lt;li&gt;
&lt;p&gt;&lt;strong&gt;A read-only photos pool&lt;/strong&gt;: a mergerfs view that aggregates all my photo directories (personal photos, DCIM camera imports) into a single mount point for easy access and import.&lt;/p&gt;
&lt;/li&gt;
&lt;/ol&gt;
&lt;p&gt;SnapRAID does parity syncs on a schedule (not real-time like traditional RAID), which means:&lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;There&amp;rsquo;s no write penalty; writes go directly to the underlying btrfs drives&lt;/li&gt;
&lt;li&gt;If a drive fails, I can recover its contents from parity + the remaining drives&lt;/li&gt;
&lt;li&gt;Drives can be different sizes (and they very much are)&lt;/li&gt;
&lt;li&gt;Each drive is a standard filesystem you can read independently in an emergency&lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;The trade-off is that data written between parity syncs is unprotected. For a homelab storing photos and media, that&amp;rsquo;s an acceptable risk.&lt;/p&gt;
&lt;p&gt;&lt;strong&gt;Proxmox Backup Server&lt;/strong&gt; also runs in Docker on this same NAS, providing VM and container backups from the Proxmox cluster. Both Proxmox nodes mount the vault&amp;rsquo;s PBS storage directly.&lt;/p&gt;
&lt;h2 id=&#34;monitoring-and-alerting&#34;&gt;Monitoring and alerting&lt;/h2&gt;
&lt;p&gt;You can&amp;rsquo;t manage what you can&amp;rsquo;t see. The monitoring stack:&lt;/p&gt;
&lt;table&gt;
  &lt;thead&gt;
      &lt;tr&gt;
          &lt;th&gt;Tool&lt;/th&gt;
          &lt;th&gt;Role&lt;/th&gt;
      &lt;/tr&gt;
  &lt;/thead&gt;
  &lt;tbody&gt;
      &lt;tr&gt;
          &lt;td&gt;&lt;strong&gt;Prometheus&lt;/strong&gt;&lt;/td&gt;
          &lt;td&gt;Metrics collection&lt;/td&gt;
      &lt;/tr&gt;
      &lt;tr&gt;
          &lt;td&gt;&lt;strong&gt;Grafana&lt;/strong&gt;&lt;/td&gt;
          &lt;td&gt;Dashboards and visualization&lt;/td&gt;
      &lt;/tr&gt;
      &lt;tr&gt;
          &lt;td&gt;&lt;strong&gt;Uptime Kuma&lt;/strong&gt;&lt;/td&gt;
          &lt;td&gt;Service uptime monitoring&lt;/td&gt;
      &lt;/tr&gt;
      &lt;tr&gt;
          &lt;td&gt;&lt;strong&gt;cAdvisor&lt;/strong&gt;&lt;/td&gt;
          &lt;td&gt;Container resource metrics&lt;/td&gt;
      &lt;/tr&gt;
      &lt;tr&gt;
          &lt;td&gt;&lt;strong&gt;NetAlertX&lt;/strong&gt;&lt;/td&gt;
          &lt;td&gt;Network device monitoring&lt;/td&gt;
      &lt;/tr&gt;
      &lt;tr&gt;
          &lt;td&gt;&lt;strong&gt;ntfy&lt;/strong&gt;&lt;/td&gt;
          &lt;td&gt;Push notifications to my phone&lt;/td&gt;
      &lt;/tr&gt;
  &lt;/tbody&gt;
&lt;/table&gt;
&lt;p&gt;Komodo itself integrates with &lt;strong&gt;ntfy&lt;/strong&gt; for deployment alerts. If a stack fails to deploy or a container goes unhealthy, I get a push notification immediately. The ntfy-alerter stack maps Komodo alert severity to ntfy priority levels, so a critical alert gets a high-priority push that bypasses Do Not Disturb.&lt;/p&gt;
&lt;p&gt;The whole thing runs 24/7, manages itself for the most part, and costs nothing beyond electricity and the initial hardware investment. When something does need attention, Komodo and ntfy make sure I know about it, and the GitOps workflow means I can fix most things with a &lt;code&gt;git push&lt;/code&gt; from my phone.&lt;/p&gt;
&lt;p&gt;If you&amp;rsquo;re running more than a handful of self-hosted services and you&amp;rsquo;re still managing them manually, give &lt;a href=&#34;https://komo.do/&#34; target=&#34;_blank&#34; rel=&#34;noopener&#34;&gt;Komodo&lt;/a&gt; a look. It turned my homelab from a collection of Docker hosts into a proper managed platform.&lt;/p&gt;
</description>
    </item>
    
    <item>
      <title>Ditching Cloud Cameras: Self-Hosted Security with Frigate, Tapo, and an Intel Arc B580</title>
      <link>https://antoine.weill-duflos.fr/en/post/frigate/</link>
      <pubDate>Sun, 12 Apr 2026 00:00:00 +0000</pubDate>
      <guid>https://antoine.weill-duflos.fr/en/post/frigate/</guid>
      <description>&lt;h1&gt;&lt;/h1&gt;
&lt;p&gt;I live in Canada. At some point I started noticing signs that someone (or something) had been visiting my garden. Could be an animal, could be a person. Hard to tell. So I figured it was time to put up some cameras. What started as a simple purchase ended up becoming a proper self-hosted setup with AI-based detection. Here&amp;rsquo;s the story.&lt;/p&gt;
&lt;h2 id=&#34;the-starting-point-amazon-blink&#34;&gt;The starting point: Amazon Blink&lt;/h2&gt;
&lt;p&gt;I went with &lt;strong&gt;Amazon Blink&lt;/strong&gt; cameras first. They&amp;rsquo;re cheap, battery-powered, motion-triggered, and they handle Canadian winters without issues. No wiring needed, no network setup. Just stick them up and go.&lt;/p&gt;
&lt;p&gt;The problem? False positives. Constantly. A branch moving in the wind, a shadow, snowfall&amp;hellip; everything triggers an alert. After a few weeks of this you either start ignoring all notifications (which defeats the whole point) or you waste time scrubbing through clips of nothing. Neither option is great.&lt;/p&gt;
&lt;p&gt;That&amp;rsquo;s when I started reading about &lt;strong&gt;Frigate&lt;/strong&gt; and RTSP cameras, and things got interesting.&lt;/p&gt;
&lt;h2 id=&#34;the-new-setup&#34;&gt;The new setup&lt;/h2&gt;
&lt;h3 id=&#34;tapo-cameras&#34;&gt;Tapo cameras&lt;/h3&gt;
&lt;p&gt;I swapped the Blinks for &lt;strong&gt;Tapo&lt;/strong&gt; cameras. The big deal with these is that they support &lt;strong&gt;RTSP streaming&lt;/strong&gt; natively and have a &lt;strong&gt;micro SD card slot&lt;/strong&gt; for local recording. So you get:&lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;A local backup on the SD card even if your network goes down&lt;/li&gt;
&lt;li&gt;A direct video stream over WiFi to your NVR, no cloud relay involved&lt;/li&gt;
&lt;li&gt;Cameras that work 100% on your local network, no account or subscription required&lt;/li&gt;
&lt;/ul&gt;
&lt;h3 id=&#34;frigate&#34;&gt;Frigate&lt;/h3&gt;
&lt;p&gt;&lt;a href=&#34;https://frigate.video/&#34; target=&#34;_blank&#34; rel=&#34;noopener&#34;&gt;Frigate&lt;/a&gt; is an open-source NVR (network video recorder) and it has come a really long way. It gives you:&lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;A single dashboard with live views from all your cameras&lt;/li&gt;
&lt;li&gt;Motion detection as a first-pass filter&lt;/li&gt;
&lt;li&gt;AI object detection that tells you &lt;em&gt;what&lt;/em&gt; moved (person, animal, car&amp;hellip;)&lt;/li&gt;
&lt;li&gt;Full scene descriptions that explain what is actually happening in the clip&lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;That last part is the game changer. Instead of getting &amp;ldquo;motion detected&amp;rdquo; you get something like this:&lt;/p&gt;
&lt;blockquote&gt;
&lt;p&gt;&lt;strong&gt;Person picks up bicycle wheel&lt;/strong&gt;
A person enters the frame from the bottom right and walks toward the center of the area where a bicycle wheel is lying on the ground. The person bends down, picks up the bicycle wheel, and stands holding it. The individual then turns and walks back toward the camera, exiting the frame at the bottom.&lt;/p&gt;
&lt;/blockquote&gt;
&lt;p&gt;With that kind of detail, I only get notified when something real is going on.&lt;/p&gt;
&lt;h2 id=&#34;hardware-intel-arc-b580&#34;&gt;Hardware: Intel Arc B580&lt;/h2&gt;
&lt;p&gt;I added an &lt;strong&gt;Intel Arc B580&lt;/strong&gt; (Battlemage) to my server. This one card does double duty:&lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;&lt;strong&gt;Video decoding&lt;/strong&gt;: hardware-accelerated decode of all the RTSP streams&lt;/li&gt;
&lt;li&gt;&lt;strong&gt;AI inference&lt;/strong&gt;: runs the detection and description models&lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;The B580 support in Frigate is actually pretty solid. Both workloads run on the GPU at the same time, so the CPU barely notices. The descriptions aren&amp;rsquo;t always perfect but they&amp;rsquo;re more than good enough to filter out noise and only alert on real events.&lt;/p&gt;
&lt;p&gt;One card, reasonable power draw, no need for a separate ML box. Works well.&lt;/p&gt;
&lt;h3 id=&#34;the-scene-description-model-llamacpp--vulkan&#34;&gt;The scene description model: llama.cpp + Vulkan&lt;/h3&gt;
&lt;p&gt;The AI descriptions don&amp;rsquo;t come from the cloud either. I run a local LLM server using &lt;a href=&#34;https://github.com/ggml-org/llama.cpp&#34; target=&#34;_blank&#34; rel=&#34;noopener&#34;&gt;llama.cpp&lt;/a&gt; with Vulkan backend on the B580. Frigate sends snapshots to it via an OpenAI-compatible API endpoint, and the model returns scene descriptions.&lt;/p&gt;
&lt;p&gt;Here&amp;rsquo;s the docker-compose for the inference server:&lt;/p&gt;
&lt;div class=&#34;highlight&#34;&gt;&lt;pre tabindex=&#34;0&#34; class=&#34;chroma&#34;&gt;&lt;code class=&#34;language-yaml&#34; data-lang=&#34;yaml&#34;&gt;&lt;span class=&#34;line&#34;&gt;&lt;span class=&#34;cl&#34;&gt;&lt;span class=&#34;nt&#34;&gt;version&lt;/span&gt;&lt;span class=&#34;p&#34;&gt;:&lt;/span&gt;&lt;span class=&#34;w&#34;&gt; &lt;/span&gt;&lt;span class=&#34;s2&#34;&gt;&amp;#34;3.9&amp;#34;&lt;/span&gt;&lt;span class=&#34;w&#34;&gt;
&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;span class=&#34;line&#34;&gt;&lt;span class=&#34;cl&#34;&gt;&lt;span class=&#34;nt&#34;&gt;services&lt;/span&gt;&lt;span class=&#34;p&#34;&gt;:&lt;/span&gt;&lt;span class=&#34;w&#34;&gt;
&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;span class=&#34;line&#34;&gt;&lt;span class=&#34;cl&#34;&gt;&lt;span class=&#34;w&#34;&gt;  &lt;/span&gt;&lt;span class=&#34;nt&#34;&gt;llama-server-intel&lt;/span&gt;&lt;span class=&#34;p&#34;&gt;:&lt;/span&gt;&lt;span class=&#34;w&#34;&gt;
&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;span class=&#34;line&#34;&gt;&lt;span class=&#34;cl&#34;&gt;&lt;span class=&#34;w&#34;&gt;    &lt;/span&gt;&lt;span class=&#34;nt&#34;&gt;image&lt;/span&gt;&lt;span class=&#34;p&#34;&gt;:&lt;/span&gt;&lt;span class=&#34;w&#34;&gt; &lt;/span&gt;&lt;span class=&#34;l&#34;&gt;ghcr.io/ggml-org/llama.cpp:server-vulkan&lt;/span&gt;&lt;span class=&#34;w&#34;&gt;
&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;span class=&#34;line&#34;&gt;&lt;span class=&#34;cl&#34;&gt;&lt;span class=&#34;w&#34;&gt;    &lt;/span&gt;&lt;span class=&#34;nt&#34;&gt;container_name&lt;/span&gt;&lt;span class=&#34;p&#34;&gt;:&lt;/span&gt;&lt;span class=&#34;w&#34;&gt; &lt;/span&gt;&lt;span class=&#34;l&#34;&gt;llama-server-intel&lt;/span&gt;&lt;span class=&#34;w&#34;&gt;
&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;span class=&#34;line&#34;&gt;&lt;span class=&#34;cl&#34;&gt;&lt;span class=&#34;w&#34;&gt;    &lt;/span&gt;&lt;span class=&#34;nt&#34;&gt;restart&lt;/span&gt;&lt;span class=&#34;p&#34;&gt;:&lt;/span&gt;&lt;span class=&#34;w&#34;&gt; &lt;/span&gt;&lt;span class=&#34;l&#34;&gt;unless-stopped&lt;/span&gt;&lt;span class=&#34;w&#34;&gt;
&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;span class=&#34;line&#34;&gt;&lt;span class=&#34;cl&#34;&gt;&lt;span class=&#34;w&#34;&gt;    &lt;/span&gt;&lt;span class=&#34;nt&#34;&gt;devices&lt;/span&gt;&lt;span class=&#34;p&#34;&gt;:&lt;/span&gt;&lt;span class=&#34;w&#34;&gt;
&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;span class=&#34;line&#34;&gt;&lt;span class=&#34;cl&#34;&gt;&lt;span class=&#34;w&#34;&gt;      &lt;/span&gt;- &lt;span class=&#34;l&#34;&gt;/dev/dri:/dev/dri&lt;/span&gt;&lt;span class=&#34;w&#34;&gt;
&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;span class=&#34;line&#34;&gt;&lt;span class=&#34;cl&#34;&gt;&lt;span class=&#34;w&#34;&gt;    &lt;/span&gt;&lt;span class=&#34;nt&#34;&gt;volumes&lt;/span&gt;&lt;span class=&#34;p&#34;&gt;:&lt;/span&gt;&lt;span class=&#34;w&#34;&gt;
&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;span class=&#34;line&#34;&gt;&lt;span class=&#34;cl&#34;&gt;&lt;span class=&#34;w&#34;&gt;      &lt;/span&gt;- &lt;span class=&#34;l&#34;&gt;/var/models:/models&lt;/span&gt;&lt;span class=&#34;w&#34;&gt;
&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;span class=&#34;line&#34;&gt;&lt;span class=&#34;cl&#34;&gt;&lt;span class=&#34;w&#34;&gt;    &lt;/span&gt;&lt;span class=&#34;nt&#34;&gt;ports&lt;/span&gt;&lt;span class=&#34;p&#34;&gt;:&lt;/span&gt;&lt;span class=&#34;w&#34;&gt;
&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;span class=&#34;line&#34;&gt;&lt;span class=&#34;cl&#34;&gt;&lt;span class=&#34;w&#34;&gt;      &lt;/span&gt;- &lt;span class=&#34;m&#34;&gt;4040&lt;/span&gt;&lt;span class=&#34;p&#34;&gt;:&lt;/span&gt;&lt;span class=&#34;m&#34;&gt;8080&lt;/span&gt;&lt;span class=&#34;w&#34;&gt;
&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;span class=&#34;line&#34;&gt;&lt;span class=&#34;cl&#34;&gt;&lt;span class=&#34;w&#34;&gt;    &lt;/span&gt;&lt;span class=&#34;nt&#34;&gt;environment&lt;/span&gt;&lt;span class=&#34;p&#34;&gt;:&lt;/span&gt;&lt;span class=&#34;w&#34;&gt;
&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;span class=&#34;line&#34;&gt;&lt;span class=&#34;cl&#34;&gt;&lt;span class=&#34;w&#34;&gt;      &lt;/span&gt;&lt;span class=&#34;c&#34;&gt;# Workaround for Mesa ANV driver fp16 compute bug on Intel iGPUs.&lt;/span&gt;&lt;span class=&#34;w&#34;&gt;
&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;span class=&#34;line&#34;&gt;&lt;span class=&#34;cl&#34;&gt;&lt;span class=&#34;w&#34;&gt;      &lt;/span&gt;&lt;span class=&#34;c&#34;&gt;# Safe to set even on dGPUs (B580), ignored if not needed.&lt;/span&gt;&lt;span class=&#34;w&#34;&gt;
&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;span class=&#34;line&#34;&gt;&lt;span class=&#34;cl&#34;&gt;&lt;span class=&#34;w&#34;&gt;      &lt;/span&gt;- &lt;span class=&#34;l&#34;&gt;GGML_VK_DISABLE_F16=${GGML_VK_DISABLE_F16:-0}&lt;/span&gt;&lt;span class=&#34;w&#34;&gt;
&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;span class=&#34;line&#34;&gt;&lt;span class=&#34;cl&#34;&gt;&lt;span class=&#34;w&#34;&gt;    &lt;/span&gt;&lt;span class=&#34;nt&#34;&gt;command&lt;/span&gt;&lt;span class=&#34;p&#34;&gt;:&lt;/span&gt;&lt;span class=&#34;w&#34;&gt; &lt;/span&gt;&lt;span class=&#34;p&#34;&gt;&amp;gt;&lt;/span&gt;&lt;span class=&#34;sd&#34;&gt;
&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;span class=&#34;line&#34;&gt;&lt;span class=&#34;cl&#34;&gt;&lt;span class=&#34;sd&#34;&gt;      --model /models/Qwen3.5-9B-UD-Q4_K_XL.gguf
&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;span class=&#34;line&#34;&gt;&lt;span class=&#34;cl&#34;&gt;&lt;span class=&#34;sd&#34;&gt;      --mmproj /models/mmproj/mmproj9B-BF16.gguf
&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;span class=&#34;line&#34;&gt;&lt;span class=&#34;cl&#34;&gt;&lt;span class=&#34;sd&#34;&gt;      --n-gpu-layers 99
&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;span class=&#34;line&#34;&gt;&lt;span class=&#34;cl&#34;&gt;&lt;span class=&#34;sd&#34;&gt;      --ctx-size ${LLAMA_CTX_SIZE:-131072}
&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;span class=&#34;line&#34;&gt;&lt;span class=&#34;cl&#34;&gt;&lt;span class=&#34;sd&#34;&gt;      --host 0.0.0.0
&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;span class=&#34;line&#34;&gt;&lt;span class=&#34;cl&#34;&gt;&lt;span class=&#34;sd&#34;&gt;      --port 8080&lt;/span&gt;&lt;span class=&#34;w&#34;&gt;
&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;p&gt;The model I&amp;rsquo;m using is Qwen3.5-9B with a vision projector, quantized to fit in 12 GB of VRAM. Vulkan turns out to be 30-60% faster than SYCL on Intel Arc GPUs, so it&amp;rsquo;s the right backend for this card.&lt;/p&gt;
&lt;h2 id=&#34;docker-setup-for-frigate&#34;&gt;Docker setup for Frigate&lt;/h2&gt;
&lt;p&gt;Here&amp;rsquo;s the Frigate docker-compose:&lt;/p&gt;
&lt;div class=&#34;highlight&#34;&gt;&lt;pre tabindex=&#34;0&#34; class=&#34;chroma&#34;&gt;&lt;code class=&#34;language-yaml&#34; data-lang=&#34;yaml&#34;&gt;&lt;span class=&#34;line&#34;&gt;&lt;span class=&#34;cl&#34;&gt;&lt;span class=&#34;nt&#34;&gt;version&lt;/span&gt;&lt;span class=&#34;p&#34;&gt;:&lt;/span&gt;&lt;span class=&#34;w&#34;&gt; &lt;/span&gt;&lt;span class=&#34;s2&#34;&gt;&amp;#34;3.9&amp;#34;&lt;/span&gt;&lt;span class=&#34;w&#34;&gt;
&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;span class=&#34;line&#34;&gt;&lt;span class=&#34;cl&#34;&gt;&lt;span class=&#34;nt&#34;&gt;services&lt;/span&gt;&lt;span class=&#34;p&#34;&gt;:&lt;/span&gt;&lt;span class=&#34;w&#34;&gt;
&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;span class=&#34;line&#34;&gt;&lt;span class=&#34;cl&#34;&gt;&lt;span class=&#34;w&#34;&gt;  &lt;/span&gt;&lt;span class=&#34;nt&#34;&gt;frigate&lt;/span&gt;&lt;span class=&#34;p&#34;&gt;:&lt;/span&gt;&lt;span class=&#34;w&#34;&gt;
&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;span class=&#34;line&#34;&gt;&lt;span class=&#34;cl&#34;&gt;&lt;span class=&#34;w&#34;&gt;    &lt;/span&gt;&lt;span class=&#34;nt&#34;&gt;container_name&lt;/span&gt;&lt;span class=&#34;p&#34;&gt;:&lt;/span&gt;&lt;span class=&#34;w&#34;&gt; &lt;/span&gt;&lt;span class=&#34;l&#34;&gt;frigate&lt;/span&gt;&lt;span class=&#34;w&#34;&gt;
&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;span class=&#34;line&#34;&gt;&lt;span class=&#34;cl&#34;&gt;&lt;span class=&#34;w&#34;&gt;    &lt;/span&gt;&lt;span class=&#34;nt&#34;&gt;privileged&lt;/span&gt;&lt;span class=&#34;p&#34;&gt;:&lt;/span&gt;&lt;span class=&#34;w&#34;&gt; &lt;/span&gt;&lt;span class=&#34;kc&#34;&gt;true&lt;/span&gt;&lt;span class=&#34;w&#34;&gt;
&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;span class=&#34;line&#34;&gt;&lt;span class=&#34;cl&#34;&gt;&lt;span class=&#34;w&#34;&gt;    &lt;/span&gt;&lt;span class=&#34;nt&#34;&gt;restart&lt;/span&gt;&lt;span class=&#34;p&#34;&gt;:&lt;/span&gt;&lt;span class=&#34;w&#34;&gt; &lt;/span&gt;&lt;span class=&#34;l&#34;&gt;unless-stopped&lt;/span&gt;&lt;span class=&#34;w&#34;&gt;
&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;span class=&#34;line&#34;&gt;&lt;span class=&#34;cl&#34;&gt;&lt;span class=&#34;w&#34;&gt;    &lt;/span&gt;&lt;span class=&#34;nt&#34;&gt;image&lt;/span&gt;&lt;span class=&#34;p&#34;&gt;:&lt;/span&gt;&lt;span class=&#34;w&#34;&gt; &lt;/span&gt;&lt;span class=&#34;l&#34;&gt;ghcr.io/blakeblackshear/frigate:stable&lt;/span&gt;&lt;span class=&#34;w&#34;&gt;
&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;span class=&#34;line&#34;&gt;&lt;span class=&#34;cl&#34;&gt;&lt;span class=&#34;w&#34;&gt;    &lt;/span&gt;&lt;span class=&#34;nt&#34;&gt;shm_size&lt;/span&gt;&lt;span class=&#34;p&#34;&gt;:&lt;/span&gt;&lt;span class=&#34;w&#34;&gt; &lt;/span&gt;&lt;span class=&#34;l&#34;&gt;512mb&lt;/span&gt;&lt;span class=&#34;w&#34;&gt;
&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;span class=&#34;line&#34;&gt;&lt;span class=&#34;cl&#34;&gt;&lt;span class=&#34;w&#34;&gt;    &lt;/span&gt;&lt;span class=&#34;nt&#34;&gt;volumes&lt;/span&gt;&lt;span class=&#34;p&#34;&gt;:&lt;/span&gt;&lt;span class=&#34;w&#34;&gt;
&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;span class=&#34;line&#34;&gt;&lt;span class=&#34;cl&#34;&gt;&lt;span class=&#34;w&#34;&gt;      &lt;/span&gt;- &lt;span class=&#34;l&#34;&gt;/etc/localtime:/etc/localtime:ro&lt;/span&gt;&lt;span class=&#34;w&#34;&gt;
&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;span class=&#34;line&#34;&gt;&lt;span class=&#34;cl&#34;&gt;&lt;span class=&#34;w&#34;&gt;      &lt;/span&gt;- &lt;span class=&#34;l&#34;&gt;./config:/config&lt;/span&gt;&lt;span class=&#34;w&#34;&gt;
&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;span class=&#34;line&#34;&gt;&lt;span class=&#34;cl&#34;&gt;&lt;span class=&#34;w&#34;&gt;      &lt;/span&gt;- &lt;span class=&#34;l&#34;&gt;./model:/model&lt;/span&gt;&lt;span class=&#34;w&#34;&gt;
&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;span class=&#34;line&#34;&gt;&lt;span class=&#34;cl&#34;&gt;&lt;span class=&#34;w&#34;&gt;      &lt;/span&gt;- &lt;span class=&#34;l&#34;&gt;./storage:/media/frigate&lt;/span&gt;&lt;span class=&#34;w&#34;&gt;
&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;span class=&#34;line&#34;&gt;&lt;span class=&#34;cl&#34;&gt;&lt;span class=&#34;w&#34;&gt;      &lt;/span&gt;- &lt;span class=&#34;l&#34;&gt;/dev/dri/renderD128:/dev/dri/renderD128&lt;/span&gt;&lt;span class=&#34;w&#34;&gt;
&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;span class=&#34;line&#34;&gt;&lt;span class=&#34;cl&#34;&gt;&lt;span class=&#34;w&#34;&gt;      &lt;/span&gt;- &lt;span class=&#34;nt&#34;&gt;type&lt;/span&gt;&lt;span class=&#34;p&#34;&gt;:&lt;/span&gt;&lt;span class=&#34;w&#34;&gt; &lt;/span&gt;&lt;span class=&#34;l&#34;&gt;tmpfs&lt;/span&gt;&lt;span class=&#34;w&#34;&gt;
&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;span class=&#34;line&#34;&gt;&lt;span class=&#34;cl&#34;&gt;&lt;span class=&#34;w&#34;&gt;        &lt;/span&gt;&lt;span class=&#34;nt&#34;&gt;target&lt;/span&gt;&lt;span class=&#34;p&#34;&gt;:&lt;/span&gt;&lt;span class=&#34;w&#34;&gt; &lt;/span&gt;&lt;span class=&#34;l&#34;&gt;/tmp/cache&lt;/span&gt;&lt;span class=&#34;w&#34;&gt;
&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;span class=&#34;line&#34;&gt;&lt;span class=&#34;cl&#34;&gt;&lt;span class=&#34;w&#34;&gt;        &lt;/span&gt;&lt;span class=&#34;nt&#34;&gt;tmpfs&lt;/span&gt;&lt;span class=&#34;p&#34;&gt;:&lt;/span&gt;&lt;span class=&#34;w&#34;&gt;
&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;span class=&#34;line&#34;&gt;&lt;span class=&#34;cl&#34;&gt;&lt;span class=&#34;w&#34;&gt;          &lt;/span&gt;&lt;span class=&#34;nt&#34;&gt;size&lt;/span&gt;&lt;span class=&#34;p&#34;&gt;:&lt;/span&gt;&lt;span class=&#34;w&#34;&gt; &lt;/span&gt;&lt;span class=&#34;m&#34;&gt;1000000000&lt;/span&gt;&lt;span class=&#34;w&#34;&gt;
&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;span class=&#34;line&#34;&gt;&lt;span class=&#34;cl&#34;&gt;&lt;span class=&#34;w&#34;&gt;    &lt;/span&gt;&lt;span class=&#34;nt&#34;&gt;ports&lt;/span&gt;&lt;span class=&#34;p&#34;&gt;:&lt;/span&gt;&lt;span class=&#34;w&#34;&gt;
&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;span class=&#34;line&#34;&gt;&lt;span class=&#34;cl&#34;&gt;&lt;span class=&#34;w&#34;&gt;      &lt;/span&gt;- &lt;span class=&#34;m&#34;&gt;5005&lt;/span&gt;&lt;span class=&#34;p&#34;&gt;:&lt;/span&gt;&lt;span class=&#34;m&#34;&gt;5000&lt;/span&gt;&lt;span class=&#34;w&#34;&gt;
&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;span class=&#34;line&#34;&gt;&lt;span class=&#34;cl&#34;&gt;&lt;span class=&#34;w&#34;&gt;      &lt;/span&gt;- &lt;span class=&#34;m&#34;&gt;8971&lt;/span&gt;&lt;span class=&#34;p&#34;&gt;:&lt;/span&gt;&lt;span class=&#34;m&#34;&gt;8971&lt;/span&gt;&lt;span class=&#34;w&#34;&gt;
&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;span class=&#34;line&#34;&gt;&lt;span class=&#34;cl&#34;&gt;&lt;span class=&#34;w&#34;&gt;      &lt;/span&gt;- &lt;span class=&#34;m&#34;&gt;8554&lt;/span&gt;&lt;span class=&#34;p&#34;&gt;:&lt;/span&gt;&lt;span class=&#34;m&#34;&gt;8554&lt;/span&gt;&lt;span class=&#34;w&#34;&gt; &lt;/span&gt;&lt;span class=&#34;c&#34;&gt;# RTSP feeds&lt;/span&gt;&lt;span class=&#34;w&#34;&gt;
&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;span class=&#34;line&#34;&gt;&lt;span class=&#34;cl&#34;&gt;&lt;span class=&#34;w&#34;&gt;      &lt;/span&gt;- &lt;span class=&#34;m&#34;&gt;8555&lt;/span&gt;&lt;span class=&#34;p&#34;&gt;:&lt;/span&gt;&lt;span class=&#34;m&#34;&gt;8555&lt;/span&gt;&lt;span class=&#34;l&#34;&gt;/tcp&lt;/span&gt;&lt;span class=&#34;w&#34;&gt; &lt;/span&gt;&lt;span class=&#34;c&#34;&gt;# WebRTC over tcp&lt;/span&gt;&lt;span class=&#34;w&#34;&gt;
&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;span class=&#34;line&#34;&gt;&lt;span class=&#34;cl&#34;&gt;&lt;span class=&#34;w&#34;&gt;      &lt;/span&gt;- &lt;span class=&#34;m&#34;&gt;8555&lt;/span&gt;&lt;span class=&#34;p&#34;&gt;:&lt;/span&gt;&lt;span class=&#34;m&#34;&gt;8555&lt;/span&gt;&lt;span class=&#34;l&#34;&gt;/udp&lt;/span&gt;&lt;span class=&#34;w&#34;&gt; &lt;/span&gt;&lt;span class=&#34;c&#34;&gt;# WebRTC over udp&lt;/span&gt;&lt;span class=&#34;w&#34;&gt;
&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;span class=&#34;line&#34;&gt;&lt;span class=&#34;cl&#34;&gt;&lt;span class=&#34;w&#34;&gt;      &lt;/span&gt;- &lt;span class=&#34;m&#34;&gt;1984&lt;/span&gt;&lt;span class=&#34;p&#34;&gt;:&lt;/span&gt;&lt;span class=&#34;m&#34;&gt;1984&lt;/span&gt;&lt;span class=&#34;w&#34;&gt;
&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;span class=&#34;line&#34;&gt;&lt;span class=&#34;cl&#34;&gt;&lt;span class=&#34;w&#34;&gt;    &lt;/span&gt;&lt;span class=&#34;nt&#34;&gt;environment&lt;/span&gt;&lt;span class=&#34;p&#34;&gt;:&lt;/span&gt;&lt;span class=&#34;w&#34;&gt;
&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;span class=&#34;line&#34;&gt;&lt;span class=&#34;cl&#34;&gt;&lt;span class=&#34;w&#34;&gt;      &lt;/span&gt;&lt;span class=&#34;nt&#34;&gt;PLUS_API_KEY&lt;/span&gt;&lt;span class=&#34;p&#34;&gt;:&lt;/span&gt;&lt;span class=&#34;w&#34;&gt; &lt;/span&gt;&lt;span class=&#34;l&#34;&gt;${PLUS_API_KEY}&lt;/span&gt;&lt;span class=&#34;w&#34;&gt; &lt;/span&gt;&lt;span class=&#34;c&#34;&gt;# optional, for Frigate+&lt;/span&gt;&lt;span class=&#34;w&#34;&gt;
&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;span class=&#34;line&#34;&gt;&lt;span class=&#34;cl&#34;&gt;&lt;span class=&#34;w&#34;&gt;      &lt;/span&gt;&lt;span class=&#34;nt&#34;&gt;FRIGATE_RTSP_PASSWORD&lt;/span&gt;&lt;span class=&#34;p&#34;&gt;:&lt;/span&gt;&lt;span class=&#34;w&#34;&gt; &lt;/span&gt;&lt;span class=&#34;l&#34;&gt;${FRIGATE_RTSP_PASSWORD}&lt;/span&gt;&lt;span class=&#34;w&#34;&gt;
&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;span class=&#34;line&#34;&gt;&lt;span class=&#34;cl&#34;&gt;&lt;span class=&#34;w&#34;&gt;      &lt;/span&gt;&lt;span class=&#34;nt&#34;&gt;OPENAI_BASE_URL&lt;/span&gt;&lt;span class=&#34;p&#34;&gt;:&lt;/span&gt;&lt;span class=&#34;w&#34;&gt; &lt;/span&gt;&lt;span class=&#34;l&#34;&gt;http://llama-server-intel:8080/v1&lt;/span&gt;&lt;span class=&#34;w&#34;&gt; &lt;/span&gt;&lt;span class=&#34;c&#34;&gt;# points to the local LLM&lt;/span&gt;&lt;span class=&#34;w&#34;&gt;
&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;p&gt;A few things to note:&lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;&lt;code&gt;/dev/dri/renderD128&lt;/code&gt; gives Frigate access to the B580 for hardware video decoding&lt;/li&gt;
&lt;li&gt;The &lt;code&gt;tmpfs&lt;/code&gt; mount is used as a fast cache for clips being processed&lt;/li&gt;
&lt;li&gt;&lt;code&gt;shm_size&lt;/code&gt; depends on how many camera streams you run (512 MB is fine for a few cameras)&lt;/li&gt;
&lt;li&gt;&lt;code&gt;OPENAI_BASE_URL&lt;/code&gt; points to the llama.cpp server for scene descriptions. Frigate uses the OpenAI-compatible API, so any local server that speaks that protocol works&lt;/li&gt;
&lt;li&gt;Put your secrets in a &lt;code&gt;.env&lt;/code&gt; file next to the docker-compose, not in the YAML&lt;/li&gt;
&lt;/ul&gt;
&lt;h2 id=&#34;home-assistant&#34;&gt;Home Assistant&lt;/h2&gt;
&lt;p&gt;Everything plugs into &lt;strong&gt;Home Assistant&lt;/strong&gt;:&lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;Camera feeds and Frigate events show up on the HA dashboard&lt;/li&gt;
&lt;li&gt;Notifications go through HA&amp;rsquo;s automation engine&lt;/li&gt;
&lt;li&gt;Remote access through HA&amp;rsquo;s built-in secure connection&lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;Cameras detect, Frigate analyzes, Home Assistant notifies. All local.&lt;/p&gt;
&lt;h2 id=&#34;why-bother-self-hosting-cameras&#34;&gt;Why bother self-hosting cameras?&lt;/h2&gt;
&lt;ul&gt;
&lt;li&gt;&lt;strong&gt;Your data stays yours.&lt;/strong&gt; No footage leaves your network. No cloud provider is storing or processing your video&lt;/li&gt;
&lt;li&gt;&lt;strong&gt;No subscriptions.&lt;/strong&gt; Cloud cameras love charging monthly for &amp;ldquo;premium&amp;rdquo; features like person detection. This costs nothing after the initial hardware&lt;/li&gt;
&lt;li&gt;&lt;strong&gt;Way fewer false positives.&lt;/strong&gt; AI detection vs. basic motion sensing is night and day&lt;/li&gt;
&lt;li&gt;&lt;strong&gt;Actually useful alerts.&lt;/strong&gt; You know what happened, not just that something moved&lt;/li&gt;
&lt;li&gt;&lt;strong&gt;Works offline.&lt;/strong&gt; SD card backup + local NVR means the system keeps recording even if your internet goes down&lt;/li&gt;
&lt;/ul&gt;
&lt;h2 id=&#34;summary&#34;&gt;Summary&lt;/h2&gt;
&lt;table&gt;
  &lt;thead&gt;
      &lt;tr&gt;
          &lt;th&gt;Component&lt;/th&gt;
          &lt;th&gt;What it does&lt;/th&gt;
      &lt;/tr&gt;
  &lt;/thead&gt;
  &lt;tbody&gt;
      &lt;tr&gt;
          &lt;td&gt;&lt;strong&gt;Tapo cameras&lt;/strong&gt;&lt;/td&gt;
          &lt;td&gt;RTSP stream + local SD card recording&lt;/td&gt;
      &lt;/tr&gt;
      &lt;tr&gt;
          &lt;td&gt;&lt;strong&gt;Frigate&lt;/strong&gt;&lt;/td&gt;
          &lt;td&gt;Open-source NVR with AI object detection&lt;/td&gt;
      &lt;/tr&gt;
      &lt;tr&gt;
          &lt;td&gt;&lt;strong&gt;Intel Arc B580&lt;/strong&gt;&lt;/td&gt;
          &lt;td&gt;Video decoding + AI inference on one card&lt;/td&gt;
      &lt;/tr&gt;
      &lt;tr&gt;
          &lt;td&gt;&lt;strong&gt;Home Assistant&lt;/strong&gt;&lt;/td&gt;
          &lt;td&gt;Dashboard, notifications, remote access&lt;/td&gt;
      &lt;/tr&gt;
      &lt;tr&gt;
          &lt;td&gt;&lt;strong&gt;Local server&lt;/strong&gt;&lt;/td&gt;
          &lt;td&gt;Runs Frigate and Home Assistant&lt;/td&gt;
      &lt;/tr&gt;
  &lt;/tbody&gt;
&lt;/table&gt;
&lt;h2 id=&#34;final-thoughts&#34;&gt;Final thoughts&lt;/h2&gt;
&lt;p&gt;It took a bit of time to set up, but I&amp;rsquo;m really happy with how this turned out. No more cloud dependency, no subscriptions, and the false positive problem is basically solved. The AI descriptions are surprisingly good and the B580 handles everything without breaking a sweat.&lt;/p&gt;
&lt;p&gt;If you&amp;rsquo;re fed up with cloud camera notifications about tree branches, give Frigate a look. The project has matured a lot and with Home Assistant it makes for a solid, reliable system.&lt;/p&gt;
&lt;p&gt;Most importantly: I can finally stop checking my phone every time the wind blows.&lt;/p&gt;
</description>
    </item>
    
  </channel>
</rss>
