Quelle est la différence entre les ports de composition de docker et l'exposition

462

Quelle est la différence entre les options portsetexposedocker-compose.yml

bibstha
la source

Réponses:

527

Selon la référence docker-compose ,

Les ports sont définis comme:

Exposez les ports . Spécifiez les deux ports (HOST: CONTAINER) ou simplement le port de conteneur (un port d'hôte aléatoire sera choisi).

  • Les ports mentionnés dans docker-compose.yml seront partagés entre les différents services démarrés par le docker-compose.
  • Les ports seront exposés à la machine hôte vers un port aléatoire ou un port donné.

Mes docker-compose.ymllooks:

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

Si je le fais docker-compose ps, cela ressemblera à:

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

Exposer est défini comme:

Exposez les ports sans les publier sur la machine hôte - ils ne seront accessibles qu'aux services liés. Seul le port interne peut être spécifié.

Les ports ne sont pas exposés aux machines hôtes, mais uniquement aux autres services.

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

Si je le fais docker-compose ps, cela ressemblera à:

  Name                  Command             State    Ports
---------------------------------------------------------------
 mysql_1      docker-entrypoint.sh mysqld   Up      3306/tcp
bibstha
la source
24
Serait-il possible eto d'expliquer quels avantages il y a à spécifier exposedans un docker-compose? Pour autant que je sache, vous n'avez pas besoin de spécifier exposer pour rendre les ports accessibles aux services liés.
Juicy
3
Cela ne devrait-il pas dire que les ports exposés ne seront disponibles que pour les services du même réseau docker (la liaison est remplacée pour la plupart des parties)?.
meow
8
@Juicy Je suppose que c'est similaire à exposeDockerfiles: "L'instruction EXPOSE ne publie pas réellement le port. Elle fonctionne comme un type de documentation ..." docs.docker.com/engine/reference/builder/#expose
tsauerwein
1
Les ports remplacent-ils les paramètres au niveau du pare-feu? Je viens de remarquer que je n'ai pas ouvert les ports pour mysql sur le pare-feu, mais ils étaient accessibles à distance. J'ai eu des ports réglés sur "3306: 3306" au lieu d'exposer.
TekiusFanatikus
3
Et n'oubliez pas, si vous utilisez docker-compose run, la définition de port dans docker-compose.ymlest ignorée par défaut. Utilisez docker-compose upou fournissez le paramètre--service-ports
Juha Untinen
178

ports :

  1. Active le conteneur pour écouter les ports spécifiés du monde extérieur au docker (peut être la même machine hôte ou une machine différente) ET également le monde accessible à l'intérieur du docker.
  2. Plus d'un port peut être spécifié (c'est pourquoi les ports ne sont pas portés)

entrez la description de l'image ici

exposer :

  1. Active le conteneur pour écouter un port spécifique uniquement à partir du monde à l'intérieur du docker ET du monde non accessible à l'extérieur du docker.
  2. Plus d'un port peut être spécifié

entrez la description de l'image ici

Mehraj Malik
la source
3
Notez qu'exposer autorise plusieurs ports - docs.docker.com/compose/compose-file/#expose - mais vous ne fournissez que le port interne plutôt qu'interne + externe
Stuart Moore
Mais que faire si je veux accéder au monde extérieur depuis mon conteneur? stackoverflow.com/questions/61322256/…
gstackoverflow
26

Ports Cette section est utilisée pour définir le mappage entre le serveur hôte et le conteneur Docker.

ports:
   - 10005:80

Cela signifie que l'application exécutée à l'intérieur du conteneur est exposée au port 80. Mais le système / l'entité externe ne peut pas y accéder, elle doit donc être mappée au port du serveur hôte.

Remarque: vous devez ouvrir le port hôte 10005 et modifier les règles de pare-feu pour permettre aux entités externes d'accéder à l'application.

Ils peuvent utiliser

http: // {hôte IP}: 10005

quelque chose comme ça

EXPOSE Ceci est exclusivement utilisé pour définir le port sur lequel l'application s'exécute à l'intérieur du conteneur Docker.

Vous pouvez également le définir dans dockerfile. En règle générale, il est bon et largement utilisé de définir EXPOSE dans le dockerfile car très rarement, quiconque les exécute sur un autre port que le port 80 par défaut

sorabzone
la source
19

Ports

La portssection publiera les ports sur l'hôte. Docker configurera un transfert pour un port spécifique du réseau hôte vers le conteneur. Par défaut, cela est implémenté avec un processus proxy d'espace utilisateur (docker-proxy ) qui écoute sur le premier port, et transfère dans le conteneur, qui doit écouter sur le deuxième point. Si le conteneur n'écoute pas sur le port de destination, vous verrez toujours quelque chose à l'écoute sur l'hôte, mais vous obtiendrez une connexion refusée si vous essayez de vous connecter à ce port hôte, de l'échec vers l'avant dans votre conteneur.

Remarque, le conteneur doit écouter sur toutes les interfaces réseau car ce proxy ne s'exécute pas dans l'espace de noms réseau du conteneur et ne peut pas atteindre 127.0.0.1 à l'intérieur du conteneur. La méthode IPv4 consiste à configurer votre application pour écouter 0.0.0.0.

Notez également que les ports publiés ne fonctionnent pas dans la direction opposée. Vous ne pouvez pas vous connecter à un service sur l'hôte à partir du conteneur en publiant un port. Au lieu de cela, vous trouverez des erreurs de docker lors de l'écoute du port hôte déjà utilisé.

Exposer

Exposer est la documentation. Il définit des métadonnées sur l'image et, lors de l'exécution, sur le conteneur également. Généralement, vous configurez cela dans le Dockerfile avec l' EXPOSEinstruction, et elle sert de documentation aux utilisateurs exécutant votre image, pour qu'ils sachent sur quels ports par défaut votre application écoutera. Lorsqu'elles sont configurées avec un fichier de composition, ces métadonnées ne sont définies que sur le conteneur. Vous pouvez voir les ports exposés lorsque vous exécutez un docker inspectsur l'image ou le conteneur.

Il existe quelques outils qui dépendent des ports exposés. Dans Docker, le-P drapeau publiera tous les ports exposés sur les ports éphémères de l'hôte. Il existe également divers proxys inverses qui utiliseront par défaut un port exposé lors de l'envoi de trafic vers votre application si vous ne définissez pas explicitement le port de conteneur.

En dehors de ces outils externes, expose n'a aucun impact sur la mise en réseau entre les conteneurs. Vous n'avez besoin que d'un réseau Docker commun et d'une connexion au port de conteneur pour accéder à un conteneur à partir d'un autre. Si ce réseau est créé par l'utilisateur (par exemple, pas le réseau de pont par défaut nommé bridge), vous pouvez utiliser DNS pour vous connecter aux autres conteneurs.

BMitch
la source
3

Je suis totalement d'accord avec les réponses précédentes. Je voudrais juste mentionner que la différence entre exposer et ports fait partie du concept de sécurité dans docker. Cela va de pair avec la mise en réseau des dockers. Par exemple:

Imaginez une application avec un front-end web et un back-end de base de données. Le monde extérieur a besoin d'accéder au serveur Web frontal (peut-être sur le port 80), mais seul le serveur principal lui-même a besoin d'accéder à l'hôte et au port de la base de données. À l'aide d'un pont défini par l'utilisateur, seul le port Web doit être ouvert et l'application de base de données n'a pas besoin de ports ouverts, car le frontal Web peut l'atteindre via le pont défini par l'utilisateur.

Il s'agit d'un cas d'utilisation courant lors de la configuration d'une architecture réseau dans Docker. Ainsi, par exemple, dans un réseau de ponts par défaut, aucun port n'est accessible depuis le monde extérieur. Vous pouvez donc ouvrir un point d'entrée avec des "ports". En utilisant «exposer», vous définissez la communication au sein du réseau. Si vous souhaitez exposer les ports par défaut, vous n'avez pas besoin de définir «exposer» dans votre fichier docker-compose.

medTech
la source