Reader small image

You're reading from  React Components

Product typeBook
Published inApr 2016
Publisher
ISBN-139781785889288
Edition1st Edition
Tools
Right arrow
Author (1)
Christopher Pitt
Christopher Pitt
author image
Christopher Pitt

Christopher Pitt is a principal developer for SilverStripe in Wellington, New Zealand. He usually works on open source software, though sometimes you'll find him building compilers and robots.
Read more about Christopher Pitt

Right arrow

Chapter 3. Saving and Communicating Data

In the previous chapter, we created complex component hierarchies. We created a list of pages and a way to edit those pages. Yet we stopped short of saving and reading any of that data to some kind of storage.

We could, for instance, send an edit through an Ajax request to be saved in a database server. In fact, that's what often happens in the applications we use these days. They always save our interactions, irrespective of whether we expect them to or not.

In this chapter, you will learn about local data stores and communicating with them. You'll also learn about event-based architecture and how it promotes the unidirectional flow of data.

There are many ways to save data. It's a rich and interesting topic that could fill scores of books. I could go so far as to say it is at the core of how businesses and applications work.

Furthermore, how data is communicated can often be different in a maintainable application and an unmaintainable application....

Validating properties


Before we look at storing data, there is another habit I'd like to share with you. The components we created in the last chapter work well together, but our aim is to make each component self-contained. We want others to be able to reuse our components, but they will encounter problems if they don't know which properties our components expect.

Consider what would happen if we used PageAdmin like this:

ReactDOM.render(
    <PageAdmin backend="ajax" />,
    document.querySelector(".react")
);

Faced with this component, and no documentation, it might be tempting to substitute a Backend object with some other configuration data. This looks reasonable to someone unfamiliar with the component. And, without a careful study of all our components, we can't expect others to know what those properties should be.

We can protect against this situation by adding property validation. Let's add some validation to PageEd itor:

PageEditor.propTypes = {
    "id": React.PropTypes.number...

Storing cookies


You must have heard of cookies before. They're a browser-based storage mechanism as old as the Internet, and they are often comically described in movies. Here's how we use them:

document.cookie = "pages=all_the_pages";
document.cookie = "current=current_page_id";

The document.cookie parameter works as a temporary string store. You can keep adding new strings, where the key and value are separated by =, and they will be stored beyond a page reload, that is, until you reach the limit of how many cookies your browser will store per domain. If you set document.cookie multiple times, multiple cookies will be set.

You can read the cookies back again, with a function like this:

var cookies = {};

function readCookie(name) {
    var chunks = document.cookie.split("; ");

    for (var i = chunks.length - 1; i >= 0; i--) {
        var parts = chunks[i].split("=");
        cookies[parts[0]] = parts[1];
    }

    return cookies[name];
}

export default readCookie;

The whole cookie string...

Using local storage


The next type of storage we will look at is a relatively recent addition to the browser toolset. It's called local storage, and it's been around for a while. You can add items to it as follows:

localStorage.setItem("pages", "all_the_pages");

It's simpler than cookies to read items from:

localStorage.getItem("pages");

This will persist the data beyond page reloads or the browser closing. You can store considerably more data than in cookies (anywhere from 3 MB to 10 MB, by default), and the interface is easier to use.

So, how can we use this to store our pages? Let's abstract local storage a bit:

export default {
    "get": function(key, defaultValue) {
        var value = window.localStorage.getItem(key);
        
        var decoded = JSON.parse(value);

        if (decoded) {
            return decoded;
        }

        return defaultValue;
    },

    "set": function(key, value) {
        window.localStorage.setItem(
            key, JSON.stringify(value)
        );
  ...

Using event emitters


Until now, our components have communicated with the backend through method calls. That's OK for tiny applications, but when things start to scale, we will forget to make some of those method calls.

Look at onUpdate, for instance:

onUpdate(id, field, value) {
    this.props.backend.update(id, field, value);

    this.setState({
        "pages": this.props.backend.getAll()
    });
}

Every time we change the state of a page, we have to fetch an updated list of pages from the backend. What if multiple components send updates to the backend? How will our PageAdmin component know when to fetch a new list of pages?

We can turn to event-based architecture to solve this problem. We've already encountered and used events! Recollect what we did when we created the page edit form. There, we connected to input events so we could update pages when input values changed.

This kind of architecture moves us closer to a unidirectional flow of data. We can imagine our entire application like...

Summary


In this chapter, we looked at how to protect our components from faulty properties. We also saw how easy it was to use cookies, although they are limited for what we need. Fortunately, we can use local storage and work it into our existing backend and components.

Finally, we explored using events to push state changes out to all interested components.

In the next chapter, we will start prettying up our components. We'll look at ways to style and animate them, bringing our interface to life!

lock icon
The rest of the chapter is locked
You have been reading a chapter from
React Components
Published in: Apr 2016Publisher: ISBN-13: 9781785889288
Register for a free Packt account to unlock a world of extra content!
A free Packt account unlocks extra newsletters, articles, discounted offers, and much more. Start advancing your knowledge today.
undefined
Unlock this book and the full library FREE for 7 days
Get unlimited access to 7000+ expert-authored eBooks and videos courses covering every tech area you can think of
Renews at $15.99/month. Cancel anytime

Author (1)

author image
Christopher Pitt

Christopher Pitt is a principal developer for SilverStripe in Wellington, New Zealand. He usually works on open source software, though sometimes you'll find him building compilers and robots.
Read more about Christopher Pitt