Si t'es Lexpage, je t'engage...    —  Tidus

Discussions

Ansibiliser Lexpage

Guybrush 4823 Bob
Reprise automatique du message précédent.
Fabela philosophie de Docker c'est d'avoir une seule image pour dev et prod, ce qui change devrait être exposé dans les variables d'environnements ou dans un éventuel gestionnaire de secret externe.
Je commence seulement à voir les subtilités du CMD dans Docker et des possibilités de pouvoir passer des arguments à ce qui va être exécuté dans le conteneur. Mais la "difficulté", c'est qu'il y a une couche intermédiaire (gunicorn) qui doit aussi connaître ces paramètres pour distinguer prod/dev. Mon idée pour l'instant est de faire en sorte que le conteneur fonctionne sur base d'un seul fichier settings, qui sera différent en fonction de l'environnement dans lequel le conteneur va tourner. Le "hic", c'est qu'il y a déjà trois settings différents pour Lexpage (dev, prod et travis), et que je vais devoir "dupliquer" certains settings pour permettre de faire tourner le site en dehors d'un conteneur également (par ex, hors conteneur, c'est sqlite et memcache qui sont utilisés, alors que dans le conteneur ou en prod, c'est pgsql/redis). J'aimerai éviter de dupliquer les settings (y a déjà un "settings_common" qui est inclus dans les deux fichiers de settings existants, mais j'aimerai pouvoir "composer" tout cela un peu plus proprement).
SyssonEt ce serait super sympa d'en informer tous les autres gens qui ne font que du docker et pour lesquels tu peux te brosser si tu veux installer à l'ancienne! Et oui installer à l'ancienne pour connaitre le bousin ça a une valeur à minima éducative, faire l'expérience de la stack et tout via un moyen simple : le déploiement!
Tout à fait, sans compter que certaines opérations ne sont pas simples à réaliser si l'application tourne dans un conteneur lors du dev (par exemple, je ne sais pas dans quelle mesure nos tests de Django avec Selenium peuvent être lancés dans le conteneur, tout en ayant Selenium qui communique avec le browser en dehors du conteneur. A moins de faire comme avec Travis et de faire tourner ces tests en mode "headless" (mais ça veut dire un dockerfile spécifique pour le dev, du coup, même si c'est pas "fondamentalement" un souci).
Fabe 399 Maitre jedi
GuybrushMon idée pour l'instant est de faire en sorte que le conteneur fonctionne sur base d'un seul fichier settings, qui sera différent en fonction de l'environnement dans lequel le conteneur va tourner.
Si ce fichier de settings est vraiment très différent d'un environnement docker à l'autre, une possibilité est de le mettre dans un répertoire donné et d'ouvrir un "volume" dessus, mais ce n'est pas très élégant ni très exploitable en mode cloud (Kube).
L'idéal est vraiment de factoriser au max ce qui peut l'être entre tous les environnements et d'exposer le reste en variable d'env. C'est même une bonne pratique hors docker, en mettant ce type de conf dans un fichier .env facilement sourçable.
Guybrushje ne sais pas dans quelle mesure nos tests de Django avec Selenium peuvent être lancés dans le conteneur,
Quel est l'intérêt ? Selenium peut tourner sur ton poste et parler au conteneur sur le port qu'il expose pour HTTP.
Sinon, c'est aussi cool d'avoir un conteneur juste pour Selenium avec un chromium headless et de les orchestrer dans un docker-compose. Ça évite de se farcir l'install de la suite localement.
Guybrush 4823 Bob
FabeL'idéal est vraiment de factoriser au max ce qui peut l'être entre tous les environnements et d'exposer le reste en variable d'env. C'est même une bonne pratique hors docker, en mettant ce type de conf dans un fichier .env facilement sourçable.
Question bête mais comment exposes-tu les variables d'environnement sans avoir à modifier le dockerfile ?
Je peux les fournir lors de la mise en route du conteneur par systemd, je suppose ? Mais ça ne me plait pas "trop" d'avoir une partie de la configuration du Lexpage (pour la prod, celle que je ne peux pas rendre publique, comme les clés de chiffrement) dans ce genre d'endroits :-/
FabeQuel est l'intérêt ? Selenium peut tourner sur ton poste et parler au conteneur sur le port qu'il expose pour HTTP.
Selenium est directement utilisé par les tests, il faut donc que le driver soit accessible depuis le conteneur, non ?
Je suppose que je ne suis pas le seul à rencontrer ce "problème" (qui n'en est peut-être pas un d'ailleurs) donc la solution doit exister, mais voilà, c'est encore "un truc en plus" à devoir gérer :-D
FabeSinon, c'est aussi cool d'avoir un conteneur juste pour Selenium avec un chromium headless et de les orchestrer dans un docker-compose. Ça évite de se farcir l'install de la suite localement.
J'étais plus parti dans l'optique d'avoir un autre dockerfile faisant une extension du premier, y ajoutant Selenium et le browser headless, et qui run la suite de test comme un grand, mais je n'ai pas encore le réflexe de "tout séparer" ;-)
Fabe 399 Maitre jedi
GuybrushQuestion bête mais comment exposes-tu les variables d'environnement sans avoir à modifier le dockerfile ? Je peux les fournir lors de la mise en route du conteneur par systemd, je suppose ?
Effectivement, au start du conteneur, avec la cli ça ressemble à docker run moncontainer -e MAVAR:lol (de mémoire :-D)
C'est mappé dans les fichiers de config des orchestrateurs (Kube / docker-compose)
Guybrush Mais ça ne me plait pas "trop" d'avoir une partie de la configuration du Lexpage (pour la prod, celle que je ne peux pas rendre publique, comme les clés de chiffrement) dans ce genre d'endroits
C'est vraiment pas mieux de l'avoir dans le filesystem de l'image :-/
Mais effectivement pour les secrets les variables d'env sont pas non plus la panacée. Un gestionnaire de secret serait recommandé mais ça fait du code en plus.
Il y a peut-être quelque chose à creuser avec la commande docker secret create mais je ne m'en suis jamais servi.
GuybrushSelenium est directement utilisé par les tests, il faut donc que le driver soit accessible depuis le conteneur, non ?
Si les tests sont exécutés dans le conteneur, oui, mais c'est rarement le cas. Par exemple en PHP on met généralement phpunit dans les require-dev qui ne sont pas embed dans le container destiné à la prod.

Un container dédié à l'exécution des tests semble adapté, ou alors ils tournent directement sur l'host / sur travis.


Ce message a été modifié 1 fois. Dernière modification : 22 janvier 2019 à 17:51 par Fabe.

Guybrush 4823 Bob
FabeEffectivement, au start du conteneur, avec la cli ça ressemble à docker run moncontainer -e MAVAR:lol (de mémoire :-D)
C'est mappé dans les fichiers de config des orchestrateurs (Kube / docker-compose)
Ok, donc ça revient plus ou moins au même que de passer ça sous forme de paramètres via CMD, sauf que c'est un peu plus souple pour le coup.
FabeC'est vraiment pas mieux de l'avoir dans le filesystem de l'image :-/
Mais effectivement pour les secrets les variables d'env sont pas non plus la panacée. Un gestionnaire de secret serait recommandé mais ça fait du code en plus.
Qu'entends-tu exactement par "gestionnaire de secrets" ?
FabeIl y a peut-être quelque chose à creuser avec la commande docker secret create mais je ne m'en suis jamais servi.
Je vais voir, je ne connaissais pas cette commande (mais je n'ai pas encore fini la doc ^^)
FabeSi les tests sont exécutés dans le conteneur, oui, mais c'est rarement le cas. Par exemple en PHP on met généralement phpunit dans les require-dev qui ne sont pas embed dans le container destiné à la prod.
Je ne suis pas sûr de bien comprendre :-) Tu lances bien les tests dans le conteneur, non ? Si les libs de tests & co ne sont pas dans le conteneur, comment exécutes-tu les tests ? Et si c'est dans le conteneur, comme peuvent-ils interagir avec ce qui se trouve en dehors du conteneur (par ex Selenium ?).

Je vais creuser un peu, je suis sûr qu'il doit y avoir plein d'exemples de comment organiser tout ça en présence de Selenium (il faut aussi que je regarde s'il est toujours possible de lancer mon déboggueur dans une telle configuration, mais j'imagine que oui ;-)
FabeUn container dédié à l'exécution des tests semble adapté, ou alors ils tournent directement sur l'host / sur travis.
A priori, je ne compte pas faire tourner les tests sur l'host, mais bien en local (vu qu'avec les conteneurs, ce sera pratiquement un staging) et sur travis (pour le coté "automatique" bien pratique).

Tiens, question un peu con : par défaut, Docker attend un "Dockerfile". Est-ce qu'on peut placer plusieurs dockerfiles dans un même répertoire et les référencer par nom ? Dans ce cas, comment ça s'organise ? (je ne suis vraiment pas loin dans la doc, n'hésite pas à lâcher un laconique "RTFM", je ne le prendrai pas mal ;-))
Fabe 399 Maitre jedi
GuybrushOk, donc ça revient plus ou moins au même que de passer ça sous forme de paramètres via CMD, sauf que c'est un peu plus souple pour le coup.
Oui, l'objectif est pas le même, on a généralement pas envie de trop customiser le CMD quand on utilise une image, ça demande de connaître la tuyauterie interne.
GuybrushQu'entends-tu exactement par "gestionnaire de secrets" ?
Quelque chose comme Vault de Hashicorp, qui agit comme un coffre fort de configuration qui tourne dans ton infra.
Les providers cloud en fournissent un aussi, en général.
Je pense que c'est overkill dans ton cas.
GuybrushJe vais voir, je ne connaissais pas cette commande (mais je n'ai pas encore fini la doc ^^)
Je suis preneur du feedback. Dans mon esprit, docker devrait pouvoir déchiffrer le secret au start du container et l'exposer dans une variable d'env. Le doute que j'ai c'est qu'ils ne pourraient l'avoir créé que pour docker swarm.
GuybrushTu lances bien les tests dans le conteneur, non ? Si les libs de tests & co ne sont pas dans le conteneur, comment exécutes-tu les tests ?
Nop, en dev je les lance depuis mon IDE ou depuis ma command line hors conteneur. Directement sur la CI sinon. Si l'environnement de test est complexe à installer, il est possible que je lui fasse sa propre image docker.
GuybrushTiens, question un peu con : par défaut, Docker attend un "Dockerfile". Est-ce qu'on peut placer plusieurs dockerfiles dans un même répertoire et les référencer par nom
Oui, docker build prend un path en paramètre.
GuybrushDans ce cas, comment ça s'organise ? (je ne suis vraiment pas loin dans la doc, n'hésite pas à lâcher un laconique "RTFM", je ne le prendrai pas mal
C'est pas mon genre :-D

Je pense que quand tu seras plus à l'aise avec la CLI ça vaudra le coup que tu te penches sur docker-compose. Je n'utilises plus que ça pour monter mes environnements de dev.
Guybrush(il faut aussi que je regarde s'il est toujours possible de lancer mon déboggueur dans une telle configuration, mais j'imagine que oui
Je ne sais pas comment fonctionne le debugger en python, en php, ça consiste à dire à xdebug d'écouter sur un certain port et à docker d'exposer ce port. En utilisant le port par défaut les IDE retrouvent leurs petits en général.

Je note que je me contredis, en fait j'utilise en général un Dockerfile spécifique pour le dev, dans lequel les sources sont montées dans un VOLUME, afin que je les édites en live.
J'ai ensuite un autre Dockerfile pour les autres environnements :sans le volume, sans xdebug et autres dépendances de dev. Les sources sont montées par COPY. Il y a toujours des subtilités mais en gros les projets que je bosse sous docker ressemblent à ça :
.
├── docker
│ ├── dev
│ │ └── Dockerfile
│ └── prod
│ └── Dockerfile
└── docker-compose.yml


Ce message a été modifié 1 fois. Dernière modification : 23 janvier 2019 à 11:42 par Fabe.

Fabe 399 Maitre jedi
Si ça peut te donner l'inspiration, je m'étais fait template de projet PHP il y a quelques années, je suppose que c'est adaptable à un projet python : github.com/FabienM/php-d…


Ce message a été modifié 1 fois. Dernière modification : 23 janvier 2019 à 12:15 par Fabe.

Guybrush 4823 Bob
FabeOui, l'objectif est pas le même, on a généralement pas envie de trop customiser le CMD quand on utilise une image, ça demande de connaître la tuyauterie interne.
Déjà que CMD n'est pas le machin le plus intuitif quand on voit toutes les subtilités :-D
Bon, je vais partir sur l'idée que le nom du fichier de settings à utiliser sera passé en paramètre, soit via CMD, soit via une variable d'environnement, et je vais réorganiser mes settings de sorte à rendre tout ça gentiment compatible pour exécuter Lexpage en dev ou en prod, que ça soit dans le conteneur ou en dehors. A la rigueur, vu que les settings sont du pur Python, je peux aussi utiliser des variables d'environnement pour indiquer s'il doit utiliser pgsql ou sqlite, redis ou memcache, etc. mais j'aimerai que ça reste "simple" pour quelqu'un qui l'utilise sans connaître des subtilités (autrement dit, par défaut, que ça utilise sqlite et memcache).
FabeJe suis preneur du feedback. Dans mon esprit, docker devrait pouvoir déchiffrer le secret au start du container et l'exposer dans une variable d'env. Le doute que j'ai c'est qu'ils ne pourraient l'avoir créé que pour docker swarm.
J'ai bookmarké la page de la doc pour ne pas oublier d'aller lire ça (je ne sais pas si j'aurai le temps aujourd'hui, j'ai pris un peu de retard ce matin sur mon boulot ^^).
FabeJe pense que quand tu seras plus à l'aise avec la CLI ça vaudra le coup que tu te penches sur docker-compose. Je n'utilises plus que ça pour monter mes environnements de dev.
Oui, je comptais de toute façon utiliser docker-compose, ne fut-ce que pour faciliter l'orchestration avec pgsql et redis, surtout que pour ces deux derniers, je n'ai même pas besoin de créer un dockerfile spécifique (pour pgsql, je dois juste monter un volume pour les données). A priori, il y aurait 3 conteneurs :
- pgsql, avec un volume pour les data;
- redis (par défaut)
- gunicorn/lexpage, avec un volume pour lexpage (ce n'est pas idéal, mais y a des données "uploadées" que je ne peux garder uniquement dans le conteneur, ou alors je crée juste un volume/répertoire partagé pour ces données, et le reste est copié lors de la création du conteneur, mais ça veut dire qu'à chaque update du site, je dois re-créer le conteneur... enfin, ça semble logique quand je l'écris... du coup... je sais pas trop :-D).
FabeJe ne sais pas comment fonctionne le debugger en python, en php, ça consiste à dire à xdebug d'écouter sur un certain port et à docker d'exposer ce port. En utilisant le port par défaut les IDE retrouvent leurs petits en général.
Ca doit être sensiblement la même chose, je crois.
Cela dit, en première étape, je pourrai me contenter d'isoler pgsql, redis et gunicorn, et garder Lexpage en dehors du conteneur (après tout, ce sont "juste" des fichiers à devoir exposer pour gunicorn).
Guybrush 4823 Bob
Merci pour la template, je ne savais pas que l'on pouvait passer des fichiers "env" via docker-compose, c'est assez intéressant ! (je ne suis pas encore arrivé à cette étape dans la doc. Pour docker-compose, j'ai juste lu deux tutos assez généralistes pour l'instant).

Pour docker secret, ça a l'air d'être étroitement lié à docker swarm en effet.
Fabe 399 Maitre jedi
Guybrushenfin, ça semble logique quand je l'écris
Ouep 🙂 Release de l'applicatif = nouvelle version de l'image, c'est l'idée 🙂

Pour le uploaded content, le volume est la solution simple et fonctionnelle, même principe que pour postgres. Les autres solutions plus "cloud-compliant" sont vachement plus complexes et dans ton cas auront pas vraiment de valeur supplémentaire.
Guybrush 4823 Bob
Ok. Je retiens (et note, surtout :-D) ça ;-)

Si à chaque release de l'applicatif (y compris un petit changement dans les settings), il faut une nouvelle version de l'image, alors la question suivante est : est-il possible, pendant qu'un conteneur tourne, de builder une nouvelle version du conteneur, et de switcher de façon "pratiquement transparente" entre la version "runnée" et la version "à runner" pour limiter le downtime, ou également pour éviter d'avoir à stopper/redémarrer les autres conteneurs en lien avec celui qui doit être "remplacé" ?


[Edit : je vois que docker-compose a une commande up -d pour redémarrer un conteneur suite à un (potentiel) changement d'image. Mais je ne vois pas si cela implique successivement un stop / build / run, ou bien si c'est un build / stop / run, auquel cas le downtime est plutôt faible, ou encore un build / run as temp / stop / rename "temp", auquel cas le downtime est pratiquement nul. Je vais voir si la doc est plus verbeuse que Stack Overflow à ce sujet :-D]

[Edit 2 : Ok, le -d est juste pour le mode "detach" qui est, je pense, le paramètre que je devrai utiliser si je veux supporter ça via systemd (je lirai là dessus plus tard). Ce qui fait que je n'ai pas encore réponse à ma question :-D De ce que je vois, il semble qu'il soit nécessaire de se tourner vers d'autres solutions (WatchTower est notamment cité) qui sont typiquement utilisés dans des approches cloud. Peut-être que je ne devrai pas m'inquiéter d'un downtime de quelques secondes]


Ce message a été modifié 2 fois. Dernière modification : 23 janvier 2019 à 16:47 par Guybrush.

Répondre

Vous devez être inscrit et identifié.