Warning: file_get_contents(/data/phpspider/zhask/data//catemap/1/php/293.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
Php Laravel:正确覆盖软删除特性_Php_Laravel_Soft Delete - Fatal编程技术网

Php Laravel:正确覆盖软删除特性

Php Laravel:正确覆盖软删除特性,php,laravel,soft-delete,Php,Laravel,Soft Delete,我想创建一个使用SoftDeletes命名为SoftDeletesWithStatus的trait,它还将更新status列。我的问题是,我想在的中间实现我的代码。 protected function runSoftDelete() { $query = $this->newQueryWithoutScopes()->where($this->getKeyName(), $this->getKey()); $time = $this->freshT

我想创建一个使用
SoftDeletes
命名为
SoftDeletesWithStatus
的trait,它还将更新status列。我的问题是,我想在<代码>的中间实现我的代码。
protected function runSoftDelete() {
    $query = $this->newQueryWithoutScopes()->where($this->getKeyName(), $this->getKey());
    $time = $this->freshTimestamp();
    $columns = [$this->getDeletedAtColumn() => $this->fromDateTime($time)];

   //I want to implement my code here

    $this->{$this->getDeletedAtColumn()} = $time;
    if ($this->timestamps && ! is_null($this->getUpdatedAtColumn())) {
        $this->{$this->getUpdatedAtColumn()} = $time;
        $columns[$this->getUpdatedAtColumn()] = $this->fromDateTime($time);
    }
    $query->update($columns);
}

public function restore() {
    if ($this->fireModelEvent('restoring') === false) {
        return false;
    }
    $this->{$this->getDeletedAtColumn()} = null;

    //I want to implement my code here

    $this->exists = true;
    $result = $this->save();
    $this->fireModelEvent('restored', false);
    return $result;
}
复制粘贴my
SoftDeletesWithStatus
trait中的代码并在其中实现我的代码是更好的解决方案吗


感谢您的帮助。

我最接近的解决方案是:

<?php
namespace App;

use Illuminate\Database\Eloquent\SoftDeletes;

//Status 1 = Activated; Status 99 = Deleted
trait SoftDeletesWithStatus {
    use SoftDeletes {
        SoftDeletes::runSoftDelete as parentRunSoftDelete;
        SoftDeletes::restore as parentRestore;
    }

    public function getStatusColumn() {
        return defined('static::STATUS') ? static::STATUS : 'status';
    }

    public function runSoftDelete() {
        $this->parentRunSoftDelete();
        $query = $this->newQueryWithoutScopes()->where($this->getKeyName(), $this->getKey());
        $columns = [$this->getStatusColumn() => 99];
        $this->{$this->getDeletedAtColumn()} = 99;
        $query->update($columns);
    }

    public function restore() {
        $result = $this->parentRestore();
        $this->{$this->getStatusColumn()} = 1;
        $this->save();
        return $result;
    }
}
我认为解决方案不完整。
新特性的
runSoftDelete
restore
方法无法处理关系

假设您有一个简单的关系,如:
Author 1-n Book

工作示例:

$Author->delete();
$Author->restore();
$Book->author()->delete();
$Book->author()->restore();
不起作用示例:

$Author->delete();
$Author->restore();
$Book->author()->delete();
$Book->author()->restore();
多亏了Xdebug,我才找到了“不起作用的示例”的解决方案。
顺便说一句,在我的例子中,有一个字符串列的需要,所以我可以结合使用唯一约束和删除状态。因此,方法不同

app/Traits/SoftDeletes.php

<?php

namespace App\Traits;

use App\Overrides\Eloquent\SoftDeletingScope;

trait SoftDeletes
{
    use \Illuminate\Database\Eloquent\SoftDeletes;

    /**
    * Boot the soft deleting trait for a model.
    *
    * @return void
    */
    public static function bootSoftDeletes()
    {
        static::addGlobalScope(new SoftDeletingScope);
    }

    /**
    * Perform the actual delete query on this model instance.
    *
    * @return void
    */
    protected function runSoftDelete()
    {
        $query = $this->newModelQuery()->where($this->getKeyName(), $this->getKey());

        $time = $this->freshTimestamp();

        $columns = [
            $this->getDeletedAtColumn() => $this->fromDateTime($time),
            $this->getDeletedHashColumn() => uniqid(),
        ];

        $this->{$this->getDeletedAtColumn()} = $time;

        if ($this->timestamps && ! is_null($this->getUpdatedAtColumn())) {
            $this->{$this->getUpdatedAtColumn()} = $time;

            $columns[$this->getUpdatedAtColumn()] = $this->fromDateTime($time);
        }

        $query->update($columns);
    }

    /**
    * Restore a soft-deleted model instance.
    *
    * @return bool|null
    */
    public function restore()
    {
        // If the restoring event does not return false, we will proceed with this
        // restore operation. Otherwise, we bail out so the developer will stop
        // the restore totally. We will clear the deleted timestamp and save.
        if ($this->fireModelEvent('restoring') === false) {
            return false;
        }

        $this->{$this->getDeletedAtColumn()} = null;
        $this->{$this->getDeletedHashColumn()} = '';

        // Once we have saved the model, we will fire the "restored" event so this
        // developer will do anything they need to after a restore operation is
        // totally finished. Then we will return the result of the save call.
        $this->exists = true;

        $result = $this->save();

        $this->fireModelEvent('restored', false);

        return $result;
    }

    /**
    * Get the name of the "deleted at" column.
    *
    * @return string
    */
    public function getDeletedHashColumn()
    {
        return defined('static::DELETED_HASH') ? static::DELETED_HASH : 'deleted_hash';
    }

}
<?php

namespace App\Overrides\Eloquent;

use Illuminate\Database\Eloquent;

class SoftDeletingScope extends Eloquent\SoftDeletingScope
{

    /**
    * Extend the query builder with the needed functions.
    *
    * @param  \Illuminate\Database\Eloquent\Builder  $builder
    * @return void
    */
    public function extend(Eloquent\Builder $builder)
    {
        foreach ($this->extensions as $extension) {
            $this->{"add{$extension}"}($builder);
        }

        $builder->onDelete(function (Eloquent\Builder $builder) {
            $deletedAtColumn = $this->getDeletedAtColumn($builder);
            $deletedHashColumn = $builder->getModel()->getDeletedHashColumn();

            return $builder->update([
                $deletedAtColumn => $builder->getModel()->freshTimestampString(),
                $deletedHashColumn => uniqid(),
            ]);
        });
    }

    /**
    * Add the restore extension to the builder.
    *
    * @param  \Illuminate\Database\Eloquent\Builder  $builder
    * @return void
    */
    protected function addRestore(Eloquent\Builder $builder)
    {
        $builder->macro('restore', function (Eloquent\Builder $builder) {
            $builder->withTrashed();

            return $builder->update([
                $builder->getModel()->getDeletedAtColumn() => null,
                $builder->getModel()->getDeletedHashColumn() => '',
            ]);
        });
    }
}

我在新特性中添加了
bootsoftdelements
方法,该方法将自定义
SoftDeletingScope
添加到全局范围。

如果不复制并修改它,则无法执行此操作。您可以将其添加到基本模型并将模型扩展到该类。。如果你告诉我们你想做什么,也许我们能帮上忙我想做软删除(你知道,在<代码>栏中使用<代码>已删除,\u),但这也会更新自定义<代码>状态<代码>栏(即状态99已删除,状态1已激活)。@Bader为什么会投反对票?对不起,我不喜欢你的答案BTWD你有什么想法吗,为什么在通过关系删除时忽略了这个特征?@GordonFreeman我也面临着同样的问题。原因是HasRelationship检查模型是否正在使用
SoftDelete
并插入
whereNull
查询。您还需要重写
SoftDeletingScope
classes
apply
方法。@Mikeros谢谢您提供的信息。请随意编辑我的答案:)否则我会检查几天