[wp-trac] [WordPress Trac] #41305: Add lazily evaluated translations
WordPress Trac
noreply at wordpress.org
Thu Jul 13 11:16:57 UTC 2017
#41305: Add lazily evaluated translations
-------------------------+-----------------------------
Reporter: schlessera | Owner:
Type: enhancement | Status: new
Priority: normal | Milestone: Awaiting Review
Component: I18N | Version: 4.8
Severity: normal | Keywords:
Focuses: performance |
-------------------------+-----------------------------
In the context of #40988, I did a few performance tests and experimented
with adding a lazily evaluated translation object.
The general principle is this:
Instead of returning the resulting string of a translation, return an
object for which the `__toString()` and `jsonSerialize()` methods will
fetch the resulting string instead.
I tested by having the `__()` method return such a proxy object, instead
of the actual translated string.
From a quick profiling run on `wptrunk.dev/wp-json/wp/v2/posts`, I got the
following results:
Returning a `translate()` from `__()`:
{{{
Wall Time 162ms
CPU Time 157ms
I/O Time 5.48ms
Memory 16.5MB
Network n/a n/a n/a
SQL 4.41ms 13rq
}}}
Returning a `TranslationProxy` from `__()`:
{{{
Wall Time 144ms -19ms -14.9%
CPU Time 138ms -18ms -15.4%
I/O Time 5.33ms -154µs -3.0%
Memory 16.6MB +81.6KB n/s
Network n/a n/a n/a
SQL 4.33ms 13rq
}}}
As you can see, this shaved off almost 15% from this simple request.
It saved 2255 calls to `translate()`, 2157 calls to
`get_translations_for_domain()` and, more importantly still, 2156 calls to
`apply_filters()` (which could involve a lot of additional processing in
some cases).
The main problem with this approach is that WordPress does not contain
real type-hinting, so BC is broken wherever the proxy is not echoed, but
used directly.
As we cannot possibly foresee how plugins might use their localized
strings, I suggest adding new lazy variations of the translation
functions. To mirror the "echo" variations that prefix the translation
functions with an `e`, I'd suggest using the `l` prefix for these
variations:
{{{#!php
// Lazily retrieve the translation of $text.
_l( $text , $domain = 'default' );
// Lazily retrieve the translation of $text and escape it for safe use in
an attribute.
esc_attr_l( $text, $domain = 'default' );
// Lazily retrieve the translation of $text and escape it for safe use in
HTML output.
esc_html_l( $text, $domain = 'default' );
// Lazily retrieve translated string with gettext context.
_lx( $text, $context, $domain = 'default' );
// Lazily translate string with gettext context, and escape it for safe
use in an attribute.
esc_attr_lx( $text, $context, $domain = 'default' );
// Lazily translate string with gettext context, and escape it for safe
use in HTML output.
esc_html_lx( $text, $context, $domain = 'default' );
}}}
Arbitrary testing has shown that using such lazily evaluated translations
strategically can improve the performance by 10-30% for certain scenarios.
Implementing them in this BC fashion allows us to fine-tune Core usage and
make it available to plugins, while playing it safe with existing code.
--
Ticket URL: <https://core.trac.wordpress.org/ticket/41305>
WordPress Trac <https://core.trac.wordpress.org/>
WordPress publishing platform
More information about the wp-trac
mailing list