Actions
Actions have 2 purposes : update the store and propagate this change as a render event.
Overview
import { createAction } from 'dispersive';
const createBook = createAction(title => Book.objects.create({ title }), [Book]);
Basics
import { createAction } from 'dispersive';
const updateSomething = createAction(() => {
// Transaction context on Model1 and Model2
}, [Model1, Model2]);
The function createAction takes 2 arguments : a task function and a models array. Models are used to :
- Open a transaction on each model before calling the task
- Close the transaction on each model after calling the task
- Propagate an event on each model (for rendering purpose)
Transaction
const startGame = createAction((game) => {
game.players.forEach(player => {
if (!player.ready) throw `Can't start game : ${player.name} is not ready`;
player.position = [random(), random()];
player.save();
});
game.update({ started: true });
}, [Game, Player]);
In the example above, if any player is not ready everything will be canceled. The transaction will be aborted. No player will have a set position and the game will not be started.
Calling actions from async functions
Most of the time, actions are called before and/or after asynchronous calls. In these cases, actions are only used by specifics async functions. It can be done with "on the fly actions".
import { runAsAction as run } from 'dispersive/action';
const fetchBookList = async () => {
const data = await fetch('http://api...');
return run(() => data.map(
({ title }) => Book.objects.create({ title })
), [Book]);
};