corclient 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,104 @@
1
+ name: Update Homebrew Formula
2
+
3
+ on:
4
+ release:
5
+ types: [published]
6
+ workflow_dispatch:
7
+ inputs:
8
+ version:
9
+ description: 'Version to update formula for'
10
+ required: true
11
+ type: string
12
+
13
+ jobs:
14
+ update-formula:
15
+ name: Update Homebrew Formula
16
+ runs-on: ubuntu-latest
17
+ permissions:
18
+ contents: write
19
+ steps:
20
+ - name: Checkout repository
21
+ uses: actions/checkout@v4
22
+ with:
23
+ fetch-depth: 0
24
+
25
+ - name: Get release info
26
+ id: release
27
+ run: |
28
+ if [ "${{ github.event_name }}" == "release" ]; then
29
+ VERSION="${{ github.event.release.tag_name }}"
30
+ VERSION="${VERSION#v}" # Remove 'v' prefix if present
31
+ else
32
+ VERSION="${{ inputs.version }}"
33
+ fi
34
+ echo "version=${VERSION}" >> $GITHUB_OUTPUT
35
+
36
+ # Wait a bit for PyPI to have the package available
37
+ sleep 30
38
+
39
+ # Download the tarball from PyPI
40
+ wget "https://files.pythonhosted.org/packages/source/c/corclient/corclient-${VERSION}.tar.gz"
41
+
42
+ # Calculate SHA256
43
+ SHA256=$(sha256sum "corclient-${VERSION}.tar.gz" | awk '{print $1}')
44
+ echo "sha256=${SHA256}" >> $GITHUB_OUTPUT
45
+
46
+ - name: Update Formula
47
+ run: |
48
+ VERSION="${{ steps.release.outputs.version }}"
49
+ SHA256="${{ steps.release.outputs.sha256 }}"
50
+
51
+ cat > HomebrewFormula/corclient.rb << EOF
52
+ class Corclient < Formula
53
+ include Language::Python::Virtualenv
54
+
55
+ desc "Internal CLI tool for microservices management and infrastructure administration"
56
+ homepage "https://github.com/ProjectCORTeam/corcli"
57
+ url "https://files.pythonhosted.org/packages/source/c/corclient/corclient-${VERSION}.tar.gz"
58
+ sha256 "${SHA256}"
59
+ license "MIT"
60
+
61
+ depends_on "python@3.11"
62
+
63
+ resource "typer" do
64
+ url "https://files.pythonhosted.org/packages/source/t/typer/typer-0.12.5.tar.gz"
65
+ sha256 "f592f089bedcc8ec1b974125d64851029c3b1af145f04aca64d69410f0c9b722"
66
+ end
67
+
68
+ resource "rich" do
69
+ url "https://files.pythonhosted.org/packages/source/r/rich/rich-13.7.1.tar.gz"
70
+ sha256 "9be308cb1fe2f1f57d67ce99e95af38a1e2bc71ad9813b0e247cf7ffbcc3a432"
71
+ end
72
+
73
+ resource "click" do
74
+ url "https://files.pythonhosted.org/packages/source/c/click/click-8.1.7.tar.gz"
75
+ sha256 "ca9853ad459e787e2192211578cc907e7594e294c7ccc834310722b41b9ca6de"
76
+ end
77
+
78
+ resource "flask" do
79
+ url "https://files.pythonhosted.org/packages/source/f/flask/flask-3.0.3.tar.gz"
80
+ sha256 "ceb27b0af3823ea2737928a4d99d125a06175b8512c445cbd9a9ce200ef76842"
81
+ end
82
+
83
+ resource "requests" do
84
+ url "https://files.pythonhosted.org/packages/source/r/requests/requests-2.31.0.tar.gz"
85
+ sha256 "942c5a758f98d5e85e407a9981bdc7c9f82e2e1b9f8e6c2f4f4f4f4f4f4f4f4f"
86
+ end
87
+
88
+ def install
89
+ virtualenv_install_with_resources
90
+ end
91
+
92
+ test do
93
+ assert_match "CoreCLI", shell_output("#{bin}/cor --help")
94
+ end
95
+ end
96
+ EOF
97
+
98
+ - name: Commit and push formula
99
+ run: |
100
+ git config user.name "github-actions[bot]"
101
+ git config user.email "github-actions[bot]@users.noreply.github.com"
102
+ git add HomebrewFormula/corclient.rb
103
+ git commit -m "chore: update Homebrew formula to ${{ steps.release.outputs.version }}" || echo "No changes to commit"
104
+ git push
@@ -0,0 +1,50 @@
1
+ name: "Validate PR title"
2
+
3
+ on:
4
+ pull_request_target:
5
+ types:
6
+ - opened
7
+ - edited
8
+ - synchronize
9
+
10
+ jobs:
11
+ main:
12
+ name: Validate PR title
13
+ runs-on: ubuntu-latest
14
+ steps:
15
+ - uses: amannn/action-semantic-pull-request@v4
16
+ env:
17
+ GITHUB_TOKEN: ${{ secrets.ACTIONS_TOKEN }}
18
+ with:
19
+ # Configure which types are allowed.
20
+ # Default: https://github.com/commitizen/conventional-commit-types
21
+ types: |
22
+ fix
23
+ feat
24
+ docs
25
+ ci
26
+ chore
27
+ # Configure that a scope must always be provided.
28
+ requireScope: false
29
+ # Configure additional validation for the subject based on a regex.
30
+ # This example ensures the subject starts with an uppercase character.
31
+ subjectPattern: ^[a-zA-Z].+$
32
+ # If `subjectPattern` is configured, you can use this property to override
33
+ # the default error message that is shown when the pattern doesn't match.
34
+ # The variables `subject` and `title` can be used within the message.
35
+ subjectPatternError: |
36
+ The subject "{subject}" found in the pull request title "{title}"
37
+ didn't match the configured pattern. Please ensure that the subject
38
+ starts with an uppercase character.
39
+ # For work-in-progress PRs you can typically use draft pull requests
40
+ # from Github. However, private repositories on the free plan don't have
41
+ # this option and therefore this action allows you to opt-in to using the
42
+ # special "[WIP]" prefix to indicate this state. This will avoid the
43
+ # validation of the PR title and the pull request checks remain pending.
44
+ # Note that a second check will be reported if this is enabled.
45
+ wip: true
46
+ # When using "Squash and merge" on a PR with only one commit, GitHub
47
+ # will suggest using that commit message instead of the PR title for the
48
+ # merge commit, and it's easy to commit this by mistake. Enable this option
49
+ # to also validate the commit message for one commit PRs.
50
+ validateSingleCommit: false
@@ -0,0 +1,49 @@
1
+ name: Publish to PyPI
2
+
3
+ on:
4
+ workflow_dispatch:
5
+ workflow_call: # Allow being called from other workflows
6
+ release:
7
+ types: [published]
8
+ push:
9
+ tags:
10
+ - 'v*'
11
+
12
+ jobs:
13
+ build-and-publish:
14
+ name: Build and publish package
15
+ runs-on: ubuntu-latest
16
+ permissions:
17
+ contents: read
18
+ id-token: write # IMPORTANT: mandatory for trusted publishing
19
+ steps:
20
+ - name: Checkout
21
+ uses: actions/checkout@v4
22
+ with:
23
+ fetch-depth: 0 # Fetch all history and tags for setuptools-scm
24
+
25
+ - name: Set up Python
26
+ uses: actions/setup-python@v5
27
+ with:
28
+ python-version: '3.11'
29
+
30
+ - name: Upgrade pip and install build tooling
31
+ run: |
32
+ python -m pip install --upgrade pip
33
+ pip install --upgrade setuptools wheel build twine
34
+
35
+ - name: Build sdist and wheel
36
+ run: |
37
+ python -m build
38
+
39
+ - name: Verify package metadata
40
+ run: |
41
+ twine check dist/*
42
+
43
+ - name: Publish to PyPI
44
+ if: github.event_name == 'workflow_dispatch' || github.event_name == 'release' || startsWith(github.ref, 'refs/tags/v')
45
+ uses: pypa/gh-action-pypi-publish@release/v1
46
+ with:
47
+ # No password needed - uses OIDC trusted publishing
48
+ skip-existing: true
49
+
@@ -0,0 +1,106 @@
1
+ name: Release
2
+
3
+ on:
4
+ workflow_dispatch:
5
+ push:
6
+ branches:
7
+ - master
8
+ - beta
9
+ paths:
10
+ - '**/*'
11
+ - '.github/workflows/release.yml'
12
+
13
+ jobs:
14
+ release:
15
+ name: Release
16
+ runs-on: ubuntu-latest
17
+ # Skip running release workflow on forks
18
+ if: github.repository_owner == 'ProjectCORTeam'
19
+ outputs:
20
+ new_release_published: ${{ steps.semantic.outputs.new_release_published }}
21
+ new_release_version: ${{ steps.semantic.outputs.new_release_version }}
22
+ steps:
23
+ - name: Checkout
24
+ uses: actions/checkout@v3
25
+ with:
26
+ persist-credentials: false
27
+ fetch-depth: 0
28
+
29
+ - name: Set up Python
30
+ uses: actions/setup-python@v5
31
+ with:
32
+ python-version: '3.11'
33
+
34
+ - name: Install dependencies
35
+ run: |
36
+ python -m pip install --upgrade pip
37
+ pip install build twine ruff black mypy types-requests
38
+
39
+ - name: Run linting (Ruff)
40
+ run: |
41
+ ruff check corecli/
42
+
43
+ - name: Check code formatting (Black)
44
+ run: |
45
+ black --check corecli/
46
+
47
+ - name: Run type checking (MyPy)
48
+ run: |
49
+ mypy corecli/
50
+
51
+ - name: Verify package can be built
52
+ run: |
53
+ python -m build
54
+ twine check dist/*
55
+
56
+ - name: Clean build artifacts
57
+ run: |
58
+ rm -rf dist/ build/ *.egg-info
59
+
60
+ - name: Release
61
+ id: semantic
62
+ uses: cycjimmy/semantic-release-action@v3
63
+ env:
64
+ GITHUB_TOKEN: ${{ secrets.ACTIONS_TOKEN }}
65
+ with:
66
+ branches: |
67
+ [
68
+ '+([0-9])?(.{+([0-9]),x}).x',
69
+ 'master',
70
+ 'next',
71
+ 'next-major',
72
+ {
73
+ name: 'beta',
74
+ prerelease: true
75
+ }
76
+ ]
77
+ semantic_version: 18.0.0
78
+ extra_plugins: |
79
+ @semantic-release/changelog@6.0.0
80
+ @semantic-release/git@10.0.0
81
+ conventional-changelog-conventionalcommits@4.6.3
82
+
83
+ - name: Do something when a new release published
84
+ if: steps.semantic.outputs.new_release_published == 'true'
85
+ run: |
86
+ echo ${{ steps.semantic.outputs.new_release_version }}
87
+ echo ${{ steps.semantic.outputs.new_release_major_version }}
88
+ echo ${{ steps.semantic.outputs.new_release_minor_version }}
89
+ echo ${{ steps.semantic.outputs.new_release_patch_version }}
90
+
91
+ - name: Google Chat Notification
92
+ uses: nakamuraos/google-chat-notifications@v2.0.1
93
+ with:
94
+ title: Release
95
+ subtitle: ${{ steps.semantic.outputs.new_release_version }}
96
+ webhookUrl: ${{ secrets.GOOGLE_WEBHOOK }}
97
+ status: ${{ job.status }}
98
+ if: always()
99
+
100
+ # Publish to PyPI after creating release
101
+ publish-pypi:
102
+ name: Publish to PyPI
103
+ needs: release
104
+ if: needs.release.outputs.new_release_published == 'true'
105
+ uses: ./.github/workflows/pypi-release.yaml
106
+ secrets: inherit
@@ -0,0 +1,10 @@
1
+ # Python-generated files
2
+ __pycache__/
3
+ *.py[oc]
4
+ build/
5
+ dist/
6
+ wheels/
7
+ *.egg-info
8
+
9
+ # Virtual environments
10
+ .venv
@@ -0,0 +1,29 @@
1
+ repos:
2
+ - repo: https://github.com/astral-sh/ruff-pre-commit
3
+ rev: v0.1.9
4
+ hooks:
5
+ - id: ruff
6
+ args: [--fix, --exit-non-zero-on-fix]
7
+ - id: ruff-format
8
+
9
+ - repo: https://github.com/psf/black
10
+ rev: 24.1.1
11
+ hooks:
12
+ - id: black
13
+ language_version: python3.11
14
+
15
+ - repo: https://github.com/pre-commit/pre-commit-hooks
16
+ rev: v4.5.0
17
+ hooks:
18
+ - id: trailing-whitespace
19
+ - id: end-of-file-fixer
20
+ - id: check-yaml
21
+ - id: check-added-large-files
22
+ - id: check-merge-conflict
23
+ - id: check-toml
24
+
25
+ - repo: https://github.com/pre-commit/mirrors-mypy
26
+ rev: v1.8.0
27
+ hooks:
28
+ - id: mypy
29
+ additional_dependencies: [types-requests]
@@ -0,0 +1,30 @@
1
+ {
2
+ "branches": [
3
+ "+([0-9])?(.{+([0-9]),x}).x",
4
+ "master",
5
+ "next",
6
+ "next-major",
7
+ {
8
+ "name": "beta",
9
+ "prerelease": true
10
+ }
11
+ ],
12
+ "plugins": [
13
+ "@semantic-release/commit-analyzer",
14
+ "@semantic-release/release-notes-generator",
15
+ "@semantic-release/changelog",
16
+ [
17
+ "@semantic-release/git",
18
+ {
19
+ "assets": ["CHANGELOG.md"],
20
+ "message": "chore(release): ${nextRelease.version} [skip ci]\n\n${nextRelease.notes}"
21
+ }
22
+ ],
23
+ [
24
+ "@semantic-release/github",
25
+ {
26
+ "assets": []
27
+ }
28
+ ]
29
+ ]
30
+ }
@@ -0,0 +1,10 @@
1
+ # 1.0.0 (2025-09-30)
2
+
3
+
4
+ ### Features
5
+
6
+ * add linting and code quality tools ([a0a8a28](https://github.com/ProjectCORTeam/corcli/commit/a0a8a28f310005ddc3de4bf3dcb11c2722f2faf8))
7
+ * add linting and code quality tools ([e5ee76d](https://github.com/ProjectCORTeam/corcli/commit/e5ee76d89a853f83b6681c30756c0207b34aa469))
8
+ * configure semantic-release for Python project ([6944590](https://github.com/ProjectCORTeam/corcli/commit/6944590667bf498fea5c9938b35b3a16659f40cc))
9
+ * configure semantic-release for Python with setuptools-scm ([b43fea1](https://github.com/ProjectCORTeam/corcli/commit/b43fea15f4d658f2cc8209a42ef770a86f257494))
10
+ * initial version ([deac096](https://github.com/ProjectCORTeam/corcli/commit/deac0960690fdf43208efcd893472ce3f95283ee))
@@ -0,0 +1,196 @@
1
+ # Homebrew Distribution Guide
2
+
3
+ This guide explains how to install `corclient` via Homebrew using the same repository as a custom Tap.
4
+
5
+ ## 🍺 Installation
6
+
7
+ ### For Users
8
+
9
+ Users can install `corclient` directly from this repository:
10
+
11
+ ```bash
12
+ # Add the tap (one-time setup)
13
+ brew tap ProjectCORTeam/corcli https://github.com/ProjectCORTeam/corcli.git
14
+
15
+ # Install corclient
16
+ brew install corclient
17
+
18
+ # Or in one command
19
+ brew install ProjectCORTeam/corcli/corclient
20
+ ```
21
+
22
+ ### Update
23
+
24
+ ```bash
25
+ brew update
26
+ brew upgrade corclient
27
+ ```
28
+
29
+ ### Uninstall
30
+
31
+ ```bash
32
+ brew uninstall corclient
33
+ brew untap ProjectCORTeam/corcli
34
+ ```
35
+
36
+ ## 🔧 How It Works
37
+
38
+ This repository serves dual purposes:
39
+ 1. **Source code repository** - Contains the Python package code
40
+ 2. **Homebrew Tap** - Contains Homebrew formulae in `HomebrewFormula/`
41
+
42
+ When users tap this repository, Homebrew looks for formulae in the `HomebrewFormula/` directory.
43
+
44
+ ## 🚀 Automated Updates
45
+
46
+ The workflow `.github/workflows/homebrew-formula.yaml` automatically:
47
+
48
+ 1. **Triggers when a GitHub Release is published**
49
+ 2. **Downloads the tarball from PyPI**
50
+ 3. **Calculates the SHA256 hash**
51
+ 4. **Updates the Homebrew formula** in `HomebrewFormula/corclient.rb`
52
+ 5. **Commits and pushes to the repository**
53
+
54
+ No separate repository needed!
55
+
56
+ ## 📦 Manual Formula Update
57
+
58
+ If you need to manually update the formula:
59
+
60
+ ```bash
61
+ # 1. Get the version and tarball
62
+ VERSION="1.0.0"
63
+ wget "https://files.pythonhosted.org/packages/source/c/corclient/corclient-${VERSION}.tar.gz"
64
+
65
+ # 2. Calculate SHA256
66
+ SHA256=$(sha256sum corclient-${VERSION}.tar.gz | awk '{print $1}')
67
+
68
+ # 3. Update HomebrewFormula/corclient.rb
69
+ # Replace the url and sha256 values
70
+
71
+ # 4. Test the formula
72
+ brew install --build-from-source ./HomebrewFormula/corclient.rb
73
+
74
+ # 5. Commit and push
75
+ git add HomebrewFormula/corclient.rb
76
+ git commit -m "chore: update Homebrew formula to ${VERSION}"
77
+ git push
78
+ ```
79
+
80
+ ## 🧪 Testing
81
+
82
+ ### Local Testing
83
+
84
+ ```bash
85
+ # Test installation from local formula
86
+ brew install --build-from-source ./HomebrewFormula/corclient.rb
87
+
88
+ # Verify it works
89
+ cor --help
90
+
91
+ # Run formula audit
92
+ brew audit --strict ./HomebrewFormula/corclient.rb
93
+
94
+ # Test uninstall
95
+ brew uninstall corclient
96
+ ```
97
+
98
+ ### Test the Tap
99
+
100
+ ```bash
101
+ # Add your local repo as a tap
102
+ brew tap ProjectCORTeam/corcli /Users/carlos/Documents/04-Repositories/COR/corcli-cli
103
+
104
+ # Install from the tap
105
+ brew install corclient
106
+
107
+ # Test
108
+ cor --help
109
+
110
+ # Clean up
111
+ brew uninstall corclient
112
+ brew untap ProjectCORTeam/corcli
113
+ ```
114
+
115
+ ## 📝 Repository Structure
116
+
117
+ ```
118
+ corcli/
119
+ ├── corecli/ # Python package source
120
+ ├── HomebrewFormula/ # Homebrew formulae directory
121
+ │ └── corclient.rb # Homebrew formula
122
+ ├── .github/workflows/
123
+ │ ├── pypi-release.yaml # PyPI publication
124
+ │ ├── homebrew-formula.yaml # Auto-update Homebrew formula
125
+ │ └── release.yaml # Semantic release
126
+ ├── pyproject.toml # Python package config
127
+ └── README.md # Main documentation
128
+ ```
129
+
130
+ ## 🔍 Troubleshooting
131
+
132
+ ### Formula Not Found
133
+
134
+ ```bash
135
+ # Re-add the tap
136
+ brew untap ProjectCORTeam/corcli
137
+ brew tap ProjectCORTeam/corcli https://github.com/ProjectCORTeam/corcli.git
138
+ ```
139
+
140
+ ### Installation Fails
141
+
142
+ 1. Check Python version: `brew info python@3.11`
143
+ 2. Clear cache: `brew cleanup`
144
+ 3. Try with verbose output: `brew install corclient --verbose`
145
+
146
+ ### Version Not Updating
147
+
148
+ ```bash
149
+ # Force update the tap
150
+ brew update
151
+ brew upgrade corclient
152
+
153
+ # Or reinstall
154
+ brew reinstall corclient
155
+ ```
156
+
157
+ ## 📚 Adding the Tap to README
158
+
159
+ Add this section to your main README.md:
160
+
161
+ ```markdown
162
+ ### Install via Homebrew
163
+
164
+ \`\`\`bash
165
+ # Add the tap
166
+ brew tap ProjectCORTeam/corcli https://github.com/ProjectCORTeam/corcli.git
167
+
168
+ # Install
169
+ brew install corclient
170
+ \`\`\`
171
+
172
+ ### Update
173
+
174
+ \`\`\`bash
175
+ brew update
176
+ brew upgrade corclient
177
+ \`\`\`
178
+ ```
179
+
180
+ ## 🎯 Advantages of Single Repository
181
+
182
+ ✅ **Simplified maintenance** - One repository to manage
183
+ ✅ **Synchronized versioning** - Formula updates with releases
184
+ ✅ **Automatic updates** - Workflow handles everything
185
+ ✅ **No extra setup** - No separate tap repository needed
186
+ ✅ **Single source of truth** - Code and distribution in one place
187
+
188
+ ## 🔗 Resources
189
+
190
+ - [Homebrew Taps](https://docs.brew.sh/Taps)
191
+ - [Formula Cookbook](https://docs.brew.sh/Formula-Cookbook)
192
+ - [Python Formula Guide](https://docs.brew.sh/Python-for-Formula-Authors)
193
+
194
+ ---
195
+
196
+ **Note**: The formula directory MUST be named `HomebrewFormula/` (or `Formula/`) for Homebrew to recognize it as a tap.
@@ -0,0 +1,39 @@
1
+ class Corclient < Formula
2
+ include Language::Python::Virtualenv
3
+
4
+ desc "Internal CLI tool for microservices management and infrastructure administration"
5
+ homepage "https://github.com/ProjectCORTeam/corcli"
6
+ url "https://files.pythonhosted.org/packages/source/c/corclient/corclient-VERSION.tar.gz"
7
+ sha256 "SHA256_HASH"
8
+ license "MIT"
9
+
10
+ depends_on "python@3.11"
11
+
12
+ resource "typer" do
13
+ url "https://files.pythonhosted.org/packages/source/t/typer/typer-0.12.0.tar.gz"
14
+ sha256 "TODO: Add actual hash"
15
+ end
16
+
17
+ resource "rich" do
18
+ url "https://files.pythonhosted.org/packages/source/r/rich/rich-13.7.0.tar.gz"
19
+ sha256 "TODO: Add actual hash"
20
+ end
21
+
22
+ resource "flask" do
23
+ url "https://files.pythonhosted.org/packages/source/f/flask/flask-3.0.0.tar.gz"
24
+ sha256 "TODO: Add actual hash"
25
+ end
26
+
27
+ resource "requests" do
28
+ url "https://files.pythonhosted.org/packages/source/r/requests/requests-2.31.0.tar.gz"
29
+ sha256 "TODO: Add actual hash"
30
+ end
31
+
32
+ def install
33
+ virtualenv_install_with_resources
34
+ end
35
+
36
+ test do
37
+ assert_match "CoreCLI", shell_output("#{bin}/cor --help")
38
+ end
39
+ end
File without changes
@@ -0,0 +1,52 @@
1
+ .PHONY: help install install-dev lint format type-check test build clean
2
+
3
+ help:
4
+ @echo "Available commands:"
5
+ @echo " make install - Install package"
6
+ @echo " make install-dev - Install package with dev dependencies"
7
+ @echo " make lint - Run ruff linter"
8
+ @echo " make format - Format code with black"
9
+ @echo " make format-check - Check code formatting without modifying"
10
+ @echo " make type-check - Run mypy type checker"
11
+ @echo " make test - Run tests"
12
+ @echo " make build - Build package"
13
+ @echo " make clean - Clean build artifacts"
14
+ @echo " make all - Run linting, formatting check, type check, and build"
15
+
16
+ install:
17
+ pip install -e .
18
+
19
+ install-dev:
20
+ pip install -e ".[dev]"
21
+ pip install pre-commit
22
+ pre-commit install
23
+
24
+ lint:
25
+ ruff check corecli/
26
+
27
+ lint-fix:
28
+ ruff check --fix corecli/
29
+
30
+ format:
31
+ black corecli/
32
+
33
+ format-check:
34
+ black --check corecli/
35
+
36
+ type-check:
37
+ mypy corecli/
38
+
39
+ test:
40
+ pytest tests/ -v
41
+
42
+ build:
43
+ python -m build
44
+ twine check dist/*
45
+
46
+ clean:
47
+ rm -rf dist/ build/ *.egg-info
48
+ find . -type d -name __pycache__ -exec rm -rf {} +
49
+ find . -type f -name '*.pyc' -delete
50
+
51
+ all: lint format-check type-check build
52
+ @echo "✅ All checks passed!"