MDrivenWiki
Log in

Advanced MDrivenServer periodic server-side actions

From MDrivenWiki

Running background jobs on the server

A re-occurring pattern when building multi user software systems is the need to execute periodic actions. With MDrivenServer you can use it to execute re-occurring actions, or periodic actions.

A Periodic action is defined by a selection expression that selects what objects to act on. For each object selected for a periodic action we want to do the “action” and that probably needs a cluster of objects and it needs to do different stuff to evolve some object state. To enable efficient load for such an object cluster you must define and associate a viewmodel with each periodic action.

The periodic action logic will load the viewmodel for your object and loop through all actions that it finds in its root viewmodel class. When all actions are executed the periodic action logic will save any changed state that was the result of your actions.

Periodic actions can be used to “automatically” step your information from one state to the next – given that the circumstances are correct.

This ability might take some getting used to – but it can be used for things like assigning a unique number to an order or an article in your domain model – or for actions that need to be done serverside for some particular reason.

Define the periodic actions in the ViewModelEditor:

ServerSide Actions 01.pngServerSide Actions 02.png

With this technique you can change any and all state of objects in your database in an efficient manner with very little code.

As a common case is the need to assign a unique number I will show this. The client cannot alone be used to guarantee that the next number in a sequence is taken, since there may be multiple users trying to do this at the same time. We need to make sure we serialize all user requests for a new number. This is commonly done with a database lock. There is however a nice alternative to a harsh db-locking technique and that is to serialize via a server side action.

Consider having this state machine:

ServerSide Actions 03.png

The ViewModel associated with the periodic action on the server can now assign my number.

ServerSide Actions 04.png

The client will set the AssignNumber state. The Server side action will look for

Order.allinstances- >select(o|o.State=’AssignNumber’)

When objects are found they will be assigned a new number by the actions in the ServerSide ViewModel and saved.

Combined with a periodic client action that calls selfVM.Refresh we will see on the client as soon as state is changed to NumberAssigned.

Since we do not want the client to poll selfVM.Refresh all the time we set the EnableExpression in this action to self.State=’AssignNumber’.

Following this pattern we get the user pushing a button to get a new number, we can show some info about working – the client starts refreshing – the server does its job – the client gets the new info by its refresh – the info abut progress can be hidden as a consequence. This way we have serialized an action in our system with model driven techniques that will scale well and work of any number of users of your system.

New recommendation on Number Assignment pattern

As above but mark the state-attribute and the number attribute with tagged value Realtime - this removes the need for having periodic action with Refresh on the client.

Combine with triggering via SysAsyncTicket and lower/remove the frequency of the ServerSide-job execution

Other uses of Server side Actions

We have also implemented several additional common actions that you can have the MDrivenServer perform for you.

Emailing from the server

This topic is described here Emailing from an app using MDrivenServer

Importing data from other SQL sources

This topic is described here Import_data_from_other_SQL_servers

Exporting files from MDriven Server

This topic is described here More about exporting

Catching errors and debug info for serverside actions

Debugging serverside is covered here Debugging MDrivenServer Serverside actions

Environment specific execution

Read on Server wide variables here Server_Wide_Variables