Как сохранить сессию через все тесты на phpunit? - PullRequest
10 голосов
/ 21 февраля 2012

Я работаю над тестированием корзины покупок, оформлением заказа, процессом оплаты на Zend Framework с помощью phpunit.Я тестирую ShoppingCartController, добавляя продукты в корзину, модель ShoppingCart обрабатывает добавления продуктов, сохраняя идентификаторы продуктов в пространстве имен Zend Session, а затем в другом тесте я хочу проверить, что продукты были добавлены.Та же самая модель ShoppingCart извлекает список добавленных продуктов из той же переменной пространства имен Zend Session.

Тест добавления продукта выглядит следующим образом и работает хорошо, а var_dump($_SESSION) был добавлен для отладки и показывает продуктыправильно:

public function testCanAddProductsToShoppingCart() {

    $testProducts = array(
        array(
            "product_id" => "1",
            "product_quantity" => "5"
        ),
        array(
            "product_id" => "1",
            "product_quantity" => "3"
        ),
        array(
            "product_id" => "2",
            "product_quantity" => "1"
        )
    );

    Ecommerce_Model_Shoppingcart::clean();

    foreach ($testProducts as $product) {
        $this->request->setMethod('POST')
                ->setPost(array(
                    'product_id' => $product["product_id"],
                    'quantity' => $product["product_quantity"]
                ));

        $this->dispatch($this->getRouteUrl("add_to_shopping_cart"));
        $this->assertResponseCode('200');
    }

    $products = Ecommerce_Model_Shoppingcart::getData();
    $this->assertTrue($products[2][0]["product"] instanceof Ecommerce_Model_Product);
    $this->assertEquals($products[2][0]["quantity"],
            "8");

    $this->assertTrue($products[2][1]["product"] instanceof Ecommerce_Model_Product);
    $this->assertEquals($products[2][1]["quantity"],
            "1");

    var_dump($_SESSION);
}

Во втором тесте предпринимается попытка получить продукты, запрашивая модель, что значение var_dump($_SESSION) равно нулю уже в начале теста. Переменные сеанса были сброшены, я хочу найти способ их сохранения, кто-нибудь может помочь?

public function testCanDisplayShoppingCartWidget()  {
    var_dump($_SESSION);
    $this->dispatch($this->getRouteUrl("view_shopping_mini_cart"));
    $this->assertResponseCode('200');
}

Ответы [ 3 ]

9 голосов
/ 21 февраля 2012

Извините за указание в неправильном направлении. Вот лучший способ достижения этого, предложенный Эшоули из #phpunit channel of irc.freenode.net:

<?php

# running from the cli doesn't set $_SESSION here on phpunit trunk
if ( !isset( $_SESSION ) ) $_SESSION = array(  );

class FooTest extends PHPUnit_Framework_TestCase {
    protected $backupGlobalsBlacklist = array( '_SESSION' );

    public function testOne(  ) {
        $_SESSION['foo'] = 'bar';
    }

    public function testTwo(  ) {
        $this->assertEquals( 'bar', $_SESSION['foo'] );
    }

}

?>

== КОНЕЦ ОБНОВЛЕНИЯ

  1. В функции tearDown () : скопировать $ _SESSION в атрибут класса и
  2. В функции setUp () : скопировать атрибут класса в $ _SESSION

Например, этот тест не пройден при удалении функций setUp () и tearDown ():

<?php
# Usage: save this to test.php and run phpunit test.php    

# running from the cli doesn't set $_SESSION here on phpunit trunk                                                                                                
if ( !isset( $_SESSION ) ) $_SESSION = array(  );

class FooTest extends PHPUnit_Framework_TestCase {
    public static $shared_session = array(  ); 

    public function setUp() {
        $_SESSION = FooTest::$shared_session;
    }  

    public function tearDown() {

        FooTest::$shared_session = $_SESSION;
    }  

    public function testOne(  ) {
        $_SESSION['foo'] = 'bar';
    }  

    public function testTwo(  ) {
        $this->assertEquals( 'bar', $_SESSION['foo'] ); 
    }  
}

Также есть функция backupGlobals , но она не работает для меня. Вы должны попробовать, подумал, может быть, он работает на стабильном PHPUnit.

2 голосов
/ 10 сентября 2014

это очень уродливо делать это. Правильный путь должен использовать внедрение зависимости.

Это подразумевает изменение исходного кода для использования этого класса вместо сеансов напрямую:

class Session
{
  private $adapter;
  public static function init(SessionAdapter $adapter)
  {
    self::$adapter = $adapter;
  }
  public static function get($var)
  {
      return self::$adapter->get($var);
  }
  public static function set($var, $value)
  {
    return self::$adapter->set($var, $value);
  }
}

interface SessionAdapter
{
  public function get($var);
  public function set($var, $value);
}

Дополнительная информация:

0 голосов
/ 31 августа 2016

Вы также можете просто создать случайный идентификатор сеанса для своего теста PHPUnit, а затем убедиться, что вы передаете этот идентификатор сеанса в cookie при каждом последующем вызове. При использовании Curl вы должны использовать параметр CURLOPT_COOKIE и установить его на 'PHPSESSID=thesessionidofyourunittest' следующим образом:

$ch = curl_init($url);
curl_setopt($ch, CURLOPT_COOKIE, 'PHPSESSID=thesessionidofyourunittest');

Я объяснил более подробно и с примером в этот ответ stackoverflow .

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...