Sqlite - עבודה עם WAL.

ב־4.12.2011, מאת ארתיום; פורסם תחת: תכנה חופשית, פיתוח, תכנה ומחשבים; ‏0 תגובות

אומנם גרסה 3.7 של Sqlite שוחררה יותר מלפני שנה, לא רבים שמו לב לשורה הקצרה ברשימת השינויים:

Added support for write-ahead logging.‎

זאת שיטת עבודה שכל בסיס נתונים מודרני עובד איתה, לעומת שיטת העבודה הרגילה של Sqlite3 והיא ניהול "לוג לשחזור לאחור" - Rollback.

כיצד קובץ Rollback עובד. בכל פעם שרוצים לעשות שינויים בדף של קובץ בסיס הנתונים, רושמים את הערכים בקודמים בקובץ במיוחד. כך שאם ניפול, נדע בדיוק איך לשחזר את המצב הקודם. אז בכל טרנזקציה Sqlite3 מבצע את הפעולות הבאות: רושם את הכל המחיקות לקובץ rollback ומבצע fsync עליו, לאחר מכן מעדכן את בסיס הנתונים הראשי ומוודא כי הנתונים הגיעו לדיסק עם fsync נוסף ובסוף מוחק את קובץ ה־rollback. מה שחשוב כאן זה שקריאת מערכת הפעלה fsync, מתבצעת פעמיים: פעם על קובץ לוג ופעם על הקובץ הראשי. הקריאה הזו מבטיחה שהמידע הגיע לדיסק פיזי והיא כמובן מאוד יקרה מבחינת הזמן.

השיטה החדשה שמומשה בגרסה 3.7, עובדת עם קובץ WAL -‏ Write Ahead Log. כל שינוי נרשם לקובץ הלוג והקובץ המקורי נשמר ללא שינויים. מה שחשוב כאן שכדי להבטיח שרידות מספיק לקרוא fsync - פעם אחת בלבד עבור קובץ WAL. הטרנזקציות הבאות יוסיפו עוד מידע לסוף הקובץ. אחת לכמה זמן sqlite3 מעביר את כל השינויים לקובץ בסיס הנתונים המקורי ומאפס את קובץ הלוג. יותר מזה, כיוון שהקובץ המקורי נשאר ללא שינויים אז טרנזקציות קריאה יכולות לרוץ במקביל לטרנזקציות כתיבה.

השיטה החדש מבטיחה מהירות ביצוע טרנזקציה גבוהה יותר בגלל ש־fsync נקרא רק פעם אחת. בנוסף וגם עדכונים לא מעכבים את טרנזקציות השליפה.

כך שאם אתם משתמשים פעילים של Sqlite3 - תבדקו את האופציה

PRAGMA journal_mode=WAL;

היא יכול לשפר משמעותית את היישומים שלכם.

בנוסף עם תמיכה ב־WAL, התווספה עוד אופציה מעניינת שמאפשרת להאיץ פעולות עדכון של בסיס נתונים בצורה משמעותית בלי לפגוע בקונסיסטינטיות שלו. כלומר לוותר על ה־D של ACID.

אם מגדירים

PARAGMA synchronous=NORMAL

אז במצב של WAL ה־fsyncים שמבטיחים את ה־D -‏ Durability ייקראו רק פעם ב־checkpoint ולא כל טרזקציה. אם המחשב קורס (חשמל/חומרה) אז אנחנו נאבד מספר טרנזקציות אחרונות אבל בסיס הנתונים יישאר תקין, במילים אחרות, אנחנו ניפול בגבול טרנזקציה, אבל לאו דווקא הטרנזקציה האחרונה. שיטה זו מאפשר להגדיל מספר עדכונים מכמה עשרות בשנייה לכמה אלפים.

גם חלק מבסיסי הנתונים הגדולים תומכים באפשרות העבודה ב־ACI ללא D.

למשל, ב־PostgreSQL ניתן להגדיר אופציה synchonous_commits=off ברמת הקשר. אז עדכון הלוג יתבצע ללא fsync ורק פעם בשניה יתבצע עדכון מלא. בבסיס הנתונים MySQL אפשר להגדיר את זה בעזרת אופציה innodb_flush_log_at_trx_commit=2, אבל ההגדרה הזו תעבוד ברמת שרת MySQL כולו ולא רק ברמת הקשר או בסיס הנתונים הספציפי.

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

הוסף תגובה:

 
 כתובת דוא"ל לא תוצג
 

ניתן לכתוב תגובות עם שימוש בתחביר Markdown.

חובה לאפשר JavaScript כדי להגיב.

דפים

נושאים