Tenant Patching

Hi CUBA team,

This is my first time using CUBA and there are some confirmation I need before I start developing for my first CUBA project requested by me client. I have searched in google and forum and read but still a bit confused on some topics.

  1. Multiple Databases (Tenant Database)
    From other forum posts, I understand that CUBA is going to add features on Multiple Databases. I have some questions.
    a. I will write a HR solution for my client. The client will offers HR solution to their existing customers. Their requirements are 1 webapp for multiple databases. The reason is said there are 100 customers with 100 databases (all entities are same across tenants) and there are 100 webapp.war then it will be very tedious to patch after fixing bugs or adding more features into the project. Will the promised Multiple Databases in another post’s summary caters my client’s requirement? Previously, we have a project to customize Liferay for Logistics modules and our client gone into Liferay Tenant Sharding with 400 databases. When the main Liferay Server boot up, it takes more than 2 hours. Although Liferay are using Hibernate but I think there must be some testing on this. May be implement it to connect only main DB or chosen DB, and connect only when the DB connection is requested from within eclipselink.

  2. Multiple Databases (Non-Tenant / Non-CUBA / Integration)
    a. My client’s customers has Finger print devices and some databases in their server. My plan is to generate Entities from their Db and works inside CUBA. They have MsSQL, MySQL and some even .mdb (not sure CUBA can works on .mdb or not haha :smiley: ). I mean, if we have 3 Db in the project, 1 is type Pg, 1 is type My and 1 is type Ms. Will it be possible?

  3. Because of some reason, we will implement portal either using CUBA MVC Portal or HTML5 + CSS + JavaScript. The website / portal will get data either from DataManager or JSON. I have an issue. Said Customer A login into portal (not necessary CUBA own MVC portal), instead of working inside portal, they want to use CUBA webclient, if we redirect them to the webclient address like http://www.abc.com:8089/app, they will need to login by typing user name and password. Is it possible to silent login and straight go to the main page with menu items? And better silent logout when customer close all firefox or close all chrome browser (doesn’t matter my portal has remember me on or not)

  4. From the scaling manual, the middlewares will share webclient sessions and users of webclient will not logout if the webclient down. How about Portal. After I obtain Session Id from REST, I can operate on REST using &s=sessionid. Will user get error if 1 of the portal server is down? In addition, if the session info (either portal or webclient) is in middleware server C, if server C is down, will the session lost (causing either logout or errors on webclient or portal browser connection)?

  5. Said I have 2 middleware server, 2 webclient server and 2 portal server. And I want to patch middleware, weblclient and portal with a new version. How do I operate so that customer is still operating while I am doing patching. Do I need to stop all server, patch and start all server?

  6. I have a friend and he is also interesting on CUBA after he saw me hacking with samples projects. He asked is it possible to do all below steps in a script.

  7. delete old temp folder, duplicate current project folder into temp folder

  8. using temp folder, modify project property so that final war will have different file name (to be deployed into existing tomcat server before moving to new live server <<< I have another answered post asking about sharing same tomcat with multiple same project).

  9. using temp folder, compile and create war

  10. deploy war to server A, B, C …

  11. modify config files and copy and paste to server A, B, C

I am not that good in scripting. Is scripting possible to perform above steps?

Thanks for helping up.

1 Like

Hi Adam,
please see my answers below.

> 1. Multiple Databases (Tenant Database)

The upcoming CUBA multiple database support is designed for connecting different databases in terms of their scheme and purpose. It means that every database will have its own set of entities and the corresponding persistence.xml file. So I don’t think it is suitable for your task - I cannot imagine 100 sets of identical entities in one project, it would be just a huge waste. I would recommend a more traditional approach to muti-tenancy - one database with tenantId and DBMS-specific sharding, or separate WAR plus database per tenant.

Regarding startup time, the application will connect only to the primary database on startup, and all other persistence units are initialized only on the first access to their entities. So the startup time should be a constant time regardless of the number of databases.

> 2. Multiple Databases (Non-Tenant / Non-CUBA / Integration)

This is possible and actually the primary use case for connecting to multiple databases. However, MS Access databases are not supported.

> 3. …Is it possible to silent login and straight go to the main page with menu items?

We’ve just started working on Single Sign-On feature for CUBA applications. If things go well, it will be available in the recent release 6.3 in September. If we don’t make it in time, it will be released later this year.

> 4. From the scaling manual, the middlewares will share webclient sessions and users of webclient will not logout if the webclient down.

This is not quite correct. Middleware servers share UserSession (not a HttpSession) objects which helps when a Middleware server goes down. If a WebClient server is down, all its HttpSessions are lost and all users connected to this WebClient will have to login again. The same is true for Portal Client if you don’t set up a HttpSession replication between them. However, unlike WebClient sessions, PortalClient sessions should be small and the replication is possible. See Apache Tomcat 8 (8.0.53) - Clustering/Session Replication HOW-TO

> 5. Said I have 2 middleware server, 2 webclient server and 2 portal server. And I want to patch middleware, webclient and portal with a new version.

You can update your 24/7 systems without downtime using either a whole spare cluster or one by one.

In the first case, you roll out the new version to a spare cluster and move some users to it for final testing. After that, move the rest of the users to the spare cluster and update the main cluster.

In the second case, which is more risky but does not require additional servers, you can update Middleware by just stopping and updating the servers one by one. Before stopping a WebClient server, use connection draining on the load balancer.

Both approaches assume that your database scheme is compatible with the old and the new version of the software. In the second case, you should also be sure that serialized form of objects shared between Middleware servers (e.g. something stored in UserSession attributes) is compatible too.

> 6. …is it possible to do all below steps in a script.

I’m sure everything you mentioned here is possible to do by scripts, at least on Unix-like systems. If you have more concrete questions, feel free to ask.

1 Like

Thanks Konstantin Krivopustov,

My checking list is almost done. Thank you very much.

The new multiple databases feature is what I need to work with finger print logs DB.

1 DB sharing for many tenants is rejected from my client for some reasons. So, I have to go for Wars and DBs. Which led me to Item 6. I might need a service to write the script for me as my friend and I are not that expert in Unix-like systems.

Finally, are there any tweaks so that 1 war and DBs can work? Because 100 DB is exactly having same set of Entities.

> are there any tweaks so that 1 war and DBs can work?

Perhaps it can be done on the connection pool level. I can imagine a solution when the connection pool returns a connection depending on some thread-local variable identifying the database.

Hi Konstantin Krivopustov,

Said there are 300 wars and 300 dbs. Updating dbs are easy. The 300 wars …

I wish there will be a way.

  1. user login (main db)
  2. get db connection info based on user. (main db)
  3. switch db connection from the main to the user’s
  4. user doing things (user db)

may be

  1. after login
  2. specify every db (1 war can have multiple db according to september version that mean if 1 war has 3 dbs, 300 wars will have 900 dbs) connection string.
  3. call something to refresh db connections

That means, inside Studio, we are working on main db(s). While runtime, after login, each db(s) connection string / url / password can be specify.

I wonder how CUBA or eclipselink caching. Is it global or on each database connection?

If this can be done. Then mostly i will have like 3 wars (main version, customize version 1 and 2) with 900 dbs.

Note : forget about dbs, maintaining 300 wars are insane.

BTW, how many concurrent users are expected for each tenant/DB?

Each tenant must at least support 10 concurrent users.

The client has agreed to do the initial scaling structure at here Application Scaling - CUBA Platform. Developer’s Manual @ Stage 4.

The tenant will be inside our cluster (that mean 300 wars in each server for middleware and webclient 2x2 or 5x5 or 10x10) until they sign up for an instance or instances for performance boosting.

Note : 300 tenants target is first year expected target.

Honestly, from the past projects, vaadin is super slow and did not perform well on tablet or mobile. We might do more in Portal scaling (either Enonic XP or HippoCMS or CUBA MVC Portal or Spring Boot). May be vaadin is speedy in CUBA? I wonder if there is a browse page for Customer in portal, how do I restrict it as exactly the same form in webclient. Any link?

Okay, now I have a better understanding of your situation.
Give me some time to think of how your multi-database requirement can be approached.

Regarding Vaadin and UI performance, I would suggest you creating a test project in Studio, add some entities with many attributes and generate standard screens. Use COMPOSITION relations, then your edit screens will also contain tables. It will take less than an hour, and you will be able to test the real-life performance on any device and connection.

In general, I would recommend creating the first version of your application UI in CUBA/Vaadin generic UI, because you will do it very fast and will be able to go to production ASAP. After that, if the performance is not good enough, you can consider creating another UI on different technology working with your Middleware via REST API. Perhaps by that time CUBA will offer you easy scaffolding of JavaScript portals - we are working on it now.

Hi Adam,
I’ve got the following idea for how to implement your multi-database requirements.

Setup:

  • The main database stores the list of users and information about tenants and their databases.
  • At design time, only one tenant database is defined in Studio as an additional data store (the feature of the upcoming 6.3/2.3 release). Business entities are defined in this data store.
  • At run time, the standard DBCP2 connection pools for tenant databases are defined in Tomcat’s context.xml with different JNDI names (e.g. jdbc/db1, jdbc/db2, … jdbc/db100).
  • The core of the solution is a custom java.sql.DataSource implementation that can select one of the above-mentioned connection pools for obtaining a connection dynamically based on some in-memory condition (a thread-local variable or UserSession attribute)
  • The persistence unit working with tenants data is set up to use this custom datasource.

So the following happens at runtime:

  • A user logs in to the application using the credentials stored in the main shared database.
  • After login, the application sets the JNDI name of the tenant’s database in a UserSession attribute.
  • All requests for connection through the custom DataSource will return a connection to the tenant’s database.

If you decide to go this way, and if you want us to implement this solution for you, please drop us an email at info@cuba-platform.com to discuss terms.

Hi @knstvk and @adamtang777

I know this post is old now but I’m interested in it’s outcome as I have a very similar need. I’d prefer to have a few big servers connecting to database per tenant than having to find servers per tenant.

I’d appreciate any information or feedback about the discussions above.

Thanks
John