audiobookifier 2.6.0__py3-none-any.whl
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.
- audiobookifier-2.6.0.dist-info/METADATA +561 -0
- audiobookifier-2.6.0.dist-info/RECORD +49 -0
- audiobookifier-2.6.0.dist-info/WHEEL +5 -0
- audiobookifier-2.6.0.dist-info/entry_points.txt +5 -0
- audiobookifier-2.6.0.dist-info/licenses/LICENSE +674 -0
- audiobookifier-2.6.0.dist-info/top_level.txt +1 -0
- epub2tts_edge/__init__.py +270 -0
- epub2tts_edge/audio_generator.py +767 -0
- epub2tts_edge/audio_normalization.py +244 -0
- epub2tts_edge/batch_processor.py +811 -0
- epub2tts_edge/chapter_detector.py +1384 -0
- epub2tts_edge/chapter_selector.py +215 -0
- epub2tts_edge/config.py +249 -0
- epub2tts_edge/content_filter.py +469 -0
- epub2tts_edge/core/__init__.py +39 -0
- epub2tts_edge/core/events.py +231 -0
- epub2tts_edge/core/output_naming.py +242 -0
- epub2tts_edge/core/pipeline.py +627 -0
- epub2tts_edge/core/profiles.py +179 -0
- epub2tts_edge/epub2tts_edge.py +1305 -0
- epub2tts_edge/errors.py +212 -0
- epub2tts_edge/job_manager.py +556 -0
- epub2tts_edge/logger.py +97 -0
- epub2tts_edge/mobi_parser.py +466 -0
- epub2tts_edge/multi_voice.py +315 -0
- epub2tts_edge/pause_resume.py +262 -0
- epub2tts_edge/pronunciation.py +208 -0
- epub2tts_edge/silence_detection.py +235 -0
- epub2tts_edge/testing/__init__.py +11 -0
- epub2tts_edge/testing/mock_tts.py +243 -0
- epub2tts_edge/tui/__init__.py +64 -0
- epub2tts_edge/tui/app.py +2055 -0
- epub2tts_edge/tui/handlers/__init__.py +9 -0
- epub2tts_edge/tui/handlers/event_adapter.py +281 -0
- epub2tts_edge/tui/models/__init__.py +6 -0
- epub2tts_edge/tui/models/preview_state.py +138 -0
- epub2tts_edge/tui/models/voice_status.py +69 -0
- epub2tts_edge/tui/panels/__init__.py +23 -0
- epub2tts_edge/tui/panels/file_panel.py +419 -0
- epub2tts_edge/tui/panels/jobs_panel.py +325 -0
- epub2tts_edge/tui/panels/log_panel.py +46 -0
- epub2tts_edge/tui/panels/preview_panel.py +894 -0
- epub2tts_edge/tui/panels/progress_panel.py +114 -0
- epub2tts_edge/tui/panels/queue_panel.py +89 -0
- epub2tts_edge/tui/panels/settings_panel.py +464 -0
- epub2tts_edge/tui/screens/__init__.py +6 -0
- epub2tts_edge/tui/screens/directory_browser.py +109 -0
- epub2tts_edge/tui/screens/help_screen.py +104 -0
- epub2tts_edge/voice_preview.py +655 -0
|
@@ -0,0 +1,561 @@
|
|
|
1
|
+
Metadata-Version: 2.4
|
|
2
|
+
Name: audiobookifier
|
|
3
|
+
Version: 2.6.0
|
|
4
|
+
Summary: Convert EPUB and MOBI/AZW files to M4B audiobooks using Microsoft Edge TTS
|
|
5
|
+
Author-email: Christopher Aedo <c@aedo.dev>
|
|
6
|
+
Maintainer-email: loganrooks <loganrooks@users.noreply.github.com>
|
|
7
|
+
License: GPL-3.0
|
|
8
|
+
Project-URL: Homepage, https://github.com/loganrooks/audiobookify
|
|
9
|
+
Project-URL: Documentation, https://github.com/loganrooks/audiobookify#readme
|
|
10
|
+
Project-URL: Repository, https://github.com/loganrooks/audiobookify.git
|
|
11
|
+
Project-URL: Issues, https://github.com/loganrooks/audiobookify/issues
|
|
12
|
+
Project-URL: Changelog, https://github.com/loganrooks/audiobookify/blob/main/CHANGELOG.md
|
|
13
|
+
Keywords: audiobook,epub,mobi,kindle,tts,text-to-speech,edge-tts,m4b,ebook,converter
|
|
14
|
+
Classifier: Development Status :: 4 - Beta
|
|
15
|
+
Classifier: Environment :: Console
|
|
16
|
+
Classifier: Intended Audience :: End Users/Desktop
|
|
17
|
+
Classifier: License :: OSI Approved :: GNU General Public License v3 (GPLv3)
|
|
18
|
+
Classifier: Operating System :: OS Independent
|
|
19
|
+
Classifier: Programming Language :: Python :: 3
|
|
20
|
+
Classifier: Programming Language :: Python :: 3.11
|
|
21
|
+
Classifier: Programming Language :: Python :: 3.12
|
|
22
|
+
Classifier: Programming Language :: Python :: 3.13
|
|
23
|
+
Classifier: Programming Language :: Python :: 3.14
|
|
24
|
+
Classifier: Topic :: Multimedia :: Sound/Audio :: Speech
|
|
25
|
+
Classifier: Topic :: Text Processing :: General
|
|
26
|
+
Requires-Python: >=3.11
|
|
27
|
+
Description-Content-Type: text/markdown
|
|
28
|
+
License-File: LICENSE
|
|
29
|
+
Requires-Dist: beautifulsoup4>=4.12.0
|
|
30
|
+
Requires-Dist: ebooklib>=0.18
|
|
31
|
+
Requires-Dist: edge-tts<8,>=7.2.4
|
|
32
|
+
Requires-Dist: lxml>=4.9.0
|
|
33
|
+
Requires-Dist: mobi>=0.3.0
|
|
34
|
+
Requires-Dist: mutagen>=1.46.0
|
|
35
|
+
Requires-Dist: nltk>=3.8.0
|
|
36
|
+
Requires-Dist: pillow>=10.0.0
|
|
37
|
+
Requires-Dist: pydub>=0.25.0
|
|
38
|
+
Requires-Dist: setuptools>=61.0
|
|
39
|
+
Requires-Dist: textual>=0.40.0
|
|
40
|
+
Requires-Dist: tqdm>=4.65.0
|
|
41
|
+
Requires-Dist: audioop-lts; python_version >= "3.13"
|
|
42
|
+
Provides-Extra: dev
|
|
43
|
+
Requires-Dist: pytest>=7.4.0; extra == "dev"
|
|
44
|
+
Requires-Dist: pytest-cov>=4.1.0; extra == "dev"
|
|
45
|
+
Requires-Dist: pytest-asyncio>=0.21.0; extra == "dev"
|
|
46
|
+
Requires-Dist: mypy>=1.5.0; extra == "dev"
|
|
47
|
+
Requires-Dist: ruff<0.17.0,>=0.16.0; extra == "dev"
|
|
48
|
+
Requires-Dist: pre-commit>=3.6.0; extra == "dev"
|
|
49
|
+
Requires-Dist: bandit[toml]<2.0,>=1.9.4; extra == "dev"
|
|
50
|
+
Requires-Dist: build>=1.0.0; extra == "dev"
|
|
51
|
+
Requires-Dist: twine>=5.0.0; extra == "dev"
|
|
52
|
+
Provides-Extra: tui
|
|
53
|
+
Requires-Dist: textual>=0.40.0; extra == "tui"
|
|
54
|
+
Provides-Extra: all
|
|
55
|
+
Requires-Dist: audiobookifier[dev,tui]; extra == "all"
|
|
56
|
+
Dynamic: license-file
|
|
57
|
+
|
|
58
|
+
# Audiobookify
|
|
59
|
+
|
|
60
|
+
[](https://github.com/loganrooks/audiobookify/actions/workflows/ci.yml)
|
|
61
|
+
[](https://pypi.org/project/audiobookifier/)
|
|
62
|
+
[](https://pypi.org/project/audiobookifier/)
|
|
63
|
+
[](./LICENSE)
|
|
64
|
+
|
|
65
|
+
> Convert EPUB and MOBI/AZW files to high-quality M4B audiobooks using Microsoft Edge's cloud-based text-to-speech.
|
|
66
|
+
|
|
67
|
+
Forked from [epub2tts-edge](https://github.com/aedocw/epub2tts-edge) with enhanced chapter detection, batch processing, and a terminal UI.
|
|
68
|
+
|
|
69
|
+
> **Requires an internet connection.** Edge TTS is a cloud service: the text of
|
|
70
|
+
> every book you convert is sent to Microsoft's speech endpoint. There is no
|
|
71
|
+
> offline mode yet — see [ROADMAP.md](./ROADMAP.md).
|
|
72
|
+
|
|
73
|
+
## Features
|
|
74
|
+
|
|
75
|
+
- **Multi-Format Support** - EPUB, MOBI, AZW, and AZW3 files
|
|
76
|
+
- **Enhanced Chapter Detection** - Parses Table of Contents (EPUB2/EPUB3) and HTML headings
|
|
77
|
+
- **Batch Processing** - Convert entire folders of ebooks at once
|
|
78
|
+
- **Terminal UI** - Interactive interface for easy conversion
|
|
79
|
+
- **Smart Resume** - Picks up where it left off if interrupted
|
|
80
|
+
- **Chapter Markers** - Proper M4B chapter navigation
|
|
81
|
+
- **Cover Art** - Automatically embeds cover images
|
|
82
|
+
- **Fast** - Parallel sentence processing for quick conversion
|
|
83
|
+
|
|
84
|
+
### New in v2.3.0
|
|
85
|
+
- **MOBI/AZW Support** - Parse Kindle format ebooks (MOBI, AZW, AZW3)
|
|
86
|
+
- **Docker Support** - Containerized deployment with docker-compose
|
|
87
|
+
- **Calibre Plugin** - Convert books directly from Calibre library
|
|
88
|
+
|
|
89
|
+
### New in v2.2.0
|
|
90
|
+
- **Audio Normalization** - Consistent volume across chapters (`--normalize`)
|
|
91
|
+
- **Silence Trimming** - Remove excessive pauses (`--trim-silence`)
|
|
92
|
+
- **Custom Pronunciation** - Dictionary for proper nouns (`--pronunciation`)
|
|
93
|
+
- **Multiple Voices** - Different voices for characters (`--voice-mapping`)
|
|
94
|
+
|
|
95
|
+
### New in v2.1.0
|
|
96
|
+
- **Voice Preview** - Listen to voices before converting (`--preview-voice`)
|
|
97
|
+
- **Speed/Volume Control** - Adjust speech rate and volume (`--rate`, `--volume`)
|
|
98
|
+
- **Chapter Selection** - Convert only specific chapters (`--chapters "1-5"`)
|
|
99
|
+
- **Pause/Resume** - Continue interrupted conversions (`--resume`)
|
|
100
|
+
|
|
101
|
+
> **Note:** EPUB and MOBI/AZW files must be DRM-free
|
|
102
|
+
|
|
103
|
+
## Quick Start
|
|
104
|
+
|
|
105
|
+
```bash
|
|
106
|
+
# Install (use pipx for isolated environment)
|
|
107
|
+
pipx install audiobookifier
|
|
108
|
+
# Or: pip install audiobookifier
|
|
109
|
+
|
|
110
|
+
# Convert a single EPUB
|
|
111
|
+
audiobookify mybook.epub # Export to text
|
|
112
|
+
audiobookify mybook.txt # Convert to audiobook
|
|
113
|
+
|
|
114
|
+
# Convert a MOBI/AZW file
|
|
115
|
+
audiobookify mybook.mobi # Export to text
|
|
116
|
+
audiobookify mybook.azw3 # Export to text
|
|
117
|
+
|
|
118
|
+
# Or use the short alias
|
|
119
|
+
abfy mybook.epub
|
|
120
|
+
|
|
121
|
+
# Batch convert a folder
|
|
122
|
+
audiobookify /path/to/books --batch
|
|
123
|
+
|
|
124
|
+
# Launch interactive TUI
|
|
125
|
+
audiobookify --tui
|
|
126
|
+
```
|
|
127
|
+
|
|
128
|
+
### Docker
|
|
129
|
+
|
|
130
|
+
The image runs as a non-root user (uid 1000). A bind-mounted directory keeps its
|
|
131
|
+
**host** ownership, so pass `--user "$(id -u):$(id -g)"` unless your host uid
|
|
132
|
+
already happens to be 1000 — otherwise the container cannot write the finished
|
|
133
|
+
audiobook back into the mount, and you get a "Could not move audiobook" warning
|
|
134
|
+
with the output stranded inside the container.
|
|
135
|
+
|
|
136
|
+
```bash
|
|
137
|
+
# Build the image
|
|
138
|
+
docker build -t audiobookify .
|
|
139
|
+
|
|
140
|
+
# Export EPUB to text
|
|
141
|
+
docker run --rm --user "$(id -u):$(id -g)" -e HOME=/tmp \
|
|
142
|
+
-v $(pwd)/books:/books audiobookify /books/mybook.epub
|
|
143
|
+
|
|
144
|
+
# Convert to audiobook
|
|
145
|
+
docker run --rm --user "$(id -u):$(id -g)" -e HOME=/tmp \
|
|
146
|
+
-v $(pwd)/books:/books audiobookify /books/mybook.txt
|
|
147
|
+
|
|
148
|
+
# Batch processing
|
|
149
|
+
docker run --rm --user "$(id -u):$(id -g)" -e HOME=/tmp \
|
|
150
|
+
-v $(pwd)/books:/books audiobookify /books --batch
|
|
151
|
+
|
|
152
|
+
# Using docker-compose
|
|
153
|
+
docker-compose build
|
|
154
|
+
docker-compose run audiobookify /books/mybook.epub
|
|
155
|
+
```
|
|
156
|
+
|
|
157
|
+
`-e HOME=/tmp` is needed alongside `--user` because the overridden uid has no
|
|
158
|
+
home directory in the image, and the job scratch directory lives under `$HOME`.
|
|
159
|
+
Output is written next to the source file, so it lands in your mounted folder.
|
|
160
|
+
|
|
161
|
+
### Calibre Plugin
|
|
162
|
+
|
|
163
|
+
Convert books directly from your Calibre library:
|
|
164
|
+
|
|
165
|
+
```bash
|
|
166
|
+
# Build the plugin
|
|
167
|
+
cd calibre_plugin
|
|
168
|
+
./build_plugin.sh
|
|
169
|
+
|
|
170
|
+
# Install in Calibre:
|
|
171
|
+
# 1. Preferences → Plugins → Load plugin from file
|
|
172
|
+
# 2. Select audiobookify-calibre.zip
|
|
173
|
+
# 3. Restart Calibre
|
|
174
|
+
```
|
|
175
|
+
|
|
176
|
+
See [calibre_plugin/README.md](calibre_plugin/README.md) for detailed instructions.
|
|
177
|
+
|
|
178
|
+
## Usage
|
|
179
|
+
|
|
180
|
+
### Single File Conversion
|
|
181
|
+
|
|
182
|
+
```bash
|
|
183
|
+
# Step 1: Export EPUB to text (review/edit chapters)
|
|
184
|
+
audiobookify mybook.epub
|
|
185
|
+
|
|
186
|
+
# Step 2: Convert text to audiobook
|
|
187
|
+
audiobookify mybook.txt --cover mybook.png
|
|
188
|
+
```
|
|
189
|
+
|
|
190
|
+
### Batch Processing
|
|
191
|
+
|
|
192
|
+
```bash
|
|
193
|
+
# Process all EPUBs in a folder
|
|
194
|
+
audiobookify /path/to/books --batch
|
|
195
|
+
|
|
196
|
+
# Recursive (include subfolders)
|
|
197
|
+
audiobookify /path/to/library --batch --recursive
|
|
198
|
+
|
|
199
|
+
# Export only (no audio conversion)
|
|
200
|
+
audiobookify /path/to/books --batch --export-only
|
|
201
|
+
|
|
202
|
+
# Custom output directory
|
|
203
|
+
audiobookify /path/to/books --batch -o /path/to/audiobooks
|
|
204
|
+
```
|
|
205
|
+
|
|
206
|
+
### Terminal UI
|
|
207
|
+
|
|
208
|
+
```bash
|
|
209
|
+
# Launch TUI
|
|
210
|
+
audiobookify /path/to/books --tui
|
|
211
|
+
|
|
212
|
+
# Or use dedicated command
|
|
213
|
+
audiobookify-tui /path/to/books
|
|
214
|
+
|
|
215
|
+
# Short alias
|
|
216
|
+
abfy-tui
|
|
217
|
+
```
|
|
218
|
+
|
|
219
|
+
**Keyboard Shortcuts:**
|
|
220
|
+
| Key | Action |
|
|
221
|
+
|-----|--------|
|
|
222
|
+
| `s` | Start processing |
|
|
223
|
+
| `Esc` | Stop |
|
|
224
|
+
| `r` | Refresh files |
|
|
225
|
+
| `a` | Select all |
|
|
226
|
+
| `d` | Deselect all |
|
|
227
|
+
| `p` | Preview voice |
|
|
228
|
+
| `q` | Quit |
|
|
229
|
+
|
|
230
|
+
### Voice Preview & Adjustment (v2.1.0)
|
|
231
|
+
|
|
232
|
+
```bash
|
|
233
|
+
# List available voices
|
|
234
|
+
audiobookify --list-voices
|
|
235
|
+
|
|
236
|
+
# Preview a voice before converting
|
|
237
|
+
audiobookify --preview-voice # Preview default voice
|
|
238
|
+
audiobookify --preview-voice --speaker en-US-JennyNeural # Preview specific voice
|
|
239
|
+
|
|
240
|
+
# Adjust speech rate
|
|
241
|
+
audiobookify mybook.txt --rate "+20%" # 20% faster
|
|
242
|
+
audiobookify mybook.txt --rate "-10%" # 10% slower
|
|
243
|
+
|
|
244
|
+
# Adjust volume
|
|
245
|
+
audiobookify mybook.txt --volume "+50%" # Louder
|
|
246
|
+
audiobookify mybook.txt --volume "-25%" # Quieter
|
|
247
|
+
|
|
248
|
+
# Combine adjustments
|
|
249
|
+
audiobookify mybook.txt --rate "+20%" --volume "-10%"
|
|
250
|
+
```
|
|
251
|
+
|
|
252
|
+
### Chapter Selection (v2.1.0)
|
|
253
|
+
|
|
254
|
+
```bash
|
|
255
|
+
# Convert specific chapters only
|
|
256
|
+
audiobookify mybook.txt --chapters "1-5" # Chapters 1 through 5
|
|
257
|
+
audiobookify mybook.txt --chapters "1,3,7" # Chapters 1, 3, and 7
|
|
258
|
+
audiobookify mybook.txt --chapters "5-" # Chapter 5 to end
|
|
259
|
+
audiobookify mybook.txt --chapters "1,3,5-7" # Mix of single and ranges
|
|
260
|
+
```
|
|
261
|
+
|
|
262
|
+
### Pause/Resume (v2.1.0)
|
|
263
|
+
|
|
264
|
+
```bash
|
|
265
|
+
# Resume an interrupted conversion
|
|
266
|
+
audiobookify mybook.txt --resume
|
|
267
|
+
|
|
268
|
+
# Start fresh (ignore saved progress)
|
|
269
|
+
audiobookify mybook.txt --no-resume
|
|
270
|
+
```
|
|
271
|
+
|
|
272
|
+
Conversions automatically save progress and can be resumed after Ctrl+C interruption.
|
|
273
|
+
|
|
274
|
+
### Audio Normalization (v2.2.0)
|
|
275
|
+
|
|
276
|
+
```bash
|
|
277
|
+
# Normalize volume across chapters
|
|
278
|
+
audiobookify mybook.txt --normalize
|
|
279
|
+
|
|
280
|
+
# Custom target loudness (default: -16 dBFS)
|
|
281
|
+
audiobookify mybook.txt --normalize --normalize-target -14.0
|
|
282
|
+
|
|
283
|
+
# Use RMS method instead of peak
|
|
284
|
+
audiobookify mybook.txt --normalize --normalize-method rms
|
|
285
|
+
```
|
|
286
|
+
|
|
287
|
+
### Silence Trimming (v2.2.0)
|
|
288
|
+
|
|
289
|
+
```bash
|
|
290
|
+
# Trim excessive silence
|
|
291
|
+
audiobookify mybook.txt --trim-silence
|
|
292
|
+
|
|
293
|
+
# Custom silence threshold (default: -40 dBFS)
|
|
294
|
+
audiobookify mybook.txt --trim-silence --silence-thresh -50
|
|
295
|
+
|
|
296
|
+
# Maximum silence duration (default: 2000ms)
|
|
297
|
+
audiobookify mybook.txt --trim-silence --max-silence 1500
|
|
298
|
+
```
|
|
299
|
+
|
|
300
|
+
### Custom Pronunciation (v2.2.0)
|
|
301
|
+
|
|
302
|
+
Create a pronunciation dictionary file:
|
|
303
|
+
|
|
304
|
+
**JSON format (`pronunciation.json`):**
|
|
305
|
+
```json
|
|
306
|
+
{
|
|
307
|
+
"Hermione": "Her-my-oh-nee",
|
|
308
|
+
"Voldemort": "Vol-de-mor",
|
|
309
|
+
"Nguyen": "Win"
|
|
310
|
+
}
|
|
311
|
+
```
|
|
312
|
+
|
|
313
|
+
**Text format (`pronunciation.txt`):**
|
|
314
|
+
```
|
|
315
|
+
# Comments start with #
|
|
316
|
+
Hermione = Her-my-oh-nee
|
|
317
|
+
Voldemort = Vol-de-mor
|
|
318
|
+
```
|
|
319
|
+
|
|
320
|
+
```bash
|
|
321
|
+
# Use pronunciation dictionary
|
|
322
|
+
audiobookify mybook.txt --pronunciation pronunciation.json
|
|
323
|
+
|
|
324
|
+
# Case-sensitive matching
|
|
325
|
+
audiobookify mybook.txt --pronunciation pronunciation.txt --pronunciation-case-sensitive
|
|
326
|
+
```
|
|
327
|
+
|
|
328
|
+
### Multiple Voices (v2.2.0)
|
|
329
|
+
|
|
330
|
+
Create a voice mapping file (`voices.json`):
|
|
331
|
+
```json
|
|
332
|
+
{
|
|
333
|
+
"default_voice": "en-US-AndrewNeural",
|
|
334
|
+
"narrator_voice": "en-US-GuyNeural",
|
|
335
|
+
"character_voices": {
|
|
336
|
+
"Harry": "en-GB-RyanNeural",
|
|
337
|
+
"Hermione": "en-GB-SoniaNeural",
|
|
338
|
+
"Dumbledore": "en-GB-ThomasNeural"
|
|
339
|
+
}
|
|
340
|
+
}
|
|
341
|
+
```
|
|
342
|
+
|
|
343
|
+
```bash
|
|
344
|
+
# Use voice mapping for multi-voice narration
|
|
345
|
+
audiobookify mybook.txt --voice-mapping voices.json
|
|
346
|
+
|
|
347
|
+
# Just set a different narrator voice (non-dialogue)
|
|
348
|
+
audiobookify mybook.txt --narrator-voice en-US-GuyNeural
|
|
349
|
+
```
|
|
350
|
+
|
|
351
|
+
The multi-voice processor automatically detects dialogue (quoted text) and attributes speakers.
|
|
352
|
+
|
|
353
|
+
> **Tip:** See the `examples/` folder for sample pronunciation and voice mapping files you can use as templates.
|
|
354
|
+
|
|
355
|
+
### Chapter Detection Options
|
|
356
|
+
|
|
357
|
+
```bash
|
|
358
|
+
# Detection method
|
|
359
|
+
audiobookify mybook.epub --detect toc # Table of Contents only
|
|
360
|
+
audiobookify mybook.epub --detect headings # HTML headings only
|
|
361
|
+
audiobookify mybook.epub --detect combined # Both (default)
|
|
362
|
+
audiobookify mybook.epub --detect auto # Auto-select best
|
|
363
|
+
|
|
364
|
+
# Hierarchy display style
|
|
365
|
+
audiobookify mybook.epub --hierarchy flat # Chapter 1
|
|
366
|
+
audiobookify mybook.epub --hierarchy numbered # 1.1 Chapter 1
|
|
367
|
+
audiobookify mybook.epub --hierarchy arrow # Part 1 > Chapter 1
|
|
368
|
+
audiobookify mybook.epub --hierarchy breadcrumb # Part 1 / Chapter 1
|
|
369
|
+
|
|
370
|
+
# Preview chapters without converting
|
|
371
|
+
audiobookify mybook.epub --preview
|
|
372
|
+
|
|
373
|
+
# Limit chapter depth
|
|
374
|
+
audiobookify mybook.epub --max-depth 2
|
|
375
|
+
```
|
|
376
|
+
|
|
377
|
+
### All Options
|
|
378
|
+
|
|
379
|
+
| Option | Description |
|
|
380
|
+
|--------|-------------|
|
|
381
|
+
| `--speaker VOICE` | TTS voice (default: en-US-AndrewNeural) |
|
|
382
|
+
| `--cover IMAGE` | Cover image (jpg/png) |
|
|
383
|
+
| `--detect METHOD` | Detection: toc, headings, combined, auto |
|
|
384
|
+
| `--hierarchy STYLE` | Display: flat, numbered, arrow, breadcrumb, indented |
|
|
385
|
+
| `--max-depth N` | Maximum chapter depth |
|
|
386
|
+
| `--preview` | Preview chapters only |
|
|
387
|
+
| `--legacy` | Use original detection algorithm |
|
|
388
|
+
| `--batch` | Batch processing mode |
|
|
389
|
+
| `--recursive` | Scan subfolders |
|
|
390
|
+
| `--output-dir DIR` | Output directory |
|
|
391
|
+
| `--export-only` | Export to text only |
|
|
392
|
+
| `--no-skip` | Don't skip already processed |
|
|
393
|
+
| `--tui` | Launch terminal UI |
|
|
394
|
+
| `--paragraphpause MS` | Pause between paragraphs (default: 1200) |
|
|
395
|
+
| `--sentencepause MS` | Pause between sentences (default: 1200) |
|
|
396
|
+
| **v2.1.0 Options** | |
|
|
397
|
+
| `--list-voices` | List available voices |
|
|
398
|
+
| `--preview-voice` | Preview the selected voice |
|
|
399
|
+
| `--rate RATE` | Speech rate (e.g., "+20%", "-10%") |
|
|
400
|
+
| `--volume VOL` | Volume adjustment (e.g., "+50%", "-25%") |
|
|
401
|
+
| `--chapters RANGE` | Select chapters (e.g., "1-5", "1,3,7") |
|
|
402
|
+
| `--resume` | Resume interrupted conversion |
|
|
403
|
+
| `--no-resume` | Start fresh, ignore saved progress |
|
|
404
|
+
| **v2.2.0 Options** | |
|
|
405
|
+
| `--normalize` | Normalize audio volume across chapters |
|
|
406
|
+
| `--normalize-target DBFS` | Target loudness (default: -16.0 dBFS) |
|
|
407
|
+
| `--normalize-method METHOD` | Normalization method: peak or rms |
|
|
408
|
+
| `--trim-silence` | Trim excessive silence from audio |
|
|
409
|
+
| `--silence-thresh DBFS` | Silence threshold (default: -40 dBFS) |
|
|
410
|
+
| `--max-silence MS` | Max silence duration before trimming (default: 2000) |
|
|
411
|
+
| `--pronunciation FILE` | Path to pronunciation dictionary |
|
|
412
|
+
| `--pronunciation-case-sensitive` | Case-sensitive pronunciation matching |
|
|
413
|
+
| `--voice-mapping FILE` | Path to voice mapping JSON file |
|
|
414
|
+
| `--narrator-voice VOICE` | Voice for narration (non-dialogue) |
|
|
415
|
+
|
|
416
|
+
List available voices: `audiobookify --list-voices` or `edge-tts --list-voices`
|
|
417
|
+
|
|
418
|
+
## Installation
|
|
419
|
+
|
|
420
|
+
**Requirements:** Python 3.11+, FFmpeg, espeak-ng
|
|
421
|
+
|
|
422
|
+
### Quick Install (PyPI)
|
|
423
|
+
|
|
424
|
+
```bash
|
|
425
|
+
# Recommended: use pipx for isolated CLI installation
|
|
426
|
+
pipx install audiobookifier
|
|
427
|
+
|
|
428
|
+
# Or with pip in a virtual environment
|
|
429
|
+
pip install audiobookifier
|
|
430
|
+
```
|
|
431
|
+
|
|
432
|
+
### Platform-Specific Setup
|
|
433
|
+
|
|
434
|
+
<details>
|
|
435
|
+
<summary><b>Linux</b></summary>
|
|
436
|
+
|
|
437
|
+
```bash
|
|
438
|
+
# Install system dependencies
|
|
439
|
+
sudo apt install espeak-ng ffmpeg python3-venv pipx
|
|
440
|
+
|
|
441
|
+
# Option 1: pipx (recommended for CLI tools)
|
|
442
|
+
pipx install audiobookifier
|
|
443
|
+
|
|
444
|
+
# Option 2: Virtual environment
|
|
445
|
+
git clone https://github.com/loganrooks/audiobookify
|
|
446
|
+
cd audiobookify
|
|
447
|
+
python3 -m venv .venv
|
|
448
|
+
source .venv/bin/activate
|
|
449
|
+
pip install -e .
|
|
450
|
+
```
|
|
451
|
+
</details>
|
|
452
|
+
|
|
453
|
+
<details>
|
|
454
|
+
<summary><b>macOS</b></summary>
|
|
455
|
+
|
|
456
|
+
```bash
|
|
457
|
+
# Install system dependencies
|
|
458
|
+
brew install espeak ffmpeg pipx
|
|
459
|
+
|
|
460
|
+
# Option 1: pipx (recommended for CLI tools)
|
|
461
|
+
pipx install audiobookifier
|
|
462
|
+
|
|
463
|
+
# Option 2: Virtual environment
|
|
464
|
+
git clone https://github.com/loganrooks/audiobookify
|
|
465
|
+
cd audiobookify
|
|
466
|
+
python3 -m venv .venv
|
|
467
|
+
source .venv/bin/activate
|
|
468
|
+
pip install -e .
|
|
469
|
+
```
|
|
470
|
+
</details>
|
|
471
|
+
|
|
472
|
+
<details>
|
|
473
|
+
<summary><b>Windows</b></summary>
|
|
474
|
+
|
|
475
|
+
1. Install [Python 3.11+](https://www.python.org/downloads/)
|
|
476
|
+
2. Install [espeak-ng](https://github.com/espeak-ng/espeak-ng/releases) (x64 msi)
|
|
477
|
+
3. Install [FFmpeg](https://github.com/BtbN/FFmpeg-Builds/releases) and add to PATH
|
|
478
|
+
|
|
479
|
+
```powershell
|
|
480
|
+
# Option 1: pipx (recommended)
|
|
481
|
+
pip install pipx
|
|
482
|
+
pipx install audiobookifier
|
|
483
|
+
|
|
484
|
+
# Option 2: Virtual environment
|
|
485
|
+
git clone https://github.com/loganrooks/audiobookify
|
|
486
|
+
cd audiobookify
|
|
487
|
+
py -m venv .venv
|
|
488
|
+
.venv\Scripts\activate
|
|
489
|
+
pip install -e .
|
|
490
|
+
```
|
|
491
|
+
</details>
|
|
492
|
+
|
|
493
|
+
<details>
|
|
494
|
+
<summary><b>Docker</b></summary>
|
|
495
|
+
|
|
496
|
+
The image runs as uid 1000; pass `--user` so it can write into your bind mount
|
|
497
|
+
(see [Docker](#docker) above).
|
|
498
|
+
|
|
499
|
+
```bash
|
|
500
|
+
docker build . -t audiobookify
|
|
501
|
+
|
|
502
|
+
# Export EPUB
|
|
503
|
+
docker run --rm --user "$(id -u):$(id -g)" -e HOME=/tmp \
|
|
504
|
+
-v ~/Books:/files audiobookify "/files/mybook.epub"
|
|
505
|
+
|
|
506
|
+
# Convert to audiobook
|
|
507
|
+
docker run --rm --user "$(id -u):$(id -g)" -e HOME=/tmp \
|
|
508
|
+
-v ~/Books:/files audiobookify "/files/mybook.txt"
|
|
509
|
+
```
|
|
510
|
+
</details>
|
|
511
|
+
|
|
512
|
+
### Development Install
|
|
513
|
+
|
|
514
|
+
```bash
|
|
515
|
+
git clone https://github.com/loganrooks/audiobookify
|
|
516
|
+
cd audiobookify
|
|
517
|
+
./scripts/setup-dev.sh # system deps, venv, dev extras, NLTK data, pre-commit
|
|
518
|
+
./scripts/doctor.sh # report what your environment can verify
|
|
519
|
+
```
|
|
520
|
+
|
|
521
|
+
### Running Tests
|
|
522
|
+
|
|
523
|
+
```bash
|
|
524
|
+
# Run all tests (no network calls; TTS is mocked)
|
|
525
|
+
python -m pytest tests/
|
|
526
|
+
|
|
527
|
+
# Run with coverage
|
|
528
|
+
python -m pytest tests/ --cov=epub2tts_edge --cov-report=html
|
|
529
|
+
```
|
|
530
|
+
|
|
531
|
+
Tests requiring `ffmpeg` skip automatically if it isn't installed. The live
|
|
532
|
+
Edge TTS connectivity tests in `tests/test_tts_connectivity.py` do make real
|
|
533
|
+
network calls — set `SKIP_TTS_TESTS=1` to skip them (CI does this, and runs
|
|
534
|
+
them separately on a schedule).
|
|
535
|
+
|
|
536
|
+
## Documentation
|
|
537
|
+
|
|
538
|
+
**For users**
|
|
539
|
+
- [CHANGELOG.md](./CHANGELOG.md) - What changed in each release
|
|
540
|
+
- [ROADMAP.md](./ROADMAP.md) - Planned features and known limitations
|
|
541
|
+
- [SECURITY.md](./SECURITY.md) - Reporting vulnerabilities, privacy notes
|
|
542
|
+
|
|
543
|
+
**For contributors**
|
|
544
|
+
- [CONTRIBUTING.md](./CONTRIBUTING.md) - Development setup and contribution guidelines
|
|
545
|
+
- [Project Review](./docs/project-review-2026-07.md) - Current state of the codebase and infrastructure
|
|
546
|
+
- [Uplift Plan](./docs/uplift-plan.md) - Sequenced engineering priorities
|
|
547
|
+
- [docs/](./docs/) - Architecture notes, testing strategy, and design records
|
|
548
|
+
|
|
549
|
+
## Credits
|
|
550
|
+
|
|
551
|
+
**Original Author:** [Christopher Aedo](https://github.com/aedocw) (epub2tts-edge)
|
|
552
|
+
|
|
553
|
+
**Fork Maintainer:** [loganrooks](https://github.com/loganrooks)
|
|
554
|
+
|
|
555
|
+
## Contributing
|
|
556
|
+
|
|
557
|
+
Contributions welcome! See [CONTRIBUTING.md](./CONTRIBUTING.md).
|
|
558
|
+
|
|
559
|
+
## License
|
|
560
|
+
|
|
561
|
+
GPL 3.0
|
|
@@ -0,0 +1,49 @@
|
|
|
1
|
+
audiobookifier-2.6.0.dist-info/licenses/LICENSE,sha256=OXLcl0T2SZ8Pmy2_dmlvKuetivmyPd5m1q-Gyd-zaYY,35149
|
|
2
|
+
epub2tts_edge/__init__.py,sha256=pEB2HXYxC3pT9SIv0T-Vt8GFViHLUHXEo3462HcNF2s,5472
|
|
3
|
+
epub2tts_edge/audio_generator.py,sha256=7aBY78QlAmNue9YcoijurmDDWdsNBMez3KObT_MCj-U,27415
|
|
4
|
+
epub2tts_edge/audio_normalization.py,sha256=8olYvK8Qbcc00egM3bBPHs0a1omujSeQKi-e5jdoFt4,7842
|
|
5
|
+
epub2tts_edge/batch_processor.py,sha256=7yYR__2k41ivCsNTuMGSrJ3j6479c0-UvjcN7wUxzFk,29068
|
|
6
|
+
epub2tts_edge/chapter_detector.py,sha256=XKNYHVxLu8WuhfSxBJaqTTgSlLqfmvw5EjAnXz3fXN4,52421
|
|
7
|
+
epub2tts_edge/chapter_selector.py,sha256=8tJmzDCcb5Bx4hWEDSlQGC-EHUda1DTowwcNr7YxX0E,7095
|
|
8
|
+
epub2tts_edge/config.py,sha256=wItC9Ex_-9uLQQEcnDGBKtDk00FDOGpaCey3MQnjn1U,8257
|
|
9
|
+
epub2tts_edge/content_filter.py,sha256=8WUGEdvp4jII9YmeQwWMZS8lIM4iOzJ8YG5Ckc0FbCQ,16406
|
|
10
|
+
epub2tts_edge/epub2tts_edge.py,sha256=myeVyxS45RdOt42mEfvjSQlanK07uKf4XrAljv7ebDc,44604
|
|
11
|
+
epub2tts_edge/errors.py,sha256=__DtlZIbRDSq3uTyw81LGV_H0915fHVKJATvv6dCeeU,7618
|
|
12
|
+
epub2tts_edge/job_manager.py,sha256=Du4qqaCTEN4gTYDLDOlrSxtz6R1roBozzWuSbF1HhH4,18278
|
|
13
|
+
epub2tts_edge/logger.py,sha256=XZTPhysOLWwbCg3dR1ZczZE5bH5yKnRS5SAAyjg_0KY,2772
|
|
14
|
+
epub2tts_edge/mobi_parser.py,sha256=v3LNdVOyvuXvNJMpHjiwEmGVk_-Zo67D0zYoM5wBo4E,14172
|
|
15
|
+
epub2tts_edge/multi_voice.py,sha256=7c68W_nlxMea0OsSO7q-HZgDJ_8EWeVf0b462ZZpV4c,9519
|
|
16
|
+
epub2tts_edge/pause_resume.py,sha256=hLd7tzq1xCEO1T_LRCgDTXK-oDWd8Xxq7AeeTJtVQcI,8111
|
|
17
|
+
epub2tts_edge/pronunciation.py,sha256=ypdKHR3Eku3Xq8HjBl4Y-jX2RUzIcV3Jjsd4EslfMog,6312
|
|
18
|
+
epub2tts_edge/silence_detection.py,sha256=DtxS5ZUzrwEoyQT5e1IpT1-GSlSGX6j1AfMSk21i_q8,7183
|
|
19
|
+
epub2tts_edge/voice_preview.py,sha256=5HzjfG6SoZoBKH8vQspHT7W8V_oKHLzhUeavdXJPoFQ,18307
|
|
20
|
+
epub2tts_edge/core/__init__.py,sha256=1P1mWq8ayhzrPd66aLmFXvzJ81gExMJgoEpyAvVPbJo,953
|
|
21
|
+
epub2tts_edge/core/events.py,sha256=PpLCDHAbJuGgy4e9or0hAcrFPFMjmfhVooz--UEAiKw,6766
|
|
22
|
+
epub2tts_edge/core/output_naming.py,sha256=_ratmqU8JRCn3rymPIkTPgssq4AOuGdOoVfspdU3eDE,7518
|
|
23
|
+
epub2tts_edge/core/pipeline.py,sha256=nMsproSf4cpg81md0Hf672D-2cIvZTqXvWtsFMS4IYM,21421
|
|
24
|
+
epub2tts_edge/core/profiles.py,sha256=Y4nZCO_Oq3RrokRH_JJ7TO-HI_RiZsusx2cxm-9Y8Us,5676
|
|
25
|
+
epub2tts_edge/testing/__init__.py,sha256=If68EUl3Po_sRiKu1jNpsxpQ0jvO27sXd2EIRB0uZO0,395
|
|
26
|
+
epub2tts_edge/testing/mock_tts.py,sha256=jy9jSLK1jzjuO6L9e2HWRSWRv2lt0y4-EQDIsoBFXWU,7667
|
|
27
|
+
epub2tts_edge/tui/__init__.py,sha256=7e9HetL5qsO7Xmxfng0xI9vn_2kLnlhxY0F4f9T2hNE,1542
|
|
28
|
+
epub2tts_edge/tui/app.py,sha256=IOGt8mA6gAqRTc546ZchaRPdMI57FBr5hEwLY6p7kag,85013
|
|
29
|
+
epub2tts_edge/tui/handlers/__init__.py,sha256=m8UYlMGE4UNtp7uUKmFnSBf5G6hTQT2-7nYp8_X3H3Y,216
|
|
30
|
+
epub2tts_edge/tui/handlers/event_adapter.py,sha256=D1GlZNeqNNDCFLEU83SbbJhpisqO8YffF5vFMugI7J4,10446
|
|
31
|
+
epub2tts_edge/tui/models/__init__.py,sha256=5yychbcqcuguXHQoC4VLVv1nMN73erRegPclkDfYiBk,234
|
|
32
|
+
epub2tts_edge/tui/models/preview_state.py,sha256=6N3DGVkktjaEBnW7_k8_TFPD5E_0lekOdcvI3_Zmvs8,4642
|
|
33
|
+
epub2tts_edge/tui/models/voice_status.py,sha256=xmibZj_1gnEukoDpNCqI4hNu6TyXPkJt7S2wzlf7UYk,1785
|
|
34
|
+
epub2tts_edge/tui/panels/__init__.py,sha256=8i5XGJYbnpBEDF-4--ODQrpzWyuXOAivta7ZxAkOHhc,571
|
|
35
|
+
epub2tts_edge/tui/panels/file_panel.py,sha256=wH0-MQmVl8FeRGaTwIWFKKOr501uxjFs3NTkljzkNjg,14257
|
|
36
|
+
epub2tts_edge/tui/panels/jobs_panel.py,sha256=TV66QPs5v6i1FnZJ0P5A6Wpyt1GysV6fzBMBk6M402M,12164
|
|
37
|
+
epub2tts_edge/tui/panels/log_panel.py,sha256=B_29D76TMUoxobx-WIGKoNXB1PcQ-HeCEdn53YOrQE0,1202
|
|
38
|
+
epub2tts_edge/tui/panels/preview_panel.py,sha256=iMLiwk8-fUVTEv7vP_xSCuAs_SaZa5Yn1HnZL8a2oys,31893
|
|
39
|
+
epub2tts_edge/tui/panels/progress_panel.py,sha256=kAxtCtFQEMxCTNRj9K-GysUKffja_5eGnpwG0WufLJA,4058
|
|
40
|
+
epub2tts_edge/tui/panels/queue_panel.py,sha256=26BjDl5q30d8byTyn4huFY5XB_KiGuVEm2vHKwj_MEM,2885
|
|
41
|
+
epub2tts_edge/tui/panels/settings_panel.py,sha256=PIXNMDu7CgDICrRMSlLRvUQpHjA45mXJh1yCYvGfJ38,18590
|
|
42
|
+
epub2tts_edge/tui/screens/__init__.py,sha256=oBof1UJyvMaardF6v4E6gybStBA9dSdSQjOFg9P0Tlk,224
|
|
43
|
+
epub2tts_edge/tui/screens/directory_browser.py,sha256=vtNuCArHnB9RKPBSUsCbvTkGTLS24l0CJZjnrQJWumI,3381
|
|
44
|
+
epub2tts_edge/tui/screens/help_screen.py,sha256=7vLmDf85kjs9FytDlqbdU52gUBdYDVVDmatVkVCZQMA,3732
|
|
45
|
+
audiobookifier-2.6.0.dist-info/METADATA,sha256=jx2HhWj4fjBlUe-hoJOQSqHsTbjiLuiM4dBWh_kVIXc,17478
|
|
46
|
+
audiobookifier-2.6.0.dist-info/WHEEL,sha256=K260EYznzXsJYBQGqmI8VTxEdiZYNvDZwW9cBh9-_MA,91
|
|
47
|
+
audiobookifier-2.6.0.dist-info/entry_points.txt,sha256=UjGadll4I49ZdbhcDdfBun8P2drUJWYZmGwZKfxf5x8,154
|
|
48
|
+
audiobookifier-2.6.0.dist-info/top_level.txt,sha256=k8mQ6r-Djtfd4UUR2ef158pM8nroPobYYREuseU1QSI,14
|
|
49
|
+
audiobookifier-2.6.0.dist-info/RECORD,,
|