Troubleshooting
Common setup and development issues and how to resolve them.
Setup
pnpm install fails or npm/yarn is rejected
The repo enforces pnpm via a preinstall script. Using npm install or yarn install will fail on purpose.
- Install pnpm:
npm install -g pnpm(or see pnpm.io) - Verify Node version is 18+:
node --version - Run
pnpm installfrom the repo root
Aftman tools not found after install
If rojo, selene, stylua, or luau-lsp aren't available after running aftman install:
- Ensure aftman's bin directory is on your
PATH. See aftman's README for platform-specific setup. - Re-run
aftman installfrom the repo root — it readsaftman.tomlfor tool versions. - On first install, you may need to restart your shell for
PATHchanges to take effect.
Luau-LSP not working in VS Code
Nevermore uses a forked luau-lsp. The standard extension works, but you must point it at the custom binary:
- Run
aftman installto get the fork - In VS Code settings, set
luau-lsp.server.pathto your aftman-installed binary (seedocs/ides/vscode.md) - Restart VS Code after changing the setting
Linting
lint:luau errors about missing sourcemap
The luau type checker needs a sourcemap to resolve module paths. npm run lint:luau auto-runs build:sourcemap via its prelint:luau script, so this usually "just works". If it fails:
- Run
npm run build:sourcemapmanually and check for errors - Ensure Rojo is installed via aftman (the sourcemap is built with Rojo)
Linting hangs or uses excessive memory
Linters traverse symlinks infinitely if run repo-wide. They must run per-package via npx lerna exec --parallel. The npm run lint:* scripts in the root package.json handle this — don't run selene, moonwave-extractor, or similar tools directly at the repo root.
Testing
Cloud tests fail with authentication errors
nevermore test --cloud needs a Roblox Open Cloud API key. Credential resolution order:
--api-keyCLI flagROBLOX_OPEN_CLOUD_API_KEYenvironment variable.envfile in the package directory
See docs/testing/testing.md for full credential documentation.
Tests pass locally but fail in CI
- CI uses the same
nevermore test --cloudpath. Check thatdeploy.nevermore.jsonhas the correctuniverseIdandplaceId. - Look at the CI job summary for sourcemap-resolved failure annotations.
- The
--script-textflag can help debug:nevermore test --cloud --script-text 'print(workspace:GetChildren())'
Cloud test times out with zero output
Test timed out after 120s with no jest output at all means the place run never completed — and
output is only relayed when the run completes, so any prints the run made are lost. Debug
instrumentation that still times out tells you nothing. Two distinct causes to rule out:
- The engine itself crashed. The cloud runner reports a crash only as a timeout. Run the same
test locally in Studio (
nevermore testwithout--cloud) — if Studio hard-crashes, check%LOCALAPPDATA%\Roblox\logs\*.logfor anRBXCRASHline naming the assertion (e.g.RBXCRASH: WorldModel removed from wrong workspacefrom Lua mutating a ViewportFrame's WorldModel contents while an ancestorDestroy()cascade is tearing it down — destroy client-realm bags before destroying the mock/server bag that owns the mounted UI). - An unyielding loop or infinite yield. If Studio doesn't crash but hangs, it's Lua. To get
data out of the cloud despite the output limitation, make the run complete: run the suspect
step detached (
task.spawn) so the test body returns, and have a later test in the same suite sample and print the detached thread'scoroutine.status/debug.traceback.
Test fails with loader is not a valid member of ModuleScript "..."
The standard file header require(script.Parent.loader).load(script) deliberately does not
resolve under a ModuleScript: loader links are never injected inside ModuleScripts, so libraries
that use sub-modules don't accidentally intercept a loader. A spec (or any file) placed inside
an init.lua-style ModuleScript folder therefore has no loader to find — the require throws at
runtime and Jest reports the whole suite as failed with 0 tests run.
Fix: move the file up so it sits directly under the realm folder, and require the module under test
by name (require("MyModule")) instead of require(script.Parent).
Rojo
Rojo build errors or missing modules
Nevermore uses a custom Rojo fork that understands symlinks (installed via aftman). Standard Rojo won't resolve the monorepo's symlinked node_modules correctly.
- Verify you're using the forked version: check
aftman.tomlfor the Rojo entry - If modules are missing, run
pnpm installfirst — Rojo resolves paths through npm's dependency tree