ci: 규칙을 자동으로 강제하는 검사 추가

지금까지 "커밋 전 lint/test 통과"는 문서상의 약속일 뿐 강제되지 않았다.

- CI(GitHub Actions) 추가 — 세 스택의 lint·test·build 와 backend e2e 를 PR 마다 실행.
  error-codes-sync 잡은 sync 를 재실행한 뒤 git diff 로 생성 파일 드리프트를 검사한다.
  레지스트리만 고치고 sync 를 빠뜨리면 클라이언트 사전이 조용히 어긋나기 때문.
- lint 스크립트에 --max-warnings 0 적용. 기존에는 경고가 있어도 통과해
  "Warning 0" 규칙이 사실상 무의미했다. 자동 수정은 lint:fix 로 분리.
- 문서로만 있던 규칙을 린트로 이관:
  any/dynamic 금지, console/print 금지, Vue 인라인 스타일·Options API 금지,
  Dart const 누락·await 누락, HttpException 직접 생성 차단(BusinessException 유도).
- backend 에 @/ 경로 alias 설정 (tsconfig paths + jest moduleNameMapper).
  공통 규칙이 요구하는 절대경로 alias 가 backend 에만 빠져 있었다.
- npm audit 취약점 10건 중 9건 해결.
  남은 multer(high)는 platform-express v12 가 필요해 Nest v11 생태계와 충돌하고,
  파일 업로드 엔드포인트가 없어 도달 경로가 없다 — security.md 에 재검토 조건 기록.
- PR 템플릿 추가.

Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>
This commit is contained in:
2026-09-17 14:31:34 +09:00
parent e7c00e6f65
commit dac1603b03
10 changed files with 413 additions and 306 deletions
+37 -5
View File
@@ -6,7 +6,7 @@ import tseslint from 'typescript-eslint';
export default tseslint.config(
{
ignores: ['eslint.config.mjs'],
ignores: ['eslint.config.mjs', 'dist/**', 'coverage/**'],
},
eslint.configs.recommended,
...tseslint.configs.recommendedTypeChecked,
@@ -26,10 +26,42 @@ export default tseslint.config(
},
{
rules: {
'@typescript-eslint/no-explicit-any': 'off',
'@typescript-eslint/no-floating-promises': 'warn',
'@typescript-eslint/no-unsafe-argument': 'warn',
"prettier/prettier": ["error", { endOfLine: "auto" }],
// 타입 규칙 — 명시적 타입 선언 강제 ([[coding-common]])
'@typescript-eslint/no-explicit-any': 'error',
// 비동기 누락은 조용한 버그가 되므로 error 로 승격
'@typescript-eslint/no-floating-promises': 'error',
'@typescript-eslint/no-unsafe-argument': 'error',
// 로깅 규칙 — console 대신 winston/Nest Logger 사용 ([[logging]])
'no-console': 'error',
// 에러 규칙 — 코드 없는 실패 금지. HttpException 직접 상속/생성 대신
// BusinessException 을 사용한다 ([[error-codes]])
'no-restricted-syntax': [
'error',
{
selector:
"NewExpression[callee.name='HttpException']:not([callee.name='BusinessException'])",
message:
'HttpException 을 직접 생성하지 말고 BusinessException(code) 을 사용하세요. (.claude/rules/error-codes.md)',
},
],
'prettier/prettier': ['error', { endOfLine: 'auto' }],
},
},
{
// 에러 코드 레지스트리·예외 필터는 프레임워크 예외를 직접 다루는 계층이므로 예외 허용
files: ['src/common/errors/**/*.ts', 'src/common/filters/**/*.ts'],
rules: {
'no-restricted-syntax': 'off',
},
},
{
// CLI 스크립트는 콘솔 출력이 정상 동작이다
files: ['scripts/**/*.ts'],
rules: {
'no-console': 'off',
},
},
);