Где лучше возвращать ошибку 404 в yii2

226
15 марта 2018, 10:53

В приложении в контроллере user есть несколько экшнов, каждый из которых получает из запроса параметр user_id и по нему ищет пользователя в бд. Отсюда возникаем необходимость проверять существует ли пользователь с указанным id и если такого нет то возвращать сообщение об ошибке

Например так:

$user_id = $_GET['id'];
if (User::findIdentity($user_id)==null)
        throw new HttpException(404 ,'User not found');

Где лучше будет вставить код с проверкой чтобы избежать повторения одного и того же кода во всех экшнах?

Answer 1

В контроллере можно создать метод который будет возвращать пользователя в противном случаи кидать Exception

public function actionIndex() {
    $user = $this->findUser($_GET['id']);
}
public function findUser(id) {
    $user = User::findIdentity($id);
    if (null != $user) {
        throw new HttpException(404 ,'User not found');
    }
    return $user
}
Answer 2

Простой вариант - базовый контроллер (от которого потом отнаследуете все остальные) в котором необходимо переопределить метод beforeAction. В нем вы будете проверять ваше условие и выбрасывать ошибку. Это будет работать, но будет несколько неправильно идеологически. В вашем случае, насколько я понимаю, вы проверяете аутентификацию пользователя - можно создать базовый контроллер, с поведением authenticator (подробнее здесь http://www.yiiframework.com/doc-2.0/guide-rest-authentication.html), и значением

[
    'class' => CompositeAuth::className(),
    'authMethods' => [
        [
            'class' => UserIDAuth::className(),
        ],
    ],
]

где UserIDAuth - это потомок класса AuthMethod реализующий метод authenticate в котором вы осуществите свою проверку и вернете либо аутентифицированного пользователя либо null, если он не найден. Если пользователь не найден - то будет выброшена ошибка. Если найден - то его пропустит дальше, при этом впоследствии можно обращаться к модели аутентифицированного пользователя через Yii::$app->getUser(). Можно переопределить выбрасываемую ошибку на 404. Можно оставить как есть - 403 что возможно будет правильнее для вашего случая. Управлять применением аутентификатора к определенным actionам можно так же через поведение authenticator - поля optional, only, except.

Помимо этого можно использовать поведение access со значением

[
    'class' => AccessFilter::className(),
]

в котором фильтром будет выступать реализованный вами класс AccessFilter наследованный от ActionFilter с переопределенным методом beforeAction в котором вы осуществите вашу проверку и вернете булево значение пропускать пользователя дальше или нет. P.S - если у вас user_id - это действительно значение передаваемое в get параметрах, по которому вы проверяете аутентификацию - хотелось бы предостеречь вас от такой реализации т.к это очень небезопасно - возможно стоит посмотреть в сторону Oauth или хотя бы Basic авторизации поверх https

READ ALSO
Не меняется версия PHP в PhpStorm

Не меняется версия PHP в PhpStorm

Создаю проект в PhpStorm, выбираю интерпретатор Php 72

220
Разница в способах включения файлов

Разница в способах включения файлов

В чем разница include() и require(), а также include_once() и require_once()? Не могу понять

166
Прочитать многомерный массив foreach

Прочитать многомерный массив foreach

Вычитываю JSON ответ, в нем много мерный массив, делаю это так :

239
Разные id в таблице mysql

Разные id в таблице mysql

Приветствую

211