I'm trying to load a external JSON file into my laravel application. Below you will find a snippet of my code.
$location = __DIR__.'/config.json';
echo $location; // Results in correct file location
echo File::exists($location); // Return 1
echo Storage::get($location); // Throws a FileNotFound Exception
How can the File::exists() method return true and the Storage::get() throw an exception?
My config/filesystems.php file:
<?php
return [
'default' => env('FILESYSTEM_DRIVER', 'local'),
'cloud' => env('FILESYSTEM_CLOUD', 's3'),
'disks' => [
'local' => [
'driver' => 'local',
'root' => storage_path('app'),
],
'public' => [
'driver' => 'local',
'root' => storage_path('app/public'),
'url' => env('APP_URL').'/storage',
'visibility' => 'public',
],
's3' => [
'driver' => 's3',
'key' => env('AWS_ACCESS_KEY_ID'),
'secret' => env('AWS_SECRET_ACCESS_KEY'),
'region' => env('AWS_DEFAULT_REGION'),
'bucket' => env('AWS_BUCKET'),
],
],
];
Why use the Storage class for this? That class is specifically for accessing the storage folder or external file servers. You stored your file right next to your controller/code, so it's probably easier to do it the old-fashioned way.
$location = __DIR__.'/config.json';
if (File::exists($location)) {
$string = file_get_contents($location);
$json = json_decode($string, true);
// logic
} else {
// Do something
}
You can try accessing it through the file facade by
File::get($location);
The error is probably because Storage is trying to access the file from its default path (./project/storage/app) plus what you send it. My best advice, is to add a new disk
like this
// config/filesystems.php
'customDrive' => [
'driver' => 'local',
'root' => base_path(), // here put your full path
],
and acess it through
Storage::disk("customDrive")->get("config.json");
Source https://laravel.com/docs/5.6/filesystem
Related
In the following route, inspecting the image paths that this method returns, they all have "/categories/" at the start but this is not right, the actual path should be /public/images/categories/gallery/1 not /public/categories/images/categories/gallery/1
Route::get('/categories/{group:id}', function (Group $group) {
$images = Storage::disk('public_path')->files('images/categories/gallery/' . $group->id);
return view('categories.index', ['group' => $group], compact('images'));
})->name('categories');
The following is an example of a route where it actually gets the correct paths
Route::get('/news', function () {
$categories = Category::get();
$images = Storage::disk('public_path')->files('images/news/gallery');
return view('news', ['categories' => $categories], compact('images'));
})->name('news');
So my question is, why is it in the previous route, it returns the incorrect path with /categories/ attached to the start but not in the one above, also how do I get the correct path in the first code example posted.
I tried changing the route to Route::get('/{group:id}', function ... etc and it works but I won't be able to use that because the url subdir will just be a number.
I also tried adding a forward slash to the path in the files() method so it was ->files('/images/categories/gallery/1'); but it still appends /categories/ to the start.
This is the config for the method in filesystems.php
'disks' => [
'local' => [
'driver' => 'local',
'root' => storage_path('app'),
],
'public' => [
'driver' => 'local',
'root' => storage_path('app/public'),
'url' => env('APP_URL').'/storage',
'visibility' => 'public',
],
'public_path' => [
'driver' => 'local',
'root' => public_path(''),
],
's3' => [
'driver' => 's3',
'key' => env('AWS_ACCESS_KEY_ID'),
'secret' => env('AWS_SECRET_ACCESS_KEY'),
'region' => env('AWS_DEFAULT_REGION'),
'bucket' => env('AWS_BUCKET'),
'url' => env('AWS_URL'),
'endpoint' => env('AWS_ENDPOINT'),
],
],
The problem was not in my php but in the vue component I was using which failed to place a forward slash at the start of the src path so I changed
<source media="(min-width: 768px)" :srcset="`${image}`">
to
<source media="(min-width: 768px)" :srcset="`/${image}`">
and it works.
I'm using laravel 5.6 and i wanted to create my custom disk for uploading images
and i received this error
InvalidArgumentException Driver [] is not supported.
this is how i save file in controller
$cover = $request->file('cover_image');
$extension = $cover->getClientOriginalExtension();
Storage::disk('test')->put($cover->getFilename().'.'.$extension, File::get($cover));
this is my config/filesystems.php
'disks' => [
'local' => [
'driver' => 'local',
'root' => storage_path('app'),
],
'test' => [
'driver' => 'local',
'root' => storage_path(),
],
'public' => [
'driver' => 'local',
'root' => storage_path('app/public/asghar'),
'url' => env('APP_URL').'/storage',
'visibility' => 'public',
],
's3' => [
'driver' => 's3',
'key' => env('AWS_ACCESS_KEY_ID'),
'secret' => env('AWS_SECRET_ACCESS_KEY'),
'region' => env('AWS_DEFAULT_REGION'),
'bucket' => env('AWS_BUCKET'),
'url' => env('AWS_URL'),
],
the error occurred because my configuration was cached.
probably I accidentally used config:cache or sth similar.
the issue resolved by clearing the config cache using this command
php artisan config:clear
I have tried streaming a pdf in the browser but it still tells me i am passing a string as a parameter.
public function cv($id){
$user = new user;
$cv = $user->where('id', $id)->firstOrfail()->Publicprofile->cv_path;
return response()->file(Storage::get($cv));
}
and when i try passing in the name of the file and path it tells me file does not exist
return response()->file($cv);
here is my filesystem config settings
'disks' => [
'local' => [
'driver' => 'local',
'root' => storage_path('app'),
],
'public' => [
'driver' => 'local',
'root' => storage_path('app/public'),
'url' => env('APP_URL').'/storage',
'visibility' => 'public',
],
's3' => [
'driver' => 's3',
'key' => env('AWS_ACCESS_KEY_ID'),
'secret' => env('AWS_SECRET_ACCESS_KEY'),
'region' => env('AWS_DEFAULT_REGION'),
'bucket' => env('AWS_BUCKET'),
],
],
and here is the value the $cv variable returns
"public/cv/61520610986.pdf"
The solution required that I provide an absolute path using the
Public_path() method
ended up doing this:
public function streamCV($id){
$user = new user;
$cv = $user->where('id', $id)->firstOrfail()->Publicprofile->cv_path;
$cv ="storage". ltrim($cv, 'public');
return response()->file(public_path($cv));
}
FileSystem :
'disks' => [
'local' => [
'driver' => 'local',
'root' => storage_path('app'),
],
'public' => [
'driver' => 'local',
'root' => storage_path('app/public'),
'url' => env('APP_URL').'/storage',
'visibility' => 'public',
],
'shares' => [
'driver' => 'local',
'root' => public_path('shares'),
'visibility' => 'public',
],
's3' => [
'driver' => 's3',
'key' => env('AWS_KEY'),
'secret' => env('AWS_SECRET'),
'region' => env('AWS_REGION'),
'bucket' => env('AWS_BUCKET'),
],
],
My controller :
public function store(Request $request) {
$rules = [
'user_id' => 'required|exists:users,id',
'patient_case_id' => 'required|exists:patient_cases,id',
'shared_with' => 'required|exists:users,id',
];
$this->validate($request, $rules);
$data = $request->all();
$data['shared_file'] = $request->file('file')->store('shares/'.$data["user_id"], $data["shared_file"]->getClientOriginalName());
$newShare = WayneRooney::create($data);
return $this->showOne($newShare, 201);
}
if i leave store method empty, it works and writes file in shares folder in public path with a unique id. But i want to write file with original name under the shares/{USER_ID} folder.
how can i do this ?
If you would not like a file name to be automatically assigned to your stored file, you may use the storeAs method, which receives the path, the file name, and the (optional) disk as its arguments:
$path = $request->file('avatar')->storeAs(
'avatars', $request->user()->id
);
you may also use the putFileAs method on the Storage facade, which will perform the same file manipulation as the example above:
$path = Storage::putFileAs(
'avatars', $request->file('avatar'), $request->user()->id
);
Hope this fixed your issue!
Anyone else had this issue:
I set my filesystems.php config defualt from local to cloud (which is set to my s3) and I get this error with my storage code:
$path = $request->file('avatar')->store('avatars'); -> in my UserController
Error : Driver [] is not supported.
If I leave the filesystems config to stock and just run this code the image uploads to my s3 fine
$path = $request->file('avatar')->store('avatars', 's3'); -> in my UserController
shouldnt $path = $request->file('avatar')->store('avatars'); run to what ever the default is without passing the specific driver? I tried 'default' => 's3', and that gets the same error
CONFIG DRIVERS
'default' => 'local',
'cloud' => 's3',
'disks' => [
'local' => [
'driver' => 'local',
'root' => storage_path('app'),
],
'public' => [
'driver' => 'local',
'root' => storage_path('app/public'),
'url' => env('APP_URL').'/storage',
'visibility' => 'public',
],
's3' => [
'driver' => 's3',
'key' => env('AWS_KEY'),
'secret' => env('AWS_SECRET'),
'region' => env('AWS_REGION'),
'bucket' => env('AWS_BUCKET'),
],
],
I guess, that whether your example with manually typing a storage to the store() function works well, you can have a problem with storage config.
Could you, please, show your configuration file with storage types?