Skip to content

Commit

Permalink
Tests + Travis + Phpstan
Browse files Browse the repository at this point in the history
  • Loading branch information
vitkutny committed Mar 8, 2017
1 parent 0763191 commit 3c3b57c
Show file tree
Hide file tree
Showing 10 changed files with 233 additions and 15 deletions.
1 change: 0 additions & 1 deletion .gitignore
Original file line number Diff line number Diff line change
@@ -1,3 +1,2 @@
/vendor
/composer.lock
/composer.phar
17 changes: 17 additions & 0 deletions .travis.yml
Original file line number Diff line number Diff line change
@@ -0,0 +1,17 @@
language: php
php:
- 7.0
- 7.1

script:
- vendor/bin/phpstan analyse -l 5 -c phpstan.neon src
- vendor/bin/tester tests

before_script:
- travis_retry composer install --no-interaction --prefer-dist

sudo: false

cache:
directories:
- $HOME/.composer/cache
10 changes: 0 additions & 10 deletions Makefile

This file was deleted.

2 changes: 2 additions & 0 deletions README.md
Original file line number Diff line number Diff line change
@@ -1,5 +1,7 @@
# AsyncControl

[![Build Status](https://travis-ci.org/peckadesign/AsyncControl.svg?branch=master)](https://travis-ci.org/peckadesign/AsyncControl)

Trait for asynchronous control rendering.

## Usage
Expand Down
4 changes: 3 additions & 1 deletion composer.json
Original file line number Diff line number Diff line change
Expand Up @@ -25,7 +25,9 @@
"nette/application": "^2.2"
},
"require-dev": {
"phpstan/phpstan": "~0.6.0"
"phpstan/phpstan": "~0.6.0",
"nette/tester": "~1.7.0",
"mockery/mockery": "~0.9.0"
},
"autoload": {
"psr-4": {
Expand Down
10 changes: 10 additions & 0 deletions phpstan.neon
Original file line number Diff line number Diff line change
@@ -0,0 +1,10 @@
parameters:
ignoreErrors:
- '#Call to an undefined method [a-zA-Z0-9\\_]+::renderAsync\(\)#'
- '#Call to an undefined method [a-zA-Z0-9\\_]+::render\(\)#'
fileExtensions:
- phpt

autoload_directories:
# - %rootDir%/../../../test

12 changes: 12 additions & 0 deletions src/UI/AsyncControl.php
Original file line number Diff line number Diff line change
@@ -0,0 +1,12 @@
<?php declare(strict_types = 1);

namespace Pd\AsyncControl\UI;

use Nette\Application\UI\Control;


class AsyncControl extends Control
{

use AsyncControlTrait;
}
8 changes: 5 additions & 3 deletions src/UI/AsyncControlTrait.php
Original file line number Diff line number Diff line change
Expand Up @@ -4,7 +4,7 @@

use Nette\Application\UI\Control;
use Nette\Application\UI\Presenter;
use Nette\Application\UI\PresenterComponent;
use Nette\Bridges\ApplicationLatte\Template;


/**
Expand All @@ -21,7 +21,7 @@ trait AsyncControlTrait

public function handleAsyncLoad()
{
if ( ! $this instanceof PresenterComponent || ! ($presenter = $this->getPresenter(FALSE)) || ! $presenter->isAjax()) {
if ( ! $this instanceof Control || ! ($presenter = $this->getPresenter(FALSE)) || ! $presenter->isAjax()) {
return;
}
ob_start(function () {
Expand Down Expand Up @@ -49,7 +49,9 @@ public function renderAsync(string $linkMessage = NULL, array $linkAttributes =
&& strpos((string) $this->getPresenter()->getParameter(Presenter::SIGNAL_KEY), sprintf('%s-', $this->getUniqueId())) !== 0
) {
$template = $this->createTemplate();
$template->link = new AsyncControlLink($linkMessage, $linkAttributes);
if ($template instanceof Template) {
$template->add('link', new AsyncControlLink($linkMessage, $linkAttributes));
}
$template->setFile(__DIR__ . '/templates/asyncLoadLink.latte');
$template->render();
} elseif (is_callable($this->asyncRenderer)) {
Expand Down
38 changes: 38 additions & 0 deletions tests/UI/AsyncControlLinkTest.phpt
Original file line number Diff line number Diff line change
@@ -0,0 +1,38 @@
<?php declare(strict_types = 1);

namespace Pd\AsyncControl\UI;

use Tester\Assert;
use Tester\TestCase;


require_once __DIR__ . '/../../vendor/autoload.php';


final class AsyncControlLinkTest extends TestCase
{

public function testLink()
{
$link = new AsyncControlLink;
Assert::equal('Load content', $link->getMessage());
Assert::equal([], $link->getAttributes());

$link = new AsyncControlLink('Custom message', ['foo' => 'bar']);
Assert::equal('Custom message', $link->getMessage());
Assert::equal(['foo' => 'bar'], $link->getAttributes());

AsyncControlLink::setDefault('Default message', ['bar' => 'baz']);

$link = new AsyncControlLink;
Assert::equal('Default message', $link->getMessage());
Assert::equal(['bar' => 'baz'], $link->getAttributes());

$link = new AsyncControlLink('Custom message', ['foo' => 'bar']);
Assert::equal('Custom message', $link->getMessage());
Assert::equal(['foo' => 'bar'], $link->getAttributes());
}
}


(new AsyncControlLinkTest)->run();
146 changes: 146 additions & 0 deletions tests/UI/AsyncControlTest.phpt
Original file line number Diff line number Diff line change
@@ -0,0 +1,146 @@
<?php declare(strict_types = 1);

namespace Pd\AsyncControl\UI;

use Mockery;
use Nette\Application\UI\ITemplate;
use Nette\Application\UI\ITemplateFactory;
use Nette\Application\UI\Presenter;
use Tester\Assert;
use Tester\TestCase;


require_once __DIR__ . '/../../vendor/autoload.php';


final class AsyncControlTest extends TestCase
{

const VALID_SIGNAL = 'control-form-submit';
const FRAGMENT_PARAMETER = '_escaped_fragment_';


public function testHandleAjax()
{
$presenter = Mockery::mock(Presenter::class);
$presenter->shouldReceive('isAjax')->once()->andReturn(TRUE);
$presenter->shouldReceive('getPayload')->andReturn($payload = new \stdClass);
$presenter->shouldReceive('sendPayload')->once();
/**
* @var AsyncControl|Mockery\Mock $control
*/
$control = Mockery::mock(AsyncControl::class)->makePartial();
$control->shouldReceive('getPresenter')->andReturn($presenter);
$renderedContent = 'rendered content';
$control->shouldReceive('renderAsync')->once()->andReturnUsing(function () use ($renderedContent) {
echo $renderedContent;
})
;
$control->shouldReceive('getSnippetId')->with('async')->andReturn($snippetId = 'snippet-control-async');
$control->handleAsyncLoad();

Assert::equal(['snippets' => [$snippetId => $renderedContent]], (array) $payload);
}


public function testHandleNoAjax()
{
$presenter = Mockery::mock(Presenter::class);
$presenter->shouldReceive('isAjax')->once()->andReturn(FALSE);
$presenter->shouldNotReceive('getPayload');
$presenter->shouldNotReceive('sendPayload');
/**
* @var AsyncControl|Mockery\Mock $control
*/
$control = Mockery::mock(AsyncControl::class)->makePartial();
$control->shouldReceive('getPresenter')->andReturn($presenter);
$control->shouldNotReceive('renderAsync');
$control->shouldNotReceive('getSnippetId');
$control->handleAsyncLoad();
}


public function testRenderAsyncLoadLink()
{
/**
* @var AsyncControl|Mockery\Mock $control
*/
$control = Mockery::mock(AsyncControl::class)->makePartial();

$template = Mockery::mock(ITemplate::class);
$template->shouldReceive('setFile')->once()->withAnyArgs();
$template->shouldReceive('render')->once();

$templateFactory = Mockery::mock(ITemplateFactory::class);
$templateFactory->shouldReceive('createTemplate')->once()->with($control)->andReturn($template);

$presenter = Mockery::mock(Presenter::class);
$presenter->shouldReceive('getParameter')->once()->with(self::FRAGMENT_PARAMETER)->andReturn(NULL);
$presenter->shouldReceive('getParameter')->once()->with(Presenter::SIGNAL_KEY)->andReturn(NULL);
$presenter->shouldReceive('getTemplateFactory')->once()->andReturn($templateFactory);

$control->shouldReceive('getPresenter')->andReturn($presenter);
$control->shouldReceive('getUniqueId')->once()->andReturn('control');
$control->renderAsync();
}


public function testRenderWithSignal()
{
$presenter = Mockery::mock(Presenter::class);
$presenter->shouldReceive('getParameter')->once()->with(self::FRAGMENT_PARAMETER)->andReturn(NULL);
$presenter->shouldReceive('getParameter')->once()->with(Presenter::SIGNAL_KEY)->andReturn(self::VALID_SIGNAL);
/**
* @var AsyncControl|Mockery\Mock $control
*/
$control = Mockery::mock(AsyncControl::class)->makePartial();
$control->shouldReceive('getPresenter')->andReturn($presenter);
$control->shouldReceive('getUniqueId')->once()->andReturn('control');
$control->shouldReceive('render')->once();
$control->renderAsync();
}


public function testRenderWithFragment()
{
$presenter = Mockery::mock(Presenter::class);
$presenter->shouldReceive('getParameter')->once()->with(self::FRAGMENT_PARAMETER)->andReturn('');
/**
* @var AsyncControl|Mockery\Mock $control
*/
$control = Mockery::mock(AsyncControl::class)->makePartial();
$control->shouldReceive('getPresenter')->andReturn($presenter);
$control->shouldReceive('render')->once();
$control->renderAsync();
}


public function testRenderAsyncRenderer()
{
$presenter = Mockery::mock(Presenter::class);
$presenter->shouldReceive('getParameter')->once()->with(self::FRAGMENT_PARAMETER)->andReturn(NULL);
$presenter->shouldReceive('getParameter')->once()->with(Presenter::SIGNAL_KEY)->andReturn(self::VALID_SIGNAL);
/**
* @var AsyncControl|Mockery\Mock $control
*/
$control = Mockery::mock(AsyncControl::class)->makePartial();
$control->shouldReceive('getPresenter')->andReturn($presenter);
$control->shouldReceive('getUniqueId')->once()->andReturn('control');
$asyncRendered = FALSE;
$control->setAsyncRenderer(function () use (&$asyncRendered) {
$asyncRendered = TRUE;
});
$control->renderAsync();
Assert::equal(TRUE, $asyncRendered);
}


protected function tearDown()
{
parent::tearDown();
Mockery::close();
}
}


(new AsyncControlTest)->run();

0 comments on commit 3c3b57c

Please sign in to comment.