ניהול סודות ב-GitOps: Sealed Secrets, SOPS, ESO

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

היכולות שלנו:

שאלות נפוצות

העבודות האחרונות

  • פיתוח אפליקציית ווב עבור FEEDME
    פיתוח אפליקציית ווב עבור FEEDME
    1359
  • פיתוח חנות מקוונת לחברת FURNORO
    פיתוח חנות מקוונת לחברת FURNORO
    1330
  • עיצוב לוגו לחברת B2B Advance
    עיצוב לוגו לחברת B2B Advance
    776
  • פיתוח אפליקציית ווב עבור Enviok
    פיתוח אפליקציית ווב עבור Enviok
    1077
  • פיתוח לוגו חברת AIDER
    פיתוח לוגו חברת AIDER
    1022
  • פיתוח CRM עבור Chasseurs
    פיתוח CRM עבור Chasseurs
    1113

ניהול סודות ב-GitOps: היכן נשבר קו האספקה

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

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

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

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

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

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

מה משתנה לאחר ההטמעה: מהירות, גישה, כשלים

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

שחזוריות סביבות

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

רוטציה מנוהלת ללא עצירת שירותים

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

מחלקת כשלים שהוסרה

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

השוואת גישות: הצפנה במאגר מול מאגרים חיצוניים

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

אפשרות מתי מתאימה מגבלות
הצפנת קבצים במאגר (SOPS, Sealed Secrets) קלאסטר אחד-שניים, צוות קטן, עשרות סודות מפתח הפענוח ממילא בקלאסטר; שלילת גישה — הצפנה מחדש של כל הקבצים
מאגר חיצוני ואופרטור סנכרון (ESO) ריבוי קלאסטרים, כמה צוותים, רוטציה לפי לוח זמנים נדרש קו אמין של המאגר וזמינות רשת; מחלקת כשלים משלו
היברידי: סודות אתחול במאגר, סודות עבודה בחיצוני גישות למאגר ואתחול ראשוני שני סטים של הרשאות ושתי פרוצדורות רוטציה

במה משלמים על הצפנת קבצים במאגר

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

מתי מוצדק מאגר חיצוני

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

שלבי ההטמעה: ביקורת, סכמה, הגדרה, בדיקה, העברה

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

איך נראית ביקורת המצב הנוכחי

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

בפלט — מפת תלויות ורשימת מקומות שבהם הסוד נחשף בגלוי: היסטוריית קומיטים, לוגים של בנייה, דאמפים של תצורה.

  1. ביקורת הטיפול בסודות — מפת תלויות, נקודות דליפה, שירותים קריטיים.
  2. סכמת קו האספקה — מה מוצפן במאגר, מה חי במאגר חיצוני, כיצד הערך מגיע ל-pod.
  3. הגדרת מדיניות גישה — תפקידים, מרחבי שמות, טווח הנראות של מפתחות.
  4. מיגרציה של סודות קיימים — אחד-אחד, עם עבודה מקבילה זמנית של הסכמה הישנה והחדשה.
  5. השתלבות בצינור הבנייה והמהדורה — בדיקות לזיהוי ערכים גלויים בקומיט.
  6. בדיקת כשל ושחזור — ריסטארט, אובדן צומת, שלילת מפתח, החזרת מהדורה לאחור.
  7. העברת קו האספקה לצוות — גישות, תקנון רוטציה, סקירה עם התורנים.

כיצד עוברת קבלת קו האספקה על ידי הלקוח

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

סכמות גישה, מדיניות רוטציה ותיעוד קו האספקה

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

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

כיצד חומרים אלה חיים לאחר ההעברה

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

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

מקרה בוחן: הוצאת סודות מהמאגר ללא השבתת שירותים

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

המעבר בוצע בשלבים — תחילה פיילוט על שירותים לא קריטיים, אחר כך שירותי עבודה — כדי לא לעצור את השירותים.

מה היה קודם

רוטציה של מפתח אחד נמשכה שבועיים-שלושה: התיקון הוכן ביד, אושר, המתין לחלון תחזוקה והשירותים הופעלו מחדש. החזרת שינוי לאחור משמעה שחזור מגיבוי והשוואת ערכים ידנית, בעוד שחלק מקו האספקה עבד עם המפתח הישן. מדידות לפני: מחוץ למאגר — אפס סודות, רוטציה ממוצעת — 18 ימים, השבתה בעת פריסה — עד 40 דקות.

מה נהיה לאחר

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

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

כיצד לבצע רוטציה של סודות ב-GitOps מבלי לעצור שירותים?

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

הטכניקה המרכזית — חלון חפיפת גישות. במאגר חיות בו-זמנית שתי גרסאות: החדשה והקודמת, שעדיין תקפה. האפליקציה מקבלת את החדשה דרך External Secrets Operator, והישנה נשארת פעילה עד שהמופע האחרון עובר אליה.

אם pod אחד פיגר או מחזיק חיבור למשאב חיצוני, הוא ממשיך לעבוד — רוטציה ללא השבתה נשענת בדיוק על החפיפה הזו.

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

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

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

ספקות הנדסיים: הצפנה, גישה, חזרה לאחור, ביקורת

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

מי והיכן מפענח את הסוד?

תלוי בכלי. Sealed Secrets חושף את הערך רק לקונטרולר בתוך הקלאסטר — המפתח הפרטי אינו נופל לא למאגר ולא לתחנות העבודה של המהנדסים. SOPS שומר את הצפנת-הצופן ב-git וחושף אותו במפתח age או GPG בשלב ההחלה.

External Secrets Operator אינו מחזיק ערכים במאגר: ב-git מונחת הפניה לרשומה במאגר חיצוני, והאובייקט נבנה בקלאסטר.

כיצד להפריד הרשאות בין צוותים וסביבות?

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

מה קורה בעת חזרה למהדורה קודמת?

חזרה לאחור היא revert של קומיט: הגרסה הקודמת של הסוד חוזרת באותה החלה כמו כל שינוי אחר. התנאי אחד — הערך חייב להישאר במקור. קונטרולר הקלאסטר או המאגר החיצוני מחזיקים היסטוריית גרסאות, אחרת החזרה לאחור תחזיר הפניה ללא נתונים, וה-pod עם הסוד לא יעלה.

כיצד בנויה ביקורת הגישה לסודות?

הביקורת נתפרת משלושה יומנים: היסטוריית קומיטים ומחבר השינוי ב-git, יומן הפניות ל-API של הקלאסטר, יומן הנפקות במאגר החיצוני. לפי שם הסוד והזמן רואים מי שינה את האובייקט, איזה קונטרולר קרא אותו והאם הייתה גישה מחוץ לקו הרגיל.

סודות שאי אפשר להניח ב-git אפילו מוצפנים — טוקנים שורשיים, תצורה ראשונית, מפתחות המאגר עצמו — מוציאים לקו נפרד של הזנה ידנית ואינם מועברים למאגר.

נדון במשימה ונחזור עם הערכה ותוכנית עבודה

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

מה מנתחים בשיחה:

  • ניתוח הסכמה הנוכחית: היכן מקור האמת לסודות, כיצד הם מגיעים למאגר, מה ובאיזה שלב מפוענח.
  • נקודות כשל: אחסון מפתחות הצפנה, גישות של חשבונות שירות, פערים בין סביבות, תרחיש חזרה לאחור.
  • השוואת אפשרויות — Sealed Secrets, SOPS, אופרטור סודות חיצוני — עם המגבלות של כל אחת ביחס לסכמה שלכם, ולא באופן כללי.
  • סדר השלבים: מה מעבירים ראשון, היכן משאירים קו ידני לתקופת מעבר, כיצד בודקים שהסוד הגיע.
  • הערכת היקף: הרכב התיקונים במניפסטים ובתפקידים, תקנון רוטציה, אזור האחריות על המפתחות.
  • מה נשאר אצל הצוות: תיעוד, תבניות סודות, בדיקות בצינור האספקה לפני החלת שינויים.

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