GemDB Code normally installs and runs its own database. On a hosted or shared
machine an administrator does that instead — installing the engine, running the
stone and NetLDI as services, and giving each developer an ordinary database
account — and GemDB Code only connects. Setting
gemdb.externalDatabase.gemstone switches it to that mode.
Against an external database, GemDB Code:
- does stage its bundled Grail under
gemdb.rootPathand file it into the configured account, open sessions as that account, write thegemdbcommand, and run the MCP server ifgemdb.mcp.enabledis on; - does not download an engine, create a database, check or ask to raise shared memory, start or stop the stone or NetLDI, or remove anything. Start, Stop and Remove are hidden, and a database that is down is reported rather than started.
Refusing to start the stone is the point rather than a convenience. The administrator's stone runs as its own operating-system account. A stone started by GemDB on the same extent would run as the developer, and GemStone allows passwordless logins — as any user, SystemUser included — to linked sessions running as the stone's account.
All "scope": "machine", so a repository's .vscode/settings.json cannot set
them. In a remote window (code-server, SSH) they are read on the machine the
database is on.
| Setting | Default | |
|---|---|---|
gemdb.externalDatabase.gemstone |
(empty: off) | The engine's product directory (GEMSTONE) |
gemdb.externalDatabase.globalDirectory |
/opt/gemstone |
GEMSTONE_GLOBAL_DIR, which holds locks/ |
gemdb.externalDatabase.stone |
gs64stone |
The stone's name |
gemdb.externalDatabase.netldi |
gs64ldi |
The NetLDI's name |
gemdb.externalDatabase.user |
DataCurator |
The account GemDB Code logs in as |
gemdb.externalDatabase.passwordFile |
(empty: stock password) | A file whose first line is that account's password |
The password is read from a file on every login rather than stored in a
setting, so it never appears in settings.json, and a password changed on the
server is picked up without touching the editor. Make it readable by the
developer's account only (chmod 600).
Changing any of the others while the editor is open moves GemDB Code to the
database they now name: every notebook's session is logged out, the MCP server
is stopped, and the gemdb command is rewritten. The MCP server is stopped by
signalling its gem rather than with System stopSession:, because the session
id GemDB Code recorded belongs to the previous database. Changing only
passwordFile logs nobody out, since it changes the next login rather than
any session already open, but it does rewrite the gemdb command, which
carries the password.
The engine version is read from the product's version.txt, because it names
the GCI library GemDB Code loads.
-
An engine GemDB Code can use: Grail needs a 4.0 of 2026-07-29 or later.
-
A running stone and NetLDI with the configured names. The NetLDI must run in guest mode (
startnetldi -g -a <developer>) as the developer's operating-system account, so sessions need no host password. -
Python's environment on the NetLDI. Sessions inherit the NetLDI's environment, and Grail finds itself through it, so start the NetLDI with these set to the developer's GemDB Code root path (
~/GemDBby default):GRAIL_DIR=/home/<developer>/GemDB/grail PYTHON_PACKAGE_PATH=/home/<developer>/GemDB/grail/src/python SHIM_LIB_PATH=/home/<developer>/GemDB/grail/src/c/shim/libcpython_ua.so
-
Grail's shared base, installed once. Its
install_base.shsets the database's Unicode comparison mode and a marker in Globals, both of which need SystemUser; GemDB Code's installer runs it only if the marker is missing, and logs in as SystemUser with the stock password to do it. Run it as SystemUser before handing the database over, at the Grail commit GemDB Code bundles (PINNED_GRAIL_REFinvendor-pins.sh). -
An account for the developer — the same shape as the
gemdbaccount GemDB Code creates on a database of its own (src/account.ts) — with theCodeModificationprivilege, which is what defining classes and methods needs, and with which Grail installs. Withgemdb.mcp.enabledit also needsCreateOnetimePassword: the MCP server runs in a gem of its own, which logs in as the developer with a one-time password. That privilege covers only the account's own logins; one-time passwords for another account need that account allowlisted (UserProfile >> addOnetimePasswordUserProfile:). As SystemUser:(AllUsers userWithId: 'developer') addPrivilege: #CreateOnetimePassword. System commitTransaction.
An ordinary account cannot create the MCP server's
McpReadOnlyuser, sogemdb.mcp.readOnlyneeds that user created by an administrator. -
Access for linked sessions. The
gemdbcommand runs Python in a linked session as the developer's account, which needs read-write access to the extent and the shared page cache — typically by putting that account in the stone owner's group, with the extent660and the cache at its defaultSHR_PAGE_CACHE_PERMISSIONSof0660.