prepare() public static method

Get a working render function by a string of PHP code. This method may requires php setting allow_url_include=1 and allow_url_fopen=1 , or access right to tmp file system.
Deprecation:
public static prepare ( string $php, string | null $tmpDir = null, boolean $delete = true ) : Closure | false
$php string PHP code
$tmpDir string | null Optional, change temp directory for php include file saved by prepare() when cannot include PHP code with data:// format.
$delete boolean Optional, delete temp php file when set to tru. Default is true, set it to false for debug propose
return Closure | false result of include()
 /**
  * @dataProvider issueProvider
  */
 public function testIssues($issue)
 {
     global $tmpdir;
     $php = LightnCandy::compile($issue['template'], isset($issue['options']) ? $issue['options'] : null);
     $context = LightnCandy::getContext();
     $parsed = print_r(LightnCandy::$lastParsed, true);
     if (count($context['error'])) {
         $this->fail('Compile failed due to:' . print_r($context['error'], true) . "\nPARSED: {$parsed}");
     }
     $renderer = LightnCandy::prepare($php);
     $this->assertEquals($issue['expected'], $renderer($issue['data'], array('debug' => $issue['debug'])), "PHP CODE:\n{$php}\n{$parsed}");
 }
Beispiel #2
0
 /**
  * @dataProvider renderErrorProvider
  */
 public function testRenderingErrorLog($test)
 {
     start_catch_error_log();
     $php = LightnCandy::compile($test['template'], $test['options']);
     $renderer = LightnCandy::prepare($php);
     $renderer(null, array('debug' => Runtime::DEBUG_ERROR_LOG));
     $e = stop_catch_error_log();
     if ($e) {
         $this->assertEquals(array($test['expected']), $e);
     } else {
         $this->markTestIncomplete('skip HHVM');
     }
 }
Beispiel #3
0
 public function renderWidget($widget)
 {
     $filename = get_class($widget) . '.hbs';
     $filename = str_replace('\\', '/', $filename);
     $filename = $this->themePath . '/' . $filename;
     if (!file_exists($filename)) {
         throw new RuntimeException("Can't find widget template: " . $filename);
     }
     $template = file_get_contents($filename);
     $helper = new Helper();
     $phpStr = LightnCandy::compile($template, ['flags' => LightnCandy::FLAG_INSTANCE | LightnCandy::FLAG_METHOD, 'helpers' => ['route' => 'Materia\\Helper::route']]);
     $renderer = LightnCandy::prepare($phpStr);
     $data = ['widget' => $widget];
     $data['urlGenerator'] = $this->urlGenerator;
     $data['materia'] = $this;
     return $renderer($data);
 }
 /**
  * @dataProvider jsonSpecProvider
  */
 public function testSpecs($spec)
 {
     global $tmpdir;
     $flag = LightnCandy::FLAG_MUSTACHE | LightnCandy::FLAG_ERROR_EXCEPTION;
     if ($spec['name'] == 'Interpolation - Expansion' || $spec['name'] == 'Interpolation - Alternate Delimiters' || $spec['desc'] == 'Lambdas used for sections should receive the raw section string.' || $spec['name'] == 'Section - Expansion' || $spec['name'] == 'Section - Alternate Delimiters' || $spec['name'] == 'Section - Multiple Calls' || $spec['name'] == 'Inverted Section') {
         $this->markTestIncomplete('Not supported case: complex mustache lambdas');
     }
     if (isset($spec['data']['lambda']['php'])) {
         $spec['data']['lambda'] = getFunctionCode('function ($text = null) {' . $spec['data']['lambda']['php'] . '}');
     }
     foreach (array($flag, $flag | LightnCandy::FLAG_STANDALONEPHP) as $f) {
         global $calls;
         $calls = 0;
         $php = LightnCandy::compile($spec['template'], array('flags' => $f, 'partials' => isset($spec['partials']) ? $spec['partials'] : null, 'basedir' => $tmpdir));
         $parsed = print_r(LightnCandy::$lastParsed, true);
         $renderer = LightnCandy::prepare($php);
         $this->assertEquals($spec['expected'], $renderer($spec['data'], array('debug' => 0)), "SPEC:\n" . print_r($spec, true) . "\nPHP CODE: {$php}\nPARSED: {$parsed}");
     }
 }
 /**
  * @dataProvider jsonSpecProvider
  */
 public function testSpecs($spec)
 {
     global $tmpdir;
     global $tested;
     global $test_flags;
     recursive_unset($spec, '!sparsearray');
     recursive_lambda_fix($spec['data']);
     if (isset($spec['options']['data'])) {
         recursive_lambda_fix($spec['options']['data']);
     }
     //// Skip bad specs
     // 1. No expected nor exception in spec
     if (!isset($spec['expected']) && !isset($spec['exception'])) {
         $this->markTestIncomplete("Skip [{$spec['file']}#{$spec['description']}]#{$spec['no']} , no expected result in spec, skip.");
     }
     // 2. Not supported case: foo/bar path
     if ($spec['it'] === 'literal paths' && $spec['no'] === 58 || $spec['it'] === 'literal paths' && $spec['no'] === 59 || $spec['it'] === 'this keyword nested inside path' || $spec['it'] === 'this keyword nested inside helpers param' || $spec['it'] === 'should handle invalid paths' || $spec['it'] === 'parameter data throws when using complex scope references' || $spec['it'] === 'block with complex lookup using nested context') {
         $this->markTestIncomplete('Not supported case: foo/bar path');
     }
     // 3. Different API, no need to test
     if ($spec['it'] === 'registering undefined partial throws an exception') {
         $this->markTestIncomplete('Not supported case: just skip it');
     }
     // 4. block parameters, special case now do not support
     if ($spec['it'] === 'should not take presedence over pathed values') {
         $this->markTestIncomplete('Not supported case: just skip it');
     }
     // 5. Not supported case: helperMissing and blockHelperMissing
     if ($spec['it'] === 'if a context is not found, helperMissing is used' || $spec['it'] === 'if a context is not found, custom helperMissing is used' || $spec['it'] === 'if a value is not found, custom helperMissing is used' || $spec['it'] === 'should include in simple block calls' || $spec['it'] === 'should include full id' || $spec['it'] === 'should include full id if a hash is passed' || $spec['it'] === 'lambdas resolved by blockHelperMissing are bound to the context') {
         $this->markTestIncomplete('Not supported case: just skip it');
     }
     // 6. Not supported case: misc
     if ($spec['description'] === 'compat mode' || $spec['description'] === 'directives' || $spec['file'] === 'specs/handlebars/spec/track-ids.json' || $spec['it'] === 'knows how to report the correct line number in errors' || $spec['it'] === 'knows how to report the correct line number in errors when the first character is a newline' || $spec['it'] === 'should allow block params on chained helpers' || $spec['it'] === 'chained inverted sections' || $spec['description'] === 'decorators' || $spec['it'] === 'helper for raw block gets parameters' || $spec['template'] === '{{foo}') {
         $this->markTestIncomplete('Not supported case: just skip it');
     }
     // TODO: require fix
     if ($spec['template'] === '{{#with .}}{{#*inline "myPartial"}}success{{/inline}}{{/with}}{{> myPartial}}' || $spec['it'] === 'functions returning safestrings shouldn\'t be escaped' || $spec['it'] === 'rendering function partial in vm mode' || $spec['it'] === 'provides each nested helper invocation its own options hash' || $spec['template'] === '{{echo (header)}}' || $spec['it'] === 'block functions without context argument' || $spec['it'] === 'depthed block functions with context argument' || $spec['it'] === 'block functions with context argument') {
         $this->markTestIncomplete('TODO: require fix');
     }
     // FIX SPEC
     if ($spec['it'] === 'should take presednece over parent block params') {
         $spec['helpers']['goodbyes']['php'] = 'function($options) { static $value; if($value === null) { $value = 1; } return $options->fn(array("value" => "bar"), array("blockParams" => ($options["fn.blockParams"] === 1) ? array($value++, $value++) : null));}';
     }
     if ($spec['it'] === 'should handle undefined and null' && $spec['expected'] === 'true true object') {
         $spec['expected'] = 'true true array';
     }
     foreach ($test_flags as $f) {
         // setup helpers
         $tested++;
         $helpers = array();
         $helpersList = '';
         foreach (array_merge(isset($spec['globalHelpers']) && is_array($spec['globalHelpers']) ? $spec['globalHelpers'] : array(), isset($spec['helpers']) && is_array($spec['helpers']) ? $spec['helpers'] : array()) as $name => $func) {
             if (!isset($func['php'])) {
                 $this->markTestIncomplete("Skip [{$spec['file']}#{$spec['description']}]#{$spec['no']} , no PHP helper code provided for this case.");
             }
             $hname = preg_replace('/\\.|\\//', '_', "custom_helper_{$spec['no']}_{$tested}_{$name}");
             $helpers[$name] = $hname;
             $helper = preg_replace('/\\$options->(\\w+)/', '$options[\'$1\']', patch_this(preg_replace('/\\$block\\/\\*\\[\'(.+?)\'\\]\\*\\/->(.+?)\\(/', '$block[\'$2\'](', patch_safestring(preg_replace('/function/', "function {$hname}", $func['php'], 1)))));
             if ($spec['it'] === 'helper block with complex lookup expression' && $name === 'goodbyes') {
                 $helper = preg_replace('/\\[\'fn\'\\]\\(\\)/', '[\'fn\'](array())', $helper);
             }
             $helpersList .= "{$helper}\n";
             eval($helper);
         }
         try {
             $partials = isset($spec['globalPartials']) ? $spec['globalPartials'] : array();
             // Do not use array_merge() here because it destories numeric key
             if (isset($spec['partials'])) {
                 foreach ($spec['partials'] as $k => $v) {
                     $partials[$k] = $v;
                 }
             }
             if (isset($spec['compileOptions']['preventIndent'])) {
                 if ($spec['compileOptions']['preventIndent']) {
                     $f = $f | LightnCandy::FLAG_PREVENTINDENT;
                 }
             }
             if (isset($spec['compileOptions']['explicitPartialContext'])) {
                 if ($spec['compileOptions']['explicitPartialContext']) {
                     $f = $f | LightnCandy::FLAG_PARTIALNEWCONTEXT;
                 }
             }
             if (isset($spec['compileOptions']['ignoreStandalone'])) {
                 if ($spec['compileOptions']['ignoreStandalone']) {
                     $f = $f | LightnCandy::FLAG_IGNORESTANDALONE;
                 }
             }
             if (isset($spec['compileOptions']['stringParams'])) {
                 if ($spec['compileOptions']['stringParams']) {
                     $f = $f | LightnCandy::FLAG_STRINGPARAMS;
                 }
             }
             if (isset($spec['compileOptions']['knownHelpersOnly'])) {
                 if ($spec['compileOptions']['knownHelpersOnly']) {
                     $f = $f | LightnCandy::FLAG_KNOWNHELPERSONLY;
                 }
             }
             $php = LightnCandy::compile($spec['template'], array('flags' => $f, 'hbhelpers' => $helpers, 'basedir' => $tmpdir, 'partials' => $partials));
             $parsed = print_r(LightnCandy::$lastParsed, true);
         } catch (Exception $e) {
             // Exception as expected, pass!
             if (isset($spec['exception'])) {
                 continue;
             }
             // Failed this case
             $this->fail('Exception:' . $e->getMessage());
         }
         $renderer = LightnCandy::prepare($php);
         if ($spec['description'] === 'Tokenizer') {
             // no compile error means passed
             continue;
         }
         try {
             $ropt = array('debug' => Runtime::DEBUG_ERROR_EXCEPTION);
             if (isset($spec['options']['data'])) {
                 $ropt['data'] = $spec['options']['data'];
             }
             $result = $renderer($spec['data'], $ropt);
         } catch (Exception $e) {
             if (!isset($spec['expected'])) {
                 // expected error and catched here, so passed
                 continue;
             }
             $this->fail("Rendering Error in {$spec['file']}#{$spec['description']}]#{$spec['no']}:{$spec['it']} PHP CODE: {$php}\nPARSED: {$parsed}\n" . $e->getMessage());
         }
         if (!isset($spec['expected'])) {
             $this->fail('Should Fail:' . print_r($spec, true) . "PHP CODE: {$php}\nPARSED: {$parsed}\nHELPERS:{$helpersList}");
         }
         $this->assertEquals($spec['expected'], $result, "[{$spec['file']}#{$spec['description']}]#{$spec['no']}:{$spec['it']} PHP CODE: {$php}\nPARSED: {$parsed}\nHELPERS:{$helpersList}");
     }
 }
<?php

use LightnCandy\LightnCandy;
$template = '{{> (partial_name_helper type)}}';
$data = array('type' => 'dog', 'name' => 'Lucky', 'age' => 5);
function partial_name_helper($type)
{
    switch ($type[0]) {
        case 'man':
        case 'woman':
            return 'people';
        case 'dog':
        case 'cat':
            return 'animal';
        default:
            return 'default';
    }
}
$php = LightnCandy::compile($template, array('flags' => LightnCandy::FLAG_HANDLEBARSJS | LightnCandy::FLAG_RUNTIMEPARTIAL | LightnCandy::FLAG_ERROR_EXCEPTION, 'helpers' => array('partial_name_helper'), 'partials' => array('people' => 'This is {{name}}, he is {{age}} years old.', 'animal' => 'This is {{name}}, it is {{age}} years old.', 'default' => 'This is {{name}}.')));
$renderer = LightnCandy::prepare($php);
echo "Data:\n";
print_r($data);
echo "\nTemplate:\n{$template}\n";
echo "\nCode:\n{$php}\n\n";
echo "\nOutput:\n";
echo $renderer($data);
echo "\n";
 /**
  * Fetch rendered template
  *
  * @param  string $template Template pathname relative to templates directory
  * @param  array  $data     Associative array of template variables
  *
  * @return string
  */
 public function fetch($template, $data = [])
 {
     $data = array_merge($this->defaultVariables, $data);
     $php = Engine::compile($this->getTemplate($template), array('flags' => Engine::FLAG_ERROR_EXCEPTION | Engine::FLAG_ERROR_LOG | Engine::FLAG_INSTANCE | Engine::FLAG_MUSTACHE | Engine::FLAG_HANDLEBARS, 'basedir' => $this->directories, 'fileext' => $this->extensions, 'helpers' => $this->helpers, 'hbhelpers' => $this->block_helpers));
     $renderer = Engine::prepare($php);
     return $renderer(array_merge($data ?: array()), LCRun3::DEBUG_ERROR_LOG);
 }