עובדי Multiplex (תכונה ניסיונית)

במאמר הזה מתוארים מדריכי Multiplex, איך לכתוב כללים תואמים ל-Multiplex ופתרונות זמניים למגבלות מסוימות.

עובדי Multiplex מאפשרים ל-Bazel לטפל בבקשות מרובות בתהליך עובדים יחיד. עבור עובדים בעלי שרשורים מרובים, בזל יכולה להשתמש בפחות משאבים כדי להשיג ביצועים זהים או טובים יותר. לדוגמה, במקום שכל תהליך עבודה יגיע לעובדים, תוכלו לשמור על קשר של ארבעה עובדים עם אותו מספר עובדים, שיוכלו לטפל בבקשות במקביל. עבור שפות כמו Java ו-Scala, שמירת זמן החימום של JVM ומשך האיסוף של JIT גדולה, ובאופן כללי היא מאפשרת להשתמש במטמון משותף אחד לכל העובדים מאותו סוג.

סקירה כללית

יש שתי שכבות בין שרת ה-Bazel לבין התהליך לעובדים. לארכיטקטורה מסוימת שאפשר להריץ תהליכים במקביל, בזל מקבל WorkerProxy ממאגר העובדים. ב-WorkerProxy הבקשות נשלחות לעיבוד העובד ברציפות יחד עם request_id, תהליך העיבוד מעבד את הבקשה ושולח תשובות אל WorkerMultiplexer. כשהמערכת WorkerMultiplexer מקבלת תגובה, היא מנתחת את request_id ולאחר מכן מעבירה את התגובות בחזרה אל WorkerProxy הנכון. בדיוק כמו עם עובדים ללא ריבוי משתמשים, כל התקשורת מבוצעת באופן רגיל או מושבת, אבל הכלי לא יכול להשתמש רק ב-stderr כדי לקבל פלט גלוי למשתמש (ראו בהמשך).

לכל עובד יש מפתח. Bazel משתמשת בקוד הגיבוב (hash) של המפתח (המורכב ממשתני סביבה, שורש הביצוע וה ישרה) כדי לקבוע באיזה WorkerMultiplexer להשתמש. WorkerProxy מתקשרים עם אותו WorkerMultiplexer באמצעות אותו קוד גיבוב. לכן, בהנחה שמשתני הסביבה ושורש הביצוע זהים בהפעלה אחת ב-Bazel, לכל מינון יכול להיות תהליך אחד ועובד אחד בלבד. המספר הכולל של העובדים, כולל עובדים קבועים ו-WorkerProxy, עדיין מוגבל על ידי --worker_max_instances.

כתיבה של כללים תואמים ל-Multiplex

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

טיפול בפלט Multiplex

עובדי Multiplex צריכים להיות זהירים יותר בכל הקשור לטיפול בפלט. כל מה שיישלח אל stderr יועבר לקובץ יומן יחיד המשותף בין כל ה-WorkerProxy מאותו סוג, שמשולבים בו בצורה אקראית בין הבקשות המקבילות. הפניה אוטומטית של stdout אל stderr היא רעיון טוב, אבל לא כדאי לאסוף את הפלט הזה בשדה output של WorkResponse, כי מידע זה עלול להראות את פלט הפלט של המשתמש מעורפל. אם הכלי שלכם שולח פלט שמכוון למשתמשים רק אל stdout או stderr, עליכם לשנות את ההתנהגות הזו כדי להפעיל עובדי Multiplex.

הפעלה של עובדי Multiplex

עובדי Multiplex לא מופעלים כברירת מחדל. כלב מפעיל יכול להפעיל את ריבוי העובדים באמצעות התג supports-multiplex-workers ב-execution_requirements של פעולה (בדומה לתג supports-workers שמפעיל עובדים רגילים). כמו שקורה כשמשתמשים בעובדים רגילים, צריך לציין אסטרטגיית עבודה ברמת הכלל (לדוגמה, --strategy=[some_mnemonic]=worker), או ברמת השיטה (לדוגמה, --dynamic_local_strategy=worker,standalone.) אין צורך בסימונים נוספים, וsupports-multiplex-workers מקבל עדיפות על פני supports-workers, אם שניהם מוגדרים. כדי להשבית את עובדי ה-Multiplex באופן גלובלי, צריך לעבור את --noexperimental_worker_multiplex.

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

ארגז חול של Multiplex

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

כדי לתמוך בארגז חול של Multiplex, העובדים צריכים להשתמש בשדה sandbox_dir מה-WorkRequest ולהשתמש בו כקידומת לכל ההקראה והכתיבה של הקבצים. השדות arguments ו-inputs לא משתנים מבקשה ללא ארגז חול, אבל הקלט בפועל הוא יחסי ל-sandbox_dir. העובד חייב לתרגם נתיבי קבצים שנמצאו ב-arguments וב-inputs כדי לקרוא מהנתיב שהשתנה, והוא חייב גם לכתוב את כל התוצאות בהתאם ל-sandbox_dir. נכללים בכך נתיבים כמו '.' וכן נתיבים שנמצאו בקבצים שצוינו בארגומנטים (כגון ארגומנטים מסוג "argfile" ).

אחרי שהעובד תומך בארגז חול עם כמה ארגזים, הכללים יכולים להצהיר על התמיכה על ידי הוספת supports-multiplex-sandboxing לפעולה execution_requirements. לאחר מכן, ה-Bazel ישתמש בארגז חול עם מספר קומות אם ההתרעה של --experimental_worker_multiplex_sandboxing תעבור, או אם העובד ישמש לביצוע דינמי.

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