2012-01-04 43 views
14

phép nói rằng tôi có một mô hình được gọi là John với những params:Backbone.js và api REST với silex (PHP)

{ 
    Language : { 
     code : 'gr', 
     title : 'Greek' 
    }, 
    Name : 'john' 
} 

Vì vậy, bây giờ khi tôi kích hoạt John.save() nó POST những máy chủ:

post params http://o7.no/ypvWNp

với những tiêu đề:

headers http://o7.no/x5DVw0

.210

Các mã trong silex là thực sự đơn giản:

<?php 

require_once __DIR__.'/silex.phar'; 

$app = new Silex\Application(); 

use Symfony\Component\HttpFoundation\Request; 
use Symfony\Component\HttpFoundation\Response; 

// definitions 
$app['debug'] = true; 

$app->post('/api/user', function (Request $request) { 
    var_dump($request->get('Name')); 

    $params = json_decode(file_get_contents('php://input')); 
    var_dump($params->Name); 
}); 

$app->run(); 

nhưng trước tiên var_dump trở lại vô var_dump thứ hai của quá trình làm việc kể từ khi tôi nhận được yêu cầu trực tiếp từ php://input tài nguyên. Tôi tự hỏi làm thế nào tôi có thể nhận được các thông số bằng cách sử dụng đối tượng Yêu cầu từ Silex

Cảm ơn

Trả lời

15

Thật dễ dàng.

use Symfony\Component\HttpFoundation\Request; 
use Symfony\Component\HttpFoundation\ParameterBag; 

$app->before(function (Request $request) { 
    if (0 === strpos($request->headers->get('Content-Type'), 'application/json')) { 
     $data = json_decode($request->getContent(), true); 
     $request->request = new ParameterBag(is_array($data) ? $data : array()); 
    } 
}); 

Và sau đó là một con đường dụ:

$app->match('/', function (Request $request) { 
    return $request->get('foo'); 
}); 

Và thử nghiệm với curl:

$ curl http://localhost/foobarbazapp/app.php -d '{"foo": "bar"}' -H 'Content-Type: application/json' 
bar 
$ 

Ngoài ra nhìn vào (hơi lỗi thời) RestServiceProvider.

EDIT: Tôi đã chuyển câu trả lời này thành cookbook recipe in the silex documentation.

+0

Xin chào, cảm ơn rất nhiều! Đó là một giải pháp! Mặc dù tôi tin rằng Silex nên cẩn thận theo mặc định mà không cần thêm bộ lọc 'trước'. Về kiểu nội dung, '$ request-> headers-> get ('Content-Type')' trả về 'application/json; charset = UTF-8' vì vậy tôi muốn kiểm tra như sau: 'if ('application/json' === strstr ($ request-> headers-> get ('Content-Type'), ';', true)) 'hoặc để được chống đạn hơn như thế:' if (false! == strpos ($ request-> headers-> get ('Content-Type'), 'application/json')) ' – panosru

+0

' 0 === strpos ('thậm chí, sẽ điều chỉnh câu trả lời của tôi. – igorw

+0

Từ hướng dẫn sử dụng php:' Hàm này có thể trả về Boolean FALSE, nhưng cũng có thể trả về giá trị không Boolean đánh giá thành FALSE, chẳng hạn như 0 hoặc ".'' vì vậy tôi có xu hướng sử dụng sai thay vì 0 :) – panosru

4

Con đường tôi đã thực hiện nó trước như sau:

$app->post('/api/todos', function (Request $request) use ($app) { 
    $data = json_decode($request->getContent()); 

    $todo = $app['paris']->getModel('Todo')->create(); 
    $todo->title = $data->title; 
    $todo->save(); 

    return new Response(json_encode($todo->as_array()), 200, array('Content-Type' => 'application/json')); 
}); 

Trong bộ sưu tập xương sống của bạn, thêm những điều sau đây:

window.TodoList = Backbone.Collection.extend({ 
    model: Todo, 

    url: "api/todos", 

    ... 
}); 

Tôi đã viết lên một bước-by-bước hướng dẫn đầy đủ tại đây http://cambridgesoftware.co.uk/blog/item/59-backbonejs-%20-php-with-silex-microframework-%20-mysql

0

Tôi đã tự khắc phục bằng cách đặt thêm thuộc tính $payload vào đối tượng Yêu cầu

$app->before(function(Request $request) { 
    if (stristr($request->getContentType(), 'json')) { 
     $data    = json_decode($request->getContent()); 
     $request->payload = $data; 
    } else { 
     $request->payload = null; 
    } 
});