Reputation: 115
I need to port a PHP application using Smarty in PHP environment for Google Application Engine.
reviewing development guidelines:
"An App Engine application cannot:
write to the filesystem. PHP applications can use Google Cloud Storage for storing persistent files. Reading from the filesystem is allowed, and all application files uploaded with the application are available."
Is this limitation applied to compiled smarty templates? because compilation writes them on file system.
I tried locally starting GAE and it works, but I cannot try a deploy because I have not yet an access to production environment.
Have someone news on that? Suggestion? workaround?
Upvotes: 0
Views: 1100
Reputation: 126
You can precompile templates before you deploy them - the idea is to have script that will create all compiled files at once - you have to execute it each time before you do appcfg.py update .
This will avoid using Google Storage at all!
Here is the solution for file tpl resources only - however you can modify it so it supports other resource handlers (e.g. when loading smarty template from database)
Smarty template directory must contain relative path and we need to override behavior of the _realpath in the Smarty Library - in order to have same compiled filenames across different environments.
This is the build.php that builds all Smarty template files in directory app/Templates
require_once('libs/Smarty/libs/Smarty.class.php');
class SmartyCompileDir extends Smarty {
public function _realpath($path, $realpath = null) {
return $path;
}
}
$smarty = new SmartyCompileDir;
$smarty->setCompileDir(__DIR__ . "/template_c");
// Template dir must be relative
$smarty->setTemplateDir("app/Templates");
// make sure the escape html is enabled only if enabled in production!
$smarty->setEscapeHtml(false);
// empty compile directory
foreach (glob(__DIR__ . "/template_c/*.php") as $filename) {
if (is_file($filename)) {
unlink($filename);
}
}
foreach (new RecursiveIteratorIterator(new RecursiveDirectoryIterator("app/Templates", FilesystemIterator::SKIP_DOTS | FilesystemIterator::UNIX_PATHS), RecursiveIteratorIterator::CHILD_FIRST) as $value) {
if ($value->isFile()) {
$file = (string)$value;
$_smarty = clone $smarty;
$_smarty->force_compile = true;
$_tpl = new $smarty->template_class($file, $_smarty);
$_tpl->caching = Smarty::CACHING_OFF;
$_tpl->source = Smarty_Template_Source::load($_tpl);
if ($_tpl->mustCompile()) {
$_tpl->compileTemplateSource();
echo ' compiled ' . $file . "\n";
flush();
} else {
echo ' ' . $file . ' is up to date' . "\n";
flush();
}
}
}
after the build is done, you should have all templates compiled and if you check them out, they should have relative path in the header of the file - e.g. 7c3fc31b70e264e4d45f4ba59da830015ed4025f_0.file.index.tpl.php
/* Smarty version 3.1.29, created on 2016-07-28 13:52:49
from "app/Templates/controls/column-tags.tpl" */
Now, initialization the Smarty in your app like this
require_once(LIBS_DIR . "/Smarty/libs/Smarty.class.php");
class SmartyCompileDir extends \Smarty {
// this is to resolve all ../ to relative path - if you use smarty include function with relative path containing ..
public function _realpath($path, $realpath = null) {
$parts = explode('/', $path);
foreach($parts as $part) {
if ($part == '.') {
continue;
} if ($part == '..') {
array_pop($result);
} else {
$result[] = $part;
}
}
return (implode('/', $result));
}
}
$smarty = new SmartyCompileDir();
// relative path so we work fully from pre-compiled version
$smarty->setTemplateDir("app/Templates");
$smarty->setCompileDir(__DIR__ . "/template_c");
// do not check file modification time
$smarty->setCompileCheck(false);
// this must be set same as in the build script
$smarty->setEscapeHtml(false);
$smarty->display("index.tpl");
deploy your app to the GAE with the template_c directory That's it.
For debugging, you can check function populateCompiledFilepath of Smarty/libs/sysplugins/smarty_template_compiled.php
to get idea, how is Smarty making compiled file names.
Upvotes: 0
Reputation: 36
In smarty 3 demo, i modify the index.php adding this 2 lines:
$smarty->compile_dir= "gs://achievotmp/compiled/"; $smarty->cache_dir="gs://achievotmp/cache/";
And the smarty 3 demo index working both locally and in GAE cloud. (Don forget to create bucket, as in example: achievotmp).
Upvotes: 1
Reputation: 441
As mentioned on the google app engine doc, the APC extension are enabled, so you can use it as cache manager for smarty like this : http://www.smarty.net/forums/viewtopic.php?t=16809
Upvotes: 1