Vaadin 14 and dynamic UI with OSGi


knowing that full OSGi support with npm will only come with Vaadin 18, I’d like to create some proof-of-concept for migrating the Vaadin-8 based UI of the project I work for to Vaadin 14+. Basically, it was already possible to run a UI in a Karaf environment with Vaadin 14.

The next step would now be to check how a dynamic UI can be realized, “dynamic” meaning that e.g. the entries in the main menu depend on the available view bundles, or the tabs in a tab sheet depend on the available tab bundles. Taking the view bundles as an example, the pattern used up to now was to realize an individual view provider for each specific view, the view provider instantiated as service using Declarative Service annotations, having all the necessary dependencies (@Reference) injected which are required for the specific view. Then passing these dependencies to the respective view class when instantiating the view.

The different view provider services were then registered as dependency (optional, cardinality multiple) by a UI provider which passed them to the instantiated UI, and the UI then built the main menu using the list of registered view providers. Tab providers worked in a similar way, only one level deeper.

UiProvider and ViewProvider are no longer available in Vaadin 14. It was mentioned that the Instantiator would be the replacement for the providers for such dynamic injections (see here: Looking at the Instantiator interface documentation, this seems to be singleton-like (“Deployment will fail if multiple candidates are returning true from init(VaadinService)”). Does this mean that I need to create one custom Instantiator as Declarative Service component, to which all required services for the UI are injected, including possibly required “second-level instantiators” which are view specific, then deciding in the “getOrCreate” method which instantiator shall be used to create the object, e.g. with the class name of the view/tab/… object as discriminator?

Has anybody already tried this? It there some sample project or some tutorial how to create and use such a custom instantiator, maybe specifically in combination with Declarative Services? Looking at the DefaultInstantiator and SpringInstantiator code hasn’t really shed much light on this, although the SpringInstantiator points towards the direction that instantiation is really “centralized”, i.e. only happens at one point in a singleton, with the Spring bean factory taking care of everything else.