laravel框架访问器调用belongsTo中的未定义属性

时间:2019-01-08 21:21:53

标签: laravel accessor belongs-to

我需要你的帮助。 我正在使用Laravel Framework,但我对归属关系有麻烦。 我的项目必须有表格,通讯录和交付类型,表格中的列为:

地址簿 ID 名称 邮件 delivery_1 deliverytype_id_1 delivery_2 deliverytype_id_2 ...

delivery_types ID 名称 ...

交付类型模型的代码是这样的:

<?php

namespace App;

use Illuminate\Database\Eloquent\Model;

class DeliveryType extends Model
{
    protected $table = 'delivery_types';

    protected $guarded = ['id'];
}

这是通讯录模型:

<?php

namespace App;

use Illuminate\Database\Eloquent\Model;

class AddressBook extends Model
{
    protected $table = 'address_book';  // table
    protected $guarded = ['id'];    // primary key
    protected $appends = ['delivery', 'actions'];   // accessors

    protected $delivery = '';

    public function del1() {
        return $this->belongsTo('App\DeliveryType', 'deliverytype_id_1', 'id')->withDefault();
    }

    public function del2() {
        return $this->belongsTo('App\DeliveryType', 'deliverytype_id_2', 'id');
    }


    /**
    * Accessor: get the actions column information.
    *
    * @return string
    */
    public function getActionsAttribute() {
        $actions = '<a href='. route('admin.addressbook.show', $this->id) .'>'.
                    'show<i class="livicon" data-name="info" data-size="18" data-loop="true" data-c="#428BCA" data-hc="#428BCA" title="view contact"></i></a>';
        return $actions;
    }

    /**
    * Accessor: get the deliveries information.
    *
    * @return string
    */
    public function getDeliveryAttribute () {
        $deliveries = [
            ['val' => $this->delivery_1, 'type' => $this->del1()->name], //row error
            ['val' => $this->delivery_2, 'type' => $this->del2()->name]
        ];

        foreach($deliveries as $delivery) {
            $this->delivery = (strlen($delivery['val']) > 0) ? 
                $this->appendString($this->delivery, '<strong>'.$delivery['type'].'</strong> '.$delivery['val']) : 
                $this->delivery;
        }
        return $this->delivery;
    }

    protected function appendString(string $str, string $val) {
        return (strlen($str) > 0) ? $str.'<br>'.$val : $val;
    }

在html页面中,通过ajax调用将数据加载到控制器功能。这是功能代码:

public function data(Request $request) {

        // Init data
        $this->addressbooks = AddressBook::get(
                ['address_book.id',
               'address_book.name',
               'address_book.email',
               'address_book.delivery_1',
               'address_book.delivery_2');

        // Return json array
        header("Content-Type: application/json");
        return $this->addressbooks;
    }

当页面通过ajax调用函数时,框架在访问器getDeliveryAttribute中返回错误“未定义的属性”,在这里我尝试调用关系属于传递类型ID及其引用投放类型表。

我做错了什么?在此先感谢可以帮助我的人。

1 个答案:

答案 0 :(得分:0)

Here is how I would write the AddressBook model

<?php
namespace App;

use Illuminate\Database\Eloquent\Model;

//use Illuminate\Support\Facades\Log;

class AddressBook extends Model
{
    protected $table = 'address_book';  // table

    //protected $guarded = ['id'];    // primary key

    // always load these accessors
    protected $appends = [
        'delivery',
        'actions',
    ];

    protected $mail    = '';

    // No need for $delInfo, use $this->delivery (same data)
    // protected $delInfo = '';

    public function category() {
        /*
            You can use `AddressBookCategory::class` instead of `'App\DeliveryType'`

            http://php.net/manual/en/migration55.new-features.php#migration55.new-features.class-name

            Because models are in the same napespace, we don't need to write \App\AddressBookCategory
         */
        return $this->belongsTo(AddressBookCategory::class, 'address_book_category_id', 'id');
    }

    public function deliveryType1() {
        return $this->belongsTo(DeliveryType::class, 'deliverytype_id_1', 'id')
                    /*
                        Specify empty string for the name, so that when we access
                        $this->deliveryType1->name it's equal ''
                     */
                    ->withDefault(['name' => '']);
    }

    public function deliveryType2() {
        return $this->belongsTo(DeliveryType::class, 'deliverytype_id_2', 'id')
                    ->withDefault(['name' => '']);
    }

    /**
    * Accessor: get the actions column information.
    *
    * Access by using: $this->action
    * 
    * @return string
    */
    public function getActionsAttribute() {
        // moved this into multi line, easier to read
        return '<a href='. route('admin.addressbook.show', $this->id) .'>'
                 .'show'
                 .'<i class="livicon" data-name="info" data-size="18" data-loop="true" data-c="#428BCA" data-hc="#428BCA" title="view contact"></i>'
              .'</a>';
    }

    /**
    * Accessor: get the deliveries information
    *
    * Access by using: $this->delivery
    *
    * @return string
    */
    public function getDeliveryAttribute () {
        // I've updated logic here, it should be easier to read...
        $delivery = [];

        if ( ! empty($this->delivery_1) ) {
            $delivery[] = '<strong>'.$this->deliveryType1->name.'</strong> '.$this->delivery_1;
        }

        if ( ! empty($this->delivery_2) ) {
            $delivery[] = '<strong>'.$this->deliveryType2->name.'</strong> '.$this->delivery_2;
        }

        // join array elements with a string `<br>`
        return implode('<br>', $delivery);
    }

}