Php 在laravel中有条件地向模型附加属性

Php 在laravel中有条件地向模型附加属性,php,laravel,orm,eloquent,append,Php,Laravel,Orm,Eloquent,Append,每当调用模型作用域时,是否可以向我的模型附加属性 例如,在我的控制器中,我想调用一个作用域来附加这些动态属性,如: $Media_query = OutDoorMedia::query(); $Media_query->orderby('created_at', 'desc'); $Media_query->PreviouslyOrdered(); $Media = $Media_query->get(); 在我的模型中,我想做如下事情: class OutDoorMedia

每当调用模型作用域时,是否可以向我的模型附加属性

例如,在我的控制器中,我想调用一个作用域来附加这些动态属性,如:

$Media_query = OutDoorMedia::query();
$Media_query->orderby('created_at', 'desc');
$Media_query->PreviouslyOrdered();
$Media = $Media_query->get();
在我的模型中,我想做如下事情:

class OutDoorMedia extends Model
{
    /**
     * The attributes that are mass assignable.
     *
     * @var array
     */
    protected $fillable = [
        'id',
        'user_id',
        'address',
        'location',
        'media_type',
    ];
}

class scopePreviouslyOrdered extends OutDoorMedia
{
public $appends = ['previously_ordered'];

public function getPreviouslyOrderedAttribute()
{
    if ($this->hasMany('App\Models\OutDoorMediaOrders', 'odm_id', 'id')->Where(function ($query) {
        $query->where('status', MEDIA_ORDER_CHECKOUT_STATUS)
            ->orWhere('status', STATUS_TO_PAY);
    })->exists()) {
        return true;
    } else {
        return false;
    }
}
}


但它不起作用,我知道这是错误的,如何实现这一点

我认为对示波器的工作原理存在误解。范围基本上类似于模型的快捷查询。您正在使用它来测试关系的存在性,但有一种更好的方法可以使用
whereHas

以下是如何利用关系实现这一目标:

class OutDoorMedia extends Model
{
    /**
     * The attributes that are mass assignable.
     *
     * @var array
     */
    protected $fillable = [
        'id',
        'user_id',
        'address',
        'location',
        'media_type',
    ];

    public function previousOrders() {
         return $this->hasMany('App\Models\OutDoorMediaOrders', 'odm_id', 'id');
    }
    public function getPreviouslyOrderedAttribute() {
        return $this->previousOrders()->exists(); 
    }
}
然后你只需做:

$Media_query = OutDoorMedia::whereHas('previousOrders')
                ->orderby('created_at', 'desc');
如果自动将动态属性附加到模型上,则只需将以下内容添加到模型中:

 public $appends = [ 'previously_ordered' ];
我想如果你想从两个世界中得到最好的,你可以做到:

class OutdoorMediaWithPreviouslyOrdered extends OutDoorMedia {
     public $appends = [ 'previously_ordered' ];         
 }
然后,当需要附加模型时,可以使用:

 $Media_query = OutdoorMediaWithPreviouslyOrdered ::orderby('created_at', 'desc');

我在@apokryfos的帮助下解决了这个问题,但做了一些调整。希望这能减少浪费别人的时间

我没有在模型上附加属性,而是通过雄辩的魔术方法将上述属性附加到我的模型上:

$Media_query = OutDoorMedia::query();
$Media_query->orderby('created_at', 'desc');
$Media = $Media_query->get()->each(function ($items) {
          $items->append('previously_ordered');//add this attribute to all records which has the condition
         });    
在模型中,正如apokryfos所说,我已经提出了以下两种方法:

  public function PreviousOrders() {
      return $this->hasMany('App\Models\OutDoorMediaOrders', 'odm_id', 'id');
  }

  public function getPreviouslyOrderedAttribute() {
      return $this->PreviousOrders()->exists();
  }
但我不需要这个方法,我必须将它从模型中删除,因为如果它存在于模型中,它将自动附加到模型中:

public $appends = [ 'previously_ordered' ];

谢谢,是的,我想我弄糊涂了。但仍然存在一个问题,我想返回所有记录,那些与订单相关的记录的参数previous\u ordered=true,那些没有任何订单的记录previous\u ordered=false,我不想是全局的,我想将它附加到一些控制器中的查询中。这就是为什么我认为scope现在可以用你的方法解决我的问题。查询只返回那些有顺序的。如果你不包括
whereHas
,你就得到了一切,然后如果你添加属性代码,你应该在模型上得到布尔值
之前排序的
,问题是如何将属性代码添加到查询我应该在模型中为它写另一个方法吗?你是什么意思?如果属性位于
$appends
属性中,则无需执行任何操作即可将其添加到模型中。它将自动追加。