динамическое создание get методов в методе модели

Общие вопросы по использованию второй версии фреймворка. Если не знаете как что-то сделать и это про Yii 2, вам сюда.
Ответить
Аватара пользователя
webplus
Сообщения: 336
Зарегистрирован: 2012.02.24, 22:05

динамическое создание get методов в методе модели

Сообщение webplus »

Здравствуйте!
Необходимо в модели в методе создавать в цикле методы для атрибутов, например getItems(). Это необходимо автоматически в цикле сделать, если атрибут array.
вот пример кода:

Код: Выделить всё

class JsonModel extends \yii\base\Model
{
    public function load($data, $formName = '')
    {
        foreach ($data as $key => $value) {
            if(is_array($value)) {
                $className = Inflector::camel2words($key);
                $modelName = "\\frontend\\models\\json\\$className";
                $model = new $modelName;
                $model->load($value);
                $this->addMethod('get' . Inflector::camel2words($key), function($model){return $model;});
            }
        }
        return parent::load($data, $formName);
    }

    function addMethod($name, $method)
    {
        $this->{$name} = $method;
    }

    public function __call($name, $arguments)
    {
        return call_user_func($this->{$name}, $arguments);
    }
}

//********************

class Json extends JsonModel
{
    public $user_id;
    public $name;
    public $attribute;

    public function rules()
    {
        return [
            [['user_id', 'name', 'attribute'], 'required'],
            [['user_id'], 'integer'],
            [['name'], 'string', 'max' => 250],
        ];
    }
}

//******

class Attribute extends JsonModel
{
    public $name;

    public function rules()
    {
        return [
            [['name'], 'required'],
            [['name'], 'string', 'max' => 250],
        ];
    }

}
А вот вызов в контроллере:

Код: Выделить всё

    public function actionJson()
    {
        $json = '{
  "data": {
    "name": "users",
    "user_id": "1",
    "attribute": {
      "name": "test"
    }
  }
}';
        $model = new Json();
        $model->load(json_decode($json, 1)['data']);
        $model->validate();
        echo "\n<pre>" . print_r($model->attribute->name,1) . "</pre>"; die;

    }
В общем в базовой модели не работает создание через __call новых методов get
Сайт по работе в Украине: https://jobis.com.ua/. Сайт по поиску строителей: https://stroyzakaz.com.ua/
Создание сайтов в Киеве: https://webplus.com.ua/ по доступной цене.
someweb
Сообщения: 552
Зарегистрирован: 2017.03.09, 10:12

Re: динамическое создание get методов в методе модели

Сообщение someweb »

__call не создает метод.
Для доступа надо не get* методы создавать, а перекрыть __get() и __set()
Чтобы правильно задать вопрос, нужно знать бо́льшую часть ответа. Роберт Шекли.
Аватара пользователя
webplus
Сообщения: 336
Зарегистрирован: 2012.02.24, 22:05

Re: динамическое создание get методов в методе модели

Сообщение webplus »

someweb писал(а): 2019.02.19, 12:12 Для доступа надо не get* методы создавать, а перекрыть __get() и __set()
а можно пример? а то мне так сложно понять. спасибо!
Сайт по работе в Украине: https://jobis.com.ua/. Сайт по поиску строителей: https://stroyzakaz.com.ua/
Создание сайтов в Киеве: https://webplus.com.ua/ по доступной цене.
someweb
Сообщения: 552
Зарегистрирован: 2017.03.09, 10:12

Re: динамическое создание get методов в методе модели

Сообщение someweb »

Чтобы правильно задать вопрос, нужно знать бо́льшую часть ответа. Роберт Шекли.
Аватара пользователя
webplus
Сообщения: 336
Зарегистрирован: 2012.02.24, 22:05

Re: динамическое создание get методов в методе модели

Сообщение webplus »

someweb писал(а): 2019.02.19, 12:22 viewtopic.php?f=19&t=50014#p245430
сделал так:

Код: Выделить всё

class JsonModel extends \yii\base\Model
{
    public $methods;

    public function load($data, $formName = '')
    {
        foreach ($data as $key => $value) {
            if(is_array($value)) {
                $className = Inflector::camel2words($key);
                $modelName = "\\frontend\\models\\json\\$className";
                $model = new $modelName;
                $model->load($value);
                $this->addMethod('get' . Inflector::camel2words($key), function($model){return $model;});
            }
        }
        return parent::load($data, $formName);
    }

    function addMethod($name, $method)
    {
        $this->{$name} = $method;
        return call_user_func($this->{$name});
    }

    public function __set($name, $value)
    {
        return $this->methods[$name] = $value;
    }

    public function __get($name)
    {
        return $this->methods[$name];
    }
}
Ошибка: Too few arguments to function common\base\JsonModel::common\base\{closure}(), 0 passed and exactly 1 expected
Сайт по работе в Украине: https://jobis.com.ua/. Сайт по поиску строителей: https://stroyzakaz.com.ua/
Создание сайтов в Киеве: https://webplus.com.ua/ по доступной цене.
Ответить