A Python framework for managing development tasks across projects.
- Organizes commands by project namespace
- Provides automatic command-line argument parsing based on function annotations
- Supports tab completion for commands and arguments
- Includes colorized logging output
- Makes it easy to extend with new projects and commands
Prerequisites:
- Python 3.x
argcompletepackage for command completion
-
Clone the repository in your dev-main directory or add it as a git submodule:
git clone https://github.com/fahien/dev.git # or git submodule add https://github.com/fahien/dev.git
-
Create a virtual environment (optional but recommended):
python -m venv .venv source .venv/bin/activate # On Windows use `.venv\Scripts\activate`
-
Install the required packages:
pip install -r requirements.txt -
Enable global completion:
activate-global-python-argcomplete --user -
Add to your shell configuration:
# Root directory for all projects (required) export WORKSPACE_PATH="/path/to/your/workspace" DEV_PATH="$WORKSPACE_PATH/dev-main" DEV_MAIN_PATH="$DEV_PATH/main.py" DEV_VENV_BIN_PATH="$DEV_PATH/.venv/bin" eval "$($DEV_VENV_BIN_PATH/register-python-argcomplete $DEV_MAIN_PATH)" alias dev="$DEV_VENV_BIN_PATH/python3 $DEV_MAIN_PATH"
Add the following to your PowerShell profile (e.g.,
Microsoft.PowerShell_profile.ps1):function Python-Dev-Gfxr { $pythonExe = Join-Path $env:LUNARG_WORKSPACE_PATH 'dev-gfxr/.venv/Scripts/python.exe' $mainPy = Join-Path $env:LUNARG_WORKSPACE_PATH 'dev-gfxr/main.py' & $pythonExe $mainPy $args } New-Alias lunarg Python-Dev-Gfxr register-python-argcomplete.exe --shell powershell lunarg | Out-String | Invoke-Expression
Run commands with the following structure:
dev <project-name> <command> [arguments]Example:
dev myproject build --config release__init__.py- Sets up importsconfig.py- Handles command-line parsinglog.py- Implements colored loggingproject.py- Defines the base Project classutil.py- Provides utility functions
- Create a new Python file in the
dev-main/projectsdirectory - Define a class that extends
Projectfrom theprojectsmodule - Add methods decorated with
@commandfor each method that you want to be exposed to the CLI
Example:
from enum import Enum
from project import Project, command, BuildType
import util
class MyProject(Project):
def __init__(self):
Project.__init__(self, "myproject") # This sets the project name for CLI
@command
def build(self, config: BuildType = BuildType.DEBUG):
"""Build the project with specified configuration."""
util.run(["make", f"CONFIG={config}"], cwd=self.project_path)
@command
def clean(self):
"""Clean build artifacts."""
util.run(["make", "clean"], cwd=self.project_path)-
Commands can use type annotations to define the values expected through the CLI:
@command def deploy(self, target: str, verbose: bool = False): """Deploy to specified target.""" # Implementation here
Will yield:
$ dev myproject deploy --help usage: dev myproject deploy [-h] [--verbose VERBOSE] target Deploy to specified target. positional arguments: target str optional arguments: -h, --help show this help message and exit --verbose VERBOSE bool (default: False)
-
Enum types are automatically converted to command-line choices via the
__str__method:class Platform(Enum): LINUX = "linux" MACOS = "macos" WINDOWS = "windows" def __str__(self): return self.value @command def build_for(self, platform: Platform): """Build for specific platform.""" # Implementation
Will yield:
$ dev myproject build_for --help usage: dev myproject build_for [-h] {linux,macos,windows} Build for specific platform. positional arguments: {linux,macos,windows} optional arguments: -h, --help show this help message and exit
-
Default values for optional arguments:
@command def build(self, config: BuildType = BuildType.DEBUG): """Build the project with specified configuration.""" util.run(["make", f"CONFIG={config}"], cwd=self.project_path)
Will yield:
$ dev myproject build --help usage: dev myproject build [-h] [--config {debug,release}] Build the project with specified configuration. optional arguments: -h, --help show this help message and exit --config {debug,release} None (default: debug)
-
Use the built-in colored logging:
import logging logging.info("Starting build process...") logging.warning("Configuration file not found") logging.error("Build failed")
Dual licensed under either
Unless you explicitly state otherwise, any contribution intentionally submitted for inclusion in the work by you, as defined in the Apache-2.0 license, shall be dual licensed as above, without any additional terms or conditions.