การปรับกฎของ Bazel เพื่อการเรียกใช้ระยะไกล

หน้านี้มีไว้สำหรับผู้ใช้ Bazel ที่เขียนกฎการสร้างและการทดสอบที่กำหนดเอง ซึ่งต้องการทำความเข้าใจข้อกำหนดสำหรับกฎ Bazel ในบริบทของการดำเนินการจากระยะไกล

การดำเนินการจากระยะไกลช่วยให้ Bazel ดำเนินการในแพลตฟอร์มแยกต่างหากได้ เช่น ศูนย์ข้อมูล Bazel ใช้ โปรโตคอล gRPC สำหรับการดำเนินการจากระยะไกล คุณสามารถลองใช้การดำเนินการจากระยะไกลด้วย bazel-buildfarm, ซึ่งเป็นโปรเจ็กต์แบบโอเพนซอร์สที่มีเป้าหมายเพื่อจัดหาแพลตฟอร์มการดำเนินการจากระยะไกลแบบกระจาย

หน้านี้ใช้คำศัพท์ต่อไปนี้เมื่ออ้างถึงประเภทสภาพแวดล้อมหรือ แพลตฟอร์มต่างๆ

  • แพลตฟอร์มโฮสต์ - ที่ Bazel ทำงาน
  • แพลตฟอร์มการดำเนินการ - ที่การดำเนินการของ Bazel ทำงาน
  • แพลตฟอร์มเป้าหมาย - ที่เอาต์พุตบิลด์ (และการดำเนินการบางอย่าง) ทำงาน

ภาพรวม

เมื่อกำหนดค่าการสร้าง Bazel สำหรับการดำเนินการจากระยะไกล คุณต้องปฏิบัติตามหลักเกณฑ์ที่อธิบายไว้ในหน้านี้เพื่อให้แน่ใจว่าการสร้างจะดำเนินการจากระยะไกลโดยไม่มีข้อผิดพลาด ซึ่งเป็นผลมาจากลักษณะของการดำเนินการจากระยะไกล ดังนี้

  • การดำเนินการบิลด์ที่แยกกัน เครื่องมือสร้างจะไม่เก็บสถานะไว้และทรัพยากร Dependency จะไม่รั่วไหลระหว่างเครื่องมือ

  • สภาพแวดล้อมการดำเนินการที่หลากหลาย การกำหนดค่าบิลด์ในเครื่องอาจไม่เหมาะกับสภาพแวดล้อมการดำเนินการจากระยะไกลเสมอไป

หน้านี้อธิบายปัญหาที่อาจเกิดขึ้นเมื่อใช้กฎการสร้างและการทดสอบ Bazel ที่กำหนดเองสำหรับการดำเนินการจากระยะไกล รวมถึงวิธีหลีกเลี่ยงปัญหาดังกล่าว โดยครอบคลุมหัวข้อต่อไปนี้

การเรียกใช้เครื่องมือบิลด์ผ่านกฎ Toolchain

กฎ Toolchain ของ Bazel เป็นผู้ให้บริการการกำหนดค่าที่บอกกฎการสร้างว่าจะใช้เครื่องมือสร้างใด เช่น คอมไพเลอร์และลิงเกอร์ รวมถึงวิธีกำหนดค่าเครื่องมือเหล่านั้นโดยใช้พารามิเตอร์ที่กำหนดโดยผู้สร้างกฎ กฎ Toolchain ช่วยให้กฎการสร้างและการทดสอบเรียกใช้เครื่องมือสร้างในลักษณะที่คาดการณ์ได้และกำหนดค่าไว้ล่วงหน้า ซึ่งเข้ากันได้กับการดำเนินการจากระยะไกล ตัวอย่างเช่น ใช้กฎ Toolchain แทนการเรียกใช้เครื่องมือสร้างผ่าน PATH, JAVA_HOME หรือตัวแปรในเครื่องอื่นๆ ที่อาจไม่ได้ตั้งค่าเป็นค่าเทียบเท่า (หรือไม่ได้ตั้งค่าเลย) ในสภาพแวดล้อมการดำเนินการจากระยะไกล

ปัจจุบันมีกฎ Toolchain สำหรับกฎการสร้างและการทดสอบ Bazel สำหรับ Scala, Rust, และ Go, รวมถึงกฎ Toolchain ใหม่สำหรับภาษาและเครื่องมืออื่นๆ เช่น Bashกำลังอยู่ระหว่างการพัฒนา หากไม่มีกฎ Toolchain สำหรับเครื่องมือที่กฎของคุณใช้ ให้พิจารณา สร้างกฎ Toolchain

การจัดการทรัพยากร Dependency โดยนัย

หากเครื่องมือสร้างเข้าถึงทรัพยากร Dependency ในการดำเนินการสร้างได้ การดำเนินการเหล่านั้นจะล้มเหลวเมื่อดำเนินการจากระยะไกล เนื่องจากระบบจะดำเนินการสร้างจากระยะไกลแต่ละรายการแยกกัน เครื่องมือสร้างบางรายการจะเก็บสถานะไว้ในการดำเนินการสร้างและเข้าถึงทรัพยากร Dependency ที่ไม่ได้รวมไว้ในการเรียกใช้เครื่องมืออย่างชัดเจน ซึ่งจะทำให้การดำเนินการสร้างที่ดำเนินการจากระยะไกลล้มเหลว

ตัวอย่างเช่น เมื่อ Bazel สั่งให้คอมไพเลอร์ที่เก็บสถานะสร้าง foo ในเครื่อง คอมไพเลอร์จะเก็บข้อมูลอ้างอิงถึงเอาต์พุตการบิลด์ของ foo ไว้ จากนั้นเมื่อ Bazel สั่งให้คอมไพเลอร์สร้าง bar ซึ่งขึ้นอยู่กับ foo โดยไม่ได้ระบุทรัพยากร Dependency นั้นอย่างชัดเจนในไฟล์ BUILD เพื่อรวมไว้ในการเรียกใช้คอมไพเลอร์ การดำเนินการจะดำเนินการได้สำเร็จตราบใดที่อินสแตนซ์คอมไพเลอร์เดียวกันดำเนินการทั้ง 2 อย่าง (ซึ่งเป็นลักษณะปกติของการดำเนินการในเครื่อง) อย่างไรก็ตาม เนื่องจากในสถานการณ์การดำเนินการจากระยะไกล การดำเนินการบิลด์แต่ละรายการจะเรียกใช้คอมไพเลอร์อินสแตนซ์แยกกัน สถานะคอมไพเลอร์และทรัพยากร Dependency โดยนัยของ bar ที่มีต่อ foo จะหายไปและการบิลด์จะล้มเหลว

Bazel 0.14.1 มีแซนด์บ็อกซ์ Docker ในเครื่อง ซึ่งมีข้อจำกัดเดียวกันสำหรับทรัพยากร Dependency กับการดำเนินการจากระยะไกล เพื่อช่วยตรวจหาและขจัดปัญหาทรัพยากร Dependency เหล่านี้ ใช้แซนด์บ็อกซ์เพื่อเตรียมการสร้างสำหรับการดำเนินการจากระยะไกลโดยระบุและแก้ไขข้อผิดพลาดในการสร้างที่เกี่ยวข้องกับทรัพยากร Dependency ดูข้อมูลเพิ่มเติมได้ที่ การแก้ปัญหาการดำเนินการจากระยะไกลของ Bazel ด้วยแซนด์บ็อกซ์ Docker

การจัดการไบนารีที่ขึ้นอยู่กับแพลตฟอร์ม

โดยปกติแล้ว ไบนารีที่สร้างในแพลตฟอร์มโฮสต์จะไม่สามารถดำเนินการได้อย่างปลอดภัยในแพลตฟอร์มการดำเนินการจากระยะไกลที่กำหนด เนื่องจากอาจมีทรัพยากร Dependency ที่ไม่ตรงกัน ตัวอย่างเช่น ไบนารี SingleJar ที่มาพร้อมกับ Bazel จะกำหนดเป้าหมายเป็นแพลตฟอร์มโฮสต์ อย่างไรก็ตาม สำหรับการดำเนินการจากระยะไกล จะต้องคอมไพล์ SingleJar เป็นส่วนหนึ่งของกระบวนการสร้างโค้ดเพื่อให้กำหนดเป้าหมายเป็นแพลตฟอร์มการดำเนินการจากระยะไกล (ดูตรรกะการเลือก เป้าหมาย)

อย่าจัดส่งไบนารีของเครื่องมือบิลด์ที่บิลด์ของคุณต้องใช้พร้อมกับซอร์สโค้ด เว้นแต่คุณจะมั่นใจว่าเครื่องมือเหล่านั้นจะทำงานได้อย่างปลอดภัยในแพลตฟอร์มการดำเนินการ ให้ทำอย่างใดอย่างหนึ่งต่อไปนี้แทน

  • จัดส่งหรืออ้างอิงซอร์สโค้ดของเครื่องมือจากภายนอกเพื่อให้สร้างเครื่องมือสำหรับแพลตฟอร์มการดำเนินการจากระยะไกลได้

  • ติดตั้งเครื่องมือไว้ล่วงหน้าในสภาพแวดล้อมการดำเนินการจากระยะไกล (เช่น คอนเทนเนอร์ Toolchain) หากเครื่องมือมีความเสถียรเพียงพอ และใช้กฎ Toolchain เพื่อเรียกใช้เครื่องมือในการสร้าง

การจัดการกฎ WORKSPACE ในรูปแบบการกำหนดค่า

คุณสามารถใช้กฎ WORKSPACE ของ Bazel เพื่อตรวจสอบเครื่องมือและไลบรารีที่การบิลด์ต้องใช้ในแพลตฟอร์มโฮสต์ ซึ่งสำหรับการบิลด์ในเครื่องก็คือแพลตฟอร์มการดำเนินการของ Bazel ด้วย หากบิลด์ขึ้นอยู่กับเครื่องมือสร้างและอาร์ติแฟกต์ในเครื่องอย่างชัดเจน บิลด์จะล้มเหลวระหว่างการดำเนินการจากระยะไกลหากแพลตฟอร์มการดำเนินการจากระยะไกลไม่เหมือนกับแพลตฟอร์มโฮสต์

การดำเนินการต่อไปนี้ที่กฎ WORKSPACE ดำเนินการไม่เข้ากันกับการดำเนินการจากระยะไกล

  • การสร้างไบนารี การดำเนินการคอมไพเลชันในกฎ WORKSPACE จะส่งผลให้เกิดไบนารีที่ไม่เข้ากันกับแพลตฟอร์มการดำเนินการจากระยะไกลหากแพลตฟอร์มดังกล่าวแตกต่างจากแพลตฟอร์มโฮสต์

  • การติดตั้งแพ็กเกจ pip แพ็กเกจ pip ที่ติดตั้งผ่านกฎ WORKSPACE กำหนดให้ต้องติดตั้งทรัพยากร Dependency ของแพ็กเกจไว้ล่วงหน้าในแพลตฟอร์มโฮสต์ แพ็กเกจดังกล่าวที่สร้างขึ้นสำหรับแพลตฟอร์มโฮสต์โดยเฉพาะจะไม่เข้ากันกับแพลตฟอร์มการดำเนินการจากระยะไกลหากแพลตฟอร์มดังกล่าวแตกต่างจากแพลตฟอร์มโฮสต์

  • การสร้างลิงก์สัญลักษณ์ไปยังเครื่องมือหรืออาร์ติแฟกต์ในเครื่อง ลิงก์สัญลักษณ์ไปยังเครื่องมือหรือไลบรารีที่ติดตั้งในแพลตฟอร์มโฮสต์ซึ่งสร้างผ่านกฎ WORKSPACE จะทำให้บิลด์ล้มเหลวในแพลตฟอร์มการดำเนินการจากระยะไกล เนื่องจาก Bazel จะค้นหาเครื่องมือหรือไลบรารีเหล่านั้นไม่พบ ให้สร้างลิงก์สัญลักษณ์โดยใช้การดำเนินการสร้างมาตรฐานเพื่อให้เครื่องมือและไลบรารีที่สร้างลิงก์สัญลักษณ์เข้าถึงได้จากทรี runfiles ของ Bazel อย่าใช้ repository_ctx.symlink เพื่อสร้างลิงก์สัญลักษณ์ไปยังไฟล์เป้าหมายนอกไดเรกทอรีที่เก็บภายนอก

  • การเปลี่ยนแปลงแพลตฟอร์มโฮสต์ หลีกเลี่ยงการสร้างไฟล์นอกทรี runfiles ของ Bazel, การสร้างตัวแปรสภาพแวดล้อม และการดำเนินการที่คล้ายกัน เนื่องจาก อาจทำงานไม่เป็นไปตามที่คาดไว้ในแพลตฟอร์มการดำเนินการจากระยะไกล

คุณสามารถใช้ บันทึกกฎ Workspace เพื่อช่วยค้นหาลักษณะการทำงานที่อาจไม่เป็นไปตามหลักการแยกส่วน

หากทรัพยากร Dependency ภายนอกดำเนินการบางอย่างที่ขึ้นอยู่กับแพลตฟอร์มโฮสต์ คุณควรแยกการดำเนินการเหล่านั้นระหว่างกฎ WORKSPACE และกฎการบิลด์ ดังนี้

  • การตรวจสอบแพลตฟอร์มและการแจกแจงทรัพยากร Dependency การดำเนินการเหล่านี้สามารถดำเนินการในเครื่องได้อย่างปลอดภัยผ่านกฎ WORKSPACE ซึ่งจะตรวจสอบได้ว่ามีการติดตั้งไลบรารีใดบ้าง ดาวน์โหลดแพ็กเกจที่ต้องสร้าง และเตรียมอาร์ติแฟกต์ที่จำเป็นสำหรับการคอมไพเลชัน สำหรับการดำเนินการจากระยะไกล กฎเหล่านี้ต้องรองรับการใช้อาร์ติแฟกต์ที่ตรวจสอบไว้ล่วงหน้าด้วยเพื่อแสดงข้อมูลที่จะได้รับตามปกติระหว่างการตรวจสอบแพลตฟอร์มโฮสต์ อาร์ติแฟกต์ที่ตรวจสอบไว้ล่วงหน้าช่วยให้ Bazel อธิบายทรัพยากร Dependency ได้ราวกับว่าทรัพยากรเหล่านั้นอยู่ในเครื่อง ใช้คำสั่งแบบมีเงื่อนไขหรือแฟล็ก --override_repository สำหรับการดำเนินการนี้

  • การสร้างหรือคอมไพล์อาร์ติแฟกต์ที่เฉพาะเจาะจงกับเป้าหมายและการเปลี่ยนแปลงแพลตฟอร์ม การดำเนินการเหล่านี้ต้องดำเนินการผ่านกฎการสร้างปกติ การดำเนินการที่สร้างอาร์ติแฟกต์ที่เฉพาะเจาะจงกับเป้าหมายสำหรับทรัพยากร Dependency ภายนอกต้องดำเนินการระหว่างการสร้าง

คุณสามารถใช้กฎ WORKSPACE เพื่อส่งไฟล์ที่สร้างขึ้นเพื่อให้สร้างอาร์ติแฟกต์ที่ตรวจสอบไว้ล่วงหน้าสำหรับการดำเนินการจากระยะไกลได้ง่ายขึ้น คุณสามารถเรียกใช้กฎเหล่านั้นในสภาพแวดล้อมการดำเนินการใหม่แต่ละรายการ เช่น ภายในคอนเทนเนอร์ Toolchain แต่ละรายการ และตรวจสอบเอาต์พุตของบิลด์การดำเนินการจากระยะไกลในที่เก็บซอร์สโค้ดเพื่อใช้อ้างอิง

ตัวอย่างเช่น สำหรับกฎของ Tensorflow สำหรับ cuda และ python, กฎ WORKSPACE จะสร้าง BUILD files ต่อไปนี้ สำหรับการดำเนินการในเครื่อง ระบบจะใช้ไฟล์ที่สร้างขึ้นโดยการตรวจสอบสภาพแวดล้อมโฮสต์ สำหรับการดำเนินการจากระยะไกล คำสั่งแบบมีเงื่อนไข ในตัวแปรสภาพแวดล้อมจะช่วยให้กฎใช้ไฟล์ที่ตรวจสอบแล้วในที่เก็บได้

ไฟล์ BUILD จะประกาศ genrules ที่สามารถเรียกใช้ได้ทั้งในเครื่องและจากระยะไกล รวมถึงดำเนินการประมวลผลที่จำเป็น ซึ่งก่อนหน้านี้ดำเนินการผ่าน repository_ctx.symlink ดังที่แสดง ไว้ที่นี่