Error if not clearing cache after deployment - php

In my Laravel app, I sometimes want to pull the latest version from GitHub without clearing the cache first.
So I just do:
git pull origin staging
But every time I do this and then open the page in the browser, I get this error:
ErrorException (E_WARNING)
file_put_contents(/path/to/laravel/storage/framework/cache/data/30/6c/306cbe845aa9840ab0c14a1cd4b5d83fd6728839): failed to open stream: Permission denied
However, if I just do php artisan cache:clear this issue doesn't happen.
This isn't ideal because I'd sometimes like to keep the cache when I pull changes from Git. We use caching extensively (on every request) and it's a performance issue if we have to clear it on every update.
For example, the last time this happened, my only change was to a View file. No need to mess with the existing cache.
How can I pull changes from Git without clearing the cache and without encountering errors?

My storage folder lives outside the laravel folder. That way I can keep the cache and log files when I update my project.
For this I'm using a custom app where the storage path is defined in the .env.
<?php
namespace App;
use Illuminate\Foundation\Application;
class CustomApp extends Application
{
public function __construct($basePath = null)
{
parent::__construct($basePath);
$this->afterLoadingEnvironment(function () {
$this->useStoragePath(env('STORAGE_PATH', storage_path()));
});
}
}

The issue may be someone committed a logfile into the repository. Follow these
Give Permission to storage file.
Navigate to project folder in terminal
And run chmod -R 755 storage/*
check .gitignore contains /storage/logs path.
Not only on your side on everyone who works in the same repository.

Related

Uncaught Exception: Unable to locate Mix file

I am trying to run a laravel app in my local system. I have followed the https://gist.github.com/hootlex/da59b91c628a6688ceb1 link. I run the command php artisan serve command, and when I browse it, then produces the error
PHP Fatal error: Uncaught Exception: Unable to locate Mix file: /css/vendor.css. Please check your webpack.mix.js output paths and try again. in /var/www/html/laravel-app/app/helpers.php:439
In the specified line of helpers.php, it has
if (! isset($manifest[$path])) {
throw new Exception(
"Unable to locate Mix file: {$path}. Please check your ".
'webpack.mix.js output paths and try again.'
);
}
public/mix-manifest.json
{
"/mix.js": "/mix.js"
}
I couldn't sort it out. Please help. Thanks
The blade file you're loading obviously has mix('/css/vendor.css') call. You either comment out this line(s) or install npm then build your assets.
Your manifest file doesn't have /css/vendor.css but if you check your blade files (views) you'll see you are calling mix('/css/vendor.css'). So if you find and comment out this line(s) your problem will be solved.
Ideally, mix() is used for loading assets that were built by webpack. It will then take care of the versioning string for you. How mix can be used is detailed in the documentation. I will refrain myself from discussing that here.
You've built your assets by running npm run dev or similar commands. And then the manifest file doesn't contain those assets mapping. And your public directory doesn't have those assets as well. Then it's safe to assume that you can remove those mix calls from your blade (views) files.
If you have the assets built in your public directory then you can load those assets by assets function.
Lastly, you should know your assets first, before loading them to your site. I get the notion that you don't have any clue where those assets came from, so you shouldn't load them in the first place.
This happened with me and after spending quite some time and effort, I did manage to figure out what was happening and how to fix it.
Here's what happens:
You update your webpack.mix.js file with the destination where you wish to publish your compiled JS and CSS files respectively.
mix.js('resources/js/app.js', 'public/js').vue();
Mix compiles and stores the hence generated CSS and JS files within their respective destination folders when you run npm run dev or npm run watch.
laravel-app (Your laravel app root folder)
\public
\css
\app.css
\js
\app.js
When you open the application in your browser with, say Valet, Laravel spits out the following error message:
Unable to locate Mix file: /js/app.js
(or)
Unable to locate Mix file: /css/app.css
Something worth noting on the Uncaught Exception screen though, is that Laravel by default attempts to look for the files at localhost:8080. Implied that Laravel is looking for the files respectively at:
localhost:8080\css\app.css
(and)
localhost:8080\js\app.js
Hence, if your hostname or port is anything other than localhost:8080, Laravel would not be able to find your files. For example, if you're using Valet, your default URL would become laravel-app.test where laravel-app is the name of your app's root folder.
But, there's a way to fix this. And it comes directly out to Laravel's documentation.
Solution (TL;DR)
In order to use a custom mix base URL, you would require to update your config\app.php file to add the following configuration value for setting the mix URL:
'mix_url' => env('MIX_ASSET_URL', 'localhost'),
With your mix_url config option set in your app.php file, you should now be able to manipulate it by adding the MIX_ASSET_URL key in your .env file and setting it to blank, so that it points to \public\js\app.js and \public\css\app.css respectively, within your project directory.
MIX_ASSET_URL=""
That solved it for me. Hope it does it for your too. Lemme know how it goes. Cheers!
Try running npm install and after that build the assets, either npm run dev or npm run watch , depends on what you are using.
In my case,
laravel 9
I should have changed the mix-manifest.json file
"/js/application.js": "/js/application.js",
"/js/admin.js": "/js/admin.js",
"/css/application.css": "/css/application.css",
"/css/admin.css":"/css/admin.css"
Delete package-lock.json.
Delete folder 'node_modules' and run 'npm install' to reinstall all modules.
Then run 'npm run watch' or 'npm run production'.
That helps me to fix that problem.
check the package.json file for the command to build the scripts and styles, normally you will have by default: npm run dev. Might happen that you will need to run:
npm rebuild node-sass
npm run dev or npm run watch
I changed my webpack.mix.js files and made these changes there and worked. Only define the specific path to public/js/app.js in webpack.mix.js
mix.js(
[
"resources/assets/js/jquery.js",
"resources/assets/js/popper.js",
"resources/js/app.js",
],
"public/js/app.js"
)
.autoload({
jquery: ["jquery", "jQuery", "$", "window.jQuery"],
Popper: ["popper", "Popper", "popper.js"],
popper: ["Popper", "popper.js"],
})
.vue()
.postCss("resources/css/app.css", "public/css", [])
.sass("resources/sass/app.scss", "public/css")
.disableNotifications(); // to disable notifications of building app;
In My case, I change
'debug' => false, to true
in the file app.config under config folder in my project to see log in my browser. Then when I run my project got error above like you. then I change to
'debug' => false again. It works.

Move Laravel to another server error

I am trying to move a laravel project to a new server. Before moving on to the new server I am testing it on localhost.
I am getting the error like this: file_put_contents(/megashopping_dk_files/storage/framework/views/d2f79fe2bf4361439b4c43509087ad6167dfffd9.php): failed to open stream: No such file or directory
The original path in config.php was
0 => '/var/zpanel/hostdata/zadmin/public_html/megashopping_dk_files/resources/views',
which I have changed to
0 => '/megashopping_dk_files/resources/views',
I have already deleted all the files in the folders cache sessions and views in storage/framework
Again I have got two root folders with file structure like this:
1st root Folder - megashopping_dk
backend
compaign
css
fonts
img
js
library
....
2nd Root Folder - megashopping_dk_files
app
bootstrap
config
database
public
resources
storage
....
From the above what I understand is that the
contents of the First Root Folder should go in the root
and the contents of the second Root Folder should go alongwith the folder in contains.
Please advise me the right path?
TRY chmod -R guo+w storage
Few explanations
chmod -R guo+w storage : Whenever we add new service provider the cache folder for that service provider will be created in inside storage/framework . we need to make them writable from our application
php artisan optimize : to reuse all frequently used classes php will make an cached class in cache/service.php. So we if add new service we need to run it. We need to use it whenever we add new dependency without using composer.
php artisan cache:clear : clear all the above cache and remap everything
For more information read https://sentinelstand.com/article/laravel-5-optimization-commands
Remove the cached data. Go to storage\framework and remove all the files in sessions, cache and views
Once you are done with that, give proper permissions to your storage folder recursively.

Laravel, dump-autoload without Shell Access

I have two controllers with the same name:
app\controllers\CareersController.php (for public use)
app\controllers\Admin\CareersController.php (for admins)
Because of the naming conflict, I added namespace admin; to the admin controller.
Everything works fine locally but when I uploaded the new admin controller to my server, I get an error: Class Admin\CareersController does not exist
From what I understand, the fix is:
php artisan dump-autoload
and composer dump-autoload
However, I don't have Shell access to run those commands and composer isn't installed on the server anyway. So, is there a way to reload the auto-load file without Shell access?
Run composer dump-autoload locally. Then, in your hosting site,
you can update two files, autoload_classmap.php and autoload_static.php, manually in vendor/composer folder. I prefer to copy and paste the added classes from local to the hosting server.
You dont need shell access. Artisan includes a dump-autoload function. You can just it via a PHP call within your app:
Route::get('/updateapp', function()
{
\Artisan::call('dump-autoload');
echo 'dump-autoload complete';
});
Edit: just noticed you wrote "composer isn't installed on the server anyway". Not sure what will happen - try the command above and let us know.
If it doesnt work - then just run composer dump-autoload locally - then upload your new autoload.php.
As a side point - is there any option to switch servers? You going to keep running into various issues if you dont have command line & composer access. You could just use Forge and spin up a new server on DigitalOcean, Linode etc in less time than it would take to fix this issue :)
I was using a shared hosting by client's requirements and did not have access to ssh or composer, what I did was to composer dump-autoload on my local machine and then I figured that for my project autoloader just updates composer directory in my vendor directory, so I just re-uploaded that one folder after each dump-autoload and not all vendor directory
Edit:
Another pitfall for me that generated the same error but the cause was something else, I develop on Windows machine in which file and directory names are case insensitive when deploying to Linux server, the framework could actually not find my controllers so I changed
Route::get('/news', 'newsController#index');
to
Route::get('/news', 'NewsController#index');
now it is working, autoload is doing it's job correctly

OpsWorks / Chef PHP deploy process

I'm having some serious frustration getting a simple PHP application to deploy reliably using OpsWorks, I can't find any documentation of how the srv/www/app-name/releases directory is managed, but I think that may been the cause of my current problem.
I'm deploying a Laravel application, so I need two things to happen with chef recipes on deploy: composer install, and some directories to be made writable. Composer does seem to be installing fine, but my recipe to create & chmod the directories seems to happen to the previous release - which makes no sense to me at all.
Install composer:
node[:deploy].each do |application, deploy|
script "composer-install" do
interpreter "bash"
cwd "#{deploy[:deploy_to]}/current"
user "root"
code <<-EOH
composer install
EOH
end
end
This works fine, I can refresh the vendor directory as this runs see the dependencies appearing. But the next recipe to run:
node[:deploy].each do |application, deploy|
Chef::Log.info("Application path: #{deploy[:deploy_to]}");
node['directories'].each do |path|
# Get the path we need
new_path = "#{deploy[:deploy_to]}/current/"+path
Chef::Log.info("Checking directory: "+new_path);
# Ensure the dir exists
unless File.exists?(new_path)
Chef::Log.info("Creating directory: "+new_path);
Dir.mkdir( new_path, 777 )
end
# Ensure its writable
File.chmod( 777, new_path )
end
end
The content from Chef::log does appear in the log, there are no errors, but the directories are simply not there - they are created in the PREVIOUS release/timestamp directory, as if the 'current' symlink has reverted back for the duration of this recipe. They are also created with permissions '411'.
Can anyone explain where I'm going wrong here?
Can I access the new directory path instead of using the 'current' symlink?
What is very likely happening is that you're applying these two specified recipes at different stages of the deployment. Since you're using Current - it will be at one stage the old directory, while checking out the next part of the application.
What you should be maybe doing instead is :
use the "#{release_path}" variable in your recipes to generate build specific files/events in your app.
use the deploy/before_restart.rb file to execute some symlinks that provide the files at a predictable location
If you provide screenshot of the recipes that are being called and on what layer from the layer edit view, it will help people here to see what is happening and give you a better feedback.

Laravel 4 - class not found on live server

I'm uploading my laravel 4 app to a testing server which is shared hosting.
I'm uploading to a password protected directory which has a .htaccess file within it. My subdomain points to the public folder.
For the most part they app is working as expected I can log in, view most of the pages however every class that I have created such as a helper class and additional controllers are not being found on the live server yet all works on my local environment.
I've redone a composer dump-autoload and uploaded the composer.json file
I'm not sure where to start with this.
In my upload I've included all the files and folders to the live server (twice now). I read somewhere else I should namespace my classes but why would this help if the main laravel controllers do not namespace?
Confused - all help appreciated
When you do a composer update, if Composer finds anything new it will update some files in the folder
vendor/composer
Like the file autoload_classmap.php.
So, you have to reupload at least this folder too.
Maybe it's about git, you are pushing changings with some certain case sensitive Folders and Files, but git is changing this therefore it will work on Mac and Windows OSs but not on the server.
just use this command:
git config core.ignorecase false
above command for the current repository and you may add --global just after config keyword.
please note that ignorecase option available since version 1.5.6 and I assume you are running 2.0.x but just mentioning!

Categories