Consistent Hashing: איך מפזרים מפתחות בלי לערבב הכל מחדש בכל שינוי

מאת צוות מדיה דיל · 29.06.2026 · טכנולוגיה · 4 דק׳

Hash Ring, Virtual Nodes, מודולו מול Consistent Hashing, CDN Routing, Cache Clusters, ו-Rebalancing מינימלי.

מערכת cache עם עשרה שרתים מחלקת מפתחות לפי הנוסחה הפשוטה ביותר: hash(key) % N. זה עובד מצוין עד שמוסיפים שרת אחד עשר, N משתנה, וכמעט כל מפתח מקבל יעד שונה מזה שהיה לו קודם. במקום ששרת חדש יספוג רק את החלק היחסי שלו בעומס, כל ה-cache מתרוקן בבת אחת וכל הבקשות פונות מחדש למקור. Consistent Hashing נבנה כדי לפתור בדיוק את זה: להוסיף או להסיר שרת בלי לטלטל את רוב המפתחות ממקומם.

הבעיה: מודולו רגיל שובר הכל בכל שינוי

כש-N בנוסחת hash(key) % N משתנה, כמעט כל תוצאת המודולו משתנה יחד איתו, גם אם רק שרת אחד נוסף או נפל. בקנה מידה של cache cluster זה אומר cache stampede: כל הבקשות פוגעות שוב במסד הנתונים או ב-origin server בו-זמנית, בדיוק ברגע שהמערכת הכי פחות יכולה לספוג את זה. הבעיה מחריפה ככל שהאשכול גדול יותר וככל ששינויי גודל, scale up או scale down, נפוצים יותר, מה שהופך פתרון naive לבלתי שמיש בסביבת ענן אלסטית.

הפתרון: Hash Ring במקום מודולו

Consistent Hashing ממפה גם שרתים וגם מפתחות לאותו מרחב ערכים מעגלי, hash ring, למשל טווח של 0 עד 2^32 מוצג כמעגל. כל שרת ממופה למיקום אחד או יותר על הטבעת, וכל מפתח משויך לשרת הראשון שנמצא כשמתקדמים בכיוון השעון ממיקומו. כשמוסיפים שרת, הוא נכנס לטבעת בין שני שכנים קיימים ותופס רק את המפתחות שהיו שייכים לשכן שאחריו, לא לכל האשכול. כשמורידים שרת, רק המפתחות שהיו שייכים לו עוברים לשכן הבא. השינוי נשאר מקומי.

Virtual Nodes ופיזור אחיד

מיפוי כל שרת לנקודה אחת בטבעת יוצר בעיה: אם שרת אחד נופל במקרה על קטע גדול של המעגל, הוא מקבל עומס לא פרופורציונלי, ואם שני שרתים נופלים קרוב זה לזה, החלוקה הופכת לא אחידה. הפתרון הוא Virtual Nodes: כל שרת פיזי ממופה למאות נקודות שונות על הטבעת במקום אחת. ככל שיש יותר virtual nodes, הפיזור מתקרב לאחיד סטטיסטית, וגם ההשפעה של הוספה או הסרה של שרת מתפזרת על פני הרבה שכנים קטנים במקום להתרכז בשכן יחיד אחד.

שימוש ב-CDN ו-Request Routing

רשתות CDN משתמשות ב-Consistent Hashing כדי להחליט לאיזה edge server לנתב בקשה לפי ה-URL או שם הקובץ, כך שאותו תוכן תמיד יגיע לאותו שרת קרוב, מה שמקסם cache hit rate ומאפשר להוסיף POP חדש מבלי לפזר מחדש את כל טבלת הניתוב. אותו עיקרון עומד גם מאחורי שירותי load balancing מבוססי consistent hashing, שם הבחירה היא לא רק איזה שרת פנוי אלא איזה שרת כבר מחזיק ב-cache הרלוונטי, מה שמפחית עומס על שכבות backend כבדות ומשפר latency.

Cache Clusters ו-Rebalancing מינימלי

ב-cache clusters כמו Memcached או Redis Cluster, Consistent Hashing מבטיח שהוספת node לא תגרום ל-cache miss גורף. בפועל רק כ-1/N מהמפתחות זזים כשמוסיפים שרת ל-N שרתים קיימים, יחס שנשאר קבוע בלי תלות בגודל האשכול, בניגוד למודולו הרגיל שבו כמעט הכל זז. זה מה שהופך scaling אלסטי, הוספה והסרה דינמית של שרתים לפי עומס, לישים בפועל, בלי לשלם מחיר של קריסת cache בכל שינוי טופולוגיה.

מגבלות: Hot Keys ואיזון עומס לא אחיד

Consistent Hashing פותר איזון גודל אשכול אבל לא איזון פופולריות: אם מפתח בודד מקבל תעבורה חריגה, סלבריטי פוסט ויראלי, מוצר במבצע, כל הבקשות עדיין נופלות על אותו שרת יעד, ללא קשר לגודל הטבעת. פתרונות בפועל משלבים replication של מפתחות חמים על כמה שרתים או שכבת routing נוספת שמזהה hot spots. בנוסף, שמירת עקביות בין node membership לבין הטבעת עצמה דורשת מנגנון תיאום, ולעיתים קרובות נשען על Gossip Protocol להפצת מידע על שרתים שהצטרפו או נפלו.

בונים מערכת שצריכה scale אלסטי בלי cache stampede בכל שינוי גודל? נשמח לעזור לכם בוואטסאפ.

תגיות: Consistent Hashing · Hash Ring · Virtual Nodes · Cache Clusters · CDN · Load Balancing

← חזרה לבלוג · צור קשר