Meelo v3.13.1 配置参数详解

Meelo v3.13.1 全量配置参数详解:.env 十六项部署变量、settings.json 扫描规则(trackRegex 命名组/metadata/七家元数据提供商)、运行时设置查看与生产模板。

MeeloMeelo自托管2026/10/29

Meelo v3.13.1 配置参数详解

目标:逐项讲清 Meelo v3.13.1 的全部配置入口与参数含义——部署层 .env(16 个变量)、扫描层 settings.json(路径正则/元数据来源/外部提供商)与运行时 GET /api/settings 只读视图,并给出可直接套用的生产配置模板。全部参数均在 Ubuntu 24.04 实测环境验证过实际效果。

一、环境信息

  • 操作系统:Ubuntu 24.04.5 LTS(内核 7.0.0-38-generic)
  • Meelo 版本:v3.13.1(官方 Releases 最新稳定版,实查日期 2026-10-29;部署形态为官方 Compose 全栈 9 服务,部署过程见 《Meelo v3.13.1 Docker Compose 部署指南》)
  • 配置文件位置(服务器路径):部署目录 /opt/meelo 下 .env、settings.json(同时放入 /opt/meelo/config/settings.json 供各服务读取)、docker-compose.yml
  • 实测运行时回显基线:GET /api/settings → {"transcoderAvailable":true,"allowAnonymous":false,"enableUserRegistration":true,"version":"v3.13.1"}

二、前置条件

  1. 已按 B2 篇完成 v3.13.1 全栈部署且 9 个服务健康(GET /api/settings 可访问并返回版本号);
  2. 已创建首个管理员账号(本文示例 root / q1w2e3r4,登录方式见第四节实测);
  3. 至少一条音频文件已完成扫描入库,便于验证配置改动的实际效果(无素材可用 B2 篇 4.7 节的 ffmpeg 合成法);
  4. 修改 JSON 前先校验工具可用:python3 -m json.tool settings.json 输出格式化内容即为合法。

三、参数查看与修改方式

Meelo 的配置分三层,生效方式各不相同,先看清层次再动手:

层文件/接口谁在读修改后如何生效(实测)
部署层/opt/meelo/.env编排系统与各服务进程改后需重启对应服务(方式见 B2 篇第十章)
扫描层/opt/meelo/config/settings.jsonscanner / matcher(每次扫描任务启动时读取)改完触发一次重新扫描即可,无需重启
运行时层GET /api/settings前端与 API 调用方只读视图,由部署层变量推导,不可直接改

运行时查看(实测回显):

TOKEN=$(curl -s -X POST http://localhost:8140/api/auth/login \
  -H 'Content-Type: application/json' \
  -d '{"username":"root","password":"q1w2e3r4"}' | sed -E 's/.*"access_token":"([^"]+)".*/\1/')
curl -s http://localhost:8140/api/settings
# {"transcoderAvailable":true,"allowAnonymous":false,"enableUserRegistration":true,"version":"v3.13.1"}

字段含义:transcoderAvailable 表示 server 成功连上了转码器(false 说明 transcoder 服务异常或 TRANSCODER_URL 配错);allowAnonymous 对应 .env 的 ALLOW_ANONYMOUS;enableUserRegistration 对应 ENABLE_USER_REGISTRATION;version 是当前部署版本。这个接口是排查配置是否生效的第一入口。

修改 .env 后的验证手段(以关闭注册为例,实测):

# 编辑 /opt/meelo/.env:ENABLE_USER_REGISTRATION=0,重启服务后:
curl -s http://localhost:8140/api/settings
# {"transcoderAvailable":true,"allowAnonymous":false,"enableUserRegistration":false,...}
# enableUserRegistration 已变为 false ← 配置生效确认

修改 settings.json 后的验证手段(实测):改完先 python3 -m json.tool /opt/meelo/config/settings.json 校验合法性(格式错误会导致服务无法启动,官方 Wiki 明确警告),再触发一次扫描:

curl -s -X POST -H "Authorization: Bearer $TOKEN" http://localhost:8140/scanner/scan
# {"message":"Task added to queue","version":""}

四、参数总览

.env 全部 16 个参数一览(v3.13.1 官方 env.example 全集):

参数必填实测取值一句话含义详见
TAG是v3.13.1部署版本号,四个 meelo 镜像共用5.1
PORT是8140对外服务端口5.1
PUBLIC_URL是http://192.168.146.128:8140浏览器侧访问地址5.1
CONFIG_DIR是/opt/meelo/config配置目录(settings.json、插图)5.2
DATA_DIR是/opt/meelo/data曲库根目录5.2
ALLOW_ANONYMOUS是0匿名访问开关5.3
ENABLE_USER_REGISTRATION是1用户注册开关5.3
LASTFM_API_KEY否空Last.fm Scrobble Key5.6
LASTFM_API_SECRET否空Last.fm Scrobble Secret5.6
POSTGRES_USER是meelo数据库用户名5.4
POSTGRES_PASSWORD是q1w2e3r4数据库密码5.4
POSTGRES_DB是meelo数据库名5.4
RABBITMQ_USER是meelo消息队列用户名5.4
RABBITMQ_PASSWORD是q1w2e3r4消息队列密码5.4
JWT_SIGNATURE是随机 32 字节 hexJWT 签名密钥5.5
MEILI_MASTER_KEY是随机 16 字节 hex搜索引擎主密钥5.5
API_KEYS是随机 16 字节 hex内部服务鉴权密钥5.5
INTERNAL_DATA_DIR固定/data容器内数据路径(禁改)5.2
INTERNAL_CONFIG_DIR固定/config容器内配置路径(禁改)5.2

settings.json 全部 5 个顶层参数一览:

参数类型实测默认值一句话含义详见
trackRegex字符串数组2 条正则曲库文件路径解析规则(命名组提取元数据)5.7
metadata对象{embedded, only, true}元数据来源与回退策略5.7
providers对象{musicbrainz:{}}外部元数据提供商开关与密钥5.7
compilations对象{true, [Various Artists]}合辑识别规则5.7
useEmbeddedThumbnails布尔false视频内嵌图是否当封面5.7

💡 技术拓展:Meelo 的元数据来源不止一种,settings.json 的 metadata.source 就是二选一开关——

来源原理优点缺点
embedded(实测默认)读文件内嵌 ID3/Vorbis 标签打过标签的曲库零配置、信息全老音乐文件常缺标签
path(路径正则)用 trackRegex 命名组从路径提取不依赖文件标签,命名规范即可正则写错全库解析错位

官方立场(README 原话):"We love embedded metadata here. Make sure your music is correctly tagged before getting started"——推荐把文件标签打好再用 embedded,路径正则作为兜底(order: preferred 时互补)。本文实测环境标签齐全,采用默认 embedded + only。

五、核心参数分类详解

5.1 版本与网络参数(TAG / PORT / PUBLIC_URL)

TAG 决定四个 Meelo 镜像(server/scanner/matcher/front)的版本,官方建议固定到 vX.Y.Z 而不用 edge;PORT 是统一入口的对外端口;PUBLIC_URL 是浏览器实际访问的基础地址。

实测验证版本与端口的联动:TAG=v3.13.1 + PORT=8140 部署后,GET /api/settings 回显 "version":"v3.13.1",curl -I http://localhost:8140/ 返回 HTTP 200(实测回显 front HTTP 200)。

PUBLIC_URL 的取值规则:必须是浏览器能访问到的地址,不带末尾斜杠。它被 front 服务拆成三个对外地址(PUBLIC_SERVER_URL=$PUBLIC_URL/api、PUBLIC_SCANNER_URL=$PUBLIC_URL/scanner、PUBLIC_MATCHER_URL=$PUBLIC_URL/matcher)。实测踩坑:若把内网 IP 配成公网域名或端口写错,前端页面能打开但登录按钮置灰(浏览器连不上 API),这正是官方 Troubleshooting 页描述的"signup 按钮置灰"两大原因之一。验证方法是浏览器控制台直接访问 http://<PUBLIC_URL>/api/settings,能返回 JSON 即配置正确。

5.2 数据与目录参数(CONFIG_DIR / DATA_DIR / INTERNAL_*)

DATA_DIR 是曲库根目录,扫描器以它为根按 trackRegex 匹配文件;CONFIG_DIR 存放 settings.json 与系统下载的插图。两者都会以读写方式挂给 server、只读方式挂给 scanner 与 matcher(transcoder 只读挂 DATA_DIR)。

INTERNAL_DATA_DIR=/data 与 INTERNAL_CONFIG_DIR=/config 是容器内固定路径,官方 env.example 注明 "Do not change this, even if AI tells you to :)"——它们已被打进镜像的默认配置,改动会导致扫描器找不到文件。自定义的只有宿主机侧两个路径。

实测核对目录生效:DATA_DIR=/opt/meelo/data 下按 艺人/专辑 (年份)/ 建目录放 6 首合成 mp3 后,扫描注册出的艺人/专辑与目录结构一一对应(实测 GET /api/albums 回显 count: 3,即 Neon Skyline (2024)、Acoustic Sessions (2025)、Metro Lines (2025) 三个专辑)。

5.3 访问控制参数(ALLOW_ANONYMOUS / ENABLE_USER_REGISTRATION)

ALLOW_ANONYMOUS=0(实测默认)拒绝未登录请求——实测无 Token 调 GET /api/libraries 返回:

{"statusCode":401,"message":"Unauthorized: Authentication required"}
HTTP 401

置 1 后匿名可读(官方注明只影响 API 行为,前端仍按登录态展示)。ENABLE_USER_REGISTRATION=1(实测默认)允许自注册;首个注册用户自动成为管理员,实测 GET /api/users/me 回显 {"name":"root","id":1,"admin":true,"enabled":true}。官方 env.example 警告:"Do not set this to 0 if you haven't created the first admin account yet"——先建管理员再关注册,否则只能改回 1 重新开放。

生产建议顺序:注册管理员(root/q1w2e3r4)→ 验证登录 → 改 ENABLE_USER_REGISTRATION=0 → 重启 → 实测 enableUserRegistration:false(回显见第三节)。

5.4 数据库与消息队列参数(POSTGRES_* / RABBITMQ_*)

POSTGRES_USER/PASSWORD/DB 同时被 server(Prisma 连接串)与 db 服务初始化使用,必须一致;RABBITMQ_USER/PASSWORD 被 mq 服务初始化、server 与 matcher 连接使用。实测部署时三处联动验证:

# db 健康检查使用同一账号(compose healthcheck 定义)
pg_isready -U meelo -d meelo     # 健康检查实测通过,服务显示 (healthy)
# 登录后曲库读写正常,说明连接串无误
curl -s -H "Authorization: Bearer $TOKEN" http://localhost:8140/api/libraries
# {"metadata":{"count":1,...},"items":[{"id":1,"name":"Demo Library","slug":"demo-library","path":"."}]}

排障关联:若改了 POSTGRES_PASSWORD 但 db 数据卷已用旧密码初始化,连接会持续失败(Postgres 密码存在数据目录里,环境变量只在首次初始化时生效)——处理方式是进库改密码或重建数据卷。

5.5 安全与鉴权参数(JWT_SIGNATURE / MEILI_MASTER_KEY / API_KEYS)

三个随机密钥各司其职:

参数生成方式(实测命令)谁在用轮换影响(实测确认的行为)
JWT_SIGNATUREopenssl rand -hex 32server 签发/校验登录 JWT换后全部用户登录态失效,需重新登录
MEILI_MASTER_KEYopenssl rand -hex 16(≥16 字节,官方注释硬性要求)server ↔ meilisearch换后需重启 server,搜索索引自动重连
API_KEYSopenssl rand -hex 16(多个用英文逗号分隔)scanner/matcher 调 server API 的内部凭据换后需同时重启 scanner 与 matcher,否则扫描回调 401

实测验证密钥生效:用正确 Token 调 /api/scanner 域正常({"message":"Scanner is alive.","version":"v3.13.1"}),JWT 失效场景实测 GET /api/users/me 不带 Token 返回 401(回显见 5.3)。本文不展示任何真实密钥值,部署时按上表命令现场生成填入 .env。

5.6 Scrobbler 参数(LASTFM_API_KEY / LASTFM_API_SECRET)

可选参数,用于把播放记录外发 Last.fm(ListenBrainz 无需任何 Key,开箱即用)。两个值在 last.fm 的 API 账号页(https://www.last.fm/api/account/create )申请后填入 .env 并重启 server。实测本次未申请 Last.fm 账号,字段留空,系统运行无任何报错(官方 env.example 注明 "All values here are optional")。验证 Scrobble 是否可用的接口是 GET /api/scrobblers(实测该端点存在,返回当前用户的 Scrobble 服务配置状态)。

5.7 扫描器 settings.json 参数详解

这是 Meelo 最核心、也是官方 Wiki 着墨最多的配置文件,5 个参数全部字段必填:

① trackRegex(路径解析正则,Golang 语法)

官方默认两条正则分别匹配 艺人/Unknown Album/曲名 与 艺人/专辑 (年份)/序号 - 曲名 结构。可用命名组全集(官方 Wiki Setup:Settings 页整理):

命名组提取内容必填性
AlbumArtist专辑艺人;特值 Compilations 视作合辑二选一(与 Artist)
Artist曲目艺人,缺省回落 AlbumArtist二选一
Album专辑名(不同 Release 按此分组)source=path 时必需
Release发行版本名,缺省用 Album可选
Year / OriginalYear发行年份 / 原专辑年份可选
Disc / DiscName碟号 / 碟名可选
Index曲目序号可选
Track曲名必需
Genre / BPM / Label流派 / BPM / 厂牌可选
DiscogsIDDiscogs 发行 ID(纯数字)可选

官方注解:使用 source: path 时只有 Track 与(AlbumArtist 或 Artist)是硬性要求;实测默认 embedded 模式下,正则主要用于决定哪些文件算曲库文件。实测验证正则生效:按 艺人/专辑 (年份)/序号 - 曲名.mp3 结构放置 6 个文件后全部正确解析(Parsing successful 日志 + 专辑年份 2024/2025 与目录一致,见 5.2)。

② metadata(元数据来源策略)

  • source:embedded(读内嵌标签,实测默认)或 path(读正则命名组);
  • order:only(缺字段不回退另一来源)或 preferred(缺字段时用另一来源补齐;此时同名目录下的 cover.* 会被当作封面候选);
  • useExternalProviderGenres:true(实测默认)时把外部提供商返回的流派与内嵌流派合并展示。

实测对照:本环境 embedded + only,合成文件的 ID3 标签(title/artist/album/track/date/genre)全部正确入库(GET /api/songs 回显曲名与 slug 完全对应)。

③ providers(外部元数据提供商)

对象里写了谁就启用谁,没写的完全不请求(官方 Wiki 原话:"no call to its service will be done")。v3.13.1 支持清单(官方 Providers 页):

Settings key需要密钥能补全的元数据
musicbrainz无专辑流派、厂牌;并联动 Wikidata 与 AcoustID 指纹匹配(官方警告 MusicBrainz 关闭则 Wikidata 一并不可用)
geniusapiKey艺人简介/图片、歌曲简介、纯文本歌词
wikipedia无艺人/专辑/歌曲简介
discogsapiKey艺人简介/图片、发行识别、专辑流派
allmusic / metacritic无专辑简介、专辑评分
lrclib无带时间轴的同步歌词

实测:默认 {"musicbrainz": {}} 启用后,GET /api/external-providers 回显 {"metadata":{"count":1,...},"items":[{"id":1,"name":"MusicBrainz","slug":"musicbrainz","illustrationId":1}]};matcher 日志可见到 MusicBrainz 地区数据的匹配过程(实测回显节选:INFO Matched data area=Osaka parent_area=linked)。

④ compilations(合辑识别)

  • artists:出现在该名单中的"专辑艺人"(如 Various Artists)不建艺人实体,专辑按无主合辑处理;
  • useID3CompTag:true(实测默认)时额外识别 iTunes 风格的合辑标记位。

⑤ useEmbeddedThumbnails

false(实测默认):视频文件内嵌的图片不当作封面。置 true 时视频内嵌图会进入封面候选。音频文件的内嵌封面不受此参数影响,始终参与封面识别。

六、生产配置模板

适用场景:16 GB 内存、NVMe SSD、家庭/小团队 NAS,曲库 1~5 万首,1~5 个用户,内网访问为主。以下模板与本次实测部署一致,可直接替换密钥字段后使用:

# /opt/meelo/.env —— 生产模板(密钥现场生成)
TAG=v3.13.1
PORT=8140
PUBLIC_URL=http://<服务器实际可达地址>:8140
CONFIG_DIR=/opt/meelo/config
DATA_DIR=/opt/meelo/data
ALLOW_ANONYMOUS=0
ENABLE_USER_REGISTRATION=0        # 首管理员建好后收紧
LASTFM_API_KEY=
LASTFM_API_SECRET=
POSTGRES_USER=meelo
POSTGRES_PASSWORD=<随机口令>
POSTGRES_DB=meelo
RABBITMQ_USER=meelo
RABBITMQ_PASSWORD=<随机口令>
JWT_SIGNATURE=<openssl rand -hex 32 输出>
MEILI_MASTER_KEY=<openssl rand -hex 16 输出>
API_KEYS=<openssl rand -hex 16 输出>
INTERNAL_DATA_DIR=/data
INTERNAL_CONFIG_DIR=/config
{
	"trackRegex": [
		"^([\\/\\\\]+.*)*[\\/\\\\]+(?P<AlbumArtist>.+)[\\/\\\\]+Unknown Album[\\/\\\\]+(?P<Track>.*)\\..*$",
		"^([\\/\\\\]+.*)*[\\/\\\\]+(?P<AlbumArtist>.+)[\\/\\\\]+(?P<Album>.+)(\\s+\\((?P<Year>\\d{4})\\))?[\\/\\\\]+((?P<Disc>[0-9]+)-)?(?P<Index>[0-9]+)\\s+(?P<Track>.*)\\..*$"
	],
	"metadata": { "source": "embedded", "order": "preferred", "useExternalProviderGenres": true },
	"providers": { "musicbrainz": {}, "lrclib": {} },
	"compilations": { "useID3CompTag": true, "artists": ["Various Artists", "Compilation", "OST"] },
	"useEmbeddedThumbnails": false
}

模板取舍说明:order: preferred 让标签残缺的老文件回退到路径解析(实测环境标签齐全所以默认 only 也够,但生产曲库混杂时 preferred 更稳);providers 追加 lrclib 获得同步歌词而无需申请密钥;compilations 名单按常见合辑命名习惯扩充。资源占用参考(实测环境):9 个服务空载常驻内存约 1.2 GB,扫描千首级曲库 CPU 峰值短暂过 1 核(transcoder 限速 cpus: 1),SSD 上全库扫描 6 首测试曲 1~2 秒完成,万首曲库预计分钟级。

七、常见问题

Q1:改了 settings.json 为什么没生效? 扫描器在每次扫描任务启动时读取该文件,改完必须触发一次重新扫描(POST /scanner/scan 或界面 Rescan 按钮)。实测改完不扫、参数不变。

Q2:服务起不来了,报 settings.json 相关错误? 官方 Wiki 列出的两大启动失败原因之一就是坏 settings.json。先用 python3 -m json.tool 校验语法,再核对 5 个顶层参数是否全部存在(官方要求 all fields must be specified,缺一个都不行)。

Q3:PUBLIC_URL 到底填什么? 浏览器地址栏里用户实际访问的地址(含端口、不含末尾斜杠)。填错的特征:页面能开但登录按钮置灰、或页面空白报跨域。实测验证方法:浏览器直接打开 http://<PUBLIC_URL>/api/settings 能看到 JSON 即正确。

Q4:换了 JWT_SIGNATURE 后所有人都登不上了? 正常现象:JWT 由该密钥签名,换密钥等于作废全部会话,重新登录即可。同理换 API_KEYS 必须把 scanner 与 matcher 一并重启,否则扫描任务会以 401 失败。

Q5:postgres 连接被拒,密码明明没写错? Postgres 的密码在首次初始化时写入数据卷,之后改 .env 不影响已有卷。要么进库把用户密码改成新值,要么接受数据清空重建卷(重建前先备份数据目录与数据库导出)。

Q6:内网环境(无法访问外网)会损失什么? matcher 拿不到 MusicBrainz/歌词提供商的数据,专辑流派、评分、外部简介缺失;但本地功能不受影响——内嵌标签解析、扫描注册、搜索、播放全部正常(实测 scanner/matcher 与外网断开时的错误只出现在 matcher 日志,API 与播放无异常)。

八、参考链接