diff --git a/src/Asset/EntrypointRenderer.php b/src/Asset/EntrypointRenderer.php index 38b6dfd..968fd23 100644 --- a/src/Asset/EntrypointRenderer.php +++ b/src/Asset/EntrypointRenderer.php @@ -11,14 +11,14 @@ class EntrypointRenderer private EntrypointsLookupCollection $entrypointsLookupCollection; private TagRendererCollection $tagRendererCollection; private bool $useAbsoluteUrl; - private RouterInterface $router; - private EventDispatcherInterface $eventDispatcher; + private ?RouterInterface $router; + private ?EventDispatcherInterface $eventDispatcher; - private $returnedViteClient = false; - private $returnedReactRefresh = false; - private $returnedPreloadedScripts = []; + private $returnedViteClients = []; + private $returnedReactRefresh = []; + private $returnedViteLegacyScripts = []; - private $hasReturnedViteLegacyScripts = false; + private $renderedFiles = []; public function __construct( EntrypointsLookupCollection $entrypointsLookupCollection, @@ -57,7 +57,7 @@ private function shouldUseAbsoluteURL(array $options, $configName) { $viteServer = $this->getEntrypointsLookup($configName)->getViteServer($configName); - return false === $viteServer && ($this->useAbsoluteUrl || (isset($options['absolute_url']) && true === $options['absolute_url'])); + return is_null($viteServer) && ($this->useAbsoluteUrl || (isset($options['absolute_url']) && true === $options['absolute_url'])); } public function getMode(string $configName = null): ?string @@ -73,9 +73,10 @@ public function getMode(string $configName = null): ?string public function reset() { - // resets the state of this service - $this->returnedViteClient = false; - $this->returnedReactRefresh = false; + $this->returnedViteClients = []; + $this->returnedReactRefresh = []; + $this->returnedViteLegacyScripts = []; + $this->renderedFiles = []; } public function renderScripts( @@ -96,25 +97,27 @@ public function renderScripts( $tags = []; $viteServer = $entrypointsLookup->getViteServer(); $isBuild = $entrypointsLookup->isBuild(); + $base = $entrypointsLookup->getBase(); - if (false !== $viteServer) { + if (!is_null($viteServer)) { // vite server is active - if (!$this->returnedViteClient) { - $tags[] = $tagRenderer->createViteClientScript($viteServer['origin'].$viteServer['base'].'@vite/client'); - $this->returnedViteClient = true; + if (!isset($this->returnedViteClients[$configName])) { + $tags[] = $tagRenderer->createViteClientScript($viteServer.$base.'@vite/client'); + + $this->returnedViteClients[$configName] = true; } if ( - !$this->returnedReactRefresh + !isset($this->returnedReactRefresh[$configName]) && isset($options['dependency']) && 'react' === $options['dependency'] ) { - $tags[] = $tagRenderer->createReactRefreshScript($viteServer['origin'].$viteServer['base']); + $tags[] = $tagRenderer->createReactRefreshScript($viteServer.$base); - $this->$this->returnedReactRefresh = true; + $this->returnedReactRefresh[$configName] = true; } } elseif ( $entrypointsLookup->isLegacyPluginEnabled() - && !$this->hasReturnedViteLegacyScripts + && !isset($this->returnedViteLegacyScripts[$configName]) ) { /* legacy section when vite server is inactive */ $tags[] = $tagRenderer->createDetectModernBrowserScript(); @@ -132,39 +135,48 @@ public function renderScripts( ] ); } - $this->hasReturnedViteLegacyScripts = true; + + $this->returnedViteLegacyScripts[$configName] = true; } /* normal js scripts */ foreach ($entrypointsLookup->getJSFiles($entryName) as $filePath) { - $tags[] = $tagRenderer->createScriptTag( - array_merge( - [ - 'type' => 'module', - 'src' => $this->completeURL($filePath, $useAbsoluteUrl), - 'integrity' => $entrypointsLookup->getFileHash($filePath), - ], - $options['attr'] ?? [] - ) - ); + if (false === \in_array($filePath, $this->renderedFiles, true)) { + $tags[] = $tagRenderer->createScriptTag( + array_merge( + [ + 'type' => 'module', + 'src' => $this->completeURL($filePath, $useAbsoluteUrl), + 'integrity' => $entrypointsLookup->getFileHash($filePath), + ], + $options['attr'] ?? [] + ) + ); + + $this->renderedFiles[] = $filePath; + } } /* legacy js scripts */ if ($entrypointsLookup->hasLegacy($entryName)) { $id = self::pascalToKebab("vite-legacy-entry-$entryName"); - $file = $entrypointsLookup->getLegacyJSFile($entryName); - $tags[] = $tagRenderer->createScriptTag( - [ - 'nomodule' => true, - 'data-src' => $this->completeURL($file, $useAbsoluteUrl), - 'id' => $id, - 'crossorigin' => true, - 'class' => 'vite-legacy-entry', - 'integrity' => $entrypointsLookup->getFileHash($file), - ], - InlineContent::getSystemJSInlineCode($id) - ); + $filePath = $entrypointsLookup->getLegacyJSFile($entryName); + if (false === \in_array($filePath, $this->renderedFiles, true)) { + $tags[] = $tagRenderer->createScriptTag( + [ + 'nomodule' => true, + 'data-src' => $this->completeURL($filePath, $useAbsoluteUrl), + 'id' => $id, + 'crossorigin' => true, + 'class' => 'vite-legacy-entry', + 'integrity' => $entrypointsLookup->getFileHash($filePath), + ], + InlineContent::getSystemJSInlineCode($id) + ); + + $this->renderedFiles[] = $filePath; + } } return $this->renderTags($tags, $isBuild, $toString); @@ -189,32 +201,35 @@ public function renderLinks( $tags = []; foreach ($entrypointsLookup->getCSSFiles($entryName) as $filePath) { - $tags[] = $tagRenderer->createLinkStylesheetTag( - $this->completeURL($filePath, $useAbsoluteUrl), - array_merge(['integrity' => $entrypointsLookup->getFileHash($filePath)], $options['attr'] ?? []) - ); + if (false === \in_array($filePath, $this->renderedFiles, true)) { + $tags[] = $tagRenderer->createLinkStylesheetTag( + $this->completeURL($filePath, $useAbsoluteUrl), + array_merge(['integrity' => $entrypointsLookup->getFileHash($filePath)], $options['attr'] ?? []) + ); + $this->renderedFiles[] = $filePath; + } } if ($isBuild) { foreach ($entrypointsLookup->getJavascriptDependencies($entryName) as $filePath) { - if (false === \in_array($filePath, $this->returnedPreloadedScripts, true)) { + if (false === \in_array($filePath, $this->renderedFiles, true)) { $tags[] = $tagRenderer->createModulePreloadLinkTag( $this->completeURL($filePath, $useAbsoluteUrl), ['integrity' => $entrypointsLookup->getFileHash($filePath)] ); - $this->returnedPreloadedScripts[] = $filePath; + $this->renderedFiles[] = $filePath; } } } if ($isBuild && isset($options['preloadDynamicImports']) && true === $options['preloadDynamicImports']) { foreach ($entrypointsLookup->getJavascriptDynamicDependencies($entryName) as $filePath) { - if (false === \in_array($filePath, $this->returnedPreloadedScripts, true)) { + if (false === \in_array($filePath, $this->renderedFiles, true)) { $tags[] = $tagRenderer->createModulePreloadLinkTag( $this->completeURL($filePath, $useAbsoluteUrl), ['integrity' => $entrypointsLookup->getFileHash($filePath)] ); - $this->returnedPreloadedScripts[] = $filePath; + $this->renderedFiles[] = $filePath; } } } @@ -231,7 +246,7 @@ public function renderTags(array $tags, $isBuild, $toString) } return $toString - ? implode(PHP_EOL, array_map(function ($tagEvent) { + ? implode('', array_map(function ($tagEvent) { return TagRenderer::generateTag($tagEvent); }, $tags)) : $tags; diff --git a/src/Asset/EntrypointsLookup.php b/src/Asset/EntrypointsLookup.php index 5ee3472..174295f 100644 --- a/src/Asset/EntrypointsLookup.php +++ b/src/Asset/EntrypointsLookup.php @@ -37,8 +37,11 @@ private function getFileContent(): array throw new \Exception('entrypoints.json not found at '.$this->fileInfos['entrypointsPath']); } $content = json_decode(file_get_contents($this->fileInfos['entrypointsPath']), true); - if (!isset($content['entryPoints'], $content['viteServer'])) { - throw new \Exception($this->fileInfos['entrypointsPath'].' : entryPoints or viteServer not exists'); + if (!array_key_exists('entryPoints', $content) + || !array_key_exists('viteServer', $content) + || !array_key_exists('base', $content) + ) { + throw new \Exception($this->fileInfos['entrypointsPath'].' : entryPoints, base or viteServer not exists'); } $this->fileInfos['content'] = $content; @@ -67,7 +70,7 @@ public function isLegacyPluginEnabled(): bool public function isBuild(): bool { - return false === $this->getFileContent()['viteServer']; + return null === $this->getFileContent()['viteServer']; } public function getViteServer() @@ -75,6 +78,11 @@ public function getViteServer() return $this->getFileContent()['viteServer']; } + public function getBase() + { + return $this->getFileContent()['base']; + } + public function getJSFiles($entryName): array { $this->throwIfEntrypointIsMissing($entryName); diff --git a/src/Asset/Tag.php b/src/Asset/Tag.php index bca3c62..1ea37a0 100644 --- a/src/Asset/Tag.php +++ b/src/Asset/Tag.php @@ -35,11 +35,30 @@ public function isLinkTag(): bool return self::LINK_TAG === $this->tagName; } + public function isStylesheet(): bool + { + return self::LINK_TAG === $this->tagName + && isset($this->attributes['rel']) + && 'stylesheet' === $this->attributes['rel']; + } + + public function isModulePreload(): bool + { + return self::LINK_TAG === $this->tagName + && isset($this->attributes['rel']) + && 'modulepreload' === $this->attributes['rel']; + } + public function getAttributes(): array { return $this->attributes; } + public function getAttribute($key): mixed + { + return key_exists($key, $this->attributes) ? $this->attributes[$key] : null; + } + /** * @param string $name The attribute name * @param string|bool $value Value can be "true" to have an attribute without a value (e.g. "defer") diff --git a/src/Asset/ViteAssetVersionStrategy.php b/src/Asset/ViteAssetVersionStrategy.php index eea7f65..8815268 100644 --- a/src/Asset/ViteAssetVersionStrategy.php +++ b/src/Asset/ViteAssetVersionStrategy.php @@ -10,7 +10,7 @@ class ViteAssetVersionStrategy implements VersionStrategyInterface { private string $publicPath; - private array $builds; + private array $configs; private $useAbsoluteUrl; private $router; @@ -18,41 +18,44 @@ class ViteAssetVersionStrategy implements VersionStrategyInterface private string $entrypointsPath; private $manifestData; private $entrypointsData; - private ?array $build = null; + private ?array $config = null; private bool $strictMode; + private ?string $mode = null; public function __construct( string $publicPath, - array $builds, - string $defaultBuildName, + array $configs, + string $defaultConfigName, bool $useAbsoluteUrl, RouterInterface $router = null, bool $strictMode = true ) { $this->publicPath = $publicPath; - $this->builds = $builds; + $this->configs = $configs; $this->strictMode = $strictMode; $this->useAbsoluteUrl = $useAbsoluteUrl; $this->router = $router; - $this->setBuildName($defaultBuildName); + $this->setConfig($defaultConfigName); if (($scheme = parse_url($this->manifestPath, \PHP_URL_SCHEME)) && 0 === strpos($scheme, 'http')) { throw new \Exception('You can\'t use a remote manifest with ViteAssetVersionStrategy'); } } - public function setBuildName(string $buildName): void + public function setConfig(string $configName): void { - $this->build = $this->builds[$buildName]; - $this->manifestPath = $this->publicPath.$this->build['base'].'manifest.json'; - $this->entrypointsPath = $this->publicPath.$this->build['base'].'entrypoints.json'; + $this->mode = null; + $this->config = $this->configs[$configName]; + $this->manifestPath = $this->publicPath.$this->config['base'].'manifest.json'; + $this->entrypointsPath = $this->publicPath.$this->config['base'].'entrypoints.json'; } /** * With a entrypoints, we don't really know or care about what * the version is. Instead, this returns the path to the - * versioned file. + * versioned file. as it contains a hashed and different path + * with each new config, this is enough for us. */ public function getVersion(string $path): string { @@ -75,19 +78,21 @@ private function completeURL(string $path) private function getassetsPath(string $path): ?string { - if (null === $this->manifestData) { + if (null === $this->mode) { if (!is_file($this->entrypointsPath)) { - throw new RuntimeException(sprintf('assets entrypoints file "%s" does not exist. Did you forget configure your base in pentatrion_vite.yml?', $this->manifestPath)); + throw new RuntimeException(sprintf('assets entrypoints file "%s" does not exist. Did you forget configure your `build_dir` in pentatrion_vite.yml?', $this->entrypointsPath)); } if (is_file($this->manifestPath)) { + // when vite server is running manifest file doesn't exists + $this->mode = 'build'; try { $this->manifestData = json_decode(file_get_contents($this->manifestPath), true, 512, \JSON_THROW_ON_ERROR); } catch (\JsonException $e) { throw new RuntimeException(sprintf('Error parsing JSON from entrypoints file "%s": ', $this->manifestPath).$e->getMessage(), 0, $e); } } else { - $this->manifestData = false; + $this->mode = 'dev'; try { $this->entrypointsData = json_decode(file_get_contents($this->entrypointsPath), true, 512, \JSON_THROW_ON_ERROR); } catch (\JsonException $e) { @@ -96,12 +101,12 @@ private function getassetsPath(string $path): ?string } } - if (false !== $this->manifestData) { + if ('build' === $this->mode) { if (isset($this->manifestData[$path])) { - return $this->completeURL($this->build['base'].$this->manifestData[$path]['file']); + return $this->completeURL($this->config['base'].$this->manifestData[$path]['file']); } } else { - return $this->entrypointsData['viteServer']['origin'].$this->entrypointsData['viteServer']['base'].$path; + return $this->entrypointsData['viteServer'].$this->entrypointsData['base'].$path; } if ($this->strictMode) { diff --git a/src/Controller/ViteController.php b/src/Controller/ViteController.php index 8766927..3a5d378 100644 --- a/src/Controller/ViteController.php +++ b/src/Controller/ViteController.php @@ -2,50 +2,53 @@ namespace Pentatrion\ViteBundle\Controller; -use Pentatrion\ViteBundle\Asset\EntrypointsLookup; +use Pentatrion\ViteBundle\Asset\EntrypointsLookupCollection; use Symfony\Component\HttpFoundation\Response; use Symfony\Contracts\HttpClient\HttpClientInterface; class ViteController { public $httpClient; - public string $defaultBuild; - public array $builds; - private $entrypointsLookup; + public string $defaultConfig; + public array $configs; + private $entrypointsLookupCollection; private $proxyOrigin; public function __construct( - string $defaultBuild, - array $builds, + string $defaultConfig, + array $configs, HttpClientInterface $httpClient, - EntrypointsLookup $entrypointsLookup, + EntrypointsLookupCollection $entrypointsLookupCollection, ?string $proxyOrigin ) { - $this->defaultBuild = $defaultBuild; - $this->builds = $builds; + $this->defaultConfig = $defaultConfig; + $this->configs = $configs; $this->httpClient = $httpClient; - $this->entrypointsLookup = $entrypointsLookup; + $this->entrypointsLookupCollection = $entrypointsLookupCollection; $this->proxyOrigin = $proxyOrigin; } - public function proxyBuild($path, $buildName = null): Response + public function proxyBuild($path, $configName = null): Response { - if (is_null($buildName)) { - $buildName = $this->defaultBuild; + if (is_null($configName)) { + $configName = $this->defaultConfig; } - $viteDevServer = $this->entrypointsLookup->getViteServer($buildName); + $entrypointsLookup = $this->entrypointsLookupCollection->getEntrypointsLookup($configName); - if (is_null($viteDevServer) || false === $viteDevServer) { + $viteDevServer = $entrypointsLookup->getViteServer(); + $base = $entrypointsLookup->getBase(); + + if (is_null($viteDevServer)) { return new \Exception('Vite dev server not available'); } - $origin = $this->proxyOrigin ?? $viteDevServer['origin']; + $origin = $this->proxyOrigin ?? $viteDevServer; $response = $this->httpClient->request( 'GET', - $origin.$this->builds[$buildName]['base'].$path + $origin.$base.$path ); $content = $response->getContent(); diff --git a/src/DependencyInjection/Configuration.php b/src/DependencyInjection/Configuration.php index ab02df2..8ebec11 100644 --- a/src/DependencyInjection/Configuration.php +++ b/src/DependencyInjection/Configuration.php @@ -17,9 +17,10 @@ public function getConfigTreeBuilder(): TreeBuilder $rootNode ->children() ->scalarNode('public_directory') - ->defaultValue('public') + ->defaultValue('public') ->end() ->scalarNode('build_directory') + ->info('we only need build_directory to locate entrypoints.json file, it\'s the "base" vite config parameter without slashes.') ->defaultValue('build') ->end() ->scalarNode('proxy_origin') diff --git a/tests/Asset/EntrypointRendererTest.php b/tests/Asset/EntrypointRendererTest.php new file mode 100644 index 0000000..fff2520 --- /dev/null +++ b/tests/Asset/EntrypointRendererTest.php @@ -0,0 +1,619 @@ +createStub(TagRendererCollection::class); + $tagRendererCollection + ->method('getTagRenderer') + ->willReturn($tagRenderer); + + return $tagRendererCollection; + } + + private function getEntrypointsLookupCollection(EntrypointsLookup $entrypointsLookup) + { + /** + * @var EntrypointsLookupCollection|Stub $entrypointsLookupCollection + */ + $entrypointsLookupCollection = $this->createStub(EntrypointsLookupCollection::class); + $entrypointsLookupCollection + ->method('getEntrypointsLookup') + ->willReturn($entrypointsLookup); + + return $entrypointsLookupCollection; + } + + // public function getBaseDevEntrypointsLookupStub() + // { + // /** + // * @var EntrypointsLookup|Stub $entrypointsLookup + // */ + // $entrypointsLookup = $this->createStub(EntrypointsLookup::class); + + // $entrypointsLookup + // ->method('hasFile') + // ->willReturn(true); + + // $entrypointsLookup + // ->method('isBuild') + // ->willReturn(false); + + // $entrypointsLookup + // ->method('getViteServer') + // ->willReturn([ + // 'origin' => 'http://127.0.0.1:5173', + // 'base' => '/build/', + // ]); + + // return $entrypointsLookup; + // } + + // public function getBaseBuildEntrypointsLookupStub() + // { + // /** + // * @var EntrypointsLookup|Stub $entrypointsLookup + // */ + // $entrypointsLookup = $this->createStub(EntrypointsLookup::class); + + // $entrypointsLookup + // ->method('hasFile') + // ->willReturn(true); + + // $entrypointsLookup + // ->method('isBuild') + // ->willReturn(true); + + // $entrypointsLookup + // ->method('getViteServer') + // ->willReturn(false); + + // return $entrypointsLookup; + // } + + private function getEntrypointsLookup($prefix) + { + return new EntrypointsLookup( + __DIR__.'/../fixtures/entrypoints', + ['base' => '/'.$prefix.'/'], + true + ); + } + + public function basicProvider() + { + return [ + [ + 'basic-build', + 'app', + [ + 'mode' => 'build', + 'scripts' => '', + 'links' => '', + ], + ], + [ + 'basic-build', + 'theme', + [ + 'mode' => 'build', + 'scripts' => '', + 'links' => '', + ], + ], + [ + 'basic-build', + 'with-dep', + [ + 'mode' => 'build', + 'scripts' => '', + 'links' => '' + .'' + .'', + ], + ], + [ + 'basic-build', + 'with-async', + [ + 'mode' => 'build', + 'scripts' => '', + 'links' => '' + .'' + .'', + ], + ], + [ + 'basic-dev', + 'app', + [ + 'mode' => 'dev', + 'scripts' => '' + .'', + 'links' => '', + ], + ], + [ + 'basic-dev', + 'theme', + [ + 'mode' => 'dev', + 'scripts' => '', + 'links' => '', + ], + ], + [ + 'legacy-build', + 'app', + [ + 'mode' => 'build', + 'scripts' => '' + .'' + .'' + .'' + .'' + .'', + 'links' => '', + ], + ], + [ + 'legacy-build', + 'theme', + [ + 'mode' => 'build', + 'scripts' => '' + .'' + .'' + .'' + .'', + 'links' => '', + ], + ], + [ + 'metadata-build', + 'app', + [ + 'mode' => 'build', + 'scripts' => '', + 'links' => '', + ], + ], + ]; + } + + /** + * @dataProvider basicProvider + */ + public function testBasic($config, $entryName, $expectedStrings) + { + $entrypointsLookup = $this->getEntrypointsLookup($config); + + $entrypointRenderer = new EntrypointRenderer( + $this->getEntrypointsLookupCollection($entrypointsLookup), + $this->getBasicTagRendererCollection(), + false, + null, + null, + ); + + $this->assertEquals( + $expectedStrings['mode'], + $entrypointRenderer->getMode() + ); + + $this->assertEquals( + $expectedStrings['scripts'], + $entrypointRenderer->renderScripts($entryName) + ); + + $this->assertEquals( + $expectedStrings['links'], + $entrypointRenderer->renderLinks($entryName) + ); + } + + public function testRenderOnlyOneViteClient() + { + $entrypointsLookup = $this->getEntrypointsLookup('duplication-dev'); + $entrypointRenderer = new EntrypointRenderer( + $this->getEntrypointsLookupCollection($entrypointsLookup), + $this->getBasicTagRendererCollection(), + false, + null, + null, + ); + + $this->assertEquals( + '' + .'' + .'', + $entrypointRenderer->renderScripts('app').$entrypointRenderer->renderScripts('other-app') + ); + } + + public function testRenderOnlyOneReactRefresh() + { + $entrypointsLookup = $this->getEntrypointsLookup('duplication-dev'); + $entrypointRenderer = new EntrypointRenderer( + $this->getEntrypointsLookupCollection($entrypointsLookup), + $this->getBasicTagRendererCollection(), + false, + null, + null, + ); + + $this->assertEquals( + '' + .'' + .'' + .'', + $entrypointRenderer->renderScripts('app', ['dependency' => 'react']).$entrypointRenderer->renderScripts('other-app', ['dependency' => 'react']) + ); + } + + public function testRenderOnlyOneFile() + { + $entrypointsLookup = $this->getEntrypointsLookup('duplication-build'); + $entrypointRenderer = new EntrypointRenderer( + $this->getEntrypointsLookupCollection($entrypointsLookup), + $this->getBasicTagRendererCollection(), + false, + null, + null, + ); + + $expectedScripts = '' + .''; + $expectedLinks = '' + .''; + + $this->assertEquals( + $expectedScripts, + $entrypointRenderer->renderScripts('app-1').$entrypointRenderer->renderScripts('app-2') + ); + + $this->assertEquals( + $expectedLinks, + $entrypointRenderer->renderLinks('app-1').$entrypointRenderer->renderLinks('app-2'), + 'dont render twice vuejs dependency' + ); + + $this->assertEquals( + '', + $entrypointRenderer->renderScripts('app-1').$entrypointRenderer->renderScripts('app-2') + ); + + $this->assertEquals( + '', + $entrypointRenderer->renderLinks('app-1').$entrypointRenderer->renderLinks('app-2') + ); + + $entrypointRenderer->reset(); + + $this->assertEquals( + $expectedScripts, + $entrypointRenderer->renderScripts('app-1').$entrypointRenderer->renderScripts('app-2') + ); + + $this->assertEquals( + $expectedLinks, + $entrypointRenderer->renderLinks('app-1').$entrypointRenderer->renderLinks('app-2'), + 'dont render twice vuejs dependency' + ); + } + + public function testRenderOnlyOneLegacyInlineContent() + { + $entrypointsLookup = $this->getEntrypointsLookup('legacy-build'); + $entrypointRenderer = new EntrypointRenderer( + $this->getEntrypointsLookupCollection($entrypointsLookup), + $this->getBasicTagRendererCollection(), + false, + null, + null, + ); + + $this->assertEquals( + '' + .'' + .'' + .'' + .'' + .'' + .'', + $entrypointRenderer->renderScripts('app').$entrypointRenderer->renderScripts('theme') + ); + + $this->assertEquals( + '', + $entrypointRenderer->renderLinks('app').$entrypointRenderer->renderLinks('theme') + ); + } + + public function testRenderWithAbsoluteUrl() + { + /** + * @var Stub|RequestContext $context + */ + $context = $this->createStub(RequestContext::class); + $context + ->method('getScheme') + ->willReturn('http'); + + $context + ->method('getHost') + ->willReturn('mydomain.local'); + /** + * @var Stub|RouterInterface $router + */ + $router = $this->createStub(RouterInterface::class); + $router + ->method('getContext') + ->willReturn($context); + + $entrypointsLookupBasicBuild = $this->getEntrypointsLookup('basic-build'); + $entrypointsLookupBasicDev = $this->getEntrypointsLookup('basic-dev'); + + $entrypointRenderer = new EntrypointRenderer( + $this->getEntrypointsLookupCollection($entrypointsLookupBasicBuild), + $this->getBasicTagRendererCollection(), + true, + $router, + null, + ); + $this->assertEquals( + '', + $entrypointRenderer->renderScripts('app'), + 'render complete url when absolute_url defined globally' + ); + + $entrypointRenderer = new EntrypointRenderer( + $this->getEntrypointsLookupCollection($entrypointsLookupBasicBuild), + $this->getBasicTagRendererCollection(), + false, + $router, + null, + ); + $this->assertEquals( + '', + $entrypointRenderer->renderScripts('app', ['absolute_url' => true]), + 'render complete url when absolute_url defined locally' + ); + + $entrypointRenderer = new EntrypointRenderer( + $this->getEntrypointsLookupCollection($entrypointsLookupBasicDev), + $this->getBasicTagRendererCollection(), + true, + $router, + null, + ); + $this->assertEquals( + '', + $entrypointRenderer->renderScripts('app'), + 'render correct url when absolute_url defined and vite dev server is started' + ); + } + + public function testRenderAndPreloadDynamicImports() + { + $entrypointsLookup = $this->getEntrypointsLookup('basic-build'); + $entrypointRenderer = new EntrypointRenderer( + $this->getEntrypointsLookupCollection($entrypointsLookup), + $this->getBasicTagRendererCollection(), + false, + null, + null, + ); + + $this->assertEquals( + '', + $entrypointRenderer->renderScripts('with-async', [ + 'preloadDynamicImports' => true, + ]) + ); + + $this->assertEquals( + '' + .'' + .'' + .'', + $entrypointRenderer->renderLinks('with-async', [ + 'preloadDynamicImports' => true, + ]), + 'render css files, preload preload&dynamic files' + ); + } + + public function testRenderWithEvent() + { + /** + * @var EventDispatcherInterface|Stub $dispatcher + */ + $dispatcher = $this->createStub(EventDispatcherInterface::class); + $dispatcher + ->method('dispatch') + ->willReturnCallback(function (RenderAssetTagEvent $evt) { + $tag = $evt->getTag(); + if ($tag->isScriptTag()) { + $tag->setAttribute('src', $tag->getAttribute('src').'-modified'); + $tag->setAttribute('nonce', 'custom-nonce'); + } elseif ($tag->isStylesheet()) { + $tag->removeAttribute('referrerpolicy'); + } elseif ($tag->isModulePreload()) { + $tag->setAttribute('data-foo', 'bar'); + } + + return $evt; + }); + + $entrypointsLookup = $this->getEntrypointsLookup('basic-build'); + $entrypointRenderer = new EntrypointRenderer( + $this->getEntrypointsLookupCollection($entrypointsLookup), + $this->getBasicTagRendererCollection(['defer' => true], ['referrerpolicy' => 'origin']), + false, + null, + $dispatcher, + ); + + $this->assertSame( + '', + $entrypointRenderer->renderScripts('app'), + 'filter script, add custom attribute, modify attributes in last' + ); + $this->assertSame( + '', + $entrypointRenderer->renderLinks('theme'), + 'filter stylesheet, remove attribute' + ); + $this->assertSame( + '' + .'' + .'', + $entrypointRenderer->renderLinks('with-dep'), + 'filter modulepreload, add custom attribute' + ); + } + + public function testMultipleConfigInBuild() + { + $entrypointsLookupConfig1 = $this->getEntrypointsLookup('config1-build'); + $entrypointsLookupConfig2 = $this->getEntrypointsLookup('config2-build'); + + /** + * @var EntrypointsLookupCollection|Stub $entrypointsLookupCollection + */ + $entrypointsLookupCollection = $this->createStub(EntrypointsLookupCollection::class); + $entrypointsLookupCollection + ->method('getEntrypointsLookup') + ->will($this->returnValueMap([ + ['config1-dev', $entrypointsLookupConfig1], + ['config2-dev', $entrypointsLookupConfig2], + ])); + + $tagRendererConfig1 = new TagRenderer([], []); + $tagRendererConfig2 = new TagRenderer(['defer' => true], ['referrerpolicy' => 'origin']); + + /** + * @var TagRendererCollection|Stub $tagRendererCollection + */ + $tagRendererCollection = $this->createStub(TagRendererCollection::class); + $tagRendererCollection + ->method('getTagRenderer') + ->will($this->returnValueMap([ + ['config1-dev', $tagRendererConfig1], + ['config2-dev', $tagRendererConfig2], + ])); + + $entrypointRenderer = new EntrypointRenderer( + $entrypointsLookupCollection, + $tagRendererCollection, + false, + null, + null, + ); + + $this->assertEquals( + '' + .'', + $entrypointRenderer->renderScripts('app-1', [], 'config1-dev') + .$entrypointRenderer->renderScripts('app-2', [], 'config2-dev'), + 'render correct global script attributes' + ); + + $this->assertEquals( + '' + .'', + $entrypointRenderer->renderLinks('theme-1', [], 'config1-dev') + .$entrypointRenderer->renderLinks('theme-2', [], 'config2-dev'), + 'render correct global link attributes' + ); + } + + public function testMultipleConfigInDev() + { + $entrypointsLookupConfig1 = $this->getEntrypointsLookup('config1-dev'); + $entrypointsLookupConfig2 = $this->getEntrypointsLookup('config2-dev'); + + /** + * @var EntrypointsLookupCollection|Stub $entrypointsLookupCollection + */ + $entrypointsLookupCollection = $this->createStub(EntrypointsLookupCollection::class); + $entrypointsLookupCollection + ->method('getEntrypointsLookup') + ->will($this->returnValueMap([ + ['config1-dev', $entrypointsLookupConfig1], + ['config2-dev', $entrypointsLookupConfig2], + ])); + + $tagRendererConfig1 = new TagRenderer(); + $tagRendererConfig2 = new TagRenderer(); + + /** + * @var TagRendererCollection|Stub $tagRendererCollection + */ + $tagRendererCollection = $this->createStub(TagRendererCollection::class); + $tagRendererCollection + ->method('getTagRenderer') + ->will($this->returnValueMap([ + ['config1-dev', $tagRendererConfig1], + ['config2-dev', $tagRendererConfig2], + ])); + + $entrypointRenderer = new EntrypointRenderer( + $entrypointsLookupCollection, + $tagRendererCollection, + false, + null, + null, + ); + + $expectedScripts = '' + .'' + .'' + .''; + + $this->assertEquals( + $expectedScripts, + $entrypointRenderer->renderScripts('app-1', [], 'config1-dev') + .$entrypointRenderer->renderScripts('app-2', [], 'config2-dev'), + 'render multiple vite client' + ); + + $this->assertEquals( + '', + $entrypointRenderer->renderScripts('app-1', [], 'config1-dev') + .$entrypointRenderer->renderScripts('app-2', [], 'config2-dev'), + 'render multiple vite client' + ); + + $entrypointRenderer->reset(); + + $this->assertEquals( + $expectedScripts, + $entrypointRenderer->renderScripts('app-1', [], 'config1-dev') + .$entrypointRenderer->renderScripts('app-2', [], 'config2-dev'), + 'render multiple vite client' + ); + } +} diff --git a/tests/Asset/EntrypointsLookupTest.php b/tests/Asset/EntrypointsLookupTest.php index fbb003e..325b7dd 100644 --- a/tests/Asset/EntrypointsLookupTest.php +++ b/tests/Asset/EntrypointsLookupTest.php @@ -47,12 +47,12 @@ public function testViteServer() $entrypointsLookupBasicBuild = $this->getEntrypointsLookup('basic-build'); $this->assertEquals( - ['origin' => 'http://127.0.0.1:5173', 'base' => '/build/'], + 'http://127.0.0.1:5173', $entrypointsLookupBasicDev->getViteServer() ); $this->assertEquals( - false, + null, $entrypointsLookupBasicBuild->getViteServer() ); @@ -90,14 +90,14 @@ public function devfilesProvider() /** * @dataProvider devfilesProvider */ - public function testGetDevFiles($entryName, $files) + public function testGetDevFiles($entryName, $expectedFiles) { $entrypointsLookupBasicDev = $this->getEntrypointsLookup('basic-dev'); - $this->assertEquals($files['css'], $entrypointsLookupBasicDev->getCSSFiles($entryName)); - $this->assertEquals($files['dynamic'], $entrypointsLookupBasicDev->getJavascriptDynamicDependencies($entryName)); - $this->assertEquals($files['js'], $entrypointsLookupBasicDev->getJSFiles($entryName)); - $this->assertEquals($files['preload'], $entrypointsLookupBasicDev->getJavascriptDependencies($entryName)); + $this->assertEquals($expectedFiles['css'], $entrypointsLookupBasicDev->getCSSFiles($entryName)); + $this->assertEquals($expectedFiles['dynamic'], $entrypointsLookupBasicDev->getJavascriptDynamicDependencies($entryName)); + $this->assertEquals($expectedFiles['js'], $entrypointsLookupBasicDev->getJSFiles($entryName)); + $this->assertEquals($expectedFiles['preload'], $entrypointsLookupBasicDev->getJavascriptDependencies($entryName)); } public function buildfilesProvider() @@ -107,29 +107,29 @@ public function buildfilesProvider() 'assets' => [], 'css' => [], 'dynamic' => [], - 'js' => ['/build/assets/pageImports-53eb9fd1.js'], + 'js' => ['/build/assets/app.js'], 'preload' => [], ]], ['theme', [ 'assets' => [], - 'css' => ['/build/assets/theme-62617963.css'], + 'css' => ['/build/assets/theme.css'], 'dynamic' => [], 'js' => [], 'preload' => [], ]], ['with-dep', [ 'assets' => [], - 'css' => ['/build/assets/main-76fa9059.css'], + 'css' => ['/build/assets/main.css'], 'dynamic' => [], - 'js' => ['/build/assets/main-e664f4b5.js'], - 'preload' => ['/build/assets/vue-2d05229a.js', '/build/assets/react-2d05228c.js'], + 'js' => ['/build/assets/main.js'], + 'preload' => ['/build/assets/vue.js', '/build/assets/react.js'], ]], ['with-async', [ 'assets' => [], - 'css' => ['/build/assets/main-76fa9059.css'], - 'dynamic' => ['/build/assets/async-script-12324565.js'], - 'js' => ['/build/assets/main-e664f4b5.js'], - 'preload' => ['/build/assets/vue-2d05229a.js', '/build/assets/react-2d05228c.js'], + 'css' => ['/build/assets/main.css'], + 'dynamic' => ['/build/assets/async-script.js'], + 'js' => ['/build/assets/main.js'], + 'preload' => ['/build/assets/vue.js', '/build/assets/react.js'], ]], ]; } @@ -137,14 +137,14 @@ public function buildfilesProvider() /** * @dataProvider buildfilesProvider */ - public function testGetBuildFiles($entryName, $files) + public function testGetBuildFiles($entryName, $expectedFiles) { $entrypointsLookupBasicBuild = $this->getEntrypointsLookup('basic-build'); - $this->assertEquals($files['css'], $entrypointsLookupBasicBuild->getCSSFiles($entryName)); - $this->assertEquals($files['dynamic'], $entrypointsLookupBasicBuild->getJavascriptDynamicDependencies($entryName)); - $this->assertEquals($files['js'], $entrypointsLookupBasicBuild->getJSFiles($entryName)); - $this->assertEquals($files['preload'], $entrypointsLookupBasicBuild->getJavascriptDependencies($entryName)); + $this->assertEquals($expectedFiles['css'], $entrypointsLookupBasicBuild->getCSSFiles($entryName)); + $this->assertEquals($expectedFiles['dynamic'], $entrypointsLookupBasicBuild->getJavascriptDynamicDependencies($entryName)); + $this->assertEquals($expectedFiles['js'], $entrypointsLookupBasicBuild->getJSFiles($entryName)); + $this->assertEquals($expectedFiles['preload'], $entrypointsLookupBasicBuild->getJavascriptDependencies($entryName)); } public function buildLegacyProvider() @@ -154,17 +154,17 @@ public function buildLegacyProvider() 'assets' => [], 'css' => [], 'dynamic' => [], - 'js' => ['/build/assets/app-23802617.js'], + 'js' => ['/build/assets/app.js'], 'preload' => [], - 'legacy_js' => '/build/assets/app-legacy-59951366.js', + 'legacy_js' => '/build/assets/app-legacy.js', ]], ['theme', [ 'assets' => [], - 'css' => ['/build/assets/theme-5cd46aed.css'], + 'css' => ['/build/assets/theme.css'], 'dynamic' => [], 'js' => [], 'preload' => [], - 'legacy_js' => '/build/assets/theme-legacy-de9eb869.js', + 'legacy_js' => '/build/assets/theme-legacy.js', ]], ]; } @@ -172,15 +172,15 @@ public function buildLegacyProvider() /** * @dataProvider buildLegacyProvider */ - public function testGetBuildLegacyFiles($entryName, $files) + public function testGetBuildLegacyFiles($entryName, $expectedFiles) { $entrypointsLookupLegacyBuild = $this->getEntrypointsLookup('legacy-build'); - $this->assertEquals($files['css'], $entrypointsLookupLegacyBuild->getCSSFiles($entryName)); - $this->assertEquals($files['dynamic'], $entrypointsLookupLegacyBuild->getJavascriptDynamicDependencies($entryName)); - $this->assertEquals($files['js'], $entrypointsLookupLegacyBuild->getJSFiles($entryName)); - $this->assertEquals($files['preload'], $entrypointsLookupLegacyBuild->getJavascriptDependencies($entryName)); - $this->assertEquals($files['legacy_js'], $entrypointsLookupLegacyBuild->getLegacyJSFile($entryName)); + $this->assertEquals($expectedFiles['css'], $entrypointsLookupLegacyBuild->getCSSFiles($entryName)); + $this->assertEquals($expectedFiles['dynamic'], $entrypointsLookupLegacyBuild->getJavascriptDynamicDependencies($entryName)); + $this->assertEquals($expectedFiles['js'], $entrypointsLookupLegacyBuild->getJSFiles($entryName)); + $this->assertEquals($expectedFiles['preload'], $entrypointsLookupLegacyBuild->getJavascriptDependencies($entryName)); + $this->assertEquals($expectedFiles['legacy_js'], $entrypointsLookupLegacyBuild->getLegacyJSFile($entryName)); } public function testHashOfFiles() @@ -188,13 +188,13 @@ public function testHashOfFiles() $entrypointsLookupBasicBuild = $this->getEntrypointsLookup('basic-build'); $this->assertEquals( null, - $entrypointsLookupBasicBuild->getFileHash('/build/assets/pageImports-53eb9fd1.js') + $entrypointsLookupBasicBuild->getFileHash('/build/assets/app.js') ); $entrypointsLookupMetadataBuild = $this->getEntrypointsLookup('metadata-build'); $this->assertEquals( - 'sha256-qABtt8+MbhDq8dts7DSJOnBqCO1QbV2S6zg24ylLkKY=', - $entrypointsLookupMetadataBuild->getFileHash('http://cdn.with-cdn.symfony-vite-dev.localhost/assets/pageVue-bda8ac3b.js') + 'sha256-XYZ', + $entrypointsLookupMetadataBuild->getFileHash('/build/assets/app.js') ); $entrypointsLookupMetadataBuild = $this->getEntrypointsLookup('metadata-build'); diff --git a/tests/fixtures/entrypoints/basic-build/entrypoints.json b/tests/fixtures/entrypoints/basic-build/entrypoints.json index 799a1ef..b49838d 100644 --- a/tests/fixtures/entrypoints/basic-build/entrypoints.json +++ b/tests/fixtures/entrypoints/basic-build/entrypoints.json @@ -1,11 +1,12 @@ { + "base": "/build/", "entryPoints": { "app": { "assets": [], "css": [], "dynamic": [], "js": [ - "/build/assets/pageImports-53eb9fd1.js" + "/build/assets/app.js" ], "legacy": false, "preload": [] @@ -13,7 +14,7 @@ "theme": { "assets": [], "css": [ - "/build/assets/theme-62617963.css" + "/build/assets/theme.css" ], "dynamic": [], "js": [], @@ -23,37 +24,37 @@ "with-dep": { "assets": [], "css": [ - "/build/assets/main-76fa9059.css" + "/build/assets/main.css" ], "dynamic": [], "js": [ - "/build/assets/main-e664f4b5.js" + "/build/assets/main.js" ], "legacy": false, "preload": [ - "/build/assets/vue-2d05229a.js", - "/build/assets/react-2d05228c.js" + "/build/assets/vue.js", + "/build/assets/react.js" ] }, "with-async": { "assets": [], "css": [ - "/build/assets/main-76fa9059.css" + "/build/assets/main.css" ], "dynamic": [ - "/build/assets/async-script-12324565.js" + "/build/assets/async-script.js" ], "js": [ - "/build/assets/main-e664f4b5.js" + "/build/assets/main.js" ], "legacy": false, "preload": [ - "/build/assets/vue-2d05229a.js", - "/build/assets/react-2d05228c.js" + "/build/assets/vue.js", + "/build/assets/react.js" ] } }, "legacy": false, "metadatas": {}, - "viteServer": false + "viteServer": null } \ No newline at end of file diff --git a/tests/fixtures/entrypoints/basic-dev/entrypoints.json b/tests/fixtures/entrypoints/basic-dev/entrypoints.json index 9e27575..bcb98ab 100644 --- a/tests/fixtures/entrypoints/basic-dev/entrypoints.json +++ b/tests/fixtures/entrypoints/basic-dev/entrypoints.json @@ -1,4 +1,5 @@ { + "base": "/build/", "entryPoints": { "app": { "js": [ @@ -13,8 +14,5 @@ }, "legacy": false, "metadatas": {}, - "viteServer": { - "origin": "http://127.0.0.1:5173", - "base": "/build/" - } + "viteServer": "http://127.0.0.1:5173" } \ No newline at end of file diff --git a/tests/fixtures/entrypoints/config1-build/entrypoints.json b/tests/fixtures/entrypoints/config1-build/entrypoints.json new file mode 100644 index 0000000..b4e8737 --- /dev/null +++ b/tests/fixtures/entrypoints/config1-build/entrypoints.json @@ -0,0 +1,28 @@ +{ + "base": "/build-config1/", + "entryPoints": { + "app-1": { + "assets": [], + "css": [], + "dynamic": [], + "js": [ + "/build-config1/assets/app-1.js" + ], + "legacy": false, + "preload": [] + }, + "theme-1": { + "assets": [], + "css": [ + "/build-config1/assets/theme-1.css" + ], + "dynamic": [], + "js": [], + "legacy": false, + "preload": [] + } + }, + "legacy": false, + "metadatas": {}, + "viteServer": null +} \ No newline at end of file diff --git a/tests/fixtures/entrypoints/config1-dev/entrypoints.json b/tests/fixtures/entrypoints/config1-dev/entrypoints.json new file mode 100644 index 0000000..f01c65b --- /dev/null +++ b/tests/fixtures/entrypoints/config1-dev/entrypoints.json @@ -0,0 +1,18 @@ +{ + "base": "/build-config1/", + "entryPoints": { + "app-1": { + "js": [ + "http://127.0.0.1:5173/build-config1/assets/app-1.js" + ] + }, + "theme-1": { + "css": [ + "http://127.0.0.1:5173/build-config1/assets/theme-1.scss" + ] + } + }, + "legacy": false, + "metadatas": {}, + "viteServer": "http://127.0.0.1:5173" +} \ No newline at end of file diff --git a/tests/fixtures/entrypoints/config2-build/entrypoints.json b/tests/fixtures/entrypoints/config2-build/entrypoints.json new file mode 100644 index 0000000..6720c31 --- /dev/null +++ b/tests/fixtures/entrypoints/config2-build/entrypoints.json @@ -0,0 +1,28 @@ +{ + "base": "/build/", + "entryPoints": { + "app-2": { + "assets": [], + "css": [], + "dynamic": [], + "js": [ + "/build-config2/assets/app-2.js" + ], + "legacy": false, + "preload": [] + }, + "theme-2": { + "assets": [], + "css": [ + "/build-config2/assets/theme-2.css" + ], + "dynamic": [], + "js": [], + "legacy": false, + "preload": [] + } + }, + "legacy": false, + "metadatas": {}, + "viteServer": null +} \ No newline at end of file diff --git a/tests/fixtures/entrypoints/config2-dev/entrypoints.json b/tests/fixtures/entrypoints/config2-dev/entrypoints.json new file mode 100644 index 0000000..8c5317d --- /dev/null +++ b/tests/fixtures/entrypoints/config2-dev/entrypoints.json @@ -0,0 +1,18 @@ +{ + "base": "/build-config2/", + "entryPoints": { + "app-2": { + "js": [ + "http://127.0.0.1:5174/build-config2/assets/app-2.js" + ] + }, + "theme-2": { + "css": [ + "http://127.0.0.1:5174/build-config2/assets/theme-2.scss" + ] + } + }, + "legacy": false, + "metadatas": {}, + "viteServer": "http://127.0.0.1:5174" +} \ No newline at end of file diff --git a/tests/fixtures/entrypoints/duplication-build/entrypoints.json b/tests/fixtures/entrypoints/duplication-build/entrypoints.json new file mode 100644 index 0000000..e4990c8 --- /dev/null +++ b/tests/fixtures/entrypoints/duplication-build/entrypoints.json @@ -0,0 +1,34 @@ +{ + "base": "/build/", + "entryPoints": { + "app-1": { + "assets": [], + "css": [], + "dynamic": [], + "js": [ + "/build/assets/app-1.js" + ], + "legacy": false, + "preload": [ + "/build/assets/vue.js" + ] + }, + "app-2": { + "assets": [], + "css": [ + "/build/assets/app-2.css" + ], + "dynamic": [], + "js": [ + "/build/assets/app-2.js" + ], + "legacy": false, + "preload": [ + "/build/assets/vue.js" + ] + } + }, + "legacy": false, + "metadatas": {}, + "viteServer": null +} \ No newline at end of file diff --git a/tests/fixtures/entrypoints/duplication-dev/entrypoints.json b/tests/fixtures/entrypoints/duplication-dev/entrypoints.json new file mode 100644 index 0000000..799dc40 --- /dev/null +++ b/tests/fixtures/entrypoints/duplication-dev/entrypoints.json @@ -0,0 +1,23 @@ +{ + "base": "/build/", + "entryPoints": { + "app": { + "js": [ + "http://127.0.0.1:5173/build/assets/app.js" + ] + }, + "other-app": { + "js": [ + "http://127.0.0.1:5173/build/assets/other-app.js" + ] + }, + "theme": { + "css": [ + "http://127.0.0.1:5173/build/assets/theme.scss" + ] + } + }, + "legacy": false, + "metadatas": {}, + "viteServer": "http://127.0.0.1:5173" +} \ No newline at end of file diff --git a/tests/fixtures/entrypoints/legacy-build/entrypoints.json b/tests/fixtures/entrypoints/legacy-build/entrypoints.json index a9dcdb9..12c6d16 100644 --- a/tests/fixtures/entrypoints/legacy-build/entrypoints.json +++ b/tests/fixtures/entrypoints/legacy-build/entrypoints.json @@ -1,11 +1,12 @@ { + "base": "/build/", "entryPoints": { "app-legacy": { "assets": [], "css": [], "dynamic": [], "js": [ - "/build/assets/app-legacy-59951366.js" + "/build/assets/app-legacy.js" ], "legacy": false, "preload": [] @@ -15,19 +16,19 @@ "css": [], "dynamic": [], "js": [ - "/build/assets/app-23802617.js" + "/build/assets/app.js" ], "legacy": "app-legacy", "preload": [] }, "theme-legacy": { "assets": [ - "/build/assets/topography-303b8303.svg" + "/build/assets/topography-svg" ], "css": [], "dynamic": [], "js": [ - "/build/assets/theme-legacy-de9eb869.js" + "/build/assets/theme-legacy.js" ], "legacy": false, "preload": [] @@ -35,7 +36,7 @@ "theme": { "assets": [], "css": [ - "/build/assets/theme-5cd46aed.css" + "/build/assets/theme.css" ], "dynamic": [], "js": [], @@ -47,7 +48,7 @@ "css": [], "dynamic": [], "js": [ - "/build/assets/polyfills-legacy-40963d34.js" + "/build/assets/polyfills-legacy.js" ], "legacy": false, "preload": [] @@ -55,5 +56,5 @@ }, "legacy": true, "metadatas": {}, - "viteServer": false + "viteServer": null } \ No newline at end of file diff --git a/tests/fixtures/entrypoints/metadata-build/entrypoints.json b/tests/fixtures/entrypoints/metadata-build/entrypoints.json index d3aacf6..29853c0 100644 --- a/tests/fixtures/entrypoints/metadata-build/entrypoints.json +++ b/tests/fixtures/entrypoints/metadata-build/entrypoints.json @@ -1,11 +1,12 @@ { + "base": "/build/", "entryPoints": { - "pageVue": { + "app": { "assets": [], "css": [], "dynamic": [], "js": [ - "http://cdn.with-cdn.symfony-vite-dev.localhost/assets/pageVue-bda8ac3b.js" + "/build/assets/app.js" ], "legacy": false, "preload": [] @@ -13,9 +14,9 @@ }, "legacy": false, "metadatas": { - "http://cdn.with-cdn.symfony-vite-dev.localhost/assets/pageVue-bda8ac3b.js": { - "hash": "sha256-qABtt8+MbhDq8dts7DSJOnBqCO1QbV2S6zg24ylLkKY=" + "/build/assets/app.js": { + "hash": "sha256-XYZ" } }, - "viteServer": false + "viteServer": null } \ No newline at end of file