16 KiB
PyINT LT-1 精密轨道桥接设计
日期: 2026-04-19
状态: 方案设计
范围: LT-1 精密轨道真正参与 PyINT / Gamma 计算、与现有 Task_* 输入模式协同、前后端与运维落点、分阶段实施
1. 结论
当前仓库已经完成了 LT-1 轨道 TXT 的治理级接入,但还没有完成“精密轨道真实参与 PyINT / Gamma 计算”这一层。
本次设计的核心结论如下:
- 不能把系统轨道池里的
LT1*_GpsData_GAS_C_YYYYMMDD.txt简单当成par_LT1_SLC的直接输入,因为当前 PyINT / Gamma 的 LT-1 导入链并没有暴露这样的接口。 - 正确的桥接点是 LT-1 导入完成后生成的
.slc.par/.slc.update.par里的state_vector_*段,而不是当前外层run_lt1_pyint_pipeline.py的任务参数层。 - 推荐方案是在现有 Windows 侧轨道治理不变的前提下,在 WSL 侧新增一个 LT-1 精轨桥接 helper,把系统选中的精轨 TXT 重采样到 Gamma 参数文件已有的时间栅格,再回写
.slc.par。 - 桥接动作必须发生在 LT-1 导入之后、DEM / coreg / 干涉处理之前;只做“提交前预检”或“运行记录留痕”是不够的。
- 一期先不改数据库,先把桥接结果写进
input_assets、pyint_run_summary.json、结果 manifest 和运行日志;只有在后续确实需要跨运行检索、统计、追责时,再通过现有数据库自维护机制补迁移。
2. 现状与依据
2.1 当前本地代码链路
现有 vendored PyINT 的 LT-1 流程为:
pyintApp.py
-> down2slc_LT1_all.py
-> down2slc_LT1.py 或 down2slc_cat_LT1.py
-> LT1_import_SLC_from_zipfiles1
-> par_LT1_SLC / par_LT1_SLC_YSLi
-> 生成 .slc.par / .slc.update.par
已确认的关键事实:
- pyintApp.py 会先执行 LT-1
raw2slc,然后再进入 DEM、coreg、差分干涉。 - down2slc_LT1.py 与 down2slc_cat_LT1.py 是当前 LT-1 Python 入口。
- LT1_import_SLC_from_zipfiles1 已经显式处理
state_vector_*,说明轨道状态向量确实是 LT-1 导入链中的有效控制点。 - 20210110.slc.par 展示了 Gamma 参数文件中的状态向量布局,包括:
number_of_state_vectorstime_of_first_state_vectorstate_vector_intervalstate_vector_position_istate_vector_velocity_i
2.2 当前系统已有能力
仓库已经具备以下基础:
- pyint_input_assets_service.py 已能从
ORBIT_POOL_ENVI/PYINT_ORBIT_POOL_TXT解析 master/slave 对应的 LT-1 精轨 TXT。 - run_lt1_pyint_pipeline.py 已能把
Task_*目录物化成 PyINT 工作区,并记录orbit_policy与input_assets。 - DinsarProductionPanel.jsx 已经有 PyINT 输入资产预检入口,能够把“轨道是否齐全”提前暴露给用户。
- ISCE2 侧已经有 LT-1 轨道 TXT 解析链,可复用 convert_lt1_orbit_to_isce_xml.py 与 lt1_input_resolver.py 中的
parse_orbit_file、时间窗口解析等逻辑。
2.3 Gamma 官方文档给出的关键约束
用户提供的 Gamma 官方文档是:
其中与本设计直接相关的结论有两点:
- 在 LT-1 repeat-pass DInSAR 流程中,Gamma 文档明确说明,
par_LT1_SLC导入后需要立即检查并过滤 orbit state vectors,并使用ORB_filt_spline.py做校验。 - 在 LT-1 tandem single-pass 流程中,文档同样建议“读入数据后立刻检查/过滤状态向量”,以确保后续 MLI 参数和几何步骤使用的是修正后的状态向量。
这意味着桥接点必须放在“LT-1 导入完成之后立刻执行”,而不是只在外层运行摘要里记录轨道来源。
3. 当前缺口
当前实现还缺以下一层:
- 系统已经知道“这次任务应该用哪份精轨 TXT”,但 PyINT / Gamma 还不知道。
- 预检面板只能阻断“轨道缺失”的任务,不能保证“轨道已进入计算”。
- 只改外层
run_lt1_pyint_pipeline.py不够,因为 PyINT 内部会自己完成raw2slc -> dem -> coreg连续流程,桥接必须插在内部raw2slc之后。 cat场景不能只更新单个.slc.par。当前 down2slc_cat_LT1.py 最终拼接依赖*.slc.update.par,所以方案必须覆盖:- 每个分片导入后的参数文件
- 最终拼接得到的
<date>.slc.par
4. 目标与非目标
4.1 目标
- 保留当前
Task_*输入模式,不要求用户维护第二套 PyINT 原生目录。 - 让 LT-1 精轨 TXT 真正参与 PyINT / Gamma 计算,而不是只做治理留痕。
- 同时覆盖单场景和多分片
cat场景。 - 与现有 DEM 策略、结果目录、运行日志、预检面板兼容。
- 为后续 Gamma 配对集成保留复用路径。
4.2 非目标
- 一期不修改数据库主结构。
- 一期不在运维自检页新增复杂操作区。
- 一期不承诺完成 LT1A/LT1B tandem 单通道单程干涉生产链,只保证当前 repeat-pass PyINT 流程的精轨桥接。
- 一期不让用户在前端手工输入单次轨道路径。
5. 推荐总体方案
5.1 分层思路
推荐把方案拆成“控制面”和“计算面”两层。
A. 控制面,继续由现有后端负责
控制面继续沿用现有资产治理链路:
- 从
Task_*解析 master/slave 的卫星与日期 - 从
PYINT_ORBIT_POOL_TXT或ORBIT_POOL_ENVI定位精轨 TXT - 在
input_assets/orbits/下留痕 - 在预检接口中返回“是否可提交”
这部分由现有 pyint_input_assets_service.py 继续承担。
B. 计算面,新增 WSL 侧精轨桥接 helper
新增一个 helper,例如:
backend/app/pyint_pipeline/apply_lt1_precise_orbit.py
其职责是:
- 读取当前任务已解析好的 orbit manifest / staged TXT。
- 读取目标
.slc.par或.slc.update.par。 - 复用现有 LT-1 TXT 解析逻辑,解析精轨状态向量。
- 以 Gamma 当前参数文件已有的时间栅格为目标,进行插值和回写。
- 备份原始参数文件。
- 可选调用
ORB_filt_spline.py做二次校验或残差诊断。 - 输出
orbit_bridge_summary.json。
5.2 为什么目标时间栅格要复用 .slc.par 自身
推荐不要自己发明新的状态向量数量和时间间隔,而是直接复用当前 .slc.par 中已有的:
number_of_state_vectorstime_of_first_state_vectorstate_vector_interval
然后把系统精轨 TXT 插值到这个时间栅格上。
这样做的收益是:
- 不改变 Gamma 已经生成的参数文件结构。
- 不引入新的向量个数假设。
- 更容易和
ORB_filt_spline.py、后续 DEM / coreg 步骤兼容。 - 对
cat场景、已有模板和下游脚本影响最小。
5.3 插值策略
推荐优先使用“基于位置和速度的 Hermite 插值”,原因是 LT-1 TXT 同时提供了位置和速度。
最小实现要求如下:
- 先复用 convert_lt1_orbit_to_isce_xml.py 的
parse_orbit_file解析状态向量。 - 根据
.slc.par的采样时间点计算目标 UTC 时间序列。 - 对目标时间序列进行状态向量重采样。
- 回写
state_vector_position_i和state_vector_velocity_i。
如果一期为了稳妥,不想一次性引入更复杂的插值器,也可以先做:
- 线性插值作为第一落地版
ORB_filt_spline.py作为强校验
但长期建议还是切到 Hermite,以减少轨道形状失真。
6. 推荐挂接点
6.1 不推荐只改最外层 wrapper
不推荐只在 run_lt1_pyint_pipeline.py 里做轨道处理,因为它在 PyINT 看来只是外层启动器,无法插入到内部 raw2slc 与 makedem 之间。
6.2 推荐挂接点
推荐优先修改以下 vendored Python 脚本:
推荐执行时机:
- 每次
LT1_import_SLC_from_zipfiles1完成后:- 对当前生成的
.slc.par - 对当前生成的
.slc.update.par执行一次桥接
- 对当前生成的
SLC_cat_list.py生成最终<date>.slc.par后:- 再对最终参数文件执行一次桥接或至少一次强校验
这样可以同时满足:
- 符合 Gamma 文档“导入后立即检查/过滤状态向量”的原则
- 覆盖单片和多分片场景
- 避免只在最终产物上补丁而遗漏拼接过程
LT1_import_SLC_from_zipfiles1 本身先不作为一期主改点,除非后续验证发现必须把逻辑进一步下沉到 shell 层才能完全覆盖。
7. 运行时流程
推荐的整体执行顺序如下:
- 用户在生产面板选择 PyINT 引擎并填写
root_dir - 后端调用 PyINT 输入资产预检
- 系统为每个
Task_*解析:- master/slave 日期
- master/slave 卫星
- 对应精轨 TXT
- DEM 策略
run_lt1_pyint_pipeline.py物化:input_assets/orbits/task_manifest.json- PyINT 工作区和模板
- 外层 wrapper 将 orbit manifest 路径、helper 路径和桥接开关注入 WSL 环境
- PyINT 执行
down2slc_LT1.py/down2slc_cat_LT1.py - 每个 LT-1 导入步骤完成后,调用
apply_lt1_precise_orbit.py - helper 回写
.slc.par - PyINT 继续执行 DEM、coreg、差分干涉、解缠、地理编码
- 系统输出:
orbit_bridge_summary.jsonpyint_run_summary.json- 结果 manifest 摘要
8. 建议新增配置
当前已有:
PYINT_ORBIT_POLICY=require_txt
PYINT_ORBIT_POOL_TXT=
建议新增或明确以下配置:
PYINT_LT1_PRECISE_ORBIT_ENABLED=true
PYINT_LT1_PRECISE_ORBIT_MODE=replace_and_validate
PYINT_LT1_PRECISE_ORBIT_STRICT=true
PYINT_LT1_PRECISE_ORBIT_MARGIN_SECONDS=120
PYINT_LT1_PRECISE_ORBIT_VALIDATE_WITH_ORB_FILT=true
PYINT_LT1_PRECISE_ORBIT_BACKUP=true
建议含义如下:
PYINT_LT1_PRECISE_ORBIT_ENABLED- 是否启用真实桥接
PYINT_LT1_PRECISE_ORBIT_MODEreplace_and_validate为推荐默认值- 后续也可扩展
validate_only
PYINT_LT1_PRECISE_ORBIT_STRICT- 桥接失败时是否阻断任务
PYINT_LT1_PRECISE_ORBIT_MARGIN_SECONDS- 对场景时间窗口额外扩展的秒数
PYINT_LT1_PRECISE_ORBIT_VALIDATE_WITH_ORB_FILT- 是否调用
ORB_filt_spline.py做残差校验
- 是否调用
PYINT_LT1_PRECISE_ORBIT_BACKUP- 是否在回写前备份原始
.slc.par
- 是否在回写前备份原始
9. 元数据与落盘策略
一期建议不改数据库,先把桥接痕迹记录到运行产物里。
9.1 input_assets 侧
建议在 input_assets/orbits/ 下保留:
- 解析到的 master/slave 精轨 TXT
orbit_resolution.jsonorbit_bridge_request.json
9.2 运行摘要侧
建议在 pyint_run_summary.json 中新增:
{
"orbit_bridge": {
"enabled": true,
"mode": "replace_and_validate",
"status": "applied",
"master": {
"orbit_txt": "..."
},
"slave": {
"orbit_txt": "..."
},
"applied_files": [
{
"path": ".../20250309.slc.par",
"role": "slave",
"vector_count": 15,
"validated": true
}
]
}
}
9.3 结果 manifest 侧
结果 manifest 只保留摘要,不重复放大块明细,建议记录:
- 是否启用精轨桥接
- 桥接状态
- master/slave 轨道来源 stem
- 是否通过
ORB_filt_spline.py校验
9.4 数据库策略
一期不改数据库。
如果后续明确需要:
- 按轨道版本检索历史运行
- 统计桥接失败原因
- 审计某次产品到底使用了哪份精轨
再通过现有 db_maintenance.py 机制新增迁移。
10. 前端与运维落点
10.1 前端
前端主入口继续放在现有 PyINT 生产区域,不新增独立页面。
建议在 DinsarProductionPanel.jsx 的 PyINT 输入资产预检卡中增加两类信息:
- 全局级:
精轨桥接: 已启用 / 仅治理 / 未启用桥接模式
- 任务级:
- master/slave 是否已解析精轨
- 本次是否满足真实桥接前置条件
不要让用户手工输入 orbit 路径。
10.2 运维自检
运维自检页不再承载新的操作区,只保留状态摘要。
建议在引擎健康或 PyINT 健康项里补充:
PYINT_LT1_PRECISE_ORBIT_ENABLED- helper 脚本是否存在
PYINT_ORBIT_POOL_TXT/ORBIT_POOL_ENVI是否可读ORB_filt_spline.py是否可调用
不建议把桥接按钮堆进现有 HealthCheckPanel.jsx。
11. 与 Gamma 配对集成的关系
这套桥接不是只服务 D-InSAR 生产,也是在为后续 Gamma 配对打基础。
原因是:
- 如果后续要把 Gamma / PyINT 配对结果真正纳入系统,配对阶段对 baseline 和场景几何的一致性要求会更高。
- 只做“轨道存在性预检”仍然不够,仍然需要一条“导入后立即修正状态向量”的内部链路。
因此推荐把本次 helper 设计成通用能力:
- 当前用于
pyintApp.py的 LT-1raw2slc - 后续也可复用于
select_pairs.py前的 LT-1 导入准备
12. 风险与未决问题
当前仍有几项需要在实现阶段验证:
- LT-1 TXT 的时间系统与
.slc.par的date + seconds-of-day是否存在跨日边界问题。 ORB_filt_spline.py更适合用于“替换后校验”还是“替换后再执行一次修正”,需要先做小样本验证。SLC_cat_list.py当前并未 vendored 到仓库中,实现阶段要进一步确认它对输入.par的依赖细节。- 当前 repeat-pass 流程与 LT1A/LT1B tandem single-pass 流程并不完全等价,后者需要单独设计。
- 如果发现某些场景的 Gamma 原始导入时间栅格明显不合理,可能需要从“复用现有时间栅格”升级到“按 scene window 重新构造时间栅格”。
13. 分阶段实施建议
Phase 1
- 新增
apply_lt1_precise_orbit.py - 复用现有 LT-1 TXT 解析器
- 实现
.slc.par读取、备份、状态向量回写 - 产出
orbit_bridge_summary.json
Phase 2
- 修改
down2slc_LT1.py和down2slc_cat_LT1.py - 在导入后与最终拼接后调用 helper
- 跑通单任务 smoke test
Phase 3
- 在运行摘要和结果 manifest 中纳入桥接信息
- 在生产面板预检区域增加“精轨桥接已启用”可见性
- 在 health 中增加最小状态摘要
Phase 4
- 用真实 LT-1 样本比较桥接前后:
ORB_filt_spline.py残差- 后续 coreg 质量
- 干涉相位整体趋势
- 评估是否为 Gamma 配对链复用相同 helper
14. 最终建议
推荐按以下原则推进:
- 继续保留现有
Task_*输入模式和轨道治理链。 - 把 LT-1 精轨接入点明确落到
.slc.par的state_vector_*回写,不再停留在治理层。 - 一期先实现“桥接 helper + vendored LT-1 raw2slc 挂接 + 运行元数据留痕”。
- 数据库先不动,运维面板先不扩张。
- 桥接 helper 从第一天起就按“未来可复用于 Gamma 配对”来设计接口。