/**
  * Return the json array for a given locale, sourceCatalog, xliffPath and package.
  * The json will be cached.
  *
  * @param Locale $locale The locale
  * @return Result
  * @throws Exception
  */
 public function getCachedJson(Locale $locale)
 {
     $cacheIdentifier = md5($locale);
     if ($this->xliffToJsonTranslationsCache->has($cacheIdentifier)) {
         $json = $this->xliffToJsonTranslationsCache->get($cacheIdentifier);
     } else {
         $labels = [];
         $localeChain = $this->localizationService->getLocaleChain($locale);
         foreach ($this->packagesRegisteredForAutoInclusion as $packageKey => $sourcesToBeIncluded) {
             if (!is_array($sourcesToBeIncluded)) {
                 continue;
             }
             $translationBasePath = Files::concatenatePaths([$this->packageManager->getPackage($packageKey)->getResourcesPath(), $this->xliffBasePath]);
             // We merge labels in the chain from the worst choice to best choice
             foreach (array_reverse($localeChain) as $allowedLocale) {
                 $localeSourcePath = Files::getNormalizedPath(Files::concatenatePaths([$translationBasePath, $allowedLocale]));
                 foreach ($sourcesToBeIncluded as $sourceName) {
                     foreach (glob($localeSourcePath . $sourceName . '.xlf') as $xliffPathAndFilename) {
                         $xliffPathInfo = pathinfo($xliffPathAndFilename);
                         $sourceName = str_replace($localeSourcePath, '', $xliffPathInfo['dirname'] . '/' . $xliffPathInfo['filename']);
                         $labels = Arrays::arrayMergeRecursiveOverrule($labels, $this->parseXliffToArray($xliffPathAndFilename, $packageKey, $sourceName));
                     }
                 }
             }
         }
         $json = json_encode($labels);
         $this->xliffToJsonTranslationsCache->set($cacheIdentifier, $json);
     }
     return $json;
 }
 /**
  * Returns translated $stringToTranslate from a file defined by $sourceName using the function $functionName of the XliffModel.
  *
  * Chooses particular form of label if available and defined in $pluralForm.
  *
  * @param string $functionName The name of the function in the XliffModel to get the translation from
  * @param string $stringToTranslate String passed to function in order to find translation
  * @param \TYPO3\Flow\I18n\Locale $locale Locale to use
  * @param float|int|null $quantity A number to find plural form for (float or int), NULL to not use plural forms
  * @param string $sourceName A relative path to the filename with translations (labels' catalog)
  * @param string $packageKey Key of the package containing the source file
  * @return mixed Translated label or FALSE on failure
  * @throws \TYPO3\Flow\I18n\TranslationProvider\Exception\InvalidPluralFormException
  */
 protected function getTranslationByFunction($functionName, $stringToTranslate, \TYPO3\Flow\I18n\Locale $locale = null, $quantity = null, $sourceName = 'Main', $packageKey = 'TYPO3.Flow')
 {
     if ($locale === null) {
         $locale = $this->localizationService->getConfiguration()->getCurrentLocale();
     }
     $translation = false;
     foreach ($this->localizationService->getLocaleChain($locale) as $localeInChain) {
         $model = $this->getModel($packageKey, $sourceName, $localeInChain);
         if ($quantity !== null) {
             $pluralFormsForProvidedLocale = $this->pluralsReader->getPluralForms($localeInChain);
             $pluralForm = $this->pluralsReader->getPluralForm($quantity, $localeInChain);
             // We need to convert plural form's string to index, as they are accessed using integers in XLIFF files
             $pluralFormIndex = (int) array_search($pluralForm, $pluralFormsForProvidedLocale);
         } else {
             $pluralFormIndex = 0;
         }
         //if we find a valid translation, we don't have to search in the remaining locale chain
         if (($translation = $model->{$functionName}($stringToTranslate, $pluralFormIndex)) !== false) {
             break;
         }
     }
     return $translation;
 }