From 91cfb9e8e6a06a8d48b5fca73fa987b09dd61bcb Mon Sep 17 00:00:00 2001 From: "hugo.pradier2" Date: Wed, 22 May 2024 15:22:57 +0200 Subject: [PATCH] correctifs par rapport a reponse de la demande d ajout --- .gitignore | 1 + package.json | 1 - src/database.ts | 103 ++++------ src/db/database.db | Bin 24576 -> 24576 bytes src/server.ts | 469 ++++++++++++++++++++++++++++----------------- 5 files changed, 339 insertions(+), 235 deletions(-) diff --git a/.gitignore b/.gitignore index 8195efd..da0b00d 100644 --- a/.gitignore +++ b/.gitignore @@ -8,3 +8,4 @@ package-lock.json *.js *.tsbuildinfo *.d.ts +*.db diff --git a/package.json b/package.json index 23bfe2a..85171a3 100644 --- a/package.json +++ b/package.json @@ -16,7 +16,6 @@ "@fastify/type-provider-typebox": "^4.0.0", "@sinclair/typebox": "^0.32.9", "fastify": "^4.27.0", - "fastify-sqlite-typed": "^0.1.1", "nanoid": "^5.0.4", "sqlite3": "^5.1.7", "zeromq": "6.0.0-beta.19" diff --git a/src/database.ts b/src/database.ts index 3c94f85..caa5b2f 100644 --- a/src/database.ts +++ b/src/database.ts @@ -7,7 +7,7 @@ const dbFilePath = `${dbDirectory}/database.db`; /* Fonction pour exécuter une requête sur la base de données */ /* Fonction pour exécuter une requête de modification de la base de données (INSERT, UPDATE, DELETE) */ -function runDB( +export function runDB( db: sqlite3.Database, query: string, params: any[] @@ -24,7 +24,10 @@ function runDB( } /* Fonction pour récupérer plusieurs lignes de la base de données */ -function allDB(db: sqlite3.Database, query: string): Promise { +export function allDB( + db: sqlite3.Database, + query: string +): Promise { return new Promise((resolve, reject) => { db.all(query, (err, rows) => { if (err) { @@ -37,11 +40,11 @@ function allDB(db: sqlite3.Database, query: string): Promise { } /* Fonction pour récupérer une seule ligne de la base de données */ -function getDB( +export function getDB( db: sqlite3.Database, query: string, params: any[] -): Promise { +): Promise { return new Promise((resolve, reject) => { db.get(query, params, (err, row: any) => { if (err) { @@ -56,14 +59,14 @@ function getDB( /* Fonctions pour la gestion de la base de données */ /* Créer le répertoire db s'il n'existe pas */ -function createDbDirectory() { +export function createDbDirectory() { if (!fs.existsSync(dbDirectory)) { fs.mkdirSync(dbDirectory); } } /* Ouvrir la base de données */ -function openDatabase() { +export function openDatabase() { console.log("Ouverture de la connexion à la base de données."); return new sqlite3.Database( dbFilePath, @@ -75,7 +78,7 @@ function openDatabase() { } /* Fermer la base de données */ -function closeDatabase(db: sqlite3.Database) { +export function closeDatabase(db: sqlite3.Database) { db.close((err) => { if (err) { console.error(err.message); @@ -85,7 +88,7 @@ function closeDatabase(db: sqlite3.Database) { } /* Create all the tables in the database */ -function createTables(db: sqlite3.Database) { +export function createTables(db: sqlite3.Database) { createRegisteredUserTable(db); createLanguageTable(db); createWorkTable(db); @@ -101,14 +104,14 @@ function createTables(db: sqlite3.Database) { // ); /* Créer la table registered_user dans la base de données */ -function createRegisteredUserTable(db: sqlite3.Database): Promise { +export function createRegisteredUserTable(db: sqlite3.Database): Promise { const tableRegisteredUser = `CREATE TABLE IF NOT EXISTS registered_user (id_user INTEGER PRIMARY KEY AUTOINCREMENT, login TEXT NOT NULL, password TEXT NOT NULL, permissions INTEGER NOT NULL, UNIQUE (login))`; return runDB(db, tableRegisteredUser, []); } /* Insérer un utilisateur dans la table registered_user */ -function insertUser( +export function insertUser( db: sqlite3.Database, login: string, password: string, @@ -120,14 +123,18 @@ function insertUser( } /* Modifier le login d'un utilisateur dans la table registered_user */ -function updateUserLogin(db: sqlite3.Database, id: number, newLogin: string) { +export function updateUserLogin( + db: sqlite3.Database, + id: number, + newLogin: string +) { const updateUserLoginQuery = `UPDATE registered_user SET login = ? WHERE id_user = ?`; return runDB(db, updateUserLoginQuery, [newLogin, id]); } /* Modifier le mot de passe d'un utilisateur dans la table registered_user */ -function updateUserPassword( +export function updateUserPassword( db: sqlite3.Database, id: number, newPassword: string @@ -138,7 +145,7 @@ function updateUserPassword( } /* Modifier les permissions d'un utilisateur dans la table registered_user */ -function updateUserPermissions( +export function updateUserPermissions( db: sqlite3.Database, id: number, newPermissions: number @@ -149,42 +156,42 @@ function updateUserPermissions( } /* Supprimer un utilisateur de la table registered_user par son ID */ -function deleteUserById(db: sqlite3.Database, id: number) { +export function deleteUserById(db: sqlite3.Database, id: number) { const deleteUserQuery = `DELETE FROM registered_user WHERE id_user = ?`; return runDB(db, deleteUserQuery, [id]); } /* Supprimer un utilisateur de la table registered_user par son login */ -function deleteUserByLogin(db: sqlite3.Database, login: string) { +export function deleteUserByLogin(db: sqlite3.Database, login: string) { const deleteUserQuery = `DELETE FROM registered_user WHERE login = ?`; return runDB(db, deleteUserQuery, [login]); } /* Supprimer tous les utilisateurs de la table registered_user */ -function deleteAllUsers(db: sqlite3.Database) { +export function deleteAllUsers(db: sqlite3.Database) { const deleteAllUsersQuery = `DELETE FROM registered_user`; return runDB(db, deleteAllUsersQuery, []); } /* Sélectionner tous les utilisateurs de la table registered_user */ -function selectAllUsers(db: sqlite3.Database): Promise { +export function selectAllUsers(db: sqlite3.Database): Promise { const selectAllUsersQuery = `SELECT * FROM registered_user`; return allDB(db, selectAllUsersQuery); } /* Sélectionner un utilisateur par son login */ -function selectUserByLogin(db: sqlite3.Database, login: string) { +export function selectUserByLogin(db: sqlite3.Database, login: string) { const selectUserByLoginQuery = `SELECT * FROM registered_user WHERE login = ?`; return getDB(db, selectUserByLoginQuery, [login]); } /* Sélectionner un utilisateur par son ID */ -function selectUserById(db: sqlite3.Database, id: number) { +export function selectUserById(db: sqlite3.Database, id: number) { const selectUserByIdQuery = `SELECT * FROM registered_user WHERE id_user = ?`; return getDB(db, selectUserByIdQuery, [id]); @@ -198,13 +205,13 @@ function selectUserById(db: sqlite3.Database, id: number) { // ); /* Créer la table language dans la base de données */ -function createLanguageTable(db: sqlite3.Database): Promise { +export function createLanguageTable(db: sqlite3.Database): Promise { const tableLanguage = `CREATE TABLE IF NOT EXISTS language (id_language INTEGER PRIMARY KEY AUTOINCREMENT, designation TEXT NOT NULL, version INTEGER NOT NULL)`; return runDB(db, tableLanguage, []); } /* Insérer un language dans la table language */ -function insertLanguage( +export function insertLanguage( db: sqlite3.Database, designation: string, version: number @@ -215,7 +222,7 @@ function insertLanguage( } /* Modifier la designation d'un language dans la table language */ -function updateLanguageDesignation( +export function updateLanguageDesignation( db: sqlite3.Database, id: number, newDesignation: string @@ -226,7 +233,7 @@ function updateLanguageDesignation( } /* Modifier la version d'un language dans la table language */ -function updateLanguageVersion( +export function updateLanguageVersion( db: sqlite3.Database, id: number, newVersion: number @@ -237,28 +244,28 @@ function updateLanguageVersion( } /* Supprimer un language de la table language par son ID */ -function deleteLanguage(db: sqlite3.Database, id: number) { +export function deleteLanguage(db: sqlite3.Database, id: number) { const deleteLanguageQuery = `DELETE FROM language WHERE id_language = ?`; return runDB(db, deleteLanguageQuery, [id]); } /* Supprimer tous les languages de la table language */ -function deleteAllLanguages(db: sqlite3.Database) { +export function deleteAllLanguages(db: sqlite3.Database) { const deleteAllLanguagesQuery = `DELETE FROM language`; return runDB(db, deleteAllLanguagesQuery, []); } /* Sélectionner tous les languages de la table language */ -function selectAllLanguages(db: sqlite3.Database): Promise { +export function selectAllLanguages(db: sqlite3.Database): Promise { const selectAllLanguagesQuery = `SELECT * FROM language`; return allDB(db, selectAllLanguagesQuery); } /* Sélectionner un language par son ID */ -function selectLanguageById(db: sqlite3.Database, id: number) { +export function selectLanguageById(db: sqlite3.Database, id: number) { const selectLanguageByIdQuery = `SELECT * FROM language WHERE id_language = ?`; return getDB(db, selectLanguageByIdQuery, [id]); @@ -274,13 +281,13 @@ function selectLanguageById(db: sqlite3.Database, id: number) { // ); /* Créer la table work dans la base de données */ -function createWorkTable(db: sqlite3.Database): Promise { +export function createWorkTable(db: sqlite3.Database): Promise { const tableWork = `CREATE TABLE IF NOT EXISTS work (id_work INTEGER PRIMARY KEY AUTOINCREMENT, link CHAR(36) NOT NULL, user_id INTEGER REFERENCES registered_user(id_user), language_id INTEGER NOT NULL REFERENCES language(id_language), content TEXT NOT NULL)`; return runDB(db, tableWork, []); } /* Insérer un work dans la table work */ -function insertWork( +export function insertWork( db: sqlite3.Database, link: string, user_id: number, @@ -293,59 +300,29 @@ function insertWork( } /* Sélectionner tous les works de la table work */ -function selectAllWorks(db: sqlite3.Database): Promise { +export function selectAllWorks(db: sqlite3.Database): Promise { const selectAllWorksQuery = `SELECT * FROM work`; return allDB(db, selectAllWorksQuery); } /* Supprimer tous les works de la table work */ -function deleteAllWorks(db: sqlite3.Database) { +export function deleteAllWorks(db: sqlite3.Database) { const deleteAllWorksQuery = `DELETE FROM work`; return runDB(db, deleteAllWorksQuery, []); } /* Supprimer un work de la table work */ -function deleteWork(db: sqlite3.Database, id: number) { +export function deleteWork(db: sqlite3.Database, id: number) { const deleteWorkQuery = `DELETE FROM work WHERE id_work = ?`; return runDB(db, deleteWorkQuery, [id]); } /* Sélectionner un work par son ID */ -function selectWorkById(db: sqlite3.Database, id: number) { +export function selectWorkById(db: sqlite3.Database, id: number) { const selectWorkByIdQuery = `SELECT * FROM work WHERE id_work = ?`; return getDB(db, selectWorkByIdQuery, [id]); } - -/////////////////////////// Export des fonctions /////////////////////////// -export { - createDbDirectory, - openDatabase, - closeDatabase, - createTables, - insertUser, - updateUserLogin, - updateUserPassword, - updateUserPermissions, - deleteUserById, - deleteUserByLogin, - deleteAllUsers, - selectAllUsers, - selectUserByLogin, - selectUserById, - insertLanguage, - updateLanguageDesignation, - updateLanguageVersion, - deleteLanguage, - deleteAllLanguages, - selectAllLanguages, - selectLanguageById, - insertWork, - selectAllWorks, - deleteAllWorks, - deleteWork, - selectWorkById, -}; diff --git a/src/db/database.db b/src/db/database.db index 78185c29a42a5ab65773058bd25a2566fb9eaa7c..c33d49ac73d18762af7066538a6cd165d31ee32b 100644 GIT binary patch delta 175 zcmZoTz}Rqrae_1>$3z)tMvjdMOZd5%`7bc=f8c+>e_^wrz#)DGK4w-1aZ%2a)Z!9j zLnC7oJ|;Nd2*jWKL0$x?=`jQUcmB8hkAa%5@@sN3i!*|CFvD0zOdQPOU{efv`QI=w z@t+e8^>Mz)O!OZeFs`9Co5f7mSO@Qi=*2YC@7|2qT!cOd^QzbFT@ vIA=*}afu->0|NsS|6>OJH~f!*QrG!;*_oI{Im`2lvV|C#wKspT7f=8IG!YvO diff --git a/src/server.ts b/src/server.ts index 5d39fb0..088851e 100644 --- a/src/server.ts +++ b/src/server.ts @@ -5,34 +5,7 @@ import { nanoid } from "nanoid"; import { allocateBuffer, IMAGES } from "runner"; import { Pull, Push } from "zeromq"; -import { - createDbDirectory, - openDatabase, - closeDatabase, - createTables, - insertUser, - updateUserLogin, - updateUserPassword, - updateUserPermissions, - deleteUserById, - deleteUserByLogin, - deleteAllUsers, - selectAllUsers, - selectUserByLogin, - selectUserById, - insertLanguage, - updateLanguageDesignation, - updateLanguageVersion, - deleteLanguage, - deleteAllLanguages, - selectAllLanguages, - selectLanguageById, - insertWork, - selectAllWorks, - deleteAllWorks, - deleteWork, - selectWorkById, -} from "./database"; +import * as db from "./database"; const sender = new Push(); await sender.bind(`tcp://127.0.0.1:5557`); @@ -88,215 +61,369 @@ fastify.post( /* Database */ /* Création du répertoire de la base de données s'il n'existe pas */ -createDbDirectory(); +db.createDbDirectory(); /* Ouvrir la base de données */ -const db = openDatabase(); +const database = db.openDatabase(); /* Créer les tables si elles n'existent pas */ -createTables(db); +db.createTables(database); /* Route pour créer un utilisateur */ -fastify.post<{ - Body: { - login: string; - password: string; - permissions: number; - }; -}>("/users", async (request, reply) => { - const { login, password, permissions } = request.body; - insertUser(db, login, password, permissions); - reply.send({ success: true }); -}); +fastify.post( + "/users", + { + schema: { + body: Type.Object({ + login: Type.String(), + password: Type.String(), + permissions: Type.Number(), + }), + }, + }, + async (request, reply) => { + const { login, password, permissions } = request.body; + db.insertUser(database, login, password, permissions); + reply.send({ success: true }); + } +); /* Route pour mettre à jour le login d'un utilisateur */ -fastify.put<{ - Params: { id: string }; - Body: { newLogin: string }; -}>("/users/:id/login", async (request, reply) => { - const { id } = request.params; - const { newLogin } = request.body; - updateUserLogin(db, parseInt(id), newLogin); - reply.send({ success: true }); -}); +fastify.put( + "/users/:id/login", + { + schema: { + params: Type.Object({ + id: Type.Number({ + minimum: 0, + }), + }), + body: Type.Object({ + newLogin: Type.String(), + }), + }, + }, + async (request, reply) => { + const { id } = request.params; + const { newLogin } = request.body; + db.updateUserLogin(database, id, newLogin); + reply.send({ success: true }); + } +); /* Route pour mettre à jour le mot de passe d'un utilisateur */ -fastify.put<{ - Params: { id: string }; - Body: { newPassword: string }; -}>("/users/:id/password", async (request, reply) => { - const { id } = request.params; - const { newPassword } = request.body; - await updateUserPassword(db, parseInt(id), newPassword); - reply.send({ success: true }); -}); +fastify.put( + "/users/:id/password", + { + schema: { + params: Type.Object({ + id: Type.Number({ + minimum: 0, + }), + }), + body: Type.Object({ + newPassword: Type.String(), + }), + }, + }, + async (request, reply) => { + const { id } = request.params; + const { newPassword } = request.body; + db.updateUserPassword(database, id, newPassword); + reply.send({ success: true }); + } +); /* Route pour mettre à jour les permissions d'un utilisateur */ -fastify.put<{ - Params: { id: string }; - Body: { newPermissions: number }; -}>("/users/:id/permissions", async (request, reply) => { - const { id } = request.params; - const { newPermissions } = request.body; - await updateUserPermissions(db, parseInt(id), newPermissions); - reply.send({ success: true }); -}); +fastify.put( + "/users/:id/permissions", + { + schema: { + params: Type.Object({ + id: Type.Number({ + minimum: 0, + }), + }), + body: Type.Object({ + newPermissions: Type.Number(), + }), + }, + }, + async (request, reply) => { + const { id } = request.params; + const { newPermissions } = request.body; + await db.updateUserPermissions(database, id, newPermissions); + reply.send({ success: true }); + } +); /* Route pour supprimer un utilisateur par son ID */ -fastify.delete<{ - Params: { id: string }; -}>("/users/:id", async (request, reply) => { - const { id } = request.params; - await deleteUserById(db, parseInt(id)); - reply.send({ success: true }); -}); +fastify.delete( + "/users/:id", + { + schema: { + params: Type.Object({ + id: Type.Number({ + minimum: 0, + }), + }), + }, + }, + async (request, reply) => { + const { id } = request.params; + await db.deleteUserById(database, id); + reply.send({ success: true }); + } +); /* Route pour supprimer un utilisateur par son login */ -fastify.delete<{ - Params: { login: string }; -}>("/users/login/:login", async (request, reply) => { - const { login } = request.params; - await deleteUserByLogin(db, login); - reply.send({ success: true }); -}); +fastify.delete( + "/users/login/:login", + { + schema: { + params: Type.Object({ + login: Type.String(), + }), + }, + }, + async (request, reply) => { + const { login } = request.params; + await db.deleteUserByLogin(database, login); + reply.send({ success: true }); + } +); /* Route pour supprimer tous les utilisateurs */ fastify.delete("/users", async (request, reply) => { - await deleteAllUsers(db); + await db.deleteAllUsers(database); reply.send({ success: true }); }); /* Route pour récupérer tous les utilisateurs */ fastify.get("/users", async (request, reply) => { - const users = await selectAllUsers(db); + const users = await db.selectAllUsers(database); reply.send(users); }); /* Route pour récupérer un utilisateur par son ID */ -fastify.get<{ - Params: { id: string }; -}>("/users/:id", async (request, reply) => { - const { id } = request.params; - const user = await selectUserById(db, parseInt(id)); - reply.send(user); -}); +fastify.get( + "/users/:id", + { + schema: { + params: Type.Object({ + id: Type.Number({ + minimum: 0, + }), + }), + }, + }, + async (request, reply) => { + const { id } = request.params; + const user = await db.selectUserById(database, id); + reply.send(user); + } +); /* Route pour récupérer un utilisateur par son login */ -fastify.get<{ - Params: { login: string }; -}>("/users/login/:login", async (request, reply) => { - const { login } = request.params; - const user = await selectUserByLogin(db, login); - reply.send(user); -}); +fastify.get( + "/users/login/:login", + { + schema: { + params: Type.Object({ + login: Type.String(), + }), + }, + }, + async (request, reply) => { + const { login } = request.params; + const user = await db.selectUserByLogin(database, login); + reply.send(user); + } +); /* Route pour créer un language */ -fastify.post<{ - Body: { - designation: string; - version: string; - }; -}>("/languages", async (request, reply) => { - const { designation, version } = request.body; - insertLanguage(db, designation, parseInt(version)); - reply.send({ success: true }); -}); +fastify.post( + "/languages", + { + schema: { + body: Type.Object({ + designation: Type.String(), + version: Type.Number(), + }), + }, + }, + async (request, reply) => { + const { designation, version } = request.body; + db.insertLanguage(database, designation, version); + reply.send({ success: true }); + } +); /* Route pour mettre à jour la désignation d'un language */ -fastify.put<{ - Params: { id: string }; - Body: { newDesignation: string }; -}>("/languages/:id/designation", async (request, reply) => { - const { id } = request.params; - const { newDesignation } = request.body; - updateLanguageDesignation(db, parseInt(id), newDesignation); - reply.send({ success: true }); -}); +fastify.put( + "/languages/:id/designation", + { + schema: { + params: Type.Object({ + id: Type.Number({ + minimum: 0, + }), + }), + body: Type.Object({ + newDesignation: Type.String(), + }), + }, + }, + async (request, reply) => { + const { id } = request.params; + const { newDesignation } = request.body; + db.updateLanguageDesignation(database, id, newDesignation); + reply.send({ success: true }); + } +); /* Route pour mettre à jour la version d'un language */ -fastify.put<{ - Params: { id: string }; - Body: { newVersion: number }; -}>("/languages/:id/version", async (request, reply) => { - const { id } = request.params; - const { newVersion } = request.body; - updateLanguageVersion(db, parseInt(id), newVersion); - reply.send({ success: true }); -}); +fastify.put( + "/languages/:id/version", + { + schema: { + params: Type.Object({ + id: Type.Number({ + minimum: 0, + }), + }), + body: Type.Object({ + newVersion: Type.Number(), + }), + }, + }, + async (request, reply) => { + const { id } = request.params; + const { newVersion } = request.body; + db.updateLanguageVersion(database, id, newVersion); + reply.send({ success: true }); + } +); /* Route pour supprimer un language */ -fastify.delete<{ - Params: { id: string }; -}>("/languages/:id", async (request, reply) => { - const { id } = request.params; - deleteLanguage(db, parseInt(id)); - reply.send({ success: true }); -}); +fastify.delete( + "/languages/:id", + { + schema: { + params: Type.Object({ + id: Type.Number({ + minimum: 0, + }), + }), + }, + }, + async (request, reply) => { + const { id } = request.params; + db.deleteLanguage(database, id); + reply.send({ success: true }); + } +); /* Route pour supprimer tous les languages */ fastify.delete("/languages", async (request, reply) => { - deleteAllLanguages(db); + db.deleteAllLanguages(database); reply.send({ success: true }); }); /* Route pour récupérer un language par son ID */ -fastify.get<{ - Params: { id: string }; -}>("/languages/:id", async (request, reply) => { - const { id } = request.params; - const language = await selectLanguageById(db, parseInt(id)); - reply.send(language); -}); +fastify.get( + "/languages/:id", + { + schema: { + params: Type.Object({ + id: Type.Number({ + minimum: 0, + }), + }), + }, + }, + async (request, reply) => { + const { id } = request.params; + const language = await db.selectLanguageById(database, id); + reply.send(language); + } +); /* Route pour récupérer tous les languages */ fastify.get("/languages", async (request, reply) => { - const languages = await selectAllLanguages(db); + const languages = await db.selectAllLanguages(database); reply.send(languages); }); /* Route pour créer un work */ -fastify.post<{ - Body: { - id_user: number; - link: string; - id_language: number; - code: string; - }; -}>("/works", async (request, reply) => { - const { id_user, link, id_language, code } = request.body; - insertWork(db, link, id_user, id_language, code); - reply.send({ success: true }); -}); +fastify.post( + "/works", + { + schema: { + body: Type.Object({ + id_user: Type.Number(), + link: Type.String(), + id_language: Type.Number(), + code: Type.String(), + }), + }, + }, + async (request, reply) => { + const { id_user, link, id_language, code } = request.body; + db.insertWork(database, link, id_user, id_language, code); + reply.send({ success: true }); + } +); /* Route pour récupérer tous les works */ fastify.get("/works", async (request, reply) => { - const works = await selectAllWorks(db); + const works = await db.selectAllWorks(database); reply.send(works); }); /* Route pour supprimer tous les works */ fastify.delete("/works", async (request, reply) => { - deleteAllWorks(db); + db.deleteAllWorks(database); reply.send({ success: true }); }); /* Route pour supprimer un work par son ID */ -fastify.delete<{ - Params: { id: string }; -}>("/works/:id", async (request, reply) => { - const { id } = request.params; - deleteWork(db, parseInt(id)); - reply.send({ success: true }); -}); +fastify.delete( + "/works/:id", + { + schema: { + params: Type.Object({ + id: Type.Number({ + minimum: 0, + }), + }), + }, + }, + async (request, reply) => { + const { id } = request.params; + db.deleteWork(database, id); + reply.send({ success: true }); + } +); /* Route pour récupérer un work par son ID */ -fastify.get<{ - Params: { id: string }; -}>("/works/:id", async (request, reply) => { - const { id } = request.params; - const work = await selectWorkById(db, parseInt(id)); - reply.send(work); -}); +fastify.get( + "/works/:id", + { + schema: { + params: Type.Object({ + id: Type.Number({ + minimum: 0, + }), + }), + }, + }, + async (request, reply) => { + const { id } = request.params; + const work = await db.selectWorkById(database, id); + reply.send(work); + } +); /* Forward output est une fonction asynchrone qui permet de récupérer les messages envoyés par le container et de les renvoyer au client */ async function forwardOutput() {