{"id":21473195,"url":"https://github.com/johan-perso/roc-framework","last_synced_at":"2025-07-15T08:32:08.756Z","repository":{"id":174061494,"uuid":"650762039","full_name":"johan-perso/roc-framework","owner":"johan-perso","description":"Le générateur de sites parfait pour le développement de sites statique, sans backend, et sans nouvelles méthodes complexes à apprendre","archived":false,"fork":false,"pushed_at":"2025-06-04T21:01:46.000Z","size":290,"stargazers_count":3,"open_issues_count":0,"forks_count":0,"subscribers_count":1,"default_branch":"main","last_synced_at":"2025-06-29T05:48:22.023Z","etag":null,"topics":["daisyui","expressjs","framework","tailwindcss"],"latest_commit_sha":null,"homepage":"","language":"JavaScript","has_issues":true,"has_wiki":null,"has_pages":null,"mirror_url":null,"source_name":null,"license":"mit","status":null,"scm":"git","pull_requests_enabled":true,"icon_url":"https://github.com/johan-perso.png","metadata":{"files":{"readme":"README.md","changelog":null,"contributing":null,"funding":null,"license":"LICENSE","code_of_conduct":null,"threat_model":null,"audit":null,"citation":null,"codeowners":null,"security":null,"support":null,"governance":null,"roadmap":null,"authors":null,"dei":null,"publiccode":null,"codemeta":null,"zenodo":null}},"created_at":"2023-06-07T18:50:11.000Z","updated_at":"2025-06-04T21:01:48.000Z","dependencies_parsed_at":null,"dependency_job_id":"95bd66c2-a828-4f7a-8be7-347d60b476d5","html_url":"https://github.com/johan-perso/roc-framework","commit_stats":null,"previous_names":["johan-perso/roc-framework"],"tags_count":14,"template":true,"template_full_name":null,"purl":"pkg:github/johan-perso/roc-framework","repository_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/johan-perso%2Froc-framework","tags_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/johan-perso%2Froc-framework/tags","releases_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/johan-perso%2Froc-framework/releases","manifests_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/johan-perso%2Froc-framework/manifests","owner_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners/johan-perso","download_url":"https://codeload.github.com/johan-perso/roc-framework/tar.gz/refs/heads/main","sbom_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/johan-perso%2Froc-framework/sbom","host":{"name":"GitHub","url":"https://github.com","kind":"github","repositories_count":265419694,"owners_count":23761858,"icon_url":"https://github.com/github.png","version":null,"created_at":"2022-05-30T11:31:42.601Z","updated_at":"2022-07-04T15:15:14.044Z","host_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub","repositories_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories","repository_names_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repository_names","owners_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners"}},"keywords":["daisyui","expressjs","framework","tailwindcss"],"created_at":"2024-11-23T10:15:22.223Z","updated_at":"2025-07-15T08:32:08.744Z","avatar_url":"https://github.com/johan-perso.png","language":"JavaScript","funding_links":[],"categories":[],"sub_categories":[],"readme":"# ROC\n\nROC est un générateur de site imaginé pour être le plus facile à utiliser pour ceux qui ont l'habitude de développer des sites web avec du HTML et du JavaScript.\n\nROC embarque nativement des outils pour faciliter le développement comme une optimisation des fichiers lors du build, un serveur de développement avec rafraîchissement automatique, un système de routage minimale et plus encore.\n\n\n## (CLI) Création d'un projet\n\nIl n'existe pas encore d'outil capable de créer un projet automatiquement, mais il est possible de créer un projet manuellement :\n\n```bash\n# Optionnel : créer un nouveau dossier\nmkdir mon-projet\ncd mon-projet\n\n# Vous devrez télécharger l'exemple présent dans le dossier \"examples/static\"\n# GUI (Web) : https://download-directory.github.io/?url=https%3A%2F%2Fgithub.com%2Fjohan-perso%2Froc-framework%2Ftree%2Fmain%2Fexamples%2Fstatic\ngit clone github.com/johan-perso/roc-framework --branch main --single-branch roc-framework-starter\nmv roc-framework-starter/examples/static/* .\nrm -rf roc-framework-starter\n\n# Installer les dépendances\nnpm install\nnpm install roc-framework@latest\n# ou pnpm install \u0026\u0026 pnpm install roc-framework@latest\n\n# Lancer le serveur de développement\nnpm run dev\n# ou pnpm dev\n```\n\n\u003e Vous pourrez commencez à coder en modifiant le fichier `public/index.html` !\n\n\n## (CLI) Liste des commandes\n\n### Développement\n\nPour lancer le serveur de développement, il suffit d'exécuter la commande suivante :\n\n```bash\nnpm run dev\n# ou pnpm dev\n```\n\n\u003e Un serveur de développement sera lancé sur le port 3000 par défaut, vous pouvez changer ce port dans le fichier `roc.config.js`.\n\n### Build\n\nLa construction d'un projet permet d'optimiser les fichiers pour une utilisation en production. Ceux-ci seront ensuite utilisables pour un déploiement sur des services comme GitHub Pages ou Vercel. Pour construire un projet, il suffit d'exécuter la commande suivante :\n\n```bash\nnpm run build\n# ou pnpm build\n```\n\n\u003e Les fichiers seront placés dans le dossier `build` par défaut, vous pouvez changer l'emplacement dans le fichier `roc.config.js`.\n\n### Démarrer un serveur\n\nDans le cas où vous ne souhaitez pas configurer un serveur tel que Nginx ou Apache pour servir les fichiers après build, ROC inclut un serveur minimaliste qui peut être utilisé pour servir les fichiers. Pour démarrer ce serveur, il suffit d'exécuter la commande suivante :\n\n```bash\nnpm start\n# ou pnpm start\n```\n\n\u003e Chaque démarrage lancera un build avant de démarrer le serveur, vous pouvez ignorer cette étape en ajoutant l'option `--no-build` à la commande.\n\n\u003e Il est en général préférable de servir les fichiers statiquement pour obtenir de meilleures performances.\n\n\n## (CLI) Configuration\n\nLa configuration de ROC se fait en modifiant le fichier `roc.config.js`. Ce fichier contient un objet avec les propriétés suivantes :\n\n* `useTailwindCSS` | `boolean` : détermine si Tailwind CSS doit être utilisé ou non\n* `exposeComponents` | `boolean` : autorise l'accès aux fichiers dans le dossier `public/components`\n* `serversideCodeExecution` | `boolean` : autorise l'exécution de code côté serveur dans les pages via la syntaxe `{{ ... }}`\n* `buildDir` | `string` : chemin vers le dossier de build\n* `minifyHtml` | `boolean` : détermine si le code HTML doit être minifié ou non (Tailwind CSS est toujours minifié)\n* `devPort` | `number` : port du serveur (utilisé lors du démarrage avec `dev` ou `start`, la variable d'environnement `PORT` restera prioritaire)\n* `devOpenBrowser` | `boolean` : détermine si le navigateur doit s'ouvrir automatiquement lors du lancement du serveur de développement ; la variable d'environnement `ROC_DEFAULT_BROWSER` permet de changer le navigateur par défaut\n\n\n---\n\n\n## (Dynamique) Création d'un projet\n\nIl n'existe pas encore d'outil capable de créer un projet automatiquement, mais il est possible de créer un projet manuellement :\n\n```bash\n# Optionnel : créer un nouveau dossier\nmkdir mon-projet\ncd mon-projet\n\n# Vous devrez télécharger l'exemple présent dans le dossier \"examples/static\"\n# GUI (Web) : https://download-directory.github.io/?url=https%3A%2F%2Fgithub.com%2Fjohan-perso%2Froc-framework%2Ftree%2Fmain%2Fexamples%2Fdynamic\ngit clone github.com/johan-perso/roc-framework --branch main --single-branch roc-framework-starter\nmv roc-framework-starter/examples/dynamic/* .\nrm -rf roc-framework-starter\n\n# Installer les dépendances\nnpm install\nnpm install roc-framework@latest\n# ou pnpm install \u0026\u0026 pnpm install roc-framework@latest\n\n# Lancer le serveur de développement\nnpm run dev\n# ou pnpm dev\n```\n\n\u003e Vous pourrez commencez à coder en modifiant le fichier `index.js` et `public/index.html` !\n\n\n## (Dynamique) Fonctionnement\n\n```js\nvar roc = require('roc')\n\nvar server = new roc.server({\n\tport: 3000, // process.env.PORT restera prioritaire dans tous les cas\n\tlogger: true, // important, vous ne verrez pas les erreurs si désactivé\n\tpath: './public', // chemin contenant vos pages web\n\n\tinterceptRequests: true, // vous ne pourrez pas répondre manuellement aux requêtes si désactivé. Si activé, vous *devrez* répondre manuellement aux requêtes\n\n\texposeComponents: false, // autorise l'accès aux fichiers dans le dossier qui contient les composants customs\n\tserversideCodeExecution: true, // autorise l'exécution de code côté serveur dans les pages via la syntaxe `{{ ... }}`\n\tliveReloadEnabled: true, // sera désactivé si process.env.NODE_ENV = 'production'\n\tuseTailwindCSS: true,\n\tminifyHtml: true, // les pages HTML et les fichiers JavaScript seront minifiés, Tailwind CSS sera minifié et inclut dans la page, les autres fichiers ne seront pas impactés\n})\n\nserver.on('ready', () =\u003e { console.log('received msg ready!') }) // facultatif, permet de savoir quand le serveur est démarré\nserver.on('request', (req, res) =\u003e { // requis si l'option interceptRequests est à true\n\t// Ici, vous pourrez répondre aux requêtes que vous recevez en fonction de vos critières\n\t// Vous pouvez lire la requête `req` et y répondre avec les fonctions présentes dans `res`\n\n\t// res.initialAction = { type: 'sendHtml' | 'sendJs' | 'sendFile' | 'redirect' | '404', content: string }\n\t// res.send(bool statusCode, string content, object options)\n\t// res.sendFile(bool statusCode, string filePath, object options)\n\t// res.json(bool statusCode, object content, object options)\n\t// res.redirect(bool statusCode, string url, object options)\n\t// res.send404()\n\n\t// à l'heure actuelle, `options` ne permet que de définir des `headers` retournés avec la réponse\n\n\tif(res.initialAction.type == 'sendHtml') res.send(200, res.initialAction.content.replaceAll('ROC', 'ROC Dynamic')) // TODO (user): à remplacer, c'est un simple exemple\n\tif(res.initialAction.type == 'sendJs') res.send(200, res.initialAction.content, { headers: { 'Content-Type': 'application/javascript' } })\n\tif(res.initialAction.type == 'sendFile') res.sendFile(200, res.initialAction.content)\n\tif(res.initialAction.type == 'redirect') res.redirect(302, res.initialAction.content)\n\tif(res.initialAction.type == '404') res.send404()\n})\n\nserver.start()\n\n/*\n\tVous pouvez aussi générer le contenu HTML d'une page web en utilisant la méthode :\n\t`server.generateHtml(routePath: string)`\n\n\tUn fichier JavaScript peut être envoyé tel quel, ou minifié (si non désactivé) avec la méthode :\n\t`await server.generateJs(routePath: string)`\n*/\n```\n\n\u003e Roc Dynamic a été créé par dessus le CLI, il est donc compliqué de démarrer plusieurs serveurs dans le même processus.\n\n\n---\n\n\n## Utilisation de Tailwind CSS\n\n[Tailwind CSS](https://tailwindcss.com/) permet de styliser une page web plus simplement, et sans écrire de CSS soi-même. Pour l'utiliser avec ROC, il suffit de modifier la propriété `useTailwindCSS` dans le fichier `roc.config.js`.\n\nLe contenu de toutes les pages web HTML inclura automatiquement Tailwind CSS. Il est cependant possible de désactiver Tailwind CSS pour une page en particulier via le fichier de routage.\n\nPour ajouter du CSS personnalisé, il suffit de créer un fichier `style.css` dans le dossier `public`, ce fichier sera directement inclus dans le CSS généré avec Tailwind CSS.\n\n\u003e Pour plus d'informations sur le fonctionnement de Tailwind CSS, vous pouvez consulter leur [documentation](https://tailwindcss.com/docs).\n\n\n## Utilisation du routage\n\nROC embarque un système de routage simple à utiliser.\n\nTous les fichiers .html dans le dossier `public` seront automatiquement considérés comme des pages web et bénéficieront de fonctionnalité comme la minification, l'utilisation de Tailwind CSS et le rafraîchissement automatique pendant le développement. Les autres fichiers seront également accessibles sans ces fonctionnalités.\n\nVous pouvez aussi ajouter une route personnalisée depuis le fichier de routage `public/_routing.json`. Ce fichier doit contenir un objet par route, avec ce format : `\"/chemin/vers/la/page\": { \"options\": { ... } }`.\n\n* `options` | `object` : options pour cette route, voir ci-dessous.\n\nLes options disponibles sont les suivantes :\n\n* `redirect` | `string` : redirige vers une autre route, incompatible avec `showFile`.\n* `showFile` | `string` : affiche un fichier, incompatible avec `redirect`.\n\n* `disableTailwind` | `boolean` : désactive Tailwind CSS pour cette route.\n* `disableLiveReload` | `boolean` : désactive le Live Reload pour cette route.\n* `preventMinify` | `boolean` : désactive la minification pour cette route, s'il s'agit d'une page HTML.\n* `forceMinify` | `boolean` : force la minification pour cette route, s'il s'agit d'une page HTML.\n\n\u003e Les routes sont prioritaires sur les fichiers, si une route est définie pour une page, le fichier ne sera pas utilisé.\n\u003e Une route doit inclure l'option `showFile` ou `redirect` pour fonctionner, sauf sur serveur dynamique. Si elle ne contient aucun des deux mais qu'un fichier existe, celui-ci sera utilisé.\n\u003e Si une propriété avec le nom d'une route existe dans le fichier, mais ne contient pas d'options, celle-ci sera ignorée et ne sera pas servie.\n\nExemple :\n\n```json\n{\n\t\"/ex\": {\n\t\t\"options\": {\n\t\t\t\"redirect\": \"exemple\",\n\t\t\t\"disableTailwind\": true,\n\t\t\t\"preventMinify\": true,\n\t\t}\n\t},\n\t\"/accueil\": {\n\t\t\"options\": {\n\t\t\t\"forceMinify\": true,\n\t\t\t\"showFile\": \"public/index.html\"\n\t\t}\n\t},\n\t\"/test\": {\n\t\t\"method\": \"POST\",\n\t\t\"options\": {\n\t\t\t\"showFile\": \"public/test.txt\"\n\t\t}\n\t}\n}\n```\n\n\n## Exécution de code côté serveur pendant le build\n\nIl est possible depuis une page HTML d'exécuter du code JavaScript côté serveur lors du build. Pour cela, vous n'avez qu'à inclure du code entre deux accolades (`{{ ... }}`) dans votre page HTML.\n\nExemple :\n\n```html\n\u003cp\u003eCompiled at {{ new Date().toLocaleString() }}\u003c/p\u003e\n```\nproduira :\n```html\n\u003cp\u003eCompiled at 07/06/2023, 11:38:45\u003c/p\u003e\n```\n\nLe code est exécuté dans le même processus que roc, il est donc possible d'utiliser des librairies, des fonctions natives, des éléments systèmes, des variables globales, etc. Certaines propriétés ont été rajoutées pour améliorer l'utilisation de cette fonctionnalité : `routeFile`, `isDev`, `escapeHtml(unsafe: string)` et `getHtmlComponent(componentPath: string)`, `options`. Lors de l'exécution de code depuis un composant, les propriétés `componentName` et `componentAttribs` sont également disponibles.\n\nExemple :\n\n```html\n\u003cp\u003e{{ escapeHtml('Hello \u003cWorld\u003e') }}\u003c/p\u003e\n```\nproduira :\n```html\n\u003cp\u003eHello \u0026lt;World\u0026gt;\u003c/p\u003e\n```\n\n\n## Composants\n\nRoc intègre un système de composants minimes pour éviter les répétitions dans vos pages WEBs. Chaque composant doit être gardé dans un fichier séparé, situé dans le dossier `public/components` avec l'extension `.html`. Le nom du fichier utilisé pour votre composant sera celui à utiliser dans votre page.\n\n### Exemple\n\n```bash\n$ tree\n.\n├── _routing.json\n├── components\n│   ├── BlockFeature.html\n│   └── SectionFeature.html\n├── index.html\n```\n\n```bash\n$ bat components/BlockFeature.html\n───────┬────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────\n       │ File: components/BlockFeature.html\n───────┼────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────\n   1   │ \u003cdiv class=\"bg-[#0F0F0F] rounded-md border border-[#27272A] max-sm:space-y-4 w-full h-full py-8 px-8 gap-8 shadow-md\"\u003e\n   2   │     \u003ch3 class=\"font-[Rethink] text-white text-[26px] min-[2000px]:text-3xl font-medium\"\u003e{{ $title }}\u003c/h3\u003e\n   3   │     \u003cp class=\"mt-1 min-[2000px]:mt-3 font-[Geist] text-[#A1A1AA] text-lg min-[2000px]:text-[22px] leading-relaxed\"\u003e\n   4   │         {{ $content }}\n   5   │     \u003c/p\u003e\n   6   │ \u003c/div\u003e\n```\n\n```bash\n$ bat index.html\n───────┬────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────\n       │ File: index.html\n───────┼────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────\n 164   │ \u003cBlockFeature title=\"Exemple\" content=\"Hello world from a component, rendered with zero client-side JavaScript.\"\u003e\u003c/BlockFeature\u003e\n 165   │ \u003c!-- ✅ \u003cBlockFeature\u003e\u003c/BlockFeature\u003e --\u003e\n 165   │ \u003c!-- ❌ \u003cBlockFeature /\u003e --\u003e\n```\n\n### Attributs et exécution de code\n\nComme dans l'exemple, ajoutez simplement un attribut lorsque vous incluez le composant dans votre page WEB, pour l'utiliser avec la syntaxe `{{ $nom_de_l_attribut }}` dans celui-ci. Vous pouvez aussi les utiliser via l'exécution de code `{{ this.componentAttribs.nom_de_l_attribut }}` pour les afficher selon une certaine logique.\n\n\n## Versions des libs intégrées\n\n| Librairie     | Version |\n| ------------- | ------- |\n| Tailwind CSS  | 3.4.17  |\n| daisyUI       | 4.12.23 |\n\n\n## Déploiement\n\n### Vercel\n\nVous pouvez déployer votre projet sur Vercel à l'aide du fichier `vercel.json` fourni dans l'exemple de base : vous n'aurez qu'à lancer un déploiement avec `vercel --prod` ou l'intégration Git, et Vercel s'occupera du reste.\n\n\u003e Déconseillé pour les projets dynamiques.\n\n### Ailleurs\n\n**Statique :** pour servir votre site, vous pouvez utiliser un simple hébergeur web et lui donner les fichiers présents dans le dossier `build` après la phase de build. Sur votre infrastructure, vous pouvez utiliser un serveur web tel que Nginx ou Apache pour servir les fichiers.\n**Dynamique :** vous aurez besoin d'une machine en capacité d'exécuter votre fichier JavaScript (un VPS par exemple), ROC s'occupera du serveur et vous n'aurez pas besoin de Nginx ou d'alternatives similaires.\n\n\n\n## Licence\n\nMIT © [Johan](https://johanstick.fr). [Soutenez ce projet](https://johanstick.fr/#donate) si vous souhaitez m'aider 💙","project_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Fjohan-perso%2Froc-framework","html_url":"https://awesome.ecosyste.ms/projects/github.com%2Fjohan-perso%2Froc-framework","lists_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Fjohan-perso%2Froc-framework/lists"}