Merge pull request #4077 from Nicofuma/ticket/14306

[ticket/14306] Automatically enable a safe mode when container building fails
This commit is contained in:
Marc Alexander 2016-01-15 18:13:34 +01:00
commit 8e584dfa6b
4 changed files with 106 additions and 64 deletions

View file

@ -49,7 +49,7 @@ function marklist(id, name, state)
} }
var rb = parent.getElementsByTagName('input'); var rb = parent.getElementsByTagName('input');
for (var r = 0; r < rb.length; r++) for (var r = 0; r < rb.length; r++)
{ {
if (rb[r].name.substr(0, name.length) == name) if (rb[r].name.substr(0, name.length) == name)
@ -103,7 +103,7 @@ function popup(url, width, height, name)
<p><a href="{U_ADM_INDEX}">{L_ADMIN_INDEX}</a> &bull; <a href="{U_INDEX}">{L_FORUM_INDEX}</a></p> <p><a href="{U_ADM_INDEX}">{L_ADMIN_INDEX}</a> &bull; <a href="{U_INDEX}">{L_FORUM_INDEX}</a></p>
<p id="skip"><a href="#acp">{L_SKIP}</a></p> <p id="skip"><a href="#acp">{L_SKIP}</a></p>
</div> </div>
<div id="page-body"> <div id="page-body">
<div id="tabs"> <div id="tabs">
<ul> <ul>
@ -120,7 +120,7 @@ function popup(url, width, height, name)
<!-- DEFINE $LI_USED = 0 --> <!-- DEFINE $LI_USED = 0 -->
<!-- BEGIN l_block1 --> <!-- BEGIN l_block1 -->
<!-- IF l_block1.S_SELECTED --> <!-- IF l_block1.S_SELECTED -->
<!-- BEGIN l_block2 --> <!-- BEGIN l_block2 -->
<!-- IF .l_block1.l_block2.l_block3 --> <!-- IF .l_block1.l_block2.l_block3 -->
<!-- IF $LI_USED --></ul></div><!-- ENDIF --> <!-- IF $LI_USED --></ul></div><!-- ENDIF -->
@ -129,13 +129,13 @@ function popup(url, width, height, name)
<ul> <ul>
<!-- DEFINE $LI_USED = 1 --> <!-- DEFINE $LI_USED = 1 -->
<!-- ENDIF --> <!-- ENDIF -->
<!-- BEGIN l_block3 --> <!-- BEGIN l_block3 -->
<li<!-- IF l_block1.l_block2.l_block3.S_SELECTED --> id="activemenu"<!-- ENDIF -->><a href="{l_block1.l_block2.l_block3.U_TITLE}"><span>{l_block1.l_block2.l_block3.L_TITLE}</span></a></li> <li<!-- IF l_block1.l_block2.l_block3.S_SELECTED --> id="activemenu"<!-- ENDIF -->><a href="{l_block1.l_block2.l_block3.U_TITLE}"><span>{l_block1.l_block2.l_block3.L_TITLE}</span></a></li>
<!-- DEFINE $LI_USED = 1 --> <!-- DEFINE $LI_USED = 1 -->
<!-- END l_block3 --> <!-- END l_block3 -->
<!-- END l_block2 --> <!-- END l_block2 -->
<!-- ENDIF --> <!-- ENDIF -->
<!-- END l_block1 --> <!-- END l_block1 -->
<!-- IF $LI_USED --> <!-- IF $LI_USED -->
@ -143,6 +143,13 @@ function popup(url, width, height, name)
</div> </div>
<!-- ENDIF --> <!-- ENDIF -->
</div> </div>
<div id="main"> <div id="main">
<div class="main"> <div class="main">
{% if CONTAINER_EXCEPTION !== false %}
<div class="errorbox">
<p>{{ lang('CONTAINER_EXCEPTION') }}</p><br />
<p>{{ lang('EXCEPTION') }}{{ lang('COLON') }} {{ CONTAINER_EXCEPTION.getMessage() }}</p>
<pre>{{ CONTAINER_EXCEPTION.getTraceAsString() }}</pre>
</div>
{% endif %}

View file

@ -26,7 +26,7 @@ function adm_page_header($page_title)
{ {
global $config, $user, $template; global $config, $user, $template;
global $phpbb_root_path, $phpbb_admin_path, $phpEx, $SID, $_SID; global $phpbb_root_path, $phpbb_admin_path, $phpEx, $SID, $_SID;
global $phpbb_dispatcher; global $phpbb_dispatcher, $phpbb_container;
if (defined('HEADER_INC')) if (defined('HEADER_INC'))
{ {
@ -105,6 +105,8 @@ function adm_page_header($page_title)
'S_CONTENT_ENCODING' => 'UTF-8', 'S_CONTENT_ENCODING' => 'UTF-8',
'S_CONTENT_FLOW_BEGIN' => ($user->lang['DIRECTION'] == 'ltr') ? 'left' : 'right', 'S_CONTENT_FLOW_BEGIN' => ($user->lang['DIRECTION'] == 'ltr') ? 'left' : 'right',
'S_CONTENT_FLOW_END' => ($user->lang['DIRECTION'] == 'ltr') ? 'right' : 'left', 'S_CONTENT_FLOW_END' => ($user->lang['DIRECTION'] == 'ltr') ? 'right' : 'left',
'CONTAINER_EXCEPTION' => $phpbb_container->hasParameter('container_exception') ? $phpbb_container->getParameter('container_exception') : false,
)); ));
// An array of http headers that phpbb will set. The following event may override these. // An array of http headers that phpbb will set. The following event may override these.

View file

@ -225,6 +225,9 @@ $lang = array_merge($lang, array(
'BACK' => 'Back', 'BACK' => 'Back',
'CONTAINER_EXCEPTION' => 'phpBB encountered an error building the container due to an installed extension. For this reason, all extensions have been temporarily disabled. Please try purging your forum cache. All extensions will automatically be re-enabled once the container error is resolved. If this error continues, please visit <a href="https://www.phpbb.com/support">phpBB.com</a> for support.',
'EXCEPTION' => 'Exception',
'COLOUR_SWATCH' => 'Web-safe colour swatch', 'COLOUR_SWATCH' => 'Web-safe colour swatch',
'CONFIG_UPDATED' => 'Configuration updated successfully.', 'CONFIG_UPDATED' => 'Configuration updated successfully.',
'CRON_LOCK_ERROR' => 'Could not obtain cron lock.', 'CRON_LOCK_ERROR' => 'Could not obtain cron lock.',

View file

@ -90,7 +90,7 @@ class container_builder
* *
* @var array * @var array
*/ */
protected $custom_parameters = null; protected $custom_parameters = [];
/** /**
* @var \phpbb\config_php_file * @var \phpbb\config_php_file
@ -107,13 +107,16 @@ class container_builder
*/ */
private $container_extensions; private $container_extensions;
/** @var \Exception */
private $build_exception;
/** /**
* Constructor * Constructor
* *
* @param string $phpbb_root_path Path to the phpbb includes directory. * @param string $phpbb_root_path Path to the phpbb includes directory.
* @param string $php_ext php file extension * @param string $php_ext php file extension
*/ */
function __construct($phpbb_root_path, $php_ext) public function __construct($phpbb_root_path, $php_ext)
{ {
$this->phpbb_root_path = $phpbb_root_path; $this->phpbb_root_path = $phpbb_root_path;
$this->php_ext = $php_ext; $this->php_ext = $php_ext;
@ -126,67 +129,96 @@ class container_builder
*/ */
public function get_container() public function get_container()
{ {
$container_filename = $this->get_container_filename(); try
$config_cache = new ConfigCache($container_filename, defined('DEBUG'));
if ($this->use_cache && $config_cache->isFresh())
{ {
require($config_cache->getPath()); $container_filename = $this->get_container_filename();
$this->container = new \phpbb_cache_container(); $config_cache = new ConfigCache($container_filename, defined('DEBUG'));
} if ($this->use_cache && $config_cache->isFresh())
else
{
$this->container_extensions = array(new extension\core($this->get_config_path()));
if ($this->use_extensions)
{ {
$this->load_extensions(); require($config_cache->getPath());
$this->container = new \phpbb_cache_container();
} }
else
// Inject the config
if ($this->config_php_file)
{ {
$this->container_extensions[] = new extension\config($this->config_php_file); $this->container_extensions = array(new extension\core($this->get_config_path()));
}
$this->container = $this->create_container($this->container_extensions); if ($this->use_extensions)
// Easy collections through tags
$this->container->addCompilerPass(new pass\collection_pass());
// Event listeners "phpBB style"
$this->container->addCompilerPass(new RegisterListenersPass('dispatcher', 'event.listener_listener', 'event.listener'));
// Event listeners "Symfony style"
$this->container->addCompilerPass(new RegisterListenersPass('dispatcher'));
if ($this->use_extensions)
{
$this->register_ext_compiler_pass();
}
$filesystem = new filesystem();
$loader = new YamlFileLoader($this->container, new FileLocator($filesystem->realpath($this->get_config_path())));
$loader->load($this->container->getParameter('core.environment') . '/config.yml');
$this->inject_custom_parameters();
if ($this->compile_container)
{
$this->container->compile();
if ($this->use_cache)
{ {
$this->dump_container($config_cache); $this->load_extensions();
}
// Inject the config
if ($this->config_php_file)
{
$this->container_extensions[] = new extension\config($this->config_php_file);
}
$this->container = $this->create_container($this->container_extensions);
// Easy collections through tags
$this->container->addCompilerPass(new pass\collection_pass());
// Event listeners "phpBB style"
$this->container->addCompilerPass(new RegisterListenersPass('dispatcher', 'event.listener_listener', 'event.listener'));
// Event listeners "Symfony style"
$this->container->addCompilerPass(new RegisterListenersPass('dispatcher'));
if ($this->use_extensions)
{
$this->register_ext_compiler_pass();
}
$filesystem = new filesystem();
$loader = new YamlFileLoader($this->container, new FileLocator($filesystem->realpath($this->get_config_path())));
$loader->load($this->container->getParameter('core.environment') . '/config.yml');
$this->inject_custom_parameters();
if ($this->compile_container)
{
$this->container->compile();
if ($this->use_cache)
{
$this->dump_container($config_cache);
}
} }
} }
}
if ($this->compile_container && $this->config_php_file) if ($this->compile_container && $this->config_php_file)
{
$this->container->set('config.php', $this->config_php_file);
}
return $this->container;
}
catch (\Exception $e)
{ {
$this->container->set('config.php', $this->config_php_file); // Don't try to recover if we are in the development environment
} if ($this->get_environment() === 'development')
{
throw $e;
}
return $this->container; if ($this->build_exception === null)
{
$this->build_exception = $e;
return $this
->without_extensions()
->without_cache()
->with_custom_parameters(array_merge($this->custom_parameters, [
'container_exception' => $e,
]))
->get_container();
}
else
{
// Rethrow the original exception if it's still failing
throw $this->build_exception;
}
}
} }
/** /**
@ -451,13 +483,11 @@ class container_builder
*/ */
protected function inject_custom_parameters() protected function inject_custom_parameters()
{ {
if ($this->custom_parameters !== null) foreach ($this->custom_parameters as $key => $value)
{ {
foreach ($this->custom_parameters as $key => $value) $this->container->setParameter($key, $value);
{
$this->container->setParameter($key, $value);
}
} }
} }
/** /**