codexspec 0.4.7__tar.gz → 0.4.8__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.
- {codexspec-0.4.7 → codexspec-0.4.8}/PKG-INFO +27 -1
- {codexspec-0.4.7 → codexspec-0.4.8}/README.md +26 -0
- {codexspec-0.4.7 → codexspec-0.4.8}/pyproject.toml +1 -1
- {codexspec-0.4.7 → codexspec-0.4.8}/scripts/python/notify_telegram.py +0 -1
- {codexspec-0.4.7 → codexspec-0.4.8}/src/codexspec/__init__.py +95 -4
- {codexspec-0.4.7 → codexspec-0.4.8}/src/codexspec/i18n.py +22 -0
- {codexspec-0.4.7 → codexspec-0.4.8}/.gitignore +0 -0
- {codexspec-0.4.7 → codexspec-0.4.8}/LICENSE +0 -0
- {codexspec-0.4.7 → codexspec-0.4.8}/scripts/bash/check-i18n-completeness.sh +0 -0
- {codexspec-0.4.7 → codexspec-0.4.8}/scripts/bash/check-i18n-structure.sh +0 -0
- {codexspec-0.4.7 → codexspec-0.4.8}/scripts/bash/check-prerequisites.sh +0 -0
- {codexspec-0.4.7 → codexspec-0.4.8}/scripts/bash/common.sh +0 -0
- {codexspec-0.4.7 → codexspec-0.4.8}/scripts/bash/create-new-feature.sh +0 -0
- {codexspec-0.4.7 → codexspec-0.4.8}/scripts/powershell/check-prerequisites.ps1 +0 -0
- {codexspec-0.4.7 → codexspec-0.4.8}/scripts/powershell/common.ps1 +0 -0
- {codexspec-0.4.7 → codexspec-0.4.8}/scripts/powershell/create-new-feature.ps1 +0 -0
- {codexspec-0.4.7 → codexspec-0.4.8}/scripts/python/README.md +0 -0
- {codexspec-0.4.7 → codexspec-0.4.8}/scripts/python/claude_monitor.py +0 -0
- {codexspec-0.4.7 → codexspec-0.4.8}/scripts/python/tests/__init__.py +0 -0
- {codexspec-0.4.7 → codexspec-0.4.8}/scripts/python/tests/test_notify.py +0 -0
- {codexspec-0.4.7 → codexspec-0.4.8}/src/codexspec/commands/__init__.py +0 -0
- {codexspec-0.4.7 → codexspec-0.4.8}/src/codexspec/commands/installer.py +0 -0
- {codexspec-0.4.7 → codexspec-0.4.8}/src/codexspec/idea.md +0 -0
- {codexspec-0.4.7 → codexspec-0.4.8}/src/codexspec/translator.py +0 -0
- {codexspec-0.4.7 → codexspec-0.4.8}/templates/commands/analyze.md +0 -0
- {codexspec-0.4.7 → codexspec-0.4.8}/templates/commands/check-i18n-semantics.md +0 -0
- {codexspec-0.4.7 → codexspec-0.4.8}/templates/commands/checklist.md +0 -0
- {codexspec-0.4.7 → codexspec-0.4.8}/templates/commands/clarify.md +0 -0
- {codexspec-0.4.7 → codexspec-0.4.8}/templates/commands/commit-staged.md +0 -0
- {codexspec-0.4.7 → codexspec-0.4.8}/templates/commands/commit.md +0 -0
- {codexspec-0.4.7 → codexspec-0.4.8}/templates/commands/constitution.md +0 -0
- {codexspec-0.4.7 → codexspec-0.4.8}/templates/commands/generate-spec.md +0 -0
- {codexspec-0.4.7 → codexspec-0.4.8}/templates/commands/implement-tasks.md +0 -0
- {codexspec-0.4.7 → codexspec-0.4.8}/templates/commands/plan-to-tasks.md +0 -0
- {codexspec-0.4.7 → codexspec-0.4.8}/templates/commands/pr.md +0 -0
- {codexspec-0.4.7 → codexspec-0.4.8}/templates/commands/review-plan.md +0 -0
- {codexspec-0.4.7 → codexspec-0.4.8}/templates/commands/review-spec.md +0 -0
- {codexspec-0.4.7 → codexspec-0.4.8}/templates/commands/review-tasks.md +0 -0
- {codexspec-0.4.7 → codexspec-0.4.8}/templates/commands/spec-to-plan.md +0 -0
- {codexspec-0.4.7 → codexspec-0.4.8}/templates/commands/specify.md +0 -0
- {codexspec-0.4.7 → codexspec-0.4.8}/templates/commands/tasks-to-issues.md +0 -0
- {codexspec-0.4.7 → codexspec-0.4.8}/templates/commands/translate-docs.md +0 -0
- {codexspec-0.4.7 → codexspec-0.4.8}/templates/docs/checklist-template.md +0 -0
- {codexspec-0.4.7 → codexspec-0.4.8}/templates/docs/constitution-template.md +0 -0
- {codexspec-0.4.7 → codexspec-0.4.8}/templates/docs/plan-template-detailed.md +0 -0
- {codexspec-0.4.7 → codexspec-0.4.8}/templates/docs/plan-template-simple.md +0 -0
- {codexspec-0.4.7 → codexspec-0.4.8}/templates/docs/spec-template-detailed.md +0 -0
- {codexspec-0.4.7 → codexspec-0.4.8}/templates/docs/spec-template-simple.md +0 -0
- {codexspec-0.4.7 → codexspec-0.4.8}/templates/docs/tasks-template-detailed.md +0 -0
- {codexspec-0.4.7 → codexspec-0.4.8}/templates/docs/tasks-template-simple.md +0 -0
- {codexspec-0.4.7 → codexspec-0.4.8}/templates/translations/de.json +0 -0
- {codexspec-0.4.7 → codexspec-0.4.8}/templates/translations/en.json +0 -0
- {codexspec-0.4.7 → codexspec-0.4.8}/templates/translations/es.json +0 -0
- {codexspec-0.4.7 → codexspec-0.4.8}/templates/translations/fr.json +0 -0
- {codexspec-0.4.7 → codexspec-0.4.8}/templates/translations/ja.json +0 -0
- {codexspec-0.4.7 → codexspec-0.4.8}/templates/translations/ko.json +0 -0
- {codexspec-0.4.7 → codexspec-0.4.8}/templates/translations/pt-BR.json +0 -0
- {codexspec-0.4.7 → codexspec-0.4.8}/templates/translations/zh-CN.json +0 -0
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
Metadata-Version: 2.4
|
|
2
2
|
Name: codexspec
|
|
3
|
-
Version: 0.4.
|
|
3
|
+
Version: 0.4.8
|
|
4
4
|
Summary: CodexSpec - A Spec-Driven Development (SDD) toolkit for Claude Code
|
|
5
5
|
Project-URL: Homepage, https://github.com/Zts0hg/codexspec
|
|
6
6
|
Project-URL: Repository, https://github.com/Zts0hg/codexspec
|
|
@@ -599,6 +599,30 @@ CodexSpec supports multiple languages through **LLM dynamic translation**. Inste
|
|
|
599
599
|
### Setting Language
|
|
600
600
|
|
|
601
601
|
**During initialization:**
|
|
602
|
+
|
|
603
|
+
When you run `codexspec init` without the `--lang` parameter in an interactive terminal, you'll see a language selection prompt:
|
|
604
|
+
|
|
605
|
+
```bash
|
|
606
|
+
# Interactive language selection (TTY only)
|
|
607
|
+
codexspec init my-project
|
|
608
|
+
|
|
609
|
+
# Output:
|
|
610
|
+
# Select output language:
|
|
611
|
+
# [1] English (en)
|
|
612
|
+
# [2] Chinese (Simplified) (zh-CN)
|
|
613
|
+
# [3] Japanese (ja)
|
|
614
|
+
# [4] Korean (ko)
|
|
615
|
+
# [5] Spanish (es)
|
|
616
|
+
# [6] French (fr)
|
|
617
|
+
# [7] German (de)
|
|
618
|
+
# [8] Portuguese (Brasil) (pt-BR)
|
|
619
|
+
# [9] Other... (enter custom code)
|
|
620
|
+
#
|
|
621
|
+
# Enter choice [1]:
|
|
622
|
+
```
|
|
623
|
+
|
|
624
|
+
You can also specify the language directly:
|
|
625
|
+
|
|
602
626
|
```bash
|
|
603
627
|
# Create a project with Chinese output
|
|
604
628
|
codexspec init my-project --lang zh-CN
|
|
@@ -607,6 +631,8 @@ codexspec init my-project --lang zh-CN
|
|
|
607
631
|
codexspec init my-project --lang ja
|
|
608
632
|
```
|
|
609
633
|
|
|
634
|
+
> **Note:** In non-interactive environments (CI/CD, scripts), the default language is English. Use `--lang` to specify a different language.
|
|
635
|
+
|
|
610
636
|
**After initialization:**
|
|
611
637
|
```bash
|
|
612
638
|
# View current configuration
|
|
@@ -553,6 +553,30 @@ CodexSpec supports multiple languages through **LLM dynamic translation**. Inste
|
|
|
553
553
|
### Setting Language
|
|
554
554
|
|
|
555
555
|
**During initialization:**
|
|
556
|
+
|
|
557
|
+
When you run `codexspec init` without the `--lang` parameter in an interactive terminal, you'll see a language selection prompt:
|
|
558
|
+
|
|
559
|
+
```bash
|
|
560
|
+
# Interactive language selection (TTY only)
|
|
561
|
+
codexspec init my-project
|
|
562
|
+
|
|
563
|
+
# Output:
|
|
564
|
+
# Select output language:
|
|
565
|
+
# [1] English (en)
|
|
566
|
+
# [2] Chinese (Simplified) (zh-CN)
|
|
567
|
+
# [3] Japanese (ja)
|
|
568
|
+
# [4] Korean (ko)
|
|
569
|
+
# [5] Spanish (es)
|
|
570
|
+
# [6] French (fr)
|
|
571
|
+
# [7] German (de)
|
|
572
|
+
# [8] Portuguese (Brasil) (pt-BR)
|
|
573
|
+
# [9] Other... (enter custom code)
|
|
574
|
+
#
|
|
575
|
+
# Enter choice [1]:
|
|
576
|
+
```
|
|
577
|
+
|
|
578
|
+
You can also specify the language directly:
|
|
579
|
+
|
|
556
580
|
```bash
|
|
557
581
|
# Create a project with Chinese output
|
|
558
582
|
codexspec init my-project --lang zh-CN
|
|
@@ -561,6 +585,8 @@ codexspec init my-project --lang zh-CN
|
|
|
561
585
|
codexspec init my-project --lang ja
|
|
562
586
|
```
|
|
563
587
|
|
|
588
|
+
> **Note:** In non-interactive environments (CI/CD, scripts), the default language is English. Use `--lang` to specify a different language.
|
|
589
|
+
|
|
564
590
|
**After initialization:**
|
|
565
591
|
```bash
|
|
566
592
|
# View current configuration
|
|
@@ -15,7 +15,7 @@ from typing import Optional
|
|
|
15
15
|
import typer
|
|
16
16
|
from rich.console import Console
|
|
17
17
|
from rich.panel import Panel
|
|
18
|
-
from rich.prompt import Confirm
|
|
18
|
+
from rich.prompt import Confirm, Prompt
|
|
19
19
|
from rich.table import Table
|
|
20
20
|
|
|
21
21
|
from .commands.installer import (
|
|
@@ -387,11 +387,11 @@ def init(
|
|
|
387
387
|
"-a",
|
|
388
388
|
help="AI assistant to use (default: claude)",
|
|
389
389
|
),
|
|
390
|
-
lang: str = typer.Option(
|
|
391
|
-
|
|
390
|
+
lang: Optional[str] = typer.Option(
|
|
391
|
+
None,
|
|
392
392
|
"--lang",
|
|
393
393
|
"-l",
|
|
394
|
-
help="Output language
|
|
394
|
+
help="Output language (e.g., en, zh-CN, ja). Interactive prompt if not specified in TTY.",
|
|
395
395
|
),
|
|
396
396
|
force: bool = typer.Option(
|
|
397
397
|
False,
|
|
@@ -425,6 +425,20 @@ def init(
|
|
|
425
425
|
codexspec init --here --ai claude
|
|
426
426
|
codexspec init . --force --ai claude
|
|
427
427
|
"""
|
|
428
|
+
# Handle interactive language selection when --lang not specified
|
|
429
|
+
if lang is None:
|
|
430
|
+
if sys.stdin.isatty():
|
|
431
|
+
# TTY environment: show interactive prompt
|
|
432
|
+
try:
|
|
433
|
+
lang = prompt_language_selection()
|
|
434
|
+
except KeyboardInterrupt:
|
|
435
|
+
console.print()
|
|
436
|
+
console.print("[yellow]Selection cancelled, using default language (en)[/yellow]")
|
|
437
|
+
lang = "en"
|
|
438
|
+
else:
|
|
439
|
+
# Non-TTY environment: use default
|
|
440
|
+
lang = "en"
|
|
441
|
+
|
|
428
442
|
# Normalize language code early for use throughout the function
|
|
429
443
|
normalized_lang = normalize_locale(lang)
|
|
430
444
|
|
|
@@ -1484,6 +1498,83 @@ def prepend_compliance_section(claude_md_path: Path) -> None:
|
|
|
1484
1498
|
claude_md_path.write_text(import_statement + existing_content, encoding="utf-8")
|
|
1485
1499
|
|
|
1486
1500
|
|
|
1501
|
+
def prompt_language_selection(default: str = "en") -> str:
|
|
1502
|
+
"""Display interactive language selection prompt.
|
|
1503
|
+
|
|
1504
|
+
Shows a numbered list of supported languages and prompts the user to select one.
|
|
1505
|
+
If the user selects "Other...", they can enter a custom language code.
|
|
1506
|
+
|
|
1507
|
+
Args:
|
|
1508
|
+
default: Default language code to use if user cancels or enters empty input
|
|
1509
|
+
|
|
1510
|
+
Returns:
|
|
1511
|
+
The selected language code (normalized)
|
|
1512
|
+
|
|
1513
|
+
Raises:
|
|
1514
|
+
KeyboardInterrupt: If user presses Ctrl+C
|
|
1515
|
+
"""
|
|
1516
|
+
from .i18n import get_all_supported_languages, normalize_locale
|
|
1517
|
+
|
|
1518
|
+
# Get all supported languages
|
|
1519
|
+
all_languages = get_all_supported_languages()
|
|
1520
|
+
|
|
1521
|
+
# Build the prompt message
|
|
1522
|
+
console.print()
|
|
1523
|
+
console.print("[bold cyan]Select output language:[/bold cyan]")
|
|
1524
|
+
console.print()
|
|
1525
|
+
|
|
1526
|
+
# Create choices mapping
|
|
1527
|
+
choices = {}
|
|
1528
|
+
for i, (code, name) in enumerate(all_languages, start=1):
|
|
1529
|
+
console.print(f" [cyan][{i}][/cyan] {name} [dim]({code})[/dim]")
|
|
1530
|
+
choices[str(i)] = code
|
|
1531
|
+
|
|
1532
|
+
# Add "Other..." option
|
|
1533
|
+
other_index = str(len(all_languages) + 1)
|
|
1534
|
+
console.print(f" [cyan][{other_index}][/cyan] [italic]Other...[/italic] [dim](enter custom code)[/dim]")
|
|
1535
|
+
console.print()
|
|
1536
|
+
choices[other_index] = None # Marker for custom input
|
|
1537
|
+
|
|
1538
|
+
# Prompt for selection
|
|
1539
|
+
valid_choices = list(choices.keys())
|
|
1540
|
+
selection = Prompt.ask(
|
|
1541
|
+
"Enter choice",
|
|
1542
|
+
default="1",
|
|
1543
|
+
show_choices=False,
|
|
1544
|
+
)
|
|
1545
|
+
|
|
1546
|
+
# Validate input - Prompt.ask doesn't validate when show_choices=False
|
|
1547
|
+
while selection not in valid_choices:
|
|
1548
|
+
console.print(f"[yellow]Invalid choice. Please enter 1-{other_index}.[/yellow]")
|
|
1549
|
+
selection = Prompt.ask(
|
|
1550
|
+
"Enter choice",
|
|
1551
|
+
default="1",
|
|
1552
|
+
show_choices=False,
|
|
1553
|
+
)
|
|
1554
|
+
|
|
1555
|
+
# Handle selection
|
|
1556
|
+
if choices[selection] is None:
|
|
1557
|
+
# "Other..." selected - prompt for custom code
|
|
1558
|
+
custom_code = Prompt.ask(
|
|
1559
|
+
"Enter language code (e.g., ru, ar, hi)",
|
|
1560
|
+
default="",
|
|
1561
|
+
show_default=False,
|
|
1562
|
+
)
|
|
1563
|
+
|
|
1564
|
+
# Edge Case 3: Empty string input -> fallback to default
|
|
1565
|
+
if not custom_code.strip():
|
|
1566
|
+
console.print("[dim]No language code entered, using default (en)[/dim]")
|
|
1567
|
+
return default
|
|
1568
|
+
|
|
1569
|
+
# Normalize the custom code
|
|
1570
|
+
normalized = normalize_locale(custom_code)
|
|
1571
|
+
console.print(f"[dim]Note: Pre-translated content may not be available for '{normalized}'.[/dim]")
|
|
1572
|
+
return normalized
|
|
1573
|
+
|
|
1574
|
+
# Return the selected predefined language
|
|
1575
|
+
return choices[selection]
|
|
1576
|
+
|
|
1577
|
+
|
|
1487
1578
|
def confirm_add_compliance(language: str = "en") -> bool:
|
|
1488
1579
|
"""Ask user whether to add the Constitution Compliance section.
|
|
1489
1580
|
|
|
@@ -164,6 +164,28 @@ def get_supported_languages() -> list[tuple[str, str]]:
|
|
|
164
164
|
return [(code, get_language_name(code)) for code in LANGUAGE_ALIASES.keys()]
|
|
165
165
|
|
|
166
166
|
|
|
167
|
+
# Lazy-loaded list of all supported languages (en + pre-translated)
|
|
168
|
+
_ALL_LANGUAGES_CACHE: list[str] | None = None
|
|
169
|
+
|
|
170
|
+
|
|
171
|
+
def get_all_supported_languages() -> list[tuple[str, str]]:
|
|
172
|
+
"""
|
|
173
|
+
获取所有支持的语言列表(包括 en 和预翻译语言)。
|
|
174
|
+
|
|
175
|
+
Returns:
|
|
176
|
+
List of (code, name) tuples,en 排在首位,随后是预翻译语言
|
|
177
|
+
"""
|
|
178
|
+
global _ALL_LANGUAGES_CACHE
|
|
179
|
+
|
|
180
|
+
if _ALL_LANGUAGES_CACHE is None:
|
|
181
|
+
# Lazy import to avoid circular dependency with translator.py
|
|
182
|
+
from codexspec.translator import SUPPORTED_LANGUAGES
|
|
183
|
+
|
|
184
|
+
_ALL_LANGUAGES_CACHE = ["en"] + list(SUPPORTED_LANGUAGES)
|
|
185
|
+
|
|
186
|
+
return [(code, get_language_name(code)) for code in _ALL_LANGUAGES_CACHE]
|
|
187
|
+
|
|
188
|
+
|
|
167
189
|
# Default config.yml template
|
|
168
190
|
CONFIG_TEMPLATE = """# CodexSpec Configuration
|
|
169
191
|
# This file configures project-level settings for CodexSpec
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|