Last active
October 21, 2022 07:41
-
-
Save rhythnic/6521495650a215ccab8bf7120949fb7d to your computer and use it in GitHub Desktop.
Reusable Vuex Functions
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
// ******************************************************************* | |
// ATTENTION | |
// This gist is now an npm module | |
// The API of some functions is altered slightly. | |
// All future work will happen in the repo. | |
// | |
// https://gitlab.com/rhythnic/vuex-intern | |
// ******************************************************************* | |
// ******************************************************************* | |
// Helpers | |
// ******************************************************************* | |
const last = xs => xs[xs.length - 1] | |
// ******************************************************************* | |
// Getters | |
// ******************************************************************* | |
// Find an object in a list of objects by matching a property value. | |
// userById: findByKey('users', 'id') | |
// getters.userById('123') | |
export function findByKey (prop, targetKey) { | |
return state => val => state[prop].find(x => x[targetKey] === val) | |
} | |
// Filter a list of objects by matching a property value. | |
// usersByStatus: filterByKey('users', 'status') | |
// getters.usersByStatus('INACTIVE') | |
export function filterByKey (prop, targetKey) { | |
return state => vals => { | |
if (!Array.isArray(vals)) vals = [vals] | |
return state[prop].filter(x => vals.indexOf(x[targetKey]) > -1) | |
} | |
} | |
export function mapKeys (prop, targetKey) { | |
const filter = filterByKey(prop, targetKey) | |
return state => vals => filter(state)(vals) | |
.sort((a, b) => vals.indexOf(a[targetKey]) - vals.indexOf(b[targetKey])) | |
} | |
// ******************************************************************* | |
// Mutators | |
// ******************************************************************* | |
// Set property on state | |
// setUser: set('user') | |
// commit('setUser', { name: 'foo' }) | |
export const set = key => (state, val) => { state[key] = val } | |
// Set a value at a path within state | |
// Create objects and arrays as needed | |
// Path is an array, and array indicies are numbers (not string numbers) | |
// setUserName: setPath(['user', 'name']) | |
// commit('setUserName', 'foo') | |
export const setPath = path => (state, val) => { | |
const obj = path.slice(0, -1).reduce((acc, x, i) => { | |
if (!(x in acc)) acc[x] = typeof path[i + 1] === 'number' ? [] : {} | |
return acc[x] | |
}, state) | |
obj[last(path)] = val | |
} | |
// Toggle boolean in state | |
// toggleOpen: toggle('open') | |
// commit('toggleOpen') | |
export const toggle = key => state => { state[key] = !state[key] } | |
// For all key/value in propMap, set state[key] = data[propMap[value]] | |
export const pick = propMap => (state, data) => { | |
data = data || {} | |
Object.keys(propMap).forEach(x => { state[x] = data[propMap[x]] }) | |
} | |
// push an item onto a list | |
// addItem: pushTo('items') | |
export const pushTo = key => (state, val) => state[key].push(val) | |
// copy all key/values from data to state | |
// useful for resetting state to default values | |
// resetState: assignConstant(initialState) | |
// commit('resetState') | |
export const assignConstant = data => state => Object.assign(state, data) | |
// remove item from list | |
export const omitFromList = key => (state, item) => { | |
const index = state[key].indexOf(item) | |
if (index > -1) state[key].splice(index, 1) | |
} | |
// increment the index of a list argument or a list in state | |
export const incrementListIndex = (key, listOrListProp) => state => { | |
const list = Array.isArray(listOrListProp) ? listOrListProp : state[listOrListProp] | |
state[key] = (state[key] + 1) % list.length | |
} | |
// add or extend a record in a list | |
export const extendRecordInList = (key, idKey = 'id', valKey) => (state, data) => { | |
const id = data[idKey] | |
const val = valKey ? data[valKey] : data | |
const index = state[key].findIndex(x => x[idKey] === id) | |
return index < 0 | |
? state[key].push(val) | |
: state[key].splice(index, 1, Object.assign({}, state[key][index], val)) | |
} | |
// add or replace a record in a list | |
export const replaceRecordInList = (key, idKey = 'id', valKey) => (state, data) => { | |
const id = data[idKey] | |
const val = valKey ? data[valKey] : data | |
const index = state[key].findIndex(x => x[idKey] === id) | |
return index < 0 | |
? state[key].push(val) | |
: state[key].splice(index, 1, val) | |
} |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment