Yesterday (1.06.2014) Symfony 2.5.0 was released. http://symfony.com/blog/symfony-2-5-0-released
Let's update it!
Yesterday (1.06.2014) Symfony 2.5.0 was released. http://symfony.com/blog/symfony-2-5-0-released
Let's update it!
code at http://cgit.drupalcode.org/sandbox-sun-1255586/?h=theme-init-2228093-dawehner2
Theme system is a mess.
If you interact with the theme functionality, you currently use one of the following ways:
This direct access only works, because the current theme happens to be manually initialized in various spots of the code-base. (@see LegacyRequestSubscriber)
Provide a service ('theme') which you can use to either render some output or get the current theme.
This is the canonical place for interaction.
In case you don't have the current theme initialized yet, the theme service asks the negotiator to get one and initializes (direct or indirect) that theme.
In order to do that, it needs a domain object of the current theme, which for example contains the theme info, stylesheets and libraries, as well as a list of the same domain object representing the parent themes (if any).
<?php
// @todo Find a better name.
interface ThemeServiceInterface {
/**
* @return string
*/
public function render($hook, $variables);
/**
* @return \Drupal\Core\Theme\ActiveTheme
*/
public function getActiveTheme();
/**
* Execute the alter hook on the current theme.
*/
public function alter($type, &$data, &$context1 = NULL, &$context2 = NULL);
}
?>
The theme service has the following dependencies:
theme:
class: Drupal\Core\Theme\Theme
arguments: ['@theme_handler', '@theme.negotiator', '@theme.initialization', '@state']
State is used instead of cache to not rebuild the theme domain object all the time. (as in HEAD)
ThemeHandler
only cares about managing theme extension objects, in the exact same way as ModuleHandler
.
The Extension
objects are no longer manipulated with theme info/data.
ThemeNegotiator
determines the theme to use for a particular request.
ThemeInitialization
consults ThemeHandler
to retrieve the list of enabled themes, in order to instantiate the ActiveTheme
domain object initialize the required theme engines.
This is essentially drupal_theme_initialize()
+ _drupal_theme_initialize()
.
ThemeHandler::rebuildThemeData()
+ system_rebuild_theme_data()
is moved into this service.
The ActiveTheme
domain object is only built once for each theme and stored in state.
This domain object consists of global $theme_info
and global $base_theme_info
.
The Theme
service returns the initialized ActiveTheme
domain object of the current/active theme for consumers.
This replaces access to all global $theme*
variables.
Theme::alter()
removes support for themes to participate in all alter hooks from ModuleHandler::alter()
.
Instead, Theme::alter()
will be specifically invoked manually for the few hooks in which themes are supposed to participate. That list is very limited; e.g.:
hook_form_alter()
hook_page_alter()
hook_theme_suggestions_alter()
hook_theme_registry_alter()
This plan should allow us to get rid of $request->attributes->set('_theme_active')
in ThemeNegotiator
, but we admit that we don't know how many things depend on that currently.
Updated: Comment 0
The theme negotiator issue allowed us to determine the active theme on a request, though it did not replaced all the global theme calls.
This patch tries to replace most of the global $theme/$theme_key places, though it is tough as it is also used in order to figure out whether the theme system is already initialized.
Updated: Comment 0
In order to get rid of getting the theme system untangled we need a clean way to fill up the globals (which will be somewhere else in the future).
These globals are currently filled in drupal_theme_initialize()
global $theme
== global $theme_key
(just the name)
global $theme_info
== Extension $theme
(object)
→ global $theme
== global $theme_info->getName()
global $theme_info
into global $theme
.global $theme
with global $theme_info->getName()
.I add 2 formats:
2 July 2014
2 Jul 1:15
But default drupal formats are in current date
29/07/2014 - 1:15
So if I chose my custom format the date is wrong.
Working on #1813186: Integrate scripts/stylesheets from info/layout files with libraries I found out that color module only look for CSS files declared in the info file with the stylesheets key. It doesn't look for CSS files that are declared in a library. For example see the bartik changes in #1813186-11: Integrate scripts/stylesheets from info/layout files with libraries.
Per #2294177-5: Allow Drupal\Core to provide [config] entity types, we want to move some config entity types from a core module into core/lib, but that's impeded for entity types that define an "admin_permission" in their annotation, since hook_permissions() is a hook, and we don't currently support hook implementations in core/lib.
Change hook_permissions() to a YAML file, which is more inline with D8 patterns. Then core.permissions.yml could define permissions needed by core/lib classes.
Decide if that's still an allowable change for D8. If so, do it. If not, decide if system_permissions() is an acceptable place in which to define those permissions.
1. Create field of type "List (text)" with field add form, and fill the allowed values (they are not empty).
2. Export config of this field. It will be something like this (filename: 'field.storage.taxonomy_term.field_type.yml'):
langcode: en
status: true
dependencies:
module:
- options
- taxonomy
id: taxonomy_term.field_type
name: field_type
entity_type: taxonomy_term
type: list_text
settings:
allowed_values:
-
value: City
label: City
-
value: 'Administrative area'
label: 'Administrative area'
-
value: Continent
label: Continent
-
value: Country
label: Country
-
value: Region
label: Region
allowed_values_function: ''
module: options
locked: false
cardinality: 1
translatable: true
indexes: { }
3. Try to import this config on some fresh-installed Drupal 8 site. You will get an error:
"The configuration property settings.allowed_values.0.label.0 doesn't exist."
If you put this config in module config/install directory, you will get following in your php error log:
[Sat Jul 26 00:47:02.830178 2014] [:error] [pid 4305] [client 127.0.0.1:36675] Uncaught PHP Exception InvalidArgumentException: "The configuration property settings.allowed_values.0.label.0 doesn't exist." at /var/www/drupal/drupal8-core/core/lib/Drupal/Core/Config/Schema/Mapping.php line 66, referer: http://d8.local/admin/modules/list/confirm
4. If allowed_values are empty in config ('allowed_values: { }'), the config imports normally.
Provide a patch that fix this error.
No
No.
No.
Discuss and figure out what our options are.
We've been working for many months now to improve Drupal 8 performance. But not only is measuring (i.e. "profiling") it hard, it's also hard — even for the most prolific contributors — to not accidentally introduce performance regressions. Currently, it's trivial to introduce performance regressions that go unnoticed: additional services being added for one purpose may in fact be initialized always (even when unnecessary — see #1973618-27: DIC: Lazy instantiation of service dependencies (ProxyManager for "proxy services")), additional JS assets that are loaded accidentally (e.g. #2160555: Disable Edit on admin pages), and so on.
The only way (currently) to see if a patch negatively impacts performance, is by performing many manual steps:
devel_generate
to be fixed (it, too, is often broken due to changes in HEAD)Not to mention that actually making proper comparisons is extremely hard.
It's nigh impossible to do it with XHProf unless you have a computer with a constant, controlled environment — results vary wildly with the environment (hardware, PHP version, system load, etc.)! On top of that: if we're comparing a specific, approximately-real-world-scenario, you need generated content, and it's currently very painful to generate the exact same content in different versions of Drupal 8 (due to changes in HEAD).
In order for Drupal 8's performance to only move in the general right direction performance-wise from now on, we need to:
Ideally, we'd have an interface to install Drupal (#2115533: Add InstallerInterface to provide a stable non-interactive installer) as well as an API to generate content. Then, anyone could write scripts for the scenarios they care about. But, that's a massive undertaking (which msonnabaum eventually had to give up on) and it still doesn't help with the above points.
Also ideally, we'd be able to automatically run XHProf (but alas, it's never installed by default and in fact for a few months you've needed a custom build of XHProf for it to work with Drupal 8 — none of the packaged XHProf versions work with PHP 5.5 + Drupal 8!), and even more ideally we'd be able to get the number of CPU instructions it took to render a page. Neither of those are achievable. And even if they were, we'd still not have apples-to-apples comparable numbers, because the results depend on the environment (hardware, PHP version, etc.)
In an überideal world, we'd have a PerfBot running in tandem with TestBot. But creating the infrastructure for this is non-trivial, especially because there are more strict environment requirements for a PerfBot, if we want its results to actually be correct.
What is achievable, is measuring numbers that don't depend on the environment and still are good performance indicators: number of CSS/JS assets, cache/config/state gets, DB queries, initialized services, rendered blocks … And to measure those things, we can simply build on top of what we already have in core: http://api.symfony.com/2.4/Symfony/Component/HttpKernel/Profiler/Profiler.html
Symfony's Profiler
! (This is also what Web Profiler uses.)
Yes, those numbers should be interpreted with care as well. There is nothing inherently bad about the number of services or the number of cache gets for a certain response. But it usually is bad when those numbers increase, and all too often that happens without us noticing. So that is what this issue wants to provide. And at the same time, we get profiling scenarios in core that we can
Therefore, this issue proposes a simpler set of steps:
ProfilingTest
(much like the 'Standard' profile has StandardTest
), but instead of testing whether things work as expected (which is already covered by the current body of tests), it enables a hidden'Simple Profiler' module (part of the 'Profiling' profile), which compares the actual number of cache gets, config gets, initialized services … with the expected numbers for various scenariosProfiler
and DataCollector
(just like Web Profiler)ProfilingTest
will make it pass again). This is how every patch author would be notified of (potential) performance improvements/regressions.This is what that looks like:
None.
None.
Let's inform people if they have a problematic route variable.
The theme function looks a bit like this:
// Generate the output using either a function or a template.
if (isset($info['function'])) {
if (function_exists($info['function'])) {
$output = $info['function']($variables);
}
}
else {
..
// Render the output using the found template file.
$output = $render_function($template_file, $variables);
}
return $output;
if $info['function'] doesn't exist, a notice will be thrown:
Notice: Undefined variable: output in theme() (line 932 of /home/nsh/drupal7/drupal/includes/theme.inc).
The documentation for implementing hook_load(), hook_delete(), hook_prepare(), hook_insert(), hook_validate(), hook_update() and hook_view() is unclear at best, incorrect at worst.
These modules are not implemented using the module name as the base name, but the node type's "base" instead. The documentation does not suggest that and the documentation that does explain it (in hook_node_info()) could be improved.
This patch seeks to correct the errors and improve the documentaion, including three textual examples of how one can use hook_node_info() and node type "base" to implement these hooks effectively.
Tokens are unusable, because DrupalWebTestCase::drupalGetToken() does not use a hash salt, while drupal_get_token() does. This bug makes it impossible to test code that uses tokens.
Core does not use this method. However, I have a contrib patching waiting that does: #1550940: Extend and test payment permissions
Meta issue: #2205673: [meta] Remove all @deprecated functions marked "remove before 8.0"
Remove the usage of user_format_name()
Occurrence of the function
[ashish@xeon:~/proj/self/d8/data/drupal8]$grep user_format_name -r *
core/modules/file/src/Tests/FileTokenReplaceTest.php: $tests['[file:owner]'] = String::checkPlain(user_format_name($this->admin_user));
core/modules/user/user.module:function user_format_name(AccountInterface $account) {
core/modules/user/src/Plugin/entity_reference/selection/UserSelection.php: ->where(str_replace('anonymous_name', ':anonymous_name', (string) $value_part), $value_part->arguments() + array(':anonymous_name' => user_format_name(user_load(0))))
core/modules/user/src/Plugin/views/field/Name.php: return user_format_name($account);
core/modules/user/src/Tests/UserTokenReplaceTest.php: $tests['[user:name]'] = String::checkPlain(user_format_name($account));
core/modules/user/src/Tests/UserTokenReplaceTest.php: $tests['[current-user:name]'] = String::checkPlain(user_format_name($global_account));
core/modules/user/src/Tests/UserTokenReplaceTest.php: $tests['[user:name]'] = user_format_name($account);
core/modules/user/src/Tests/UserTokenReplaceTest.php: $tests['[current-user:name]'] = user_format_name($global_account);
core/modules/user/src/Entity/User.php: * label_callback = "user_format_name",
core/modules/user/src/Entity/User.php: \Drupal::moduleHandler()->alter('user_format_name', $name, $this);
core/modules/user/user.api.php: * Called by user_format_name() to allow modules to alter the username that's
core/modules/user/user.api.php: * The string that user_format_name() will return.
core/modules/user/user.api.php: * The account object passed to user_format_name().
core/modules/user/user.api.php: * @see user_format_name()
core/modules/user/user.api.php:function hook_user_format_name_alter(&$name, $account) {
core/modules/user/user.tokens.inc: $name = user_format_name($account);
core/modules/system/system.api.php: '%username' => user_format_name($account),
core/modules/contact/contact.module: '!sender-name' => user_format_name($sender),
core/modules/contact/contact.module: '!recipient-name' => user_format_name($params['recipient']),
core/includes/bootstrap.inc: * $text = t("@name's blog", array('@name' => user_format_name($account)));
core/lib/Drupal/Core/Session/UserSession.php: \Drupal::moduleHandler()->alter('user_format_name', $name, $this);
core/lib/Drupal/Core/Session/AccountInterface.php: * hook_user_format_name_alter(&$name, $account).
core/lib/Drupal/Core/Session/AccountInterface.php: * @see hook_user_format_name_alter()
#2226761: Change all default settings and config to fast/safe production values added the null and memory backends to the container, despite objections from me and catch. This clutters up the container, adding stuff back in for dev only purposes when we are striving for fast default values for this stuff.
Remove the null and memory backend definitions from core.services.yml and add these to devel module. This can then easily provide these so a dev env can utilise them
None
Clean up cache backends available out of the box. Delegate to devel module.
In the code we have the following comment
public function preSave(EntityStorageInterface $storage) {
// Ensure the filters have been sorted before saving.
$this->filters()->sort();
parent::preSave($storage);
$this->name = trim($this->label());
// @todo Do not save disabled filters whose properties are identical to
// all default properties.
}
This causing problems for #2144263: Decouple entity field storage from configurable fields since its changes allow ConfigImportAllTest uninstall the filter module which then causes a discrepancy between staging and active after import.
Follow-up from #1984766: Change notice: Start relying on Request/Response objects for cache handling.
HTTP headers are now handed by the Symfony Request/Response objects. The legacy http header functions probably aren't doing anything. All uses of these functions need to be updated to use the objects. The functions themselves should be removed in a followup patch.
The affected functions include:
_drupal_set_preferred_header_name
drupal_add_http_header
drupal_get_http_header
drupal_page_header
drupal_send_headers