2013-07-24 7 views
9

मैं अपने छोटे स्लिम फ्रेमवर्क ऐप के लिए कुछ PHPUnit परीक्षण लिखने की कोशिश कर रहा हूं, लेकिन दस्तावेज़ों में कहीं भी नहीं दिखता जो पूर्ण अनुरोध करने के लिए इंगित करता है और प्रतिक्रिया पर जोर देता है (या तो पाठ या 200 स्थिति, या कुछ भी वास्तव में)।स्लिम फ्रेमवर्क एंडपॉइंट यूनिट परीक्षण

क्या ऐसा करने का कोई तरीका है जिसे किसी ने पाया/उपयोग किया है?

+0

पर पिछले 12 महीनों के भीतर उनके सहायता मंचों पर चर्चा की गई, लेकिन इसका स्पष्ट नहीं है कि इसे कभी हल किया गया है: http://help.slimframework.com/discussions/questions/222-how-to-test-a-silm -app – Kristian

उत्तर

3

ठीक है, तो मैं इसे मोटा करने और इसे काम करने में सक्षम था। एंडपॉइंट टेस्ट क्लास का एक उदाहरण यहां दिया गया है।

मान लें कि आप एक विकास वातावरण में काम कर रहे हैं, तो आप अपने खुद के लोकहोस्ट पर curl अनुरोध निष्पादित कर सकते हैं, इस प्रकार एक रेपो करने से पहले परीक्षण कर सकते हैं।

पहले, बनाने के अपने वर्ग:

class ApiEndpointsTest extends PHPUnit_Framework_TestCase 
{ 
    protected $api_url = "http://localhost/api/v1"; 

    //create a function that will allow you to call API endpoints at-will. 
    private function loadEndpoint($url) { 
     $ch = curl_init(); 
     curl_setopt($ch, CURLOPT_URL, $url); 
     curl_setopt($ch, CURLOPT_RETURNTRANSFER, 1); 
     $output = curl_exec($ch); 
     $info = curl_getinfo($ch); 
     curl_close($ch); 
     return array(
      'body' => $output, 
      'info' => $info 
     ); 
    } 

    //this allows you to write messages in the test output 
    private function printToConsole($statement) { 
     fwrite(STDOUT, $statement."\n"); 
    } 

इस का उपयोग करना, आप एक विशेष endpoint प्रतिक्रिया के लिए एक परीक्षण समारोह लिख सकते हैं:

//this will test the actual body of the response against something expected. 
public function testGetUserResponse() { 
    $this->printToConsole(__METHOD__); 
    $url = $this->api_url."https://stackoverflow.com/users/124"; 
    $response = $this->loadEndpoint($url); 
    $expected = '[{"name":"John Smith","email":"[email protected]"}]'; 
    $this->assertEquals($response['body'], $expected); 
} 

एक अलग परीक्षण में, आप किसी अन्य संपत्ति परीक्षण कर सकते हैं एपीआई कॉल की प्रतिक्रिया:

public function testGetUserMimeType() { 
    $this->printToConsole(__METHOD__); 
    $url = $this->api_url."https://stackoverflow.com/users/124"; 
    $response = $this->loadEndpoint($url); 
    $this->assertEquals($response['info']['content_type'], 'application/json'); 
} 

आपकी जानकारी संपत्ति विकल्प यहां पाए जा सकते हैं: http://php.net/manual/en/function.curl-getinfo.php

साइड नोट: यदि कोई इसे पढ़ता है तो PHPUnit पर एक विशेषज्ञ है और एक बेहतर तरीका जानता है, मुझे इसके बारे में सीखने में दिलचस्पी है - मैं PHPUnit के लिए नया हूं।

8

यहां उदाहरण के कैसे आप अपने स्लिम आवेदन का परीक्षण कर सकते है:

https://github.com/mac2000/SlimTestable

मान लीजिए हम सरल अनुप्रयोग है:

<?php 
use Slim\Slim; 

require_once 'vendor/autoload.php'; 

$app = new Slim(); 

$app->get('/', function(){ 
    echo 'home'; 
})->name('home'); 

$app->get('/hello/:name', function($name){ 
    echo "hello $name"; 
})->name('hello'); 

$app->map('/login', function() use($app) { 
    if($app->request()->params('login')) { 
     $app->flash('success', 'Successfully logged in'); 
     $app->redirect($app->urlFor('hello', array('name' => $app->request()->params('login')))); 
    } else { 
     $app->flash('error', 'Wrong login'); 
     $app->redirect($app->urlFor('home')); 
    } 
})->via('GET', 'POST'); 

$app->run(); 

कैसे हम इसे परीक्षण करते हैं?

App वर्ग बनाएँ:

<?php // src/App.php 
use Slim\Slim; 

class App extends Slim { 
    function __construct(array $userSettings = array()) 
    { 
     parent::__construct($userSettings); 

     $this->get('/', function(){ 
      echo 'home'; 
     })->name('home'); 

     $this->get('/hello/:name', function($name){ 
      echo "hello $name"; 
     })->name('hello'); 

     $this->map('/login', function() { 
      if($this->request()->params('login')) { 
       $this->flash('success', 'Successfully logged in'); 
       $this->redirect($this->urlFor('hello', array('name' => $this->request()->params('login')))); 
      } else { 
       $this->flash('error', 'Wrong login'); 
       $this->redirect($this->urlFor('home')); 
      } 
     })->via('GET', 'POST'); 
    } 

    /** 
    * @return \Slim\Http\Response 
    */ 
    public function invoke() { 
     $this->middleware[0]->call(); 
     $this->response()->finalize(); 
     return $this->response(); 
    } 
} 

सूचना है कि हम नया वर्ग निर्माता के लिए हमारी सभी मार्गों ले जाते हैं, भी नए invoke विधि, को छोड़कर यह इसे बाहर गूंज से प्रतिक्रिया देता है बल्कि जो run पद्धति के रूप में भी ऐसा ही करने पर ध्यान दें।

अब आप अपने index.php फ़ाइल इस तरह हो सकता है:

<?php 
require_once 'vendor/autoload.php'; 

$app = new App(); 
$app->run(); 

और अब यह परीक्षण के लिए समय आ गया है:

<?php // tests/ExampleTest.php 
use Slim\Environment; 

class ExampleTest extends PHPUnit_Framework_TestCase { 
    private $app; 

    public function setUp() 
    { 
     $_SESSION = array(); 
     $this->app = new App(); 
    } 

    public function testHome() { 
     Environment::mock(array(
      'PATH_INFO' => '/' 
     )); 
     $response = $this->app->invoke(); 

     $this->assertContains('home', $response->getBody()); 
    } 

    public function testHello() { 
     Environment::mock(array(
      'PATH_INFO' => '/hello/world' 
     )); 
     $response = $this->app->invoke(); 

     $this->assertTrue($response->isOk()); 
     $this->assertContains('hello world', $response->getBody()); 
    } 

    public function testNotFound() { 
     Environment::mock(array(
      'PATH_INFO' => '/not-exists' 
     )); 
     $response = $this->app->invoke(); 

     $this->assertTrue($response->isNotFound()); 
    } 

    public function testLogin() { 
     Environment::mock(array(
      'PATH_INFO' => '/login' 
     )); 
     $response = $this->app->invoke(); 

     $this->assertTrue($response->isRedirect()); 
     $this->assertEquals('Wrong login', $_SESSION['slim.flash']['error']); 
     $this->assertEquals('/', $response->headers()->get('Location')); 
    } 

    public function testPostLogin() { 
     Environment::mock(array(
      'REQUEST_METHOD' => 'POST', 
      'PATH_INFO' => '/login', 
      'slim.input' => 'login=world' 
     )); 
     $response = $this->app->invoke(); 

     $this->assertTrue($response->isRedirect()); 
     $this->assertEquals('Successfully logged in', $_SESSION['slim.flash']['success']); 
     $this->assertEquals('/hello/world', $response->headers()->get('Location')); 
    } 

    public function testGetLogin() { 
     Environment::mock(array(
      'PATH_INFO' => '/login', 
      'QUERY_STRING' => 'login=world' 
     )); 
     $response = $this->app->invoke(); 

     $this->assertTrue($response->isRedirect()); 
     $this->assertEquals('Successfully logged in', $_SESSION['slim.flash']['success']); 
     $this->assertEquals('/hello/world', $response->headers()->get('Location')); 
    } 
} 

आप कुछ चीज़ों पर ध्यान देना चाहिए:

परीक्षण की स्थापना करते समय हम परीक्षण उद्देश्यों के लिए $_SESSION सरणी बना रहे हैं और हमारे App क्लास ऑब्जेक्ट को तुरंत चालू कर रहे हैं।

run के बजाय परीक्षणों में हम invoke पर कॉल कर रहे हैं जो वही करते हैं, लेकिन प्रतिक्रिया ऑब्जेक्ट देता है।

Environment::mock हमारे आवेदन के साथ संसाधित अनुरोधों का नकल करने के लिए उपयोग किया जाता है।

संबंधित मुद्दे