Front-End Assets
Introduction​
Bow est préconfiguré avec un environnement Frontend moderne basé sur Vite, incluant :
- React 19
- Vue.js 3
- Tailwind CSS 3
- Sass/SCSS
Cette configuration offre un rechargement instantané (HMR) et une compilation ultra-rapide.
Installation​
npm install
Commandes​
| Commande | Description |
|---|---|
npm run dev | Lance le serveur de développement Vite avec HMR |
npm run build | Compile et optimise pour la production |
Développement​
npm run dev
Lance le serveur Vite avec rechargement à chaud. Les modifications sont reflétées instantanément sans recharger la page.
Production​
npm run build
Compile et minifie les assets dans le dossier public/.
Structure des fichiers​
assets/
├── js/
│ ├── app.js # Point d'entrée principal
│ ├── Example.jsx # Composant React
│ └── Example.vue # Composant Vue
├── sass/
│ ├── app.scss # Styles principaux
│ └── variables.scss # Variables SCSS
└── css/
└── app.css # CSS/Tailwind
Configuration Vite​
import { defineConfig } from 'vite';
import vue from '@vitejs/plugin-vue';
import react from '@vitejs/plugin-react';
import path from 'path';
import tailwindcss from '@tailwindcss/vite';
export default defineConfig({
plugins: [
vue(),
react(),
tailwindcss(),
],
root: path.resolve(__dirname, 'assets'),
build: {
outDir: path.resolve(__dirname, 'public'),
emptyOutDir: true,
rollupOptions: {
input: {
app: path.resolve(__dirname, 'assets/js/app.js'),
},
output: {
entryFileNames: 'js/[name].js',
assetFileNames: (assetInfo) => {
if (/\.(css|scss)$/.test(assetInfo.name)) {
return 'css/[name]-[hash][extname]';
}
if (/\.(png|jpe?g|gif|svg|webp)$/.test(assetInfo.name)) {
return 'img/[name]-[hash][extname]';
}
return '[ext]/[name]-[hash][extname]';
},
},
},
},
});
Tailwind CSS​
Configuration​
import defaultTheme from "tailwindcss/defaultTheme";
export default {
content: [
"./templates/**/*.{blade,tintin}.php",
"./templates/**/*.twig",
"./templates/**/*.{js,jsx,ts,tsx,vue}",
"./assets/js/**/*.{js,jsx,ts,tsx,vue}",
],
theme: {
extend: {
fontFamily: {
sans: ["Figtree", ...defaultTheme.fontFamily.sans],
},
},
},
plugins: [],
};
Utilisation​
@tailwind base;
@tailwind components;
@tailwind utilities;
/* Styles personnalisés */
.btn-primary {
@apply bg-blue-500 text-white px-4 py-2 rounded hover:bg-blue-600;
}
Composants React​
import React, { useState } from 'react';
export default function Example() {
const [count, setCount] = useState(0);
return (
<div className="p-4">
<h1 className="text-2xl font-bold">Compteur: {count}</h1>
<button
className="btn-primary mt-4"
onClick={() => setCount(count + 1)}
>
Incrémenter
</button>
</div>
);
}
Composants Vue​
<script setup>
import { ref } from 'vue';
const count = ref(0);
</script>
<template>
<div class="p-4">
<h1 class="text-2xl font-bold">Compteur: {{ count }}</h1>
<button class="btn-primary mt-4" @click="count++">
Incrémenter
</button>
</div>
</template>
Intégration dans les templates​
Avec Tintin​
<!DOCTYPE html>
<html>
<head>
<link rel="stylesheet" href="/css/app.css">
</head>
<body>
<div id="app"></div>
<script type="module" src="/js/app.js"></script>
</body>
</html>
Helper asset​
Le helper asset() construit simplement une URL vers un fichier statique du
dossier public/. Il ne connaît pas le hash de cache ajouté par Vite en
production — réservez-le aux fichiers dont le nom ne change pas (favicon,
images statiques, etc.).
<link rel="stylesheet" href="{{ asset('css/app.css') }}">
<script src="{{ asset('js/app.js') }}"></script>
Helper vite (assets compilés)​
En production, npm run build ajoute un hash au nom de chaque fichier
(app-CBsLkjX9.js) pour le cache-busting, et enregistre la correspondance
nom logique → fichier réel dans un manifeste. Le helper vite() lit ce
manifeste et retourne l'URL du fichier compilé correspondant :
<link rel="stylesheet" href="{{ vite('css/app.css') }}">
<script type="module" src="{{ vite('js/app.js') }}"></script>
Signature :
vite(string $file, bool $absolute = false): string
$file: la clé d'entrée dans le manifeste (ex.js/app.js). Chaque fichier référencé doit être déclaré comme entrée (input) dansvite.config.jspour apparaître dans le manifeste.$absolute: sitrue, l'URL est préfixée par l'URL de l'application (viaurl()) au lieu d'être relative.- Lève une
Exceptionsi l'entrée n'existe pas dans le manifeste.
Le helper cherche le manifeste, dans l'ordre, aux emplacements suivants :
public/build/.vite/manifest.json
public/build/manifest.json
public/.vite/manifest.json
manifest.json (racine du projet)
vite() renvoie des URLs préfixées par /build/ (ex.
/build/js/app-CBsLkjX9.js). Les fichiers compilés doivent donc être servis
sous /build/ : assurez-vous que la sortie du build (outDir dans
vite.config.js) et l'emplacement du manifeste sont cohérents avec ce préfixe.
Pendant npm run dev, les assets sont servis par le serveur Vite avec HMR.
Le helper vite() n'est utile qu'après un npm run build, quand le
manifeste existe. Pensez Ă lancer le build avant de tester en mode production.
Variables d'environnement​
Vite expose les variables préfixées par VITE_ :
{
"VITE_APP_NAME": "Mon App",
"VITE_API_URL": "https://api.example.com"
}
// Accès dans le code
const appName = import.meta.env.VITE_APP_NAME;
Pour plus d'informations, consultez la documentation Vite.
Il manque quelque chose ?
Si vous rencontrez des problèmes avec la documentation ou si vous avez des suggestions pour améliorer la documentation ou le projet en général, veuillez déposer une issue pour nous, ou envoyer un tweet mentionnant le compte Twitter @bowframework ou sur directement sur le github.