From f88dfe61d92ef387f677af17d78d1c0376d23596 Mon Sep 17 00:00:00 2001 From: dyszczo <krzysztof.dyszczyk@gmail.com> Date: Mon, 23 Sep 2019 21:08:49 +0200 Subject: [PATCH] view builder --- CHANGELOG.md | 3 + src/PluginViewBuilder.php | 70 +++++++++++++++++++++ tests/unit/Resolver/TestDirResolver.php | 9 +++ tests/unit/Resolver/TestWpThemeResolver.php | 2 +- tests/unit/TestPluginViewBuilder.php | 36 +++++++++++ tests/unit/stub/template/file.php | 1 + 6 files changed, 120 insertions(+), 1 deletion(-) create mode 100644 CHANGELOG.md create mode 100644 src/PluginViewBuilder.php create mode 100644 tests/unit/TestPluginViewBuilder.php create mode 100644 tests/unit/stub/template/file.php diff --git a/CHANGELOG.md b/CHANGELOG.md new file mode 100644 index 0000000..2fff2e5 --- /dev/null +++ b/CHANGELOG.md @@ -0,0 +1,3 @@ +## [1.1.0] - 2019-09-23 +### Added +- PluginViewBuilder to facilitate building and rendering views for plugins \ No newline at end of file diff --git a/src/PluginViewBuilder.php b/src/PluginViewBuilder.php new file mode 100644 index 0000000..cb96a84 --- /dev/null +++ b/src/PluginViewBuilder.php @@ -0,0 +1,70 @@ +<?php + +namespace WPDesk\View; + +use WPDesk\View\Renderer\SimplePhpRenderer; +use WPDesk\View\Resolver\ChainResolver; +use WPDesk\View\Resolver\DirResolver; +use WPDesk\View\Resolver\WPThemeResolver; + +/** + * Facilitates building of the default plugin renderer. + * + * @package WPDesk\View + */ +class PluginViewBuilder { + /** @var string */ + private $plugin_dir; + + /** @var string[] */ + private $template_dirs; + + /** + * @param string $plugin_dir Plugin directory path(absolute path) + * @param string|string[] $template_dir Directory or list of directories with templates to render + */ + public function __construct( $plugin_dir, $template_dir = 'templates' ) { + $this->plugin_dir = $plugin_dir; + if ( ! is_array( $template_dir ) ) { + $this->template_dirs = [ $template_dir ]; + } else { + $this->template_dirs = $template_dir; + } + } + + /** + * Creates simple renderer that search for the templates in plugin dir and in theme/child dir. + * + * For example if your plugin dir is /plugin, template dir is /templates, theme is /theme, and a child theme is /child + * the templates will be loaded from(order is important): + * - /child/plugin/*.php + * - /theme/plugin/*.php + * - /plugin/templates/*.php + * + * @return SimplePhpRenderer + */ + public function createSimpleRenderer() { + $resolver = new ChainResolver(); + $resolver->appendResolver( new WPThemeResolver( basename( $this->plugin_dir ) ) ); + foreach ( $this->template_dirs as $dir ) { + $dir = trailingslashit( $this->plugin_dir ) . trailingslashit( $dir ); + $resolver->appendResolver( new DirResolver( $dir ) ); + } + return new SimplePhpRenderer( $resolver ); + } + + /** + * Load templates using simple renderer. + * + * @param string $name Name of the template + * @param string $path Additional path of the template ie. for path "path" the templates would be loaded from /plugin/templates/path/*.php + * @param array $args Arguments for templates to use + * + * @return string Rendered template. + */ + public function loadTemplate( $name, $path = '.', $args = array() ) { + $renderer = $this->createSimpleRenderer(); + + return $renderer->render( trailingslashit( $path ) . $name, $args ); + } +} \ No newline at end of file diff --git a/tests/unit/Resolver/TestDirResolver.php b/tests/unit/Resolver/TestDirResolver.php index 7c98760..c8c79f3 100644 --- a/tests/unit/Resolver/TestDirResolver.php +++ b/tests/unit/Resolver/TestDirResolver.php @@ -9,6 +9,15 @@ class TestDirResolver extends \PHPUnit\Framework\TestCase const TEMPLATE_FILE = 'some_template.php'; const TEMPLATE_SUBDIR = 'templates'; + public function setUp() + { + \WP_Mock::setUp(); + } + + public function tearDown() + { + \WP_Mock::tearDown(); + } public function testCanFindInDirPath() { diff --git a/tests/unit/Resolver/TestWpThemeResolver.php b/tests/unit/Resolver/TestWpThemeResolver.php index ddcc43c..635aeeb 100644 --- a/tests/unit/Resolver/TestWpThemeResolver.php +++ b/tests/unit/Resolver/TestWpThemeResolver.php @@ -32,7 +32,7 @@ class TestThemeResolver extends \PHPUnit\Framework\TestCase \WP_Mock::userFunction('trailingslashit', [ 'return' => function ($string) { - return untrailingslashit($string) . '/'; + return rtrim($string, '/\\') . '/'; } ]); diff --git a/tests/unit/TestPluginViewBuilder.php b/tests/unit/TestPluginViewBuilder.php new file mode 100644 index 0000000..fcefdb7 --- /dev/null +++ b/tests/unit/TestPluginViewBuilder.php @@ -0,0 +1,36 @@ +<?php + + +use WPDesk\View\PluginViewBuilder; + +class TestPluginViewBuilder extends \PHPUnit\Framework\TestCase { + public function setUp() { + \WP_Mock::setUp(); + + \WP_Mock::userFunction('trailingslashit', [ + 'return' => function ($string) { + return rtrim($string, '/\\') . '/'; + } + ]); + } + + public function tearDown() + { + \WP_Mock::tearDown(); + } + + public function testCanRenderUsingDir() { + $builder = new PluginViewBuilder( __DIR__ . '/stub', 'template' ); + $renderer = $builder->createSimpleRenderer(); + + $val = 'val to render'; + $args = [ 'singleArg' => $val ]; + $content = $renderer->render( 'file', $args ); + $this->assertRegExp( '/template content/', $content, 'Content from stub/template/file.php should be renderer' ); + $this->assertRegExp( "/{$val}/", $content, 'Content from stub/template/file.php should contain $val' ); + + $contentUsingOtherMethod = $builder->loadTemplate( 'file', '.', $args ); + $this->assertEquals( $content, $contentUsingOtherMethod, + 'Content should be the same no matter the method of render' ); + } +} \ No newline at end of file diff --git a/tests/unit/stub/template/file.php b/tests/unit/stub/template/file.php new file mode 100644 index 0000000..5149c9f --- /dev/null +++ b/tests/unit/stub/template/file.php @@ -0,0 +1 @@ +template content <?php echo $singleArg; ?> \ No newline at end of file -- GitLab