laminatefish
laminatefish

Reputation: 5256

Laravel 5 unit testing. Unable to set JSON of Request object

How on earth do you get Laravel 5.0 to accept a JSON encoded string into it's request object? Because my REST api is returning 500 errors, and upon closer inspection, the request object has an empty json property...?

My array:

    private $test_1_create_user = array(
        "name" => "Mr T Est",
        "email" => "[email protected]",
        "password" => "testing1234"
    );

My test method:

    /**
    * Attempts to Create a single user with no permissions
    */
    public function testCreateUser(){
        /** Obtain instance of Request object */
        $req = $this->app->request->instance();
        /** Set the JSON packet */
        $req->json(json_encode($this->test_1_create_user));
        /** Run the test */
        $response = $this->call('POST', '/api/v1/user');
        /** Read the response */    
        $this->assertResponseOk();
    }

And a var_dump of $req (slimmed down a bit):

C:\wamp\www\nps>php phpunit.phar
PHPUnit 4.6.2 by Sebastian Bergmann and contributors.

Configuration read from C:\wamp\www\nps\phpunit.xml

class Illuminate\Http\Request#34 (25) {
  protected $json =>
  class Symfony\Component\HttpFoundation\ParameterBag#261 (1) {
    protected $parameters =>
    array(0) {
    }
  }
  protected $sessionStore =>
  NULL
  protected $userResolver =>
  NULL
  protected $routeResolver =>
  NULL
  public $attributes =>
  class Symfony\Component\HttpFoundation\ParameterBag#41 (1) {
    protected $parameters =>
    array(0) {
    }
  }
  public $request =>
  class Symfony\Component\HttpFoundation\ParameterBag#43 (1) {
    protected $parameters =>
    array(0) {
   }
 }

It took me quite a while to figure out how to access the request object from within a unit test. Anyone have any ideas as to why the $req->json is always empty? :( Cheers!

Upvotes: 3

Views: 2663

Answers (2)

laminatefish
laminatefish

Reputation: 5256

Apparently I was over complicating things. For anyone else who may be having issues with posting json to a Laravel controller (inside of unit testing), I simply solved it with:

$response = $this->call('POST', '/api/v1/user', $this->test_1_create_user);

The key element being the last parameter which is a php array. This gets 'magically' converted to json prior to the POST. Documentation for this is sorely lacking...

Upvotes: 2

Dan Krieger
Dan Krieger

Reputation: 119

The way you are attempting to set the json values is incorrect, as the json method in Request is meant to get JSON values from the request, not set them. You'll need to re-initialize the Request object for your test. Something like this should do the trick for you:

/**
* Attempts to Create a single user with no permissions
*/
public function testCreateUser(){
    /** Obtain instance of Request object */
    $req = $this->app->request->instance();
    /** Initialize the Request object */
    $req->initialize(
        array(), // GET values
        array(), // POST values
        array(), // request attributes
        array(), // COOKIE values
        array(), /// FILES values
        array('CONTENT_TYPE' => 'application/json'), // SERVER values
        json_encode($this->test_1_create_user) // raw body content
    );
    /** Run the test */
    $response = $this->call('POST', '/api/v1/user');
    /** Read the response */    
    $this->assertResponseOk();
}

Keep in mind you may want to populate the other request values as necessary, I've only included the Content-Type and the json content

Upvotes: 0

Related Questions