| name | coding-rules |
| description | プロジェクト共通のコーディング規約。TypeScript、命名規則、関数設計、React/Next.js等。 使用タイミング: (1) コードレビュー時 (2) 新規ファイル作成時 (3) リファクタリング時 (4) コーディングスタイルの確認時 (5) チーム開発のルール確認時。 トリガー例: 「コーディング規約」「命名規則は?」「TypeScriptのルール」 「インポート順序」「コミットメッセージの書き方」
|
coding-rules - コーディング規約
プロジェクト共通のコーディングルール。
1. TypeScript
型定義
interface User {
id: string;
email: string;
name: string;
createdAt: Date;
}
const users = await repository.findAll();
const data: any = response.json();
const data: unknown = await response.json();
if (isUser(data)) {
console.log(data.email);
}
Null/Undefined
const email = user?.profile?.email;
const name = user.name ?? 'Anonymous';
const name = user.name || 'Anonymous';
2. インポート順序
import { useState } from 'react';
import { z } from 'zod';
import { db } from '@/db';
import { User } from '@/types';
import { helper } from './utils';
import styles from './styles.module.css';
3. 命名規則
| 種類 | 規則 | 例 |
|---|
| 変数・関数 | camelCase | getUserById, isActive |
| 定数 | UPPER_SNAKE_CASE | MAX_RETRY_COUNT |
| クラス・型 | PascalCase | UserService, CreateUserInput |
| ファイル | kebab-case | user-service.ts |
| Reactコンポーネント | PascalCase | UserCard.tsx |
| 環境変数 | UPPER_SNAKE_CASE | DATABASE_URL |
Boolean命名
const isActive = true;
const hasPermission = user.role === 'admin';
const canEdit = isOwner || isAdmin;
const shouldRefetch = isStale && !isLoading;
4. 関数
単一責任
async function processUser(userId: string) {
const user = await db.select().from(users).where(eq(users.id, userId));
await sendEmail(user.email);
await updateLastLogin(userId);
return user;
}
async function getUser(userId: string) {
return db.select().from(users).where(eq(users.id, userId));
}
async function notifyUser(email: string) {
await sendEmail(email);
}
async function recordLogin(userId: string) {
await updateLastLogin(userId);
}
早期リターン
function processData(data: Data | null) {
if (data) {
if (data.isValid) {
if (data.items.length > 0) {
return data.items.map(process);
}
}
}
return [];
}
function processData(data: Data | null) {
if (!data) return [];
if (!data.isValid) return [];
if (data.items.length === 0) return [];
return data.items.map(process);
}
5. エラーハンドリング
class ValidationError extends Error {
constructor(
message: string,
public field: string
) {
super(message);
this.name = 'ValidationError';
}
}
try {
await riskyOperation();
} catch (error) {
if (error instanceof ValidationError) {
return apiError(error.message, { status: 400 });
}
console.error('Unexpected error:', error);
return apiError('Internal error', { status: 500 });
}
6. コメント
const BATCH_SIZE = 100;
const user = await getUser(id);
7. React/Next.js
Server vs Client Components
'use client';
export function LikeButton({ postId }: { postId: string }) {
const [liked, setLiked] = useState(false);
return <button onClick={() => setLiked(!liked)}>Like</button>;
}
Props
interface UserCardProps {
user: User;
onEdit?: (id: string) => void;
className?: string;
}
export function UserCard({ user, onEdit, className }: UserCardProps) {
}
8. Git コミット
Conventional Commits
feat: 新機能追加
fix: バグ修正
docs: ドキュメント
refactor: リファクタリング
test: テスト
chore: その他
例
feat: add user authentication
fix: resolve login redirect loop
docs: update API documentation
refactor: extract validation logic to separate module
test: add unit tests for UserService
chore: update dependencies