8000 [Translation] Loco provider fails when pushing for multiple domains · Issue #43953 · symfony/symfony · GitHub
[go: up one dir, main page]

Skip to content

[Translation] Loco provider fails when pushing for multiple domains #43953

New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Closed
vlad-ghita opened this issue Nov 7, 2021 · 2 comments
Closed

Comments

@vlad-ghita
Copy link
vlad-ghita commented Nov 7, 2021

Symfony version(s) affected

5.3.6

Description

Given:

  • non-empty Loco project.
  • multiple translation domains

When pushing multiple domains to Loco, exception is thrown:

php bin\console translation:push loco --domains forms --domains messages --domains validators --force
12:31:09 INFO      [http_client] Request: "POST https://localise.biz/api/assets"
12:31:09 INFO      [http_client] Request: "POST https://localise.biz/api/assets"
12:31:09 INFO      [http_client] Request: "POST https://localise.biz/api/assets"
12:31:09 INFO      [http_client] Request: "POST https://localise.biz/api/assets"
12:31:10 INFO      [http_client] Response: "201 https://localise.biz/api/assets"
12:31:10 INFO      [http_client] Response: "201 https://localise.biz/api/assets"
12:31:10 INFO      [http_client] Response: "201 https://localise.biz/api/assets"
12:31:10 INFO      [http_client] Response: "201 https://localise.biz/api/assets"
12:31:10 INFO      [http_client] Request: "GET https://localise.biz/api/tags.json"
12:31:11 INFO      [http_client] Response: "200 https://localise.biz/api/tags.json"
12:31:11 INFO      [http_client] Request: "POST https://localise.biz/api/tags/forms.json"
12:31:11 INFO      [http_client] Response: "200 https://localise.biz/api/tags/forms.json"
12:31:11 INFO      [http_client] Request: "GET https://localise.biz/api/locales"
12:31:11 INFO      [http_client] Response: "200 https://localise.biz/api/locales"
12:31:11 INFO      [http_client] Request: "GET https://localise.biz/api/assets?filter=forms"
12:31:11 INFO      [http_client] Response: "200 https://localise.biz/api/assets?filter=forms"

In LocoProvider.php line 78:
                                                                                                        
  [ValueError]                                                                                          
  array_combine(): Argument #1 ($keys) and argument #2 ($values) must have the same number of elements  
                                                                                                        

Exception trace:
  at C:\work\jtmweb\vendor\symfony\loco-translation-provider\LocoProvider.php:78
 array_combine() at C:\work\jtmweb\vendor\symfony\loco-translation-provider\LocoProvider.php:78
 Symfony\Component\Translation\Bridge\Loco\LocoProvider->write() at C:\work\jtmweb\vendor\symfony\translation\Provider\FilteringProvider.php:47
 Symfony\Component\Translation\Provider\FilteringProvider->write() at C:\work\jtmweb\vendor\symfony\translation\Command\TranslationPushCommand.php:116
 Symfony\Component\Translation\Command\TranslationPushCommand->execute() at C:\work\jtmweb\vendor\symfony\console\Command\Command.php:299
 Symfony\Component\Console\Command\Command->run() at C:\work\jtmweb\vendor\symfony\console\Application.php:996
 Symfony\Component\Console\Application->doRunCommand() at C:\work\jtmweb\vendor\symfony\framework-bundle\Console\Application.php:96
 Symfony\Bundle\FrameworkBundle\Console\Application->doRunCommand() at C:\work\jtmweb\vendor\symfony\console\Application.php:295
 Symfony\Component\Console\Application->doRun() at C:\work\jtmweb\vendor\symfony\framework-bundle\Console\Application.php:82
 Symfony\Bundle\FrameworkBundle\Console\Application->doRun() at C:\work\jtmweb\vendor\symfony\console\Application.php:167
 Symfony\Component\Console\Application->run() at C:\work\jtmweb\vendor\symfony\runtime\Runner\Symfony\ConsoleApplicationRunner.php:56
 Symfony\Component\Runtime\Runner\Symfony\ConsoleApplicationRunner->run() at C:\work\jtmweb\vendor\autoload_runtime.php:35
 require_once() at C:\work\jtmweb\bin\console:11

translation:push [--force] [--delete-missing] [--domains [DOMAINS]] [--locales [LOCALES]] [--] [<provider>]


Process finished with exit code 255

How to reproduce

  1. Have empty Loco project.
  2. Run this command once:
    php bin\console translation:push loco --domains forms --domains messages --domains validators --force
  3. Run same command again:
    php bin\console translation:push loco --domains forms --domains messages --domains validators --force
    Error occurs.

Possible Solution

No response

Additional Context

No response

@OskarStark
Copy link
Contributor

Friendly ping @welcoMattic

@welcoMattic
Copy link
Member

I'm working on a fix, but it's more complex than I expected, and it could result on breaking BC. I'll open a PR soon with a first version of the fix.

nicolas-grekas added a commit that referenced this issue Nov 29, 2021
… method (welcoMattic)

This PR was merged into the 5.3 branch.

Discussion
----------

[Translation] [Loco] Fix idempotency of LocoProvider write method

| Q             | A
| ------------- | ---
| Branch?       | 5.3
| Bug fix?      | yes
| New feature?  | no <!-- please update src/**/CHANGELOG.md files -->
| Deprecations? | no <!-- please update UPGRADE-*.md and src/**/CHANGELOG.md files -->
| Tickets       | Fix #43953 <!-- prefix each issue number with "Fix #", no need to create an issue if none exist, explain below instead -->
| License       | MIT
| Doc PR        |

This PR fix the exception thrown when we push translations twice, with existing translations on Loco.

Explanation of the fix:

To translate an "asset" (a translation key in Loco vocabulary), we need its Loco `id`. But Loco does not allow us to retrieve an id from a key. So, we fetch all ids for the current domain. Then, we build a map with `key` as key, and `id` as value. After that, we can intersect the keys of this map and our messages array to get all Loco ids of the currently processed messages.

```php
foreach ($catalogue->all() as $domain => $messages) {
    $keysIdsMap = [];

    foreach ($this->getAssetsIds($domain) as $id) {
        $keysIdsMap[$this->retrieveKeyFromId($id, $domain)] = $id;
    }

    $ids = array_intersect_key($keysIdsMap, $messages);

    $this->translateAssets(array_combine(array_values($ids), array_values($messages)), $locale);
}
```

Todo:

- [x] Make some real tests to be 100% sure there is no BC
- [x] Add tests to guarantee the fix

Commits
-------

66a3c03 Fix idempot
5A21
ency of LocoProvider write method
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Projects
None yet
Development

No branches or pull requests

5 participants
0