Page Menu
Home
WMGMC Issues
搜索
Configure Global Search
登录
Files
F15892
Localization.php
No One
Temporary
Actions
Download File
Edit File
Delete File
View Transforms
订阅
标记用于日后
授予令牌
Size
28 KB
Referenced Files
None
订阅者
None
Localization.php
View Options
<?php
/**
* This file is part of the Carbon package.
*
* (c) Brian Nesbitt <brian@nesbot.com>
*
* For the full copyright and license information, please view the LICENSE
* file that was distributed with this source code.
*/
namespace
Carbon\Traits
;
use
Carbon\CarbonInterface
;
use
Carbon\Exceptions\InvalidTypeException
;
use
Carbon\Exceptions\NotLocaleAwareException
;
use
Carbon\Language
;
use
Carbon\Translator
;
use
Carbon\TranslatorStrongTypeInterface
;
use
Closure
;
use
Symfony\Component\Translation\TranslatorBagInterface
;
use
Symfony\Component\Translation\TranslatorInterface
;
use
Symfony\Contracts\Translation\LocaleAwareInterface
;
use
Symfony\Contracts\Translation\TranslatorInterface
as
ContractsTranslatorInterface
;
// @codeCoverageIgnoreStart
if
(
interface_exists
(
'Symfony
\\
Contracts
\\
Translation
\\
TranslatorInterface'
)
&&
!
interface_exists
(
'Symfony
\\
Component
\\
Translation
\\
TranslatorInterface'
)
)
{
class_alias
(
'Symfony
\\
Contracts
\\
Translation
\\
TranslatorInterface'
,
'Symfony
\\
Component
\\
Translation
\\
TranslatorInterface'
);
}
// @codeCoverageIgnoreEnd
/**
* Trait Localization.
*
* Embed default and locale translators and translation base methods.
*/
trait
Localization
{
/**
* Default translator.
*
* @var \Symfony\Component\Translation\TranslatorInterface
*/
protected
static
$translator
;
/**
* Specific translator of the current instance.
*
* @var \Symfony\Component\Translation\TranslatorInterface
*/
protected
$localTranslator
;
/**
* Options for diffForHumans().
*
* @var int
*/
protected
static
$humanDiffOptions
=
CarbonInterface
::
NO_ZERO_DIFF
;
/**
* @deprecated To avoid conflict between different third-party libraries, static setters should not be used.
* You should rather use the ->settings() method.
* @see settings
*
* @param int $humanDiffOptions
*/
public
static
function
setHumanDiffOptions
(
$humanDiffOptions
)
{
static
::
$humanDiffOptions
=
$humanDiffOptions
;
}
/**
* @deprecated To avoid conflict between different third-party libraries, static setters should not be used.
* You should rather use the ->settings() method.
* @see settings
*
* @param int $humanDiffOption
*/
public
static
function
enableHumanDiffOption
(
$humanDiffOption
)
{
static
::
$humanDiffOptions
=
static
::
getHumanDiffOptions
()
|
$humanDiffOption
;
}
/**
* @deprecated To avoid conflict between different third-party libraries, static setters should not be used.
* You should rather use the ->settings() method.
* @see settings
*
* @param int $humanDiffOption
*/
public
static
function
disableHumanDiffOption
(
$humanDiffOption
)
{
static
::
$humanDiffOptions
=
static
::
getHumanDiffOptions
()
&
~
$humanDiffOption
;
}
/**
* Return default humanDiff() options (merged flags as integer).
*
* @return int
*/
public
static
function
getHumanDiffOptions
()
{
return
static
::
$humanDiffOptions
;
}
/**
* Get the default translator instance in use.
*
* @return \Symfony\Component\Translation\TranslatorInterface
*/
public
static
function
getTranslator
()
{
return
static
::
translator
();
}
/**
* Set the default translator instance to use.
*
* @param \Symfony\Component\Translation\TranslatorInterface $translator
*
* @return void
*/
public
static
function
setTranslator
(
TranslatorInterface
$translator
)
{
static
::
$translator
=
$translator
;
}
/**
* Return true if the current instance has its own translator.
*
* @return bool
*/
public
function
hasLocalTranslator
()
{
return
isset
(
$this
->
localTranslator
);
}
/**
* Get the translator of the current instance or the default if none set.
*
* @return \Symfony\Component\Translation\TranslatorInterface
*/
public
function
getLocalTranslator
()
{
return
$this
->
localTranslator
?:
static
::
translator
();
}
/**
* Set the translator for the current instance.
*
* @param \Symfony\Component\Translation\TranslatorInterface $translator
*
* @return $this
*/
public
function
setLocalTranslator
(
TranslatorInterface
$translator
)
{
$this
->
localTranslator
=
$translator
;
return
$this
;
}
/**
* Returns raw translation message for a given key.
*
* @param \Symfony\Component\Translation\TranslatorInterface $translator the translator to use
* @param string $key key to find
* @param string|null $locale current locale used if null
* @param string|null $default default value if translation returns the key
*
* @return string
*/
public
static
function
getTranslationMessageWith
(
$translator
,
string
$key
,
?
string
$locale
=
null
,
?
string
$default
=
null
)
{
if
(!(
$translator
instanceof
TranslatorBagInterface
&&
$translator
instanceof
TranslatorInterface
))
{
throw
new
InvalidTypeException
(
'Translator does not implement '
.
TranslatorInterface
::
class
.
' and '
.
TranslatorBagInterface
::
class
.
'. '
.
(
\is_object
(
$translator
)
?
\get_class
(
$translator
)
:
\gettype
(
$translator
)).
' has been given.'
);
}
if
(!
$locale
&&
$translator
instanceof
LocaleAwareInterface
)
{
$locale
=
$translator
->
getLocale
();
}
$result
=
self
::
getFromCatalogue
(
$translator
,
$translator
->
getCatalogue
(
$locale
),
$key
);
return
$result
===
$key
?
$default
:
$result
;
}
/**
* Returns raw translation message for a given key.
*
* @param string $key key to find
* @param string|null $locale current locale used if null
* @param string|null $default default value if translation returns the key
* @param \Symfony\Component\Translation\TranslatorInterface $translator an optional translator to use
*
* @return string
*/
public
function
getTranslationMessage
(
string
$key
,
?
string
$locale
=
null
,
?
string
$default
=
null
,
$translator
=
null
)
{
return
static
::
getTranslationMessageWith
(
$translator
?:
$this
->
getLocalTranslator
(),
$key
,
$locale
,
$default
);
}
/**
* Translate using translation string or callback available.
*
* @param \Symfony\Component\Translation\TranslatorInterface $translator
* @param string $key
* @param array $parameters
* @param null $number
*
* @return string
*/
public
static
function
translateWith
(
TranslatorInterface
$translator
,
string
$key
,
array
$parameters
=
[],
$number
=
null
):
string
{
$message
=
static
::
getTranslationMessageWith
(
$translator
,
$key
,
null
,
$key
);
if
(
$message
instanceof
Closure
)
{
return
(
string
)
$message
(...
array_values
(
$parameters
));
}
if
(
$number
!==
null
)
{
$parameters
[
'%count%'
]
=
$number
;
}
if
(
isset
(
$parameters
[
'%count%'
]))
{
$parameters
[
':count'
]
=
$parameters
[
'%count%'
];
}
// @codeCoverageIgnoreStart
$choice
=
$translator
instanceof
ContractsTranslatorInterface
?
$translator
->
trans
(
$key
,
$parameters
)
:
$translator
->
transChoice
(
$key
,
$number
,
$parameters
);
// @codeCoverageIgnoreEnd
return
(
string
)
$choice
;
}
/**
* Translate using translation string or callback available.
*
* @param string $key
* @param array $parameters
* @param string|int|float|null $number
* @param \Symfony\Component\Translation\TranslatorInterface|null $translator
* @param bool $altNumbers
*
* @return string
*/
public
function
translate
(
string
$key
,
array
$parameters
=
[],
$number
=
null
,
?
TranslatorInterface
$translator
=
null
,
bool
$altNumbers
=
false
):
string
{
$translation
=
static
::
translateWith
(
$translator
?:
$this
->
getLocalTranslator
(),
$key
,
$parameters
,
$number
);
if
(
$number
!==
null
&&
$altNumbers
)
{
return
str_replace
(
$number
,
$this
->
translateNumber
(
$number
),
$translation
);
}
return
$translation
;
}
/**
* Returns the alternative number for a given integer if available in the current locale.
*
* @param int $number
*
* @return string
*/
public
function
translateNumber
(
int
$number
):
string
{
$translateKey
=
"alt_numbers.$number"
;
$symbol
=
$this
->
translate
(
$translateKey
);
if
(
$symbol
!==
$translateKey
)
{
return
$symbol
;
}
if
(
$number
>
99
&&
$this
->
translate
(
'alt_numbers.99'
)
!==
'alt_numbers.99'
)
{
$start
=
''
;
foreach
([
10000
,
1000
,
100
]
as
$exp
)
{
$key
=
"alt_numbers_pow.$exp"
;
if
(
$number
>=
$exp
&&
$number
<
$exp
*
10
&&
(
$pow
=
$this
->
translate
(
$key
))
!==
$key
)
{
$unit
=
floor
(
$number
/
$exp
);
$number
-=
$unit
*
$exp
;
$start
.=
(
$unit
>
1
?
$this
->
translate
(
"alt_numbers.$unit"
)
:
''
).
$pow
;
}
}
$result
=
''
;
while
(
$number
)
{
$chunk
=
$number
%
100
;
$result
=
$this
->
translate
(
"alt_numbers.$chunk"
).
$result
;
$number
=
floor
(
$number
/
100
);
}
return
"$start$result"
;
}
if
(
$number
>
9
&&
$this
->
translate
(
'alt_numbers.9'
)
!==
'alt_numbers.9'
)
{
$result
=
''
;
while
(
$number
)
{
$chunk
=
$number
%
10
;
$result
=
$this
->
translate
(
"alt_numbers.$chunk"
).
$result
;
$number
=
floor
(
$number
/
10
);
}
return
$result
;
}
return
(
string
)
$number
;
}
/**
* Translate a time string from a locale to an other.
*
* @param string $timeString date/time/duration string to translate (may also contain English)
* @param string|null $from input locale of the $timeString parameter (`Carbon::getLocale()` by default)
* @param string|null $to output locale of the result returned (`"en"` by default)
* @param int $mode specify what to translate with options:
* - CarbonInterface::TRANSLATE_ALL (default)
* - CarbonInterface::TRANSLATE_MONTHS
* - CarbonInterface::TRANSLATE_DAYS
* - CarbonInterface::TRANSLATE_UNITS
* - CarbonInterface::TRANSLATE_MERIDIEM
* You can use pipe to group: CarbonInterface::TRANSLATE_MONTHS | CarbonInterface::TRANSLATE_DAYS
*
* @return string
*/
public
static
function
translateTimeString
(
$timeString
,
$from
=
null
,
$to
=
null
,
$mode
=
CarbonInterface
::
TRANSLATE_ALL
)
{
// Fallback source and destination locales
$from
=
$from
?:
static
::
getLocale
();
$to
=
$to
?:
'en'
;
if
(
$from
===
$to
)
{
return
$timeString
;
}
// Standardize apostrophe
$timeString
=
strtr
(
$timeString
,
[
'’'
=>
"'"
]);
$fromTranslations
=
[];
$toTranslations
=
[];
foreach
([
'from'
,
'to'
]
as
$key
)
{
$language
=
$$key
;
$translator
=
Translator
::
get
(
$language
);
$translations
=
$translator
->
getMessages
();
if
(!
isset
(
$translations
[
$language
]))
{
return
$timeString
;
}
$translationKey
=
$key
.
'Translations'
;
$messages
=
$translations
[
$language
];
$months
=
$messages
[
'months'
]
??
[];
$weekdays
=
$messages
[
'weekdays'
]
??
[];
$meridiem
=
$messages
[
'meridiem'
]
??
[
'AM'
,
'PM'
];
if
(
isset
(
$messages
[
'ordinal_words'
]))
{
$timeString
=
self
::
replaceOrdinalWords
(
$timeString
,
$key
===
'from'
?
array_flip
(
$messages
[
'ordinal_words'
])
:
$messages
[
'ordinal_words'
]
);
}
if
(
$key
===
'from'
)
{
foreach
([
'months'
,
'weekdays'
]
as
$variable
)
{
$list
=
$messages
[
$variable
.
'_standalone'
]
??
null
;
if
(
$list
)
{
foreach
(
$$variable
as
$index
=>
&
$name
)
{
$name
.=
'|'
.
$messages
[
$variable
.
'_standalone'
][
$index
];
}
}
}
}
$$translationKey
=
array_merge
(
$mode
&
CarbonInterface
::
TRANSLATE_MONTHS
?
static
::
getTranslationArray
(
$months
,
12
,
$timeString
)
:
[],
$mode
&
CarbonInterface
::
TRANSLATE_MONTHS
?
static
::
getTranslationArray
(
$messages
[
'months_short'
]
??
[],
12
,
$timeString
)
:
[],
$mode
&
CarbonInterface
::
TRANSLATE_DAYS
?
static
::
getTranslationArray
(
$weekdays
,
7
,
$timeString
)
:
[],
$mode
&
CarbonInterface
::
TRANSLATE_DAYS
?
static
::
getTranslationArray
(
$messages
[
'weekdays_short'
]
??
[],
7
,
$timeString
)
:
[],
$mode
&
CarbonInterface
::
TRANSLATE_DIFF
?
static
::
translateWordsByKeys
([
'diff_now'
,
'diff_today'
,
'diff_yesterday'
,
'diff_tomorrow'
,
'diff_before_yesterday'
,
'diff_after_tomorrow'
,
],
$messages
,
$key
)
:
[],
$mode
&
CarbonInterface
::
TRANSLATE_UNITS
?
static
::
translateWordsByKeys
([
'year'
,
'month'
,
'week'
,
'day'
,
'hour'
,
'minute'
,
'second'
,
],
$messages
,
$key
)
:
[],
$mode
&
CarbonInterface
::
TRANSLATE_MERIDIEM
?
array_map
(
function
(
$hour
)
use
(
$meridiem
)
{
if
(
\is_array
(
$meridiem
))
{
return
$meridiem
[
$hour
<
12
?
0
:
1
];
}
return
$meridiem
(
$hour
,
0
,
false
);
},
range
(
0
,
23
))
:
[]
);
}
return
substr
(
preg_replace_callback
(
'/(?<=[
\d\s
+.
\/
,_-])('
.
implode
(
'|'
,
$fromTranslations
).
')(?=[
\d\s
+.
\/
,_-])/iu'
,
function
(
$match
)
use
(
$fromTranslations
,
$toTranslations
)
{
[
$chunk
]
=
$match
;
foreach
(
$fromTranslations
as
$index
=>
$word
)
{
if
(
preg_match
(
"/^$word
\$
/iu"
,
$chunk
))
{
return
$toTranslations
[
$index
]
??
''
;
}
}
return
$chunk
;
// @codeCoverageIgnore
},
" $timeString "
),
1
,
-
1
);
}
/**
* Translate a time string from the current locale (`$date->locale()`) to an other.
*
* @param string $timeString time string to translate
* @param string|null $to output locale of the result returned ("en" by default)
*
* @return string
*/
public
function
translateTimeStringTo
(
$timeString
,
$to
=
null
)
{
return
static
::
translateTimeString
(
$timeString
,
$this
->
getTranslatorLocale
(),
$to
);
}
/**
* Get/set the locale for the current instance.
*
* @param string|null $locale
* @param string ...$fallbackLocales
*
* @return $this|string
*/
public
function
locale
(
string
$locale
=
null
,
...
$fallbackLocales
)
{
if
(
$locale
===
null
)
{
return
$this
->
getTranslatorLocale
();
}
if
(!
$this
->
localTranslator
||
$this
->
getTranslatorLocale
(
$this
->
localTranslator
)
!==
$locale
)
{
$translator
=
Translator
::
get
(
$locale
);
if
(!
empty
(
$fallbackLocales
))
{
$translator
->
setFallbackLocales
(
$fallbackLocales
);
foreach
(
$fallbackLocales
as
$fallbackLocale
)
{
$messages
=
Translator
::
get
(
$fallbackLocale
)->
getMessages
();
if
(
isset
(
$messages
[
$fallbackLocale
]))
{
$translator
->
setMessages
(
$fallbackLocale
,
$messages
[
$fallbackLocale
]);
}
}
}
$this
->
localTranslator
=
$translator
;
}
return
$this
;
}
/**
* Get the current translator locale.
*
* @return string
*/
public
static
function
getLocale
()
{
return
static
::
getLocaleAwareTranslator
()->
getLocale
();
}
/**
* Set the current translator locale and indicate if the source locale file exists.
* Pass 'auto' as locale to use closest language from the current LC_TIME locale.
*
* @param string $locale locale ex. en
*
* @return bool
*/
public
static
function
setLocale
(
$locale
)
{
return
static
::
getLocaleAwareTranslator
()->
setLocale
(
$locale
)
!==
false
;
}
/**
* Set the fallback locale.
*
* @see https://symfony.com/doc/current/components/translation.html#fallback-locales
*
* @param string $locale
*/
public
static
function
setFallbackLocale
(
$locale
)
{
$translator
=
static
::
getTranslator
();
if
(
method_exists
(
$translator
,
'setFallbackLocales'
))
{
$translator
->
setFallbackLocales
([
$locale
]);
if
(
$translator
instanceof
Translator
)
{
$preferredLocale
=
$translator
->
getLocale
();
$translator
->
setMessages
(
$preferredLocale
,
array_replace_recursive
(
$translator
->
getMessages
()[
$locale
]
??
[],
Translator
::
get
(
$locale
)->
getMessages
()[
$locale
]
??
[],
$translator
->
getMessages
(
$preferredLocale
)
));
}
}
}
/**
* Get the fallback locale.
*
* @see https://symfony.com/doc/current/components/translation.html#fallback-locales
*
* @return string|null
*/
public
static
function
getFallbackLocale
()
{
$translator
=
static
::
getTranslator
();
if
(
method_exists
(
$translator
,
'getFallbackLocales'
))
{
return
$translator
->
getFallbackLocales
()[
0
]
??
null
;
}
return
null
;
}
/**
* Set the current locale to the given, execute the passed function, reset the locale to previous one,
* then return the result of the closure (or null if the closure was void).
*
* @param string $locale locale ex. en
* @param callable $func
*
* @return mixed
*/
public
static
function
executeWithLocale
(
$locale
,
$func
)
{
$currentLocale
=
static
::
getLocale
();
$result
=
$func
(
static
::
setLocale
(
$locale
)
?
static
::
getLocale
()
:
false
,
static
::
translator
());
static
::
setLocale
(
$currentLocale
);
return
$result
;
}
/**
* Returns true if the given locale is internally supported and has short-units support.
* Support is considered enabled if either year, day or hour has a short variant translated.
*
* @param string $locale locale ex. en
*
* @return bool
*/
public
static
function
localeHasShortUnits
(
$locale
)
{
return
static
::
executeWithLocale
(
$locale
,
function
(
$newLocale
,
TranslatorInterface
$translator
)
{
return
(
$newLocale
&&
((
$y
=
static
::
translateWith
(
$translator
,
'y'
))
!==
'y'
&&
$y
!==
static
::
translateWith
(
$translator
,
'year'
)))
||
(
(
$y
=
static
::
translateWith
(
$translator
,
'd'
))
!==
'd'
&&
$y
!==
static
::
translateWith
(
$translator
,
'day'
)
)
||
(
(
$y
=
static
::
translateWith
(
$translator
,
'h'
))
!==
'h'
&&
$y
!==
static
::
translateWith
(
$translator
,
'hour'
)
);
});
}
/**
* Returns true if the given locale is internally supported and has diff syntax support (ago, from now, before, after).
* Support is considered enabled if the 4 sentences are translated in the given locale.
*
* @param string $locale locale ex. en
*
* @return bool
*/
public
static
function
localeHasDiffSyntax
(
$locale
)
{
return
static
::
executeWithLocale
(
$locale
,
function
(
$newLocale
,
TranslatorInterface
$translator
)
{
if
(!
$newLocale
)
{
return
false
;
}
foreach
([
'ago'
,
'from_now'
,
'before'
,
'after'
]
as
$key
)
{
if
(
$translator
instanceof
TranslatorBagInterface
&&
self
::
getFromCatalogue
(
$translator
,
$translator
->
getCatalogue
(
$newLocale
),
$key
)
instanceof
Closure
)
{
continue
;
}
if
(
$translator
->
trans
(
$key
)
===
$key
)
{
return
false
;
}
}
return
true
;
});
}
/**
* Returns true if the given locale is internally supported and has words for 1-day diff (just now, yesterday, tomorrow).
* Support is considered enabled if the 3 words are translated in the given locale.
*
* @param string $locale locale ex. en
*
* @return bool
*/
public
static
function
localeHasDiffOneDayWords
(
$locale
)
{
return
static
::
executeWithLocale
(
$locale
,
function
(
$newLocale
,
TranslatorInterface
$translator
)
{
return
$newLocale
&&
$translator
->
trans
(
'diff_now'
)
!==
'diff_now'
&&
$translator
->
trans
(
'diff_yesterday'
)
!==
'diff_yesterday'
&&
$translator
->
trans
(
'diff_tomorrow'
)
!==
'diff_tomorrow'
;
});
}
/**
* Returns true if the given locale is internally supported and has words for 2-days diff (before yesterday, after tomorrow).
* Support is considered enabled if the 2 words are translated in the given locale.
*
* @param string $locale locale ex. en
*
* @return bool
*/
public
static
function
localeHasDiffTwoDayWords
(
$locale
)
{
return
static
::
executeWithLocale
(
$locale
,
function
(
$newLocale
,
TranslatorInterface
$translator
)
{
return
$newLocale
&&
$translator
->
trans
(
'diff_before_yesterday'
)
!==
'diff_before_yesterday'
&&
$translator
->
trans
(
'diff_after_tomorrow'
)
!==
'diff_after_tomorrow'
;
});
}
/**
* Returns true if the given locale is internally supported and has period syntax support (X times, every X, from X, to X).
* Support is considered enabled if the 4 sentences are translated in the given locale.
*
* @param string $locale locale ex. en
*
* @return bool
*/
public
static
function
localeHasPeriodSyntax
(
$locale
)
{
return
static
::
executeWithLocale
(
$locale
,
function
(
$newLocale
,
TranslatorInterface
$translator
)
{
return
$newLocale
&&
$translator
->
trans
(
'period_recurrences'
)
!==
'period_recurrences'
&&
$translator
->
trans
(
'period_interval'
)
!==
'period_interval'
&&
$translator
->
trans
(
'period_start_date'
)
!==
'period_start_date'
&&
$translator
->
trans
(
'period_end_date'
)
!==
'period_end_date'
;
});
}
/**
* Returns the list of internally available locales and already loaded custom locales.
* (It will ignore custom translator dynamic loading.)
*
* @return array
*/
public
static
function
getAvailableLocales
()
{
$translator
=
static
::
getLocaleAwareTranslator
();
return
$translator
instanceof
Translator
?
$translator
->
getAvailableLocales
()
:
[
$translator
->
getLocale
()];
}
/**
* Returns list of Language object for each available locale. This object allow you to get the ISO name, native
* name, region and variant of the locale.
*
* @return Language[]
*/
public
static
function
getAvailableLocalesInfo
()
{
$languages
=
[];
foreach
(
static
::
getAvailableLocales
()
as
$id
)
{
$languages
[
$id
]
=
new
Language
(
$id
);
}
return
$languages
;
}
/**
* Initialize the default translator instance if necessary.
*
* @return \Symfony\Component\Translation\TranslatorInterface
*/
protected
static
function
translator
()
{
if
(
static
::
$translator
===
null
)
{
static
::
$translator
=
Translator
::
get
();
}
return
static
::
$translator
;
}
/**
* Get the locale of a given translator.
*
* If null or omitted, current local translator is used.
* If no local translator is in use, current global translator is used.
*
* @param null $translator
*
* @return string|null
*/
protected
function
getTranslatorLocale
(
$translator
=
null
):
?
string
{
if
(
\func_num_args
()
===
0
)
{
$translator
=
$this
->
getLocalTranslator
();
}
$translator
=
static
::
getLocaleAwareTranslator
(
$translator
);
return
$translator
?
$translator
->
getLocale
()
:
null
;
}
/**
* Throw an error if passed object is not LocaleAwareInterface.
*
* @param LocaleAwareInterface|null $translator
*
* @return LocaleAwareInterface|null
*/
protected
static
function
getLocaleAwareTranslator
(
$translator
=
null
)
{
if
(
\func_num_args
()
===
0
)
{
$translator
=
static
::
translator
();
}
if
(
$translator
&&
!(
$translator
instanceof
LocaleAwareInterface
||
method_exists
(
$translator
,
'getLocale'
)))
{
throw
new
NotLocaleAwareException
(
$translator
);
// @codeCoverageIgnore
}
return
$translator
;
}
/**
* @param mixed $translator
* @param \Symfony\Component\Translation\MessageCatalogueInterface $catalogue
*
* @return mixed
*/
private
static
function
getFromCatalogue
(
$translator
,
$catalogue
,
string
$id
,
string
$domain
=
'messages'
)
{
return
$translator
instanceof
TranslatorStrongTypeInterface
?
$translator
->
getFromCatalogue
(
$catalogue
,
$id
,
$domain
)
// @codeCoverageIgnore
:
$catalogue
->
get
(
$id
,
$domain
);
}
/**
* Return the word cleaned from its translation codes.
*
* @param string $word
*
* @return string
*/
private
static
function
cleanWordFromTranslationString
(
$word
)
{
$word
=
str_replace
([
':count'
,
'%count'
,
':time'
],
''
,
$word
);
$word
=
strtr
(
$word
,
[
'’'
=>
"'"
]);
$word
=
preg_replace
(
'/({
\d
+(,(
\d
+|Inf))?}|[
\[\]
]
\d
+(,(
\d
+|Inf))?[
\[\]
])/'
,
''
,
$word
);
return
trim
(
$word
);
}
/**
* Translate a list of words.
*
* @param string[] $keys keys to translate.
* @param string[] $messages messages bag handling translations.
* @param string $key 'to' (to get the translation) or 'from' (to get the detection RegExp pattern).
*
* @return string[]
*/
private
static
function
translateWordsByKeys
(
$keys
,
$messages
,
$key
):
array
{
return
array_map
(
function
(
$wordKey
)
use
(
$messages
,
$key
)
{
$message
=
$key
===
'from'
&&
isset
(
$messages
[
$wordKey
.
'_regexp'
])
?
$messages
[
$wordKey
.
'_regexp'
]
:
(
$messages
[
$wordKey
]
??
null
);
if
(!
$message
)
{
return
'>>DO NOT REPLACE<<'
;
}
$parts
=
explode
(
'|'
,
$message
);
return
$key
===
'to'
?
self
::
cleanWordFromTranslationString
(
end
(
$parts
))
:
'(?:'
.
implode
(
'|'
,
array_map
([
static
::
class
,
'cleanWordFromTranslationString'
],
$parts
)).
')'
;
},
$keys
);
}
/**
* Get an array of translations based on the current date.
*
* @param callable $translation
* @param int $length
* @param string $timeString
*
* @return string[]
*/
private
static
function
getTranslationArray
(
$translation
,
$length
,
$timeString
):
array
{
$filler
=
'>>DO NOT REPLACE<<'
;
if
(
\is_array
(
$translation
))
{
return
array_pad
(
$translation
,
$length
,
$filler
);
}
$list
=
[];
$date
=
static
::
now
();
for
(
$i
=
0
;
$i
<
$length
;
$i
++)
{
$list
[]
=
$translation
(
$date
,
$timeString
,
$i
)
??
$filler
;
}
return
$list
;
}
private
static
function
replaceOrdinalWords
(
string
$timeString
,
array
$ordinalWords
):
string
{
return
preg_replace_callback
(
'/(?<![a-z])[a-z]+(?![a-z])/i'
,
function
(
array
$match
)
use
(
$ordinalWords
)
{
return
$ordinalWords
[
mb_strtolower
(
$match
[
0
])]
??
$match
[
0
];
},
$timeString
);
}
}
File Metadata
详情
附加的
Mime Type
text/x-php
Expires
9月 9 Tue, 5:47 AM (10 h, 58 m)
Storage Engine
blob
Storage Format
Raw Data
Storage Handle
5378
默认替代文本
Localization.php (28 KB)
Attached To
Mode
rMAILCOW mailcow-tracking
附加的
Detach File
Event Timeline
Log In to Comment