Integration with your Symfony app & Vite

Related tags

API vite-bundle
Overview

Symfony logo Vite logo

ViteBundle : Symfony integration with Vite

This bundle helping you render all of the dynamic script and link tags needed. Essentially, he provide two twig functions to load the correct scripts into your templates.

{# any template or base layout where you need to include a JavaScript entry #}

{% block stylesheets %}
    {{ vite_entry_link_tags('app.js') }}
{% endblock %}

{% block javascripts %}
    {{ vite_entry_script_tags('app.js') }}
{% endblock %}

would render in dev:

<!--Nothing with vite_entry_link_tags('app.js') -->

<!-- vite_entry_script_tags('app.js') -->
<script src="http://localhost:3000/build/@vite/client" type="module"></script>
<script src="http://localhost:3000/build/app.js" type="module"></script>

would render in prod:

<!-- vite_entry_link_tags('app.js') -->
<link rel="stylesheet" href="/build/app.[hash].css" />
<link rel="modulepreload" href="/build/vendor.[hash].js" />

<!-- vite_entry_script_tags('app.js') -->
<script src="/build/app.[hash].js" type="module"></script>

if you are using React, you have to add this option in order to have FastRefresh.

{{ vite_entry_script_tags('app.js', { dependency: 'react' }) }}

Installation

Install the bundle with

composer require pentatrion/vite-bundle

create a directory structure for your js/css files:

├──assets
│ ├──app.js
│ ├──app.css
│...
├──public
├──composer.json
├──package.json
├──vite.config.js

create or complete your package.json

{
  "scripts": {
    "dev": "vite",
    "build": "vite build"
  },
  "devDependencies": {
    "vite": "^2.1.5"
  }
}

create a vite.config.js file on your project root directory. the symfonyPlugin and the manifest: true are required for the bundle to work. when you run the npm run dev the plugin remove the manifest.json file so ViteBundle know that he must return the served files. when you run the npm run build the manifest.json is constructed and ViteBundle read his content to return the build files.

// vite.config.js
import { resolve } from "path";
import { unlinkSync, existsSync } from "fs";

const symfonyPlugin = {
  name: "symfony",
  configResolved(config) {
    if (config.env.DEV && config.build.manifest) {
      let buildDir = resolve(config.root, config.build.outDir, "manifest.json");
      existsSync(buildDir) && unlinkSync(buildDir);
    }
  },
  configureServer(devServer) {
    let { watcher, ws } = devServer;
    watcher.add(resolve("templates/**/*.twig"));
    watcher.on("change", function (path) {
      if (path.endsWith(".twig")) {
        ws.send({
          type: "full-reload",
        });
      }
    });
  },
};

export default {
  plugins: [symfonyPlugin],
  server: {
    watch: {
      disableGlobbing: false,
    },
  },
  root: "./assets",
  base: "/build/",
  build: {
    manifest: true,
    emptyOutDir: true,
    assetsDir: "",
    outDir: "../public/build/",
    rollupOptions: {
      input: ["./assets/app.js"],
    },
  },
};

Configuration

default configuration

# config/packages/pentatrion_vite.yaml
pentatrion_vite:
  # Base public path when served in development or production
  base: /build/

  # Server options
  server:
    host: localhost
    port: 3000
    https: false
Comments
  • The configuration in 'pentatrion_vite.yaml' doesn't work with Docker

    The configuration in 'pentatrion_vite.yaml' doesn't work with Docker

    Hello

    Thanks for your bundle.

    I tried to use it with Docker, but I have some issue. To work with docker, I have to define a host in 'vite.config.js' :

    export default defineConfig({
        plugins: [react(), symfonyPlugin()],
        build: {
            rollupOptions: {
                input: {
                    app: "./assets/App.tsx",
                },
            },
        },
        server: {
            port: 3000,
            host: '0.0.0.0',
        },
    });
    

    But if I do that, the generated entrypoint.json don't work anymore, because the host will be now '0.0.0.0' instead of 'localhost

    {
      "isProd": false,
      "viteServer": {
        "origin": "http://0.0.0.0:3000",
        "base": "/build/"
      },
      "entryPoints": {
        "app": {
          "js": [
            "http://0.0.0.0:3000/build/assets/App.tsx"
          ]
        }
      },
      "assets": null
    }
    

    I tried to add this in config/packages/pentatrion_vite.yaml

    pentatrion_vite:
        server:
            host: localhost
            port: 3000
            https: false
    

    But it didn't work

    The only solution I found is to add 'origin: 'http://localhost:3000' in Vite config

    export default defineConfig({
        plugins: [react(), symfonyPlugin()],
        build: {
            rollupOptions: {
                input: {
                    app: "./assets/App.tsx",
                },
            },
        },
        server: {
            origin: 'http://localhost:3000',
            port: 3000,
            host: '0.0.0.0',
        },
    });
    

    And I removed the pentatrion_vite.yaml (this file didn't work)

    Now, the entrypoints.json is OK, and everything is working fine with Docker.

    I spend a lot of time to figure why this bundle didn't work with Docker, so if this issue can help someone else who struggle to use this bundle with docker.

    opened by fred-lab 12
  • Usage with asset

    Usage with asset

    It would be great to be able to use the asset symfony helper with the bundle. The way it works usually is by reading a manifest file in the build directory in order to resolve the asset path. Not sure if it is possible to generate such a file with vite but it would be awesome.

    opened by Vincz 12
  • Configuration Option Base Ignored

    Configuration Option Base Ignored

    I am trying to use this bundle in a Sulu CMS project. In order to do so and not overwrite the admin assets (that are built in /public/build/admin) I am trying to set the pentatrion_vite.base option to "/build/website".

    If I run bin/console debug:container vite --show-arguments and select vite.entrypoints_lookup I get the appropriate path /public/build/website/entrypoints.json, however the generated html from the {{ vite_entry_link_tags('app') }} (and script tag) shows the default /public/build/ paths (no /website).

    This seems to be the case even if changing build to something like app (so it is not to do with being a subdirectory).

    Vite itself is placing the files in the correct place, so I believe the vite-plugin-symfony config is working correctly (pasted relevant option below for reference):

    symfonyPlugin({
        buildDirectory: "/build/website/"
    }),
    
    opened by porl 11
  • Relative Assets in SASS aren't resolved correctly

    Relative Assets in SASS aren't resolved correctly

    Hey there,

    There seems to be an issue in this bundle and/or its Vite configuration with relative asset paths in SASS.

    With a directory structure like this:

    assets
    ├── app.js
    ├── images
    │   └── vite.svg
    └── styles
        ├── pages
        │   └── home.scss
        └── style.scss
    
    

    And home.scss containing this:

    #app {
      width: 410px;
      height: 404px;
      background-image: url('../../images/vite.svg');
    }
    

    The background image does not load.

    However, if you change the background image URL to ../images/vite.svg then it does load - but this is incorrect because images/ is 2 levels above styles/pages.

    This used to be an issue in Vite itself, but was recently fixed in v3.2.3

    I have created two demo projects to help debug this issue:

    This is a standard Vite project, showing that the path is resolved correctly: https://stackblitz.com/edit/vitejs-vite-2btrkm

    And this is a standard Symfony 6.1 project with this bundle installed: https://github.com/andyexeter/vite-bundle-issue-demo

    If you install and run the Symfony project you'll see that the background image does not display unless you change the path to the incorrect one.

    opened by andyexeter 9
  • add the possibility to modify the public folder

    add the possibility to modify the public folder

    i got issue when i tried change public directory, i propose add to possibility change it in config/packages/pentatrion_vite.yaml by public_dir variable.

    PS: my english is bad so i don't know if my comment is explicit enough in the readme

    opened by maamri95 8
  • Files only included in Dev-Mode

    Files only included in Dev-Mode

    I've installed the bundle exactly as described in the README. The only change I've made is in vite.config.js, where I've imported the Vue plugin:

    ...
    import vuePlugin from "@vitejs/plugin-vue";
    ...
      plugins: [
        vuePlugin(),
        symfonyPlugin,
      ],
    ...
    

    When I run yarn dev, everything works as expected: The Vite server is started and the files get included. But after running yarn build, the files get not included. The vite_entry_link_tags and vite_entry_script_tags return nothing.

    Is there anything else to do?

    opened by marcstraube 6
  • Include publicDir: false in vite.config.js

    Include publicDir: false in vite.config.js

    When building a project for deployment I run npm run build, which runs vite build. By default, Vite will copy all assets in /public to the build directory. However, this is generally not what you want with the Symfony /public directory: apart from useless files like index.php it will also copy bundles in /public/bundles, so a directory is created. At this moment, you will run into trouble with npm run dev, which outputs:

    error when starting dev server:
    SystemError [ERR_FS_EISDIR]: Path is a directory: rm returned EISDIR (is a directory) /Users/xxx/Sites/project-dir/public/build/bundles
    

    You can circumvent this whole copying behaviour by adding

    publicDir: false
    

    to vite.config.js.

    Would this be a sane default to add to the README?

    opened by marcelkorpel 4
  • Upgrade to vite 2.8.x shows Entry points must be inside Vite root directory

    Upgrade to vite 2.8.x shows Entry points must be inside Vite root directory

    Hey there!

    unfortunately i cannot upgrade to vite 2.8. with the plugin.

    When I downgrade vite to 2.7.x it works as before.

    My vite config looks exactly like the readme.md file

    I get the error: "Entry points must be inside Vite root directory" i debugged a bit and it resolves the relative path wrong. It resolves it to the pwd instead of pwd + config.root, that's why the error occurs

    opened by pscheit 4
  • Images fail to load in dev mode

    Images fail to load in dev mode

    I am importing and using an image like this:

    import logo from "./logo.png"
    
    const img = document.createElement("img")
    img.src = logo
    document.body.append(img)
    

    When running npm run dev, the logo variable contains /build/js/components/logo.png. The browser tries to load the file but fails with a 404 error.

    When I look in public/build, I have the output of a previous build, but no js/components/logo.png file.

    If I run npm run build, there is works fine.

    Here is my configuration file (vite.config.ts):

    import { resolve } from "path"
    import { unlinkSync, existsSync } from "fs"
    import react, { Options } from "@vitejs/plugin-react"
    import glob from "glob"
    import { defineConfig } from "vite"
    
    const symfonyPlugin = {
      name: "symfony",
      configResolved(config: any) {
        if (config.env.DEV && config.build.manifest) {
          let buildDir = resolve(config.root, config.build.outDir, "manifest.json")
          existsSync(buildDir) && unlinkSync(buildDir)
        }
      },
      configureServer(devServer: any) {
        let { watcher, ws } = devServer
        watcher.add(resolve("templates/**/*.twig"))
        watcher.on("change", function (path: string) {
          if (path.endsWith(".twig")) {
            ws.send({
              type: "full-reload",
            })
          }
        })
      },
    }
    
    const getEntrypoints = () => {
      return glob.sync("./assets/js/pages/**/index.tsx")
    }
    
    export default defineConfig({
      plugins: [react({ configFile: true } as Options), symfonyPlugin],
      server: {
        watch: {
          disableGlobbing: false,
        },
        fs: {
          strict: false,
          allow: [".."],
        },
      },
      root: "./assets",
      base: "/build/",
      build: {
        manifest: true,
        emptyOutDir: true,
        assetsDir: "",
        outDir: "../public/build/",
        rollupOptions: {
          input: getEntrypoints(),
        },
      },
      resolve: {
        alias: {
          app: resolve(__dirname, "assets/js"),
        },
      },
      optimizeDeps: {
        include: ["react", "react-dom", "@mui/material"],
      },
    })
    
    opened by drazik 4
  • Vite HMR and symfony serve

    Vite HMR and symfony serve

    Salût,

    we currently use Symfony Encore in several projects, one is planned for relaunch using Vue3 and I was hoping to move away from Encore and WebPack and use Vite with this fine bundle.

    To get more familiar with this, I have created a blank local symfony test project using the symfony binary. All things like Twig, loading the "app" js and css etc. works fine, but I can't get HMR to work.

    symfony server:start --no-tls or symfony serve --no-tls run on http://127.0.0.1:8000/ where I can see the output of my routes and twig templates. I need to run build --watch instead of dev, then manually refresh the browser to see the change. Using build seems ok with a couple of scripts, but there will be loads more js and css files in the actual web project. I have no experience yet whether build watch mode will give us the same DX like dev watch mode, let alone build doesn't give me HMR, which is one major selling point for using Vite in the first place.

    When I run yarn dev --watch, Vite tells me to visit Local: http://127.0.0.1:5173/build/ where all I find is the Symfony + Vite default page image This is not the place to view your application. To access your Symfony application, you will need to run a local development server. symfony serve

    What's this /build route for? How does symfony serve with yarn dev (vite) give me hot module reloads?

    I understand port 5173 is Vite's new default port, but how do I "link" this with Symfony's local web server ... ... or eventually nginx which is used for developing the final website and running on a different machine. Would this then require port forwarding?

    I'm a bit lost here and any help and hints are appreciated. 🙏

    Thank you!

    opened by WebMechanic 3
  • Bundle config being seemingly ignored

    Bundle config being seemingly ignored

    Server options seems to be ignored as setting host to a different domain other than localhost does nothing.

    Then browser keeps reloading because it can't connect to the websocket.

    [vite] connecting...
    ​ WebSocket connection to 'ws://my.domain.local:3000/build/' failed: 
    (anonymous) @ client:188
    ​ [vite] server connection lost. polling for restart...
     GET http://my.domain.local/build/__vite_ping 404 (Not Found)
    

    My config at config/packages/pentatrion_vite.yaml

    pentatrion_vite:
        base: /build/
        public_dir: /public
        server:
            host: my.domain.local
            port: 3000
            https: false
    

    Running the vite command shows that it's still listening to localhost.

    vite v2.8.6 dev server running at:
    
      > Local: http://localhost:3000/build/
      > Network: use `--host` to expose
    
      ready in 12137ms.
    

    Oddly enough, after upgrading vite from 2.7 to 2.8 and your plugin from 0.2.4 to 0.3.1 makes it that the server is suddenly slow as snail. It went from ready in about 1s to ready in 12 secs That is insane, any tips ? Is it scanning the whole project because the root is no longer ./assets but . in vite.config.js ?

    import {defineConfig} from "vite"
    import symfonyPlugin from "vite-plugin-symfony"
    import { svelte } from "@sveltejs/vite-plugin-svelte"
    import autoPreprocess from 'svelte-preprocess'
    import viteDefineEnvs from "vite-define-envs-plugin"
    import { visualizer } from 'rollup-plugin-visualizer'
    
    export default defineConfig({
        plugins: [
            symfonyPlugin(),
            svelte({
                preprocess: autoPreprocess()
            }),
            viteDefineEnvs(["NODE_ENV"], "process.env"),
            // visualizer({
            //     template: 'treemap',
            //     gzipSize: true,
            //     open: true,
            // })
        ],
        root: ".",
        base: "/build/",
        build: {
            manifest: true,
            emptyOutDir: true,
            assetsDir: "",
            outDir: "./public/build/",
            rollupOptions: {
                input: {
                    app: "./assets/app.ts",
                    admin: "./assets/admin.ts",
                },
            },
        },
        resolve: {
            alias: [
                {
                    find: /^~.+/,
                    replacement: (val) => {
                        return val.replace(/^~/, "");
                    },
                },
            ],
        },
    });
    

    vite-plugin-symfony: 0.3.1 pentatrion/vite-bundle: 1.2.0

    opened by FluffyDiscord 3
  • Loading Build assets when in dev mode

    Loading Build assets when in dev mode

    We are wondering since our backend-developers don't make changes to the JS and SCSS and thus don't really need to do a yarn dev if it is possible to rewrite the config to not load assets from localhost:3000 but directly from the generated (via yarn build) assets.

    Not sure if this is a config we have to make in the config/packages/pentatrion_vite.yaml or the vite.config.js.

    opened by sander-lameco 2
Owner
Hugues Tavernier
Hugues Tavernier
This bundle provides tools to build a complete GraphQL server in your Symfony App.

OverblogGraphQLBundle This Symfony bundle provides integration of GraphQL using webonyx/graphql-php and GraphQL Relay. It also supports: batching with

Webedia - Overblog 720 Dec 25, 2022
Provides a Middleware to integration Tideways into Symfony Messenger Processing

Tideways Middleware for Symfony Messenger This package is currently under development and might be moved into the Tideways PHP Extension or stay indep

Tideways 6 Jul 5, 2022
OpenAPI(v3) Validators for Symfony http-foundation, using `league/openapi-psr7-validator` and `symfony/psr-http-message-bridge`.

openapi-http-foundation-validator OpenAPI(v3) Validators for Symfony http-foundation, using league/openapi-psr7-validator and symfony/psr-http-message

n1215 2 Nov 19, 2021
Fork of Symfony Rate Limiter Component for Symfony 4

Rate Limiter Component Fork (Compatible with Symfony <=4.4) The Rate Limiter component provides a Token Bucket implementation to rate limit input and

AvaiBook by idealista 4 Apr 19, 2022
Enter-to-the-Matrix-with-Symfony-Console - Reproduction of the "Matrix characterfall" effect with the Symfony Console component.

Enter to the Matrix (with Symfony Console) Reproduction of the "Matrix characterfall" effect with the Symfony Console component. Run Clone the project

Yoan Bernabeu 23 Aug 28, 2022
CORS (Cross-Origin Resource Sharing) for your Symfony/Laravel requests

CORS for PHP (using the Symfony HttpFoundation) Library and middleware enabling cross-origin resource sharing for your http-{foundation,kernel} using

Fruitcake 91 Dec 22, 2022
A Symfony bundle that provides #StandWithUkraine banner and has some built-in features to block access to your resource for Russian-speaking users.

StandWithUkraineBundle На русском? Смотри README.ru.md This bundle provides a built-in StandWithUkraine banner for your Symfony application and has so

Victor Bocharsky 10 Nov 12, 2022
System to control your app from site

ProgramManager System to control your app from site You can add more featutre and develop page you must use DataBase mysql 3 columns , 1 for id ( AI c

OmarMazin 4 Mar 17, 2022
Ariama Victor (A.K.A. OVAC4U) 106 Dec 25, 2022
Facebook SDK for PHP (v6) - allows you to access the Facebook Platform from your PHP app

Facebook SDK for PHP (v6) This repository contains the open source PHP SDK that allows you to access the Facebook Platform from your PHP app. Installa

null 0 Aug 10, 2022
Fully unit tested Facebook SDK v5 integration for Laravel & Lumen

Laravel Facebook SDK A fully unit-tested package for easily integrating the Facebook SDK v5 into Laravel and Lumen 5.0, 5.1, 5.2, & 5.3. This is packa

Sammy Kaye Powers 697 Nov 6, 2022
Modern version of pocketmine forms API, ported to PHP 8.0+ with high quality code and phpstan integration

forms Modern version of pocketmine forms API, ported to PHP 8.0+ with high quality code and phpstan integration Code samples ModalForm Using ModalForm

Frago9876543210 23 Nov 18, 2022
A RESTful and extendable Backend as a Service that provides instant backend to develop sites and apps faster, with dead-simple integration for JavaScript, iOS, Android and more.

Welcome to hook ![Gitter](https://badges.gitter.im/Join Chat.svg) hook is a RESTful, extendable Backend as a Service that provides instant backend to

doubleleft 762 Dec 30, 2022
Doctrine-like fixtures integration for Shopware 6.

Shopware 6 Fixtures Did you ever want to create and load Doctrine-like fixtures in your Shopware 6 plugin? Look no further! This plugin provides an ul

Familiy Office 0 Oct 29, 2021
Judge0 API integration for running/judging code with different languages

Laravel Judge0 Judge0 API integration for running/judging code with different languages use Mouadbnl\Judge0\Models\Submission; $submission = Submissi

Mouad Benali 10 Dec 6, 2022
PHP library for Qvapay API integration.

Php library for Qvapay API This PHP library facilitates the integration of the Qvapay API. Sign up on QvaPay Create your account to process payments t

Omar Villafuerte 9 Aug 20, 2022
Paynow SDK Laravel integration

About Laravel Laravel is a web application framework with expressive, elegant syntax. We believe development must be an enjoyable and creative experie

Alfred Tanaka Kudiwahove 2 Sep 20, 2021
WordPress integration for globalis/chargebee-php-sdk

chargebee-php-sdk-wp Overview WordPress integration for globalis/chargebee-php-sdk Features Convert PSR-14 events into WordPress hooks Add query-monit

GLOBALIS media systems 7 Feb 17, 2022
Pure PHP implementation of GraphQL Server – Symfony Bundle

Symfony GraphQl Bundle This is a bundle based on the pure PHP GraphQL Server implementation This bundle provides you with: Full compatibility with the

null 283 Dec 15, 2022