How can I give HA access to my Bluetooth dongle without network_mode=host?

Hi,

I am running container HA. I would like to give it access to my Bluetooth dongle for some devices. It is currently running in default network_mode=bridge . Keeping it that way is much better because network_mode=host would mean I would have to expose ports on a dozen of other containers (Piper, Whisper, OpenWakeWord, Music Assistant…) if I want HA to be able to connect to them. This is really not ideal, I prefer to keep everything in a virtual docker network.

I have mounted /run/dbus:/run/dbus:ro as said in Bluetooth - Home Assistant .

Currently, my compose is the following:

  homeassistant:
    image: homeassistant/homeassistant:latest
    platform: "linux/arm64"
    container_name: homeassistant
    restart: unless-stopped
    #network_mode: host
    networks:
      - services
    environment:
      - PUID=${PUID}
      - PGID=${PGID}
      - TZ=${TZ}
    volumes:
      - ${CONFIG_FOLDER}/homeassistant:/config
      - /run/dbus:/run/dbus:ro
    #ports:
    #  - 8123:8123
    #devices:
    #  - /path/to/device:/path/to/device

Is there a way to give it Bluetooth permission without network_mode=host ?
Any answer is welcome, have a great day

Macvlan is best docker networking method for HA in container. Trust me, you will love it. Also you can still use your services network to connect to other containers. It will also eliminate the mdns issues and other problems from using bridge networking

Is there an idiot’s guide to Macvlan? I have always struggled understanding it.

I would be very interested in a guide too

Bluetooth is unrelated to the container network config. BT in HA exclusively goes through the dbus socket you expose with

      - /run/dbus:/run/dbus:ro

I’ve seen this question already, and I’m curious where this notion comes from…

I will make it find something and post it

1 Like

That’s very kind of you!

Not difficult if you understand VLAN concept. Provides examples using an Alpine image.

To be fair setting up macvlan gets complicated for those using Portainer. I honestly hadn’t realized this until I started rereading the docs posted above.

If using command line you can simply follow docker docs.

If using portainer there are actually 2 steps.

Step 1. Setup the network configuration to use the ethernet interface
step 2. create the network to use macvlan config setup in step1

STEP1
The portainer setup is pretty straigtforward and same settings of command line.
for me I have server network that uses IP range 192.168.10.1 - 224 and I want HA in this IP range so I setup docker macvlan config in portainer to use this

NAME: MacVlan_Config
DRIVER: Macvlan
Macvlan Configuration: configuration
PARENT NETWORK CARD: eth0
SUBNET: 192.168.10.0/24
IP RANGE: 192.168.10.20 -192.168.10.30
GATEWAY: 192.168.10.1

My DHCP does not assign within the IP RANGE I used. Docker will automatically assign the IP but when I create container I manually assign the IP. In either case I want to make sure docker and my router arent assigning same IPs so be to prevent this.
It is also possible to use IPV6 range

STEP2
You need to actually create the docker network that the containers will attach to and use.

NAME: MacVlan_Network
DRIVER: Macvlan
Configuration: MacVlan_Config

after this the network is ready for use like below
I define the mac address and IP for the container so it shows in my router properly and IP is static.


services:

##########################################
#           HOMEASSISTANT                #
##########################################
  hass:
    container_name: homeassistant
    hostname: homeassistant
    mac_address: "02:42:0a:3c:1b:f1"
    privileged: false
    restart: unless-stopped
    stop_grace_period: 10s
    depends_on:
      - mariadb    
    image: ghcr.io/ghcr.io/home-assistant/home-assistant:2023.12.1
    volumes:
      - "/srv/cam/docker/frigate/application/media_frigate:/media/frigate:ro"
      - "/srv/main/docker/homeassistant/application/config:/config"
      - "/etc/localtime:/etc/localtime:ro"
    ports:
      - "8123:8123/tcp" # HA UI
      - "20165:21065/tcp" #
      - "5353:5353/udp" # mDNS
      - "51837:51827/udp" # homekit
    environment:
      - PUID:"1002"    
      - GUID:"1002"
    networks:
      dockerlocal:
      homeassistant:
      MacVlan_Net:
        ipv4_address: "192.168.10.15"
      reverseproxy:
    deploy:
      resources:
        limits:
          cpus: '2'
          memory: 4096M
        reservations:
          cpus: '1'
          memory: 1500M
          
##########################################
#              HASS_DB                   #
##########################################
  mariadb:
    image: mariadb:latest
    container_name: hass_db
    hostname: hass_db
    user: 1002:1002
    restart: "unless-stopped"
    stop_grace_period: 5s
    security_opt: # see https://github.com/MariaDB/mariadb-docker/issues/434#issuecomment-1136151239
      - seccomp:unconfined
      - apparmor:unconfined
    command: mariadbd --innodb-buffer-pool-size=512M --transaction-isolation=READ-COMMITTED --character-set-server=utf8mb4 --collation-server=utf8mb4_unicode_ci --max-connections=512 --innodb-rollback-on-timeout=OFF --innodb-lock-wait-timeout=120
    ## Never store database files on an unreliable device such as a USB flash drive, an SD card, or a shared network folder:
    volumes:
      - "/srv/main/docker/homeassistant/application/var_lib_mysql:/var/lib/mysql" # DO NOT REMOVE
    environment:
      MARIADB_AUTO_UPGRADE: "1"
      MARIADB_INITDB_SKIP_TZINFO: "1"
      MARIADB_DATABASE: "homeassistant"
      MARIADB_USER: "homeassistant"
      MARIADB_PASSWORD: "homeassistant"
      MARIADB_ROOT_PASSWORD: "mariadb"
      PGID: 1002
      PUID: 1002
    networks:
      homeassistant:
    deploy:
      resources:
        limits:
          cpus: '2'
          memory: 2000M
        reservations:
          cpus: '1'
          memory: 512M

          
##########################################
#              NETWORKS                  #
##########################################      
networks:
  dockerlocal:
    external: true 
  homeassistant:
    driver: bridge
  MacVlan_Network:
    external: true
  reverseproxy:
    external: true
1 Like

Macvlan looks like it is the perfect solution ! I don’t know why it is the first time I hear of it. Here is how I created my macvlan network:

  macvlan:
    name: macvlan
    driver: macvlan
    driver_opts:
      parent: eth0
    ipam:
      driver: default
      config:
        - subnet: 192.168.1.0/24
          gateway: 192.168.1.1

On my LAN, I now have new devices showing up for each container I connected to that network. Is that normal ? Is there a way to still have them using the IP of the server or is it the normal behaviour ? I followed the docker docs a bit blindly, do you have recommendations ? I didn’t run into issues even when using Portainer. You can create networks directly from the compose in Portainer, no need to manually create it in Portainer network UI.

If networking is container to container just use docker network and no need to open port. If you notice my example I make “homeassistant” network. Maria db has no external connection and container connect to it at the hostname “hass_db” that instead of an IP.

Normally if you use macvlan you won’t use server IP. If you want to use server ip just use normal bridge mode. I use both. I use macvlan for Ha specifically because things like HomeKit and emulated hue don’t work with bride mode.

Side note.
You cannot connect to container using bridge mode from macvlan container using hostip:port. You MUST use Docker network as hostip:port is blocked to macvlan.

Hi,
Thanks for yout recommendations @tmjpugh ,

So Macvlan works great for DLNA players for example, and still allows me to use my bridges network. So it is great, but I found a limitation with this addon:

This addon is required to scan for nearby BLE devices, like my bluetooth scale.
When using Macvlan, it doesn’t find the hci0 bluetooth interface. What is strange is that HA’s bluetooth integration finds hci0, but it is useless for my devices. I am trying to understand why HA’s bluetooth integration works with Macvlan but not BLE monitor. I made a post about this in hope of finding more information [Bug]: Doesn't work with Docker macvlan - Bluetooth interface is not available · Issue #1301 · custom-components/ble_monitor · GitHub

My HA is currently deployed this way:

  homeassistant:
    image: homeassistant/homeassistant:latest
    platform: "linux/arm64"
    container_name: homeassistant
    restart: unless-stopped
    #network_mode: host
    networks:
      - services
      - macvlan
    environment:
      - PUID=0
      - PGID=0
      - TZ=${TZ}
    volumes:
      - ${CONFIG_FOLDER}/homeassistant:/config
      - /run/dbus:/run/dbus:ro

Do you have an idea about why BLE Monitor can’t find the Bluetooth interface in Macvlan ?

I also tried IPvlan with the same results.

Have a nice day

Network Chuck did a very clear breakdown in this video.

1 Like

Macvlan can’t connect to localhost and localhost cannot connect macvlan. Sorry, I should have mentioned this limitation. This holds true for docker container on same Host attempting connection to macvlan.

I’m not familiar with blue monitor but if it is integration or docker container you MUST use seperate docker bridge network for this communication. This is also better method.

Ok I see the limitation, it maybe what is blocking me from using BLE Monitor. But what do you mean by using a seperate docker bridge network for this communication ? My HA is already on a bridge network (so that Caddy can access HA to expose it) in addition to the macvlan network. How can I set that BLE Monitor uses a different network ? It only asks for a bluetooth interface mac address.

After reading the integrations docs I think maybe you just need to use the correct Mac. I presume it used a default Mac that is incorrect. According to below you should check the logs for available Mac. I would either test 5hem one by one if multiple are available or set it to use all as initial test.

bt_interface

MAC address of the Bluetooth interface/adapter (MAC address or list of multiple MAC addresses or “disable”)(Optional) This parameter is used to select the Bluetooth-interface of your Home Assistant host. When using YAML, a list of available Bluetooth-interfaces available on your system is given in the Home Assistant log during startup of the Integration, when you enable the Home Assistant logger at info-level. In the UI, both the MAC address and the hci number will be shown. If you don’t specify a MAC address, by default the first interface of the list will be used. If you want to use multiple interfaces in YAML, you can use the following configuration:

ble_monitor:
  bt_interface:
    - '04:B1:38:2C:84:2B'
    - '34:DE:36:4F:23:2C'

EDIT
I check log in you GitHub post and below look like blue monitor find Mac but cannot use it. Can you confirm what this Mac is for. Maybe you can assign Mac to docker bridge network and force it to use that if macvlan cause the problem

2024-01-17 22:17:05.422 DEBUG (MainThread) [custom_components.ble_monitor] Initializing BLE Monitor entry (config entry): <homeassistant.config_entries.ConfigEntry object at 0x7f75239e40>
2024-01-17 22:17:05.422 DEBUG (MainThread) [custom_components.ble_monitor] async_setup_entry: domain {‘bt_interface’: [‘00:1A:7D:DA:71:15’], ‘discovery’: False, ‘devices’: [{‘mac’: ‘0C:95:41:D7:4A:F8’, ‘report_unknown’: False, ‘restore_state’: ‘default’, ‘consider_home’: 180, ‘reset_timer’: 35, ‘track_device’: False, ‘use_median’: ‘default’, ‘tracker_scan_interval’: 20}], ‘report_unknown’: ‘Off’, ‘restore_state’: False, ‘batt_entities’: True, ‘period’: 60, ‘bt_auto_restart’: False, ‘hci_interface’: , ‘active_scan’: False, ‘use_median’: False, ‘log_spikes’: False, ‘is_flow’: False, ‘ids_from_name’: True}
2024-01-17 22:17:05.423 INFO (MainThread) [custom_components.ble_monitor] Available Bluetooth interfaces for BLE monitor: [“Don’t use Bluetooth adapter”]
2024-01-17 22:17:05.423 ERROR (MainThread) [custom_components.ble_monitor] Bluetooth interface with MAC address 00:1A:7D:DA:71:15 is not available
2024-01-17 22:17:05.423 WARNING (MainThread) [custom_components.ble_monitor] No configured Bluetooth interface was found, using default interface instead
2024-01-17 22:17:05.424 DEBUG (MainThread) [custom_components.ble_monitor] HCI interface is [‘disable’]
2024-01-17 22:17:05.424 DEBUG (MainThread) [custom_components.ble_monitor] async_setup_entry: {‘bt_interface’: [‘disable’], ‘discovery’: False, ‘devices’: [{‘mac’: ‘0C:95:41:D7:4A:F8’, ‘report_unknown’: False, ‘restore_state’: ‘default’, ‘consider_home’: 180, ‘reset_timer’: 35, ‘track_device’: False, ‘use_median’: ‘default’, ‘tracker_scan_interval’: 20}], ‘report_unknown’: ‘Off’, ‘restore_state’: False, ‘batt_entities’: True, ‘period’: 60, ‘bt_auto_restart’: False, ‘hci_interface’: [‘disable’], ‘active_scan’: False, ‘use_median’: False, ‘log_spikes’: False, ‘is_flow’: False, ‘ids_from_name’: True}
2

Thanks a lot for helping about this issue. The dev said the integration works by making HCI dumps : https://github.com/custom-components/ble_monitor/issues/1301 I’m not sure how that plays with macvlan.

I have tried manually specifying the mac address in the yaml file like you show it (instead of letting the addon wizard detect it), and in both cases I have Bluetooth interface with MAC address 00:1A:7D:DA:71:15 is not available . This mac address is the address of the bluetooth adapter on the host. I can see it by doing. “hcitool dev” on the host. I’m not sure if setting this in docker would work as it is not the mac address of a network adapter.

Not sure if I helped. May have taken you off track but I think your GitHub said issue was corrected by changing network configuration of docker.

But then there is also below so not sure what to suggest