useQuery للقراءة. useMutation للكتابة: إضافة، تعديل، مسح.
import { useMutation, useQueryClient } from "@tanstack/react-query";function addStudent(newStudent) { return fetch("/api/students", { method: "POST", headers: { "Content-Type": "application/json" }, body: JSON.stringify(newStudent), }).then((res) => res.json());}function AddStudentForm() { const queryClient = useQueryClient(); const mutation = useMutation({ mutationFn: addStudent, onSuccess: () => { queryClient.invalidateQueries({ queryKey: ["students"] }); }, }); return ( <button onClick={() => mutation.mutate({ name: "أحمد", grade: "A" })} disabled={mutation.isPending} > {mutation.isPending ? "بيتضاف..." : "ضيف طالب"} </button> );}بعد الكتابة الناجحة، قول للمكتبة إن الرف ده بقى قديم. invalidateQueries يعمل كده، والقراءات المرتبطة تتجاب تاني. من غير الخطوة دي الشاشة تفضل على القائمة اللي قبل الإضافة.
exact
الفلتر مش دايمًا استعلام واحد. ساعات المفتاح بادئة، وعايز تلمس كل اللي تحتها.
تخيل الكاش فيه:
- مفتاح القائمة كلها
- مفتاح القائمة مع صف أ
- مفتاح القائمة مع صف ب
- مفتاح طالب برقمه
exact مش متحدد، يعني false. نداء الإبطال على بادئة الطلاب يلمس الأربعة، لأن كلهم بيبدأوا بنفس أول جزء.
queryClient.invalidateQueries({ queryKey: ["students"], exact: true,});كده القائمة العريانة بس. المفتاح اللي فيه الصف، أو رقم الطالب، مش هيتمس.
الافتراضي false لأن إضافة طالب عادةً لازم تحدّث كل العروض: القائمة، والمفلترة، وأي نسخة تانية من نفس البداية. من غير ما تكرر الإبطال لكل مفتاح.
استخدم exact: true لما التحديث لازم يكون على مطابقة حرفية. مفتاح درجات طالب، وفيه كمان مفتاح لنفس الطالب زائد خانة الدرجات: المطابقة الحرفية متلمسش الزيادة. من غيرها، أي مفتاح بيبدأ بنفس البادئة يتبطّل.
queryClient.invalidateQueries({ queryKey: ["grades", studentId], exact: true,});