View source | Discuss this page | Page history | Printable version   

Retail:Developers Guide/How-to/IndexedDBMigrationGuide

Contents

Introduction

As of 20Q4 release, the WebPOS is no longer using WebSQL to store any information, and instead uses IndexedDB across the whole application. All usage of WebSQL is no longer supported, our WebSQL-based API is deprecated and will be removed in some future release.

Therefore, all developers are encouraged to migrate all their WebSQL-based code to the newer IndexedDB APIs.

On top of this, even in 20Q4 some existing APIs and hooks have been either deprecated or removed, so all developers that need their custom code to work in 20Q4 will need to make adjustments to it.

This document is a general guide that walks developers through the process of updating their code so that it works correctly in 20Q4 and newer releases, using our new IndexedDB-based APIs.

Usage of WebSQL and IndexedDB

WebSQL and IndexedDB are used essentially with the same purpose in Openbravo. Both technologies allow the application to store data that is required for it to work correctly in offline. This includes:

All this information was stored in WebSQL in previous versions of Openbravo. Starting 20Q4, all this information is now stored in IndexedDB

However, Openbravo does not exactly use IndexedDB in the same way that WebSQL was used before. Instead, there are significant differences that developers need to take into account

Databases

Previously, only one WebSQL database was created per application. Data of all types (masterdata, transactional, offline login-related) was stored in this database.

Instead, now a separate IndexedDB database is created per each data type. So currently four IndexedDB databases exist per application:

APIs

Previously, we had a single, combined API that was used for every database operation. This API was used across the board to do any database-related operation, from reading products, to saving the ticket.

This was a source of several problems, like unwillingly exposing to developers the ability to modify models that should in general not be modifiable by normal means (like masterdata records that might later on be overwritten by the incremental refresh process).

On IndexedDB, each type of data that can be either read or modified has its own specialised APIs and components. There are two main APIs:

These APIs are also very different from the previous OB.Dal API that was used to do operations in WebSQL:

As an example of this last statement, the MasterdataController allows developers to define models, and to query the database in several different ways, but does not allow developers to modify the database records directly, because the Masterdata refresh process in general has the responsibility of updating this data correctly.

Similarly, the StateController API allows developers to define models and actions, and dispatch actions on the state, but the details about the persistence of the data in the database is handled internally by the controller, and is not exposed to the developer.

It is very important that all developers know well both main APIs before any migration process is attempted.

We have separate documents that describe the MasterdataController and the StateController APIs, and developers should read them before continuing with the next sections.

Migration Process

This section will describe the main steps that should be followed when approaching the migration of custom code to IndexedDB and the newer APIs.

The general idea is that for any custom piece of code, module or modules for a particular customer, all individual functionality must be reviewed to understand the current usage of WebSQL, and then specific migration steps need to be followed for each component.

Identification of WebSQL usage

The first step in the migration process is to identify which parts of the code are using WebSQL or our old business logic components or hooks, and what they are using them for.

As a general rule, the following code will need to be adjusted:

Masterdata models

Any code creating Backbone models that are registered later as Masterdata models by doing some code similar to:


 
  OB.Data.Registry.registerModel(OBCOMBO_Product);
  OB.OBPOSPointOfSale.Model.PointOfSale.prototype.models.push(OBCOMBO_Product);

will need to be updated to use the MasterdataController infrastructure

Synchronised models

Any code creating Backbone models that are registered later as a 'synchronised model' by registering it in the synchronised models array:

 
  OB.MobileApp.model.get('dataSyncModels').push({
    model: OB.Model.TerminalMonitor,
    className:
      'org.openbravo.certification.france.terminalmonitor.ProcessTerminalMonitor',
    criteria: {}
  });

will need to be refactored into an action dispatched on the new StateController.


Transactional models saved in WebSQL

Sometimes Backbone models were persisted into the WebSQL database by using the initCache function and then saving it in the table:

 
  OB.Dal.initCache(OB.Model.MyModel);
  OB.Dal.save(OB.Model.MyModel);

In general if a model was saved by using the OB.Dal.save function, it will have to be refactored into a State Model, and some actions to save/update it in the state will also have to be created using the StateController API.

Deprecated/removed hooks

As part of the transition to IndexedDB state, some very central parts of the business logic of the application has been completely reimplemented. This includes all basic Ticket functionality like:

As part of this reimplementation, some hooks have been deprecated (and lost some functionality in the process), and others have been deleted.

In the coming section we will provide a list of all affected hooks. You should review your code to see if any of them is being used. If that's the case, the code will need to be refactored using some combination of ActionPreparation/ActionHooks, provided by the StateController.

Migration of Masterdata code

For the topic of masterdata migration, we have a separate document that explains the necessary steps to migrate any masterdata-related code to IndexedDB.

Migration of synchronised models

Synchronised models were a mechanism that was used to synchronise data to the backend using a WebSQL-based model. The main idea was:

Some of these principles still remain in our new layer, but if code is using a synchronisedModel to synchronise data to the backend, some parts need to be refactored.

The following steps must be followed:

 
OB.App.StateAPI.Global.registerAction(
  'synchronizeLoyaltyEarnedPoints',
  (state, payload) => {
    const newState = { ...state };
    const newObject = { id: OB.App.UUID.generate(), ...payload };
    const data = {
      modelName: 'LoyaltyEarnedPoints',
      service:
        'org.openbravo.retail.loyalty.programs.process.LoyaltyEarnedPointsLoader',
      newObject: payload,
    };
    const backendMsg = OB.App.State.Messages.Utils.createNewMessage(
      data.modelName,
      data.service,
      newObject,
      { type: 'backend' }
    );
 
    newState.Messages = [...newState.Messages, backendMsg];
 
    return newState;
  }
);

This is, in fact, the only required step. This action will create a new message and add it to the array of messages currently in the system. This message contains essentially the same information the dataSyncModels previously contained: the modelName, and the service (the class that will be used in the backend to process the data).

Once the message is added to the state, it will automatically be persisted in the IndexedDB state database. Then, a separate component called Synchronisation Buffer will pick the message and ensure it is synchronised. The rest of the process doesn't change: an ImportEntry will be created and the data will be processed asynchronously, as before.

In order to actually synchronise data, the action must be dispatched, by doing:


 
OB.App.State.Global.synchronizeLoyaltyEarnedPoints({
  loyaltyProgram: 'MyLoyaltyProgram',
  points: 100
});

Migration of Transactional state persisted models

Transactional models might be persisted in WebSQL, by creating a Backbone model and then using the OB.Dal API to save records in the corresponding table.

The equivalent to this in the new IndexedDB API is the StateModels, that can be registered using the StateController API. By registering a StateModel, you reserve a property in the state, which you can set using actions defined on this model. You need to define actions to set the value of the model, or process it the way you want.

There is no need to actually persist anything explicitly, because any StateModel will be automatically persisted in IndexedDB after any action is dispatched for it.

You can find clear examples on how to define these models in the StateController main document.

Migration of code executed in hooks related to application state actions

As part of the IndexedDB project, a very large part of the WebPOS business logic was refactored to use the new StateController API.

This refactor in many cases meant that functionality that previously was divided in parts and worked non-transactionally was transformed into a transactional action. Because of this, some intermediate hooks had to be removed.

On top of this, some hooks were also removed because the actions themselves already provide a new infrastructure of ActionPreparations and ActionHooks that have great advantages compared to the old ones.

Some of the hooks were not fully removed though, but all of the hooks related to refactored logic should be considered deprecated, and we strongly encourage all developers to refactor all their functionality based on old hooks as ActionPreparations or ActionHooks whenever possible.

The following is a list of all hooks affected by the changes, with their current status:

Functionality Hook Status Notes
Ticket completion OBPOS_PreOrderSave Deprecated Still basically functional, but recommended not to be used. Payment rounding and adjustment now happens inside the action, which means that the hook will receive the original payments instead of the final ones.
Ticket completion OBPOS_PostSyncReceipt Deprecated Still functional, but should only be used for visualisation purposes. All related business logic/state changes should be done in a PostActionHook of the ticket completion action instead.
Ticket completion OBPOS_PostPaymentDone Removed
Ticket completion OBPOS_preAddPayment Deprecated Still exists in main payment actions (payment addition/deletion). However, keep in mind that it was removed from the ticket completion flows.
Ticket completion OBPOS_postAddPayment Deprecated Still exists in main payment actions (payment addition/deletion). However, keep in mind that it was removed from the ticket completion flows.
Ticket completion OBPOS_PreSyncReceipt Removed Should be replaced by a combination of ActionPreparation/ActionHooks for the related ticket completion actions
Ticket deletion OBPOS_PreDeleteCurrentOrder Removed Should be replaced by a combination of ActionPreparation/ActionHooks for the related 'deleteTicket' action
Ticket payments OBPOS_preRemovePayment Removed
Pay Open Tickets OBPOS_MultiOrders_PreSetPaymentsToReceipt Removed
Pay Open Tickets OBPOS_MultiOrderAddPaymentLine Removed
Ticket creation OBPOS_NewReceipt Removed Should be replaced by a combination of ActionPreparation/ActionHooks for the related 'addNewTicket' action
Ticket price modification OBPOS_PreSetPrice Removed Should be replaced by a combination of ActionPreparation/ActionHooks for the related 'setLinePrice' action
Ticket line deletion OBPOS_CheckStockDeleteLine Removed
Ticket line deletion OBPOS_PreDeleteLine Removed Should be replaced by a combination of ActionPreparation/ActionHooks for the related 'deleteLine' action
Ticket line deletion OBPOS_PostDeleteRelatedServices Removed
Ticket line deletion OBPOS_PreDeleteSingleLine Removed
Ticket line deletion OBPOS_PostDeleteLine Removed
Adding products to ticket OBPOS_CheckStockAddProduct Removed Although the code is still there because the old flow is still executed in some cases, the hook itself will not be executed for the main flows
Adding products to ticket OBPOS_GroupedProductPreCreateLine Removed
Adding products to ticket OBPOS_AddProductToOrder Removed Should be replaced by a combination of ActionPreparation/ActionHooks for the related 'addProduct' action
Adding products to ticket OBPOS_PostAddProductToOrderHook Removed
Ticket payments OBPOS_preRemovePayment Removed Should be replaced by a combination of ActionPreparation/ActionHooks for the related 'removePayment' action
Ticket list manipulation OBPOS_PostAddPaidReceipt Removed

Retrieved from "http://wiki.openbravo.com/wiki/Retail:Developers_Guide/How-to/IndexedDBMigrationGuide"

This page has been accessed 10,135 times. This page was last modified on 7 September 2020, at 05:17. Content is available under Creative Commons Attribution-ShareAlike 2.5 Spain License.