flexaligner 0.1.0a1__tar.gz
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- flexaligner-0.1.0a1/.gitignore +51 -0
- flexaligner-0.1.0a1/LICENSE +22 -0
- flexaligner-0.1.0a1/PKG-INFO +284 -0
- flexaligner-0.1.0a1/README.md +255 -0
- flexaligner-0.1.0a1/pyproject.toml +138 -0
- flexaligner-0.1.0a1/src/flexaligner/__init__.py +101 -0
- flexaligner-0.1.0a1/src/flexaligner/__main__.py +7 -0
- flexaligner-0.1.0a1/src/flexaligner/adapters/__init__.py +1 -0
- flexaligner-0.1.0a1/src/flexaligner/adapters/hf_local.py +548 -0
- flexaligner-0.1.0a1/src/flexaligner/adapters/lexicon_file.py +399 -0
- flexaligner-0.1.0a1/src/flexaligner/adapters/wav_pcm16.py +196 -0
- flexaligner-0.1.0a1/src/flexaligner/api.py +149 -0
- flexaligner-0.1.0a1/src/flexaligner/capabilities.py +171 -0
- flexaligner-0.1.0a1/src/flexaligner/cli.py +164 -0
- flexaligner-0.1.0a1/src/flexaligner/contracts.py +267 -0
- flexaligner-0.1.0a1/src/flexaligner/core/__init__.py +89 -0
- flexaligner-0.1.0a1/src/flexaligner/core/stage1.py +1015 -0
- flexaligner-0.1.0a1/src/flexaligner/core/stage2.py +1438 -0
- flexaligner-0.1.0a1/src/flexaligner/errors.py +135 -0
- flexaligner-0.1.0a1/src/flexaligner/pipeline.py +889 -0
- flexaligner-0.1.0a1/src/flexaligner/ports.py +120 -0
- flexaligner-0.1.0a1/src/flexaligner/py.typed +1 -0
- flexaligner-0.1.0a1/src/flexaligner/textgrid.py +820 -0
|
@@ -0,0 +1,51 @@
|
|
|
1
|
+
__pycache__/
|
|
2
|
+
*.py[cod]
|
|
3
|
+
*.egg-info/
|
|
4
|
+
|
|
5
|
+
# 操作系统和编辑器本地文件
|
|
6
|
+
.DS_Store
|
|
7
|
+
Thumbs.db
|
|
8
|
+
Desktop.ini
|
|
9
|
+
.idea/
|
|
10
|
+
.vscode/
|
|
11
|
+
|
|
12
|
+
# Python 测试、质量检查和构建产物
|
|
13
|
+
.coverage
|
|
14
|
+
coverage.json
|
|
15
|
+
coverage.xml
|
|
16
|
+
.mypy_cache/
|
|
17
|
+
.pytest_cache/
|
|
18
|
+
.ruff_cache/
|
|
19
|
+
.venv/
|
|
20
|
+
build/
|
|
21
|
+
dist/
|
|
22
|
+
htmlcov/
|
|
23
|
+
|
|
24
|
+
# 本地运行输入、模型、输出和临时中间数据
|
|
25
|
+
/artifacts/
|
|
26
|
+
/data/
|
|
27
|
+
/models/
|
|
28
|
+
/outputs/
|
|
29
|
+
/runs/
|
|
30
|
+
/scratch/
|
|
31
|
+
/temp/
|
|
32
|
+
/tmp/
|
|
33
|
+
*.log
|
|
34
|
+
*.TextGrid.tmp
|
|
35
|
+
*.incomplete
|
|
36
|
+
|
|
37
|
+
# 仅供本地维护者/agent 使用的治理、计划和验收文档
|
|
38
|
+
/ACCEPTANCE.md
|
|
39
|
+
/AGENTS.md
|
|
40
|
+
/ALPHA_RESOURCE_VALIDATION.md
|
|
41
|
+
/DECISIONS.md
|
|
42
|
+
/FINAL_ACCEPTANCE_REPORT.md
|
|
43
|
+
/IMPLEMENTATION_PLAN.md
|
|
44
|
+
/OPEN_QUESTIONS.md
|
|
45
|
+
/REAL_MODEL_E2E_REPORT.md
|
|
46
|
+
/REVIEW_DECISION_REPORT.md
|
|
47
|
+
/STAGE1_RESOURCE_REPORT.md
|
|
48
|
+
/STAGE2_RESOURCE_REPORT.md
|
|
49
|
+
/STATE.md
|
|
50
|
+
/project.md
|
|
51
|
+
/docs/archive/
|
|
@@ -0,0 +1,22 @@
|
|
|
1
|
+
MIT License
|
|
2
|
+
|
|
3
|
+
Copyright (c) 2026 WANG Yiming
|
|
4
|
+
|
|
5
|
+
Permission is hereby granted, free of charge, to any person obtaining a copy
|
|
6
|
+
of this software and associated documentation files (the "Software"), to deal
|
|
7
|
+
in the Software without restriction, including without limitation the rights
|
|
8
|
+
to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
|
|
9
|
+
copies of the Software, and to permit persons to whom the Software is
|
|
10
|
+
furnished to do so, subject to the following conditions:
|
|
11
|
+
|
|
12
|
+
The above copyright notice and this permission notice shall be included in all
|
|
13
|
+
copies or substantial portions of the Software.
|
|
14
|
+
|
|
15
|
+
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
|
16
|
+
IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
|
17
|
+
FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
|
18
|
+
AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
|
19
|
+
LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
|
|
20
|
+
OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
|
|
21
|
+
SOFTWARE.
|
|
22
|
+
|
|
@@ -0,0 +1,284 @@
|
|
|
1
|
+
Metadata-Version: 2.5
|
|
2
|
+
Name: flexaligner
|
|
3
|
+
Version: 0.1.0a1
|
|
4
|
+
Summary: Two-stage forced alignment for long-form real-world speech.
|
|
5
|
+
Project-URL: Homepage, https://github.com/USTCPhonetics/FlexAligner
|
|
6
|
+
Project-URL: Repository, https://github.com/USTCPhonetics/FlexAligner
|
|
7
|
+
Project-URL: Issues, https://github.com/USTCPhonetics/FlexAligner/issues
|
|
8
|
+
Author: Yiming Wang, Jiahong Yuan
|
|
9
|
+
License-Expression: MIT
|
|
10
|
+
License-File: LICENSE
|
|
11
|
+
Keywords: ctc,forced-alignment,phonetics,speech,textgrid
|
|
12
|
+
Classifier: Development Status :: 3 - Alpha
|
|
13
|
+
Classifier: Intended Audience :: Science/Research
|
|
14
|
+
Classifier: Programming Language :: Python :: 3
|
|
15
|
+
Classifier: Programming Language :: Python :: 3.10
|
|
16
|
+
Classifier: Programming Language :: Python :: 3.11
|
|
17
|
+
Classifier: Programming Language :: Python :: 3.12
|
|
18
|
+
Classifier: Programming Language :: Python :: 3.13
|
|
19
|
+
Classifier: Programming Language :: Python :: 3.14
|
|
20
|
+
Classifier: Topic :: Multimedia :: Sound/Audio :: Speech
|
|
21
|
+
Classifier: Typing :: Typed
|
|
22
|
+
Requires-Python: <3.15,>=3.10
|
|
23
|
+
Requires-Dist: numpy<2.3,>=1.26; python_version < '3.14'
|
|
24
|
+
Requires-Dist: numpy<3,>=2.3.5; python_version >= '3.14'
|
|
25
|
+
Provides-Extra: inference
|
|
26
|
+
Requires-Dist: torch==2.3.1; extra == 'inference'
|
|
27
|
+
Requires-Dist: transformers==4.41.2; extra == 'inference'
|
|
28
|
+
Description-Content-Type: text/markdown
|
|
29
|
+
|
|
30
|
+
<div align="center">
|
|
31
|
+
|
|
32
|
+
# 🌊 FlexAligner
|
|
33
|
+
|
|
34
|
+
### Robust Speech-Text Alignment from Signal to Symbol
|
|
35
|
+
|
|
36
|
+
[](http://phonetics.ustc.edu.cn/)
|
|
37
|
+
[](https://www.python.org/)
|
|
38
|
+
[](LICENSE)
|
|
39
|
+
[](https://huggingface.co/USTCPhonetics)
|
|
40
|
+
|
|
41
|
+
**A Neural-Based Forced Alignment Framework for "Wild" Real-World Data**
|
|
42
|
+
<br>
|
|
43
|
+
**面向真实非受控数据的深度学习强鲁棒性对齐工具**
|
|
44
|
+
|
|
45
|
+
[**English**](#-introduction) | [**简体中文**](#-简介)
|
|
46
|
+
|
|
47
|
+
</div>
|
|
48
|
+
|
|
49
|
+
---
|
|
50
|
+
|
|
51
|
+
## 📖 Introduction
|
|
52
|
+
|
|
53
|
+
**FlexAligner** is a robust speech-text alignment framework built upon
|
|
54
|
+
**wav2vec 2.0**. It is designed for real-world linguistic data, where audio
|
|
55
|
+
signals and textual transcriptions may contain noise, hesitations, untranscribed
|
|
56
|
+
events, or local mismatches.
|
|
57
|
+
|
|
58
|
+
FlexAligner decomposes forced alignment into two stages:
|
|
59
|
+
|
|
60
|
+
1. **Macro-Segmentation (CTC Chunking):** Uses a CTC acoustic model to locate
|
|
61
|
+
reliable transcript anchors and divide long-form audio into ordered chunks.
|
|
62
|
+
2. **Micro-Alignment (Local Alignment):** Uses a constrained pronunciation
|
|
63
|
+
graph and two-pass Viterbi decoding to estimate word and phone boundaries
|
|
64
|
+
within each chunk.
|
|
65
|
+
|
|
66
|
+
### 🌟 Key Features
|
|
67
|
+
|
|
68
|
+
* **🛡️ Tolerance to Mismatch:** Uncovered portions of the audio timeline are
|
|
69
|
+
represented explicitly as `NULL` intervals instead of being silently forced
|
|
70
|
+
into neighboring words or phones.
|
|
71
|
+
* **🎯 Word and Phone Boundaries:** Produces Praat TextGrid files with continuous
|
|
72
|
+
`words` and `phones` tiers while preserving the input word order.
|
|
73
|
+
* **🔒 Local and Reproducible:** Models and pronunciation dictionaries are
|
|
74
|
+
supplied as explicit local paths; alignment does not automatically download
|
|
75
|
+
models or silently generate OOV pronunciations.
|
|
76
|
+
* **📦 Python Package and CLI:** Provides a typed Python API and a command-line
|
|
77
|
+
interface for single-file alignment.
|
|
78
|
+
|
|
79
|
+
The first public preview focuses on **English, CPU, and single-file alignment**.
|
|
80
|
+
Mandarin, GPU, batch processing, Web services, automatic model download,
|
|
81
|
+
multi-format decoding, resampling, default G2P, and confidence calibration are
|
|
82
|
+
reserved interfaces and are not yet production features.
|
|
83
|
+
|
|
84
|
+
---
|
|
85
|
+
|
|
86
|
+
## 🌏 简介
|
|
87
|
+
|
|
88
|
+
**FlexAligner** 是一个基于 **wav2vec 2.0** 的语音—文本对齐框架,面向真实语言材料中
|
|
89
|
+
常见的噪音、停顿、未转写声音事件以及音频与文本局部不一致等问题。
|
|
90
|
+
|
|
91
|
+
FlexAligner 将强制对齐分为两个阶段:
|
|
92
|
+
|
|
93
|
+
1. **宏观切分(CTC Chunking):** 使用 CTC 声学模型寻找可靠的文本锚点,并将长音频
|
|
94
|
+
划分为顺序一致的局部片段。
|
|
95
|
+
2. **微观对齐(Local Alignment):** 在每个片段内构建受约束的发音图,通过两遍
|
|
96
|
+
Viterbi 解码估计词和音素边界。
|
|
97
|
+
|
|
98
|
+
### 🌟 核心优势
|
|
99
|
+
|
|
100
|
+
* **🛡️ 容错设计:** 对未被词或音素覆盖的时段使用明确的 `NULL` 区间表示,避免将其
|
|
101
|
+
静默挤压到相邻标签中。
|
|
102
|
+
* **🎯 词与音素边界:** 输出 Praat TextGrid,`words` 和 `phones` 两层连续覆盖完整
|
|
103
|
+
音频时间轴,同时保持输入词序。
|
|
104
|
+
* **🔒 本地与可复现:** 模型和发音词典均由用户显式指定;运行时不会自动下载模型,
|
|
105
|
+
也不会对 OOV 词静默生成发音。
|
|
106
|
+
* **📦 Python 包与 CLI:** 提供带类型定义的 Python API 和单文件命令行接口。
|
|
107
|
+
|
|
108
|
+
首个公开预览版聚焦于**英语、CPU、单文件对齐**。普通话、GPU、批处理、Web 服务、
|
|
109
|
+
自动模型下载、多格式解码、自动重采样、默认 G2P 和置信度校准目前仅保留接口,尚未
|
|
110
|
+
作为正式能力开放。
|
|
111
|
+
|
|
112
|
+
---
|
|
113
|
+
|
|
114
|
+
## 🏗️ Architecture
|
|
115
|
+
|
|
116
|
+
```mermaid
|
|
117
|
+
graph TD
|
|
118
|
+
Input[Input: PCM16 WAV + Transcript] --> Lexicon[Local Pronunciation Lexicon];
|
|
119
|
+
Lexicon --> B[Stage 1: CTC Chunking];
|
|
120
|
+
B --> C{Reliable Ordered Chunks};
|
|
121
|
+
C --> D[Stage 2: Pronunciation Graph];
|
|
122
|
+
D --> E[Two-pass Viterbi Decoding];
|
|
123
|
+
E --> F[Words + Phones + NULL TextGrid];
|
|
124
|
+
```
|
|
125
|
+
|
|
126
|
+
## 🚀 Installation
|
|
127
|
+
|
|
128
|
+
The import-safe core package targets Python 3.10–3.14. The frozen inference
|
|
129
|
+
extra pins Torch 2.3.1 and Transformers 4.41.2 and is installable on Python
|
|
130
|
+
3.10–3.12. Real-model release evidence currently covers only Linux x86_64 with
|
|
131
|
+
Python 3.10.8; Python 3.13–3.14 are core-only.
|
|
132
|
+
|
|
133
|
+
After the public alpha is available from PyPI, install the exact preview with:
|
|
134
|
+
|
|
135
|
+
```bash
|
|
136
|
+
python -m pip install "flexaligner[inference]==0.1.0a1"
|
|
137
|
+
```
|
|
138
|
+
|
|
139
|
+
For a CPU-only Linux environment, install the frozen Torch build from its CPU
|
|
140
|
+
index first:
|
|
141
|
+
|
|
142
|
+
```bash
|
|
143
|
+
python -m pip install torch==2.3.1 --index-url https://download.pytorch.org/whl/cpu
|
|
144
|
+
python -m pip install "flexaligner[inference]==0.1.0a1"
|
|
145
|
+
```
|
|
146
|
+
|
|
147
|
+
To work from a reviewed source checkout:
|
|
148
|
+
|
|
149
|
+
```bash
|
|
150
|
+
git clone https://github.com/USTCPhonetics/FlexAligner.git
|
|
151
|
+
cd FlexAligner
|
|
152
|
+
|
|
153
|
+
python -m pip install -e ".[inference]"
|
|
154
|
+
```
|
|
155
|
+
|
|
156
|
+
The package does not include acoustic models. Prepare compatible local Chunker
|
|
157
|
+
and Aligner model directories and a pronunciation dictionary before alignment.
|
|
158
|
+
|
|
159
|
+
基础包支持 Python 3.10–3.14。首个 alpha 的推理依赖固定为 Torch 2.3.1 和
|
|
160
|
+
Transformers 4.41.2,仅支持在 Python 3.10–3.12 上安装;真实模型发布验证目前仅覆盖
|
|
161
|
+
Linux x86_64 与 Python 3.10.8。Python 3.13–3.14 暂时只承诺基础包和接口可用。
|
|
162
|
+
wheel 不包含声学模型,也不会自动下载模型;运行前必须准备本地 Chunker、Aligner
|
|
163
|
+
模型目录和发音词典。
|
|
164
|
+
|
|
165
|
+
## 💻 Usage
|
|
166
|
+
|
|
167
|
+
### 1. Command Line Interface (CLI)
|
|
168
|
+
|
|
169
|
+
Align one English 16 kHz mono PCM16 WAV file:
|
|
170
|
+
|
|
171
|
+
```bash
|
|
172
|
+
flexaligner align \
|
|
173
|
+
--audio recording.wav \
|
|
174
|
+
--text-file transcript.txt \
|
|
175
|
+
--lexicon english.dict \
|
|
176
|
+
--chunker-model /local/models/en/chunker \
|
|
177
|
+
--aligner-model /local/models/en/aligner \
|
|
178
|
+
--output recording.TextGrid \
|
|
179
|
+
--chunk-metadata recording.alignment.json \
|
|
180
|
+
--num-threads 1
|
|
181
|
+
```
|
|
182
|
+
|
|
183
|
+
Literal transcript text may be passed with `--text` instead of `--text-file`.
|
|
184
|
+
`--num-threads` configures Torch's process-global CPU thread count for the
|
|
185
|
+
inference lifetime; it is not isolated to a single aligner instance.
|
|
186
|
+
Use the capability command to inspect the installed preview:
|
|
187
|
+
|
|
188
|
+
```bash
|
|
189
|
+
flexaligner capabilities
|
|
190
|
+
flexaligner capabilities --json
|
|
191
|
+
```
|
|
192
|
+
|
|
193
|
+
### 2. Python API
|
|
194
|
+
|
|
195
|
+
```python
|
|
196
|
+
from pathlib import Path
|
|
197
|
+
|
|
198
|
+
from flexaligner import (
|
|
199
|
+
AlignmentRequest,
|
|
200
|
+
FlexAligner,
|
|
201
|
+
LocalModelBundle,
|
|
202
|
+
TextGridOutput,
|
|
203
|
+
)
|
|
204
|
+
|
|
205
|
+
models = LocalModelBundle(
|
|
206
|
+
chunker_dir=Path("/local/models/en/chunker"),
|
|
207
|
+
aligner_dir=Path("/local/models/en/aligner"),
|
|
208
|
+
)
|
|
209
|
+
|
|
210
|
+
with FlexAligner(
|
|
211
|
+
models=models,
|
|
212
|
+
lexicon_path=Path("english.dict"),
|
|
213
|
+
) as aligner:
|
|
214
|
+
result = aligner.align(
|
|
215
|
+
AlignmentRequest(
|
|
216
|
+
audio_path=Path("recording.wav"),
|
|
217
|
+
transcript=Path("transcript.txt").read_text(encoding="utf-8"),
|
|
218
|
+
output=TextGridOutput(path=Path("recording.TextGrid")),
|
|
219
|
+
utterance_id="recording",
|
|
220
|
+
)
|
|
221
|
+
)
|
|
222
|
+
|
|
223
|
+
print(result.output_sha256)
|
|
224
|
+
```
|
|
225
|
+
|
|
226
|
+
### Input Requirements / 输入要求
|
|
227
|
+
|
|
228
|
+
* Audio must be uncompressed 16 kHz mono PCM16 WAV.
|
|
229
|
+
* The transcript must be UTF-8 text and fully covered by the pronunciation
|
|
230
|
+
dictionary.
|
|
231
|
+
* Model and dictionary files must be available locally.
|
|
232
|
+
* Output paths use no-clobber semantics: an existing output file is not
|
|
233
|
+
overwritten.
|
|
234
|
+
|
|
235
|
+
* 音频必须是未压缩的 16 kHz、单声道、PCM16 WAV。
|
|
236
|
+
* 文本必须为 UTF-8,且发音词典需要覆盖全部输入词。
|
|
237
|
+
* 模型与词典必须提前保存在本地。
|
|
238
|
+
* 输出采用不覆盖已有文件的策略;若目标文件已存在,程序不会将其覆盖。
|
|
239
|
+
* `--num-threads` 会设置 Torch 的进程全局 CPU 线程数,并非仅对单个 aligner 实例生效。
|
|
240
|
+
|
|
241
|
+
## 🗓️ Roadmap
|
|
242
|
+
|
|
243
|
+
- [x] **Core Alignment Engine:** Two-stage CTC chunking and local alignment.
|
|
244
|
+
- [x] **English CPU Single-File Alignment:** CLI, Python API, and validated
|
|
245
|
+
TextGrid output.
|
|
246
|
+
- [x] **Continuous TextGrid Coverage:** `words` and `phones` tiers use `NULL`
|
|
247
|
+
intervals to cover the complete timeline.
|
|
248
|
+
- [ ] **Mandarin Alignment:** Model, segmentation, and release validation.
|
|
249
|
+
- [ ] **GPU and Batch Processing:** Accelerated and high-throughput workflows.
|
|
250
|
+
- [ ] **Audio Frontend:** Multi-format decoding and automatic resampling.
|
|
251
|
+
- [ ] **Model Distribution:** Documented model acquisition and compatibility
|
|
252
|
+
validation.
|
|
253
|
+
- [ ] **PyPI Release:** Publish the approved public preview as `flexaligner`.
|
|
254
|
+
|
|
255
|
+
## 👨💻 Authors & Affiliation
|
|
256
|
+
|
|
257
|
+
```text
|
|
258
|
+
Yiming Wang (王一鸣) - University of Science and Technology of China (USTC)
|
|
259
|
+
|
|
260
|
+
Jiahong Yuan (袁家宏) - University of Science and Technology of China (USTC)
|
|
261
|
+
```
|
|
262
|
+
|
|
263
|
+
## 📜 Citation
|
|
264
|
+
|
|
265
|
+
If you use FlexAligner in your research, please cite:
|
|
266
|
+
|
|
267
|
+
```bibtex
|
|
268
|
+
@misc{flexaligner2026,
|
|
269
|
+
title = {FlexAligner: Robust Speech--Text Alignment via CTC Chunking and Local Cross-Entropy Alignment},
|
|
270
|
+
author = {Wang, Yiming and Yuan, Jiahong},
|
|
271
|
+
year = {2026},
|
|
272
|
+
publisher = {GitHub},
|
|
273
|
+
journal = {GitHub repository},
|
|
274
|
+
howpublished = {\url{https://github.com/USTCPhonetics/FlexAligner}},
|
|
275
|
+
organization = {University of Science and Technology of China}
|
|
276
|
+
}
|
|
277
|
+
```
|
|
278
|
+
|
|
279
|
+
## 📄 License
|
|
280
|
+
|
|
281
|
+
FlexAligner is released under the [MIT License](LICENSE). Please refer to the
|
|
282
|
+
repository's `LICENSE` file for the authoritative license and copyright notice.
|
|
283
|
+
|
|
284
|
+
<div align="center"><sub>Built by USTCPhonetics.</sub></div>
|
|
@@ -0,0 +1,255 @@
|
|
|
1
|
+
<div align="center">
|
|
2
|
+
|
|
3
|
+
# 🌊 FlexAligner
|
|
4
|
+
|
|
5
|
+
### Robust Speech-Text Alignment from Signal to Symbol
|
|
6
|
+
|
|
7
|
+
[](http://phonetics.ustc.edu.cn/)
|
|
8
|
+
[](https://www.python.org/)
|
|
9
|
+
[](LICENSE)
|
|
10
|
+
[](https://huggingface.co/USTCPhonetics)
|
|
11
|
+
|
|
12
|
+
**A Neural-Based Forced Alignment Framework for "Wild" Real-World Data**
|
|
13
|
+
<br>
|
|
14
|
+
**面向真实非受控数据的深度学习强鲁棒性对齐工具**
|
|
15
|
+
|
|
16
|
+
[**English**](#-introduction) | [**简体中文**](#-简介)
|
|
17
|
+
|
|
18
|
+
</div>
|
|
19
|
+
|
|
20
|
+
---
|
|
21
|
+
|
|
22
|
+
## 📖 Introduction
|
|
23
|
+
|
|
24
|
+
**FlexAligner** is a robust speech-text alignment framework built upon
|
|
25
|
+
**wav2vec 2.0**. It is designed for real-world linguistic data, where audio
|
|
26
|
+
signals and textual transcriptions may contain noise, hesitations, untranscribed
|
|
27
|
+
events, or local mismatches.
|
|
28
|
+
|
|
29
|
+
FlexAligner decomposes forced alignment into two stages:
|
|
30
|
+
|
|
31
|
+
1. **Macro-Segmentation (CTC Chunking):** Uses a CTC acoustic model to locate
|
|
32
|
+
reliable transcript anchors and divide long-form audio into ordered chunks.
|
|
33
|
+
2. **Micro-Alignment (Local Alignment):** Uses a constrained pronunciation
|
|
34
|
+
graph and two-pass Viterbi decoding to estimate word and phone boundaries
|
|
35
|
+
within each chunk.
|
|
36
|
+
|
|
37
|
+
### 🌟 Key Features
|
|
38
|
+
|
|
39
|
+
* **🛡️ Tolerance to Mismatch:** Uncovered portions of the audio timeline are
|
|
40
|
+
represented explicitly as `NULL` intervals instead of being silently forced
|
|
41
|
+
into neighboring words or phones.
|
|
42
|
+
* **🎯 Word and Phone Boundaries:** Produces Praat TextGrid files with continuous
|
|
43
|
+
`words` and `phones` tiers while preserving the input word order.
|
|
44
|
+
* **🔒 Local and Reproducible:** Models and pronunciation dictionaries are
|
|
45
|
+
supplied as explicit local paths; alignment does not automatically download
|
|
46
|
+
models or silently generate OOV pronunciations.
|
|
47
|
+
* **📦 Python Package and CLI:** Provides a typed Python API and a command-line
|
|
48
|
+
interface for single-file alignment.
|
|
49
|
+
|
|
50
|
+
The first public preview focuses on **English, CPU, and single-file alignment**.
|
|
51
|
+
Mandarin, GPU, batch processing, Web services, automatic model download,
|
|
52
|
+
multi-format decoding, resampling, default G2P, and confidence calibration are
|
|
53
|
+
reserved interfaces and are not yet production features.
|
|
54
|
+
|
|
55
|
+
---
|
|
56
|
+
|
|
57
|
+
## 🌏 简介
|
|
58
|
+
|
|
59
|
+
**FlexAligner** 是一个基于 **wav2vec 2.0** 的语音—文本对齐框架,面向真实语言材料中
|
|
60
|
+
常见的噪音、停顿、未转写声音事件以及音频与文本局部不一致等问题。
|
|
61
|
+
|
|
62
|
+
FlexAligner 将强制对齐分为两个阶段:
|
|
63
|
+
|
|
64
|
+
1. **宏观切分(CTC Chunking):** 使用 CTC 声学模型寻找可靠的文本锚点,并将长音频
|
|
65
|
+
划分为顺序一致的局部片段。
|
|
66
|
+
2. **微观对齐(Local Alignment):** 在每个片段内构建受约束的发音图,通过两遍
|
|
67
|
+
Viterbi 解码估计词和音素边界。
|
|
68
|
+
|
|
69
|
+
### 🌟 核心优势
|
|
70
|
+
|
|
71
|
+
* **🛡️ 容错设计:** 对未被词或音素覆盖的时段使用明确的 `NULL` 区间表示,避免将其
|
|
72
|
+
静默挤压到相邻标签中。
|
|
73
|
+
* **🎯 词与音素边界:** 输出 Praat TextGrid,`words` 和 `phones` 两层连续覆盖完整
|
|
74
|
+
音频时间轴,同时保持输入词序。
|
|
75
|
+
* **🔒 本地与可复现:** 模型和发音词典均由用户显式指定;运行时不会自动下载模型,
|
|
76
|
+
也不会对 OOV 词静默生成发音。
|
|
77
|
+
* **📦 Python 包与 CLI:** 提供带类型定义的 Python API 和单文件命令行接口。
|
|
78
|
+
|
|
79
|
+
首个公开预览版聚焦于**英语、CPU、单文件对齐**。普通话、GPU、批处理、Web 服务、
|
|
80
|
+
自动模型下载、多格式解码、自动重采样、默认 G2P 和置信度校准目前仅保留接口,尚未
|
|
81
|
+
作为正式能力开放。
|
|
82
|
+
|
|
83
|
+
---
|
|
84
|
+
|
|
85
|
+
## 🏗️ Architecture
|
|
86
|
+
|
|
87
|
+
```mermaid
|
|
88
|
+
graph TD
|
|
89
|
+
Input[Input: PCM16 WAV + Transcript] --> Lexicon[Local Pronunciation Lexicon];
|
|
90
|
+
Lexicon --> B[Stage 1: CTC Chunking];
|
|
91
|
+
B --> C{Reliable Ordered Chunks};
|
|
92
|
+
C --> D[Stage 2: Pronunciation Graph];
|
|
93
|
+
D --> E[Two-pass Viterbi Decoding];
|
|
94
|
+
E --> F[Words + Phones + NULL TextGrid];
|
|
95
|
+
```
|
|
96
|
+
|
|
97
|
+
## 🚀 Installation
|
|
98
|
+
|
|
99
|
+
The import-safe core package targets Python 3.10–3.14. The frozen inference
|
|
100
|
+
extra pins Torch 2.3.1 and Transformers 4.41.2 and is installable on Python
|
|
101
|
+
3.10–3.12. Real-model release evidence currently covers only Linux x86_64 with
|
|
102
|
+
Python 3.10.8; Python 3.13–3.14 are core-only.
|
|
103
|
+
|
|
104
|
+
After the public alpha is available from PyPI, install the exact preview with:
|
|
105
|
+
|
|
106
|
+
```bash
|
|
107
|
+
python -m pip install "flexaligner[inference]==0.1.0a1"
|
|
108
|
+
```
|
|
109
|
+
|
|
110
|
+
For a CPU-only Linux environment, install the frozen Torch build from its CPU
|
|
111
|
+
index first:
|
|
112
|
+
|
|
113
|
+
```bash
|
|
114
|
+
python -m pip install torch==2.3.1 --index-url https://download.pytorch.org/whl/cpu
|
|
115
|
+
python -m pip install "flexaligner[inference]==0.1.0a1"
|
|
116
|
+
```
|
|
117
|
+
|
|
118
|
+
To work from a reviewed source checkout:
|
|
119
|
+
|
|
120
|
+
```bash
|
|
121
|
+
git clone https://github.com/USTCPhonetics/FlexAligner.git
|
|
122
|
+
cd FlexAligner
|
|
123
|
+
|
|
124
|
+
python -m pip install -e ".[inference]"
|
|
125
|
+
```
|
|
126
|
+
|
|
127
|
+
The package does not include acoustic models. Prepare compatible local Chunker
|
|
128
|
+
and Aligner model directories and a pronunciation dictionary before alignment.
|
|
129
|
+
|
|
130
|
+
基础包支持 Python 3.10–3.14。首个 alpha 的推理依赖固定为 Torch 2.3.1 和
|
|
131
|
+
Transformers 4.41.2,仅支持在 Python 3.10–3.12 上安装;真实模型发布验证目前仅覆盖
|
|
132
|
+
Linux x86_64 与 Python 3.10.8。Python 3.13–3.14 暂时只承诺基础包和接口可用。
|
|
133
|
+
wheel 不包含声学模型,也不会自动下载模型;运行前必须准备本地 Chunker、Aligner
|
|
134
|
+
模型目录和发音词典。
|
|
135
|
+
|
|
136
|
+
## 💻 Usage
|
|
137
|
+
|
|
138
|
+
### 1. Command Line Interface (CLI)
|
|
139
|
+
|
|
140
|
+
Align one English 16 kHz mono PCM16 WAV file:
|
|
141
|
+
|
|
142
|
+
```bash
|
|
143
|
+
flexaligner align \
|
|
144
|
+
--audio recording.wav \
|
|
145
|
+
--text-file transcript.txt \
|
|
146
|
+
--lexicon english.dict \
|
|
147
|
+
--chunker-model /local/models/en/chunker \
|
|
148
|
+
--aligner-model /local/models/en/aligner \
|
|
149
|
+
--output recording.TextGrid \
|
|
150
|
+
--chunk-metadata recording.alignment.json \
|
|
151
|
+
--num-threads 1
|
|
152
|
+
```
|
|
153
|
+
|
|
154
|
+
Literal transcript text may be passed with `--text` instead of `--text-file`.
|
|
155
|
+
`--num-threads` configures Torch's process-global CPU thread count for the
|
|
156
|
+
inference lifetime; it is not isolated to a single aligner instance.
|
|
157
|
+
Use the capability command to inspect the installed preview:
|
|
158
|
+
|
|
159
|
+
```bash
|
|
160
|
+
flexaligner capabilities
|
|
161
|
+
flexaligner capabilities --json
|
|
162
|
+
```
|
|
163
|
+
|
|
164
|
+
### 2. Python API
|
|
165
|
+
|
|
166
|
+
```python
|
|
167
|
+
from pathlib import Path
|
|
168
|
+
|
|
169
|
+
from flexaligner import (
|
|
170
|
+
AlignmentRequest,
|
|
171
|
+
FlexAligner,
|
|
172
|
+
LocalModelBundle,
|
|
173
|
+
TextGridOutput,
|
|
174
|
+
)
|
|
175
|
+
|
|
176
|
+
models = LocalModelBundle(
|
|
177
|
+
chunker_dir=Path("/local/models/en/chunker"),
|
|
178
|
+
aligner_dir=Path("/local/models/en/aligner"),
|
|
179
|
+
)
|
|
180
|
+
|
|
181
|
+
with FlexAligner(
|
|
182
|
+
models=models,
|
|
183
|
+
lexicon_path=Path("english.dict"),
|
|
184
|
+
) as aligner:
|
|
185
|
+
result = aligner.align(
|
|
186
|
+
AlignmentRequest(
|
|
187
|
+
audio_path=Path("recording.wav"),
|
|
188
|
+
transcript=Path("transcript.txt").read_text(encoding="utf-8"),
|
|
189
|
+
output=TextGridOutput(path=Path("recording.TextGrid")),
|
|
190
|
+
utterance_id="recording",
|
|
191
|
+
)
|
|
192
|
+
)
|
|
193
|
+
|
|
194
|
+
print(result.output_sha256)
|
|
195
|
+
```
|
|
196
|
+
|
|
197
|
+
### Input Requirements / 输入要求
|
|
198
|
+
|
|
199
|
+
* Audio must be uncompressed 16 kHz mono PCM16 WAV.
|
|
200
|
+
* The transcript must be UTF-8 text and fully covered by the pronunciation
|
|
201
|
+
dictionary.
|
|
202
|
+
* Model and dictionary files must be available locally.
|
|
203
|
+
* Output paths use no-clobber semantics: an existing output file is not
|
|
204
|
+
overwritten.
|
|
205
|
+
|
|
206
|
+
* 音频必须是未压缩的 16 kHz、单声道、PCM16 WAV。
|
|
207
|
+
* 文本必须为 UTF-8,且发音词典需要覆盖全部输入词。
|
|
208
|
+
* 模型与词典必须提前保存在本地。
|
|
209
|
+
* 输出采用不覆盖已有文件的策略;若目标文件已存在,程序不会将其覆盖。
|
|
210
|
+
* `--num-threads` 会设置 Torch 的进程全局 CPU 线程数,并非仅对单个 aligner 实例生效。
|
|
211
|
+
|
|
212
|
+
## 🗓️ Roadmap
|
|
213
|
+
|
|
214
|
+
- [x] **Core Alignment Engine:** Two-stage CTC chunking and local alignment.
|
|
215
|
+
- [x] **English CPU Single-File Alignment:** CLI, Python API, and validated
|
|
216
|
+
TextGrid output.
|
|
217
|
+
- [x] **Continuous TextGrid Coverage:** `words` and `phones` tiers use `NULL`
|
|
218
|
+
intervals to cover the complete timeline.
|
|
219
|
+
- [ ] **Mandarin Alignment:** Model, segmentation, and release validation.
|
|
220
|
+
- [ ] **GPU and Batch Processing:** Accelerated and high-throughput workflows.
|
|
221
|
+
- [ ] **Audio Frontend:** Multi-format decoding and automatic resampling.
|
|
222
|
+
- [ ] **Model Distribution:** Documented model acquisition and compatibility
|
|
223
|
+
validation.
|
|
224
|
+
- [ ] **PyPI Release:** Publish the approved public preview as `flexaligner`.
|
|
225
|
+
|
|
226
|
+
## 👨💻 Authors & Affiliation
|
|
227
|
+
|
|
228
|
+
```text
|
|
229
|
+
Yiming Wang (王一鸣) - University of Science and Technology of China (USTC)
|
|
230
|
+
|
|
231
|
+
Jiahong Yuan (袁家宏) - University of Science and Technology of China (USTC)
|
|
232
|
+
```
|
|
233
|
+
|
|
234
|
+
## 📜 Citation
|
|
235
|
+
|
|
236
|
+
If you use FlexAligner in your research, please cite:
|
|
237
|
+
|
|
238
|
+
```bibtex
|
|
239
|
+
@misc{flexaligner2026,
|
|
240
|
+
title = {FlexAligner: Robust Speech--Text Alignment via CTC Chunking and Local Cross-Entropy Alignment},
|
|
241
|
+
author = {Wang, Yiming and Yuan, Jiahong},
|
|
242
|
+
year = {2026},
|
|
243
|
+
publisher = {GitHub},
|
|
244
|
+
journal = {GitHub repository},
|
|
245
|
+
howpublished = {\url{https://github.com/USTCPhonetics/FlexAligner}},
|
|
246
|
+
organization = {University of Science and Technology of China}
|
|
247
|
+
}
|
|
248
|
+
```
|
|
249
|
+
|
|
250
|
+
## 📄 License
|
|
251
|
+
|
|
252
|
+
FlexAligner is released under the [MIT License](LICENSE). Please refer to the
|
|
253
|
+
repository's `LICENSE` file for the authoritative license and copyright notice.
|
|
254
|
+
|
|
255
|
+
<div align="center"><sub>Built by USTCPhonetics.</sub></div>
|