Laravel 5.4+: мутатор / аксессор для загруженного изображения

Я пытаюсь использовать мутатор для хранения и извлечения граватара пользователей.

В моей модели User у меня есть:

public function getGravatarAttribute($gravatar){
    if($gravatar){
        $image = Storage::disk('local')->get('public/avatars/'.$gravatar.'.jpg');
        return new Response($image, 200);
    }

    $hash = md5(strtolower(trim($this->attributes['email'])));
    return "http://www.gravatar.com/avatar/$hash?s=256";
}


public function setGravatarAttribute($gravatar){
    if(is_object($gravatar) && $gravatar->isValid()){
        $image = Image::make($gravatar)->fit(256, 256);
        Storage::disk('local')->put('public/avatars/'.$this->id . '.' . $gravatar->getClientOriginalExtension(),  $image->response());
        $this->attributes['gravatar'] = $this->id;
    }
}

В файле Blade я делаю:

<img id="avatar" src="{{ $user->gravatar }}" alt="your image" width="256" height="256"/>

Мутатор работает прекрасно: изображение хранится в каталоге storage/app/public/avatars. Проблема в аксессуаре: если я использую dd($image); перед возвратом, я вижу данные, но они не отображаются на странице html.


person Lolo    schedule 15.08.2017    source источник
comment
Это опечатка в вопросе? В вашем первом операторе возврата return \ response, если нет, это может быть вашей проблемой. Я также настоятельно рекомендую не использовать ваш идентификатор пользователя в качестве имени файла, так как любой может проверить элемент и получить уникальный идентификатор пользователя в вашей базе данных.   -  person Mike    schedule 15.08.2017
comment
Да Вы правы, я изменил код для этого. На данный момент я пытаюсь запустить этот код, в целях безопасности я посмотрю позже :)   -  person Lolo    schedule 15.08.2017


Ответы (1)


Вы пытаетесь отобразить фасад Response как строку, однако вам просто нужно вернуть путь к изображению для файла.

Вы можете использовать функцию url на Storage Facade, чтобы получить путь к изображению:

if($gravatar){
    $image = Storage::disk('local')->url('public/avatars/'.$gravatar.'.jpg');
    return $image;
}

Поскольку вы используете значение для src:

src="{{ $user->gravatar }}" 

https://laravel.com/docs/5.4/filesystem#file-urls

Изменить

Из документов:

Помните, что если вы используете локальный драйвер, все файлы, которые должны быть общедоступными, должны быть помещены в каталог storage / app / public. Кроме того, вы должны создать символическую ссылку в public / storage, которая указывает на каталог storage / app / public.

Как только это будет сделано, ваш возвращенный URL-адрес должен отображать ваше изображение.

person Mike    schedule 15.08.2017
comment
Это не работает. Кажется, это лучший способ, потому что у меня был unknow в качестве источника изображения, а теперь у меня /storage/avatars/1.jpg - person Lolo; 16.08.2017
comment
Я обновил свой ответ, вам нужно добавить символическую ссылку в папку хранилища. - person Mike; 16.08.2017
comment
Ахахах здорово ... спасибо. Тогда я не буду использовать Storage, но / public / folder ... Как убить приятную фичу. ... - person Lolo; 16.08.2017
comment
Эта функция должна быть удобна для использования, просто запустите sudo ln -s ../storage/app/public storage из общей папки, и она должна ссылаться на вашу папку хранилища в корневом каталоге. - person Mike; 16.08.2017