Labs

Code Snippets

Useful code snippets, patterns, and mini experiments I use regularly.

Backend (1)Browser (1)React (2)Utility (4)

Debounce Function

Utility

A generic debounce utility for limiting function execution rate.

typescript
function debounce<T extends (...args: unknown[]) => void>(
  fn: T,
  delay: number
): (...args: Parameters<T>) => void {
  let timer: ReturnType<typeof setTimeout>
  return (...args) => {
    clearTimeout(timer)
    timer = setTimeout(() => fn(...args), delay)
  }
}

// Usage
const handleSearch = debounce((query: string) => {
  console.log('Searching:', query)
}, 300)

useLocalStorage Hook

React

A React hook that syncs state with localStorage.

typescript
import { useState, useEffect } from 'react'

function useLocalStorage<T>(key: string, initialValue: T) {
  const [value, setValue] = useState<T>(() => {
    if (typeof window === 'undefined') return initialValue
    try {
      const item = localStorage.getItem(key)
      return item ? JSON.parse(item) : initialValue
    } catch {
      return initialValue
    }
  })

  useEffect(() => {
    localStorage.setItem(key, JSON.stringify(value))
  }, [key, value])

  return [value, setValue] as const
}

cn() Class Merge Helper

Utility

Merge Tailwind classes with clsx and tailwind-merge.

typescript
import { clsx, type ClassValue } from 'clsx'
import { twMerge } from 'tailwind-merge'

export function cn(...inputs: ClassValue[]) {
  return twMerge(clsx(inputs))
}

// Usage
cn('px-4 py-2', isActive && 'bg-blue-500', 'text-white')

Fetch with Retry

Utility

A fetch wrapper that retries on failure with exponential backoff.

typescript
async function fetchWithRetry(
  url: string,
  options?: RequestInit,
  retries = 3,
  backoff = 300
): Promise<Response> {
  for (let i = 0; i < retries; i++) {
    try {
      const res = await fetch(url, options)
      if (res.ok) return res
      throw new Error(`HTTP ${res.status}`)
    } catch (err) {
      if (i === retries - 1) throw err
      await new Promise(r => setTimeout(r, backoff * 2 ** i))
    }
  }
  throw new Error('Unreachable')
}

Prisma Client Singleton

Backend

Prevent multiple Prisma client instances in Next.js development.

typescript
import { PrismaClient } from '@prisma/client'

const globalForPrisma = globalThis as unknown as {
  prisma: PrismaClient | undefined
}

export const prisma =
  globalForPrisma.prisma ??
  new PrismaClient({ log: ['query'] })

if (process.env.NODE_ENV !== 'production')
  globalForPrisma.prisma = prisma

useIntersectionObserver

React

A hook to detect when an element enters the viewport.

typescript
import { useEffect, useRef, useState } from 'react'

function useIntersectionObserver(
  options?: IntersectionObserverInit
) {
  const ref = useRef<HTMLElement>(null)
  const [isVisible, setIsVisible] = useState(false)

  useEffect(() => {
    const el = ref.current
    if (!el) return

    const observer = new IntersectionObserver(([entry]) => {
      setIsVisible(entry.isIntersecting)
    }, options)

    observer.observe(el)
    return () => observer.disconnect()
  }, [options])

  return { ref, isVisible }
}

Date Formatter

Utility

Clean relative and absolute date formatting.

typescript
function formatRelativeDate(date: Date): string {
  const now = new Date()
  const diff = now.getTime() - date.getTime()
  const seconds = Math.floor(diff / 1000)
  const minutes = Math.floor(seconds / 60)
  const hours = Math.floor(minutes / 60)
  const days = Math.floor(hours / 24)

  if (seconds < 60) return 'just now'
  if (minutes < 60) return `${minutes}m ago`
  if (hours < 24) return `${hours}h ago`
  if (days < 7) return `${days}d ago`

  return date.toLocaleDateString('en-US', {
    month: 'short',
    day: 'numeric',
    year: date.getFullYear() !== now.getFullYear() ? 'numeric' : undefined,
  })
}

Copy to Clipboard

Browser

Cross-browser clipboard utility with fallback.

typescript
async function copyToClipboard(text: string): Promise<boolean> {
  // Modern API
  if (navigator.clipboard?.writeText) {
    try {
      await navigator.clipboard.writeText(text)
      return true
    } catch {}
  }

  // Fallback for older browsers
  const textarea = document.createElement('textarea')
  textarea.value = text
  textarea.style.position = 'fixed'
  textarea.style.opacity = '0'
  document.body.appendChild(textarea)
  textarea.select()

  try {
    document.execCommand('copy')
    return true
  } catch {
    return false
  } finally {
    document.body.removeChild(textarea)
  }
}