Тонкий PHP, возвращающий JSON

Итак, в основном у меня есть основное приложение, выполняющее вызов ajax GET для моего тонкого php-приложения. В ответ он ожидает JSON dataType.

$.ajax({
        url: './myroute',
        type: 'GET',
        dataType: "json",
        data: { username: username, password: password },
        success: function(data) {},
        error: function(data) {}
});

В моем тонком файле у меня есть:

$app->get('/myroute', function() use ($app) {

    // all the good stuff here (getting the data from the db and all that)

    $dataArray = array('id' => $id, 'somethingElse' => $somethingElse);

    $response = $app->response();
    $response['Content-Type'] = 'application/json';
    $response->body(json_encode($dataArray));

});

    // Tried with these in the above GET request as well:
    // $app->contentType('application/json');
    // echo json_encode($dataArray);

Хотя мой запрос правильно проходит (200), и я правильно получаю свои данные JSON, ошибка заключается в том, что он также возвращает полные данные страницы index.php (что не позволяет мой javascript dataType: "json", что запускает ошибка)

Я решил, что установка типа контента на «application/json» решит эту проблему, но он по-прежнему возвращает полное содержимое страницы, а также данные json.

Изменить для справки

Раньше я настраивал его так, чтобы Слим отображал мой html следующим образом:

$app->get('/', function () use ($app) {
    // would just have my main page files in home.php instead of index.php
    $app-render('home.php');
});

Таким образом, данные html-страницы не возвращались из index.php. Но в pushState мне нужно, чтобы мои javascript-скрипты работали на index.php, иначе мои страницы не будут загружаться должным образом, поскольку, когда они запрашиваются, скрипты не могут делегировать, куда должен идти маршрут.

Любая помощь приветствуется!

Спасибо ТАК!


person Devin    schedule 04.01.2013    source источник
comment
ПРОБЛЕМА РЕШЕНА: добавлен выход(); после $response-›body();   -  person Devin    schedule 04.01.2013


Ответы (4)


Не знаком с тонкими рамками. выглядит интересно. Похоже, код продолжает работать после отображения json. Может быть, попробовать exit;ing приложение php после ответа вашим json?

$app->get('/myroute', function() use ($app) {
    // all the good stuff here (getting the data from the db and all that)

    $dataArray = array('id' => $id, 'somethingElse' => $somethingElse);

    $response = $app->response();
    $response['Content-Type'] = 'application/json';
    $response->body(json_encode($dataArray));
    exit();
});
$app->run();

Надеюсь это поможет

person vortextangent    schedule 04.01.2013
comment
я не поставил exit(); внизу ниже $app-run(); .. Однако я поместил его сразу после $response-›body(); линии, и это работает как шарм! Спасибо, сэр! - person Devin; 04.01.2013
comment
Если вы сделаете ответ, отражающий то, что сработало для меня, я отмечу вас! - person Devin; 04.01.2013
comment
Это предполагает 200. Было бы лучше включить соответствующий код ответа HTTP для дополнительного контекста. - person remarsh; 01.12.2014
comment
Не лучшая идея для exit(), обратный вызов маршрута ДОЛЖЕН возвращать объект ответа. У Slim есть несколько методов для создания ответа JSON, но если вы хотите что-то написать в тело ответа, вы должны вернуть объект ответа в конце. - person Nima; 26.02.2018
comment
@Nima Вероятно, вы правы, ответ на возврат $, вероятно, был бы лучшим решением. - person vortextangent; 05.05.2020

Попробуйте изменить body() на write().

Я думаю, что это сработает: $response->write(json_encode($dataArray));

person Philip    schedule 04.01.2013

В Slim документации о возврате JSON упоминается то, что вы ищете.

Опять же из документации, каждый обратный вызов маршрута принимает три аргумента:

Запросы
Первый аргумент — это объект Psr\Http\Message\ServerRequestInterface, представляющий текущий HTTP-запрос.
Ответ
Второй аргумент — это Объект Psr\Http\Message\ResponseInterface, представляющий текущий HTTP-ответ.
Аргументы
Третий аргумент — это ассоциативный массив, содержащий значения для именованных заполнителей текущего маршрута.

Цитата с той же страницы:

Если вы используете экземпляр Closure в качестве обратного вызова маршрута, состояние замыкания привязывается к экземпляру Container. Это означает, что у вас будет доступ к экземпляру контейнера DI внутри замыкания через ключевое слово $this.

Таким образом, вам не нужно uese ($app) при определении обратного вызова маршрута.

Также как указано в документации.

В конечном счете, каждый маршрут приложения Slim ДОЛЖЕН возвращать объект ответа PSR 7.

В заключение, это должно делать то, что вы ожидаете:

$app->get('/myroute', function($request, $response, $args) {

// all the good stuff here (getting the data from the db and all that)

$dataArray = array('id' => $id, 'somethingElse' => $somethingElse);

return $response->withJson($dataArray);

});
person Nima    schedule 29.06.2017

exit(); у меня больше не работает, не знаю почему. Вот как я решил это:

$response = $app->response();
$response['Content-Type'] = 'application/json';
$response->body(json_encode($body));
return $response;
person e.printStackTrace    schedule 07.09.2015