supervertaler 1.9.174__py3-none-any.whl → 1.9.176b0__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.
@@ -186,9 +186,13 @@ def run_all_migrations(db_manager) -> bool:
186
186
  # Migration 3: Add display_order and forbidden fields to synonyms
187
187
  if not migrate_synonym_fields(db_manager):
188
188
  success = False
189
-
189
+
190
+ # Migration 4: Add ai_inject field to termbases
191
+ if not migrate_termbase_ai_inject(db_manager):
192
+ success = False
193
+
190
194
  print("="*60)
191
-
195
+
192
196
  return success
193
197
 
194
198
 
@@ -221,18 +225,26 @@ def check_and_migrate(db_manager) -> bool:
221
225
 
222
226
  # Check if synonyms table exists
223
227
  cursor.execute("""
224
- SELECT name FROM sqlite_master
228
+ SELECT name FROM sqlite_master
225
229
  WHERE type='table' AND name='termbase_synonyms'
226
230
  """)
227
231
  needs_synonyms_table = cursor.fetchone() is None
228
-
232
+
233
+ # Check if termbases table has ai_inject column
234
+ cursor.execute("PRAGMA table_info(termbases)")
235
+ termbase_columns = {row[1] for row in cursor.fetchall()}
236
+ needs_ai_inject = 'ai_inject' not in termbase_columns
237
+
229
238
  if needs_migration:
230
239
  print(f"⚠️ Migration needed - missing columns: {', '.join([c for c in ['project', 'client', 'term_uuid', 'note'] if c not in columns])}")
231
-
240
+
232
241
  if needs_synonyms_table:
233
242
  print("⚠️ Migration needed - termbase_synonyms table missing")
234
-
235
- if needs_migration or needs_synonyms_table:
243
+
244
+ if needs_ai_inject:
245
+ print("⚠️ Migration needed - termbases.ai_inject column missing")
246
+
247
+ if needs_migration or needs_synonyms_table or needs_ai_inject:
236
248
  success = run_all_migrations(db_manager)
237
249
  if success:
238
250
  # Generate UUIDs for terms that don't have them
@@ -316,6 +328,41 @@ def migrate_synonym_fields(db_manager) -> bool:
316
328
  return False
317
329
 
318
330
 
331
+ def migrate_termbase_ai_inject(db_manager) -> bool:
332
+ """
333
+ Add ai_inject column to termbases table.
334
+ When enabled, the termbase's terms will be injected into LLM translation prompts.
335
+
336
+ Args:
337
+ db_manager: DatabaseManager instance
338
+
339
+ Returns:
340
+ True if migration successful
341
+ """
342
+ try:
343
+ cursor = db_manager.cursor
344
+
345
+ # Check which columns exist
346
+ cursor.execute("PRAGMA table_info(termbases)")
347
+ columns = {row[1] for row in cursor.fetchall()}
348
+
349
+ if 'ai_inject' not in columns:
350
+ print("📊 Adding 'ai_inject' column to termbases...")
351
+ cursor.execute("ALTER TABLE termbases ADD COLUMN ai_inject BOOLEAN DEFAULT 0")
352
+ db_manager.connection.commit()
353
+ print(" ✓ Column 'ai_inject' added successfully")
354
+ else:
355
+ print("✅ termbases.ai_inject column already exists")
356
+
357
+ return True
358
+
359
+ except Exception as e:
360
+ print(f"❌ ai_inject migration failed: {e}")
361
+ import traceback
362
+ traceback.print_exc()
363
+ return False
364
+
365
+
319
366
  def generate_missing_uuids(db_manager) -> bool:
320
367
  """
321
368
  Generate UUIDs for any termbase terms that don't have them.
@@ -409,7 +409,111 @@ class TermbaseManager:
409
409
  except Exception as e:
410
410
  self.log(f"✗ Error setting termbase read_only: {e}")
411
411
  return False
412
-
412
+
413
+ def get_termbase_ai_inject(self, termbase_id: int) -> bool:
414
+ """Get whether termbase terms should be injected into LLM prompts"""
415
+ try:
416
+ cursor = self.db_manager.cursor
417
+ cursor.execute("SELECT ai_inject FROM termbases WHERE id = ?", (termbase_id,))
418
+ result = cursor.fetchone()
419
+ return bool(result[0]) if result and result[0] else False
420
+ except Exception as e:
421
+ self.log(f"✗ Error getting termbase ai_inject: {e}")
422
+ return False
423
+
424
+ def set_termbase_ai_inject(self, termbase_id: int, ai_inject: bool) -> bool:
425
+ """Set whether termbase terms should be injected into LLM prompts"""
426
+ try:
427
+ cursor = self.db_manager.cursor
428
+ cursor.execute("""
429
+ UPDATE termbases SET ai_inject = ? WHERE id = ?
430
+ """, (1 if ai_inject else 0, termbase_id))
431
+ self.db_manager.connection.commit()
432
+ status = "enabled" if ai_inject else "disabled"
433
+ self.log(f"✓ AI injection {status} for termbase {termbase_id}")
434
+ return True
435
+ except Exception as e:
436
+ self.log(f"✗ Error setting termbase ai_inject: {e}")
437
+ return False
438
+
439
+ def get_ai_inject_termbases(self, project_id: Optional[int] = None) -> List[Dict]:
440
+ """
441
+ Get all termbases with ai_inject enabled that are active for the given project.
442
+
443
+ Args:
444
+ project_id: Project ID (0 or None for global)
445
+
446
+ Returns:
447
+ List of termbase dictionaries with all terms
448
+ """
449
+ try:
450
+ cursor = self.db_manager.cursor
451
+ proj_id = project_id if project_id else 0
452
+
453
+ cursor.execute("""
454
+ SELECT t.id, t.name, t.source_lang, t.target_lang
455
+ FROM termbases t
456
+ LEFT JOIN termbase_activation ta ON t.id = ta.termbase_id AND ta.project_id = ?
457
+ WHERE t.ai_inject = 1
458
+ AND (ta.is_active = 1 OR (t.is_global = 1 AND ta.is_active IS NULL))
459
+ ORDER BY ta.priority ASC, t.name ASC
460
+ """, (proj_id,))
461
+
462
+ termbases = []
463
+ for row in cursor.fetchall():
464
+ termbases.append({
465
+ 'id': row[0],
466
+ 'name': row[1],
467
+ 'source_lang': row[2],
468
+ 'target_lang': row[3]
469
+ })
470
+ return termbases
471
+ except Exception as e:
472
+ self.log(f"✗ Error getting AI inject termbases: {e}")
473
+ return []
474
+
475
+ def get_ai_inject_terms(self, project_id: Optional[int] = None) -> List[Dict]:
476
+ """
477
+ Get all terms from AI-inject-enabled termbases for the given project.
478
+
479
+ Args:
480
+ project_id: Project ID (0 or None for global)
481
+
482
+ Returns:
483
+ List of term dictionaries with source_term, target_term, forbidden, termbase_name
484
+ """
485
+ try:
486
+ # First get all AI-inject termbases
487
+ ai_termbases = self.get_ai_inject_termbases(project_id)
488
+ if not ai_termbases:
489
+ return []
490
+
491
+ all_terms = []
492
+ cursor = self.db_manager.cursor
493
+
494
+ for tb in ai_termbases:
495
+ cursor.execute("""
496
+ SELECT source_term, target_term, forbidden, priority
497
+ FROM termbase_terms
498
+ WHERE termbase_id = ?
499
+ ORDER BY priority ASC, source_term ASC
500
+ """, (tb['id'],))
501
+
502
+ for row in cursor.fetchall():
503
+ all_terms.append({
504
+ 'source_term': row[0],
505
+ 'target_term': row[1],
506
+ 'forbidden': bool(row[2]) if row[2] else False,
507
+ 'priority': row[3] or 99,
508
+ 'termbase_name': tb['name']
509
+ })
510
+
511
+ self.log(f"📚 Retrieved {len(all_terms)} terms from {len(ai_termbases)} AI-inject glossar{'y' if len(ai_termbases) == 1 else 'ies'}")
512
+ return all_terms
513
+ except Exception as e:
514
+ self.log(f"✗ Error getting AI inject terms: {e}")
515
+ return []
516
+
413
517
  def set_termbase_priority(self, termbase_id: int, project_id: int, priority: int) -> bool:
414
518
  """
415
519
  Set manual priority for a termbase in a specific project.
@@ -367,7 +367,7 @@ class UnifiedPromptLibrary:
367
367
 
368
368
  self.active_primary_prompt = self.prompts[relative_path]['content']
369
369
  self.active_primary_prompt_path = relative_path
370
- self.log(f"✓ Set primary prompt: {self.prompts[relative_path].get('name', relative_path)}")
370
+ self.log(f"✓ Set custom prompt: {self.prompts[relative_path].get('name', relative_path)}")
371
371
  return True
372
372
 
373
373
  def set_external_primary_prompt(self, file_path: str) -> Tuple[bool, str]:
@@ -399,7 +399,7 @@ class UnifiedPromptLibrary:
399
399
  self.active_primary_prompt = content
400
400
  self.active_primary_prompt_path = f"[EXTERNAL] {file_path}"
401
401
 
402
- self.log(f"✓ Set external primary prompt: {display_name}")
402
+ self.log(f"✓ Set external custom prompt: {display_name}")
403
403
  return True, display_name
404
404
 
405
405
  def attach_prompt(self, relative_path: str) -> bool:
@@ -1566,9 +1566,9 @@ class UnifiedPromptManagerQt:
1566
1566
 
1567
1567
  layout.addWidget(mode_frame)
1568
1568
 
1569
- # Primary Prompt
1569
+ # Custom Prompt
1570
1570
  primary_layout = QHBoxLayout()
1571
- primary_label = QLabel("Primary Prompt ⭐:")
1571
+ primary_label = QLabel("Custom Prompt ⭐:")
1572
1572
  primary_label.setFont(QFont("Segoe UI", 9, QFont.Weight.Bold))
1573
1573
  primary_layout.addWidget(primary_label)
1574
1574
 
@@ -2210,8 +2210,8 @@ class UnifiedPromptManagerQt:
2210
2210
  if data['type'] == 'prompt':
2211
2211
  path = data['path']
2212
2212
 
2213
- # Set as primary
2214
- action_primary = menu.addAction("⭐ Set as Primary Prompt")
2213
+ # Set as custom prompt
2214
+ action_primary = menu.addAction("⭐ Set as Custom Prompt")
2215
2215
  action_primary.triggered.connect(lambda: self._set_primary_prompt(path))
2216
2216
 
2217
2217
  # Attach/detach
@@ -2493,7 +2493,7 @@ class UnifiedPromptManagerQt:
2493
2493
  self.library.active_primary_prompt_path = None
2494
2494
  self.primary_prompt_label.setText("[None selected]")
2495
2495
  self.primary_prompt_label.setStyleSheet("color: #999;")
2496
- self.log_message("✓ Cleared primary prompt")
2496
+ self.log_message("✓ Cleared custom prompt")
2497
2497
 
2498
2498
  def _load_external_primary_prompt(self):
2499
2499
  """Load an external prompt file (not in library) as primary"""
@@ -2787,7 +2787,7 @@ class UnifiedPromptManagerQt:
2787
2787
  composition_parts.append(f"📏 Total prompt length: {len(combined):,} characters")
2788
2788
 
2789
2789
  if self.library.active_primary_prompt:
2790
- composition_parts.append(f"✓ Primary prompt attached")
2790
+ composition_parts.append(f"✓ Custom prompt attached")
2791
2791
 
2792
2792
  if self.library.attached_prompts:
2793
2793
  composition_parts.append(f"✓ {len(self.library.attached_prompts)} additional prompt(s) attached")
@@ -2993,49 +2993,66 @@ If the text refers to figures (e.g., 'Figure 1A'), relevant images may be provid
2993
2993
 
2994
2994
  # === Prompt Composition (for translation) ===
2995
2995
 
2996
- def build_final_prompt(self, source_text: str, source_lang: str, target_lang: str, mode: str = None) -> str:
2996
+ def build_final_prompt(self, source_text: str, source_lang: str, target_lang: str,
2997
+ mode: str = None, glossary_terms: list = None) -> str:
2997
2998
  """
2998
2999
  Build final prompt for translation using 2-layer architecture:
2999
3000
  1. System Prompt (auto-selected by mode)
3000
3001
  2. Combined prompts from library (primary + attached)
3001
-
3002
+ 3. Glossary terms (optional, injected before translation delimiter)
3003
+
3002
3004
  Args:
3003
3005
  source_text: Text to translate
3004
3006
  source_lang: Source language
3005
3007
  target_lang: Target language
3006
3008
  mode: Override mode (if None, uses self.current_mode)
3007
-
3009
+ glossary_terms: Optional list of term dicts with 'source_term' and 'target_term' keys
3010
+
3008
3011
  Returns:
3009
3012
  Complete prompt ready for LLM
3010
3013
  """
3011
3014
  if mode is None:
3012
3015
  mode = self.current_mode
3013
-
3016
+
3014
3017
  # Layer 1: System Prompt
3015
3018
  system_template = self.get_system_template(mode)
3016
-
3019
+
3017
3020
  # Replace placeholders in system prompt
3018
3021
  system_template = system_template.replace("{{SOURCE_LANGUAGE}}", source_lang)
3019
3022
  system_template = system_template.replace("{{TARGET_LANGUAGE}}", target_lang)
3020
3023
  system_template = system_template.replace("{{SOURCE_TEXT}}", source_text)
3021
-
3024
+
3022
3025
  # Layer 2: Library prompts (primary + attached)
3023
3026
  library_prompts = ""
3024
-
3027
+
3025
3028
  if self.library.active_primary_prompt:
3026
- library_prompts += "\n\n# PRIMARY INSTRUCTIONS\n\n"
3029
+ library_prompts += "\n\n# CUSTOM PROMPT\n\n"
3027
3030
  library_prompts += self.library.active_primary_prompt
3028
-
3031
+
3029
3032
  for attached_content in self.library.attached_prompts:
3030
3033
  library_prompts += "\n\n# ADDITIONAL INSTRUCTIONS\n\n"
3031
3034
  library_prompts += attached_content
3032
-
3035
+
3033
3036
  # Combine
3034
3037
  final_prompt = system_template + library_prompts
3035
-
3038
+
3039
+ # Glossary injection (if terms provided)
3040
+ if glossary_terms:
3041
+ final_prompt += "\n\n# GLOSSARY\n\n"
3042
+ final_prompt += "Use these approved terms in your translation:\n\n"
3043
+ for term in glossary_terms:
3044
+ source_term = term.get('source_term', '')
3045
+ target_term = term.get('target_term', '')
3046
+ if source_term and target_term:
3047
+ # Mark forbidden terms
3048
+ if term.get('forbidden'):
3049
+ final_prompt += f"- {source_term} → ⚠️ DO NOT USE: {target_term}\n"
3050
+ else:
3051
+ final_prompt += f"- {source_term} → {target_term}\n"
3052
+
3036
3053
  # Add translation delimiter
3037
3054
  final_prompt += "\n\n**YOUR TRANSLATION (provide ONLY the translated text, no numbering or labels):**\n"
3038
-
3055
+
3039
3056
  return final_prompt
3040
3057
 
3041
3058
  # ============================================================================
@@ -0,0 +1,151 @@
1
+ Metadata-Version: 2.4
2
+ Name: supervertaler
3
+ Version: 1.9.176b0
4
+ Summary: Professional AI-enhanced translation workbench with multi-LLM support, glossary system, TM, spellcheck, voice commands, and PyQt6 interface. Batteries included (core).
5
+ Home-page: https://supervertaler.com
6
+ Author: Michael Beijer
7
+ Author-email: Michael Beijer <info@michaelbeijer.co.uk>
8
+ Maintainer-email: Michael Beijer <info@michaelbeijer.co.uk>
9
+ License-Expression: MIT
10
+ Project-URL: Homepage, https://supervertaler.com
11
+ Project-URL: Repository, https://github.com/michaelbeijer/Supervertaler.git
12
+ Project-URL: Bug Tracker, https://github.com/michaelbeijer/Supervertaler/issues
13
+ Project-URL: Changelog, https://github.com/michaelbeijer/Supervertaler/blob/main/CHANGELOG.md
14
+ Project-URL: Documentation, https://github.com/michaelbeijer/Supervertaler/blob/main/AGENTS.md
15
+ Project-URL: Author Website, https://michaelbeijer.co.uk
16
+ Keywords: translation,CAT,CAT-tool,AI,LLM,GPT,Claude,Gemini,Ollama,glossary,termbase,translation-memory,TM,PyQt6,localization,memoQ,Trados,SDLPPX,XLIFF,voice-commands,spellcheck
17
+ Classifier: Development Status :: 4 - Beta
18
+ Classifier: Programming Language :: Python :: 3
19
+ Classifier: Programming Language :: Python :: 3.10
20
+ Classifier: Programming Language :: Python :: 3.11
21
+ Classifier: Programming Language :: Python :: 3.12
22
+ Classifier: Operating System :: OS Independent
23
+ Classifier: Operating System :: Microsoft :: Windows
24
+ Classifier: Operating System :: POSIX :: Linux
25
+ Classifier: Intended Audience :: End Users/Desktop
26
+ Classifier: Topic :: Office/Business
27
+ Classifier: Topic :: Text Processing :: Linguistic
28
+ Classifier: Environment :: X11 Applications :: Qt
29
+ Requires-Python: >=3.10
30
+ Description-Content-Type: text/markdown
31
+ License-File: LICENSE
32
+ Requires-Dist: PyQt6>=6.5.0
33
+ Requires-Dist: PyQt6-WebEngine>=6.5.0
34
+ Requires-Dist: python-docx>=0.8.11
35
+ Requires-Dist: openpyxl>=3.1.0
36
+ Requires-Dist: Pillow>=10.0.0
37
+ Requires-Dist: lxml>=4.9.0
38
+ Requires-Dist: openai>=1.0.0
39
+ Requires-Dist: anthropic>=0.7.0
40
+ Requires-Dist: google-generativeai>=0.3.0
41
+ Requires-Dist: requests>=2.28.0
42
+ Requires-Dist: markitdown>=0.0.1
43
+ Requires-Dist: sacrebleu>=2.3.1
44
+ Requires-Dist: pyperclip>=1.8.2
45
+ Requires-Dist: chardet>=5.0.0
46
+ Requires-Dist: pyyaml>=6.0.0
47
+ Requires-Dist: markdown>=3.4.0
48
+ Requires-Dist: pyspellchecker>=0.7.0
49
+ Requires-Dist: sounddevice>=0.4.6
50
+ Requires-Dist: numpy>=1.24.0
51
+ Requires-Dist: PyMuPDF>=1.23.0
52
+ Requires-Dist: boto3>=1.28.0
53
+ Requires-Dist: deepl>=1.15.0
54
+ Requires-Dist: spylls>=0.1.7
55
+ Requires-Dist: keyboard>=0.13.5; platform_system == "Windows"
56
+ Requires-Dist: ahk>=1.0.0; platform_system == "Windows"
57
+ Requires-Dist: pyautogui>=0.9.54; platform_system == "Windows"
58
+ Requires-Dist: psutil>=5.9.0
59
+ Provides-Extra: local-whisper
60
+ Requires-Dist: openai-whisper>=20230314; extra == "local-whisper"
61
+ Provides-Extra: voice
62
+ Provides-Extra: web
63
+ Provides-Extra: pdf
64
+ Provides-Extra: mt
65
+ Provides-Extra: hunspell
66
+ Provides-Extra: windows
67
+ Provides-Extra: core
68
+ Provides-Extra: all
69
+ Dynamic: author
70
+ Dynamic: home-page
71
+ Dynamic: license-file
72
+ Dynamic: requires-python
73
+
74
+ # Supervertaler
75
+
76
+ [![PyPI version](https://badge.fury.io/py/supervertaler.svg)](https://pypi.org/project/Supervertaler/)
77
+ [![Python 3.10+](https://img.shields.io/badge/python-3.10+-blue.svg)](https://www.python.org/downloads/)
78
+ [![License: MIT](https://img.shields.io/badge/License-MIT-yellow.svg)](https://opensource.org/licenses/MIT)
79
+
80
+ **Professional AI-enhanced translation workbench** with multi-LLM support (GPT-4, Claude, Gemini, Ollama), translation memory, glossary management, and seamless CAT tool integration (memoQ, Trados, CafeTran, Phrase, Déjà Vu).
81
+
82
+ ---
83
+
84
+ ## Installation
85
+
86
+ ```bash
87
+ pip install supervertaler
88
+ supervertaler
89
+ ```
90
+
91
+ Or run from source:
92
+
93
+ ```bash
94
+ git clone https://github.com/michaelbeijer/Supervertaler.git
95
+ cd Supervertaler
96
+ pip install -r requirements.txt
97
+ python Supervertaler.py
98
+ ```
99
+
100
+ ---
101
+
102
+ ## Key Features
103
+
104
+ - **Multi-LLM AI Translation** - OpenAI GPT-4/5, Anthropic Claude, Google Gemini, Local Ollama
105
+ - **Translation Memory** - Fuzzy matching TM with TMX import/export
106
+ - **Glossary System** - Priority-based term highlighting with forbidden term marking
107
+ - **Superlookup** - Unified concordance search across TM, glossaries, MT, and web resources
108
+ - **CAT Tool Integration** - memoQ XLIFF, Trados SDLPPX/SDLRPX, CafeTran, Phrase, Déjà Vu X3
109
+ - **Voice Commands** - Hands-free translation with OpenAI Whisper
110
+ - **Document Support** - DOCX, bilingual DOCX, PDF, Markdown, plain text
111
+
112
+ ---
113
+
114
+ ## Documentation
115
+
116
+ | Resource | Description |
117
+ |----------|-------------|
118
+ | [Online Manual](https://supervertaler.gitbook.io/superdocs/) | Quick start, guides, and troubleshooting |
119
+ | [Changelog](CHANGELOG.md) | Complete version history |
120
+ | [Keyboard Shortcuts](docs/guides/KEYBOARD_SHORTCUTS.md) | Shortcut reference |
121
+ | [FAQ](FAQ.md) | Common questions |
122
+ | [Website](https://supervertaler.com) | Project homepage |
123
+
124
+ ---
125
+
126
+ ## Requirements
127
+
128
+ - Python 3.10+
129
+ - PyQt6
130
+ - Windows, macOS, or Linux
131
+
132
+ ---
133
+
134
+ ## Contributing
135
+
136
+ - [Report bugs](https://github.com/michaelbeijer/Supervertaler/issues)
137
+ - [Request features](https://github.com/michaelbeijer/Supervertaler/discussions)
138
+ - [Contributing guide](CONTRIBUTING.md)
139
+ - [Stargazers](https://github.com/michaelbeijer/Supervertaler/stargazers) - See who's starred the project
140
+
141
+ ---
142
+
143
+ ## About
144
+
145
+ **Supervertaler** is maintained by [Michael Beijer](https://michaelbeijer.co.uk), a professional translator with 30 years of experience in technical and patent translation.
146
+
147
+ **License:** MIT - Free for personal and commercial use.
148
+
149
+ ---
150
+
151
+ **Current Version:** See [CHANGELOG.md](CHANGELOG.md) for the latest release notes.
@@ -1,4 +1,4 @@
1
- Supervertaler.py,sha256=P2n_d1jzUgaIOpQ0z_pTHqRQbifUYBPwAUkWDh_FkRY,2298190
1
+ Supervertaler.py,sha256=ABqaS7k80j4w3EiJr52ogQVIJRAFFOD3NpaeDbzWX6k,2318994
2
2
  modules/__init__.py,sha256=G58XleS-EJ2sX4Kehm-3N2m618_W2Es0Kg8CW_eBG7g,327
3
3
  modules/ai_actions.py,sha256=i5MJcM-7Y6CAvKUwxmxrVHeoZAVtAP7aRDdWM5KLkO0,33877
4
4
  modules/ai_attachment_manager.py,sha256=juZlrW3UPkIkcnj0SREgOQkQROLf0fcu3ShZcKXMxsI,11361
@@ -7,7 +7,7 @@ modules/autofingers_engine.py,sha256=eJ7tBi7YJvTToe5hYTfnyGXB-qme_cHrOPZibaoR2Xw
7
7
  modules/cafetran_docx_handler.py,sha256=_F7Jh0WPVaDnMhdxEsVSXuD1fN9r-S_V6i0gr86Pdfc,14076
8
8
  modules/config_manager.py,sha256=MkPY3xVFgFDkcwewLREg4BfyKueO0OJkT1cTLxehcjM,17894
9
9
  modules/database_manager.py,sha256=FecvNLJa_mw0PZld8-LozUSSgtAq6wDZ8Mhq_u2aiA0,82563
10
- modules/database_migrations.py,sha256=Y1onFsLDV_6vzJLOpNy3WCZDohBZ2jc4prM-g2_RwLE,14085
10
+ modules/database_migrations.py,sha256=tndJ4wV_2JBfPggMgO1tQRwdfRFZ9zwvADllCZE9CCk,15663
11
11
  modules/dejavurtf_handler.py,sha256=8NZPPYtHga40SZCypHjPoJPmZTvm9rD-eEUUab7mjtg,28156
12
12
  modules/document_analyzer.py,sha256=t1rVvqLaTcpQTEja228C7zZnh8dXshK4wA9t1E9aGVk,19524
13
13
  modules/docx_handler.py,sha256=jSlZs5tollJnsnIA80buEXLfZBunp_GQ9lCtFZPUnBs,34053
@@ -58,7 +58,7 @@ modules/tag_manager.py,sha256=g66S0JSxdguN9AhWzZG3hsIz87Ul51wQ3c2wOCTZVSk,12789
58
58
  modules/term_extractor.py,sha256=qPvKNCVXFTGEGwXNvvC0cfCmdb5c3WhzE38EOgKdKUI,11253
59
59
  modules/termbase_entry_editor.py,sha256=iWO9CgLjMomGAqBXDsGAX7TFJvDOp2s_taS4gBL1rZY,35818
60
60
  modules/termbase_import_export.py,sha256=16IAY04IS_rgt0GH5UOUzUI5NoqAli4JMfMquxmFBm0,23552
61
- modules/termbase_manager.py,sha256=-PlGF6fIA7KYCteoQ8FZ_0SQZNRRBFAtLimHPbmhQ6w,44544
61
+ modules/termbase_manager.py,sha256=7KXEFab6y0o1EmFZwHs3ADklC95udVenxvrmN4XUoj0,48808
62
62
  modules/termview_widget.py,sha256=O3ah7g-4Lb_iUctxl9sMyxh8V3A5I5PFxmy9iIH2Kgk,53484
63
63
  modules/theme_manager.py,sha256=EOI_5pM2bXAadw08bbl92TLN-w28lbw4Zi1E8vQ-kM0,16694
64
64
  modules/tm_editor_dialog.py,sha256=AzGwq4QW641uFJdF8DljLTRRp4FLoYX3Pe4rlTjQWNg,3517
@@ -72,14 +72,14 @@ modules/trados_docx_handler.py,sha256=VPRAQ73cUHs_SEj6x81z1PmSxfjnwPBp9P4fXeK3Kp
72
72
  modules/translation_memory.py,sha256=13PDK4_kgYrWTACWBIBypOh2DvoxY9cRT8U6ulilbh4,28739
73
73
  modules/translation_results_panel.py,sha256=DmEe0pZRSfcZFg2cWeEREK7H9vrTcPkgeuMW54Pgrys,92505
74
74
  modules/translation_services.py,sha256=lyVpWuZK1wtVtYZMDMdLoq1DHBoSaeAnp-Yejb0TlVQ,10530
75
- modules/unified_prompt_library.py,sha256=lzbevgjUz_qCiYSf141BB0mmuaDhSsevWju_a7welu0,26008
76
- modules/unified_prompt_manager_qt.py,sha256=fyF3_r0N8hnImT-CcWo1AuBOQ1Dn_ExeeUCkZxeSkqE,170422
75
+ modules/unified_prompt_library.py,sha256=96u4WlMwnmmhD4uNJHZ-qVQj8v9_8dA2AVCWpBcwTrg,26006
76
+ modules/unified_prompt_manager_qt.py,sha256=U89UFGG-M7BLetoaLAlma0x-n8SIyx682DhSvaRnzJs,171285
77
77
  modules/voice_commands.py,sha256=iBb-gjWxRMLhFH7-InSRjYJz1EIDBNA2Pog8V7TtJaY,38516
78
78
  modules/voice_dictation.py,sha256=QmitXfkG-vRt5hIQATjphHdhXfqmwhzcQcbXB6aRzIg,16386
79
79
  modules/voice_dictation_lite.py,sha256=jorY0BmWE-8VczbtGrWwt1zbnOctMoSlWOsQrcufBcc,9423
80
- supervertaler-1.9.174.dist-info/licenses/LICENSE,sha256=m28u-4qL5nXIWnJ6xlQVw__H30rWFtRK3pCOais2OuY,1092
81
- supervertaler-1.9.174.dist-info/METADATA,sha256=MjFlkP5U4cAhkgRjfHo7MMcCSOrl3U5fXFEaViQ-iOU,48873
82
- supervertaler-1.9.174.dist-info/WHEEL,sha256=wUyA8OaulRlbfwMtmQsvNngGrxQHAvkKcvRmdizlJi0,92
83
- supervertaler-1.9.174.dist-info/entry_points.txt,sha256=NP4hiCvx-_30YYKqgr-jfJYQvHr1qTYBMfoVmKIXSM8,53
84
- supervertaler-1.9.174.dist-info/top_level.txt,sha256=9tUHBYUSfaE4S2E4W3eavJsDyYymkwLfeWAHHAPT6Dk,22
85
- supervertaler-1.9.174.dist-info/RECORD,,
80
+ supervertaler-1.9.176b0.dist-info/licenses/LICENSE,sha256=m28u-4qL5nXIWnJ6xlQVw__H30rWFtRK3pCOais2OuY,1092
81
+ supervertaler-1.9.176b0.dist-info/METADATA,sha256=NXnmveUpuH50y_2kAdkEavCbLiRpDYAUSIIc7YK0d-8,5727
82
+ supervertaler-1.9.176b0.dist-info/WHEEL,sha256=wUyA8OaulRlbfwMtmQsvNngGrxQHAvkKcvRmdizlJi0,92
83
+ supervertaler-1.9.176b0.dist-info/entry_points.txt,sha256=NP4hiCvx-_30YYKqgr-jfJYQvHr1qTYBMfoVmKIXSM8,53
84
+ supervertaler-1.9.176b0.dist-info/top_level.txt,sha256=9tUHBYUSfaE4S2E4W3eavJsDyYymkwLfeWAHHAPT6Dk,22
85
+ supervertaler-1.9.176b0.dist-info/RECORD,,