# Naming Constraints

## File Names

### Python Modules
- **Convention**: `snake_case.py`
- **Examples**: `motion_database.py`, `api_client.py`, `text_pipeline.py`

### Test Files
- **Convention**: `test_<module_name>.py`
- **Examples**: `test_database.py`, `test_api_client.py`

### Config Files
- **Convention**: `snake_case`
- **Examples**: `config.py`, `.env.example`, `pyproject.toml`

### Directories
- **Convention**: `snake_case/`
- **Examples**: `pipeline/`, `tests/integration/`, `src/validators/`

## Class Names

- **Convention**: `PascalCase`
- **Examples**: `MotionDatabase`, `TweedeKamerAPI`, `MotionSummarizer`

### Naming Patterns
| Pattern | Example |
|---------|---------|
| Database wrapper | `MotionDatabase` |
| API client | `TweedeKamerAPI` |
| Service/Helpers | `MotionScraper`, `MotionAnalyzer` |
| Exceptions | `ProviderError` |

## Function Names

- **Convention**: `snake_case`
- **Examples**: `get_motions`, `compute_similarity`, `process_voting_records`

### Private Methods
- **Convention**: `_snake_case` (single underscore prefix)
- **Examples**: `_get_voting_records`, `_parse_response`

## Variable Names

### Regular Variables
- **Convention**: `snake_case`
- **Examples**: `motion_id`, `party_name`, `voting_results`

### Constants (Module-Level)
- **Convention**: `UPPER_SNAKE_CASE`
- **Examples**: `DATABASE_PATH`, `API_TIMEOUT`, `MAX_RETRIES`

### Config Variables (in dataclass)
- **Convention**: `UPPER_SNAKE_CASE`
- **Examples**: `QWEN_MODEL`, `POLICY_AREAS`

### Booleans
- **Convention**: `is_`, `has_`, `can_` prefixes or `_flag` suffix
- **Examples**: `is_active`, `has_votes`, `skip_extract`

### Private Variables
- **Convention**: `_underscore_prefix`
- **Examples**: `_conn`, `_cache`, `_session`

## Singleton Instances

- **Convention**: `lower_snake_case` at module level
- **Examples**: `db = MotionDatabase()`, `summarizer = MotionSummarizer()`

```python
# database.py
class MotionDatabase:
    ...

# Singleton instance
db = MotionDatabase()

# Usage
from database import db
motions = db.get_motions()
```

## Type Variables

- **Convention**: `PascalCase`
- **Examples**: `T = TypeVar('T')`, `MotionDict = Dict[str, Any]`

## Anti-Patterns

### Inconsistent Naming
```python
# BAD - mixing styles
get_motions()      # snake_case
GetMotionById()    # PascalCase
processData()      # camelCase

# GOOD - consistent snake_case
get_motions()
get_motion_by_id()
process_voting_data()
```

### Abbreviations
```python
# AVOID - unclear abbreviations
calc_similarity()      # calculate_*
proc_votes()          # process_*
get_mp_data()          # get_mp_metadata()

# PREFER - full words
calculate_similarity()
process_votes()
get_mp_metadata()
```

### Hungarian Notation
```python
# BAD - Hungarian notation
str_title = "..."
int_count = 0
b_is_active = True

# GOOD - clear types via naming
title = "..."
count = 0
is_active = True
```

## Special Cases

### Window IDs
- **Format**: `"YYYY-QN"` or `"YYYY"`
- **Examples**: `"2024-Q1"`, `"2024-Q2"`, `"2024"`

### Policy Areas
- **Convention**: PascalCase with spaces
- **Examples**: `"Economie"`, `"Sociale Zaken"`, `"Klimaat"`

### Vote Values
- **Convention**: PascalCase Dutch terms
- **Values**: `"Voor"`, `"Tegen"`, `"Onthouden"`, `"Geen stem"`, `"Afwezig"`
