Metadata-Version: 2.4
Name: pxa-extend
Version: 0.1.0
Summary: PXA 확장 (PEP 네이밍 규칙 점검·강제) — 단독 사용 가능
Author: Platform Team
License-Expression: Apache-2.0
Requires-Python: >=3.10
Description-Content-Type: text/markdown
License-File: LICENSE
Provides-Extra: lint
Requires-Dist: flake8>=7.0; extra == "lint"
Requires-Dist: pep8-naming>=0.13; extra == "lint"
Provides-Extra: dev
Requires-Dist: pytest>=8.0; extra == "dev"
Requires-Dist: flake8>=7.0; extra == "dev"
Requires-Dist: pep8-naming>=0.13; extra == "dev"
Dynamic: license-file

# pxa-extend

PXA **PEP 네이밍 규칙 점검·강제** 패키지.

> **단독 사용 가능** — 다른 pxa 패키지에 의존하지 않습니다. 코어는 **표준 라이브러리만** 사용합니다.

점검 수단이 두 가지입니다. 규칙을 **강제**하려면 2번을 쓰세요.

| | 도구 | 필요 패키지 | 쓰는 곳 |
|---|---|---|---|
| 1 | `pxa-lint` | flake8, pep8-naming | 폭넓은 PEP 8 스타일 + 네이밍 점검 |
| 2 | `assert_naming()` / `pxa-naming` | 없음 (표준 라이브러리) | pytest 에 넣어 **규칙 강제** |

---

## 설치

```bash
pip install pxa-extend               # 2번(네이밍 강제)만 쓸 때
pip install "pxa-extend[lint]"       # 1번(flake8) 까지
```

## 1. `pxa-lint` — 표준 설정 내장 flake8

프레임워크 표준 PEP 8 + pep8-naming 규칙이 패키지에 내장되어 있어, 프로젝트마다 `.flake8` 을 관리할 필요가 없습니다.

```bash
pxa-lint                        # 기본 대상: src tests
pxa-lint src/mypkg              # 대상 지정
pxa-lint --config .flake8 src   # 프로젝트 설정으로 덮어쓰기
```

종료코드: `0` 통과 / `1` 위반 / `2` flake8 미설치. CI 에서 0이 아니면 빌드를 실패시키세요.

## 2. `assert_naming()` — pytest 에서 규칙 강제

flake8 이 없어도 동작하므로, 테스트에 한 줄 넣어두면 **네이밍 위반이 있는 코드는 빌드를 통과하지 못합니다.**

```python
# tests/test_naming.py
from pxa_extend import assert_naming

def test_pep8_naming():
    assert_naming("src", "tests")
```

실패하면 위반 위치가 그대로 나옵니다.

```
PEP 8 네이밍 규칙 위반 2건:
  src/orders/api.py:12: PXA-N802 함수명 'getOrder' 은 lower_snake_case 여야 합니다.
  src/orders/api.py:30: PXA-N801 클래스명 'order_service' 은 CapWords 여야 합니다.
```

CLI 로도 같은 점검을 합니다.

```bash
pxa-naming src tests
```

프로그램에서 다루려면 `check_paths()` / `check_source()` 가 `NamingViolation` 목록을 돌려줍니다.

```python
from pxa_extend import check_paths

for violation in check_paths("src"):
    print(violation.file, violation.line, violation.code)
```

## 3. 점검 규칙

| 코드 | 대상 | 규칙 |
|---|---|---|
| `PXA-N801` | 클래스 | CapWords (`UserAccount`) |
| `PXA-N802` | 함수/메서드 | lower_snake_case (`get_user`) |
| `PXA-N803` | 인자 | lower_snake_case (`self`/`cls`/`_` 예외) |
| `PXA-N806` | 함수 안 지역변수 | lower_snake_case 또는 UPPER_CASE |
| `PXA-N815` | 클래스 속성 | lower_snake_case 또는 UPPER_CASE |
| `PXA-N816` | 모듈 전역변수 | lower_snake_case 또는 UPPER_CASE |
| `PXA-N999` | 모듈(파일)명 | lower_snake_case |

PEP 8 이 CapWords 를 쓰도록 한 **타입 별칭**(`Authenticator = Callable[...]`, `Model = TypeVar("Model")`)은 변수 규칙에서 제외됩니다.

## 4. 예외 처리 — `# noqa`

라이브러리 API 때문에 규칙을 지킬 수 없는 줄은 `# noqa` 로 억제합니다.

```python
def visit_ClassDef(self, node):   # noqa: N802  (ast.NodeVisitor 규약)
    ...
```

`# noqa` 는 그 줄 전체를, `# noqa: N802` 는 해당 코드만 억제합니다(`PXA-N802` 로 적어도 됩니다).

## 5. 테스트 & 배포

```bash
pip install -e ".[dev]"
pytest

python -m build && twine upload -r nexus dist/*
```
