收起左侧

Claude分析 SMB 外接设备重启共享丢失配置原因跟解决方案

3
回复
50
查看
[ 复制链接 ]

5

主题

13

回帖

0

牛值

江湖小虾

二、根本原因

开机挂载竞态(boot mount race)。

fnOS 的共享由 share_service(systemd: share_service.service)在开机时"重建"。它从「持久的共享清单 + 实时挂载状态」动态生成 SMB 配置:

  • 内部盘 /vol1 永远在 → 内部共享每次都正常。
  • 外接 USB 盘挂载较慢(实测开机后约 3~14 秒才挂上 /vol00/*)。

开机时 share_service 抢在 USB 盘挂载完成之前就重建共享,发现 /vol00/* 路径不存在,于是:


[smb] Rebuild external shares for 1000
[smb] append namin**ap with path /vol00/ST1000LM035-1RK172 ... not exist skip
[smb] append namin**ap with path /vol00/WDC WD20NMVW-11EDZS7   ... not exist skip
[smb] append namin**ap with path /vol00/WDC WD20NMVW-11EDZS7_1 ... not exist skip
[smb] User 1000 has 8 shares     ← 少了 3 个外接共享

关键点:这次"跳过"不仅当次不生效,还会把外接存储从 fnOS 的「可见文件夹范围」里剔除(清成"无")。等几秒后盘挂上来(OnMountEvent),这版 fnOS(1.1.30)的自愈逻辑没有把它们补回去。于是:

  • 网页「外接存储」= 无 → 页面不显示、前端报 semi-modal-content undefined
  • SMB 上外接共享消失,必须手动重新勾选才能恢复——直到下次重启再次丢失。

顺带澄清(避免误判)

  • postgres trim 库的 share / fileshare 表为空是正常的:内部/团队是「全部允许」(无需逐项记录)、外接是「无」(没有勾选记录),所以表本就为空,不是数据库损坏
  • 早期一度怀疑"数据库被清空的定时炸弹",经核实不成立

三、诊断过程(关键证据)

步骤 命令 / 操作 结论
看 Samba 配置 cat /etc/samba/smb.conf/etc/samba/users/1000.share.conf 共享走动态 include users/%Y.share.conf
看挂载 findmntlsblkmount 三块外接盘通过 systemd 动态 .mount 单元挂载,不在 fstab
看数据库 sudo -u postgres psql -d trim share 表空(属正常,见上)
看开机日志 /usr/trim/logs/share_service.log 实锤竞态:开机时 /vol00/* ... not exist skip,3~5 秒后才 OnMountEvent
网页复现 系统设置→文件共享协议→SMB→设置可见文件夹范围 「外接存储 = 无」,三块盘能识别但全未勾选

四、最终解决方案(原生,已两次真机重启验证)

分两部分:① 恢复显示(网页勾选)+ ② 根因修复(开机等挂载,防止再被剔除)。

① 在网页里勾选外接盘(恢复 fnOS 原生外接共享)

路径:系统设置 → 文件共享协议 → SMB → 设置可见文件夹范围 → 外接存储,勾选三块盘 → 确定。

效果:fnOS 原生把外接共享写回 /etc/samba/users/1000.share.conf,网页「外接存储」显示为「3 项」。

② 给 share_service 加「开机等挂载」延迟(根因修复)

share_service /vol00 挂载稳定后再启动,从根上避免"路径不存在→剔除"。

脚本 /usr/local/bin/wait-vol00-mounts.sh

#!/bin/bash
# Block share_service start until external USB (/vol00) mounts settle, so fnOS
# does NOT prune external shares due to the boot mount race (fnOS v1.1.30).
count(){ findmnt -rn -o TARGET 2>/dev/null | grep -c '^/vol00/'; }
prev=-1; stable=0; c=0
for i in $(seq 1 30); do            # 最多 ~60s
  c=$(count)
  if [ "$c" -ge 1 ] && [ "$c" -eq "$prev" ]; then
    stable=$((stable+1)); [ "$stable" -ge 2 ] && break   # 连续 2 次稳定即放行
  else stable=0; fi
  prev=$c; sleep 2
done
logger -t share-wait-vol00 "proceeding; /vol00 mounts=$c after ~$((i*2))s"
exit 0
chmod +x /usr/local/bin/wait-vol00-mounts.sh

systemd drop-in /etc/systemd/system/share_service.service.d/wait-vol00.conf

[Service]
TimeoutStartSec=180
ExecStartPre=/usr/local/bin/wait-vol00-mounts.sh
systemctl daemon-reload

说明:drop-in 放在 *.service.d/ 下,与 fnOS 自带的 unit 文件分离,fnOS 升级替换 unit 不会删掉它。TimeoutStartSec=180 给等待留足余量(默认 90s 可能不够)。若哪天拔掉所有外接盘,脚本会等满 ~60s 后放行,仅延长开机时间,不影响功能。


五、验证结果

重启后(/usr/trim/logs/share_service.log + journalctl):

# 开机延迟生效:
share-wait-vol00: proceeding; /vol00 mounts=3 after ~14s
# share_service 重建:无任何 not exist skip
[smb] User 1000 has 10 shares          ← 6 内部 + 3 外接 + 1 远程挂载,正确

收藏
送赞
分享

感谢反馈!smb外接硬盘共享问题,我转给相关同学进一步看下。

1

主题

2

回帖

0

牛值

江湖小虾

一直被这个外接硬盘共享问题困扰 具体怎么操作 能出教程么,

步骤 1:创建等待脚本 首先,我们需要创建一个用于检测 /vol00 挂载状态的 Shell 脚本。 在终端中复制并执行以下命令,使用 cat 直接写入脚本内容: cat <<EOF > /usr/local/bin/wait-vol00-mounts.sh #!/bin/bash #  详情 回复
昨天 15:13

5

主题

13

回帖

0

牛值

江湖小虾

昨天 15:13 楼主 显示全部楼层
[quote][size=2][url=forum.php?mod=redirect&goto=findpost&pid=298708&ptid=64954][color=#999999]猫斯拉 发表于 2026-6-3 14:36[/color][/url][/size] 一直被这个外接硬盘共享问题困扰 具体怎么操作 能出教程么,[/quote]

步骤 1:创建等待脚本

首先,我们需要创建一个用于检测 /vol00 挂载状态的 Shell 脚本。

在终端中复制并执行以下命令,使用 cat 直接写入脚本内容:

cat <<EOF > /usr/local/bin/wait-vol00-mounts.sh
#!/bin/bash
# Block share_service start until external USB (/vol00) mounts settle, so fnOS
# does NOT prune external shares due to the boot mount race (fnOS v1.1.30).
count(){ findmnt -rn -o TARGET 2>/dev/null | grep -c '^/vol00/'; }
prev=-1; stable=0; c=0
for i in $(seq 1 30); do            # 最多 ~60s
  c=$(count)
  if [ "$c" -ge 1 ] && [ "$c" -eq "$prev" ]; then
    stable=$((stable+1)); [ "$stable" -ge 2 ] && break   # 连续 2 次稳定即放行
  else stable=0; fi
  prev=$c; sleep 2
done
logger -t share-wait-vol00 "proceeding; /vol00 mounts=$c after ~$((i*2))s"
exit 0
EOF

步骤 2:赋予脚本可执行权限

脚本创建后,需要添加可执行权限,否则系统无法运行它:

chmod +x /usr/local/bin/wait-vol00-mounts.sh

步骤 3:创建 systemd Drop-in 配置

为了避免 fnOS 升级时覆盖原始服务文件,我们采用 Drop-in 机制来追加配置。

首先,创建 drop-in 目录(如果不存在):

mkdir -p /etc/systemd/system/share_service.service.d

接着,写入配置文件,增加启动前等待和超时时间:

cat <<EOF > /etc/systemd/system/share_service.service.d/wait-vol00.conf
[Service]
TimeoutStartSec=180
ExecStartPre=/usr/local/bin/wait-vol00-mounts.sh
EOF

步骤 4:重载 systemd 配置

修改完配置文件后,必须通知 systemd 重新加载配置以使其生效:

systemctl daemon-reload

您需要登录后才可以回帖 登录 | 立即注册

本版积分规则