elijah 0.1.0__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.
@@ -0,0 +1,41 @@
1
+ # Codecov Configuration for Elijah
2
+ # See https://docs.codecov.com/docs/codecov-yaml for full configuration
3
+
4
+ coverage:
5
+ status:
6
+ project:
7
+ default:
8
+ target: 85% # Project-wide coverage target
9
+ threshold: 2% # Allow 2% drop before failing
10
+ if_ci_failed: error # Fail if CI fails
11
+ patch:
12
+ default:
13
+ target: 80% # New code should have 80%+ coverage
14
+ threshold: 5%
15
+ if_ci_failed: error
16
+
17
+ precision: 2 # Show 2 decimal places
18
+ round: down # Round coverage down
19
+ range: "70...95" # Coverage range (red to green)
20
+
21
+ comment:
22
+ layout: "header, diff, flags, components, footer"
23
+ behavior: default # Comment on every PR
24
+ require_changes: false # Always comment, even if no changes
25
+
26
+ flags:
27
+ unittests:
28
+ paths:
29
+ - src/
30
+ carryforward: true # Use previous coverage if job fails
31
+ full-coverage:
32
+ paths:
33
+ - src/
34
+ carryforward: true
35
+
36
+ ignore:
37
+ - "tests/**"
38
+ - "docs/**"
39
+ - "scripts/**"
40
+ - "examples/**"
41
+ - "**/__init__.py"
@@ -0,0 +1,53 @@
1
+ # EditorConfig helps maintain consistent coding styles across different editors and IDEs
2
+ # https://editorconfig.org
3
+
4
+ root = true
5
+
6
+ # Default settings for all files
7
+ [*]
8
+ charset = utf-8
9
+ end_of_line = lf
10
+ insert_final_newline = true
11
+ trim_trailing_whitespace = true
12
+
13
+ # Python files
14
+ [*.py]
15
+ indent_style = space
16
+ indent_size = 4
17
+ max_line_length = 100
18
+
19
+ # YAML files
20
+ [*.{yml,yaml}]
21
+ indent_style = space
22
+ indent_size = 2
23
+
24
+ # TOML files
25
+ [*.toml]
26
+ indent_style = space
27
+ indent_size = 2
28
+
29
+ # Markdown files
30
+ [*.md]
31
+ indent_style = space
32
+ indent_size = 2
33
+ trim_trailing_whitespace = false # Preserve trailing spaces for line breaks
34
+
35
+ # JSON files
36
+ [*.json]
37
+ indent_style = space
38
+ indent_size = 2
39
+
40
+ # Shell scripts
41
+ [*.sh]
42
+ indent_style = space
43
+ indent_size = 2
44
+ end_of_line = lf
45
+
46
+ # Makefiles require tabs
47
+ [Makefile]
48
+ indent_style = tab
49
+
50
+ # GitHub Actions workflows
51
+ [.github/workflows/*.{yml,yaml}]
52
+ indent_style = space
53
+ indent_size = 2
@@ -0,0 +1,136 @@
1
+ name: CHANGELOG Check
2
+
3
+ on:
4
+ pull_request:
5
+ branches: [main]
6
+ types: [opened, synchronize, reopened, labeled, unlabeled]
7
+
8
+ jobs:
9
+ check-changelog:
10
+ name: Verify CHANGELOG Updated
11
+ runs-on: ubuntu-latest
12
+
13
+ steps:
14
+ - name: Checkout code
15
+ uses: actions/checkout@v6
16
+ with:
17
+ fetch-depth: 0 # Need full history to check diff
18
+
19
+ - name: Check for CHANGELOG label
20
+ id: check_label
21
+ run: |
22
+ # Check if PR has skip-changelog label
23
+ SKIP_LABEL=$(gh pr view ${{ github.event.pull_request.number }} --json labels --jq '.labels[].name' | grep -c "skip-changelog" || echo "0")
24
+ echo "skip_label=$SKIP_LABEL" >> $GITHUB_OUTPUT
25
+
26
+ # Check if PR has release:none label (docs/CI only changes)
27
+ RELEASE_NONE=$(gh pr view ${{ github.event.pull_request.number }} --json labels --jq '.labels[].name' | grep -c "release:none" || echo "0")
28
+ echo "release_none=$RELEASE_NONE" >> $GITHUB_OUTPUT
29
+ env:
30
+ GH_TOKEN: ${{ secrets.GITHUB_TOKEN }}
31
+
32
+ - name: Check CHANGELOG.md changes
33
+ id: check_changelog
34
+ run: |
35
+ # Get the base branch
36
+ BASE_SHA=${{ github.event.pull_request.base.sha }}
37
+
38
+ # Check if CHANGELOG.md was modified
39
+ CHANGELOG_MODIFIED=$(git diff --name-only $BASE_SHA..HEAD | grep -c "CHANGELOG.md" || echo "0")
40
+ echo "changelog_modified=$CHANGELOG_MODIFIED" >> $GITHUB_OUTPUT
41
+
42
+ # Check if [Unreleased] section was modified
43
+ if [ "$CHANGELOG_MODIFIED" = "1" ]; then
44
+ # Check if the diff includes changes to [Unreleased] section
45
+ UNRELEASED_MODIFIED=$(git diff $BASE_SHA..HEAD -- CHANGELOG.md | grep -c "^+.*- " || echo "0")
46
+ echo "unreleased_modified=$UNRELEASED_MODIFIED" >> $GITHUB_OUTPUT
47
+ else
48
+ echo "unreleased_modified=0" >> $GITHUB_OUTPUT
49
+ fi
50
+
51
+ - name: Determine if check should pass
52
+ id: determine_result
53
+ run: |
54
+ SKIP_LABEL=${{ steps.check_label.outputs.skip_label }}
55
+ RELEASE_NONE=${{ steps.check_label.outputs.release_none }}
56
+ CHANGELOG_MODIFIED=${{ steps.check_changelog.outputs.changelog_modified }}
57
+ UNRELEASED_MODIFIED=${{ steps.check_changelog.outputs.unreleased_modified }}
58
+
59
+ # Pass if:
60
+ # 1. Has skip-changelog label, OR
61
+ # 2. Has release:none label (docs/CI only), OR
62
+ # 3. CHANGELOG was modified AND [Unreleased] section has new entries
63
+ if [ "$SKIP_LABEL" = "1" ] || [ "$RELEASE_NONE" = "1" ]; then
64
+ echo "result=pass" >> $GITHUB_OUTPUT
65
+ echo "reason=PR is labeled to skip CHANGELOG check" >> $GITHUB_OUTPUT
66
+ elif [ "$CHANGELOG_MODIFIED" = "1" ] && [ "$UNRELEASED_MODIFIED" -gt "0" ]; then
67
+ echo "result=pass" >> $GITHUB_OUTPUT
68
+ echo "reason=CHANGELOG [Unreleased] section was updated" >> $GITHUB_OUTPUT
69
+ else
70
+ echo "result=fail" >> $GITHUB_OUTPUT
71
+ if [ "$CHANGELOG_MODIFIED" = "0" ]; then
72
+ echo "reason=CHANGELOG.md was not modified" >> $GITHUB_OUTPUT
73
+ else
74
+ echo "reason=CHANGELOG.md was modified but [Unreleased] section appears unchanged" >> $GITHUB_OUTPUT
75
+ fi
76
+ fi
77
+
78
+ - name: Post comment if check fails
79
+ if: steps.determine_result.outputs.result == 'fail'
80
+ run: |
81
+ REASON="${{ steps.determine_result.outputs.reason }}"
82
+
83
+ gh pr comment ${{ github.event.pull_request.number }} --body "## ⚠️ CHANGELOG Check Failed
84
+
85
+ **Reason:** $REASON
86
+
87
+ ### How to fix:
88
+
89
+ 1. **Update CHANGELOG.md** - Add your changes to the \`[Unreleased]\` section:
90
+ \`\`\`markdown
91
+ ## [Unreleased]
92
+
93
+ ### Added
94
+ - Your new feature
95
+
96
+ ### Fixed
97
+ - Your bug fix
98
+
99
+ ### Changed
100
+ - Your modification
101
+ \`\`\`
102
+
103
+ 2. **OR add a label** if CHANGELOG update is not needed:
104
+ - Add \`skip-changelog\` label for exceptional cases
105
+ - Add \`release:none\` label for docs/CI-only changes
106
+
107
+ ### Guidelines:
108
+
109
+ - **DO update CHANGELOG for:**
110
+ - New features
111
+ - Bug fixes
112
+ - Breaking changes
113
+ - Deprecations
114
+
115
+ - **DON'T update CHANGELOG for:**
116
+ - Documentation-only changes (use \`release:none\` label)
117
+ - CI/CD configuration (use \`release:none\` label)
118
+ - Test-only changes (use \`release:none\` label)
119
+
120
+ See [CONTRIBUTING.md](https://github.com/${{ github.repository }}/blob/main/CONTRIBUTING.md) for more details.
121
+ "
122
+ env:
123
+ GH_TOKEN: ${{ secrets.GITHUB_TOKEN }}
124
+
125
+ - name: Fail if check didn't pass
126
+ if: steps.determine_result.outputs.result == 'fail'
127
+ run: |
128
+ echo "❌ ${{ steps.determine_result.outputs.reason }}"
129
+ echo ""
130
+ echo "Please update CHANGELOG.md [Unreleased] section or add skip-changelog/release:none label."
131
+ exit 1
132
+
133
+ - name: Success
134
+ if: steps.determine_result.outputs.result == 'pass'
135
+ run: |
136
+ echo "✅ ${{ steps.determine_result.outputs.reason }}"
@@ -0,0 +1,16 @@
1
+ name: Publish
2
+
3
+ on:
4
+ release:
5
+ types: [published]
6
+
7
+ jobs:
8
+ publish:
9
+ runs-on: ubuntu-latest
10
+ permissions:
11
+ id-token: write
12
+ steps:
13
+ - uses: actions/checkout@v6
14
+ - uses: astral-sh/setup-uv@v7
15
+ - run: uv build
16
+ - run: uv publish
@@ -0,0 +1,177 @@
1
+ name: Test Suite
2
+
3
+ on:
4
+ push:
5
+ branches: ["main"]
6
+ pull_request:
7
+ branches: ["main"]
8
+
9
+ jobs:
10
+ test:
11
+ name: Test Python ${{ matrix.python-version }} on ${{ matrix.os }}
12
+ runs-on: ${{ matrix.os }}
13
+ strategy:
14
+ fail-fast: false
15
+ matrix:
16
+ os: [ubuntu-latest, macos-latest, windows-latest]
17
+ python-version: ["3.13"]
18
+
19
+ steps:
20
+ - name: Checkout code
21
+ uses: actions/checkout@v6
22
+
23
+ - name: Install uv
24
+ uses: astral-sh/setup-uv@v7
25
+ with:
26
+ enable-cache: true
27
+
28
+ - name: Set up Python ${{ matrix.python-version }}
29
+ uses: actions/setup-python@v6
30
+ with:
31
+ python-version: ${{ matrix.python-version }}
32
+
33
+ - name: Install dependencies
34
+ run: uv sync --all-extras
35
+
36
+ - name: Run unit tests
37
+ run: uv run pytest tests/ --cov=src --cov-branch --cov-report=xml --cov-report=term --junitxml=test-results-unit.xml
38
+
39
+ - name: Upload coverage to Codecov
40
+ uses: codecov/codecov-action@v5
41
+ if: matrix.os == 'ubuntu-latest' && matrix.python-version == '3.13'
42
+ with:
43
+ token: ${{ secrets.CODECOV_TOKEN }}
44
+ file: ./coverage.xml
45
+ flags: unittests
46
+ name: codecov-umbrella
47
+ fail_ci_if_error: false
48
+
49
+ - name: Upload test results to Codecov
50
+ uses: codecov/codecov-action@v5
51
+ if: always()
52
+ with:
53
+ token: ${{ secrets.CODECOV_TOKEN }}
54
+ files: test-results-unit.xml
55
+ flags: ${{ matrix.os }}-py${{ matrix.python-version }}
56
+ report_type: test_results
57
+ fail_ci_if_error: false
58
+
59
+ lint:
60
+ name: Lint and Format Check
61
+ runs-on: ubuntu-latest
62
+
63
+ steps:
64
+ - name: Checkout code
65
+ uses: actions/checkout@v6
66
+
67
+ - name: Install uv
68
+ uses: astral-sh/setup-uv@v7
69
+
70
+ - name: Set up Python
71
+ uses: actions/setup-python@v6
72
+ with:
73
+ python-version: "3.13"
74
+
75
+ - name: Install dependencies
76
+ run: uv sync --all-extras
77
+
78
+ - name: Check code formatting
79
+ run: uv run ruff format --check .
80
+
81
+ - name: Lint code
82
+ run: uv run ruff check .
83
+
84
+ type-check:
85
+ name: Type Checking (mypy)
86
+ runs-on: ubuntu-latest
87
+
88
+ steps:
89
+ - name: Checkout code
90
+ uses: actions/checkout@v6
91
+
92
+ - name: Install uv
93
+ uses: astral-sh/setup-uv@v7
94
+
95
+ - name: Set up Python
96
+ uses: actions/setup-python@v6
97
+ with:
98
+ python-version: "3.13"
99
+
100
+ - name: Install dependencies
101
+ run: uv sync --all-extras
102
+
103
+ - name: Run mypy type checker
104
+ run: uv run mypy src/elijah --strict-optional --show-error-codes
105
+
106
+ security:
107
+ name: Security Scanning
108
+ runs-on: ubuntu-latest
109
+
110
+ steps:
111
+ - name: Checkout code
112
+ uses: actions/checkout@v6
113
+
114
+ - name: Install uv
115
+ uses: astral-sh/setup-uv@v7
116
+
117
+ - name: Set up Python
118
+ uses: actions/setup-python@v6
119
+ with:
120
+ python-version: "3.13"
121
+
122
+ - name: Install dependencies
123
+ run: uv sync --all-extras
124
+
125
+ - name: Run bandit security scanner
126
+ run: uv run bandit -c pyproject.toml -r src/
127
+
128
+ coverage:
129
+ name: Coverage Report
130
+ runs-on: ubuntu-latest
131
+
132
+ steps:
133
+ - name: Checkout code
134
+ uses: actions/checkout@v6
135
+
136
+ - name: Install uv
137
+ uses: astral-sh/setup-uv@v7
138
+
139
+ - name: Set up Python
140
+ uses: actions/setup-python@v6
141
+ with:
142
+ python-version: "3.13"
143
+
144
+ - name: Install dependencies
145
+ run: uv sync --all-extras
146
+
147
+ - name: Run tests with coverage
148
+ run: uv run pytest tests/ --cov=src --cov-branch --cov-report=term --cov-report=html --cov-report=xml --junitxml=test-results-full.xml
149
+
150
+ - name: Check coverage threshold
151
+ run: |
152
+ uv run coverage report --fail-under=85 || echo "Coverage below 85% - expected during initial development"
153
+
154
+ - name: Upload coverage to Codecov
155
+ uses: codecov/codecov-action@v5
156
+ with:
157
+ token: ${{ secrets.CODECOV_TOKEN }}
158
+ file: ./coverage.xml
159
+ flags: full-coverage
160
+ name: codecov-full
161
+ fail_ci_if_error: false
162
+
163
+ - name: Upload test results to Codecov
164
+ uses: codecov/codecov-action@v5
165
+ if: always()
166
+ with:
167
+ token: ${{ secrets.CODECOV_TOKEN }}
168
+ files: test-results-full.xml
169
+ flags: full-suite
170
+ report_type: test_results
171
+ fail_ci_if_error: false
172
+
173
+ - name: Upload coverage artifacts
174
+ uses: actions/upload-artifact@v4
175
+ with:
176
+ name: coverage-report
177
+ path: htmlcov/
@@ -0,0 +1,46 @@
1
+ # Python-generated files
2
+ __pycache__/
3
+ *.py[oc]
4
+ build/
5
+ dist/
6
+ wheels/
7
+ *.egg-info
8
+
9
+ # Virtual environments
10
+ .venv
11
+ venv/
12
+ env/
13
+
14
+ # Testing
15
+ .pytest_cache/
16
+ .coverage
17
+ coverage.xml
18
+ htmlcov/
19
+ test-results*.xml
20
+ *.cover
21
+ .hypothesis/
22
+
23
+ # Type checking
24
+ .mypy_cache/
25
+ .dmypy.json
26
+ dmypy.json
27
+
28
+ # Ruff
29
+ .ruff_cache/
30
+
31
+ # IDEs
32
+ .vscode/
33
+ .idea/
34
+ *.swp
35
+ *.swo
36
+ *~
37
+ .DS_Store
38
+
39
+ # Documentation
40
+ site/
41
+ docs/_build/
42
+
43
+ # Other
44
+ *.log
45
+ .env
46
+ .env.local
@@ -0,0 +1,92 @@
1
+ # Pre-commit hooks for Elijah
2
+ # Install: pip install pre-commit && pre-commit install
3
+ # Run manually: pre-commit run --all-files
4
+ # Update hooks: pre-commit autoupdate
5
+
6
+ repos:
7
+ # Ruff - Fast Python linter and formatter
8
+ - repo: https://github.com/astral-sh/ruff-pre-commit
9
+ rev: v0.8.4
10
+ hooks:
11
+ # Run the linter
12
+ - id: ruff
13
+ args: [--fix, --exit-non-zero-on-fix]
14
+ types_or: [python, pyi]
15
+ # Run the formatter
16
+ - id: ruff-format
17
+ types_or: [python, pyi]
18
+
19
+ # Type checking with mypy
20
+ - repo: https://github.com/pre-commit/mirrors-mypy
21
+ rev: v1.13.0
22
+ hooks:
23
+ - id: mypy
24
+ args: [--ignore-missing-imports, --no-strict-optional]
25
+ exclude: ^(tests/|docs/)
26
+
27
+ # Built-in pre-commit hooks
28
+ - repo: https://github.com/pre-commit/pre-commit-hooks
29
+ rev: v5.0.0
30
+ hooks:
31
+ # General file checks
32
+ - id: trailing-whitespace
33
+ args: [--markdown-linebreak-ext=md]
34
+ - id: end-of-file-fixer
35
+ - id: check-yaml
36
+ exclude: ^\.github/workflows/
37
+ - id: check-toml
38
+ - id: check-json
39
+ - id: check-added-large-files
40
+ args: [--maxkb=1000]
41
+ - id: check-merge-conflict
42
+ - id: check-case-conflict
43
+ - id: mixed-line-ending
44
+ args: [--fix=lf]
45
+
46
+ # Python-specific checks
47
+ - id: check-docstring-first
48
+ - id: check-ast
49
+ - id: debug-statements
50
+ - id: name-tests-test
51
+ args: [--pytest-test-first]
52
+ exclude: ^tests/(conftest\.py|fixtures/|helpers/)
53
+
54
+ # Security checks
55
+ - id: detect-private-key
56
+
57
+ # Security vulnerability scanning
58
+ - repo: https://github.com/PyCQA/bandit
59
+ rev: 1.8.0
60
+ hooks:
61
+ - id: bandit
62
+ args: [-c, pyproject.toml, -r, src/]
63
+ additional_dependencies: ["bandit[toml]"]
64
+
65
+ # Markdown linting
66
+ - repo: https://github.com/igorshubovych/markdownlint-cli
67
+ rev: v0.43.0
68
+ hooks:
69
+ - id: markdownlint
70
+ args: [--fix]
71
+ exclude: ^(docs/session-.*\.md|CHANGELOG\.md)
72
+
73
+ # YAML formatting
74
+ - repo: https://github.com/macisamuele/language-formatters-pre-commit-hooks
75
+ rev: v2.14.0
76
+ hooks:
77
+ - id: pretty-format-yaml
78
+ args: [--autofix, --indent, '2']
79
+ exclude: ^\.github/workflows/
80
+
81
+ # Configuration for specific hooks
82
+ ci:
83
+ autofix_commit_msg: |
84
+ [pre-commit.ci] auto fixes from pre-commit.com hooks
85
+
86
+ for more information, see https://pre-commit.ci
87
+ autofix_prs: true
88
+ autoupdate_branch: ''
89
+ autoupdate_commit_msg: '[pre-commit.ci] pre-commit autoupdate'
90
+ autoupdate_schedule: weekly
91
+ skip: [mypy] # Skip mypy in pre-commit.ci (too slow)
92
+ submodules: false
@@ -0,0 +1 @@
1
+ 3.13
@@ -0,0 +1,30 @@
1
+ # Changelog
2
+
3
+ All notable changes to this project will be documented in this file.
4
+
5
+ The format is based on [Keep a Changelog](https://keepachangelog.com/en/1.0.0/),
6
+ and this project adheres to [Semantic Versioning](https://semver.org/spec/v2.0.0.html).
7
+
8
+ ## [Unreleased]
9
+
10
+ ### Added
11
+
12
+ - Initial project structure with Python 3.13 support
13
+ - Comprehensive CI/CD pipeline with GitHub Actions
14
+ - Test suite with pytest and coverage reporting
15
+ - Code quality tools (ruff, mypy, bandit)
16
+ - Pre-commit hooks for code quality
17
+ - Documentation infrastructure with MkDocs
18
+ - PyPI publishing workflow with uv
19
+ - Makefile for common development tasks
20
+
21
+ ## [0.1.0] - 2026-02-07
22
+
23
+ ### Added
24
+
25
+ - Initial release
26
+ - Basic project structure
27
+ - CLI entry point
28
+
29
+ [Unreleased]: https://github.com/DecisionNerd/elijah/compare/v0.1.0...HEAD
30
+ [0.1.0]: https://github.com/DecisionNerd/elijah/releases/tag/v0.1.0