Skip to content
Draft
Show file tree
Hide file tree
Changes from 2 commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
11 changes: 11 additions & 0 deletions .gitignore
Original file line number Diff line number Diff line change
@@ -0,0 +1,11 @@
# macOS
._*
.DS_Store
.AppleDouble

.Spotlight-V100
.Trashes
.fseventsd

.AppleDB
.AppleDesktop
10 changes: 10 additions & 0 deletions samba/CHANGELOG.md
Original file line number Diff line number Diff line change
@@ -1,5 +1,15 @@
# Changelog

## 12.6.1

- Add `mdnsd` for macOS discoverability
- Rename `smb.conf` Go template for disambiguation with new templates
- Add config option, and `nmbd` startup logic, to disable NetBIOS
- Add config options, and startup logic, to override default ports (445/139)
- Colocate mapped mounts to a `/smbshare` prefix to avoid potential confusion
- Update `config.yaml` `map:` to new object syntax
- Refactor `smb.conf` to use Go template iterators

## 12.6.0

- Do initial healthcheck after 3s to speedup startup
Expand Down
7 changes: 5 additions & 2 deletions samba/Dockerfile
Original file line number Diff line number Diff line change
Expand Up @@ -6,8 +6,11 @@ ENV LANG C.UTF-8

# Setup base
RUN \
apk add --no-cache samba \
&& mkdir -p /var/lib/samba \
echo '@testing https://dl-cdn.alpinelinux.org/alpine/edge/testing' >> \
/etc/apk/repositories && \
apk add --no-cache samba mdnsd@testing=0.12-r1 \
&& rm -f /etc/mdns.d/* \
&& mkdir -p /var/lib/samba /smbshare \
&& touch \
/etc/samba/lmhosts \
/var/lib/samba/account_policy.tdb \
Expand Down
42 changes: 32 additions & 10 deletions samba/config.yaml
Original file line number Diff line number Diff line change
@@ -1,5 +1,5 @@
---
version: 12.6.0
version: 12.6.1
Copy link
Copy Markdown
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I'd say this is at least a new feature, so warrants a 12.7.0.

slug: samba
name: Samba share
description: Expose Home Assistant folders with SMB/CIFS
Expand All @@ -12,18 +12,31 @@ host_network: true
image: homeassistant/{arch}-addon-samba
init: false
map:
- addons:rw
- all_addon_configs:rw
- backup:rw
- homeassistant_config:rw
- media:rw
- share:rw
- ssl:rw
- type: addons
read_only: false
path: "/smbshare/addons"
- type: all_addon_configs
read_only: false
path: "/smbshare/addon_configs"
- type: backup
read_only: false
path: "/smbshare/backup"
- type: homeassistant_config
read_only: false
path: "/smbshare/homeassistant"
- type: media
read_only: false
path: "/smbshare/media"
- type: share
read_only: false
path: "/smbshare/share"
- type: ssl
read_only: false
path: "/smbshare/ssl"
options:
username: homeassistant
password: null
workgroup: WORKGROUP
local_master: true
enabled_shares:
- addons
- addon_configs
Expand All @@ -32,9 +45,11 @@ options:
- media
- share
- ssl
local_master: true
compatibility_mode: false
apple_compatibility_mode: true
server_signing: "default"
netbios: true
veto_files:
- ._*
- .DS_Store
Expand All @@ -52,14 +67,21 @@ schema:
username: str
password: password
workgroup: str
local_master: bool
enabled_shares:
- "match(^(?i:(addons|addon_configs|backup|config|media|share|ssl))$)"
local_master: bool
compatibility_mode: bool
apple_compatibility_mode: bool
server_signing: list(default|auto|mandatory|disabled)
netbios: bool
veto_files:
- str
allow_hosts:
- str
startup: services
ports:
445/tcp: null
139/tcp: null
ports_description:
445/tcp: SMB over IP
139/tcp: SMB over NetBIOS
10 changes: 8 additions & 2 deletions samba/rootfs/etc/s6-overlay/s6-rc.d/init-smbd/run
Original file line number Diff line number Diff line change
Expand Up @@ -38,11 +38,17 @@ bashio::log.info "Interfaces: $(printf '%s ' "${interfaces[@]}")"

# Generate Samba configuration.
jq ".interfaces = $(jq -c -n '$ARGS.positional' --args -- "${interfaces[@]}") |
.enabled_shares.[] |= ascii_downcase" /data/options.json \
.enabled_shares.[] |= ascii_downcase |
.ports = $(bashio::addon.network)" /data/options.json \
| tempio \
-template /usr/share/tempio/smb.gtpl \
-template /usr/share/tempio/smb.conf.gtpl \
-out /etc/samba/smb.conf

tempio \
-conf /data/options.json \
-template /usr/share/tempio/smb.conf.inc.gtpl \
-out /etc/samba/smb.conf.inc

# Init user
username=$(bashio::config 'username')
password=$(bashio::config 'password')
Expand Down
Empty file.
40 changes: 40 additions & 0 deletions samba/rootfs/etc/s6-overlay/s6-rc.d/mdnsd/run
Original file line number Diff line number Diff line change
@@ -0,0 +1,40 @@
#!/command/with-contenv bashio
# vim: ft=bash
# shellcheck shell=bash


if bashio::var.true "$(bashio::addon.host_network)"; then
Copy link
Copy Markdown
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Since host_network is really statically configured, I don't think this is necessary, it will evaluate to true always. Simply run the service.

bashio::log.info "Host network detected. Configuring mDNS"

# Read hostname from API or setting default "hassio"
HOSTNAME=$(bashio::info.hostname)
if bashio::var.is_empty "${HOSTNAME}"; then
bashio::log.warning "Can't read hostname, using default."
HOSTNAME="hassio"
fi

declare -r smbfile="/etc/mdns.d/smb.service"
declare -r adiskfile="/etc/mdns.d/adisk.service"
declare -r _TMP="$(mktemp -d -t mdnsd.XXXXXX)"
rm -f -v "${smbfile}" "${adiskfile}"

# Generate JSON configuration for tempio
jq -c "
.ports = $(bashio::addon.network)
| .sambaversion = \"$(smbstatus --version | cut -d '[ \t]+' -F 2)\"
" /data/options.json > "${_TMP}/options.json"

# Generate _smb._tcp service advertisement
tempio \
-conf "${_TMP}/options.json" \
-template /usr/share/tempio/smb.service.gtpl \
-out ${smbfile}

# Generate _adisk._tcp service advertisement
tempio \
-conf "${_TMP}/options.json" \
-template /usr/share/tempio/adisk.service.gtpl \
-out ${adiskfile}

builtin exec $(which mdnsd) -n -i $(bashio::network.name)
fi
1 change: 1 addition & 0 deletions samba/rootfs/etc/s6-overlay/s6-rc.d/mdnsd/type
Original file line number Diff line number Diff line change
@@ -0,0 +1 @@
longrun
1 change: 1 addition & 0 deletions samba/rootfs/etc/s6-overlay/s6-rc.d/mdnsd/up
Original file line number Diff line number Diff line change
@@ -0,0 +1 @@
/etc/s6-overlay/s6-rc.d/discovery/run
7 changes: 6 additions & 1 deletion samba/rootfs/etc/s6-overlay/s6-rc.d/nmbd/run
Original file line number Diff line number Diff line change
Expand Up @@ -4,7 +4,12 @@
# ==============================================================================
# Start nmbd service
# ==============================================================================
exec nmbd \

if ! bashio::config.true 'netbios'; then
Copy link
Copy Markdown
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

There is a cleaner way to enable/disable services, have a look at rootfs/etc/s6-overlay/scripts/enable-check.sh in the openthread_border_router app. Don't forget to add the script to S6_STAGE2_HOOK.

builtin exec sleep infinity
fi

builtin exec nmbd \
--foreground \
--debug-stdout \
--no-process-group
2 changes: 1 addition & 1 deletion samba/rootfs/etc/s6-overlay/s6-rc.d/smbd/run
Original file line number Diff line number Diff line change
Expand Up @@ -4,7 +4,7 @@
# ==============================================================================
# Start smbd service
# ==============================================================================
exec smbd \
builtin exec smbd \
--foreground \
--debug-stdout \
--no-process-group
Empty file.
10 changes: 10 additions & 0 deletions samba/rootfs/usr/share/tempio/adisk.service.gtpl
Original file line number Diff line number Diff line change
@@ -0,0 +1,10 @@
# /etc/mdns.d/adisk.service -- mDNS-SD _adisk._tcp for macOS Finder
# macOS uses _adisk._tcp TXT records to discover SMB shares and honours
# the port from the companion _smb._tcp SRV record.
name {{ env "HOSTNAME" }}
type _adisk._tcp
port 9
txt sys=adVF=0x100
{{ range $i, $share := .enabled_shares -}}
txt dk{{ $i }}=adVN={{ $share }},adVF=0x80
{{ end -}}
56 changes: 56 additions & 0 deletions samba/rootfs/usr/share/tempio/smb.conf.gtpl
Original file line number Diff line number Diff line change
@@ -0,0 +1,56 @@
[global]
netbios name = {{ env "HOSTNAME" }}
dns hostname = {{ env "HOSTNAME" }}.local
additional dns hostnames = {{ env "HOSTNAME" }}._smb._tcp.local
workgroup = {{ .workgroup }}
server string = Samba Home Assistant
local master = {{ .local_master | ternary "yes" "no" }}
preferred master = {{ .local_master | ternary "yes" "auto" }}
server role = standalone
{{ $smb_port := default 445 (index .ports "445/tcp") -}}
{{ $nbt_port := default 139 (index .ports "139/tcp") -}}
smb ports = {{ cat $smb_port (ternary $nbt_port nil .netbios) }}

security = user
idmap config * : backend = tdb
idmap config * : range = 1000000-2000000

load printers = no
disable spoolss = yes
{{ if .netbios -}}
server services = smb nbt
{{ else -}}
disable netbios = yes
server services = smb
{{ end -}}
dns proxy = no

log level = 1

bind interfaces only = yes
interfaces = lo {{ .interfaces | join " " }}
hosts allow = 127.0.0.1 {{ .allow_hosts | join " " }}

{{ if .compatibility_mode -}}
client min protocol = NT1
server min protocol = NT1
lanman auth = yes
ntlm auth = yes
{{ end -}}

mangled names = no
dos charset = CP850
unix charset = UTF-8

{{ if .apple_compatibility_mode -}}
vfs objects = catia fruit streams_xattr
{{ end -}}

server signing = {{ .server_signing }}
allow dns updates = disabled

{{ range $i, $share := .enabled_shares -}}
[{{ $share }}]
path = /smbshare/{{ ternary "homeassistant" $share ( eq $share "config" ) }}
include = /etc/samba/smb.conf.inc
{{ end -}}
8 changes: 8 additions & 0 deletions samba/rootfs/usr/share/tempio/smb.conf.inc.gtpl
Original file line number Diff line number Diff line change
@@ -0,0 +1,8 @@
browseable = yes
writeable = yes

valid users = {{ .username }}
force user = root
force group = root
veto files = /{{ .veto_files | join "/" }}/
delete veto files = {{ eq (len .veto_files) 0 | ternary "no" "yes" }}
Loading