1 điểm bởi GN⁺ 4 giờ trước | 1 bình luận | Chia sẻ qua WhatsApp
  • Viết các tác vụ tự động hóa máy chủ bằng mã Python và chạy song song qua SSH, thực thi lệnh theo cách idempotent mà không cần agent
  • pyinfra nhấn mạnh hiệu năng nhanh hơn Ansible 6 lần trên cùng một workload, sử dụng thực thi đồng thời dựa trên gevent và SSH
  • Với tùy chọn --dry, có thể xem diff thay đổi theo từng host trước khi áp dụng, và khi chạy thực tế kết quả được trả về dưới dạng streaming song song
  • Các host đích chỉ cần shell và SSH, không có daemon, file trạng thái hay control plane
  • Nhấn mạnh cách tiếp cận cấu hình lấy code làm trung tâm, không mã hóa luồng điều khiển bằng YAML mà dùng trực tiếp vòng lặp và câu lệnh điều kiện của Python

Tính năng cốt lõi và luồng thực thi

  • Tự động hóa hàng nghìn máy chủ

    • pyinfra là công cụ tự động hóa native cho Python, không cần agent và thực thi lệnh qua SSH
    • Việc thực thi lệnh nhấn mạnh tính đồng thời, idempotent và tốc độ, với tuyên bố nhanh hơn Ansible 6 lần trên cùng một workload
    • Lệnh cài đặt là $ uv tool install pyinfra
    • Các điều kiện cơ bản được nêu gồm MIT license, Python 3.10 trở lên, no agents, zero config
  • Ví dụ mã triển khai

    • Gọi các tác vụ apt, files, systemd bằng mã Python để cài gói, triển khai template và reload dịch vụ
    • Mã ví dụ cài các gói nginxcertbot, rồi đặt templates/nginx.conf.j2 vào /etc/nginx/sites-enabled/api
    • Ở bước cuối, reload dịch vụ nginx bằng systemd.service("nginx", reloaded=True)
    from pyinfra.operations import apt, files, systemd
    
    apt.packages(
        packages=["nginx", "certbot"],
        update=True,
    )
    
    files.template(
        src="templates/nginx.conf.j2",
        dest="/etc/nginx/sites-enabled/api",
    )
    
    systemd.service("nginx", reloaded=True)
    
  • Inventory và kết quả thực thi

    • Ví dụ inventory gồm các host web từ web-01.prod đến web-23.prod và các host cơ sở dữ liệu db-01.prod, db-02.prod
    • Lệnh $ pyinfra inventory.py deploy.py --limit web giới hạn thực thi chỉ trên nhóm web
    • Đầu ra khi chạy diễn ra theo thứ tự: nạp inventory, thu thập fact đồng thời, thực thi deploy.py, rồi tổng kết
    • Phần tổng kết ví dụ ghi nhận 23 host thành công, 18 host có thay đổi, 0 thất bại, tổng cộng 2.1 giây
  • Kiểm tra trước khi thay đổi

    • --dry cho phép xem trước diff theo từng host của mọi tác vụ mà pyinfra sẽ thực hiện
    • Khi chạy thực tế, kết quả được stream song song và hiển thị số thay đổi cùng thời gian thực thi của từng host
    • Ví dụ chạy ghi nhận 18 host có thay đổi, 6 host không thay đổi, 0 thất bại trên tổng 24 host, tổng cộng 2.1 giây

Đặc điểm, so sánh với Ansible và nguyên tắc

  • Sáu lý do để chọn pyinfra

    • Just Python: viết luồng điều khiển thực sự bằng Python, không dùng YAML hay Jinja-in-YAML
    • Concurrent SSH: thực thi đồng thời dựa trên gevent và SSH, nhanh hơn Ansible 6 lần trên cùng một workload
    • Diff before apply: xem trước mọi thay đổi bằng --dry, và các tác vụ idempotent sẽ trở thành no-op khi chạy lại
    • 0 agents: host chỉ cần shell và SSH, không có daemon, file trạng thái hay control plane
    • Scale-ready: hoạt động từ 1 host đến 10.000 host, hỗ trợ chạy song song và xuất kết quả streaming thời gian thực
    • Hackable: có thể tạo tác vụ tùy chỉnh trong 10 dòng, và kết nối tới docker, lxc, k8s giao tiếp qua shell
  • So sánh mã giữa Ansible và pyinfra

    • Ví dụ Ansible dùng playbook.yml 16 dòng để cài nginx, render template và reload dịch vụ theo kiểu handler
    • Ví dụ pyinfra dùng deploy.py 8 dòng để viết cùng luồng đó bằng mã Python
    • Ví dụ pyinfra chỉ thực thi systemd.service("nginx", reloaded=True) khi cfg.will_change từ kết quả files.template là true
    from pyinfra.operations import apt, files, systemd
    
    apt.packages(["nginx"], update=True)
    
    cfg = files.template(
        src="nginx.conf.j2",
        dest="/etc/nginx/sites-enabled/api",
    )
    if cfg.will_change:
        systemd.service("nginx", reloaded=True)
    
  • Tuyên ngôn

    • Code > config: vòng lặp vẫn là vòng lặp, không mã hóa luồng điều khiển vào YAML
    • Show, then do: xem diff trước, rồi mới áp dụng để tránh thay đổi ngoài ý muốn
    • Stay out of the way: chạy trực tiếp qua SSH mà không có agent, file trạng thái hay control plane
    • Read like english: các tác vụ được đọc như danh từ và động từ, như apt.packages, files.template, systemd.service
  • Lệnh bắt đầu

    • Lệnh cài đặt là $ uv tool install pyinfra
    • Có hướng dẫn đọc quickstart 5 phút và triển khai host đầu tiên

1 bình luận

 
Ý kiến trên Lobste.rs
  • pyinfra cho cảm giác như đây mới là thứ Ansible lẽ ra nên trở thành. Thay vì chồng thêm luồng điều khiển lên YAML trộn template, bạn có thể viết tự động hóa trực tiếp bằng Python
    Sau thời gian dài làm việc với Ansible, điều này khá mới mẻ, dù trước đó tôi cũng không phải người ghét Ansible

    • Nói chính xác thì nó có vẻ không hẳn là Ansible viết bằng Python, mà gần với một trình thông dịch chuyển từ Python sang shell hơn, và bản thân cách đó cũng có vấn đề riêng
      Có lẽ mô hình lai dùng Python cả trên máy đích sẽ tốt hơn. Khi cập nhật tệp sẽ bớt cảnh địa ngục dấu nháy, đồng thời tránh được các giới hạn regex của sed
  • Tôi thích pyinfra và mong nó được dùng rộng rãi hơn
    Tất cả các công ty tôi từng làm đều dùng Ansible, bất kể có dùng kèm Terraform hay không, và chưa nơi nào sẵn sàng viết lại toàn bộ hệ thống tự động hóa hiện có bằng một công cụ mà nhân viên không có kinh nghiệm
    pyinfra đòi hỏi SysOps phải biết Python, nhưng cá nhân tôi cho rằng SysOps nên biết ít nhất một ngôn ngữ scripting. Đặc biệt là ngay cả với Ansible, nếu viết module bằng Python thì cũng giảm được mớ hỗn độn YAML, nhưng ít nhất ở Pháp có vẻ đây không phải quan điểm phổ biến

    • Tôi đã dùng Ansible khá nhiều, và thực ra xem nó như một thứ đội lốt ngôn ngữ scripting
      Có lẽ chuyện này cũng không phải chủ đề tranh cãi quá gay gắt
  • Tôi từng dùng Ansible cho homelab rồi ngày càng thấy bí bách. Cấu hình YAML thì khủng khiếp, mọi thứ đều như kiểu chắp vá, và tốc độ thì đáng buồn. Việc chỉ để chạy vài lệnh shell mà máy chủ lại cần python3 cũng khó chấp nhận
    Nhờ Google AI Mode tôi biết đến pyinfra, và trong gần một tháng sử dụng thì nó cho cảm giác dễ thở hơn nhiều. Ưu điểm là nhanh hơn Ansible đáng kể, có thể viết vòng lặp và điều kiện bằng Python, không cần roles hay thư mục lồng nhau, và phía máy chủ chỉ cần shell là đủ. Trước khi chạy nó tạo plan dựa trên trạng thái hiện tại, và nếu không thêm -y thì còn yêu cầu xác nhận
    Nhược điểm là các tác vụ mặc định chỉ là một tập con khá nhỏ so với module của Ansible, mã nguồn có thể nhanh chóng thành spaghetti, và kiểu if 'web_server' in hosts.groups cũng không hẳn hay. Có thể operation(..., filter_group='web_server') sẽ tốt hơn
    Điểm tệ nhất là việc viết connector tùy chỉnh quá khổ sở. Có vẻ cần một pyproject.toml với entry point riêng của pyinfra, và ngay cả khi dùng uv, việc phát triển connector nội bộ vẫn như ác mộng. Đáng ra phải có thể làm nó như một tệp Python bình thường ngay trong dự án

  • Tôi đang thử pyinfra vài ngày nay cho công cụ triển khai homelab, và so với Ansible thì điều tôi thích nhất đến giờ, hơn cả cú pháp Python, là tốc độ
    Ansible lúc nào cũng cho cảm giác chậm đến mức khó chịu

    • Mảng này khá thú vị. Tôi cũng đang làm một công cụ triển khai và dùng nó cho triển khai thực tế trong công việc chính
      Tôi muốn thay thế việc dùng Ansible và Salt ở hầu hết mọi nơi
  • Thật thú vị khi hạ tầng dưới dạng mã đã đi trọn một vòng. Từ script sang YAML rồi lại quay về script tinh vi hơn
    Mỗi cách tiếp cận đều có điểm phù hợp riêng, và từ góc nhìn của người dùng Ansible thì pyinfra trông khá ổn

  • Lý do cốt lõi khiến tôi chọn Ansible là chế độ dry-run và xem khác biệt. Nhờ vậy tôi có thể tin rằng nó sẽ không làm điều gì ngoài dự kiến
    Nhưng CLI của pyinfra có vẻ không có tùy chọn như vậy. Có thể tôi đã bỏ sót vì không tìm được tài liệu tham chiếu gom tất cả tùy chọn theo thứ tự alphabet

    • Có cờ —dry, và nó xuất hiện ngay trên màn hình đầu tiên của pyinfra
  • Với ai quan tâm, tôi cũng có một dự án tương tự đã 14 năm tuổi: https://github.com/sebastien/cuisine/tree/main
    Nó không cần agent, chỉ dùng SSH, và cung cấp API đậm chất Python trên các chức năng quản trị cốt lõi, nhưng không hỗ trợ dry mode

  • Chúng tôi dùng Ansible để provision tài nguyên trên OpenStack, còn mọi thứ khác xử lý bằng pyinfra, và trong vài năm qua nó hoạt động khá tốt
    Nhược điểm lớn nhất là cộng đồng nhỏ nên bạn thường phải tự viết cách giải quyết. Ví dụ, chúng tôi tự viết vài dòng mã để lưu shared secret cần cho triển khai lên đĩa bằng keyring + privy, đồng thời chuyển inventory compute của OpenStack thành dữ liệu hosts