From 55e17408cfc37c23016152e4249aee76999a80f6 Mon Sep 17 00:00:00 2001 From: kmontemayor Date: Tue, 17 Feb 2026 17:05:59 +0000 Subject: [PATCH 1/2] Update --- .cursor/README.md | 3 +- .cursor/rules/coding.mdc | 98 +++++++++++++++++++++++++++++++ .cursor/rules/python-patterns.mdc | 16 ++++- 3 files changed, 115 insertions(+), 2 deletions(-) create mode 100644 .cursor/rules/coding.mdc diff --git a/.cursor/README.md b/.cursor/README.md index fca44fc15..71e720f8b 100644 --- a/.cursor/README.md +++ b/.cursor/README.md @@ -1,2 +1,3 @@ We setup Cursor context rules to help give useful information to agents. For more info see: -https://docs.cursor.com/en/context/rules + +https://cursor.com/docs/context/rules diff --git a/.cursor/rules/coding.mdc b/.cursor/rules/coding.mdc new file mode 100644 index 000000000..565e47010 --- /dev/null +++ b/.cursor/rules/coding.mdc @@ -0,0 +1,98 @@ +--- +description: Core coding standards - explicit naming and fail-fast error handling +alwaysApply: true +--- + +# Coding Standards + +## Use Explicit Variable Names + +Never abbreviate variable names unless the abbreviation is universally understood in the domain +(e.g. `i` for a loop index, `e` in a catch block, `url`, `id`, `config`). +Shortened names reduce readability and make code harder to search and refactor. + +```python +# BAD - unclear abbreviation +for nt in node_types: + et = edge_type_map.get(nt) + +# GOOD - explicit and readable +for node_type in node_types: + edge_type = edge_type_map[node_type] +``` + +Only shorten a name when: +- The abbreviation is a widely recognized term in the project domain or in Python at large. +- There is a concrete variable-shadowing concern with the full name in the same scope. + +When in doubt, spell it out. + +## Fail Fast on Invalid State + +Surface errors immediately when invariants are violated. +Do not silently swallow errors, return defaults, or skip logic when the situation is genuinely unexpected. + +### Dict Access + +Use `dict[key]` (bracket access) when the key **must** exist. +Only use `dict.get(key, default)` when the absence of a key is a valid, expected case with a meaningful default. + +```python +# BAD - silently returns None when the key is missing, hiding bugs downstream +value = config.get("required_setting") + +# GOOD - raises KeyError immediately, surfacing the real problem +value = config["required_setting"] + +# OK - .get() is correct when absence is an expected, handled case +value = optional_overrides.get("timeout", DEFAULT_TIMEOUT) +``` + +### Validate Preconditions Early + +Check invariants at function entry. Prefer raising an explicit exception over silently continuing +with bad data. + +```python +# BAD - silently skips work on invalid input +def process_batch(batch): + if batch: + ... + +# GOOD - fails immediately with a clear message +def process_batch(batch): + if not batch: + raise ValueError("process_batch received an empty batch") + ... +``` + +## Verify Features Before Submitting + +Once a feature is code complete, verify it works by running the type checker and relevant tests. +Do not skip these steps or suppress errors with workarounds like `# type: ignore`. + +### Type Checking + +Run the type checker to ensure all type annotations are correct: + +```bash +make type_check +``` + +If there are type errors, fix them properly. Do **not** add `# type: ignore` comments to silence them. + +### Unit Tests + +Run the unit tests for the files affected by your change: + +```bash +make unit_test_py PY_TEST_FILES="path/to/test_file.py" +``` + +### Integration Tests + +If the change touches cross-component behavior, also run integration tests: + +```bash +make integration_test PY_TEST_FILES="path/to/test_file.py" +``` diff --git a/.cursor/rules/python-patterns.mdc b/.cursor/rules/python-patterns.mdc index 51c29b6c0..9fa6f1d2e 100644 --- a/.cursor/rules/python-patterns.mdc +++ b/.cursor/rules/python-patterns.mdc @@ -51,7 +51,6 @@ class TestArgs: Example with >>> for doctests, Args, Returns, and Raises if applicable. Docstrings should be clear, consistent, testable, and Sphinx-compatible. -Example: ```python from typing import Final, Optional @@ -82,6 +81,21 @@ def add_to_magic_number( return MAGIC_NUMBER + number_1 + sum(numbers) ``` +#### Empty-Initialized Containers Must Be Typed + +Always annotate empty containers at the point of initialization. Without an annotation the type checker (and the reader) +cannot infer the element type. + +```python +# BAD - type is ambiguous +names = [] +counts = {} + +# GOOD - element type is explicit +names: list[str] = [] +counts: dict[str, int] = {} +``` + ### Error Handling & Logging - Use the GiGL logger: `from gigl.common.logger import Logger` From 96ad03249fe843235cb3d65401c77d33a65a0d18 Mon Sep 17 00:00:00 2001 From: Kyle Montemayor Date: Tue, 17 Feb 2026 13:08:58 -0800 Subject: [PATCH 2/2] Update coding.mdc --- .cursor/rules/coding.mdc | 5 +---- 1 file changed, 1 insertion(+), 4 deletions(-) diff --git a/.cursor/rules/coding.mdc b/.cursor/rules/coding.mdc index 565e47010..009413068 100644 --- a/.cursor/rules/coding.mdc +++ b/.cursor/rules/coding.mdc @@ -10,6 +10,7 @@ alwaysApply: true Never abbreviate variable names unless the abbreviation is universally understood in the domain (e.g. `i` for a loop index, `e` in a catch block, `url`, `id`, `config`). Shortened names reduce readability and make code harder to search and refactor. +It is ok to shorten or abbreviate names to avoid shadowing other variables. ```python # BAD - unclear abbreviation @@ -21,10 +22,6 @@ for node_type in node_types: edge_type = edge_type_map[node_type] ``` -Only shorten a name when: -- The abbreviation is a widely recognized term in the project domain or in Python at large. -- There is a concrete variable-shadowing concern with the full name in the same scope. - When in doubt, spell it out. ## Fail Fast on Invalid State