Skip to content
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
10 changes: 8 additions & 2 deletions exercice-1-port-web/COMMANDS.md
Original file line number Diff line number Diff line change
@@ -1,6 +1,12 @@

# Commandes

```bash
# Exemple de structure attendue
docker run -d --name web-port -p 8080:80 nginx
```
docker ps
docker port web-port
docker rm -f web-port
docker run -d --name web-port -p 127.0.0.1:8080:80 nginx
curl -sI http://localhost:8080 | head -n 5
docker rm -f web-port || true
```
5 changes: 5 additions & 0 deletions exercice-1-port-web/README.md
Original file line number Diff line number Diff line change
Expand Up @@ -22,8 +22,13 @@ Les commandes doivent etre fournies dans un fichier separe `COMMANDS.md`.
## Questions de reflexion

- Quelle est la difference entre le port hote et le port conteneur ?
Le port conteneur est service à l'intérieur,le port hôte est un port de la machine mappé vers le conteneur.

- Pourquoi `EXPOSE` ne suffit-il pas a rendre le service accessible ?
EXPOSE est documentaire, il faut `-p`/`--publish` pour créer le mapping hôte vers un conteneur.

- Dans quel cas limiter l'ecoute a `127.0.0.1` est-il utile ?
Quand on veut restreindre l'accès au host uniquement (développement, sécurité sur un hôte partagé).

## Criteres de validation

Expand Down
13 changes: 12 additions & 1 deletion exercice-2-dns-bridge/COMMANDS.md
Original file line number Diff line number Diff line change
@@ -1,6 +1,17 @@
# Commandes

```bash
# Exemple de structure attendue
docker network create test_net
docker run -d --name serveur --network test_net nginx
docker run --rm --network test_net alpine sh -c "ping -c1 serveur && echo 'serveur reachable' || echo 'serveur unreachable'"
docker network inspect test_net
docker run --rm --network bridge alpine sh -c "ping -c1 serveur && echo 'bridge: reachable' || echo 'bridge: unreachable'"
docker run -d --name client --network bridge alpine sleep 300
docker exec client sh -c "ping -c1 serveur && echo 'client before connect: reachable' || echo 'client before connect: unreachable'"
docker network connect test_net client
docker exec client sh -c "ping -c1 serveur && echo 'client after connect: reachable' || echo 'client after connect: unreachable'"
docker network disconnect test_net client || true
docker rm -f client serveur || true
docker network rm test_net || true

```
7 changes: 7 additions & 0 deletions exercice-2-dns-bridge/README.md
Original file line number Diff line number Diff line change
Expand Up @@ -21,8 +21,15 @@ Les commandes doivent etre fournies dans un fichier separe `COMMANDS.md`.
## Questions de reflexion

- Pourquoi l'utilisation d'un reseau personnalise est-elle recommandee pour des applications multi-conteneurs ?

- Pourquoi l'utilisation d'un reseau personnalise est-elle recommandee pour des applications multi-conteneurs ?
Pour l'isolation + découverte de services par nom, pas de mappage de ports entre services.

- Quel avantage apporte le DNS interne Docker ?
Résolution automatique des conteneurs par nom.

- Que permet `docker network inspect` dans une phase de diagnostic ?
De montrer les conteneurs connectés, leurs IP internes et les détails du réseau.

## Criteres de validation

Expand Down
44 changes: 42 additions & 2 deletions exercice-3-web-db-network/COMMANDS.md
Original file line number Diff line number Diff line change
@@ -1,7 +1,47 @@
# Commandes

```bash
# Exemple de structure attendue
# Variables (modifiable si besoin)
ROOT_PASS=rootpass
DB_NAME=demo_db
DB_USER=demo_user
DB_PASS=demo_pass

docker network create app_network
docker volume create db_volume
```
docker run -d --name mysql_db --network app_network \
-e MYSQL_ROOT_PASSWORD=${ROOT_PASS} \
-e MYSQL_DATABASE=${DB_NAME} \
-e MYSQL_USER=${DB_USER} \
-e MYSQL_PASSWORD=${DB_PASS} \
-v db_volume:/var/lib/mysql \
mysql:8
echo "Waiting for mysql to be ready..."
until docker exec mysql_db mysqladmin ping -h localhost -uroot -p${ROOT_PASS} --silent; do sleep 1; done
echo "mysql ready"
docker build -t webapp-image ./webapp
docker run -d --name webapp --network app_network -p 8080:8080 \
-e DB_HOST=mysql_db -e DB_USER=${DB_USER} -e DB_PASSWORD=${DB_PASS} -e DB_NAME=${DB_NAME} \
webapp-image
docker network inspect app_network --format "{{json .Containers}}"
curl -sI http://localhost:8080 | head -n 5
curl -s http://localhost:8080/init
curl -s http://localhost:8080/show
docker rm -f mysql_db
docker run -d --name mysql_db --network app_network \
-e MYSQL_ROOT_PASSWORD=${ROOT_PASS} \
-e MYSQL_DATABASE=${DB_NAME} \
-e MYSQL_USER=${DB_USER} \
-e MYSQL_PASSWORD=${DB_PASS} \
-v db_volume:/var/lib/mysql \
mysql:8
echo "Waiting for mysql (recreated) to be ready..."
until docker exec mysql_db mysqladmin ping -h localhost -uroot -p${ROOT_PASS} --silent; do sleep 1; done
echo "mysql recreated and ready"
curl -s http://localhost:8080/show
docker rm -f webapp mysql_db || true
docker network rm app_network || true
docker volume rm db_volume || true
docker rmi webapp-image || true

```
3 changes: 3 additions & 0 deletions exercice-3-web-db-network/README.md
Original file line number Diff line number Diff line change
Expand Up @@ -29,8 +29,11 @@ Les commandes doivent etre fournies dans un fichier separe `COMMANDS.md`.
## Questions de reflexion

- Pourquoi la base de donnees n'a-t-elle pas besoin d'etre exposee vers l'hote dans cette architecture ?
Parce que la base de données n’a pas besoin d’être accessible directement depuis l’extérieur, seuls les services applicatifs doivent pouvoir s’y connecter comme web app.
- En quoi le reseau personnalise simplifie-t-il la communication entre services ?
Le réseau personnalisé fournit DNS + isolation + simplicité, ce qui simplifie fortement l’architecture multi‑conteneurs.
- Que se passerait-il si le volume n'etait pas reutilise apres recreation du conteneur MySQL ?
Perte de données ou encore réinitialisation automatique par exemple

## Criteres de validation

Expand Down
6 changes: 6 additions & 0 deletions exercice-3-web-db-network/webapp/Dockerfile
Original file line number Diff line number Diff line change
@@ -0,0 +1,6 @@
FROM python:3.11-slim
WORKDIR /app
RUN pip install --no-cache-dir flask mysql-connector-python
COPY app.py /app/app.py
EXPOSE 8080
CMD ["python", "app.py"]
55 changes: 55 additions & 0 deletions exercice-3-web-db-network/webapp/app.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,55 @@
from flask import Flask
import os
import mysql.connector

app = Flask(__name__)

DB_HOST = os.environ.get('DB_HOST', 'mysql_db')
DB_USER = os.environ.get('DB_USER', 'demo_user')
DB_PASSWORD = os.environ.get('DB_PASSWORD', 'demo_pass')
DB_NAME = os.environ.get('DB_NAME', 'demo_db')

def get_conn():
return mysql.connector.connect(
host=DB_HOST,
user=DB_USER,
password=DB_PASSWORD,
database=DB_NAME,
autocommit=True
)

@app.route('/')
def index():
try:
conn = get_conn()
cur = conn.cursor()
cur.execute('SELECT COUNT(*) FROM info')
cnt = cur.fetchone()[0]
cur.close()
conn.close()
return f'webapp OK — rows={cnt}\n'
except Exception as e:
return f'ERROR: {e}\n', 500

@app.route('/init')
def init_table():
conn = get_conn()
cur = conn.cursor()
cur.execute('CREATE TABLE IF NOT EXISTS info (id INT AUTO_INCREMENT PRIMARY KEY, txt VARCHAR(100))')
cur.execute("INSERT INTO info (txt) VALUES ('hello')")
cur.close()
conn.close()
return 'initialized\n'

@app.route('/show')
def show():
conn = get_conn()
cur = conn.cursor()
cur.execute('SELECT id, txt FROM info')
rows = cur.fetchall()
cur.close()
conn.close()
return '\n'.join(f'{r[0]}:{r[1]}' for r in rows) + '\n'

if __name__ == '__main__':
app.run(host='0.0.0.0', port=8080)