Code Style¶
Consistent code style makes the codebase easier to read and maintain. We use automated tools to handle most formatting decisions, so you can focus on writing good code rather than debating style.
Linting with Ruff¶
We use Ruff for both linting and formatting. The configuration lives in pyproject.toml:
- Line length: 80 characters
- Target version: Python 3.10
- Enabled rule sets: pyflakes (
F), pycodestyle (E), McCabe complexity (C90)
Ruff runs automatically via pre-commit hooks on every commit. You can also run it manually:
ruff check src/ tests/ # Check for lint issues
ruff check src/ tests/ --fix # Auto-fix what's possible
ruff format src/ tests/ # Format code
Docstrings¶
We follow Google-style docstrings. This is important because our API reference documentation is auto-generated from docstrings using mkdocstrings.
Here's what a well-written docstring looks like:
def get_apps_map(
self, project_id: str = None, location: str = None
) -> Dict[str, str]:
"""Returns a mapping of app display names to resource names.
This is a convenience method that fetches all apps and returns
them as a dictionary, making it easy to look up an app's
resource name by its human-readable display name.
Args:
project_id: The GCP project ID. Uses the instance default
if not provided.
location: The GCP location (e.g., "us", "global"). Uses the
instance default if not provided.
Returns:
A dictionary mapping display names to full resource names.
For example: {"My App": "projects/my-proj/locations/us/apps/abc123"}
Raises:
PermissionError: If the caller lacks the required IAM role.
"""
Key points:
- First line: A concise summary of what the method does, in imperative mood ("Returns..." not "Return...").
- Extended description: Optional. Explain why someone would use this method, not just what it does.
- Args: Document each parameter with its type and purpose.
- Returns: Describe the return value with an example when it helps.
- Raises: List exceptions that callers should handle.
Type Hints¶
Use type hints on all public method signatures. They serve as documentation and help IDEs provide better autocompletion:
def create_app(
self,
display_name: str,
description: str = "",
project_id: str = None,
location: str = None,
) -> Any:
Naming Conventions¶
| Element | Convention | Example |
|---|---|---|
| Classes | PascalCase | ToolEvals, SimulationEvals |
| Methods | snake_case | get_apps_map, run_tool_tests |
| Constants | UPPER_SNAKE | GLOBAL_SCOPES, SAMPLE_RATE |
| Private methods | Leading underscore | _parse_response |
| Test files | test_ prefix | test_linter.py |
Testing¶
- Write tests for any new functionality.
- Tests live in
tests/and mirror thesrc/directory structure. - Use
pytestconventions (functions prefixed withtest_). - Aim for clear, readable test names that describe the scenario being tested.