เกี่ยวกับ Codelab นี้
1 ภาพรวม
Artifact Registry เป็นเครื่องมือจัดการแพ็กเกจที่มีการจัดการอย่างเต็มรูปแบบ และมีเครื่องมือแบบรวมเพื่อจัดการอิมเมจคอนเทนเนอร์ OCI และแพ็กเกจภาษา (เช่น Maven และ npm)
รีจิสทรีอาร์ติแฟกต์ผสานรวมกับบริการอื่นๆ ของ Google Cloud อย่างเต็มรูปแบบ เช่น ตัวอย่างต่อไปนี้
- Cloud Build สามารถอัปโหลดอาร์ติแฟกต์รูปภาพไปยัง Artifact Registry ได้โดยตรง
- Cloud Deploy สามารถทำให้รูปภาพใน Artifact Registry ใช้งานได้ในสภาพแวดล้อมรันไทม์ต่างๆ ได้โดยตรง
- โดยให้บริการอิมเมจแก่รันไทม์คอนเทนเนอร์ เช่น Cloud Run และ GKE รวมถึงเปิดใช้ความสามารถในการเพิ่มประสิทธิภาพขั้นสูง เช่น สตรีมมิงรูปภาพ
- Artifact Registry สามารถใช้เป็นจุดตรวจจับสําหรับการวิเคราะห์อาร์ติแฟกต์เพื่อตรวจสอบช่องโหว่ที่ทราบอยู่อย่างต่อเนื่อง
- Cloud IAM ให้การควบคุมการเข้าถึงและสิทธิ์ของรายการต่างๆ ที่ละเอียดและสม่ำเสมอ
ห้องทดลองนี้จะแนะนำฟีเจอร์เหล่านี้หลายอย่างในรูปแบบบทแนะนำแบบฝึกปฏิบัติ
สิ่งที่คุณจะได้เรียนรู้
วัตถุประสงค์ด้านการเรียนรู้ของห้องทดลองนี้คืออะไร
- สร้างที่เก็บข้อมูลแยกต่างหากสำหรับคอนเทนเนอร์และแพ็กเกจภาษา
- สร้างและใช้อิมเมจคอนเทนเนอร์กับ Artifact Registry
- ใช้รีจิสทรีอาร์ติแฟกต์เพื่อวิเคราะห์สถานะความปลอดภัยและเนื้อหาของอาร์ติแฟกต์
- กำหนดค่าและใช้ Artifact Registry สําหรับ Dependency ของ Maven ใน Java
2 การตั้งค่าและข้อกําหนด
การตั้งค่าสภาพแวดล้อมด้วยตนเอง
- ลงชื่อเข้าใช้ Google Cloud Console และสร้างโปรเจ็กต์ใหม่หรือใช้โปรเจ็กต์ที่มีอยู่ซ้ำ หากยังไม่มีบัญชี Gmail หรือ Google Workspace คุณต้องสร้างบัญชี
- ชื่อโปรเจ็กต์คือชื่อที่แสดงสำหรับผู้เข้าร่วมโปรเจ็กต์นี้ ซึ่งเป็นสตริงอักขระที่ Google APIs ไม่ได้ใช้ คุณจะอัปเดตได้ทุกเมื่อ
- รหัสโปรเจ็กต์จะซ้ำกันไม่ได้ในโปรเจ็กต์ Google Cloud ทั้งหมดและจะเปลี่ยนแปลงไม่ได้ (เปลี่ยนแปลงไม่ได้หลังจากตั้งค่าแล้ว) คอนโซล Cloud จะสร้างสตริงที่ไม่ซ้ำกันโดยอัตโนมัติ ซึ่งปกติแล้วคุณไม่จำเป็นต้องสนใจว่าสตริงนั้นจะเป็นอะไร ในโค้ดแล็บส่วนใหญ่ คุณจะต้องอ้างอิงรหัสโปรเจ็กต์ (ปกติจะระบุเป็น
PROJECT_ID
) หากไม่ชอบรหัสที่สร้างขึ้น คุณอาจสร้างรหัสอื่นแบบสุ่มได้ หรือจะลองใช้รหัสของคุณเองเพื่อดูว่ารหัสนั้นใช้งานได้หรือไม่ก็ได้ คุณจะเปลี่ยนแปลงหลังจากขั้นตอนนี้ไม่ได้ และชื่อนี้จะคงอยู่ตลอดระยะเวลาของโปรเจ็กต์ - โปรดทราบว่ามีค่าที่ 3 ซึ่งเป็นหมายเลขโปรเจ็กต์ที่ API บางรายการใช้ ดูข้อมูลเพิ่มเติมเกี่ยวกับค่าทั้ง 3 รายการนี้ได้ในเอกสารประกอบ
- ถัดไป คุณจะต้องเปิดใช้การเรียกเก็บเงินใน Cloud Console เพื่อใช้ทรัพยากร/API ของ Cloud การทำตามโค้ดแล็บนี้จะไม่เสียค่าใช้จ่ายมากนัก หากต้องการปิดทรัพยากรเพื่อหลีกเลี่ยงการเรียกเก็บเงินหลังจากบทแนะนำนี้ คุณก็ลบทรัพยากรที่สร้างไว้หรือลบโปรเจ็กต์ได้ ผู้ใช้ Google Cloud รายใหม่มีสิทธิ์เข้าร่วมโปรแกรมช่วงทดลองใช้ฟรีมูลค่า$300 USD
ตั้งค่า gcloud
ใน Cloud Shell ให้ตั้งค่ารหัสโปรเจ็กต์และหมายเลขโปรเจ็กต์ บันทึกเป็นตัวแปร PROJECT_ID
และ PROJECT_NUMBER
export PROJECT_ID=$(gcloud config get-value project)
export PROJECT_NUMBER=$(gcloud projects describe $PROJECT_ID --format='value(projectNumber)')
เปิดใช้บริการของ Google
gcloud services enable \
cloudresourcemanager.googleapis.com \
run.googleapis.com \
artifactregistry.googleapis.com \
containerregistry.googleapis.com \
containerscanning.googleapis.com \
binaryauthorization.googleapis.com \
cloudbuild.googleapis.com
รับซอร์สโค้ด
ซอร์สโค้ดของห้องทดลองนี้อยู่ในองค์กร GoogleCloudPlatform บน GitHub โคลนด้วยคำสั่งด้านล่าง
git clone https://github.com/GoogleCloudPlatform/java-docs-samples
3 การพุชอิมเมจคอนเทนเนอร์
สร้างที่เก็บ Docker ใน Artifact Registry
ดังที่ได้กล่าวไว้ก่อนหน้านี้ Artifact Registry รองรับรูปแบบที่เก็บข้อมูลต่างๆ ซึ่งช่วยให้คุณจัดการอิมเมจคอนเทนเนอร์และแพ็กเกจภาษาได้ การโต้ตอบกับที่เก็บอาร์ติแฟกต์ประเภทต่างๆ ได้รับการกําหนดไว้ในข้อกําหนดและเป็นมาตรฐานที่ใช้กันอย่างแพร่หลาย เช่น คำขอสำหรับ Dependency ของ Maven จะแตกต่างจากคำขอสำหรับ Dependency ของ Node
หากต้องการรองรับข้อกำหนดเฉพาะของ API รายการต่างๆ Artifact Registry จะต้องจัดการรายการต่างๆ ของคุณในที่เก็บประเภทที่เกี่ยวข้อง เมื่อสร้างที่เก็บข้อมูลใหม่ ให้ส่งผ่าน Flag --repository-format
เพื่อระบุประเภทที่เก็บข้อมูล
หากต้องการสร้างที่เก็บข้อมูลแรกสำหรับอิมเมจ Docker ให้เรียกใช้คำสั่งต่อไปนี้จาก Cloud Shell
gcloud artifacts repositories create container-example --repository-format=docker \
--location=us-central1 --description="Example Docker repository"
คลิก "ให้สิทธิ์" หากข้อความแจ้งการให้สิทธิ์ Cloud Shell ปรากฏขึ้น
ไปที่ Google Cloud Console - Artifact Registry - Repositories และดูที่ที่เก็บข้อมูล Docker ที่สร้างขึ้นใหม่ชื่อ container-example
เมื่อคลิกเข้าไป คุณจะเห็นที่เก็บข้อมูลว่างเปล่าในขณะนี้
กำหนดค่าการตรวจสอบสิทธิ์ Docker ไปยัง Artifact Registry
เมื่อเชื่อมต่อกับ Artifact Registry คุณต้องใช้ข้อมูลเข้าสู่ระบบเพื่อให้สิทธิ์เข้าถึง คุณกำหนดค่า Docker ให้ใช้ข้อมูลเข้าสู่ระบบ gcloud ได้อย่างราบรื่นแทนการตั้งค่าข้อมูลเข้าสู่ระบบแยกต่างหากได้
จาก Cloud Shell ให้เรียกใช้คําสั่งต่อไปนี้เพื่อกําหนดค่า Docker ให้ใช้ CLI ของ Google Cloud เพื่อตรวจสอบสิทธิ์คําขอไปยัง Artifact Registry ในภูมิภาค us-central1
gcloud auth configure-docker us-central1-docker.pkg.dev
หากคำสั่งแจ้งให้ยืนยันเพื่อเปลี่ยนการกำหนดค่า Docker ของ Cloud Shell ให้กด Enter
สำรวจแอปพลิเคชันตัวอย่าง
ตัวอย่างแอปพลิเคชันจะอยู่ในที่เก็บ Git ที่คุณโคลนไว้ในขั้นตอนก่อนหน้า เปลี่ยนเป็นไดเรกทอรี java และตรวจสอบโค้ดแอปพลิเคชัน
cd java-docs-samples/run/helloworld/
ls
โฟลเดอร์นี้มีตัวอย่างแอปพลิเคชัน Java ที่แสดงผลหน้าเว็บอย่างง่าย นอกจากไฟล์ต่างๆ ที่ไม่เกี่ยวข้องกับห้องทดลองนี้แล้ว โฟลเดอร์ยังมีซอร์สโค้ดอยู่ในโฟลเดอร์ src
และ Dockerfile ที่เราจะใช้สร้างอิมเมจคอนเทนเนอร์
สร้างอิมเมจคอนเทนเนอร์
คุณจะต้องสร้าง Artifact Registry ก่อนจึงจะจัดเก็บอิมเมจคอนเทนเนอร์ได้
เรียกใช้คําสั่งต่อไปนี้เพื่อสร้างอิมเมจคอนเทนเนอร์และติดแท็กด้วยเส้นทาง Artifact Registry แบบเต็ม
docker build -t us-central1-docker.pkg.dev/$PROJECT_ID/container-example/java-hello-world:tag1 .
พุชอิมเมจคอนเทนเนอร์ไปยัง Artifact Registry
เรียกใช้คำสั่งต่อไปนี้เพื่อพุชอิมเมจคอนเทนเนอร์ไปยังที่เก็บที่สร้างขึ้นก่อนหน้านี้
docker push us-central1-docker.pkg.dev/$PROJECT_ID/container-example/java-hello-world:tag1
ตรวจสอบรูปภาพใน Artifact Registry
ไปที่ คอนโซล Google Cloud - Artifact Registry - Repositories.
เปิดที่เก็บข้อมูล container-example
และตรวจสอบว่ามีอิมเมจ java-hello-world
อยู่
คลิกรูปภาพและดูรูปภาพที่ติดแท็ก tag1
เนื่องจากเราได้เปิดใช้การสแกนรูปภาพอัตโนมัติผ่านบริการ containerscanning.googleapis.com
คุณจึงเห็นว่าการสแกนช่องโหว่กำลังทำงานหรือเสร็จสมบูรณ์แล้ว เมื่อดำเนินการเสร็จแล้ว คุณจะเห็นจำนวนช่องโหว่ที่ตรวจพบสำหรับการแก้ไขรูปภาพนี้ เราจะสำรวจช่องโหว่และข้อมูลเชิงลึกอื่นๆ เกี่ยวกับรายการต่างๆ ในส่วนถัดไป
4 การตรวจสอบอิมเมจคอนเทนเนอร์
ตอนนี้คุณพุชรูปภาพแรกไปยังที่เก็บข้อมูล container-example
แล้ว เราจึงดูรายละเอียดเพิ่มเติมได้ ในแท็บเวอร์ชัน ให้คลิกเวอร์ชันที่เราเพิ่งสร้าง วิธีแสดงรูปภาพอย่างละเอียด
ปุ่มคัดลอกด้านบนมีประโยชน์อย่างยิ่งเนื่องจากเป็นวิธีที่ง่ายในการเข้าถึง URI ของรูปภาพที่สมบูรณ์สำหรับเวอร์ชันรูปภาพนั้น รวมถึงแฮช SHA จากนั้นจะใช้ URI นี้เพื่อดึงข้อมูลเวอร์ชันรูปภาพที่ต้องการหรือใช้เป็นข้อมูลอ้างอิงรูปภาพในการทำให้ใช้งานได้ของ Kubernetes หรือบริการ Cloud Run ได้ หากต้องการทดสอบ URI ของรูปภาพ ให้เรียกใช้คำสั่งต่อไปนี้ใน Cloud Shell
docker pull $IMAGE_URI
ทำความเข้าใจทรัพยากร Dependency
เมื่อไปที่แท็บ "Dependency" ที่ด้านบน คุณจะเห็น Dependency ทั้งหมดที่ตรวจพบในรูปภาพ โปรดทราบว่ารายการนี้จะแสดงทั้งทรัพยากร Dependency ที่ระดับภาษาและระดับระบบปฏิบัติการ นอกจากนี้ คุณยังดูใบอนุญาตซอฟต์แวร์ที่แนบมากับแต่ละรายการที่ต้องใช้ร่วมกันได้ด้วย
หากมองดูดีๆ จะเห็นข้อมูล SBOM ยังไม่แสดง หากต้องการป้อนข้อมูล SOM สําหรับอาร์ติแฟกต์ ให้เรียกใช้คําสั่งต่อไปนี้ใน Cloud Shell โดยใช้ URI ของรูปภาพที่สมบูรณ์ซึ่งเราคัดลอกได้จากแถบเบรดครัมบ์ที่ด้านบน
gcloud artifacts sbom export --uri $IMAGE_URI
เมื่อรีเฟรชหน้าเว็บแล้ว หน้าดังกล่าวจะมีลิงก์ไปยัง SBOM ที่สร้างขึ้นโดยอัตโนมัติซึ่งจัดเก็บไว้ใน Cloud Storage หากใช้ SBOM สำหรับรูปภาพ คุณอาจต้องสร้าง SBOM สำหรับอาร์ติแฟกต์โดยอัตโนมัติและทำให้การสร้างเป็นส่วนหนึ่งของไปป์ไลน์ CI/CD
การสํารวจช่องโหว่ของภาพ
เมื่อคลิกแท็บ "ช่องโหว่" ที่ด้านบนของมุมมอง คุณจะเห็นช่องโหว่ทั้งหมดที่ตรวจพบในรูปภาพ นอกจากดูสรุปช่องโหว่ที่ด้านบนแล้ว คุณยังดูรายการช่องโหว่ทั้งหมดได้ในตารางที่ด้านล่าง แต่ละแถวจะลิงก์ไปยังกระดานข่าวสาร CVE ซึ่งระบุความรุนแรงและแพ็กเกจที่เป็นต้นทาง สำหรับช่องโหว่ที่มีวิธีแก้ไข ระบบจะแสดงวิธีการอัปเดตทรัพยากร Dependencies เพื่อแก้ไขช่องโหว่ด้วย
5 ที่เก็บเสมือนและที่เก็บระยะไกล
ในส่วนก่อนหน้านี้ เราใช้ที่เก็บรูปภาพแห่งเดียวเพื่อพุชและดึงรูปภาพ การดำเนินการนี้เหมาะสำหรับ Use Case ขนาดเล็ก แต่อาจก่อให้เกิดปัญหาได้ โดยเฉพาะสำหรับองค์กรขนาดใหญ่ที่มีทีมต่างๆ ที่ต้องการความอิสระในการดูแลจัดการที่เก็บ เป็นเรื่องปกติที่ทีมหรือหน่วยธุรกิจจะมีที่เก็บรูปภาพของตนเองที่มีสิทธิ์และการกําหนดค่าของตนเอง Artifact Registry มีที่เก็บข้อมูลเสมือนที่สามารถรวบรวมทรัพยากรจากที่เก็บข้อมูลพื้นฐานหลายแห่ง เพื่อลดความซับซ้อนในการใช้รูปภาพในที่เก็บข้อมูลเหล่านี้และปกป้องผู้บริโภคจากโครงสร้างองค์กรที่อยู่เบื้องหลัง สถาปัตยกรรมที่เป็นไปได้อาจมีลักษณะดังนี้
ที่เก็บระยะไกลสำหรับ Docker Hub
Docker Hub เป็นรีจิสทรีอิมเมจสาธารณะที่ได้รับความนิยมและโฮสต์อิมเมจคอนเทนเนอร์แบบโอเพนซอร์สจำนวนมาก แม้ว่าการใช้ที่เก็บสาธารณะโดยตรงจะสะดวก แต่ก็มีอุปสรรคหลายประการในสภาพแวดล้อมที่ใช้งานจริง ซึ่งเราแก้ไขได้ด้วยที่เก็บระยะไกลใน Artifact Registry
รีโพซิทอรีระยะไกลช่วยให้คุณพร็อกซีคำขอไปยังรีจิสทรีต้นทางและแคชรูปภาพระหว่างทางได้ ซึ่งไม่เพียงช่วยลดเวลาในการดาวน์โหลดรูปภาพ แต่ยังช่วยลดการพึ่งพาเวลาทำงานของบริการภายนอกและช่วยให้คุณใช้นโยบายความปลอดภัยและการเข้าถึงเดียวกันกับที่ใช้กับรูปภาพของคุณเองได้
หากต้องการสร้างที่เก็บระยะไกลสําหรับ Docker Hub ให้เรียกใช้คําสั่งต่อไปนี้ใน Cloud Shell
gcloud artifacts repositories create dockerhub \
--repository-format=docker \
--mode=remote-repository \
--remote-docker-repo=docker-hub \
--location=us-central1 \
--description="Example Remote Repo for Docker Hub"
ตอนนี้คุณควรเห็นที่เก็บข้อมูลเพิ่มเติมในรายการที่เก็บ Artifact Registry
หากต้องการทดสอบว่าที่เก็บข้อมูลระยะไกลสามารถส่งคำขอไปยังที่เก็บข้อมูลระยะไกลผ่านพร็อกซีได้หรือไม่ ให้เรียกใช้คำสั่งต่อไปนี้ใน Cloud Shell เพื่อดึงอิมเมจ nginx
docker pull us-central1-docker.pkg.dev/$PROJECT_ID/dockerhub/nginx:stable-alpine
เมื่อดึงข้อมูลสำเร็จแล้ว คุณจะดูที่ที่เก็บใน Cloud Console ได้ด้วย และตอนนี้รูปภาพ nginx ที่แคชไว้จะแสดงการรายงานเกี่ยวกับข้อกำหนดและช่องโหว่เดียวกันกับที่เราเห็นสำหรับรูปภาพที่คุณสร้างเอง
การสร้างที่เก็บเสมือน
เมื่อทำตามกระบวนการที่เราใช้จนถึงตอนนี้ คุณจะสร้างที่เก็บข้อมูลจํานวนหนึ่งสําหรับแต่ละทีมหรือธุรกิจ และกำหนดการเป็นเจ้าของและสิทธิ์ IAM ของแต่ละที่เก็บข้อมูลได้อย่างชัดเจน นอกจากนี้ เรายังสร้างพร็อกซีสําหรับที่เก็บข้อมูลระยะไกลได้ ซึ่งจะช่วยให้ใช้รูปภาพของบุคคลที่สามได้ง่ายและปลอดภัยยิ่งขึ้น ข้อเสียของที่เก็บข้อมูลจํานวนมากนี้จะเห็นได้ชัดเมื่อคุณเปลี่ยนมุมมองเป็นผู้บริโภคของรูปภาพเหล่านี้ นักพัฒนาซอฟต์แวร์ควรทราบได้อย่างไรว่าควรใช้ที่เก็บรูปภาพใดในการทำให้ใช้งานได้
หากต้องการลดความซับซ้อนในการใช้งานและซ่อนที่เก็บข้อมูลที่สําคัญไว้เบื้องหลังเลเยอร์การแยกแยะ ให้สร้างที่เก็บข้อมูลเสมือนใน Artifact Registry ด้วยคําสั่งต่อไปนี้ใน Cloud Shell
gcloud projects add-iam-policy-binding $PROJECT_ID \
--member serviceAccount:service-$PROJECT_NUMBER@gcp-sa-artifactregistry.iam.gserviceaccount.com \
--role roles/artifactregistry.reader
cat <<EOF > /tmp/upstream.json
[{
"id" : "hello-repo",
"repository" : "projects/$PROJECT_ID/locations/us-central1/repositories/container-example",
"priority" : 100
},{
"id" : "dockerhub",
"repository" : "projects/$PROJECT_ID/locations/us-central1/repositories/dockerhub",
"priority" : 101
}]
EOF
gcloud artifacts repositories create all-images \
--repository-format=docker \
--mode=virtual-repository \
--location=us-central1 \
--upstream-policy-file=/tmp/upstream.json \
--description="Example Virtual Repo"
ตอนนี้เราดึงรูปภาพจากที่เก็บข้อมูลเสมือนได้โดยไม่ต้องเปิดเผยโครงสร้างพื้นฐาน หากต้องการตรวจสอบว่าทุกอย่างทำงานได้ตามที่คาดไว้ ให้เรียกใช้คําสั่งต่อไปนี้ใน Cloud Shell
docker pull us-central1-docker.pkg.dev/$PROJECT_ID/all-images/java-hello-world:tag1
docker pull us-central1-docker.pkg.dev/$PROJECT_ID/all-images/nginx:stable-alpine
6 ทำให้ใช้งานได้กับ Cloud Run
เมื่อสร้างที่เก็บและรูปภาพที่เกี่ยวข้องแล้ว เราจึงนำไปใช้ในการทำให้ใช้งานได้ เราจะทำให้คอนเทนเนอร์ใช้งานได้ใน Cloud Run เพื่อแสดงตัวอย่าง Use Case และหลีกเลี่ยงการติดตั้งใช้งานโครงสร้างพื้นฐานเพิ่มเติม รูปแบบที่ง่ายที่สุดในการทำให้ใช้งานได้คือเรียกใช้คําสั่งต่อไปนี้ใน Cloud Shell
gcloud run deploy hello-world \
--image us-central1-docker.pkg.dev/$PROJECT_ID/all-images/java-hello-world:tag1 \
--region us-central1 \
--allow-unauthenticated
เมื่อการทําให้ใช้งานได้เสร็จสิ้นแล้ว ระบบจะแสดง URL ที่สร้างขึ้นโดยอัตโนมัติซึ่งคุณจะใช้เข้าถึงบริการได้
Deploying container to Cloud Run service [hello-world] in project [my-project] region [us-central1] OK Deploying... Done. OK Creating Revision... OK Routing traffic... OK Setting IAM Policy... Done. Service [hello-world] revision [hello-world-00001-wtc] has been deployed and is serving 100 percent of traffic. Service URL: https://hello-world-13746229022.us-central1.run.app
หากเปิด URL นั้นในแท็บเบราว์เซอร์ใหม่ คุณควรเห็นข้อความ "Hello World" ที่แสดงว่าดำเนินการสำเร็จ
7 เสริมสร้างความปลอดภัยในซัพพลายเชน
เมื่อรูปภาพคอนเทนเนอร์ของคุณพร้อมใช้งานจริงแล้ว ก็ถึงเวลาที่เราจะมาดูวิธีเสริมความแข็งแกร่งให้กับซัพพลายเชนจากต้นทางถึงปลายทาง ในส่วนก่อนหน้านี้เราได้ดูว่าการวิเคราะห์คอนเทนเนอร์ของ Artifact Registry ให้ข้อมูลเชิงลึกเกี่ยวกับคลังภาพและใบอนุญาตที่ใช้ในรูปภาพอย่างไร อย่างไรก็ตาม ผู้ไม่ประสงค์ดีอาจแทรกเนื้อหาที่เป็นอันตรายลงในรูปภาพของคุณได้ตลอดทั้งซัพพลายเชน ในส่วนนี้ เราจะดูวิธีใช้เฟรมเวิร์ก SLSA เพื่อแนะนำการรับรองสำหรับอาร์ติแฟกต์การสร้าง และใช้ประโยชน์จากลายเซ็นการเข้ารหัสของอาร์ติแฟกต์เองเพื่อให้มั่นใจว่ามีการนำเฉพาะอาร์ติแฟกต์ที่เชื่อถือได้ไปยังรันไทม์ Cloud Run เท่านั้น
การรับรอง SLSA ด้วย Cloud Build
เฟรมเวิร์ก SLSA มีหลักฐานระดับต่างๆ สำหรับรายการต่างๆ ในซัพพลายเชน ข้อกําหนดและการใช้งานอาจดูน่ากลัวในตอนแรก แต่การสร้างการรับรอง SLSA ด้วย Cloud Build นั้นง่ายเพียงการเพิ่มการสร้างข้อกําหนด cloudbuild.yaml
โดยตั้งค่า requestedVerifyOption
เป็น VERIFIED
สําหรับแอปพลิเคชันของเรา เราสามารถเรียกใช้คําสั่งต่อไปนี้ใน Cloud Shell เพื่อสร้างไฟล์ cloudbuild.yaml
ในโฟลเดอร์ helloworld
cat <<EOF > cloudbuild.yaml
steps:
- name: 'gcr.io/cloud-builders/docker'
args: ['build', '-t', '\$_IMAGE_URI', '.']
- name: 'gcr.io/cloud-builders/docker'
args: ['push', '\$_IMAGE_URI']
images:
- '\$_IMAGE_URI'
options:
requestedVerifyOption: VERIFIED
substitutions:
_IMAGE_URI: us-central1-docker.pkg.dev/$PROJECT_ID/container-example/java-hello-world:latest
EOF
ตอนนี้เราจะสร้างงาน Cloud Build ใหม่ซึ่งจะสร้างอิมเมจ Hello World เวอร์ชันใหม่ของ Java โดยการเรียกใช้คําสั่งต่อไปนี้ใน Cloud Shell
gcloud builds submit --substitutions=_IMAGE_URI=us-central1-docker.pkg.dev/$PROJECT_ID/container-example/java-hello-world:cloud-build
เมื่อการบิลด์เสร็จสมบูรณ์แล้ว ให้ไปที่ UI ของ Cloud Build ในคอนโซล Google Cloud และดูระดับ SLSA ที่เราได้รับโดยการเปิดบิลด์ แล้วดูที่อาร์ติแฟกต์การสร้างในส่วนสรุปการสร้าง รูปภาพที่เห็นจะมีปุ่มสำหรับดู "ข้อมูลเชิงลึกด้านความปลอดภัย" เมื่อคลิก คุณจะเห็นการรับรอง SLSA รวมถึงรายงานช่องโหว่ที่คุ้นเคยซึ่งเราเห็นก่อนหน้านี้ใน UI ของที่เก็บอาร์ติแฟกต์เมื่อเราพุชบิลด์ในเครื่อง
คุณยังเรียกดูแหล่งที่มา SLSA ของรูปภาพได้ด้วยโดยเรียกใช้คำสั่งต่อไปนี้ใน Cloud Shell
gcloud artifacts docker images describe \
"us-central1-docker.pkg.dev/$PROJECT_ID/container-example/java-hello-world:cloud-build" \
--show-provenance
กำหนดให้ต้องมีแหล่งที่มาของ Cloud Build ที่มีการให้สิทธิ์แบบไบนารี
เมื่อใช้ไปป์ไลน์ Cloud Build แล้ว คุณคงอยากตรวจสอบว่าอิมเมจทั้งหมดที่เราทำให้ใช้งานได้จริงสร้างขึ้นโดยใช้สภาพแวดล้อมการสร้างที่เขียนโปรแกรมซ้ำได้และสร้างซ้ำได้ใช่ไหม
การให้สิทธิ์แบบไบนารีจึงเข้ามามีบทบาทในจุดนี้ ซึ่งช่วยให้คุณวางผู้ควบคุมประตูไว้ด้านหน้ารันไทม์คอนเทนเนอร์ที่จะตรวจสอบอิมเมจคอนเทนเนอร์และยืนยันการรับรองที่เชื่อถือได้ หากไม่พบการรับรอง ระบบจะสร้างรายการบันทึกการตรวจสอบหรือบล็อกการติดตั้งใช้งานโดยสมบูรณ์ ทั้งนี้ขึ้นอยู่กับการกำหนดค่า
หากต้องการเปลี่ยนการกำหนดค่าการให้สิทธิ์แบบไบนารีเริ่มต้นของโปรเจ็กต์ให้กำหนดให้มีการรับรองในตัวที่ออกโดย Cloud Run เราเรียกใช้คำสั่งต่อไปนี้ใน Cloud Shell
cat << EOF > /tmp/policy.yaml
defaultAdmissionRule:
enforcementMode: ENFORCED_BLOCK_AND_AUDIT_LOG
evaluationMode: REQUIRE_ATTESTATION
requireAttestationsBy:
- projects/$PROJECT_ID/attestors/built-by-cloud-build
name: projects/$PROJECT_ID/policy
EOF
gcloud container binauthz policy import /tmp/policy.yaml
ในส่วนนี้ คุณยังเพิ่มผู้รับรองที่กําหนดเองได้ แต่การดำเนินการนี้อยู่นอกขอบเขตของโค้ดแล็บนี้และถือเป็นแบบฝึกหัดนอกหลักสูตรที่ไม่บังคับ
หากต้องการบังคับใช้การให้สิทธิ์แบบไบนารีในบริการ Cloud Run เราจะเรียกใช้คําสั่งต่อไปนี้ใน Cloud Shell
gcloud run services update hello-world \
--region us-central1 \
--binary-authorization=default
มาทดสอบว่าการใช้การให้สิทธิ์แบบไบนารีถูกต้องหรือไม่ด้วยการทำให้อิมเมจที่สร้างขึ้นในพื้นที่ใช้งานได้อีกครั้งก่อน
gcloud run deploy hello-world \
--image us-central1-docker.pkg.dev/$PROJECT_ID/all-images/java-hello-world:tag1 \
--region us-central1
คุณควรได้รับข้อความแสดงข้อผิดพลาดที่อธิบายสาเหตุที่ไม่สามารถทำให้รูปภาพใช้งานได้ ซึ่งมีลักษณะดังนี้
Image us-central1-docker.pkg.dev/my-project/all-images/java-hello-world@sha256:71eebbf04bf7d1d023e5de5e18f786ea3b8b6411bf64c8def3301c71baca0518 denied by attestor projects/my-project/attestors/built-by-cloud-build: No attestations found that were valid and signed by a key trusted by the attestor
ดังนั้น หากต้องการทำให้เวอร์ชันใหม่ใช้งานได้ในบริการ Cloud Run เราจึงต้องระบุอิมเมจที่สร้างด้วย Cloud Build
gcloud run deploy hello-world \
--image us-central1-docker.pkg.dev/$PROJECT_ID/all-images/java-hello-world:cloud-build \
--region us-central1
ครั้งนี้การทำให้ใช้งานได้ควรสำเร็จและแสดงข้อความการทำให้ใช้งานได้สําเร็จคล้ายกับข้อความด้านล่าง
Deploying container to Cloud Run service [hello-world] in project [my-project] region [us-central1] OK Deploying... Done. OK Creating Revision... OK Routing traffic... Done. Service [hello-world] revision [hello-world-00005-mq4] has been deployed and is serving 100 percent of traffic. Service URL: https://hello-world-13746229022.us-central1.run.app
8 การจัดการแพ็กเกจภาษา Java Maven
ส่วนนี้จะแสดงวิธีตั้งค่าที่เก็บ Java ของ Artifact Registry และอัปโหลดแพ็กเกจไปยังที่เก็บดังกล่าวเพื่อใช้ประโยชน์ในแอปพลิเคชันต่างๆ
สร้างที่เก็บแพ็กเกจ Maven
จาก Cloud Shell ให้เรียกใช้คำสั่งต่อไปนี้เพื่อสร้างที่เก็บสำหรับอาร์ติแฟกต์ Java
gcloud artifacts repositories create java-repo \
--repository-format=maven \
--location=us-central1 \
--description="Example Java Maven Repo"
คลิก "ให้สิทธิ์" หากข้อความแจ้งการให้สิทธิ์ Cloud Shell ปรากฏขึ้น
ไปที่ Google Cloud Console - Artifact Registry - Repositories และดูที่เก็บ Maven ที่สร้างขึ้นใหม่ชื่อ java-repo
เมื่อคลิกที่เก็บนี้ คุณจะเห็นว่ามันว่างเปล่าในขณะนี้
ตั้งค่าการตรวจสอบสิทธิ์ไปยังที่เก็บอาร์ติแฟกต์
ใช้คำสั่งต่อไปนี้เพื่ออัปเดตตำแหน่งที่รู้จักสำหรับข้อมูลเข้าสู่ระบบเริ่มต้นของแอปพลิเคชัน (ADC) ด้วยข้อมูลเข้าสู่ระบบของบัญชีผู้ใช้เพื่อให้เครื่องมือช่วยตรวจสอบสิทธิ์ของ Artifact Registry ตรวจสอบสิทธิ์ได้โดยใช้ข้อมูลเข้าสู่ระบบดังกล่าวเมื่อเชื่อมต่อกับที่เก็บ
gcloud auth login --update-adc
กำหนดค่า Maven สำหรับ Artifact Registry
เรียกใช้คำสั่งต่อไปนี้เพื่อพิมพ์การกำหนดค่าที่เก็บเพื่อเพิ่มลงในโปรเจ็กต์ Java
gcloud artifacts print-settings mvn \
--repository=java-repo \
--location=us-central1 | tee config.xml
เปิด pom.xml ใน Cloud Shell Editor โดยเรียกใช้คำสั่งต่อไปนี้ใน Cloud Shell จากภายในไดเรกทอรี helloworld
cloudshell edit pom.xml
และเพิ่มการตั้งค่าที่แสดงผลในส่วนที่เหมาะสมในไฟล์
อัปเดตส่วน distributionManagement
<distributionManagement>
<snapshotRepository>
<id>artifact-registry</id>
<url>artifactregistry://us-central1-maven.pkg.dev/<PROJECT>/java-repo</url>
</snapshotRepository>
<repository>
<id>artifact-registry</id>
<url>artifactregistry://us-central1-maven.pkg.dev/<PROJECT>/java-repo</url>
</repository>
</distributionManagement>
อัปเดตส่วน repositories
<repositories>
<repository>
<id>artifact-registry</id>
<url>artifactregistry://us-central1-maven.pkg.dev/<PROJECT>/java-repo</url>
<releases>
<enabled>true</enabled>
</releases>
<snapshots>
<enabled>true</enabled>
</snapshots>
</repository>
</repositories>
อัปเดตส่วนส่วนขยายในส่วนบิลด์
<extensions>
<extension>
<groupId>com.google.cloud.artifactregistry</groupId>
<artifactId>artifactregistry-maven-wagon</artifactId>
<version>2.1.0</version>
</extension>
</extensions>
ต่อไปนี้คือตัวอย่างไฟล์ที่สมบูรณ์สำหรับใช้อ้างอิง อย่าลืมแทนที่ <PROJECT> ด้วยรหัสโปรเจ็กต์ของคุณ
<?xml version="1.0" encoding="UTF-8"?>
<project xmlns="http://maven.apache.org/POM/4.0.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd">
<modelVersion>4.0.0</modelVersion>
<groupId>com.example.run</groupId>
<artifactId>helloworld</artifactId>
<version>0.0.1-SNAPSHOT</version>
<packaging>jar</packaging>
<parent>
<groupId>com.google.cloud.samples</groupId>
<artifactId>shared-configuration</artifactId>
<version>1.2.0</version>
</parent>
<dependencyManagement>
<dependencies>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-dependencies</artifactId>
<version>${spring-boot.version}</version>
<type>pom</type>
<scope>import</scope>
</dependency>
</dependencies>
</dependencyManagement>
<properties>
<project.build.sourceEncoding>UTF-8</project.build.sourceEncoding>
<project.reporting.outputEncoding>UTF-8</project.reporting.outputEncoding>
<maven.compiler.target>17</maven.compiler.target>
<maven.compiler.source>17</maven.compiler.source>
<spring-boot.version>3.2.2</spring-boot.version>
</properties>
<dependencies>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-web</artifactId>
</dependency>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-test</artifactId>
<scope>test</scope>
</dependency>
<dependency>
<groupId>org.junit.vintage</groupId>
<artifactId>junit-vintage-engine</artifactId>
<scope>test</scope>
</dependency>
<dependency>
<groupId>junit</groupId>
<artifactId>junit</artifactId>
<scope>test</scope>
</dependency>
</dependencies>
<!-- [START Artifact Registry Config] -->
<distributionManagement>
<snapshotRepository>
<id>artifact-registry</id>
<url>artifactregistry://us-central1-maven.pkg.dev/<PROJECT>/java-repo</url>
</snapshotRepository>
<repository>
<id>artifact-registry</id>
<url>artifactregistry://us-central1-maven.pkg.dev/<PROJECT>/java-repo</url>
</repository>
</distributionManagement>
<repositories>
<repository>
<id>artifact-registry</id>
<url>artifactregistry://us-central1-maven.pkg.dev/<PROJECT>/java-repo</url>
<releases>
<enabled>true</enabled>
</releases>
<snapshots>
<enabled>true</enabled>
</snapshots>
</repository>
</repositories>
<build>
<extensions>
<extension>
<groupId>com.google.cloud.artifactregistry</groupId>
<artifactId>artifactregistry-maven-wagon</artifactId>
<version>2.2.0</version>
</extension>
</extensions>
<!-- [END Artifact Registry Config] -->
<plugins>
<plugin>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-maven-plugin</artifactId>
<version>${spring-boot.version}</version>
<executions>
<execution>
<goals>
<goal>repackage</goal>
</goals>
</execution>
</executions>
</plugin>
<plugin>
<groupId>com.google.cloud.tools</groupId>
<artifactId>jib-maven-plugin</artifactId>
<version>3.4.0</version>
<configuration>
<to>
<image>gcr.io/PROJECT_ID/helloworld</image>
</to>
</configuration>
</plugin>
</plugins>
</build>
</project>
อัปโหลดแพ็กเกจ Java ไปยัง Artifact Registry
เมื่อกำหนดค่า Artifact Registry ใน Maven แล้ว คุณจะใช้ Artifact Registry เพื่อจัดเก็บไฟล์ Java Jar ไว้ให้โปรเจ็กต์อื่นๆ ในองค์กรของคุณใช้ได้
เรียกใช้คำสั่งต่อไปนี้เพื่ออัปโหลดแพ็กเกจ Java ไปยัง Artifact Registry
mvn deploy
ตรวจสอบแพ็กเกจ Java ใน Artifact Registry
ไปที่ Cloud Console - Artifact Registry - Repositories คลิก java-repo
แล้วตรวจสอบว่ามีอาร์ติแฟกต์ไบนารี helloworld
อยู่
9 ยินดีด้วย
ยินดีด้วย คุณทำ Codelab เสร็จแล้ว
สิ่งที่คุณครอบคลุม
- สร้างที่เก็บสำหรับคอนเทนเนอร์และแพ็กเกจภาษาแล้ว
- อิมเมจคอนเทนเนอร์ที่มีการจัดการด้วย Artifact Registry
- Artifact Registry ที่ผสานรวมกับ Cloud Code
- กำหนดค่า Maven ให้ใช้ Artifact Registry สําหรับการอ้างอิง Java
ล้างข้อมูล
เรียกใช้คําสั่งต่อไปนี้ใน Cloud Shell เพื่อลบทั้งโปรเจ็กต์
gcloud projects delete $PROJECT_ID