Php Codeception,使用pageObject设计模式和小黄瓜编写验收测试
我正在寻找一个简单的pageObject设计模式和gherkin代码示例,因为当我学习时,所有示例都是在tests/support/AcceptanceTester.php中编写的。我不明白(糟糕的英语技能--)为什么不能将所有代码集中在AcceptanceTester.php文件中 例如,我有一个带有两个按钮a和B的示例主页。如果用户单击按钮a,则加载页面a;如果用户单击按钮B,则加载页面B 目前,我的验收测试仪:Php Codeception,使用pageObject设计模式和小黄瓜编写验收测试,php,codeception,gherkin,pageobjects,Php,Codeception,Gherkin,Pageobjects,我正在寻找一个简单的pageObject设计模式和gherkin代码示例,因为当我学习时,所有示例都是在tests/support/AcceptanceTester.php中编写的。我不明白(糟糕的英语技能--)为什么不能将所有代码集中在AcceptanceTester.php文件中 例如,我有一个带有两个按钮a和B的示例主页。如果用户单击按钮a,则加载页面a;如果用户单击按钮B,则加载页面B 目前,我的验收测试仪: <?php // tests/_support/AcceptanceTe
<?php
// tests/_support/AcceptanceTester.php
/**
* Inherited Methods
* @method void wantToTest($text)
* @method void wantTo($text)
* @method void execute($callable)
* @method void expectTo($prediction)
* @method void expect($prediction)
* @method void amGoingTo($argumentation)
* @method void am($role)
* @method void lookForwardTo($achieveValue)
* @method void comment($description)
* @method \Codeception\Lib\Friend haveFriend($name, $actorClass = NULL)
*
* @SuppressWarnings(PHPMD)
*/
class AcceptanceTester extends \Codeception\Actor
{
use _generated\AcceptanceTesterActions;
/**
* @Given The home page
*/
public function inHomePage()
{
$this->amOnPage("/");
$this->seeInTitle('home');
}
/**
* @When I click on the button A
*/
public function goToThePageA()
{
$this->click(['name' => 'A']);
}
/**
* @Then l go to the page A
*/
public function ImInPageA()
{
$this->seeInTitle('page A');
}
/**
* @When I click on the button B
*/
public function goToThePageB()
{
$this->click(['name' => 'B']);
}
/**
* @Then l go to the page B
*/
public function ImInPageB()
{
$this->seeInTitle('page B');
}
}
<?php
// tests/_support/Page/PageHome.php
namespace Page;
class PageHome
{
public static $URL = '/home';
public static $title = "home";
public static $aButton = ['name' => 'A'] ;
public static $bButton = ['name' => 'B'] ;
public static function route($param){
return static::$URL.$param;
}
/**
* @var \AcceptanceTester;
*/
protected $acceptanceTester;
public function __construct(\AcceptanceTester $I){
$this->acceptanceTester = $I;
}
}
<?php
// tests/_support/Page/PageA.php
namespace Page;
class PageA
{
public static $URL = '/home/pageA';
public static $title = "page A";
public static function route($param){
return static::$URL.$param;
}
/**
* @var \AcceptanceTester;
*/
protected $acceptanceTester;
public function __construct(\AcceptanceTester $I){
$this->acceptanceTester = $I;
}
}
<?php
// tests/_support/Page/PageB.php
namespace Page;
class PageB
{
public static $URL = '/home/pageB';
public static $title = "page B";
public static function route($param){
return static::$URL.$param;
}
/**
* @var \AcceptanceTester;
*/
protected $acceptanceTester;
public function __construct(\AcceptanceTester $I){
$this->acceptanceTester = $I;
}
}
<?php
// tests/_support/Step/Acceptance/HomeChecker.php
namespace Step\Acceptance;
use Page\Acceotance\HomePage;
class HomeChecker extends \AcceptanceTester
{
/**
* @Given The home page
*/
public function main()
{
$homePage = new PageHome($this);
$this->amOnPage($homePage::URL);
$this->checkTitle($homePage);
$this->checkButtons($homePage);
}
private function checkTitle($homePage){
$this->seeInTitle($homePage::$title);
}
private function checkButtons($homePage){
$this->see($homePage::$aButton);
$this->see($homePage::$bButton);
}
}
<?php
// tests/_support/Step/Acceptance/PageAChecker.php
namespace Step\Acceptance;
use Page\PageHome;
use Page\PageA;
class PageAChecker extends \AcceptanceTester
{
/**
* @When I click on the button A
*/
public function clickButton()
{
$homePage = new PageHome($this);
$this->click($homePage::$aButton);
}
/**
* @Then l go to the page A
*/
public function checkTitle()
{
$aPage = new PageA($this);
$this->seeInTitle($aPage::$title);
}
}
<?php
// tests/_support/Step/Acceptance/PageBChecker.php
namespace Step\Acceptance;
use Page\PageHome;
use Page\PageB;
class PageBChecker extends \AcceptanceTester
{
/**
* @When I click on the button B
*/
public function clickButton()
{
$homePage = new PageHome($this);
$this->click($homePage::$bButton);
}
/**
* @Then l go to the page B
*/
public function checkTitle()
{
$bPage = new PageB($this);
$this->seeInTitle($bPage::$title);
}
}
我在shell中收到“在上下文中找不到”警告
好的,如何将小黄瓜文件的执行与我自己的上下文类(PageObjects,StepObjects,…)中定义的步骤链接起来?我们可以阅读Codeception文档中的第“”章:
正如我们前面提到的,应该在上下文类中定义步骤。默认情况下,所有步骤都在Actor类中定义,例如AcceptanceTester。但是,您可以包含更多上下文。这可以在global codeception.yml或套件配置文件中配置:
(…)这样,PageObjects、Helper和StepObjects也可以成为上下文
更好
如果我们继续阅读:
但更可取的做法是通过标记或角色包含上下文类
这意味着,考虑到可扩展性和良好的组织,您不会希望用每个页面对象重载每个测试。因此,您可以按角色、标记或路径分配页面对象(或任何助手类)。见下文关于文件的段落。按照您的示例,并按标记分配:
gherkin:
contexts:
default:
- AcceptanceTester
tag:
myTagX:
- Page\Acceotance\HomePage\HomeChecker
- Page\PageHome
anotherTag:
- Page\Acceotance\another\AnotherChecker
- Page\PageAnother
…在小黄瓜文件中:
@myTagX
Feature
(...)
尝试将依赖项作为方法参数传递,例如,function clickButton($homePage PageHome){$this->click($homePage::$bButton);}
。谢谢您的帮助:)我像您说的那样进行了更改,但得到了相同的输出。。。(的步骤定义我点击按钮B
在上下文中找不到”),我确信您在上述/**/comments函数中设置的消息正在被您的工具解析。你把@notation放在那里了,也许你不应该这样做?我在创建stackoverflow帖子时收到了这些信息:/为了帮助我,我的救世主hahaThis看起来很复杂。“页面对象”和“步骤对象”本质上不是一回事吗?两者都是你反复做的事情的速记符号。把它们结合在一起就像掉进了兔子洞。测试应该容易理解。或者这有什么意义。
@myTagX
Feature
(...)