typescript
63 lines · 3 tabs
Maya Patel
Jan 2026
3 tabs
import { useState, useEffect } from 'react'
export function useDebounce<T>(value: T, delay: number = 500): T {
const [debouncedValue, setDebouncedValue] = useState<T>(value)
useEffect(() => {
const handler = setTimeout(() => {
setDebouncedValue(value)
}, delay)
return () => {
clearTimeout(handler)
}
}, [value, delay])
return debouncedValue
}
import { useState, useEffect } from 'react'
export function useLocalStorage<T>(key: string, initialValue: T) {
const [storedValue, setStoredValue] = useState<T>(() => {
try {
const item = window.localStorage.getItem(key)
return item ? JSON.parse(item) : initialValue
} catch (error) {
console.error('Error reading from localStorage:', error)
return initialValue
}
})
const setValue = (value: T | ((val: T) => T)) => {
try {
const valueToStore = value instanceof Function ? value(storedValue) : value
setStoredValue(valueToStore)
window.localStorage.setItem(key, JSON.stringify(valueToStore))
} catch (error) {
console.error('Error writing to localStorage:', error)
}
}
return [storedValue, setValue] as const
}
function SearchPosts() {
const [searchTerm, setSearchTerm] = useState('')
const debouncedSearchTerm = useDebounce(searchTerm, 300)
const { data: posts } = useQuery({
queryKey: ['posts', 'search', debouncedSearchTerm],
queryFn: () => fetchPosts({ search: debouncedSearchTerm }),
enabled: debouncedSearchTerm.length > 2,
})
return (
<div>
<input
value={searchTerm}
onChange={(e) => setSearchTerm(e.target.value)}
placeholder="Search posts..."
/>
{/* Results render here */}
</div>
)
}
3 files · typescript
Explain with highlit
Custom hooks extract component logic into reusable functions that can share stateful behavior across components. I prefix hook names with use and compose them from built-in hooks like useState, useEffect, and useCallback. Hooks encapsulate concerns like data fetching, form handling, local storage sync, or WebSocket connections. The key is identifying repeated patterns in components and abstracting them. For example, a useDebounce hook delays value updates, useful for search inputs. A useLocalStorage hook syncs state with browser storage. Custom hooks make components cleaner and logic more testable since hooks can be tested independently from UI rendering.
Related snips
ruby
class Post < ApplicationRecord
belongs_to :author, class_name: 'User'
has_many :comments, dependent: :destroy
scope :published, -> { where.not(published_at: nil).where('published_at <= ?', Time.current) }
scope :draft, -> { where(published_at: nil) }
ActiveRecord scopes for reusable query logic
rails
activerecord
patterns
by Alex Kumar
1 tab
typescript
export interface RetryOptions {
retries: number;
baseMs: number;
maxMs: number;
signal?: AbortSignal;
onRetry?: (attempt: number, delay: number, err: unknown) => void;
Exponential backoff with jitter for retries
typescript
reliability
retry
by codesnips
2 tabs
typescript
import axios, { AxiosError } from 'axios'
import { v4 as uuidv4 } from 'uuid'
const api = axios.create({
baseURL: import.meta.env.VITE_API_URL || 'http://localhost:3000/api/v1',
timeout: 15000,
Axios API client with interceptors
react
axios
api
by Maya Patel
1 tab
typescript
import { create } from 'zustand'
import { persist } from 'zustand/middleware'
interface FilterState {
search: string
category: string | null
Zustand for lightweight state management
react
zustand
state-management
by Maya Patel
2 tabs
typescript
import React from "react";
type FallbackProps = {
error: Error;
reset: () => void;
};
React Error Boundary + error reporting hook
react
frontend
error-boundary
by codesnips
3 tabs
javascript
const withBundleAnalyzer = require('@next/bundle-analyzer')({
enabled: process.env.ANALYZE === 'true',
openAnalyzer: true,
});
/** @type {import('next').NextConfig} */
Next.js bundle analyzer for targeted performance work
nextjs
performance
tooling
by codesnips
4 tabs
Share this code
Here's the card — post it anywhere.