Tips & Tricks

Claude Code के साथ Web Worker Implementation

Claude Code का उपयोग करके web worker implementation सीखें। Practical tips और code examples शामिल हैं।

Web Workerがज़रूरीな場面

JavaScriptはシングルthreadで動作するため、重い計算processingはUIをフリーズさせ है।Web Workerを使えば、バックグラウンドthreadでprocessingを実行し、メインthreadの応答性を維持でき है।Claude Code का उपयोग करके、型safeなWeb Worker通信の仕組みを素早くbuild किया जा सकता है。

型safeなWeb Worker通信

> TypeScriptで型safeなWeb Workerの通信レイヤーを作って。
> messageのtype definitionsとPromiseベースの呼び出しにsupportして。
// worker-types.ts
export interface WorkerRequest {
  id: string;
  type: string;
  payload: any;
}

export interface WorkerResponse {
  id: string;
  result?: any;
  error?: string;
}

// typed-worker.ts
type MessageHandler = (payload: any) => any | Promise<any>;

class TypedWorkerHost {
  private worker: Worker;
  private pending = new Map<string, { resolve: Function; reject: Function }>();
  private counter = 0;

  constructor(workerUrl: string | URL) {
    this.worker = new Worker(workerUrl, { type: 'module' });
    this.worker.onmessage = (e: MessageEvent<WorkerResponse>) => {
      const { id, result, error } = e.data;
      const handler = this.pending.get(id);
      if (!handler) return;
      this.pending.delete(id);
      error ? handler.reject(new Error(error)) : handler.resolve(result);
    };
  }

  call<T>(type: string, payload: any): Promise<T> {
    return new Promise((resolve, reject) => {
      const id = `msg-${++this.counter}`;
      this.pending.set(id, { resolve, reject });
      this.worker.postMessage({ id, type, payload } satisfies WorkerRequest);
    });
  }

  terminate() {
    this.worker.terminate();
    this.pending.forEach(({ reject }) => reject(new Error('Worker terminated')));
    this.pending.clear();
  }
}

worker側のimplementation

// heavy-computation.worker.ts
const handlers: Record<string, (payload: any) => any> = {
  'sort-data': (data: number[]) => {
    return data.sort((a, b) => a - b);
  },

  'filter-search': ({ items, query }: { items: any[]; query: string }) => {
    return items.filter((item) =>
      Object.values(item).some((v) =>
        String(v).toLowerCase().includes(query.toLowerCase())
      )
    );
  },

  'compute-statistics': (data: number[]) => {
    const n = data.length;
    const mean = data.reduce((a, b) => a + b, 0) / n;
    const sorted = [...data].sort((a, b) => a - b);
    const median = n % 2 === 0
      ? (sorted[n / 2 - 1] + sorted[n / 2]) / 2
      : sorted[Math.floor(n / 2)];
    const variance = data.reduce((sum, x) => sum + (x - mean) ** 2, 0) / n;

    return { mean, median, stdDev: Math.sqrt(variance), min: sorted[0], max: sorted[n - 1] };
  },
};

self.onmessage = async (e: MessageEvent<WorkerRequest>) => {
  const { id, type, payload } = e.data;

  try {
    const handler = handlers[type];
    if (!handler) throw new Error(`Unknown handler: ${type}`);
    const result = await handler(payload);
    self.postMessage({ id, result });
  } catch (error: any) {
    self.postMessage({ id, error: error.message });
  }
};

workerプール

> 複数のWorkerをmanagementするプールを作って。taskを効率よく分散して。
class WorkerPool {
  private workers: TypedWorkerHost[] = [];
  private queue: { type: string; payload: any; resolve: Function; reject: Function }[] = [];
  private busy: Set<number> = new Set();

  constructor(workerUrl: string, poolSize: number = navigator.hardwareConcurrency || 4) {
    for (let i = 0; i < poolSize; i++) {
      this.workers.push(new TypedWorkerHost(new URL(workerUrl, import.meta.url)));
    }
  }

  async execute<T>(type: string, payload: any): Promise<T> {
    const freeIndex = this.workers.findIndex((_, i) => !this.busy.has(i));

    if (freeIndex === -1) {
      return new Promise((resolve, reject) => {
        this.queue.push({ type, payload, resolve, reject });
      });
    }

    return this.runOnWorker(freeIndex, type, payload);
  }

  private async runOnWorker<T>(index: number, type: string, payload: any): Promise<T> {
    this.busy.add(index);
    try {
      return await this.workers[index].call<T>(type, payload);
    } finally {
      this.busy.delete(index);
      this.processQueue();
    }
  }

  private processQueue() {
    if (this.queue.length === 0) return;
    const freeIndex = this.workers.findIndex((_, i) => !this.busy.has(i));
    if (freeIndex === -1) return;

    const task = this.queue.shift()!;
    this.runOnWorker(freeIndex, task.type, task.payload)
      .then(task.resolve)
      .catch(task.reject);
  }

  terminate() {
    this.workers.forEach((w) => w.terminate());
  }
}

Reacthookでのutilization

function useWorker<T>(type: string, payload: any, deps: any[]) {
  const [result, setResult] = useState<T | null>(null);
  const [loading, setLoading] = useState(false);

  useEffect(() => {
    setLoading(true);
    pool.execute<T>(type, payload)
      .then(setResult)
      .finally(() => setLoading(false));
  }, deps);

  return { result, loading };
}

Summary

Claude Code का उपयोग करके、型safeなWeb Worker通信 सेworkerプール तक、並列processing基盤をefficientlybuild किया जा सकता है。performance全般はperformanceoptimizationを、Service Workerとの違いはService Workerutilizationをदेखें。

Web Worker APIの仕様はMDN Web Docs - Web Workersदेखें。

#Claude Code #Web Worker #並列processing #performance #TypeScript
मुफ़्त

मुफ़्त PDF: 5 मिनट में Claude Code चीटशीट

बस अपना ईमेल दर्ज करें और हम तुरंत A4 एक-पृष्ठ चीटशीट PDF भेज देंगे।

हम आपकी व्यक्तिगत जानकारी की सुरक्षा करते हैं और स्पैम नहीं भेजते।

Masa

लेखक के बारे में

Masa

Claude Code का गहराई से उपयोग करने वाले इंजीनियर। claudecode-lab.com चलाते हैं, जो 10 भाषाओं में 2,000 से अधिक पेजों वाला टेक मीडिया है।