moonshine-software / moonshine

Laravel Admin panel and more. Simple for beginners and powerful for experts. Using Blade, Alpine.js and Tailwind CSS.
https://moonshine-laravel.com
MIT License
786 stars 102 forks source link

Неправильно работают QueryFilters при использовании SoftDelete #877

Closed carma100 closed 7 months ago

carma100 commented 7 months ago

MoonShine Version

2.9.5|2.10.5

Laravel Version

^10|^11.0

PHP Version

8.3.4

Database Driver & Version

postgres:latest

Description

использую мягкое удаление, удаляю элементы из таблицы, нажимаю на фильтр

    /**
     * @return array|QueryTag[]
     */
    public function queryTags(): array
    {
        return [
            QueryTag::make(
                __('admin.archive'),
                fn ($query) => $query->onlyTrashed()
            )
                ->icon('heroicons.outline.trash'),
        ];
    }

показывает удалённые элементы, показываю кнопки удаления и восстановления через трейт:

<?php

namespace App\Models\Base\Traits;

use Illuminate\Database\Eloquent\Model;
use MoonShine\ActionButtons\ActionButton;
use MoonShine\MoonShineUI;
use Throwable;

/**
 * @property Model model
 * @method getItemId()
 *
 */
trait LandingRestoreOrForceDeleteSoftDeleted
{
    protected string $tableName = 'table-updated';
    /**
     * @return void
     */
    public function restore(): void
    {
        /** @var Model $item */
        $item = $this->model::withTrashed()->find($this->getItemID());
        if ($item instanceof Model && $item->trashed()) {
            $item->restore();
            MoonShineUI::toast("Элемент `{$item->__get('name')}` успешно восстановлен", type: 'success');
        }
    }

    /**
     * @return void
     */
    public function forceDelete(): void
    {
        /** @var Model $item */
        $item = $this->model::withTrashed()->find($this->getItemID());
        if ($item instanceof Model && $item->trashed()) {
            $item->forceDelete();
            MoonShineUI::toast("Элемент `{$item->__get('name')}` удален навсегда", type: 'warning');
        }
    }

    /**
     * @throws Throwable
     * @return array
     */
    public function softDeleteButtons(): array
    {
        return [
            ActionButton::make("")
                ->method('restore', events: [$this->tableName.'-index-table'])
                ->success()
                ->customAttributes(['title' => __('admin.restore')])
                ->icon('heroicons.outline.arrow-uturn-left')
                ->canSee(fn (Model $item) => null !== $item->__get('deleted_at')),
            ActionButton::make("")
                ->method('forceDelete', events: [$this->tableName.'-index-table'])
                ->error()
                ->customAttributes(['title' => __('admin.force_delete')])
                ->icon('heroicons.trash')
                ->canSee(fn (Model $item) => null !== $item->__get('deleted_at')),
        ];
    }

    /**
     * @param string $value
     * @return string
     */
    public function setTableName(string $value): string
    {
        return $this->tableName = $value;
    }
}

суть ошибки: после восстановления или принудительного удаления происходит обновление таблицы, QueryFilter подсвечивается активным, но при этом показывается компонент без QueryFilter (просто IndexPage). Если сначала удалить элементы с IndexPage, потом обновить страницу, нажать на QueryFilter - ошибки не будет.

На старой ветке нашёл старый app.js, вернул его - такой ошибки нет. После выполнения команды php artisan moonshine:publish -> Assets появляется ошибка.

При удалении элементы на старом app.js в гет параметрах ?_component_name=index-table, в новом ассете дописывается _component_name=index-table&_token=KibysLT0DhLAQXDbVumQE3KjWfn3xdZvDsBZtJjK&_method=DELETE, после этого сразу кликнув на QueryFilter для показа удалённых в гет параметрах это ?_component_name=index-table&_token=KibysLT0DhLAQXDbVumQE3KjWfn3xdZvDsBZtJjK&_method=DELETE. image1 image2

Steps To Reproduce

В модели использовать use SoftDeletes;, добавить кнопки восстановления и удаления (к примеру, мой трейт). Удалить пару элементов, ткнуть на фильтр для треша, без перезагрузки страницы, восстановить элемент, обновится страница, фильтр останется активным, но будет показана IndexPage.

carma100 commented 7 months ago

Да, isAsync включен.

lee-to commented 7 months ago

Да, isAsync включен.

Да я уже смог воспроизвести

lee-to commented 7 months ago

В ближайшем релизе будет фикс

carma100 commented 7 months ago

Отлично, спасибо!