DZone
Thanks for visiting DZone today,
Edit Profile
  • Manage Email Subscriptions
  • How to Post to DZone
  • Article Submission Guidelines
Sign Out View Profile
  • Post an Article
  • Manage My Drafts
Over 2 million developers have joined DZone.
Log In / Join
Please enter at least three characters to search
Refcards Trend Reports
Events Video Library
Refcards
Trend Reports

Events

View Events Video Library

Zones

Culture and Methodologies Agile Career Development Methodologies Team Management
Data Engineering AI/ML Big Data Data Databases IoT
Software Design and Architecture Cloud Architecture Containers Integration Microservices Performance Security
Coding Frameworks Java JavaScript Languages Tools
Testing, Deployment, and Maintenance Deployment DevOps and CI/CD Maintenance Monitoring and Observability Testing, Tools, and Frameworks
Culture and Methodologies
Agile Career Development Methodologies Team Management
Data Engineering
AI/ML Big Data Data Databases IoT
Software Design and Architecture
Cloud Architecture Containers Integration Microservices Performance Security
Coding
Frameworks Java JavaScript Languages Tools
Testing, Deployment, and Maintenance
Deployment DevOps and CI/CD Maintenance Monitoring and Observability Testing, Tools, and Frameworks

Last call! Secure your stack and shape the future! Help dev teams across the globe navigate their software supply chain security challenges.

Modernize your data layer. Learn how to design cloud-native database architectures to meet the evolving demands of AI and GenAI workloads.

Releasing software shouldn't be stressful or risky. Learn how to leverage progressive delivery techniques to ensure safer deployments.

Avoid machine learning mistakes and boost model performance! Discover key ML patterns, anti-patterns, data strategies, and more.

Related

  • Building Modern 3factor Apps in 2021 With Event-Driven Programming
  • Top React Libraries for Data-Driven Dashboard App Development
  • 7 Salesforce CRM Integration Methods You Must Know About
  • Decoding the Merits of MEAN Tech Stack for Your Organization

Trending

  • Beyond Linguistics: Real-Time Domain Event Mapping with WebSocket and Spring Boot
  • Microsoft Azure Synapse Analytics: Scaling Hurdles and Limitations
  • A Guide to Developing Large Language Models Part 1: Pretraining
  • It’s Not About Control — It’s About Collaboration Between Architecture and Security
  1. DZone
  2. Data Engineering
  3. Data
  4. Storeon: An Event-Based State Manager for Velo

Storeon: An Event-Based State Manager for Velo

In this article, we explain how to manag state in Velo with a light-weight and robust solution: Storeon, an event-based state manager.

By 
Alexander Zaytsev user avatar
Alexander Zaytsev
·
Updated May. 26, 22 · Tutorial
Likes (4)
Comment
Save
Tweet
Share
10.1K Views

Join the DZone community and get the full member experience.

Join For Free

Update: Jan 6, 2021 Corvid changed its name to Velo.

Motivation

In the article, “State management in Corvid,” Shahar Talmi brings up a question about controlling app states in Velo. If you’re not familiar with Velo, it’s a development platform running on Wix that allows you to quickly and easily develop web applications.

Accurately controlling the state of any app is a really big problem. If you have many component dependencies or need to handle constant user interactions, you're going to suffer a bit when you want to eventually add a new feature or scale your application.

In this article, I share my solution — a very tiny library called Storeon (it’s only 180 bytes) that features an easy interface. So, I wrote a wrapper for integration with Velo. As a result, we have the state manager storeon-velo, and it’s less than 90 lines of code.

You may also like: Angular Tutorial: State Management With NgRx.

How it Works

We will create a traditional study app with counters. I will use two counters to help provide a better demonstration.

At first, we need to install the library from Package Manager.

Package Manager panel in Wix editor, installing storeon-velo

Then, we can create one more file for store initialization in the public folder.

We will write our business logic in the public/store.js file.

Storeon's state is always an object; it canʼt be anything else. Itʼs a small limitation and not too important to us, but we have to remember it.

public/store.js

JavaScript
 




x
28


 
1
// The store should be created with createStoreon() function.
2
// It accepts a list of the modules.
3
import { createStoreon } from 'storeon-velo';
4
  
5
// Each module is just a function,
6
// which will accept a store and bind their event listeners.
7
const counterModule = (store) => {
8
  // @init will be fired in createStoreon.
9
  // The best moment to set an initial state.
10
  store.on('@init', () => ({ x: 0, y: 0 }));
11
 
12
  // Reducers returns only changed part of the state
13
  // You can dispatch any other events.
14
  // Just do not start event names with @.
15
  store.on('INCREMENT_X', (state) => ({ x: state.x + 1 }));
16
  store.on('DECREMENT_X', (state) => ({ x: state.x - 1 }));
17
  
18
  store.on('INCREMENT_Y', (state) => ({ y: state.y + 1 }));
19
  store.on('DECREMENT_Y', (state) => ({ y: state.y - 1 }));
20
}
21
 
22
// createStoreon() returns 4 methods to work with store
23
export const {
24
  getState, // <- will return current state.
25
  dispatch, // <- will emit an event with optional data.
26
  connect, // <- connect to state by property key.
27
  connectPage, // <- wrapper around $w.onReady()
28
} = createStoreon([counterModule]);



So, we created a store in the public folder and exported from there with four methods. In the second part, we will create our UI, and we will write logic to change the state. 

Letʼs add two text elements to display our counter value and four buttons for event increments/decrements.

Creating two counter components

Creating two counter components

Of course, we have to import the store methods from the public file to the page's code:

import { dispatch, connect, connectPage } from 'public/store'; 

With connect("key", callback), we can subscribe to any store properties, and the callback function will run when the page is loaded and each time the listed property changes.

The connectPage(callback) is a wrapper around $w.onReady(callback). With dispatch(event, [data]), we will emit events.

Page Code

JavaScript
 




xxxxxxxxxx
1
42


 
1
import { getState, dispatch, connect, connectPage } from 'public/store';
2
 
3
// Connect to property "x".
4
// The callback function will be run when the page loads ($w.onReady())
5
// and each time when property "x" would change.
6
connect('x', (state) => {
7
  console.log('counter X is changed', state);
8
 
9
  $w('#textX').text = String(state.x);
10
});
11
 
12
// Connect to "y"
13
connect('y', (state) => {
14
  console.log('counter Y is changed', state);
15
 
16
  $w('#textY').text = String(state.y);
17
});
18
 
19
// Wrapper around $w.onReady()
20
// The callback function will be run once.
21
connectPage((state) => {
22
  // Here we also have an object with initial state
23
  console.log('onReady runs', state);
24
 
25
  // X counter events
26
  $w('#buttonIncX').onClick(() => {
27
    dispatch('INCREMENT_X');
28
  });
29
 
30
  $w('#buttonDecX').onClick(() => {
31
    dispatch('DECREMENT_X');
32
  });
33
 
34
  // Y counter events
35
  $w('#buttonIncY').onClick(() => {
36
    dispatch('INCREMENT_Y');
37
  });
38
 
39
  $w('#buttonDecY').onClick(() => {
40
    dispatch('DECREMENT_Y');
41
  });
42
});


Demo

Modules

The function, createStore(modules), accepts a list of modules. We can create different functions to split business logic into our app. Letʼs look at a few examples.

Example 1: Synchronization in the app state with the wix-storage memory API:

JavaScript
 




xxxxxxxxxx
1
10


 
1
// https://www.wix.com/velo/reference/wix-storage/memory
2
import { memory } from 'wix-storage';
3
 
4
export const memoryModule = (store) => {
5
  // @changed will be fired every when event listeners changed the state.
6
  // It receives object with state changes.
7
  store.on('@changed', (state) => {
8
    memory.setItem('key', JSON.stringify(state));
9
  });
10
}



Example 2: Tracking an event to external analytics tools with wixWindow.trackEvent():

JavaScript
 




xxxxxxxxxx
1
13


 
1
import wixWindow from 'wix-window';
2
 
3
export const trackEventModule = (store) => {
4
  // @dispatch will be fired on every `dispatch(event, [data])` call.
5
  // It receives an array with the event name and the event’s data.
6
  // Can be useful for debugging.
7
  store.on('@dispatch', (state, [event, data]) => {
8
    if (event === 'product/add') {
9
      // Sends a tracking event to external analytics tools.
10
      wixWindow.trackEvent('CustomEvent', { event, data });
11
    }
12
  });
13
}



Example 3: Combining modules:

JavaScript
 




xxxxxxxxxx
1


 
1
const store = createStore([
2
  coutnerModule,
3
  memoryModule,
4
  trackEventModule,
5
]);


Conclusion

As you can see, we were able to quickly implement our state management solution with a minimal amount of code. Of course, due to data binding in Velo, you normally don’t have to worry about state management. However, in more complex applications, the issue can become more difficult, and state management will become more challenging to handle.

State management can be a tricky problem, but Storeon offers a simple, yet robust solution. In addition, Velo allows us to quickly implement this in our application, all while focusing on code and not having to spend time dealing with other issues. 

Resources 

  • Storeon on GitHub
  • Storeon
  • Storeon Velo on GitHub
  • Discussion on Velo Forum

Demo 

  • Site
  • Open In Editor

Further Reading

  • Helping SMBs Solve Data Latency Issues: A Corvid by Wix Case Study.

This article originally published on https://shoonia.site

app application Business logic JavaScript Data binding Web project Event GitHub

Published at DZone with permission of Alexander Zaytsev. See the original article here.

Opinions expressed by DZone contributors are their own.

Related

  • Building Modern 3factor Apps in 2021 With Event-Driven Programming
  • Top React Libraries for Data-Driven Dashboard App Development
  • 7 Salesforce CRM Integration Methods You Must Know About
  • Decoding the Merits of MEAN Tech Stack for Your Organization

Partner Resources

×

Comments
Oops! Something Went Wrong

The likes didn't load as expected. Please refresh the page and try again.

ABOUT US

  • About DZone
  • Support and feedback
  • Community research
  • Sitemap

ADVERTISE

  • Advertise with DZone

CONTRIBUTE ON DZONE

  • Article Submission Guidelines
  • Become a Contributor
  • Core Program
  • Visit the Writers' Zone

LEGAL

  • Terms of Service
  • Privacy Policy

CONTACT US

  • 3343 Perimeter Hill Drive
  • Suite 100
  • Nashville, TN 37211
  • support@dzone.com

Let's be friends:

Likes
There are no likes...yet! 👀
Be the first to like this post!
It looks like you're not logged in.
Sign in to see who liked this post!