• בלוג
  • לא לדאוג, אני מכיר את find

לא לדאוג, אני מכיר את find

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

כל עוד מדובר ב 2-3 פרויקטים אין בעיה לעבור אחד אחד, אבל כשיש עשרות הרבה יותר כיף להשתמש ב find.

המשימה הראשונה היא למצוא את כל תיקיות הפרויקטים, כלומר התיקיות ברמה "הראשית". בשביל זה find מציע לנו את maxdepth, type ו mindepth. עבור דוגמה פשוטה שמכילה שלוש תיקיות פרויקטים בשמות a, b ו c אני מריץ:

$ find . -mindepth 1 -maxdepth 1 -type d

./a
./c
./b

בזכות מסנן ה type הפקודה מדפיסה רק את התיקיות גם אם היו קבצים בתיקיה הראשית. אפשר לסנן עוד יותר גם לפי שמות קבצים של אותן תיקיות פרויקטים עם תוספת מתג -name.

אחרי שיש לנו את תיקיות הפרויקטים צריך בכל תיקיה להריץ את הפקודות:

mkdir app && mv * app

שימו לב לסימן ה && בין שתי הפקודות: אני רוצה להריץ את ה mv רק אם הצלחתי ליצור את התיקיה. אם mkdir נכשל זה כנראה אומר ש app היתה שם קודם (למרות שיכול להיות שמדובר בבעיית הרשאות, אבל גם במקרה כזה אין טעם לנסות להעביר לשם קבצים).

בשביל זה ל find יש כפתור exec. אבל אני לא יכול להריץ ישירות את ה && בתוך ה exec ולכן אני מריץ עותק חדש של bash שיפעיל את שתי הפקודות:

find . -mindepth 1 -maxdepth 1 -type d -exec bash -c "mkdir {}/app && mv {}/* {}/app" \;

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