Giao tiếp giữa các container trong Docker – Docker Compose

Tram Ho

Xin chào mọi người, ở bài viết lần trước mình đã nói về chủ đề kết nối và link giữa các container trong docker (link). Như đã hứa mình sẽ viết chủ đề tiếp theo liên quan đến 1 công cụ hỗ trợ mà những ai tìm hiểu Docker đều có thể đã sử dụng qua, đó chính là Docker Compose.

Tất nhiên bài viết không hoàn toàn do mình viết ra, mình có đọc quyển “Docker in Pratice” và dịch từ 1 chương trong quyển này kết hợp với kiến thức mà mình biết. Phần mình nhắc đến sẽ là Part3 – Chapter 8 – 8.1 – Container communication—beyond manual linking (tạm dịch là giao tiếp giữa các container, vượt qua nỗi khổ nhục liên kết bằng tay).

1. Mở bài

Ở bài trước chúng ta đã thấy được cách kết nối các container với linking container hay dùng mapping port với môi trường ngoài. Tuy nhiên link cũng có một vài nhược điểm. Đó là chúng ta phải sử dụng tay để xác định xem khi nào sẽ khởi động từng container một (vì container phải khởi động theo thứ tự để ta có thể link được) và hơn nữa là ko có cách nào để loại bỏ cái kết nối đó (linking) giữa các container (nếu 1 container chết, tất cả các container phụ thuộc vào nó đều phải khởi động lại để tạo lại linking.

Do đó chúng ta cần 1 công cụ giải quyết vấn đề này, vâng chính là Docker Compose.

2. Giới thiệu Docker Compose.

Oke, muốn làm thì trước tiên cũng phải biết nó là gì đã. Docker Compose bắt đầu được biết đến với cái tên fig, được tạo ra nhằm giảm thiểu và loại bỏ việc khởi động nhiều container với những tham số như linking, volumes hay ports. Docker Inc. đã rất thích ý tưởng này và họ đã tiếp nhận nó, tạo lại nó và release nó với một cái tên mới.

Docker Compose là 1 công cụ cho việc định nghĩa và khởi chạy các ứng dụng Docker phức tạp. Ý tưởng chủ đạo của công cụ này là thay vì liên kết các lệnh khởi động với những container phức tạp bằng các công cụ như Shell script hay Makefiles, bạn có thể xác định các cài đặt ban đầu khi khởi động ứng dụng (hay container) và gói gọn chúng trong chỉ 1 command duy nhất. Vào thời điểm được viết ra thì Docker Compose không được khuyến khích sử dụng ở trên môi trường production. (không nên dùng trên sản phẩm thực tế nhé)

Về cách cài đặt Docker Compose các bạn hãy tham khảo trên trang chủ https://docs.docker.com/compose/install/. Có hướng dẫn khá chi tiết, hãy nhớ nên đọc kĩ nhé. Còn nữa về chạy docker không cần sudo, tất cả cũng ở trên trang chủ nuôn, anhem ko cần lo nhé https://docs.docker.com/install/linux/linux-postinstall/.

3. Ví dụ về cách sử dụng.

Chúng ta sẽ tạo ra 1 echo server và client (cái ví dụ này mình lấy y hệt trong sách ra nhá, vì họ viết cũng đơn giản khó hiểu). Client sẽ gửi 1 message mỗi 5s tới echo server và nhận message trả về ngược lại.

Đầu tiên chúng ta tạo ra thư mục server và trỏ vào nó cái đã:

Tiếp theo, tạo Dockerfile cho phía server với nội dung như sau:

Option -l 2000 thông báo cho ncat lắng nghe cổng 2000 và options -k nói với nó để cho phép nhiều kết nối từ client xảy ra đồng thời cũng như tiếp tục chạy sau khi client đóng kết nối. Option cuối cùng --exec /bin/cat sẽ làm cho ncat chạy lệnh /bin/cat cho bất kỳ kết nối nào tới và chuyển tiếp bất kỳ data nào đều từ các ckeest nối ra ngoài chương trình.

Oke tiếp theo, ta sẽ build Dockerfile bằng lệnh

Giờ chúng ta có thể cài đặt các image clinet để gửi message đến server. Tạo thư mục client cùng cấp với server rồi tạo ra file client. py:

và Dockerfile

Sau đó tương tự ta cũng build client:

Và để xác định khả năng chạy của nó thì ta sẽ chạy 2 câu lệnh:

Khi bạn hoàn thành xong thì hãy out ra khỏi client và xóa container:

Vô vàn thứ có thể chạy sai ngay cả trong ví dụ trên: khởi động client trước sẽ khiến ứng dụng không thể khởi tạo, quên xóa container cũng có thể là vấn đề nếu bạn muốn restart, hay đặt tên container sai cũng dẫn đến lỗi. Những vấn đề này sẽ càng tăng lên nếu ứng dụng cũng như kiến trúc dự án càng phức tạp.

Compose giúp chúng ta bởi việc đóng gói sự liên kết giữa các container khi khởi tạo và caft đặt trong cùng 1 text file, quản lý đầu ra đầu vào của việc khởi tạo cũng như tắt container.

Compose sử dụng YAML file để biết. Giả sử chúng ta có file docker-compose.yml sau cùng cấp với các thư mục server và client:

Nó tè 1: Yaml file là 1 file text để khai báo thông tin theo cấp. Nó gần tương tự cấu trúc kiểu object -> child object -> child object …-> attribute. Thông ass chi tiết nó thì anhem xem ở đây: https://yaml.org/ ? Nếu các bạn đã quen với file dạng .json thì YAML là .yml cũng tương tự kiến trúc đó, chả qua là ta bỏ hết đi mấy dấu “{” hay “}” đi thuôi ✌️

Syntax của docker-compose.yml rất dễ để đọc, mỗi service được đặt tên và theo từng tầng dựa vào các dấu cách, mỗi item có dấu hai chấm sau tên và các attribute của mỗi item sẽ ở cùng 1 khoảng cách với đầu dòng. Và hơn nữa cách viết cũng tương tự như với commands, giả sử như với linking.

CHúng ta cũng sử dụng image: để định nghĩa tên image sử dụng cho mỗi service, tuy nhiên bạn cũng có thể dùng docker-compose để build lại image bằng cách trỏ đến đường dẫn chứa Dockerfile, nó sẽ build image trước cho bạn rồi mới tiến hành start container. Khi đó ta sẽ sử dụng option là build: thay cho image.

Oke sau khi chạy và in ra thì ta sẽ thấy ở màn hình: (nhìn màn hình chạy chạy cảm giác như hack cmn ker =)) cái này các ông đem đi lừa gái 100% bọn nó tin, à mà tất nhiên không phải gái IT nhé)

Nó tè 2: Nếu bạn bị gặp lỗi kiểu: “Couldn’t connect to Docker daemon at http+unix://var/run/docker.sock—is it running?” thì rất có thể nó liên quan đến quyền sudo khi chạy docker. Mình có reference link ở trên rồi, kéo lên đọc lại nhé =))

Ok nếu xem đủ rồi thì bạn có thể Ctrl + C để thoát khỏi app. Bạn có thể khởi động lại nó dễ dàng bằng lệnh up như nãy mà không cần phải nghĩ đến việc remove hay gì cả. Nhớ rằng khi khởi tạo lại thì ở màn hình sẽ hiện là Recreating thay vì Creating như nãy.

4. Chốt tộ

Bài viết này chỉ ra cho bạn những vấn đề mà Docker Compose giải quyết giúp bạn trong thực tế mà khi bạn chạy tay (hay còn gọi là chạy chay) thì dễ xảy ra lỗi. Docker Compose hay nói cách khác giúp bạn đóng gói ứng dụng, service, hỗ trợ bạn luồng chạy mà bạn phải config tay hoặc phải define sẵn qua scripts (mặc dù nguyên lý làm cũng tương tự thôi, chả qua là có người làm cho bạn ăn sẵn thuôi).

Điều mà mình thích ở thằng này đó là khả năng xây dựng nhanh (vì bạn chỉ cần define ra 1 file và bấm 1 lệnh duy nhất) khi stop hay recreate lại cũng cực kỳ nhanh), hỗ trợ rất nhiều trong việc đồng bộ môi trường làm việc giữa các dev, nhất trong giai đoạn dự án mới start. Hơn nữa config dễ hiểu cũng giúp cho người đọc dù là chưa biết gì cũng có thể mường tượng ra được.

Ở bài viết sau mình sẽ đề cập đến 1 vài ví dụ cụ thể hơn, chỉ ra điểm yếu mạnh của công cụ này, và có thể đưa chúng ta đến 1 công cụ mới, thứ mà giúp chúng ta tiếp cận gần hơn đến môi trường productions, đó là k8s. Cảm ơn anh em đã đọc, mọi thắc mắc chửi bới như thường lệ, hãy comments phía dưới để mình có thể cùng thảo luận.

Chia sẻ bài viết ngay

Nguồn bài viết : Viblo