Skip to content

📤 Класс Response

Класс Response отвечает за вывод данных из контроллера. С его помощью можно вернуть текст, HTML, JSON, объекты, шаблоны, перенаправления и коды ошибок.

⚡ Быстрый старт

Вы можете создать ответ вручную:

php
$response = new Response();
$response->json(['name' => 'Саша']);

Но гораздо удобнее использовать хелпер response():

php
response(['name' => 'Саша']);

Он автоматически определяет тип содержимого — массив, объект или текст — и возвращает соответствующий ответ.

🧪 Пример использования в контроллере

php
Route::get('/', function () {
    return response()->json([
        'message' => 'Добро пожаловать!',
        'version' => '1.0.0',
    ]);
});

🧾 Методы ответа

📄 text($text, $status = 200, $headers = [])

Возвращает простой текст.

php
Route::get('/text', function () {
    return response()->text('Простой текстовый ответ');
});

🌐 html($html, $status = 200, $headers = [])

Возвращает HTML-контент. Вставляет скрипты MODX из $modx->getRegisteredClientStartupScripts() и $modx->getRegisteredClientScripts() в </head> и </body>.

php
Route::get('/html', function () {
    return response()->html('<!DOCTYPE html><html><head></head><body><h1>Привет</h1></body></html>');
});

🔢 json(array $data, $status = 200, $headers = [])

Возвращает JSON с автоматической установкой заголовка Content-Type: application/json.

php
Route::get('/json', function () {
    return response()->json([
        'success' => true,
        'user' => ['name' => 'Саша', 'age' => 30],
    ]);
});

🧱 object($object, $status = 200, $headers = [])

Конвертирует объект или коллекцию xPDOObject в массив и возвращает как JSON. Поддерживает одиночные объекты и xPDOIterator.

php
Route::get('/user', function () {
    $user = $modx->getObject(\modUser::class, 1);
    // или $user = query(\modUser::class)->find(1)
    return response()->object($user);
});
php
Route::get('/users', function () {
    $users = $modx->getIterator(\modUser::class);
    // или $users = query(\modUser::class)->get()
    return response()->object($users);
});

🖼️ view($template, array $data = [])

Рендерит шаблон с помощью view() и возвращает как HTML.

php
Route::get('/home', function () {
    return response()->view('home', ['title' => 'Главная страница']);
});

Шаблон можно задать как @INLINE, @FILE, file:, чанк или путь.

🔁 Перенаправления

В PageBlocks вы можете создавать HTTP-редиректы с помощью метода redirect(...) у объекта Response:

php
return response()->redirect('/dashboard');

Но чаще используется глобальный хелпер redirect() — он короче и предоставляет доступ ко всем методам класса Redirect:

php
return redirect('/dashboard');               // обычный редирект
return redirect()->route('profile.show');    // именованный маршрут
return redirect()->back();                   // назад

🔀 redirect($url, $status = 302)

Простой редирект на указанный URL.

Пример в контроллере:

php
Route::get('/go-home', function () {
    return redirect('/');
});

🔙 back($fallback = '/', $status = 302)

Редирект на предыдущую страницу (HTTP_REFERER), или на $fallback, если REFERER отсутствует.

Пример:

php
Route::post('/form', function () {
    // Обработка данных...
    return redirect()->back();
});

♻️ refresh($status = 302)

Обновляет текущий URL.

Пример:

php
Route::get('/refresh', function () {
    return redirect()->refresh();
});

🏠 home($status = 302)

Редирект на главную страницу (/):

Пример:

php
Route::get('/logout', function () {
    // Очистка сессии...
    return redirect()->home();
});

🧭 route($name, $parameters = [], $status = 302)

Редиректит на именованный маршрут.

Пример:

php
Route::get('/profile/{id}', ...)->name('profile.show');

Route::post('/profile/save', function () {
    // Сохранение...
    return redirect()->route('profile.show', ['id' => 42]);
});

→ Если найден маршрут /profile/{id}, будет редирект на /profile/42.

❗ Если указанный маршрут не найден — будет вызван abort(500).


🧨 intended($defaultUrl = '/', $status = 302)

Редиректит на сохранённый адрес из $_SESSION['_intended'], или на $defaultUrl, если он не задан.

Где может использоваться:

php
Route::post('/login', function () {
    // Проверка логина...
    return redirect()->intended('/');
});

Когда это работает:

Если вы заранее сохранили $_SESSION['_intended'] при попытке доступа к защищённой странице:

php
// Middleware или логика защиты:
$_SESSION['_intended'] = $_SERVER['REQUEST_URI'];
return redirect()->route('login');

🔐 secure($url, $status = 302)

Редиректит на HTTPS-версию URL. Полезно, если нужно принудительно перевести пользователя на защищённое соединение.

Пример:

php
Route::get('/secure', function () {
    return redirect()->secure('profile/edit');
});

Результат: https://example.com/profile/edit

error($code = 404, $text = '')

Простой способ вернуть ошибку через redirect():

php
Route::get('/admin', function () {
    if (!auth('mgr')) {
        return redirect()->error(403, 'Доступ запрещён');
    }
});

🛑 Немедленное завершение — abort()

Глобальный хелпер abort() вызывает response()->abort(...)->send() и сразу завершает выполнение, отдав готовую страницу с шаблоном.

php
Route::get('/admin', function () {
    if (!auth('mgr')) {
        abort(403, 'Доступ запрещён');
    }

    return view('admin.panel');
});

⚠️ Не требует return, так как сразу отправляет заголовки и рендерит страницу.

📌 Поддерживаются стандартные HTTP-коды: 403, 404, 503 и т.д. Для них используются системные страницы MODX:

  • 403unauthorized_page
  • 404error_page
  • 503site_unavailable_page

Если код не найден в системных страницах, то создаётся временный ресурс с текстом ошибки.

📦 Если шаблон ошибки для кода существует (core/App/elements/templates/errors/{code}.tpl) — он будет использован. В противном случае подключается базовый шаблон:

templates/base.tpl

Пример использования без параметров (возвращает 404 Not Found):

php
Route::get('/admin', function () {
    if (!auth('mgr')) {
        abort(); // вернёт 404 страницу
    }

    return view('admin.panel');
});

📦 Хелпер response

php
function response($content = '', int $status = 200, array $headers = []): Response

Поведение:

  • массив → json(...)
  • объект → object(...)
  • строка → text(...)

Примеры:

php
return response(['ok' => true]);        // JSON
return response($user);                 // xPDOObject → JSON
return response('Hello, world!');       // Text

📎 Скачивание файлов

📥 download($file, $name = null, $headers = [])

Позволяет скачать файл с сервера. Устанавливает корректные заголовки Content-Type, Content-Disposition, Content-Length и читает содержимое файла.

php
Route::get('/download', function () {
    return response()->download('assets/files/manual.pdf');
});

Можно переименовать файл при загрузке:

php
Route::get('/download-invoice', function () {
    return response()->download('assets/files/invoice_2025.pdf', 'invoice.pdf');
});

Если файл не найден — возвращается 404 File not found..

✅ Универсальные ответы

Эти методы автоматически выбирают формат ответа — HTML или JSON — в зависимости от request()->expectsJson().

success($message = '', $redirect = '')

Возвращает успешный ответ. Работает в двух режимах:

  • 🔁 если expectsJson() → возвращает JSON:
json
{
  "success": true,
  "message": "Успешно сохранено",
  "errors": [],
  "redirect": "/dashboard"
}
  • 📦 если нет → редиректит назад (back() или redirect(...)), добавляет флеш-сообщение и старые данные (withInput()).
php
Route::post('/form', function () {
    // сохранение данных...
    return response()->success('Данные сохранены', '/profile');
});

error($message = '', $errors = [], $status = 422)

Возвращает ответ с ошибкой. Поведение аналогично:

  • 🔁 JSON:
json
{
  "success": false,
  "message": "Ошибка валидации",
  "errors": {
    "email": "Неверный формат"
  },
  "redirect": ""
}
  • 📦 HTML: редирект назад с флеш-сообщением, withErrors() и withInput().
php
Route::post('/form', function () {
    $errors = ['email' => 'Неверный формат'];
    return response()->error('Проверьте форму', $errors);
});

append(array $data)

Дополняет JSON-ответ дополнительными данными. Используется в связке с success() или error().

php
Route::post('/form', function () {
    return response()
        ->append(['debug' => true])
        ->success('ОК');
});

Результат:

json
{
  "success": true,
  "message": "ОК",
  "errors": [],
  "redirect": "",
  "debug": true
}

👜 withBag

Метод withBag($name) позволяет сгруппировать флеш-данные под именем мешка. Это удобно, если у вас несколько форм на странице.

✅ Пример для success()

php
return response()
    ->withBag('auth')
    ->success('Вы успешно вошли!');

В шаблоне:

tpl
{$success_message.auth}  {* Выведет: Вы успешно вошли! *}

❌ Пример для error()

php
return response()
    ->withBag('auth')
    ->error('Ошибка входа', [
        'email' => 'Почта не найдена',
        'password' => 'Неверный пароль',
    ]);

В шаблоне:

tpl
{$error_message.auth}          {* Основное сообщение *}
{$errors.auth.email}           {* Отдельное сообщение для поля email *}
{$errors.auth.password}        {* Отдельное сообщение для поля password *}
{$old_input.auth.email}        {* Старое значение поля email *}

Без withBag() данные будут доступны без вложенности:

tpl
{$error_message}
{$errors.email}
{$old_input.email}

🧾 Работа с заголовками

Класс Response позволяет гибко управлять HTTP-заголовками: добавлять, удалять, получать.

header($name, $value)

Добавляет один заголовок (сокращённый синоним setHeader()):

php
return response()
    ->text('OK')
    ->header('X-Custom-Header', 'value123');

⚙️ setHeader($name, $value)

Устанавливает или переопределяет заголовок вручную.

php
$response = response()->setHeader('Cache-Control', 'no-store');

🧩 withHeaders(array $headers)

Массовое добавление заголовков. Часто используется при форматировании ответа.

php
return response()
    ->json(['ok' => true])
    ->withHeaders([
        'X-Request-ID' => uniqid(),
        'X-Frame-Options' => 'DENY',
    ]);

🔍 getHeaders()

Возвращает все заголовки, установленные в ответе:

php
$headers = response()->getHeaders();
print_r($headers);

Пример вывода:

php
[
    'Content-Type' => 'application/json; charset=utf-8',
    'X-Powered-By' => 'PageBlocks',
]

removeHeader($name)

Удаляет заголовок, если он был установлен:

php
$response = response()->removeHeader('X-Powered-By');

💾 Прикрепление данных к ответу

Для обычных (не-AJAX) запросов вы можете сохранить данные во флеш-сессию, чтобы использовать их в шаблонах после редиректа — например, передавать ошибки, старые значения форм и любые другие сообщения.

📎 with($key, $value, $name = '')

Сохраняет данные во флеш-сессию. Поддерживает именованные "группы" ($name) для разделения значений:

php
return response()
    ->back()
    ->with('success_message', 'Запись создана');

С группой:

php
return response()
    ->back()
    ->with('message', 'Пользователь обновлён', 'admin');

👜 withBag($name)

Позволяет задать группу по умолчанию, которую будут использовать все последующие вызовы with():

php
return response()
    ->withBag('form1')
    ->back()
    ->withErrors(['email' => 'Неверный формат'])
    ->withInput();

Такой подход удобен, если вы хотите разделить данные по разным формам на странице.

🐞 withErrors(array $errors, $name = '')

Сохраняет ошибки в сессию. Если указано имя — ошибки попадут в соответствующую группу:

php
return response()->back()->withErrors([
    'email' => 'Неверный формат',
    'name' => 'Обязательное поле',
]);

С группой:

php
return response()->back()->withErrors(['required' => 'Поле обязательно'], 'validation');

🔁 withInput($name = '')

Сохраняет все введённые пользователем данные (request()->all()). Используется, чтобы восстановить значения после редиректа:

php
return response()
    ->back()
    ->withErrors($errors)
    ->withInput();

С группой:

php
return response()->withInput('register_form');

📋 Примеры в шаблоне

Без группы:

html
{$errors.email}
<input type="text" name="name" value="{$old_input.name}" />

С группой register_form:

html
{$errors.register_form.email}
<input type="text" name="email" value="{$old_input.register_form.email}" />

🔧 Низкоуровневые методы

Эти методы управляют основными параметрами ответа: содержимым и статусом. Обычно они используются внутри других методов (text, json, view и т.д.), но могут быть полезны для кастомных случаев или написания расширений.

📄 setContent($content = '')

Устанавливает «тело» ответа — строку, которая будет выведена пользователю:

php
return response()->setContent('<p>HTML напрямую</p>')->setStatusCode(200);

📄 getContent()

Возвращает текущее содержимое ответа:

php
$content = response()->getContent();

📊 setStatusCode($code, $text = '')

Устанавливает HTTP-статус-код и текст описания. Проверяет валидность кода:

php
return response()
    ->setStatusCode(403)
    ->setContent('Доступ запрещён');

Если текст не указан — используется стандартный:

php
$response->setStatusCode(404); // "Not Found"

📊 getStatusCode()

Возвращает установленный HTTP-код:

php
$code = response()->getStatusCode(); // например, 200

📝 getStatusText()

Возвращает текстовую расшифровку статуса:

php
$text = response()->getStatusText(); // например, "OK"

🚀 Отправка ответа

Все ответы завершаются методом:

📤 send()

Метод:

  • записывает флеш-данные в $_SESSION['pageblocks']['flash'];
  • устанавливает заголовки;
  • выводит содержимое;
  • завершает выполнение exit.

Этот метод вызывается автоматически фреймворком, но если вы формируете ответ вручную — не забудьте вызвать send():

php
$response = response()->text('OK');
$response->send();

🔚 Заключение

Класс Response — универсальный и гибкий компонент для контроллеров PageBlocks:

  • 📄 text, 🌐 html, 🔢 json, 🧱 object
  • 🖼️ view, 📥 download
  • 🔁 redirect, 🔙 back, 🛑 abort
  • success, ❌ error, ➕ append
  • 🧾 Заголовки: header(), setHeader(), withHeaders(), getHeaders(), removeHeader()
  • 💾 Флеш-данные: with(), withErrors(), withInput()
  • 🔧 Низкоуровневое управление: setContent(), setStatusCode(), getContent(), getStatusCode(), getStatusText()
  • 📤 Отправка: send()

С этим инструментом ты легко покроешь любые сценарии: от простых редиректов до API-ответов и обработки ошибок.

© PageBlocks 2019-present