phpUnit новичок - PullRequest
       4

phpUnit новичок

3 голосов
/ 04 декабря 2010

Как мне начать использовать phpUnit в качестве среды тестирования для набора функций и классов, которые я уже сделал?


РЕДАКТИРОВАТЬ: да, я уже прочитал документацию. В основном я пробовал тесты, следуя примеру BankAccount. Но я получаю ошибки:

Warning: require_once(PHP/CodeCoverage/Filter.php) [function.require-once]: failed to open stream: No such file or directory in [...]/unitTest/phpunit.php on line 38.

Кроме того, скрипты php, похоже, начинаются с #!/usr/bin/env php, что указывает на то, что они должны запускаться из консоли. Я бы предпочел запустить их из браузера ...

Предположим, у меня есть функция f1(), которая возвращает строку. Как проводить тесты? Я что-то упустил?

Ответы [ 2 ]

10 голосов
/ 04 декабря 2010

Краткое введение в среду тестирования

PHPUnit предоставляет простую структуру для создания набора тестов для автоматизации тестирования функций и классов.PHPUnit вдохновлен JUnit, который был создан Кентом Беком и Эрихом Гаммой как инструмент для экстремального программирования.Одним из правил XP является тестирование небольших программных компонентов как можно чаще и на ранних этапах. Таким образом, вам не придется исправлять ошибки и ошибки в API при настройке и тестировании более крупных приложений, которые зависят от класса.В то время как модульное тестирование является одним из основных правил в XP, вам не нужно переключаться на XP, чтобы воспользоваться PHPUnit.PHPUnit сам по себе является хорошим инструментом для тестирования классов или набора функций, он облегчит ваш цикл разработки и поможет избежать бесконечных сеансов отладки.

Рабочая процедура

Обычно вы пишете класс, выполняете некоторые несистематические тесты, используя echo() или var_dump().После этого вы используете класс в своем приложении и надеетесь, что все в порядке.Чтобы извлечь выгоду из PHPUnit вы должны переосмыслить поток.Лучший способ сделать это:

  1. создать свой класс / API
  2. создать набор тестов
  3. реализовать класс / API
  4. runнабор тестов
  5. исправляет сбои или ошибки и снова переходит к # 4

Может показаться, что на это потребуется много времени, но это впечатление неверное.Создание набора тестов с использованием PHPUnit занимает всего несколько минут, а запуск набора тестов - всего несколько секунд.

Разработка класса

Начнем с небольшого примера: строкового класса.Сначала мы создаем несколько объявлений функций для работы со строкой:

---- string.php ----

<?php
class String
{
    //contains the internal data
    var $data;

    // constructor
    function String($data) {
        $this->data = $data;
    }

    // creates a deep copy of the string object
    function copy() {
    }

    // adds another string object to this class
    function add($string) {
    }

    // returns the formated string
    function toString($format) {
    }
}
?>

Создание набора тестов

Теперь мы можем создать набор тестов, который проверяет каждую функциювашего класса строки.Набор тестов - это обычный PHP-класс, унаследованный от PHPUnit_TestCase, содержащий тестовые функции, идентифицируемые лидирующим «тестом» в имени функции.В тестовой функции ожидаемое значение должно сравниваться с результатом тестируемой функции.Результат этого сравнения должен делегироваться функции assert*()-family, которая решает, прошла ли функция тест или нет.

---- testcase.php ----

<?php

require_once 'string.php';
require_once 'PHPUnit.php';

class StringTest extends PHPUnit_TestCase
{
    // contains the object handle of the string class
    var $abc;

    // constructor of the test suite
    function StringTest($name) {
       $this->PHPUnit_TestCase($name);
    }

    // called before the test functions will be executed
    // this function is defined in PHPUnit_TestCase and overwritten
    // here
    function setUp() {
        // create a new instance of String with the
        // string 'abc'
        $this->abc = new String("abc");
    }

    // called after the test functions are executed
    // this function is defined in PHPUnit_TestCase and overwritten
    // here
    function tearDown() {
        // delete your instance
        unset($this->abc);
    }

    // test the toString function
    function testToString() {
        $result = $this->abc->toString('contains %s');
        $expected = 'contains abc';
        $this->assertTrue($result == $expected);
    }

    // test the copy function
    function testCopy() {
      $abc2 = $this->abc->copy();
      $this->assertEquals($abc2, $this->abc);
    }

    // test the add function
    function testAdd() {
        $abc2 = new String('123');
        $this->abc->add($abc2);
        $result = $this->abc->toString("%s");
        $expected = "abc123";
        $this->assertTrue($result == $expected);
    }
  }
?>

Первый тестовый запуск

Теперь мы можем запустить первый тест.Убедитесь, что все пути указаны правильно, и затем запустите эту программу PHP.

---- stringtest.php ----

<?php

require_once 'testcase.php';
require_once 'PHPUnit.php';

$suite  = new PHPUnit_TestSuite("StringTest");
$result = PHPUnit::run($suite);

echo $result -> toString();
?>

Если вы вызовете этот скрипт из командной строки, вы получите следующий вывод:

TestCase stringtest->testtostring() failed: expected true, actual false
TestCase stringtest->testcopy() failed: expected , actual Object
TestCase stringtest->testadd() failed: expected true, actual false

Каждая функция не проходит тест, потому что ваши строковые функции не вернули то, что мыопределяется как ожидаемое значение.

Если вы хотите вызвать скрипт через браузер, вы должны поместить скрипт на правильную HTML-страницу и вызвать $result->toHTML() вместо $result->toString().

Реализация

Хорошо, давайте начнем с реализации нашего строкового класса.

---- string.php ----

<?php
class String
{
    //contains the internal data
    var $data;

    // constructor
    function String($data) {
        $this->data = $data;
    }

    // creates a deep copy of the string object
    function copy() {
        $ret = new String($this->data);
        return $ret;
    }

    // adds another string object to this class
    function add($string) {
        $this->data = $this->data.$string->toString("%ss");
    }

    // returns the formated string
    function toString($format) {
        $ret = sprintf($format, $this->data);
        return $ret;
    }
}
?>

Реализация завершена, и мы можем снова запустить тест:

~>
php -f stringtest.php

TestCase stringtest->testtostring() passed
TestCase stringtest->testcopy() passed
TestCase stringtest->testadd() failed: expected true, actual false

Черт возьми!последний тест не удался!Мы допустили опечатку.Измените строку 16 в файле string.php на

<?php
$this->data = $this->data.$string->toString("%s");
?> 

и снова запустите тест:

~>
php -f stringtest.php

TestCase stringtest->testtostring() passed
TestCase stringtest->testcopy() passed
TestCase stringtest->testadd() passed

Теперь все в порядке!

Заключение

Кажется ли вам, что для тестирования трех простых функций требуется много работы?Не забывайте, это маленький пример.Подумайте о больших и более сложных API, таких как абстракция базы данных или классы корзин в приложении магазина.PHPUnit - отличный инструмент для выявления ошибок в реализации вашего класса.

Часто вам захочется переопределить или реорганизовать большой класс, который используется в нескольких различных приложениях.Без набора тестов вероятность того, что вы что-то сломаете в одном из приложений, которые зависят от вашего класса, очень высока.Благодаря модульным тестам вы можете создать набор тестов для своего класса, а затем переопределить ваш класс с уверенностью, зная, что, пока новый класс проходит тесты, приложения, которые зависят от класса, будут работать.

Использованный источник: http://pear.php.net

0 голосов
/ 07 декабря 2010

Я бы действительно рекомендовал запуск PHPUnit из командной строки, если это возможно.В нашей компании это невозможно, но мы пытаемся, что делает наши тесты нестабильными ...

Я предполагаю, что вам нужно настроить некоторые пути включения для php с помощью set_include_path (), поэтому phpunit находит остальнуюваши файлы.Но этого может быть недостаточно ...

Наш код выглядит примерно так

// you will have to write your own class here that collects the tests
$collector = new Unit_Test_Collector();
$suite = $collector->getSuite();

//$config is an array of phpunit config options

PHPUnit_TextUI_TestRunner::run($suite, $config);
Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...