2017-03-03 50 views
1

我试图测试一个预处理表单并最终保存它的服务。在创建表单中:验证Symfony3-Test服务

$this->container->get('security.token_storage')->getToken()->getUser(); 

被调用以获取当前登录的用户作为字段的默认值。

现在我有这个(扩展Symfony\Bundle\FrameworkBundle\Test\WebTestCase):

private $pages; 
private $formFactory; 

protected function setUp() 
{ 
    self::bootKernel(); 

    $client = self::$kernel->getContainer()->get('test.client'); 
    $client->setServerParameters([ 
    'HTTP_HOST'     => 'ajax.localhost.dev:10190', 
    'CONTENT_TYPE'    => 'application/json', 
    'HTTP_X-Requested-With' => 'XMLHttpRequest', 
    'HTTP_USER_AGENT'   => 'Symfony/2.0', 
    'PHP_AUTH_USER'    => 'root', 
    'PHP_AUTH_PW'    => '[email protected]' 
    ]); 

    $this->pages = self::$kernel->getContainer()->get('app.pages'); 
    $this->formFactory = self::$kernel->getContainer()->get('form.factory'); 
} 

public function testNewPage() { 
    $page = new Page(); 
    //shortened 
    $form = $this->formFactory->create(PageType::class, $page); 
} 

但是,这给我的错误:

Call to a member function getUser() on null 

什么表明,不存在安全令牌。

我该怎么过来?

UPDATE

由于@LBA的意见,我试过了代码,没有运气:

$session = self::$kernel->getContainer()->get('session'); 
$token = new UsernamePasswordToken('root', 'root', 'main', ['ROLE_USER', 'ROLE_ROOT']); 
$session->set('_security_main', serialize($token)); 
$session->save(); 

与设置cookie所描述here丢失,因为$kernel有一部分没有方法getCookieJar()

+0

你确定你有一个登录后的用户? – LBA

+0

@LBA请参阅最新的代码。通过将选项数组传递给'bootKernel()'我错了。但是这也行不通。 – philipp

+0

仍然我不明白您的用户应该如何登录 - 如何在您的应用程序中完成登录?您不会将每个请求的用户名和密码作为服务器参数/标头发送,对吗? – LBA

回答

1

我终于可以像这样工作:

protected function setUp() 
{ 
    self::bootKernel(); 

    $root = new User(); 
    $root->setUsername('root'); 
    $root->setPassword('root'); 
    $root->setEmail('[email protected]'); 

    $token = new UsernamePasswordToken($root, null, 'main', ['ROLE_USER', 'ROLE_ROOT']); 

    self::$kernel->getContainer() 
    ->get('security.token_storage') 
    ->setToken($token); 

    $this->pages = self::$kernel->getContainer()->get('app.pages'); 
    $this->formFactory = self::$kernel->getContainer()->get('form.factory'); 
} 

即使有可能解决这个问题,在这种情况下,真正的问题是,要具有$this->container->get('security.token_storage')->getToken()->getUser();呼叫与形式,因为这打破形式的测试案例。防止这种事情发生的模式是依赖注入,我错过了应用于表单类型。

因此,更好的解决办法是(在扩展AbstractType表格):

public function configureOptions(OptionsResolver $resolver) 
{ 
    $this->setDefined(['user]); 
} 

最后创建表单像这样(在控制器的TestCase)

在一个单元测试:

$user = new User(); 

and in the controller:

$user = $this->container->get('security.token_storage')->getToken()->getUser(); 

$form = $this->formFactory->create(TheFormType::class, 
    <some data object>, 
    ['user' => $user]); 
+0

很高兴你得到它 – LBA