TLDR: Packer sử dụng các mẫu để tự động hóa máy xây dựng image. Bạn xác định nguồn image, chỉ định cách tùy chỉnh nó bằng provisioner và Packer tạo ra image được định cấu hình cho một hoặc nhiều nền tảng. Nó giống như một hệ thống xây dựng cơ sở hạ tầng.
Trước khi viết các mẫu Packer, bạn cần hiểu Packer nghĩ như thế nào về image và quy trình làm việc mà nó sử dụng để xây dựng chúng.
Quy trình xây dựng image
Khi bạn xây dựng image theo cách thủ công, bạn thường:
- Khởi chạy phiên bản cơ sở (Ubuntu, CentOS, v.v.)
- Kết nối với nó và cài đặt phần mềm
- Định cấu hình dịch vụ và sao chép tập tin
- Dọn dẹp các tập tin và lịch sử tạm thời
- Tắt và tạo ảnh chụp nhanh image
- Kiểm tra image bằng cách khởi chạy phiên bản mới
Packer tự động hóa quy trình làm việc chính xác này. Mẫu xác định những gì cần xây dựng, builder khởi chạy một phiên bản tạm thời, provisioner tùy chỉnh nó và bộ xử lý hậu xử lý artifact cuối cùng.
Điểm khác biệt chính: Packer thực hiện điều này một cách lặp lại và nhất quán. Chạy cùng một mẫu hai lần, nhận được image giống hệt nhau.
Thành phần cốt lõi
Builder
builder chịu trách nhiệm tạo máy và tạo image từ chúng. Mỗi builder dành riêng cho một nền tảng:
amazon-ebs: Tạo AMI cho AWS EC2docker: Tạo Docker imagegooglecompute: Tạo image cho Google Cloudazure-arm: Tạo image cho Azurevirtualbox-iso: Tạo máy VirtualBox từ ISOvmware-iso: Tạo VMware image từ ISO
builder biết cách:
- Xác thực với nền tảng
- Khởi chạy một phiên bản xây dựng tạm thời
- Kết nối với phiên bản đó (SSH hoặc WinRM)
- Tạo image từ phiên bản
- Dọn dẹp tài nguyên tạm thời
Bạn có thể sử dụng nhiều builder trong một mẫu để tạo cùng một image cho các nền tảng khác nhau.
Provisioner
provisioner tùy chỉnh image sau khi builder tạo phiên bản cơ sở. provisioner phổ biến bao gồm:
Shell: Chạy lệnh hoặc tập lệnh shell
provisioner "shell" {
inline = [
"sudo apt-get update",
"sudo apt-get install -y nginx",
"sudo systemctl enable nginx"
]
}
File: Sao chép tệp từ máy của bạn sang image
provisioner "file" {
source = "configs/nginx.conf"
destination = "/tmp/nginx.conf"
}
ansible: Chạy Ansible playbook
provisioner "ansible" {
playbook_file = "./playbook.yml"
}
provisioner chạy theo thứ tự. Bạn thường:
- Cập nhật danh sách gói
- Cài đặt phần mềm
- Sao chép tập tin cấu hình
- Định cấu hình dịch vụ
- Dọn dẹp bộ đệm và nhật ký gói
Bộ xử lý sau
Bộ xử lý hậu kỳ chạy sau khi image được tạo. Họ có thể:
- Nén image
- Tải lên kho artifact
- Gắn thẻ image
- Tạo bảng kê khai với siêu dữ liệu bản dựng
- Đẩy Docker image vào cơ quan đăng ký
post-processor "docker-tag" {
repository = "mycompany/webapp"
tags = ["1.0.0", "latest"]
}
Bộ xử lý hậu kỳ là tùy chọn nhưng hữu ích để tích hợp Packer vào pipeline triển khai của bạn.
Cấu trúc mẫu HCL2
Các mẫu Packer hiện đại sử dụng HCL2 (Ngôn ngữ cấu hình HashiCorp), cùng ngôn ngữ với Terraform:
# Variables for reusability
variable "region" {
type = string
default = "us-east-1"
}
# Data sources for dynamic values
data "amazon-ami" "ubuntu" {
filters = {
name = "ubuntu/images/hvm-ssd/ubuntu-22.04-*"
}
most_recent = true
owners = ["099720109477"]
}
# Source defines reusable builder configuration
source "amazon-ebs" "web" {
ami_name = "web-server-{{timestamp}}"
instance_type = "t3.micro"
region = var.region
source_ami = data.amazon-ami.ubuntu.id
ssh_username = "ubuntu"
}
# Build brings it all together
build {
sources = ["source.amazon-ebs.web"]
provisioner "shell" {
inline = [
"sudo apt-get update",
"sudo apt-get install -y nginx"
]
}
post-processor "manifest" {
output = "manifest.json"
}
}
Mẫu này:
- Tìm AMI Ubuntu 22.04 mới nhất
- Khởi chạy phiên bản t3.micro trong us-east-1
- Cài đặt Nginx
- Tạo AMI từ phiên bản
- Lưu siêu dữ liệu bản dựng vào tệp kê khai.json
Quá trình xây dựng
Khi bạn chạy packer build template.pkr.hcl, Packer:
- Validates cú pháp và cấu hình mẫu
- Prepares builder (ví dụ: tìm nguồn AMI)
- Launches phiên bản xây dựng tạm thời
- Waits để có thể truy cập các phiên bản (SSH/WinRM)
- Runs provisioner theo thứ tự
- Phiên bản Stops
- Tạo image từ các phiên bản đã dừng
- Bộ xử lý hậu Runs
- Terminates phiên bản tạm thời
- Đầu ra image ID và artifact
Nếu có lỗi, Packer sẽ tự động dọn sạch các tài nguyên tạm thời.
Packer so với Docker
Packer có thể xây dựng Docker image, nhưng nó không thể thay thế cho Dockerfiles:
Dockerfile: Được xây dựng có mục đích cho container. Nhanh chóng, phân lớp, tối ưu hóa cho các ứng dụng được đóng gói.
Packer với trình tạo Docker: Hữu ích khi bạn cần logic cung cấp giống nhau cho cả máy ảo và container. Cũng hữu ích cho các bản dựng nhiều giai đoạn phức tạp hoặc tích hợp với quản lý cấu hình hiện có.
Hầu hết các nhóm sử dụng Dockerfiles cho container và Packer cho VM/cloud image.
Khi nào nên sử dụng Packer
Packer có ý nghĩa khi:
Bạn cần khởi chạy phiên bản nhanh: image được cấu hình sẵn khởi động trong vài giây so với vài phút cấu hình.
Bạn triển khai trên nhiều đám mây: Một mẫu xây dựng AWS AMI, GCP image và Azure image.
Bạn muốn cơ sở hạ tầng bất biến: Thay vì cập nhật các máy chủ đang chạy, hãy triển khai image mới.
Bạn có quy trình xây dựng phức tạp: Cài đặt nhiều ngôn ngữ, biên dịch phần mềm hoặc chạy thử nghiệm mở rộng.
Tuân thủ yêu cầu các bản kiểm tra: Các mẫu Packer trong tài liệu kiểm soát phiên bản chính xác có những gì trong mỗi image.
Packer có thể quá mức cần thiết nếu bạn chỉ triển khai container hoặc cơ sở hạ tầng của bạn thay đổi thường xuyên (quản lý cấu hình có thể tốt hơn).
Tiếp theo là gì
Bây giờ bạn đã hiểu kiến trúc và quy trình làm việc của Packer, chương tiếp theo sẽ đề cập đến việc cài đặt Packer và thiết lập môi trường để xây dựng image đầu tiên của bạn.