protected function loadTemplate($moduleParts, $contentType, $parentTemplate, &$globals, $isFinalPass, $isDependentPass) { $this->globals = $globals; $template = new Template(); $template->setContentType($contentType); $moduleString = $moduleParts[0]; $moduleName = $moduleParts[1]; $moduleParams = isset($moduleParts[3]) ? $moduleParts[3] : null; $parentLocals = !empty($parentTemplate) ? $parentTemplate->getLocals() : array(); $template->setName($this->parseFormatVariables($moduleName, $parentLocals)); if ($this->benchmarkRendering) { $this->Benchmark->start('load-template-' . $template->getName()); } $matchString = '{% template ' . $template->getName(); // $this->Logger->error($template->getName()); $usesGlobals = false; $deferable = false; $params = array(); if (!empty($moduleParams)) { $matchString .= '?'; $nvps = explode('&', html_entity_decode($moduleParams, ENT_QUOTES)); foreach ($nvps as $param) { $split = explode('=', $param, 2); if ($split === FALSE || count($split) == 1) { throw new Exception('Bad NVP in template call: ' . $moduleString); } list($name, $value) = $split; $dataparam = null; $previouslyFound = array(); if (substr($value, 0, 1) == '%' && substr($value, -1) == '%' && strpos(substr($value, 1, -1), '%') === FALSE) { $paramval = 'Data:' . substr($value, 1, -1); $dataparam = substr($value, 1, -1); // $template->setDependent(true); // $this->Logger->debug('Marking template ['.$template->getName().'] as dependent'); } else { $paramval = $value; if (strpos($paramval, 'Data:') === 0) { $dataparam = substr($paramval, 5); // $template->setDependent(true); // $this->Logger->debug('Marking template ['.$template->getName().'] as dependent'); // $this->Logger->error('Marking template ['.$template->getName().'] as dependent'); } elseif (strpos($paramval, 'Global:') === 0) { $dataparam = substr($paramval, 7); $deferable = true; $usesGlobals = true; } } if (strlen($dataparam) >= 3 && strpos($dataparam, '%') !== false) { $dataparam = $this->parseFormatVariables($dataparam, $parentLocals); } switch ($name) { // manual datasource parameter case 'data': if (!empty($params)) { throw new Exception("Error in template call {$moduleString} :: data parameter must be first parameter"); } $template->setDependent(true); if ($dataparam == 'DataSource') { if (empty($parentTemplate)) { throw new Exception('Impossible to use DataSource from non-existent parent template'); } $template->setData($parentTemplate->getData()); } elseif (array_key_exists($dataparam, $parentLocals)) { $template->setData($parentLocals[$dataparam]); } elseif (array_key_exists($dataparam, $this->getConstants())) { $template->setData($this->getConstant($dataparam)); } elseif (array_key_exists($dataparam, $globals)) { $template->setData($globals[$dataparam]); } elseif (strpos($dataparam, '.') !== false) { $parts = explode('.', $dataparam); if (!empty($parts)) { $broken = true; $array = $parentLocals; foreach ($parts as $pname) { if (isset($array[$pname])) { $array = $array[$pname]; $broken = false; } else { $broken = true; break; } } if (!$broken) { $value = $array; } } } if ($template->hasData() && !is_array($template->getData())) { $template->setData(array($template->getData())); } // throw new Exception("Invalid data parameter in template call ".$moduleString.", must be an array :: $dataparam\n"); break; // inherit all locals from parent // inherit all locals from parent case 'inherit': if (StringUtils::strToBool($value) == true) { $template->setDependent(true); $newParents = $parentLocals; unset($newParents['CacheTime']); unset($newParents['DataSource']); $params = array_merge($newParents, $params); } break; case 'dependent': if (StringUtils::strToBool($value) == true) { $template->setDependent(true); } break; default: if ($dataparam != null) { if ($usesGlobals) { if (!$isFinalPass) { if (!empty($previouslyFound)) { $this->globals = array_merge($this->globals, $previouslyFound); $previouslyFound = array(); } if (array_key_exists($dataparam, $parentLocals)) { $this->globals[$dataparam] = $parentLocals[$dataparam]; $value = 'Global:' . $dataparam; } } else { if (array_key_exists($dataparam, $this->getConstants())) { $value = $this->getConstant($dataparam); } elseif (array_key_exists($dataparam, $globals)) { $value = $globals[$dataparam]; } } $template->setDeferred(true); } else { if (array_key_exists($dataparam, $this->getConstants())) { $value = $this->getConstant($dataparam); // } elseif (array_key_exists($dataparam, $this->deferredOrDependentParams)) { // $value = $this->deferredOrDependentParams[$dataparam]; // } elseif ((!$deferable || $isFinalPass) && array_key_exists($dataparam, $globals)) { // $value = $globals[$dataparam]; // } elseif (!$deferable && array_key_exists($dataparam, $parentLocals)) { } elseif (array_key_exists($dataparam, $parentLocals)) { $value = $parentLocals[$dataparam]; $previouslyFound[$dataparam] = $value; // if we're deferred or only parsing data dependent modules and this module is independent, // save the passed parameters for later // $this->Logger->error('Deferred? '.$template->isDeferred()); // $this->Logger->error('Independent? '.($isDependentPass && !$template->isDependent())); // if ($template->isDeferred() || ($isDependentPass && !$template->isDependent())) { // $c = $this->deferredOrDependentParamCount++; // $this->deferredOrDependentParams[$dataparam.$c] = $parentLocals[$dataparam]; // $paramval = 'Data:'.$dataparam.$c; // $this->Logger->error('Defer ['.$name.'] param: '.$paramval); // } else { // $value = $parentLocals[$dataparam]; // } } elseif (strpos($dataparam, '.') !== false) { $parts = explode('.', $dataparam); if (!empty($parts)) { $broken = true; $array = $parentLocals; foreach ($parts as $pname) { if (isset($array[$pname])) { $array = $array[$pname]; $broken = false; } else { $broken = true; break; } } if (!$broken) { $value = $array; } else { $value = ''; } // elseif (!$isFinalPass && $deferable) // $template->setDeferred(true); } // } elseif (!$isFinalPass && $deferable) { // // defer setting a value until the final pass // $template->setDeferred(true); } else { $value = ''; } } } elseif (strlen($value) >= 4 && strpos($value, '%') !== false) { $value = $this->parseFormatVariables($value, $parentLocals); $paramval = $value; } $params[$name] = $value; break; } $matchString = $matchString . $name . '=' . $paramval . '&'; } $matchString = substr($matchString, 0, -1); } $matchString .= ' %}'; $template->setMatchString($matchString); $template->setLocals($params); $this->Logger->debug("Loaded template call: " . $matchString); if ($this->benchmarkRendering) { $this->Benchmark->end('load-template-' . $template->getName()); } // $template = $this->loadTemplateExtended($template, $globals); return $template; }