Nancy
Nancy

Reputation: 1051

How to perform mass delete on Laravel from Vue?

I'm trying to make a massive delete function for a website to delete a list of products at the same time. I insert the data through an excel.

Controller function

public function destroy(Request $request)
{
    ini_set('max_execution_time', 300);
    $products = $request->all();

    try {
        DB::beginTransaction();
        foreach ($products as $product) {
            $dbProduct = $this->getProduct($product['SKU']);
            Log::error($dbProduct);
            $dbProduct->delete();
        }
        DB::commit();
    } catch (Exception $e) {
        DB::rollBack();
        throw new HttpException(500, 'Sucedio un error eliminando la información favor intentar de nuevo');
    }
}

private function getProduct($sku)
{
    $product = Product::where('sku', $sku)->first();
    return $product;
}

I"m not sure how to do the @click method on the vue part, right now i have this, but this is used to upload on other page, not sure what to change to make it delete instead. It's receiving an array that has been separated into groups of 50, thats the (data, index).

sendData(data, index) {
  this.loading = true;
  this.error = {};
  this.$http.post(this.baseUrl, data, this.params).then(
    () => {
      this.successAction();
      this.statuses[index] = 1;
      this.errorDis = false;
    },
    res => {
      this.showErrors(res);
      this.statuses[index] = 2;
      this.errorDis = true;
    }
  );
}

Currently i get a success status but it's not deleting the products

Upvotes: 2

Views: 246

Answers (1)

dparoli
dparoli

Reputation: 9161

IMHO you can delete all the products with one query instead of $products->count() * 2 queries, something like that:

public function destroy(Request $request)
{
    //ini_set('max_execution_time', 300); no need IMHO
    $products = collect($request->all());
    $skus = $products->pluck('SKU');

    try {
        DB::beginTransaction();
        Product::whereIn('sku', $skus)->delete();
        DB::commit();
    } catch (Exception $e) {
        DB::rollBack();
        throw new HttpException(500, 'Sucedio un error eliminando la información favor intentar de nuevo');
    }
    // it's better to return something here
    return response('Finished!', 200);
}

Update: As pointed by @ceejayoz the function above bypass the individual eloquent events deleting and deleted, in case you need them, or you need the single Product model, here is a less stripped version that executes $products->count() + 1 queries:

public function destroy(Request $request)
{
    //ini_set('max_execution_time', 300); probably unneeded
    $skus = collect( $request->all() )->pluck('SKU');
    $products = Product::whereIn('sku', $skus)->get();
    try {
        DB::beginTransaction();
        foreach ($products as $product) {
            Log::error($product);
            $product->delete();
        }
        DB::commit();
    } catch (Exception $e) {
        DB::rollBack();
        throw new HttpException(500, 'Sucedio un error eliminando la información favor intentar de nuevo');
    }
    // it's better to return something here
    return response('Finished!', 200);
}

Upvotes: 2

Related Questions