Skip to content
This repository has been archived by the owner on Dec 4, 2023. It is now read-only.

looks good #1

Open
alisman opened this issue Aug 16, 2016 · 2 comments
Open

looks good #1

alisman opened this issue Aug 16, 2016 · 2 comments

Comments

@alisman
Copy link

alisman commented Aug 16, 2016

I like what you're doing here. Seems a lot more lightweight than Redux-Elm. I have some ideas that you or may not have already have thought of. As you've recognized, a component should have local reducers that allow it to act on its own data model when that model is nested somewhere in a global redux store. Those reducers can be packaged/published/distributed with the component, making it truly modular. But in a specific implementation, the global reducers may also want a chance at handling the the components dispatches, before or after the local reducers have run. Can the reducers be nested? Perhaps the action dispatched could have the local reducers bound to it. The global reducers could then actually execute the local reducers and then operate on the state object after the the local reducers have done their work but before the store's change event fires. Does this make sense?

Another hazy idea I have is that components should implement redux internally. It's not so far from how state already works except for the introduction of action intermediation. If this was true, then that local redux implementation would be executed against a global store when the component was used in a project with a global redux implementaton.

@HansDP
Copy link
Owner

HansDP commented Aug 16, 2016

Hey

Thanks for having a look!
At the moment, I'm occupied with another project, so not a lot is going on right now in this repository. However, some updates are coming up

I personally do not believe that global reducers should listen explicitly to local dispatches. That breaks the purpose of being truly local. I do recognise the need to dispatch something global from within the component. In my opinion, there are a few options to do that.

  1. The container should not dispatch a global action, but should support a handler so the parent can be notified. This explicitly separates internal workings of the container.
class MyContainer extends React.Component {
  ...
  onDoSomething() {
    this.props.dispatch({ type: 'MY_LOCAL_ACTION'});
    if (this.props.onSomething) {
      this.props.onSomething()
    }
  }
}
  1. Your project can define some global actions. In your container, you let your local action happening, and after that local process is completed, you dispatch another action, informing the application about this global thing. That is why the dispatch method passed into your container has a reference to the global dispatch as well (this.props.dispatch.global(...))
class MyContainer extends React.Component {
  ...
  onDoSomething() {
    this.props.dispatch({ type: 'MY_LOCAL_ACTION'});
    this.props.dispatch.global({ type: 'MY_GLOBAL_ACTION'});
  }
}

Both of those solutions have the disadvantage of dispatching 2 actions in redux, but in my opinion, the advantage of separating the internals of your container is more important here (it allows you to modify the local implementation later on without breaking any app-specific requirements)

Does this make any sense? :)

About the question whether reducers can be nested? What do you exactly mean? The package supports child-reducers (based on the existence of child-containers). However, the parent container itself should not be aware of this (in my opinion). Child components/containers should be black-boxes to parents, they just have a public api (the props). This makes it possible to, later on in the project, refactor your components/containers without breaking the parents that use them.

And about the hazy idea. Well, that is something I have been playing with as well. It could be logical to deal with local state within another 'instance' of redux. However, that breaks a lot of current tooling (like time-travel, dev-tools, ...)

For what its worth, I will try to update the documentation as soon as possible, because some concepts have changed a bit. But the basics are still the same

@alisman
Copy link
Author

alisman commented Aug 16, 2016

I guess I see your point that global listeners fielding local actions means that the local actions are now effectively an external interface. Changing them will inadvertantly break external code. On the other hand, dispatches are not really different than emitted events, and plugin components have long offered events as part of external apis. Would you agree?

On the "hazy idea" what I meant is that components could either target a local store or a global one. So, if you're developing a component that will be published publically, you don't have to assume a global redux store in the consuming application. You code your component with a local store. But if and when the component is instantiated with a global store available, it can then run off that store (using your local targetting mechanism of course!). Basically the interface is the same whether global or local. This way time-travel etc. still works.

Sign up for free to subscribe to this conversation on GitHub. Already have an account? Sign in.
Labels
None yet
Projects
None yet
Development

No branches or pull requests

2 participants