Skip to content

PoC API to manage internationalization#1

Open
daniloster wants to merge 1 commit intomasterfrom
poc-abstraction-level
Open

PoC API to manage internationalization#1
daniloster wants to merge 1 commit intomasterfrom
poc-abstraction-level

Conversation

@daniloster
Copy link
Owner

@daniloster daniloster commented Jul 7, 2020

Minimal API to manage internationalization

i18n seems to only require 2 services to takes care of internationalization. (at least in my naive view)

  • ResourcesService
  • LanguageService

ResourcesService

Responsible for managing resources asynchronously through 2 methods:

  • get(language: string): Promise

It will obtain the resource related to the language provided

  • set(language: string, resource: Dictionary): Promise

It will set/save the resource related to the language provided. (Not quite used)

LanguageService

Similarly, this service is responsible for managing language asynchronously through 2 methods:

  • get(): Promise

It will get the current (saved) language for the application

  • set(language: string): Promise

It will set (save) the current language for the application

factoryI18n

Factory method to create a i18n state to resolve translations based on resources and language. Through this method the 2 required service gets wired-up into the flow updating the status of resolutions.

  • Changing language or getting resources are debounced to avoid request where user is still requesting changes
  • Regarding to the resolution of the translations, it can only be performed once resource is successfully loaded
    • Debounce is skipped if the resource is already loaded
  • Changes and listeners are observed through reactive observers

@daniloster daniloster force-pushed the poc-abstraction-level branch from 1da5a95 to 1d926b8 Compare July 7, 2020 20:08
@daniloster
Copy link
Owner Author

Hey @adrai , it is me again.

So, changing the current eco-system present for i18next is likely to cause a breaking change because many of the options exposed in the API might be removed. As dev, having scalability with dry API allow systems grows seamlessly.

For instance, with the approach taken here, any nuance of change can be done on the services before the user pass it as part of the parameters for factoryI18n method.

e.g. some application may have the requirement as "Language should be bound to the current user".

languageService = {
  get: async () => {
    const userId = sharedState.getUserId()
    const response = await fetch(`account/user/${userId}/language`)
    if (response.ok) (await response.json()).language
    // returning null, it will make the library to fallback to the default language
    else return null
  },
  set: async (language) => { /* ... */ },
}

The structure in place does not care about what happen inside it and how is obtained, still, have the ability to track async status to reactive state where devs can listen to perform anything desired.

const i18n = factoryI18n({ ... })

i18n.status.subscribe({
  next: (status) => {
    // send notification based on status to put application on hold, or retry operations
  }
})

The same is possible for language and resources

At the moment, my personal concern is to have so many properties in the i18next with similar semantic meaning as well as no way to listen events to understand what is happening.

languages

lng, languages, fallbackLng, supportedLngs

namespace

ns, defaultNS, fallbackNS

Regarding namespace, is it really required? When I think about applications, even for big ones, I can not see how the translations files would be big enough to justify be broken down into namespaces to allow lazy-load as chunks. Perhaps, I am being naive.

I hope it makes sense 😅

I appreciate the effort you and the community put to have a so widely used library as i18next. Keep up the good work!

@adrai
Copy link

adrai commented Jul 7, 2020

Have not checked this PR yet, already going to sleep 😉

Also i18next started with just a minimal set of functionality... almost 10 years ago... all the features (also namespaces) were requested by the community.

In i18next to have the language bound to a user you have 2 possibilities: first load the users language option and then initialize i18next with that language or create a language-detector.
Some use cases also require a language to be detected in different ways with different fallbacks i.e check cookies, then if logged-in take user’s language, if not take browser’s languge etc...
You see... all this customizations/learnings helped i18next to grow and be used in probably all situations.

Regarding the status updates, i18next emits events...

Ok, afk now...

Good night. 😊

@daniloster
Copy link
Owner Author

Have not checked this PR yet, already going to sleep 😉

Also i18next started with just a minimal set of functionality... almost 10 years ago... all the features (also namespaces) were requested by the community.

In i18next to have the language bound to a user you have 2 possibilities: first load the users language option and then initialize i18next with that language or create a language-detector.
Some use cases also require a language to be detected in different ways with different fallbacks i.e check cookies, then if logged-in take user’s language, if not take browser’s languge etc...
You see... all this customizations/learnings helped i18next to grow and be used in probably all situations.

Regarding the status updates, i18next emits events...

Ok, afk now...

Good night. 😊

Thanks for getting back, have a good evening

@daniloster daniloster force-pushed the poc-abstraction-level branch from 1d926b8 to aad365e Compare July 12, 2020 10:42
@daniloster
Copy link
Owner Author

@adrai 🙏 Thanks again for the whole help with the integration before.

I have put this proposal in the repo (apart), because, I have noticed that what I believe being a nice way to evolve and scale kinda diffs from what we have at the moment with i18next. Then, it would not sound nice to open an issue suggesting this change in the i18next repo.

I am leaving here below some of the points you mentioned before.

In i18next to have the language bound to a user you have 2 possibilities: first load the users language option and then initialize i18next with that language or create a language-detector.

This could be provided by composition for the service. In this current API proposal, (I may be wrong) I have identified that only 2 services are required and all possibilities can be scale for them. Besides, this proposal defines a framework for initialization, update and resolution of resources/language in a way that just changing the the service allow application cover a variety of cases.

Some use cases also require a language to be detected in different ways with different fallbacks i.e check cookies, then if logged-in take user’s language, if not take browser’s languge etc...

This can be implemented in a LanguageService, and, then, provided to the factoryI18n.

You see... all this customizations/learnings helped i18next to grow and be used in probably all situations.

I do understand the way community pushes for each niche solution. Still believe that all scenarios could be covered with minimal API.

Regarding the status updates, i18next emits events...

Yeah, I noticed the emits we have there. At least for me (and again, it might be my limited experience with internationalization), I found non-unified, events were a bit loose - dev experience.


I really appreciate the effort you put in the i18next which is widely used. And it would worth thinking of a re-architecture to get a dry API considering scalability without further changes in the API. 🙂 🙌

If you feel it is not doable (for any condition: time, effort, not valid suggestion), I would appreciate to know.

Thank you again

@adrai
Copy link

adrai commented Jul 12, 2020

fyi: there might be a complete rewrite of i18next in future, but some other stuff needs to be done bofore doing so...
I don't think this happens in 2020 anymore... too much happened this year 😉

@daniloster
Copy link
Owner Author

daniloster commented Jul 12, 2020

That is great. Would you have an idea when it would be happening?

@adrai
Copy link

adrai commented Jul 12, 2020

No ETA yet...

@daniloster
Copy link
Owner Author

Thank you. I think I will try to refine and go ahead with this. ☺️

@daniloster daniloster changed the title [patch] PoC API to manage internationalization PoC API to manage internationalization Oct 3, 2020
@daniloster daniloster force-pushed the poc-abstraction-level branch from aad365e to c51412a Compare October 3, 2020 09:56
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

2 participants