How do I delete an image from the public using a form?

Viewed 63

I programmed a product registration and together with it, I upload an image. This image is saved to public / storage / products. There is an input field that is to put the name of the image and the image is given this name and that name is saved in the database along with the image extension. I want to know how I delete this image from the public / storage / products folder when I click remove.

The method I tried below, didn't work Controller:

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);
    }

    $product = new Product();

    $product->name = $request->input('name');
    $product->price = $request->input('price');
    $product->imageName = $nameFile;

    $product->save(); 

    return redirect()->route('ProductControllerIndex');
}

public function destroy($id)
{   
    $products = Product::all();
    $filePathName = 'products/' . $products->imageName;
    if( file_exists($filePathName) ){
        unlink($filePathName);
    }
    // $delete = Product::find($id);
    // if(!$delete)
    //     return redirect()->route('ProductControllerCreate');
    
    // $delete->delete();
    // return redirect()->route('ProductControllerCreate');
}

}

view:

<form action="{{ route('ProductControllerDestroy', $product->id) }}" method="post">
   @csrf
   @method('DELETE')

   <input type="submit" value="Remover">
</form>
4 Answers

You have add public path there. check below code.

    $product = Product::find($id);
    $filePathName = public_path().'/products/'. $products->imageName;
    if( file_exists($filePathName) ){
        unlink($filePathName);
    }

The storeAs function stores the files inside /storage/public Also in your destroy method you're calling ->imageName on the products collection, you haven't find the product by it's id

so to delete the image the distroy method would look something like this

First you add use Illuminate\Support\Facades\Storage; at the very top of the controller then you add this destroy method

public function destroy($id)
{   
    $product = Product::find($id);
    Storage::delete('publuc/prodcuts/' . $product->imageName);
}

In your destroy method,

$products = Product::all();
$filePathName = 'products/' . $products->imageName;
if( file_exists($filePathName) ){
    unlink($filePathName);
}

If you are using all() then it will return an object with keys for multiple values(you can use dd($products); to check the object sent), thus you need a for loop to iterate through it.

$products = Product::all();
foreach($products as $product){
    $filePathName = 'products/' . $product->imageName;
    if( file_exists($filePathName) ){
        unlink($filePathName);
    }
}

If you want to access only the first value only (or will always have one value) then you can use this

$products = Product::first();
$filePathName = 'products/' . $products->imageName;
if( file_exists($filePathName) ){
    unlink($filePathName);
}

You have to change like this.

use use File; at the top.

public function destroy($id){ 

    $product = Product::find($id);
    $filePathName = public_path().'products/' . $product->imageName;

    if(File::exists($filePathName)){
        File::delete($filePathName);
    } 
}
Related