Русское сообщество разработки на PHP-фреймворке Laravel.
Ты не вошёл. Вход тут.
кроссдоменные запросы запрещены
точнее – ограничены. гуглить CORS и content security policy
нельзя так делать. подключай в iframe
без predis/predis не будет работать кэш в редисе и сессии в редисе тоже. какие именно данные где кэшировать это нужно решать уже в конкретных местах
писать if (!Cache::has('key')){ Cache::put(…); } не надо, для этого уже есть Cache::remember(…), и вообще лучше бы для начала почитать раздел документации по кэшу, там всё очень просто…
для Cache::increment() также не нужно заранее добавлять значение в кэш, если его нет, редис считает что оно равно нулю и ноль вполне нормально инкрементируется безо всяких проверок…
Достаточно просто в cache.php установить driver => redis
лучше в .env указать CACHE_DRIVER=redis
нет, там используется нативный пхп-шный password_hash (доступен с пхп 5.5) с методом шифрования PASSWORD_BCRYPT. такой хэш сразу содержит соль и указание на то каким алгоритмом он получен, в 7.2 вроде хотят добавить ещё более безопасный алгоритм какой-то, но поскольку алгоритм указан в хэше – прежние сохранённые пароли будут продолжать работать – довольно удобно правда?
и еще один вопрос: есть ли разница в использовании?
я тоже наступал на эти грабли. если установлено расширение пхп php-redis, оно создаёт в корневом неймспейсе свой класс Redis и после этого через корень обращаться к фасаду как \Redis становится нельзя – класс к моменту обращения уже существует. и на нём естественно нет тех методов, которые использует ларавель. вообще все фасады лучше всего подключать через Illuminate\Support\Facades – неизвестно какие ещё расширения и сторонние библиотеки могут в корень чего-то насовать, что будет конфликтовать с ларавелем
да, и ещё – для работы с редисом в ларавеле расширение php-redis устанавливать не нужно! у редиса простой текстовый протокол и пакет predis/predis не использует никаких расширений. в продакшене опционально можно собрать пакет php-pecl-iredis, он чуть-чуть ускоряет работу в случаях когда присутствует большой трафик запросов в редис – но и он полностью опционален
tar cz /local/www | ssh my@host | tar xz -C /home/www
зачем так сложно? есть же scp, есть rsync…
так вроде успешно установился…
сервис-провайдеры отрабатывают на каждый запрос, это значит что на каждый запрос даже на горячем кэше будет выбираться (и потом выбрасываться) каждый из справочников. если справочники действительно большие – это лишняя нагрузка на кэш и на пхп. кроме того сама логика выборки данных – прерогатива модели. соответственно, методы выборки из кэша/базы полного списка записей также нужно размещать на модели.
я бы перекрыл в моделях метод all(). тогда код просто будет обращаться к Category::all() не беспокоясь о том как именно и откуда будут выбраны записи. а вот внутри all() уже сделать return cache()->rememberForever(…)
используют внешние утилиты, которые запускают через exec: catdoc, poppler, pdf2text. если нужно работать с самими изображениями страниц pdf, imagemagick умеет их открывать, соответственно в php-imagick есть все необходимые для этого функции. если нужно пдф отображать на страницах сайта (функционал типа книгочиталки), есть pdf2svg, который разбирает pdf на страницы с сохранением векторного формата – полезно если страницы нужно отображать на retina-экранах…
Тогда лучше на диске, чем в озу например....
сессии в памяти всегда лучше чем на диске. различия не только в скорости работы, сессии на файлах открываются с блокировкой, это препятствует параллельной обработке запросов одного и того же пользователя, например, аяксом… мемкэш или редис идеально для этого подходят. на шаред хостинге можно положить сессии в базу или даже передавать сами данные сессии в куках и фактически хранить на клиенте – такой способ безопасен, но его можно использовать только если в сессии хранится очень небольшое количество данных (например авторизация, или уникальный идентификатор пользователя для какого-либо трекинга), драйвер называется cookie
У меня проблема со слешем на конце. Если переходить по ссылке site/test, то отобразится все нормально. Если перейти по site/test/, то вызывается ошибка 301 и url становится site/public/test. Вы знаете как это исправить? Заранее спасибо.
наличие или отсутствие / в конце url определяется соглашениями той или иной cms или фреймворка. в ларавеле решено что / в конце url быть не должно, это даже не захардкожено, а просто изначально заложено в логику работы маршрутизатора и это нельзя «исправить», потому что это не ошибка. просто прими это как данное и не борись…
в том что ты создаёшь объект контроллера и пытаешься вызывать его методы за пределами контекста запроса наверное. контроллеры работают как часть процесса обработки хттп-запросов. если эти методы тебе нужны где-то ещё, их нужно из контроллера выносить в независимый класс.
кроме того, не рекомендуется вызывать env() за пределами конфига. парсинг /.env не бесплатен в плане производительности, и если конфиг на продакшене можно закэшировать с artisan config:cache, то .env не кэшируется…
return $q->whereAlias($alias)->first();
во-первых тут я бы написал firstOrFail() – тогда 404 на несуществующих в базе продуктах будет генерироваться автоматически, во-вторых изобретать скоупы только для того чтобы выбирать каким-то способом модели в маршрутах – это по-моему излишне, есть Route::model для автоматического резолва айдишника в модель, есть на моделях getRouteKey() который по умолчанию возвращает $primaryKey то есть 'id', но его можно переопределить на что угодно, например 'alias'.
тогда пример будет выглядеть так
модель:
public function setAliasAttribute($value)
{
$this->attributes['alias'] = str_slug($value);
}
public function getRouteKey()
{
return 'alias';
}
в маршрутах:
Route::model('product', App\Product::class);
Route::get('product/{product}', ['uses'=>'ProductController@index','as'=>'product']);
в контроллере:
public function index(App\Product $product)
{
return view('site.product', compact('product'));
}
генерация ссылок:
<a href="{{ route('site.product', $product) }}"></a>
всё. осталось только не забыть добавить в таблице products индекс по полю alias – запросов по нему видимо будет много. и видимо индекс должен быть unique, хотя при использовании soft-deletes может быть и нет, надо смотреть по обстоятельствам…
ps. писал по памяти, не обессудьте если где что перепутал
я бы начал с проверки того что в базе есть нужные индексы и запросы их используют. плюс некоторые артисты ухитряются положить базу большим количеством insert/update запросов, обновляя в ней разные счётчики и статистику – это всё можно складывать в промежуточное хранилище и накатывать параллельно по крону. ошибки 500 обычно не имеют отношения к нагрузке вообще, это код где-то крэшится, и если ничего не сломано, информация о крэше вся есть в storage/logs/laravel.log – его тоже надо хорошенько раскурить…
всё перепутал. судя по описанию структуры базы у тебя должно быть две модели: User и Role, связанные между собой отношением многие-ко-многим (->belongsToMany()) через пивот-таблицу role_user (для неё модели создавать не нужно). если у пользователя может быть только одна роль, пивот-таблица не нужна, достаточно поля role_id на users, в этом случае у пользователя будет связь role() { return $this->belongsTo(Role::class); } а у ролей для получения пользователей с этой ролью будет связь users() { return $this->hasMany(User::class); }
на событиях модели наверное. но тогда есть смысл всегда заворачивать удаление в транзакции. иначе если что-то пойдёт не так на полпути, база окажется в несогласованном состоянии. при использовании foreign key транзакционная семантика на on delete cascade гарантируется самой базой
кстати проверка has в данном случае лишняя. get и так вернёт null если оно его не has
я собственно не понял. если используется datatables, есть же пакет laravel-datatables в котором уже всё сделано, разве нет?
storage/logs/laravel.log
а это получается что в каждом методе мы видим одну и ту же строчку... ну как то не айс
если одна и та же в каждом, тогда она рефакторится в отдельный метод и код снова красив.
на самом деле если выбираются одни и те же данные, отличается только формат ответа в зависимости от того аяксом запрос сделан или нет – нет особого смысла городить разные контроллеры. другое дело если есть отдельное апи для данных, отдельное для страниц – тогда да, конечно
какие есть индексы на таблице?
можно просто проверять, как запрос пришёл. на \Request есть is_ajax() – проверяет заголовок X-Requested-With, который устанавливается jquery и рядом других библиотек (но в axios например это надо делать вручную) и wantsJson() – проверяет наличие application/json в заголовке Accept – если с jquery явно указывать тип "json" при запросе или использовать метод $.getJSON – он будет установлен тоже
таким образом в методе контроллера будет что-то типа
return $request->wantsJson() ? $posts : view('posts')->withPosts($posts);
Может без контроллера нельзя отправлять данные POST
нет, причина в том что без шаблона нельзя в форму вставить CSRF-токен. то есть конечно можно, но для этого нужны манипуляции с формой на джаваскприте, которые ещё сложнее, чем просто нормально вывести страницу с формой через обработчик.
просто не выводи формы через html, а сделай маршрут с формой, в нём return view('forma') а в шаблоне resources/views/forma.blade.php вставь код своей формы и вызов csrf_field()
С отдельного файла с функцией mail() тоже отправляется.
ну и поставь тогда MAIL_DRIVER=mail и отправляй локально а не через gmail