Sự khác biệt giữa các cổng soạn thảo docker so với phơi bày


Câu trả lời:


527

Theo tài liệu tham khảo soạn thảo docker ,

Các cổng được định nghĩa là:

Các cổng tiếp xúc . Hoặc chỉ định cả hai cổng (HOST: CONTAINER) hoặc chỉ cổng container (một cổng máy chủ ngẫu nhiên sẽ được chọn).

  • Các cổng được đề cập trong docker-compose.yml sẽ được chia sẻ giữa các dịch vụ khác nhau được bắt đầu bởi docker-compose.
  • Các cổng sẽ được tiếp xúc với máy chủ với một cổng ngẫu nhiên hoặc một cổng nhất định.

Hình của tôi docker-compose.ymlnhư:

mysql:
  image: mysql:5.7
  ports:
    - "3306"

Nếu tôi làm docker-compose ps, nó sẽ giống như:

  Name                     Command               State            Ports
-------------------------------------------------------------------------------------
  mysql_1       docker-entrypoint.sh mysqld      Up      0.0.0.0:32769->3306/tcp

Expose được định nghĩa là:

Đưa ra các cổng mà không xuất bản chúng cho máy chủ - chúng sẽ chỉ có thể truy cập được với các dịch vụ được liên kết. Chỉ có thể chỉ định cổng nội bộ.

Các cổng không được tiếp xúc với máy chủ, chỉ tiếp xúc với các dịch vụ khác.

mysql:
  image: mysql:5.7
  expose:
    - "3306"

Nếu tôi làm docker-compose ps, nó sẽ giống như:

  Name                  Command             State    Ports
---------------------------------------------------------------
 mysql_1      docker-entrypoint.sh mysqld   Up      3306/tcp

24
eto có thể giải thích những lợi thế nào để chỉ định exposetrong một docker-compose? Theo như tôi có thể nói, bạn không cần chỉ định phơi bày để làm cho các cổng có thể truy cập được vào các dịch vụ được liên kết.
Juicy

3
Không nên nói rằng các cổng bị lộ sẽ chỉ khả dụng cho các dịch vụ trong cùng một mạng docker (liên kết đang được thay thế cho hầu hết các bộ phận)?.
meo

8
@Juicy Tôi đoán nó tương tự như exposetrong Dockerfiles: "Lệnh EXPOSE không thực sự xuất bản cổng. Nó hoạt động như một loại tài liệu ..." docs.docker.com/engine/reference/builder/#expose
tsauerwein

1
Các cổng có ghi đè bất kỳ cài đặt nào ở cấp tường lửa không? Tôi chỉ nhận thấy rằng tôi đã không mở các cổng cho mysql trên tường lửa, nhưng chúng có thể truy cập từ xa. Tôi đã đặt Cổng thành "3306: 3306" thay vì phơi sáng.
TekiusFanatikus

3
Và hãy nhớ, nếu bạn sử dụng docker-compose run, định nghĩa cổng trong docker-compose.ymlđược bỏ qua theo mặc định. Sử dụng docker-compose uphoặc cung cấp tham số--service-ports
Juha Untinen

177

cổng :

  1. Kích hoạt bộ chứa để lắng nghe (các) cổng được chỉ định từ thế giới bên ngoài docker (có thể là cùng một máy chủ hoặc một máy khác) VÀ cũng có thể truy cập thế giới bên trong docker.
  2. Có thể chỉ định nhiều hơn một cổng (đó là lý do tại sao các cổng không phải là cổng)

nhập mô tả hình ảnh ở đây

phơi bày :

  1. Kích hoạt container để lắng nghe một cổng cụ thể chỉ từ thế giới bên trong docker VÀ thế giới không thể truy cập bên ngoài docker.
  2. Nhiều cổng có thể được chỉ định

nhập mô tả hình ảnh ở đây


3
Lưu ý rằng phơi sáng cho phép nhiều cổng - docs.docker.com/compose/compose-file/#expose - tuy nhiên bạn chỉ cung cấp cổng nội bộ chứ không phải bên trong + bên ngoài
Stuart Moore

Nhưng phải làm gì nếu tôi muốn gia nhập thế giới bên ngoài từ container của mình? stackoverflow.com/questions/61322256/
Mạnh

26

Cổng Phần này được sử dụng để xác định ánh xạ giữa máy chủ lưu trữ và bộ chứa Docker.

ports:
   - 10005:80

Nó có nghĩa là ứng dụng chạy bên trong container được hiển thị tại cổng 80. Nhưng hệ thống / thực thể bên ngoài không thể truy cập vào nó, vì vậy nó cần được ánh xạ tới cổng máy chủ lưu trữ.

Lưu ý: bạn phải mở cổng máy chủ 10005 và sửa đổi các quy tắc tường lửa để cho phép các thực thể bên ngoài truy cập vào ứng dụng.

Họ có thể sử dụng

http: // {IP máy chủ}: 10005

một cái gì đó như thế này

TIẾP XÚC Điều này được sử dụng riêng để xác định cổng mà ứng dụng đang chạy bên trong bộ chứa docker.

Bạn có thể định nghĩa nó trong dockerfile. Nói chung, đó là cách thực hành tốt và được sử dụng rộng rãi để xác định EXPOSE bên trong dockerfile vì rất hiếm khi có ai chạy chúng trên cổng khác ngoài cổng 80 mặc định


19

Cổng

Phần portsnày sẽ xuất bản các cổng trên máy chủ. Docker sẽ thiết lập chuyển tiếp cho một cổng cụ thể từ mạng chủ vào container. Theo mặc định, điều này được thực hiện với quy trình proxy không gian người dùng (docker-proxy ) lắng nghe trên cổng đầu tiên và chuyển tiếp vào vùng chứa, cần lắng nghe ở điểm thứ hai. Nếu container không nghe trên cổng đích, bạn vẫn sẽ thấy một cái gì đó đang nghe trên máy chủ, nhưng bị từ chối kết nối nếu bạn cố kết nối với cổng máy chủ đó, từ việc chuyển tiếp thất bại vào container của bạn.

Lưu ý, bộ chứa phải lắng nghe trên tất cả các giao diện mạng vì proxy này không chạy trong không gian tên của bộ chứa và không thể đạt tới 127.0.0.1 bên trong bộ chứa. Phương pháp IPv4 cho điều đó là cấu hình ứng dụng của bạn để nghe 0.0.0.0.

Cũng lưu ý rằng các cổng được xuất bản không hoạt động theo hướng ngược lại. Bạn không thể kết nối với một dịch vụ trên máy chủ từ container bằng cách xuất bản một cổng. Thay vào đó, bạn sẽ tìm thấy lỗi docker khi cố gắng lắng nghe cổng máy chủ đã sử dụng.

Lộ ra

Tiếp xúc là tài liệu. Nó đặt siêu dữ liệu trên hình ảnh và khi chạy, trên container cũng vậy. Thông thường, bạn định cấu hình này trong Dockerfile theo EXPOSEhướng dẫn và nó đóng vai trò là tài liệu cho người dùng chạy hình ảnh của bạn, để họ biết cổng nào theo mặc định ứng dụng của bạn sẽ lắng nghe. Khi được định cấu hình với tệp soạn thảo, siêu dữ liệu này chỉ được đặt trên vùng chứa. Bạn có thể thấy các cổng bị lộ khi bạn chạy một docker inspecthình ảnh hoặc thùng chứa.

Có một vài công cụ dựa vào các cổng tiếp xúc. Trong docker, -Pcờ sẽ xuất bản tất cả các cổng tiếp xúc lên các cổng phù du trên máy chủ. Ngoài ra còn có các proxy ngược khác nhau sẽ mặc định sử dụng cổng bị lộ khi gửi lưu lượng truy cập đến ứng dụng của bạn nếu bạn không đặt cổng container một cách rõ ràng.

Khác với những công cụ bên ngoài, phơi bày hoàn toàn không có tác động đến kết nối mạng giữa các container. Bạn chỉ cần một mạng docker chung và kết nối với cổng container, để truy cập một container từ một container khác. Nếu mạng đó là do người dùng tạo (ví dụ: mạng cầu nối mặc định có tên bridge), bạn có thể sử dụng DNS để kết nối với các container khác.


3

Tôi hoàn toàn đồng ý với câu trả lời trước đó. Tôi chỉ muốn đề cập rằng sự khác biệt giữa phơi bày và cổng là một phần của khái niệm bảo mật trong docker. Nó đi đôi với mạng lưới docker. Ví dụ:

Hãy tưởng tượng một ứng dụng có giao diện người dùng web và cơ sở dữ liệu phía sau. Thế giới bên ngoài cần quyền truy cập vào giao diện người dùng web (có lẽ trên cổng 80), nhưng chỉ bản thân back-end mới cần quyền truy cập vào máy chủ cơ sở dữ liệu và cổng. Sử dụng cầu do người dùng xác định, chỉ cần mở cổng web và ứng dụng cơ sở dữ liệu không cần mở bất kỳ cổng nào, vì giao diện người dùng web có thể tiếp cận qua cầu do người dùng xác định.

Đây là trường hợp sử dụng phổ biến khi thiết lập kiến ​​trúc mạng trong docker. Vì vậy, ví dụ trong một mạng cầu mặc định, không thể truy cập các cổng từ thế giới bên ngoài. Do đó, bạn có thể mở một điểm vào với "cổng". Với việc sử dụng "phơi bày", bạn xác định giao tiếp trong mạng. Nếu bạn muốn hiển thị các cổng mặc định, bạn không cần xác định "phơi sáng" trong tệp soạn thảo docker.

Khi sử dụng trang web của chúng tôi, bạn xác nhận rằng bạn đã đọc và hiểu Chính sách cookieChính sách bảo mật của chúng tôi.
Licensed under cc by-sa 3.0 with attribution required.