## The WRITE From different action, we will submit to the Localization Service a set of string to translate. It can be from template, TyObject, etc… In order to route these strings to Crowdin, we need to identify the most appropriate way to do so, taking into consideration that it is **NOT** a `real-time` system. Therefore, the translations will not be available immediately; it will depend on the approval of the translation team on Crowdin. Once the translation is completed and approved on Crowdin, a **webhook will be triggered from Crowdin** to the Localization Service to return the new translated strings. **The new data will be sent to the local database**, ready to be accessed (the READ part). ⚠️*To keep it simple (and because it don't impact the whole behaviour) in every strategy, data from Crowdin will always come back directly with webhooks and data will always be stored in the local database (embed in the Localization Namespace) on K8S* ### 1. 🟡 Send all translation requests on a queue and consume it when we have time ```mermaid flowchart LR A[Projects] --> |1: New string to translate in a queue| B C{{Localization Service}} --> |2: Consume message in the queue| B[(Queue)] D{Crowdin} -.-> |4: Webhooks returning translated datas| C C --> |3: Send new string to translate to Crowdin| D C --> |5: Store the returned datas in our database| E[(Internal Database)] ``` - **Advantage:** - The message queue can be consumed via a CRON command and can be executed during off-peak hours, reducing the service load (or atleast delaying the service load) - We can batch crowdin request: instead of calling request on each translation request, we can just consume the queue, group X strings to translate and send it on Crowdin (respecting the Crowdin's API limit) - **Disadvantage:** - We have one more service (queue system) to manage and it must be joinable ### 2. 🟢 Call the Localization Service as a middleware to optimize call on Crowdin ```mermaid flowchart LR A([Projects]) --> |1: New string to translate| B B{{Localization.Service}} --> |2: Send new string to translate to Crowdin| C{Crowdin} C -.-> |3: Webhooks returning translated datas| B B --> |4: Store the returned datas in our database| D[(Internal Database)] ``` - **Advantage:** - Simpler than a queue system, ne need to add one more service - We are calling a local service, it can be more efficient on each HTTP Call (comparing to call Crowdin Services) - **Disadvantage:** - During the day, we may reach a big load on the Localization Service - More difficult to batch Crowdin request (group string to translate) - **Alternative:** - 💡 To lighten the server load, we can add a queue service like the Redis Pub Sub, RabbitMQ or topic via Kafka. It will be between the Localization Service & Crowdin. Like the Strategy #1, the Localization Service will store temporary string to translate in a queue, waiting to be consumed later in the day. ### 3. 🔴 Call directly Crowdin, without intermediary ```mermaid flowchart LR A([Projects]) --> |1: Send new string to translate to Crowdin| B B{Crowdin} -.-> |2: Webhooks returning translated datas| C{{Localization.Service}} C --> |3: Store the returned datas in our database| D[(Internal Database)] ``` - **Advantage:** - Less code to maintain on the Localization Service: we don't need any controller to handle translation request and no need to keep a queue system to delay the call - **Disadvantage:** - We can easily reach Crowdin limit rate on the API - Calling an external service can be less efficient than a local one and remove a lot of flexibility on implementation.