useEffect

Side effect nedir, useEffect ile nasıl çalıştırılır, dependency array'in üç kullanımı, cleanup fonksiyonu ve yaygın infinite loop hatası -- basit örneklerle.

Orta 14 dk
EN

useEffect

What Are Hooks? dersinde hook kavramını gördük. Bu ders, en sık kullanılan hook'lardan biriyle -- useEffect -- component'inin dışına çıkıp bir şeyler yapmasını (bir side effect) sağlamayı anlatıyor.

Side Effect (Yan Etki) Nedir?

Bir side effect, component'in kendi render çıktısı (yani döndürdüğü JSX) DIŞINDA yaptığı bir şeydir: tarayıcının sekme başlığını değiştirmek, bir zamanlayıcı (timer) kurmak, veri çekmek, localStorage'a yazmak gibi. useEffect, bu tür işleri güvenli bir şekilde yapmanı sağlayan hook.

Temel useEffect Kullanımı

useEffect'e bir fonksiyon verirsin; React bu fonksiyonu render bittikten SONRA çalıştırır:

import { useState, useEffect } from "react";

function BasicUseEffectExample() {
  const [count, setCount] = useState(0);

  // Bir SIDE EFFECT: component'in kendi render çıktısı (JSX) dışında
  // yaptığı bir şey -- burada tarayıcının sekme başlığını değiştiriyoruz.
  useEffect(() => {
    document.title = `Sayaç: ${count}`;
  });

  return (
    <div>
      <p>Sayaç: {count}</p>
      <button onClick={() => setCount(count + 1)}>+1</button>
    </div>
  );
}

Burada her render'dan sonra sekme başlığını güncelliyoruz -- bu, JSX'in kendisinin yapamayacağı bir iş, çünkü document.title, ekrana çizilen component ağacının dışında, tarayıcının kendi bir özelliği.

Dependency Array: Boş Dizi []

useEffect'in ikinci parametresi, isteğe bağlı bir dependency array (bağımlılık dizisi). Boş bir dizi [] verirsen, effect yalnızca component ilk kez ekrana geldiğinde (mount olduğunda) bir kez çalışır:

import { useState, useEffect } from "react";

function EmptyDependencyArrayExample() {
  const [count, setCount] = useState(0);

  useEffect(() => {
    console.log("Component ilk kez ekrana geldi (mount oldu).");
  }, []); // Boş dependency array: yalnızca İLK render'dan sonra bir kez çalışır.

  return (
    <div>
      <p>Sayaç: {count}</p>
      <button onClick={() => setCount(count + 1)}>+1</button>
    </div>
  );
}

Sonraki render'larda (state her değiştiğinde) bu effect BİR DAHA ÇALIŞMAZ -- yalnızca ilk render'dan sonra.

Dependency Array: Belirli Değerler

Dependency array'e belirli değerler koyarsan, effect yalnızca O DEĞERLER değiştiğinde çalışır:

import { useState, useEffect } from "react";

function DependencyArrayExample() {
  const [count, setCount] = useState(0);
  const [name, setName] = useState("Ayşe");

  useEffect(() => {
    console.log("count değişti:", count);
  }, [count]); // Yalnızca count değiştiğinde çalışır -- name değişse de çalışmaz.

  return (
    <div>
      <p>
        {name}, sayaç: {count}
      </p>
      <button onClick={() => setCount(count + 1)}>Sayacı Artır</button>
      <button onClick={() => setName(name === "Ayşe" ? "Mehmet" : "Ayşe")}>
        İsmi Değiştir
      </button>
    </div>
  );
}

[count] yazdığımız için effect yalnızca count değiştiğinde çalışır -- name değişse bile effect tetiklenmez. React, her render'da dependency array'deki değerleri bir önceki render'la karşılaştırır; en az biri değiştiyse effect'i çalıştırır.

Cleanup Fonksiyonu

Bazı effect'ler (zamanlayıcı kurmak, bir event listener eklemek gibi) "temizlenmesi" gereken bir şey bırakır. useEffect'in verdiği fonksiyon bir CLEANUP fonksiyonu döndürebilir:

import { useState, useEffect } from "react";

function CleanupFunctionExample() {
  const [seconds, setSeconds] = useState(0);

  useEffect(() => {
    const intervalId = setInterval(() => {
      setSeconds((prev) => prev + 1);
    }, 1000);

    // Cleanup fonksiyonu: component ekrandan kalktığında (unmount) ya da
    // effect yeniden çalışmadan HEMEN ÖNCE React bunu otomatik çağırır.
    // Burada, interval'i temizlemezsek, component ekrandan kalktıktan
    // sonra bile arka planda çalışmaya devam eder -- bir "memory leak".
    return () => {
      clearInterval(intervalId);
    };
  }, []);

  return <p>Geçen süre: {seconds} saniye</p>;
}

React, cleanup fonksiyonunu component ekrandan kalktığında (unmount) ya da effect yeniden çalışmadan HEMEN ÖNCE otomatik çağırır. Burada clearInterval ile zamanlayıcıyı durdurmazsak, component ekrandan kalktıktan sonra bile arka planda çalışmaya devam eder.

Yaygın Hata: Infinite Loop

En yaygın useEffect hatası, dependency array'i unutup effect içinde state güncellemektir:

import { useState, useEffect } from "react";

function InfiniteLoopMistakeExample() {
  const [count, setCount] = useState(0);

  // YANLIŞ: dependency array'siz bir useEffect, HER render'dan sonra çalışır.
  // İçinde state güncellenirse, bu güncelleme yeni bir render tetikler,
  // o render yine effect'i çalıştırır -- SONSUZ DÖNGÜ.
  // useEffect(() => {
  //   setCount(count + 1);
  // });

  // DOĞRU: dependency array'i [] yaparak yalnızca ilk render'da çalıştır.
  useEffect(() => {
    setCount((prev) => prev + 1);
  }, []);

  return <p>Sayaç (yalnızca 1 kez artmalı): {count}</p>;
}

Dependency array'siz bir useEffect, HER render'dan sonra çalışır. İçinde state güncellenirse, bu güncelleme yeni bir render tetikler, o render yine effect'i çalıştırır -- SONSUZ DÖNGÜ. Çözüm, dependency array'i doğru kurmak: yalnızca bir kez çalışması gerekiyorsa [], belirli bir değere bağlıysa o değeri diziye koymak.

Özet ve Terimler Sözlüğü

useEffect, component'in render çıktısı dışında bir şey yapması (side effect) gerektiğinde kullanılır. Dependency array, effect'in NE ZAMAN çalışacağını belirler: [] yalnızca ilk render'da, [deger] yalnızca o değer değiştiğinde, hiç dependency array olmaması ise HER render'dan sonra. Cleanup fonksiyonu, effect'in bıraktığı şeyleri (timer, event listener gibi) temizler. Dependency array'i unutup effect içinde state güncellemek, en yaygın hata olan infinite loop'a yol açar.

Terimler Sözlüğü

Side Effect (Yan Etki) — Bir component'in render çıktısı dışında yaptığı bir şey (DOM'u doğrudan değiştirmek, veri çekmek gibi).

useEffect — Component'e side effect çalıştırma yeteneği ekleyen hook.

Dependency Array (Bağımlılık Dizisi)useEffect'in ikinci parametresi; effect'in hangi değerler değiştiğinde yeniden çalışacağını belirler.

Cleanup FonksiyonuuseEffect'in verdiği fonksiyondan döndürülen, effect'in bıraktığı şeyleri temizleyen fonksiyon; component unmount olduğunda ya da effect yeniden çalışmadan önce çağrılır.

Mount / Unmount — Bir component'in ekrana ilk kez gelmesi (mount) ve ekrandan tamamen kaldırılması (unmount).