Where communities thrive


  • Join over 1.5M+ people
  • Join over 100K+ communities
  • Free without limits
  • Create your own community
People
Repo info
Activity
GavinRay97
@GavinRay97
or something built in to HTML5
Josh Duff
@TehShrike
with others, you call dispatch actions with objects representing the state change
well, I like to use a global event bus a lot of the time https://github.com/TehShrike/mannish
but usually if you're hooking up to a state library you want the components to interact with it directly
GavinRay97
@GavinRay97

For example:
store.js

import {fetchJSON, mutateArray} from './utils';
export default {
  fetchJSON: fetchJSON,
  mutateArray: mutateArray,
  syntaxHighlight: syntaxHighlight,
    todoStore:{
      todos: ['Example 1', 'Example 2', 'Example 3'],
      users: [],
    },
}

utils.js

const fetchJSON = async(url) => { return ( await fetch(url).then(r => r.json() ) )}
const mutateArray = async(storeVar, array) => { return array.map(item => storeVar.push(item)) }
export { fetchJSON, mutateArray}

Todo.vue

<template>
  <div>
    <h1 id="title">Global Store State</h1>
    <pre id="highlight-code" v-html="formattedStore" />
    <div id="list-container">
    <div class='list animated tada'>
      <h1>
        To-do List
      </h1>
      <ul v-if="todoStore.todos && todoStore.todos.length">
        <li v-for="(todo, index) in todoStore.todos" @click="emitEvent('removeTodo', index)">
          <a href='#'>
            <i class='icon ion-android-done'></i>
          </a>
          {{todo}}
        </li>
      </ul>
     </div>
     <div class="webflow-style-input">
         <input  placeholder="Add todo's here" v-model="todoInput"></input>
         <button @click="emitEvent('addTodo')"><i class="icon ion-android-arrow-forward"></i></button>
       </div>
   </div>
  </div>
</template>

<script>
import todoController from '../store/controllers/todoController';
export default {
  name: 'Todo',
  store: ['todoStore'],
  events: todoController.events,
  methods: todoController.methods,
  computed: {
    formattedStore() {
      return this.$store.syntaxHighlight(JSON.stringify(this.$store, undefined, 4));
    }
  },
  created() {
    this.fetchUsers();
  }
}
</script>

todoController.js

export default {
  events: {
    addTodo: function() {
      this.todoStore.todos.push(this.todoInput)
      this.todoInput = ''
    },
    removeTodo: function(index) {
      this.todoStore.todos.splice(index, 1)
    },
    setUsers: function(userList) {
      this.$store.mutateArray(this.todoStore.users, userList);
    }
  },
 methods: {
    emitEvent: function(eventName, payload) {
      this.$events.emit(eventName, payload)
    },
    fetchUsers: async function() {
      this.emitEvent('setUsers', await this.$store.fetchJSON('http://jsonplaceholder.typicode.com/users'))
    }
  }
}
todoapp1.png
todoapp3.PNG
There is no generic Global Event Bus implementation I could subscribe to via any framework?
I'm just trying to figure out conceptually if the concept of an agnostic global state management library is feasible.
Josh Duff
@TehShrike
well, most things that claim the name "framework" will bring their own
GavinRay97
@GavinRay97
Sorry if this is a lot.
Josh Duff
@TehShrike
I like to keep global state separate from my view implementation as much as is practical, which is why I usually use that mediator to separate the view and my global state
Does Mannish meet your idea of a global event bus?
GavinRay97
@GavinRay97
Yeah but Redux is overly-verbose and difficult for beginners to learn, MobX is awesome with injected decorators for an observer/observable pattern but needs a binding package for every framework, and Kea.js is alrightish but still is React-centric. Also MobX is React-centric.
Let me look at that Mannish repo really quick, thank you.
Okay so, again I apologize as I'm not nearly as seasoned as you @TehShrike
Theoretically, you could use Mannish within your UI framework, and provide it functions/data for context?
Josh Duff
@TehShrike
if your component has a mediator instance it can access, it can do stuff like mediator.call('http', { type: 'GET', url: 'google.com' }) or mediator.call('dispatch', ADD_TODO_ACTION, { name: 'gotta keep on keepin on' })
and you can put whatever XHR/state library you want on the other side of that to handle those actions
GavinRay97
@GavinRay97
Ohhhhh
Yeah, that makes sense.
Still left with the problem of a state-management library that's framework agnostic though.
Which seems like it's not possible?
Due to binding
Josh Duff
@TehShrike
well, first step - and I have no idea how possible this is - come up with your ideal way for components/templates to communicate with a state management library
GavinRay97
@GavinRay97
An agnostic global event bus and pub-sub implementation
Josh Duff
@TehShrike
then, figure out how you could translate between that API, and a Mobx/Redux/whatever backend
GavinRay97
@GavinRay97
seems the best route
Hmmm
GavinRay97
@GavinRay97
@TehShrike Thanks for taking the time to answer by the way, super appreciate it.
I'd love to make a framework agnostic state-management library using a generic global event bus but I don't know how feasible it is. And even if I sunk the time and effort into it, there are bindings for most state-management libraries available already written for use.
Would seem like most people would probably want to use something that already exists and import extra packages for binding/reactivity than use an agnostic state management and event bus system.
Would you mind if I asked your opinion on something? @TehShrike
Josh Duff
@TehShrike
fire away :-)
GavinRay97
@GavinRay97
I just had a three hour long discussion with a really knowledgeable dev friend of mine on Discord, he's friends with one of the core Redux team and talk with him on Discord often.
Basically we discussed what we thought the idea of optimum state-management system and implementation would look like.
If you're into it at all, I'm really curious to hear your take.
Josh Duff
@TehShrike
Sure thing
GavinRay97
@GavinRay97

I personally think that barebones stores, with util functions and watched/computed properties with an observer/observable pattern to eliminate the need for component state, while also providing the flexibility to do things like declare classes/models with optional and required proptypes and possibly methods in-model is an ideal solution.

Something along the lines of a stripped-down MobX with optional and flexible structure implementation based on app scale/needs.

State management and design patterns around their use are super interesting to me and I love getting wiser folk's views.
Josh Duff
@TehShrike
Another thing I've been thinking about - people really like global stores, for some reason. I usually have very little global state, and leave most state isolated by ui state/component
GavinRay97
@GavinRay97
Yeah, it's app dependent for me.
Small app, probably one store called "appState"
Larger app, multiple stores with respective names.
Josh Duff
@TehShrike
For smaller apps, using component state and no global store usually gets the job done for me
GavinRay97
@GavinRay97
Also very true.
Josh Duff
@TehShrike
I usually only introduce global state if, say, the user is building up a single document as they navigate around from screen to screen
GavinRay97
@GavinRay97
I don't tend to write a store for very small apps, I guess by small app I should've clarified "small by enterprise standards" :joy:
We seem to have pretty in-line views then.
What would the ideal system of app state and the way that components handle binding (i.e. having to declare a state and re-render when state vars are changed versus observing variables in a store and intelligently re-rendering if they change) look to you?