fix(announce): 修复进站预告音频终点站名字被跳过的问题
根因链: - station_broadcast.lua 通过 BlockReader / CreateTarget 两个分支触发 train_approaching 发送时,只带 destination (中文名/站名),未带 destCode;server 端只能走 getStationCodeFromName(destination) 正则解析,正则没匹配到就会得到 UNK → ch-UNK.wav / ja-UNK.wav 不存在 → 整条目的地段音频被 ffmpeg concat 跳过 - 对比 train_arrival (Peripherals.station 分支) 是有 destCode 字段的(由 Utils.getStationCode + schedule 解析得到),所以到站广播终点站名能正常播出,预告(走 Display/BlockReader 分支)不能 修复: 1. station_broadcast.lua 四处 train_approaching / train_alert Network.send 全部补 destCode = Utils.getStationCode(destination): - L4053 (alert, blockreader) / L4091 (approach, blockreader) - L4221 (alert, createTarget) / L4257 (approach, createTarget) 2. server.js 新增 resolveStationAudioCode(rawCode, rawName) 三级兜底解析: - L1: 直接用 raw destCode(优先级最高,客户端算好的) - L2: 正则解析 destination 名字抽取 code(parens/dash/下划线模式) - L3: 把 destination 名拿去 findStationByFlexibleName 已注册站台表里 fuzzy 匹配,取其 code - 解析不到就打 WARN 日志,提示会跳过这一段 3. handleTrainApproaching / handleTrainArrival / handleTrainDeparture 三个 handler 的 destCode / nextCode 全部切到 resolveStationAudioCode 统一入口,不再各写一遍正则,所有预告/到站/发车音频用同一条解析链,保证结果一致 APP_VERSION_TEXT bump 到 v1.0.110
This commit is contained in:
+40
-5
@@ -1963,6 +1963,39 @@ function ensureSilenceWav() {
|
|||||||
execSync(`ffmpeg -y -v quiet -f lavfi -i anullsrc=r=48000:cl=mono -t 1 -c:a pcm_s16le "${silence1sWavPath}"`);
|
execSync(`ffmpeg -y -v quiet -f lavfi -i anullsrc=r=48000:cl=mono -t 1 -c:a pcm_s16le "${silence1sWavPath}"`);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
function resolveStationAudioCode(rawCode, rawName) {
|
||||||
|
const code1 = String(rawCode || '').trim().toLowerCase().replace(/_/g, '-');
|
||||||
|
const name = String(rawName || '').trim();
|
||||||
|
const pick = (c) => {
|
||||||
|
if (!c) return null;
|
||||||
|
const v = String(c).trim().toLowerCase().replace(/_/g, '-');
|
||||||
|
return v && v !== 'unk' && v !== 'unknown' ? v : null;
|
||||||
|
};
|
||||||
|
// Level 1: raw destCode (already provided)
|
||||||
|
let result = pick(code1);
|
||||||
|
let levelHit = result ? 1 : 0;
|
||||||
|
// Level 2: extract from destination name string (parens / dash / pattern)
|
||||||
|
if (!result && name) {
|
||||||
|
const extracted = getStationCodeFromName(name);
|
||||||
|
result = pick(extracted);
|
||||||
|
if (result) levelHit = 2;
|
||||||
|
}
|
||||||
|
// Level 3: fuzzy match station name to registered stations and use their code
|
||||||
|
if (!result && name) {
|
||||||
|
const reg = findStationByFlexibleName(name);
|
||||||
|
if (reg && reg.code) {
|
||||||
|
result = pick(reg.code);
|
||||||
|
if (result) levelHit = 3;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
if (result && (name || rawCode)) {
|
||||||
|
log('DEBUG', `[Station-Audio-Code] resolved destCode=${result} (level=${levelHit}) rawCode=${JSON.stringify(rawCode || null)} name=${JSON.stringify(name || null)}`);
|
||||||
|
} else {
|
||||||
|
log('WARN', `[Station-Audio-Code] FAILED to resolve station audio code: rawCode=${JSON.stringify(rawCode || null)} name=${JSON.stringify(name || null)} → sequence will skip this station audio (silence / missing wav)`);
|
||||||
|
}
|
||||||
|
return result || null;
|
||||||
|
}
|
||||||
|
|
||||||
function getOrCreateHlsStreamState(streamName) {
|
function getOrCreateHlsStreamState(streamName) {
|
||||||
if (!hlsStreams[streamName]) {
|
if (!hlsStreams[streamName]) {
|
||||||
hlsStreams[streamName] = {
|
hlsStreams[streamName] = {
|
||||||
@@ -2688,7 +2721,7 @@ function handleTrainApproaching(ws, data) {
|
|||||||
const finalPlatform = cleanPlatform || '1';
|
const finalPlatform = cleanPlatform || '1';
|
||||||
|
|
||||||
const lineCode = data.lineCode || (stationCode ? stationCode.split('-')[0] : 'UNK');
|
const lineCode = data.lineCode || (stationCode ? stationCode.split('-')[0] : 'UNK');
|
||||||
const destCode = data.destCode || getStationCodeFromName(data.destination) || 'UNK';
|
const destCode = resolveStationAudioCode(data.destCode, data.destination) || 'UNK';
|
||||||
|
|
||||||
log('INFO', `Train ${trainId} approaching ${stationName}. Broadcasting pre-arrival...`);
|
log('INFO', `Train ${trainId} approaching ${stationName}. Broadcasting pre-arrival...`);
|
||||||
|
|
||||||
@@ -2804,9 +2837,10 @@ function handleTrainArrival(ws, data) {
|
|||||||
const finalPlatform = cleanPlatform || '1';
|
const finalPlatform = cleanPlatform || '1';
|
||||||
|
|
||||||
const lineCode = data.lineCode || (stationCode ? stationCode.split('-')[0] : 'UNK');
|
const lineCode = data.lineCode || (stationCode ? stationCode.split('-')[0] : 'UNK');
|
||||||
const destCode = data.destCode || getStationCodeFromName(data.destination) || 'UNK';
|
const destCode = resolveStationAudioCode(data.destCode, data.destination) || 'UNK';
|
||||||
const nextStationRaw = data.nextStation ? String(data.nextStation).trim() : '';
|
const nextStationRaw = data.nextStation ? String(data.nextStation).trim() : '';
|
||||||
const nextCodeRaw = data.nextCode ? String(data.nextCode).trim() : (nextStationRaw ? getStationCodeFromName(nextStationRaw) : '');
|
const nextCodeRaw = resolveStationAudioCode(data.nextCode, nextStationRaw) ||
|
||||||
|
(nextStationRaw ? getStationCodeFromName(nextStationRaw) : '');
|
||||||
const hasNextStation = nextStationRaw && nextStationRaw !== '' && nextCodeRaw && nextCodeRaw !== 'UNK' && nextCodeRaw !== '';
|
const hasNextStation = nextStationRaw && nextStationRaw !== '' && nextCodeRaw && nextCodeRaw !== 'UNK' && nextCodeRaw !== '';
|
||||||
const finalNextCode = hasNextStation ? nextCodeRaw : null;
|
const finalNextCode = hasNextStation ? nextCodeRaw : null;
|
||||||
|
|
||||||
@@ -2885,9 +2919,10 @@ function handleTrainDeparture(ws, data) {
|
|||||||
const beep = data.departureBeep || data.beep || 'fc1';
|
const beep = data.departureBeep || data.beep || 'fc1';
|
||||||
|
|
||||||
const lineCode = data.lineCode || (stationCode ? stationCode.split('-')[0] : 'UNK');
|
const lineCode = data.lineCode || (stationCode ? stationCode.split('-')[0] : 'UNK');
|
||||||
const destCode = data.destCode || getStationCodeFromName(data.destination) || 'UNK';
|
const destCode = resolveStationAudioCode(data.destCode, data.destination) || 'UNK';
|
||||||
const nextStationRaw = data.nextStation ? String(data.nextStation).trim() : '';
|
const nextStationRaw = data.nextStation ? String(data.nextStation).trim() : '';
|
||||||
const nextCodeRaw = data.nextCode ? String(data.nextCode).trim() : (nextStationRaw ? getStationCodeFromName(nextStationRaw) : '');
|
const nextCodeRaw = resolveStationAudioCode(data.nextCode, nextStationRaw) ||
|
||||||
|
(nextStationRaw ? String(data.nextCode || '').trim() || getStationCodeFromName(nextStationRaw) : '');
|
||||||
const hasNextStation = nextStationRaw && nextStationRaw !== '' && nextCodeRaw && nextCodeRaw !== 'UNK' && nextCodeRaw !== '';
|
const hasNextStation = nextStationRaw && nextStationRaw !== '' && nextCodeRaw && nextCodeRaw !== 'UNK' && nextCodeRaw !== '';
|
||||||
const finalNextCode = hasNextStation ? nextCodeRaw : null;
|
const finalNextCode = hasNextStation ? nextCodeRaw : null;
|
||||||
|
|
||||||
|
|||||||
+17
-13
@@ -1,6 +1,6 @@
|
|||||||
|
|
||||||
-- 1. Configuration & Constants
|
-- 1. Configuration & Constants
|
||||||
local APP_VERSION_TEXT = "v1.0.109"
|
local APP_VERSION_TEXT = "v1.0.110"
|
||||||
|
|
||||||
local CONFIG = {
|
local CONFIG = {
|
||||||
CLOUD_URL = "ws://stabadmin.fse-media.group",
|
CLOUD_URL = "ws://stabadmin.fse-media.group",
|
||||||
@@ -4044,18 +4044,19 @@ function Main.loop()
|
|||||||
Utils.log("INFO", string.format("Train Alert: %s (ETA: %ds, Delay: %dm, Cancelled: %s, Reason: %s)", trainName, etaSeconds, displayDelayMinutes, tostring(cancelled), tostring(reason or "")))
|
Utils.log("INFO", string.format("Train Alert: %s (ETA: %ds, Delay: %dm, Cancelled: %s, Reason: %s)", trainName, etaSeconds, displayDelayMinutes, tostring(cancelled), tostring(reason or "")))
|
||||||
if Utils.isLocalStationMaster() then
|
if Utils.isLocalStationMaster() then
|
||||||
Network.send({
|
Network.send({
|
||||||
type = "train_alert",
|
type = "train_alert",
|
||||||
stationName = State.stationName,
|
stationName = State.stationName,
|
||||||
stationCode = State.stationCode,
|
stationCode = State.stationCode,
|
||||||
stationPlatform = platform,
|
stationPlatform = platform,
|
||||||
trainId = trainName,
|
trainId = trainName,
|
||||||
destination = destination,
|
destination = destination,
|
||||||
eta = tostring(etaSeconds) .. "s",
|
destCode = Utils.getStationCode(destination),
|
||||||
etaSeconds = etaSeconds,
|
eta = tostring(etaSeconds) .. "s",
|
||||||
delay = displayDelayMinutes,
|
etaSeconds = etaSeconds,
|
||||||
cancelled = cancelled,
|
delay = displayDelayMinutes,
|
||||||
reason = reason
|
cancelled = cancelled,
|
||||||
})
|
reason = reason
|
||||||
|
})
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
@@ -4087,6 +4088,7 @@ function Main.loop()
|
|||||||
stationPlatform = platform,
|
stationPlatform = platform,
|
||||||
trainId = trainName,
|
trainId = trainName,
|
||||||
destination = destination,
|
destination = destination,
|
||||||
|
destCode = Utils.getStationCode(destination),
|
||||||
eta = string.format("%.1fs", etaSeconds),
|
eta = string.format("%.1fs", etaSeconds),
|
||||||
etaSeconds = etaSeconds,
|
etaSeconds = etaSeconds,
|
||||||
delay = displayDelayMinutes,
|
delay = displayDelayMinutes,
|
||||||
@@ -4216,6 +4218,7 @@ function Main.loop()
|
|||||||
stationPlatform = platform or State.stationPlatform or "1",
|
stationPlatform = platform or State.stationPlatform or "1",
|
||||||
trainId = tName,
|
trainId = tName,
|
||||||
destination = dest,
|
destination = dest,
|
||||||
|
destCode = Utils.getStationCode(dest),
|
||||||
eta = etaStr,
|
eta = etaStr,
|
||||||
etaSeconds = etaSeconds,
|
etaSeconds = etaSeconds,
|
||||||
delay = delay
|
delay = delay
|
||||||
@@ -4251,6 +4254,7 @@ function Main.loop()
|
|||||||
stationPlatform = platform or State.stationPlatform or "1",
|
stationPlatform = platform or State.stationPlatform or "1",
|
||||||
trainId = tName,
|
trainId = tName,
|
||||||
destination = dest,
|
destination = dest,
|
||||||
|
destCode = Utils.getStationCode(dest),
|
||||||
eta = etaStr,
|
eta = etaStr,
|
||||||
etaSeconds = etaSeconds,
|
etaSeconds = etaSeconds,
|
||||||
delay = delay
|
delay = delay
|
||||||
|
|||||||
Reference in New Issue
Block a user