• בלוג
  • הצילו! הקבצים המשובטים באים!

הצילו! הקבצים המשובטים באים!

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

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

1. איך יודעים ששני קבצים הם זהים

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

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

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

הכנתי כבר תיקיה עם מספר קבצים זהים, ולכן נסיון ראשון יכול להיות להריץ את md5 בשילוב עם find:

$ find . -type f -exec md5sum {} \;
46bc5d1248d333b0c6894184a1b3e318  ./foo/passwd
08b13f1da69ce112a43bbace8436e7a7  ./foo/shells
cfbad46a63413dcf498ba1058631c823  ./hosts
46bc5d1248d333b0c6894184a1b3e318  ./passwd

קל לראות שיש 4 קבצים בתיקיה מתוכם שניים זהים (לפי זה שיש להם את אותו ערך MD5). אבל מה נעשה כשיהיו יותר קבצים בתיקיה? האם אפשר לקבל הדפסה נחמדה יותר של הפלט?

2. שילוב awk

בהחלט כן! שיחה מקרית עם חבר הזכירה לי כמה אני אוהב את awk, בדיוק למקרים כאלה. מסתבר של awk יש תחביר מערכים שמאפשר שמירה ועיבוד של קלט מהסוג שראינו. הנה אותה הפקודה עם תוספת awk (שימו לב שיש צורך לגלול ימינה כדי לצפות בכל השורה. לא רציתי לחתוך באמצע שיהיה קל לעשות copy/paste):

$ find . -type f -exec sha1sum {} \;|awk '{ f[$1] = f[$1] ? f[$1] "\t" $2 : $2 } END { for (hash in f) print f[hash]}'
./foo/passwd    ./passwd
./hosts
./foo/shells

הפעם אין לנו הדפסה של Hash Value ובמקום כל הקבצים שיש להם את אותו ערך מודפסים באותה השורה כך שקל לראות אותם.

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