0.2.1 • Published 7 years ago

react-copycat v0.2.1

Weekly downloads
-
License
MIT
Repository
github
Last release
7 years ago

react-copycat

Vitals

Travis (.com) branch npm npm bundle size (minified) GitHub

Other Stats

npm

What is it?

react-copycat is a declarative state-sharing add-on library for usage with React with minimal boilerplate. It allows you to declare what a component 'publishes', and what 'subscriptions' a component holds, if any.

Who is this for?

In short, this is for anyone who needs to manage/share state between components and wants to do so with no boilerplate and in a declarative manner. In particular, projects not already using another state-management/sharing library, or projects which feel their state-management library is too tedious and/or complex may find react-copycat attractive.

This is not meant to replace something like Redux, in apps where its features are deemed necessary. react-copycat can be seen as filling a gap somewhere between apps not currently managing global state and apps using something like Redux or Flux.

What do you get?

Selective State Visibility

Only the state attributes a publisher exposes will be accessible to subscribers and subscribers only get read-access to a copy from the Observer. This can decrease the likelihood of an unpleasant suprise.

Declarative state-sharing and propagation

A subscriber has any state components it subscribes to (provided the publisher exposes it), injected into its properties. Any time a publisher changes its state, any published values are updated in the Observer state and re-injected to subscriber properties.

Scoped Observers

The Observer component is not implemented as a singleton. The Observer component can be nested in other observers and/or does not need to wrap the whole app, although this is a common use-case. In practice, this means you can separate groups of composed components into different Observers, allowing scoped state-sharing without worrying about polluting the global state namespace. In other words, the state is only as global as you choose to make it.

What don't you get?

Boilerplate

Actions

Reducers

A Time-Travelling Debugger

Note: If these features are necessary, they can still be used with react-copycat, as it makes no assumptions about what is causing a publisher to update its state. That being said, these features are not included nor required for general use.

Getting Started

Installation

With yarn

yarn add react-copycat

With npm

npm install --save react-copycat

Usage

// App.js
import React, { Component } from 'react';
import PublishingComponent from './PublishingComponent';
import SubscribingComponent from './SubscribingComponent';
import { Observer } from 'react-copycat';

class App extends Component {
    constructor(props) {
        super(props) {
            // Anything else.
        }
    }

    render() {
        return (
            <Observer>
              <PublishingComponent 
                publish={{
                    id: 'myUniquePublishingComponent',
                    state: [
                        'publicState'
                    ]
                }}
              />
              <SubscribingComponent 
                subscribe={[{
                    // Array of subscriptions.
                    id: 'myUniquePublishingComponent',
                    props: {
                        // Injected prop name | Exposed name
                        sharedPublic:           'publicState'
                        sharedPrivate:          'privateState' // Undefined
                    }
                }]}
              />
              // Another component of the same type that doesn't subscribe.
              <SubscribingComponent 
                sharedPublic="Didn't subscribe" 
                sharedPrivate="Didn't subscribe"
              />
            </Observer>
        );
    }
};

export default App;

// PublishingComponent.js
import React from 'react';
import { Observable } from 'react-copycat';

export default class extends Observable {
    constructor(props) {
        super(props);
        this.state = {
            publicState: 'Open to subscriptions!',
            privateState: 'Secret!'
        }
    }

    render() {
        return (
            <div>
              <div>Public State: {this.state.publicState}</div>
              <div>Private State: {this.state.privateState}</div>
            </div>
        );
    }
};

// SubscribingComponent.js
import React, { Component } from 'react';

export default class extends Component {
    constructor(props) {
        super(props);
    }

    render() {
        return (
            <div>
              <div>Public Published state from Publisher: {this.props.sharedPublic}</div>
              <div>Private State from Publisher: {this.props.sharedPrivate || 'Cannot retrieve'}</div>
            </div>
        );
    }
};

How does it Work?

The package exports two classes, Observer and Observable. Observer is a wrapper component that can be accessed by any of its children. Children publish by registering the state they wish to expose to the Observer. Components which do this are known as Publishing Components, and they extend the Observable class (which extends React.Component). Any component can subscribe to a Publishing component, and components which do so are known as Subscribing components. Subscribing components do not need to extend Observable (and can extend React.Component instead) unless they are also a Publishing component. The decision of what to publish or subscribe to is done declaratively through properties

Note: Programmatic control will likely be added in a future version, allowing things like e.g. pausing and resuming subscriptions.

Under the hood, the Observer stores a copy of published state in its own state, and classes extending Observable update the values as a callback to their setState(updater, callback) method, which is also a passthrough to React's setState(updater, callback). Any Subscribing components will have access to the requested state (if the publisher exposes it) through property injection.

That's about it so far.

0.2.2

7 years ago

0.2.1

7 years ago

0.2.0

7 years ago

0.1.12

7 years ago

0.1.11

7 years ago

0.1.10

7 years ago

0.1.9

7 years ago

0.1.8

7 years ago

0.1.7

7 years ago

0.1.6

7 years ago

0.1.5

7 years ago

0.1.4

7 years ago

0.1.3

7 years ago

0.1.2

7 years ago

0.1.1

7 years ago

0.1.0

7 years ago