Laravel-modules: View cache

Created on 8 Oct 2018  路  7Comments  路  Source: nWidart/laravel-modules

I have a problem with caching views from modules.
Each module registers his views in Service Provider.
I tried php artisan view:cache and i get this exception:
The "/home/vagrant/Code/Projects/project/resources/views/modules/cor
e" directory does not exist.

Most helpful comment

ServiceProvider must filter nonexistent view paths when is registering views
`public function registerViews()
{
$viewPath = resource_path('views/modules/abcd');

    $sourcePath = __DIR__.'/../Resources/views';

    $this->publishes([
        $sourcePath => $viewPath
    ],'views');

    $this->loadViewsFrom(array_filter(array_merge(array_map(function ($path) {
        return $path . '/modules/abcd';
    }, \Config::get('view.paths')), [$sourcePath]), function ($path) {
        return file_exists($path);
    }), 'abcd');
}`

All 7 comments

The errors says a directory does not exist.

Of course that the directory does not exist because it is generated by the plugin. Views for this module are in "/home/vagrant/Code/Projects/project/Modules/core/resources/views"

This package does not generate anything for view cache.

Laravel handles this command so I would refer to its documentation.

I've encountered this issue, in the module service provider you'll see this:

$this->loadViewsFrom(array_merge(array_map(function ($path) { return $path . '/modules/moduleName'; }, \Config::get('view.paths')), [$sourcePath]), 'moduleName');

this register the module views, BUT, the $path does not points to the module's resources directory, the $path parameter points to the proyect (root) resources directory. Then when you try to run php artisan view:cache, the command will try to cache a view that does not exists on the registered path, so it brings this exception.

This can be solved with:

$this->loadViewsFrom(array_merge(array_map(function ($path) { return __DIR__.'/../Resources/views'; }, \Config::get('view.paths')), [$sourcePath]), 'moduleName');

But I don't know to what extends this can bring new problems to the table...

Also, in the ServiceProvider you will see something like

$this->loadViewsFrom(array_merge(array_map(function ($path) {
            return $path . '/modules/core';
        }, \Config::get('view.paths')), [$sourcePath]), 'core');

I have just changed to:
$this->loadViewsFrom(array_merge(\Config::get('view.paths'), [$sourcePath]), 'core');

Without mapping to the same value. This is the same as your code, you return the same route like you get from \Config::get('view.paths')

Edit: I realized that the issues I encountered after making the suggested edit above was because OpCache was not cleared. It was not related to symlinks/realpath().

I used the suggestions above, but am using Deployer to deploy the site. I was still having view issues until I added realpath() when setting $sourcePath due to the release symlink Deployer creates.

$sourcePath = realpath(__DIR__.'/../Resources/views');
...
$this->loadViewsFrom(array_merge(\Config::get('view.paths'), [$sourcePath]), 'core');

ServiceProvider must filter nonexistent view paths when is registering views
`public function registerViews()
{
$viewPath = resource_path('views/modules/abcd');

    $sourcePath = __DIR__.'/../Resources/views';

    $this->publishes([
        $sourcePath => $viewPath
    ],'views');

    $this->loadViewsFrom(array_filter(array_merge(array_map(function ($path) {
        return $path . '/modules/abcd';
    }, \Config::get('view.paths')), [$sourcePath]), function ($path) {
        return file_exists($path);
    }), 'abcd');
}`
Was this page helpful?
0 / 5 - 0 ratings