How to update a product in Laravel 5.8 - laravel

I have a product that I want to edit. Please see the following code.
public function update(ProductRequest $request, Product $product)
{
$product->user_id = auth()->user()->id;
$product->title = $request->title;
$product->body = $request->body;
$product->price = $request->price;
if ($request->has('image')) {
$image = $request->file('image');
$filename = $image->getClientOriginalName();
$image->move(public_path('images/products'), $filename);
$product->image = $request->file('image')->getClientOriginalName();
}
$product->update();
$product->categories()->sync($request->category);
return redirect()->route('products.index');
}
product.blade.php
<form class="form-horizontal" action="{{ route('products.update', $product->id) }}" method="post" enctype="multipart/form-data">
{{ csrf_field() }}
{{ method_field('PATCH') }}
.
.
.
Everything changes except the image. I tried it, but, I did not succeed. What's the solution? I want to update the image in the database.
OK, I go to database now, I changed in image to picture, then I go my project, and I tested this again.
But it did not event for me.
I changed
public function update(ProductRequest $request, Product $product)
To
public function update(Request $request, Product $product)

To update a model, you should retrieve it, set any attributes you wish to update, and then call the save method. See the updates section in the documentation.
public function update(ProductRequest $request, Product $product)
{
$product->user_id = auth()->user()->id;
$product->title = $request->title;
$product->body = $request->body;
$product->price = $request->price;
if ($request->has('image')) {
$image = $request->file('image');
$filename = $image->getClientOriginalName();
$image->move(public_path('images/products'), $filename);
$product->image = $request->file('image')->getClientOriginalName();
}
$product->save();
$product->categories()->sync($request->category);
return redirect()->route('products.index');
}
Update 1
Assuming you have debugged the above and $request->file('image')->getClientOriginalName() is returning the expected value, it's possible that you are using field whitelisting on your model and haven't added the image field to the whitelist. Make sure that image is in the $fillable array on your model.
class Product extends Model
{
protected $fillable = [
'user_id',
'title',
'body',
'price',
...
'image'
];
Update 2
If $request->file('image') is returning null then that would suggest your form is not submitting the files. Ensure your <form> element has the enctype="multipart/form-data" attribute included in the tag.
Update 3
If your already including the required enctype="multipart/form-data" tags in the <form> element then I would suggest doing the following.
Place dd($request->all()); at the top of your update(ProductRequest $request, Product $product) method. Post the form and check the output.
If the file is not included in the output, change from using ProductRequest $request to the default Request $request (Illuminate\Http\Request) and try it again. There could be something in your ProductRequest class that is causing a problem.
As a small critique, you could improve your code in the following ways.
・Use hasFile() instead of has().
・Use $product-image = $filename instead of $product->image = $request->file('image')->getClientOriginalName();.
public function update(ProductRequest $request, Product $product)
{
$product->user_id = auth()->user()->id;
$product->title = $request->title;
$product->body = $request->body;
$product->price = $request->price;
if ($request->hasFile('image')) {
$image = $request->file('image');
$filename = $image->getClientOriginalName();
$image->move(public_path('images/products'), $filename);
$product->image = $filename;
}
$product->save();
$product->categories()->sync($request->category);
return redirect()->route('products.index');
}

make sure your has
enctype="multipart/form-data"
property

Related

I am getting this error while want to update in the database

Missing required parameter for [Route: blog.update] [URI: blog/{post}/update] [Missing parameter: post].
in routes :
Route::put('/blog/{post}/update', [BlogController::class, 'update'])->name('blog.update');
in BlogController :
`
public function update(Request $request,Post $post){
$request->validate([
'title' => 'required',
'image' => 'required | image',
'body' => 'required'
]);
$postId = $post->id;
$title = $request->input('title');
$slug = Str::slug($title,'-').'-'.$postId;
// $user_id = Auth::user()->id;
$body = $request->input('body');
//File upload
$imagePath = 'storage/'. $request->file('image')->store('postImages','public');
// $post = new Post();
$post->title = $title;
$post->slug = $slug;
// $post->user_id = $user_id;
$post->body = $body;
$post->imagePath = $imagePath;
$post->save();
return redirect()->back()->with('status', 'Post edited successfully');
dd('validation passed . You can request the input');
}
`
Please solve this issue
I want to update the post
If you are using the route() helper in your form. You can pass the parameter using it :
<form action="{{ route('blog.update', ['post' => $post_id]) }}">...</form>
which is the post is the parameter you name in the route.
Since you haven't posted your blade file so here's the full method:
in your route:
Route::put('/blog/{post}/update' , [BlogController::class, 'update']);
in your blade form make tag like this:
<form method="post" action="/blog/{{$post->id}}/update">
//This will show url like /blog/1/update
//For using PUT method add this:
{{ method_field('PUT') }}
// Do not forget to use #csrf
Then in your controller update function handle the request and $id like this:
public function update(Request $request, $id){
//Find post in your data with help of model
$post = \App\Models\Post::findOrFail($id);
//validate and update with the post instance of Post class
//Feel free to add many functions same as of your controller before i'm leaving empty
$post->update([
//Add fields for update
]);
}

How to update product image using polymorphic relaitonship

This is my update method. I'm using simple polymorphic relation morphTo() and morphOne(). I'm having trouble in updating Product model.
public function update(Request $request, Product $product)
{
$product->name = $request->name;
$product->price = $request->price;
$product->discount = $request->discount;
$product->category_id = $request->category;
$product->brand_id = $request->brand;
$product->is_active = $request->is_active;
if($request->hasFile('url')) {
$image = $request->file('url');
$filename = $image->getClientOriginalName();
$image->move(public_path('storage/products'), $filename);
$product->image->url = $request->file('url')->getClientOriginalName();
// dd($product->image->url);
}
$product->save();

I want to use images of products that I register in the database - Laravel

I programmed a product registration. The registration for the database is working correctly. My problem is that I can't show the images that I registered in the database. I created an imput where the name of the image is inserted. This name is saved in the database and the image is saved with the same name, however it is saval in public. The images are inside the public / storage / products folder.
Controller:
public function index()
{
$products = Product::paginate(10);
return view('products.index', [
'products' => $products,
]);
}
public function store(Request $request)
{
// Create registration
$data = $request->only('name', 'price', 'imageName');
Product::create($data);
// Image
if($request->file('imageProduct')->isValid()){
$nameFile = $request->imageName . '.' . $request->file('imageProduct')->getClientOriginalExtension();
$request->file('imageProduct')->storeAs('products', $nameFile);
return redirect()->route('ProductControllerIndex');
}
}
view:
<div>
#foreach ($products as $product)
<p>
Id: {{ $product->id }}
</p>
<p>
Nome do produto: {{ $product->name }}
</p>
<p>
Preço: {{ $product->price }}
</p>
<p>
{{ $product->imageName }}
</p>
<p>
<img src="{{ asset('storage/products/'.$product->imageName) }}" alt="">
</p>
<hr>
#endforeach
</div>
The core issue here is that your Image's extension is not being saved to the database, so $product->imageName, when used in the asset() helper, doesn't generate a complete URL for the image. You'll need to refactor your code a little to get it to save:
public function store(Request $request) {
$nameFile = $request->input('imageName', '');
if($request->file('imageProduct')->isValid()){
$nameFile .= '.' . $request->file('imageProduct')->getClientOriginalExtension();
$request->file('imageProduct')->storeAs('products', $nameFile);
}
$request->merge(['imageName' => $nameFile]);
$data = $request->only('name', 'price', 'imageName');
Product::create($data);
return redirect()->route('ProductControllerIndex');
}
In the above code, the value for $nameFile is defaulted to the value in $request->input('imageName'), or an empty string '' if nothing is supplied. Next, if a valid image is uploaded, the $nameFile variable is appended with the extension. Lastly, the $request variable is updated with the name value for imageName. The remainder of the code creates the new Product with the data supplied (using the ->only() modifier) and redirect as required.
The rest of your code should be ok, as long as the file exists in the correct directory after ->storeAs() and the fully-qualified image name is saved to the database.
Note: If for whatever reason Product::create() doesn't work with this approach, you can use the new Product() ... $product->save() approach: (there might be an issue with $request->merge() using an existing key, as I can't actually test that)
$product = new Product();
$product->name = $request->input('name');
$product->price = $request->input('price');
$product->imageName = $fileName;
$product->save();

Laravel upload multiple files

I'm building a gallery with multiple files functionality.
So far I'm having two issues, but let's paste my code first.
Controller:
public function store(Request $request)
{
$gallery = new GalleryImage();
if($request->hasFile('image')) {
$images = $request->file('image');
foreach($images as $image) {
$path = $image->getClientOriginalName();
$name = time() . '-' . $path;
$gallery->image = $image->move(public_path().'/uploads/temp/', $name);
//$gallery->image = $request->file('image')->storeAs('public/gallery-images', $name);
}
}
$gallery->gallery_id = $request->gallery_id;
$gallery->save();
return back()->with('success_message','Images has been uploaded!');
}
View blade:
<form action="{{ route('gallery-images.store') }}" method="POST" enctype="multipart/form-data">
{{ csrf_field() }}
<div class="form-group">
<input type="hidden" name="gallery_id" value="{{ $gallery->id }}">
<input type="file" name="image[]" id="id_imageGallery" class="form-control" multiple="multiple" required>
</div>
<div class="form-group">
<button type="submit" class="btn btn-primary">Upload</button>
</div>
</form>
My first issue when I have my code like this and upload three files, it's successfully storing the files into /uploads/temp directory, but in my database I can see there's only one image uploaded, instead of three.
My second issue is when I change my code and use the commented part (because I want to store those three images into Storage):
$gallery->image = $request->file('image')->storeAs('public/gallery-images', $name);
I'm getting this error:
Call to a member function storeAs() on array
How can I upload those multiple images into the Storage folder and record them all into the database?
-- EDIT --
I've solved my first issue!
I've simply put the save method and other details inside the loop. I've should have thought about this before :)
Here's my updated code:
public function store(Request $request)
{
if($request->hasFile('image')) {
$images = $request->file('image');
foreach($images as $image) {
$gallery = new GalleryImage();
$path = $image->getClientOriginalName();
$name = time() . '-' . $path;
$gallery->image = $image->move(public_path().'/uploads/temp/', $name);
//$gallery->image = $request->file('image')->storeAs('public/gallery-images', $name);
$gallery->gallery_id = $request->gallery_id;
$gallery->save();
}
}
return back()->with('success_message','Images has been uploaded!');
}
Now only thing to do is how to store them into File Storage, instead of the public_path and avoid that error:
Call to a member function storeAs() on array
I've finally solved the issues and I'm posting it, so it may be useful for some.
Here's my code:
public function store(Request $request)
{
if($request->hasFile('image')) {
foreach($request->image as $image) {
$path = $image->getClientOriginalName();
$name = time() . '-' . $path;
$gallery = new GalleryImage();
$gallery->image = $image->storeAs('public/gallery-images', $name);
$gallery->gallery_id = $request->gallery_id;
$gallery->save();
}
}
return back()->with('success_message','The images have been uploaded!');
}
Try to implement using the following code, it will give uploaded files url in serialized format
public static function upload_file($file){
$file_name = time();
$file_name .= rand();
$file_name = sha1($file_name);
if ($file) {
$ext = $file->getClientOriginalExtension();
$file->move(public_path() . "/uploads", $file_name . "." . $ext);
$local_url = $file_name . "." . $ext;
$s3_url = url('/').'/uploads/'.$local_url;
return $s3_url;
}
return "";
}
public static function upload_multiple_files($files){
if(is_array($files)){
$return_array = array();
foreach ($files as $file){
if(!empty($file)){
$return_array[] = self::upload_file($file);
}else{
$return_array[] = '';
}
}
return serialize($return_array);
}else{
return NULL;
}
}
//I have updated and commented your code. Try it, It should work.
public function store(Request $request)
{
if($request->hasFile('image')) {
$images = $request->file('image');
foreach($images as $image) {
$gallery = new GalleryImage();
// laravel auto manages unique name and extension of file.
$gallery->image = $image->store('gallery-images', 'public');
$gallery->gallery_id = $request->gallery_id;
$gallery->save();
}
}
return back()->with('success_message','Images has been uploaded!');
}

How to automatic slug when i press the submit button

I want to create slug by using value of $item->name = $request->input('name'); before $item->save();
//use Illuminate\Support\Str;
private function saveItem(Request $request, $item){
$item->name = $request->input('name');
$item->slug = Str::title($item->name,"-");
$item->save();
}
When the $item->name = $request->input('name') value is Hello World,
Then after slug the output will be Hello-World
Please help.
You can generate a slug using the Str::slug() method:
private function saveItem(Request $request, $item){
$item->name = $request->input('name');
$item->slug = Str::slug($item->name);
$item->save();
}

Resources