| name | bellog-structure |
| description | Provides file organization and naming conventions for the Bellog project. Triggers when creating new files or reorganizing code. |
Bellog File Organization
This skill defines the file structure, naming conventions, and organization patterns for the Bellog blog project.
Project Structure
/Users/castle_bell/Projects/bellog/
├── src/
│ ├── app/ # Next.js App Router
│ │ ├── layout.tsx # Root layout with fonts & metadata
│ │ ├── page.tsx # Home page
│ │ ├── template.tsx # Page transition wrapper
│ │ ├── providers.tsx # Client-side providers
│ │ ├── posts/
│ │ │ ├── page.tsx # All posts page
│ │ │ └── [slug]/
│ │ │ └── page.tsx # Individual post
│ │ ├── api/
│ │ │ └── revalidate/
│ │ │ └── route.ts # Cache revalidation endpoint
│ │ ├── robots.ts # SEO robots.txt
│ │ └── sitemap.ts # Dynamic sitemap
│ │
│ ├── components/
│ │ ├── common/ # App-wide shared components
│ │ │ ├── Navbar.tsx
│ │ │ ├── Footer.tsx
│ │ │ ├── Intro.tsx
│ │ │ ├── Header.tsx
│ │ │ └── ...
│ │ ├── posts/ # Post-specific components
│ │ │ ├── PostCard.tsx
│ │ │ ├── PostList.tsx
│ │ │ ├── PostRenderer.tsx
│ │ │ ├── NotionToc.tsx
│ │ │ └── ...
│ │ └── ui/ # Low-level UI primitives
│ │ ├── Tag.tsx
│ │ ├── ThemeToggle.tsx
│ │ ├── switch.tsx
│ │ └── ...
│ │
│ ├── hooks/ # Custom React hooks
│ │ ├── useScrollSpy.ts
│ │ ├── useTocObserver.ts
│ │ └── useHeadings.ts
│ │
│ ├── lib/ # Business logic & utilities
│ │ ├── notion.ts # Notion API client
│ │ ├── posts.ts # Post data fetching
│ │ ├── tags.ts # Tag utilities
│ │ └── utils.ts # General utilities
│ │
│ ├── constants/ # Shared constants
│ │ └── ui.ts # UI-related constants
│ │
│ ├── types/ # TypeScript types
│ │ └── index.d.ts # Global type definitions
│ │
│ └── styles/ # Global styles
│ └── global.css # Theme variables + Tailwind
│
├── public/ # Static assets
├── .claude/ # Claude Code configuration
│ ├── agents/ # Custom sub-agents
│ └── skills/ # Custom skills
├── .github/ # GitHub configuration
│ └── PULL_REQUEST_TEMPLATE.md
├── .husky/ # Git hooks
├── tailwind.config.ts # Tailwind configuration
├── tsconfig.json # TypeScript configuration
├── next.config.ts # Next.js configuration
├── package.json # Dependencies & scripts
├── commitlint.config.ts # Commit message linting
├── CLAUDE.md # Project guide
└── README.md # Project documentation
Naming Conventions
Components
Rule: PascalCase
✅ Correct:
PostCard.tsx
NotionToc.tsx
ScrollToTop.tsx
ThemeToggle.tsx
❌ Wrong:
postCard.tsx
notion-toc.tsx
scroll_to_top.tsx
Hooks
Rule: camelCase with use prefix
✅ Correct:
useScrollSpy.ts
useTocObserver.ts
useHeadings.ts
useScrollPosition.ts
❌ Wrong:
UseScrollSpy.ts
scroll-spy-hook.ts
scrollSpy.ts (missing use prefix)
Utilities & Libraries
Rule: camelCase
✅ Correct:
notion.ts
posts.ts
tags.ts
utils.ts
❌ Wrong:
Notion.ts
Posts.ts
tag-utils.ts
Types
Rule: camelCase file, PascalCase exports
✅ Correct:
File: index.d.ts
Export: interface Post { }
Export: type PostStatus = 'published' | 'draft';
❌ Wrong:
File: Post.d.ts
Export: interface post { }
Constants
Rule: SCREAMING_SNAKE_CASE for values, camelCase for file
✅ Correct:
File: ui.ts
Exports:
export const HEADER_OFFSET = 80;
export const SCROLL_SPY_OFFSET = 100;
❌ Wrong:
export const headerOffset = 80;
export const header-offset = 80;
API Routes
Rule: camelCase folder, route.ts file
✅ Correct:
app/api/revalidate/route.ts
❌ Wrong:
app/api/Revalidate/route.ts
app/api/revalidate/revalidate.ts
Where to Place Files
Decision Tree
Q: Is it a React component?
- Yes →
/src/components/- App-wide (Navbar, Footer) →
/src/components/common/ - Post-specific (PostCard, NotionToc) →
/src/components/posts/ - Reusable UI primitive (Tag, Button) →
/src/components/ui/
- App-wide (Navbar, Footer) →
Q: Is it a custom hook?
- Yes →
/src/hooks/use[Name].ts
Q: Is it business logic or data fetching?
- Yes →
/src/lib/- Notion API →
/src/lib/notion.ts - Post data →
/src/lib/posts.ts - Utility functions →
/src/lib/utils.ts
- Notion API →
Q: Is it a constant value?
- Yes →
/src/constants/- UI-related →
/src/constants/ui.ts - API-related →
/src/constants/api.ts
- UI-related →
Q: Is it a TypeScript type?
- Yes →
/src/types/index.d.ts
Q: Is it a page or route?
- Yes →
/src/app/[route]/page.tsx
Q: Is it an API endpoint?
- Yes →
/src/app/api/[endpoint]/route.ts
Component Organization
Common Components (/src/components/common/)
Components used across multiple pages:
- Layout components (Navbar, Footer)
- Page sections (Intro, Header)
- Shared widgets (ProgressBar)
Examples:
Navbar.tsx- Site navigationFooter.tsx- Site footerIntro.tsx- Hero section with animationsProgressBar.tsx- Scroll progress indicatorHeader.tsx- Page headers
Post Components (/src/components/posts/)
Components specific to blog posts:
- Post rendering (PostRenderer)
- Post navigation (NotionToc, PostNavigation)
- Post lists (PostList, PostCard)
Examples:
PostCard.tsx- Individual post previewPostList.tsx- Grid of post cardsPostRenderer.tsx- Notion content rendererNotionToc.tsx- Table of contentsPostNavigation.tsx- Previous/Next navigationGiscusComments.tsx- Comment system
UI Components (/src/components/ui/)
Low-level, reusable UI primitives:
- Buttons, inputs, switches
- Tags, badges
- Shadcn/ui components
Examples:
Tag.tsx- Tag displayTagList.tsx- Tag filteringThemeToggle.tsx- Dark/light mode toggleswitch.tsx- Radix UI switch (shadcn/ui)
File Templates
Component Template
// For interactive components
"use client";
import { useState } from 'react';
import { motion } from 'framer-motion';
interface ComponentNameProps {
// Props
}
export function ComponentName({ }: ComponentNameProps) {
// Logic
return (
<div>
{/* JSX */}
</div>
);
}
Hook Template
import { useState, useEffect } from 'react';
/**
* Brief description of what this hook does
*
* @example
* const value = useHookName();
*/
export function useHookName() {
// Hook logic
return value;
}
Utility Template
/**
* Brief description of utility function
*
* @param paramName - Description
* @returns Description
*/
export function utilityName(paramName: Type): ReturnType {
// Implementation
}
Type Definition Template
// /src/types/index.d.ts
export interface Post {
id: string;
title: string;
slug: string;
date: string;
description: string;
tags: string[];
status: PostStatus;
}
export type PostStatus = 'published' | 'draft' | 'archived';
Import Organization
Order
// 1. React & Next.js
import { useState } from 'react';
import Link from 'next/link';
// 2. Third-party libraries
import { motion } from 'framer-motion';
import { Search } from 'lucide-react';
// 3. Internal imports (@/...)
import { Button } from '@/components/ui/button';
import { getAllPosts } from '@/lib/posts';
import { HEADER_OFFSET } from '@/constants/ui';
// 4. Relative imports
import { helperFunction } from '../utils';
// 5. Type imports (separate)
import type { Post } from '@/types';
Path Aliases
Bellog uses @/ for root imports:
// ✅ Correct
import { PostCard } from '@/components/posts/PostCard';
import { getAllPosts } from '@/lib/posts';
import { HEADER_OFFSET } from '@/constants/ui';
// ❌ Wrong (no relative paths from root)
import { PostCard } from '../../components/posts/PostCard';
Code Organization Patterns
Single Responsibility
// ✅ Good - Each file has one clear purpose
// /src/lib/notion.ts - Notion API calls
// /src/lib/posts.ts - Post data transformation
// /src/lib/tags.ts - Tag utilities
// ❌ Bad - Everything in one file
// /src/lib/everything.ts
Group Related Code
// ✅ Good - Related components together
/src/components/posts/
PostCard.tsx
PostList.tsx
PostNavigation.tsx
// ❌ Bad - All components flat
/src/components/
PostCard.tsx
Navbar.tsx
PostList.tsx
Footer.tsx
Constants Extraction
// ✅ Good - Constants in separate file
// /src/constants/ui.ts
export const HEADER_OFFSET = 80;
export const SCROLL_SPY_OFFSET = 100;
// Component uses constants
import { HEADER_OFFSET } from '@/constants/ui';
// ❌ Bad - Magic numbers in component
const offset = 80; // What is this?
File Size Guidelines
Components: < 200 lines
- If larger, consider splitting into smaller components
Hooks: < 100 lines
- If larger, consider extracting helper functions
Utils: < 50 lines per function
- If larger, break into smaller functions
Types: No limit
- Types can be long, that's okay
Barrel Exports (Avoid)
// ❌ Avoid barrel exports (index.ts files)
// /src/components/index.ts
export { PostCard } from './PostCard';
export { PostList } from './PostList';
// ✅ Prefer direct imports
import { PostCard } from '@/components/posts/PostCard';
import { PostList } from '@/components/posts/PostList';
Why: Barrel exports slow down builds and complicate tree-shaking.
Environment Files
.env.local # Local development secrets (gitignored)
.env.example # Template (committed to git)
Never commit:
.env.local.env- Any file with actual secrets
Git Ignore Patterns
Ensure these are in .gitignore:
# Dependencies
node_modules/
.pnp
.pnp.js
# Next.js
.next/
out/
# Environment
.env.local
.env
# IDE
.vscode/
.idea/
# OS
.DS_Store
Documentation Structure
/ # Root
├── README.md # Project overview & setup
├── CLAUDE.md # Development guide (for AI)
└── docs/ # Detailed documentation (if needed)
├── architecture.md
└── deployment.md
Quick Reference
Components: PascalCase.tsx /src/components/{common,posts,ui}/
Hooks: useName.ts /src/hooks/
Utilities: name.ts /src/lib/
Constants: NAME /src/constants/
Types: name.d.ts /src/types/
Pages: page.tsx /src/app/[route]/
API: route.ts /src/app/api/[endpoint]/
Checklist for New Files
- File in correct directory
- Naming convention followed (PascalCase / camelCase)
- Imports organized by category
- Using @ alias for imports (not relative from root)
- TypeScript types defined
- No magic numbers (use constants)
- Single responsibility (one clear purpose)
- File size reasonable (< 200 lines for components)
Remember: Organization is about findability. When someone looks for a file, it should be obvious where it is.