vuejs/vuex · error · Error
Missing module "${moduleName}" for path "${path}".
Error message
Missing module "${moduleName}" for path "${path}". What it means
Vuex devtools integration walks a module path (e.g. 'root/cart/items') through the module tree via _children. If any segment of the path does not exist in the module map, getStoreModule throws. This means the devtools asked for a module path that no longer matches the registered module hierarchy.
Source
Thrown at src/plugins/devtool.js:276
}
}
target = target[p]._custom.value
})
target[leafKey] = canThrow(() => getters[key])
} else {
result[key] = canThrow(() => getters[key])
}
})
return result
}
function getStoreModule (moduleMap, path) {
const names = path.split('/').filter((n) => n)
return names.reduce(
(module, moduleName, i) => {
const child = module[moduleName]
if (!child) {
throw new Error(`Missing module "${moduleName}" for path "${path}".`)
}
return i === names.length - 1 ? child : child._children
},
path === 'root' ? moduleMap : moduleMap.root._children
)
}
function canThrow (cb) {
try {
return cb()
} catch (e) {
return e
}
}
View on GitHub (pinned to bd907467b8)
Solutions
- Verify the module path segments actually match registered module names exactly (case-sensitive)
- Register the missing module with registerModule before the devtools flush
- Re-create the store or reload devtools so stale paths from HMR are cleared
- Check that the path is prefixed with 'root' as getStoreModule expects
Example fix
// before
store.registerModule('cart', cartModule) // devtools path says 'root/basket'
// after
store.registerModule('basket', basketModule) // names now match devtools path 'root/basket' Defensive patterns
Strategy: try-catch
Validate before calling
function modulePathExists(store, path) {
return path.split('/').filter(Boolean).slice(1).every(seg => {
let m = store._modules root check; return typeof store.hasModule === 'function' ? store.hasModule(path.split('/').filter(Boolean).slice(1)) : false
})
}
// simpler: verify registration before devtools read:
// path.split('/').filter(n => n).slice(1).every(seg => registeredNames.includes(seg)) Type guard
function hasModulePath(store, path) {
const names = path.split('/').filter(n => n)
if (names[0] !== 'root') return false
return names.slice(1).length === 0 ? true : store.hasModule(names.slice(1))
} Try / catch
try {
const mod = getStoreModule(moduleMap, path)
} catch (e) {
if (/Missing module/.test(e.message)) { console.warn('stale devtools path, re-registering', path) /* re-register or resubscribe */ }
else throw e
} Prevention
- Keep devtools module paths derived from the same source of truth as registerModule calls
- Re-init devtools subscription after unregisterModule or HMR updates
- Always prefix devtool paths with 'root'
- Avoid renaming modules without updating devtool plugin config
When it happens
Trigger: Calling addDevtools (store creation with devtool enabled) with a devtools event path referencing a module name not present under root._children; e.g. path 'root/user/profile' when module 'profile' was never registered or was unregistered.
Common situations: Hot module replacement removed/renamed a module while devtools holds a stale path; typo in module name in devtools plugin config; unregisterModule called before devtools re-reads state; async module registration ordering during store init.
Related errors
- [vuex] state field "${moduleName}" was overridden by a modul
- [vuex] trying to unregister module '${key}', which is not re
- [vuex] trying to add a new module '${key}' on hot reloading,
- [vuex] mutation type: ${type}. Silent option has been remove
- [vuex] ${msg}
AI-assisted analysis of vuejs/vuex@bd907467b8 (2026-08-28).
Data as JSON: /api/errors/7c2ebee732c6db37.
Report an issue: GitHub.