Skip to content

Instantly share code, notes, and snippets.

@Nishkalkashyap
Last active March 6, 2026 10:48
Show Gist options
  • Select an option

  • Save Nishkalkashyap/06c6e480da9f25d1444de8c55689dc21 to your computer and use it in GitHub Desktop.

Select an option

Save Nishkalkashyap/06c6e480da9f25d1444de8c55689dc21 to your computer and use it in GitHub Desktop.
Code Simplification prompt
You are performing a **Staff Engineer–level cleanup and refactor** of a TypeScript monorepo built with:
* Next.js (App Router)
* React
* Convex
* Turborepo
Your goal is to:
* **simplify the codebase**
* **remove unnecessary abstractions**
* **improve architecture**
* **reduce indirection**
* **make module boundaries clearer**
The result should be **simpler, easier to reason about code**.
If successful, the git diff should contain **significantly more deletions than additions**.
---
# Scope
You may **ONLY modify files inside these directories**:
```
<file paths>
```
Do **not modify files outside this scope**.
---
# Workflow
Before making changes:
1. Identify **entrypoints and route structure**
2. Trace **React component hierarchies**
3. Trace **Convex query/mutation usage**
4. Identify **server vs client boundaries**
5. Identify **cross-package dependencies**
6. Determine which modules are **actually used**
Do not begin refactoring until you understand the system.
---
# Next.js App Router Composition (SSR-First)
Follow an **SSR-first architecture**.
### Server route layer
`page.tsx` and `layout.tsx` should:
* validate params
* perform auth checks
* fetch initial data
* compose the route
Example:
```tsx
export default async function Page() {
const initialData = await getInitialData();
return <PageClient initialData={initialData} />;
}
```
---
### Client entry layer
`page.client.tsx` and `layout.client.tsx` should:
* remain **thin**
* compose hooks and components
* avoid heavy business logic
```tsx
"use client";
export function PageClient({ initialData }) {
const model = useFeatureModel(initialData);
return <FeatureView model={model} />;
}
```
---
# Component and Hook Composition
React components should stay **focused on rendering and composition**.
When a component accumulates many hooks or state variables (e.g. many `useState`, `useEffect`, `useQuery`, etc.), extract them into a **feature hook**.
Example:
Instead of:
```
const [a, setA] = useState()
const [b, setB] = useState()
const [c, setC] = useState()
useEffect(...)
useEffect(...)
useQuery(...)
```
Prefer:
```
const feature = useFeatureX(...)
```
Rules:
* hooks should encapsulate **behavior and state orchestration**
* hooks **may live in the same file as the component** if tightly coupled
* avoid creating separate hook files unless reuse or size justifies it
The goal is to **keep component top-levels readable**.
---
# Simplification Opportunities
Look for and fix the following.
---
## Dead Code
Delete:
* unused exports
* unused components
* unused hooks
* unused Convex queries/mutations
* unused types
* unused utilities
* unused constants
---
## Thin Abstractions
Remove wrappers that only:
* rename another function
* forward arguments unchanged
* exist only for indirection
Example:
```
function getProjects() {
return fetchProjects()
}
```
Inline this.
---
## Over-Modularization
Merge files when:
* files are very small
* they export one trivial function
* they artificially split cohesive logic
Prefer **fewer cohesive modules**.
---
## React Over-Engineering
Remove unnecessary:
* `useMemo`
* `useCallback`
* wrapper hooks
* wrapper components
Prefer direct logic unless optimization is necessary.
---
## Convex Simplification
Simplify Convex usage:
* remove wrappers around `useQuery` / `useMutation`
* delete unused queries/mutations
* merge duplicated queries
* prefer direct API usage
---
## Server/Client Boundary Issues
Fix cases where:
* client components import server utilities
* server logic leaks into client components
* `"use client"` appears unnecessarily
* data fetching occurs in the wrong layer
---
## Turborepo Over-Engineering
Watch for:
* unnecessary package boundaries
* cross-package indirection
* long re-export chains
Prefer **direct imports and clear ownership**.
---
# Utility Module Export Rule
Utility/helper modules must export **a single namespace object**.
Example:
```ts
const isProtectedBranch = (...)
const stripPrefix = (...)
export const branchPolicyUtils = {
isProtectedBranch,
stripPrefix,
} as const;
```
Rules:
* define functions locally
* export **one namespace object**
* call using namespace access
Example:
```
branchPolicyUtils.isProtectedBranch(...)
```
This rule applies to shared helpers and utilities.
Excluded:
* React components
* hooks
* route handlers
---
# Barrel Export Rules
Barrel exports are allowed **only for package public APIs**.
Allowed:
```
packages/<package>/index.ts
packages/<package>/src/index.ts
```
Not allowed:
* feature-internal barrel files
* re-export-only modules inside implementation folders
Delete those and import directly.
---
# Allowed Changes
You may:
* make breaking changes
* modify UI
* change API contracts
* delete files
* merge modules
* restructure code
This project **is not yet in production**, so **backwards compatibility is not required**.
---
# Success Criteria
The refactor is successful if:
* the codebase is **smaller**
* abstractions are reduced
* architecture is clearer
* Next.js composition follows SSR-first patterns
* unused code is removed
Git diff should show **more deletions than additions**.
---
# Output Format
For each refactor:
1. Explain the **problem**
2. Explain **why the abstraction adds complexity**
3. Show the **refactored implementation**
Focus on **structural simplification**, not formatting.
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment