Skip to content

Commit

Permalink
Support multiple stores (#1)
Browse files Browse the repository at this point in the history
* Multiple stores init

* Restore formatting

* Restore formatting (again)

* Remove package-lock.json

* Revert mutation

* Commit mutation
  • Loading branch information
ramadimasatria authored and ferrwan committed Jan 18, 2021
1 parent 6f7dc1e commit def98f4
Show file tree
Hide file tree
Showing 12 changed files with 237 additions and 48 deletions.
1 change: 1 addition & 0 deletions shells/dev/target.html
Original file line number Diff line number Diff line change
Expand Up @@ -6,6 +6,7 @@
</head>
<body>
<div id="app"></div>
<div id="secondApp"></div>
<div id="shadow"></div>
<script src="build/hook.js"></script>
<script src="build/target.js"></script>
Expand Down
20 changes: 20 additions & 0 deletions shells/dev/target/Random.vue
Original file line number Diff line number Diff line change
@@ -0,0 +1,20 @@
<template lang="html">
<div>
Random number: {{ random }}
<br>
<button @click="randomize">Randomize</button>
</div>
</template>

<script>
import { mapState, mapActions } from 'vuex';
export default {
computed: {
...mapState(['random'])
},
methods: {
...mapActions(['randomize'])
}
}
</script>
13 changes: 13 additions & 0 deletions shells/dev/target/index.js
Original file line number Diff line number Diff line change
@@ -1,12 +1,14 @@
import Vue from 'vue'
import store from './store'
import store1 from './store1'
import Target from './Target.vue'
import Other from './Other.vue'
import Counter from './Counter.vue'
import NativeTypes from './NativeTypes.vue'
import Events from './Events.vue'
import MyClass from './MyClass.js'
import Router from './Router.vue'
import Random from './Random.vue'
import router from './router'

window.VUE_DEVTOOLS_CONFIG = {
Expand Down Expand Up @@ -42,6 +44,17 @@ new Vue({
}
}).$mount('#app')

// another vue app with store
new Vue({
store: store1,
render (h) {
return h('div', null, [
h('h2', 'Second app with store!'),
h(Random)
])
}
}).$mount('#secondApp')

// custom element instance
const ce = document.querySelector('#shadow')
if (ce.attachShadow) {
Expand Down
22 changes: 22 additions & 0 deletions shells/dev/target/store1.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,22 @@
import Vue from 'vue'
import Vuex from 'vuex'

Vue.use(Vuex)

export default new Vuex.Store({
state: {
name: 'store1',
random: 0
},
mutations: {
UPDATE_RANDOM(state, val) {
state.random = val
}
},
actions: {
randomize({ commit }) {
const random = Math.random()
commit('UPDATE_RANDOM', random)
}
}
})
5 changes: 4 additions & 1 deletion src/backend/hook.js
Original file line number Diff line number Diff line change
Expand Up @@ -17,6 +17,8 @@ export function installHook (window) {
const hook = {
Vue: null,

stores: [],

on (event, fn) {
event = '$' + event
;(listeners[event] || (listeners[event] = [])).push(fn)
Expand Down Expand Up @@ -76,8 +78,9 @@ export function installHook (window) {
}
})

hook.once('vuex:init', store => {
hook.on('vuex:init', store => {
hook.store = store
hook.stores.push(store)
})

Object.defineProperty(window, '__VUE_DEVTOOLS_GLOBAL_HOOK__', {
Expand Down
2 changes: 1 addition & 1 deletion src/backend/index.js
Original file line number Diff line number Diff line change
Expand Up @@ -112,7 +112,7 @@ function connect () {
if (hook.store) {
initVuexBackend(hook, bridge)
} else {
hook.once('vuex:init', store => {
hook.on('vuex:init', store => {
initVuexBackend(hook, bridge)
})
}
Expand Down
41 changes: 31 additions & 10 deletions src/backend/vuex.js
Original file line number Diff line number Diff line change
@@ -1,35 +1,56 @@
import { stringify, parse } from 'src/util'

export function initVuexBackend (hook, bridge) {
const store = hook.store
const stores = hook.stores

let recording = true

const getSnapshot = () => stringify({
state: store.state,
getters: store.getters || {}
})
const getSnapshot = (store) =>
stringify({
state: store.state,
getters: store.getters || {}
})

bridge.send('vuex:init', getSnapshot())
const getSnapshots = () =>
stores.map(store => getSnapshot(store))

const getStoreIndex = (state) => {
let storeIndex
stores.forEach((store, idx) => {
if (stringify(state) === stringify(store.state)) {
storeIndex = idx
}
})
return storeIndex
}

bridge.send('vuex:init', getSnapshots())

// deal with multiple backend injections
hook.off('vuex:mutation')

// application -> devtool
hook.on('vuex:mutation', mutation => {
hook.on('vuex:mutation', (mutation, state) => {
if (!recording) return

const storeIndex = getStoreIndex(state)

bridge.send('vuex:mutation', {
mutation: {
type: mutation.type,
payload: stringify(mutation.payload)
},
timestamp: Date.now(),
snapshot: getSnapshot()
snapshot: getSnapshot(stores[storeIndex]),
storeIndex
})
})

// devtool -> application
bridge.on('vuex:travel-to-state', state => {
hook.emit('vuex:travel-to-state', parse(state, true))
bridge.on('vuex:travel-to-state', ({ storeIndex, state }) => {
const store = hook.stores[storeIndex]
store.replaceState(parse(state, true))
// hook.emit('vuex:travel-to-state', parse(state, true))
})

bridge.on('vuex:import-state', state => {
Expand Down
14 changes: 12 additions & 2 deletions src/devtools/views/vuex/VuexHistory.vue
Original file line number Diff line number Diff line change
Expand Up @@ -53,7 +53,7 @@
>
<div
ref="baseEntry"
:class="{ active: activeIndex === -1, inspected: inspectedIndex === -1 }"
:class="{ active: activeIndex[inspectedStoreIndex] === -1, inspected: inspectedIndex === -1 }"
class="entry list-item"
@click="inspect(null)"
>
Expand Down Expand Up @@ -206,6 +206,11 @@ export default {
EntryList
],
components: {
ActionHeader,
ScrollPane
},
computed: {
...mapState('vuex', [
'enabled',
Expand All @@ -215,8 +220,13 @@ export default {
'activeIndex',
'filterRegex',
'filterRegexInvalid'
'inspectedStoreIndex',
]),
...mapState('vuex', {
history: state => state.history[state.inspectedStoreIndex],
}),
...mapGetters('vuex', [
'filteredHistory'
]),
Expand Down Expand Up @@ -245,7 +255,7 @@ export default {
]),
isActive (entry) {
return this.activeIndex === this.filteredHistory.indexOf(entry)
return this.activeIndex[this.inspectedStoreIndex] === this.filteredHistory.indexOf(entry)
},
isInspected (entry) {
Expand Down
47 changes: 47 additions & 0 deletions src/devtools/views/vuex/VuexStoreSelector.vue
Original file line number Diff line number Diff line change
@@ -0,0 +1,47 @@
<template lang="html">
<div class="container">
<span class="label">Store: </span>
<select class="selector" v-model="selected">
<option :value="$idx - 1" v-for="$idx in storeCount">Store {{ $idx }}</option>
</select>
</div>
</template>

<script>
import { mapGetters, mapActions } from 'vuex';
export default {
computed: {
...mapGetters('vuex', [
'storeCount'
]),
selected: {
get() {
return this.$store.state.vuex.inspectedStoreIndex
},
set(index) {
this.$store.dispatch('vuex/changeStore', index)
}
}
},
methods: {
...mapActions('vuex', [
'changeStore'
])
}
}
</script>

<style lang="stylus" scoped>
.container
height: 50px
padding: 15px
border-bottom: 1px solid #ddd
.label
display: inline-block
color: #999
font-weight: 100
margin-right: 8px
font-size: 12px
</style>
11 changes: 8 additions & 3 deletions src/devtools/views/vuex/VuexTab.vue
Original file line number Diff line number Diff line change
@@ -1,8 +1,11 @@
<template>
<div>
<split-pane v-if="hasVuex">
<vuex-history slot="left" />
<vuex-state-inspector slot="right" />
<div slot="left">
<vuex-store-selector />
<vuex-history slot="left" />
</div>
<vuex-state-inspector slot="right"></vuex-state-inspector>
</split-pane>
<div
v-else
Expand All @@ -19,13 +22,15 @@
import SplitPane from 'components/SplitPane.vue'
import VuexHistory from './VuexHistory.vue'
import VuexStateInspector from './VuexStateInspector.vue'
import VuexStoreSelector from './VuexStoreSelector.vue';
import { mapState } from 'vuex'
export default {
components: {
SplitPane,
VuexHistory,
VuexStateInspector
VuexStateInspector,
VuexStoreSelector
},
computed: mapState('vuex', {
Expand Down
39 changes: 27 additions & 12 deletions src/devtools/views/vuex/actions.js
Original file line number Diff line number Diff line change
@@ -1,46 +1,52 @@
import { parse, stringify } from 'src/util'

export function commitAll ({ commit, state }) {
if (state.history.length > 0) {
const history = state.history[state.inspectedStoreIndex]
if (history.length > 0) {
commit('COMMIT_ALL')
travelTo(state, commit, -1)
}
}

export function revertAll ({ commit, state }) {
if (state.history.length > 0) {
const history = state.history[state.inspectedStoreIndex]
if (history.length > 0) {
commit('REVERT_ALL')
travelTo(state, commit, -1)
}
}

export function commit ({ commit, state }, entry) {
const index = state.history.indexOf(entry)
const history = state.history[state.inspectedStoreIndex]
const index = history.indexOf(entry)
if (index > -1) {
commit('COMMIT', index)
travelTo(state, commit, -1)
}
}

export function revert ({ commit, state }, entry) {
const index = state.history.indexOf(entry)
const history = state.history[state.inspectedStoreIndex]
const index = history.indexOf(entry)
if (index > -1) {
commit('REVERT', index)
travelTo(state, commit, state.history.length - 1)
travelTo(state, commit, state.history[state.inspectedStoreIndex].length - 1)
}
}

export function inspect ({ commit, getters }, entryOrIndex) {
export function inspect ({ commit, getters, state }, entryOrIndex) {
const history = getters.filteredHistory[state.inspectedStoreIndex]
let index = typeof entryOrIndex === 'number'
? entryOrIndex
: getters.filteredHistory.indexOf(entryOrIndex)
: history.indexOf(entryOrIndex)
if (index < -1) index = -1
if (index >= getters.filteredHistory.length) index = getters.filteredHistory.length - 1
if (index >= history.length) index = history.length - 1
commit('INSPECT', index)
}

export function timeTravelTo ({ state, commit }, entry) {
travelTo(state, commit, state.history.indexOf(entry))
const history = state.history[state.inspectedStoreIndex]
travelTo(state, commit, history.indexOf(entry))
}

export function toggleRecording ({ state, commit }) {
Expand All @@ -52,11 +58,20 @@ export function updateFilter ({ commit }, filter) {
commit('UPDATE_FILTER', filter)
}

export function changeStore ({ commit }, index) {
commit('CHANGE_STORE', index)
}

function travelTo (state, commit, index) {
const { history, base, inspectedIndex } = state
const targetSnapshot = index > -1 ? history[index].snapshot : base
const { history, base, inspectedIndex, inspectedStoreIndex } = state
const storeHistory = history[inspectedStoreIndex]
const targetSnapshot = index > -1 ? storeHistory[index].snapshot : base[inspectedStoreIndex]

bridge.send('vuex:travel-to-state', {
storeIndex: inspectedStoreIndex,
state: stringify(parse(targetSnapshot).state)
})

bridge.send('vuex:travel-to-state', stringify(parse(targetSnapshot).state))
if (index !== inspectedIndex) {
commit('INSPECT', index)
}
Expand Down
Loading

0 comments on commit def98f4

Please sign in to comment.