Troubleshooting
graft sql says no repository exists
Section titled “graft sql says no repository exists”Run graft init in the app data directory first:
graft initgraft sql --db data.sqlite "SELECT 1;"graft sql requires an explicit --db path and an existing .graft/
repository.
A database does not appear in status
Section titled “A database does not appear in status”Make sure the database contains a committed transaction, then stage the physical path.
graft sql --db data.sqlite "INSERT INTO notes(body) VALUES ('hello');"graft statusAny normal SQLite client can edit the file:
sqlite3 data.sqlite "INSERT INTO notes(body) VALUES ('from sqlite3');"graft add data.sqlitegraft add reads a consistent SQLite backup and includes committed WAL frames,
so a manual checkpoint is not required. An uncommitted transaction is not part
of the staged state.
Checkout or switch reports that SQLite is busy
Section titled “Checkout or switch reports that SQLite is busy”Close writers and long-lived read transactions for database paths that the operation needs to replace. Graft refuses to rename a new snapshot over a live writer and will not delete WAL or shared-memory sidecars that are still in use.
A file is stored externally when you expected inline
Section titled “A file is stored externally when you expected inline”Binary files always use external payload storage. Text files use external
storage when they exceed files.inline_text_threshold or match
files.external_paths.
graft config get files.inline_text_thresholdgraft config get files.external_pathsA payload is missing after clone or pull
Section titled “A payload is missing after clone or pull”Check and hydrate external payloads:
graft payload status HEADgraft payload fetch --remote origin HEADFor a broader repair:
graft audit --repair originPull enters merge state
Section titled “Pull enters merge state”Inspect conflicts:
graft statusgraft conflicts --jsonResolve each conflict:
graft resolve --ours data.sqlitegraft resolve --theirs attachments/report.pdfgraft merge --continue -m "resolve merge"Abort if you want to return to the pre-merge state:
graft merge --abortS3-compatible remote cannot authenticate
Section titled “S3-compatible remote cannot authenticate”Credentials do not belong in the remote URI. Configure them in the environment or standard AWS config files:
export AWS_ACCESS_KEY_ID="..."export AWS_SECRET_ACCESS_KEY="..."export AWS_REGION="auto"For Cloudflare R2 and MinIO, include the endpoint in the URI:
graft remote add origin 's3_compatible://bucket/prefix?endpoint=https://account.r2.cloudflarestorage.com'HTTP remote returns unauthorized
Section titled “HTTP remote returns unauthorized”Set the token environment variable expected by the remote URL:
export GRAFT_REMOTE_TOKEN='grt_...'If the URL uses token_env, set that variable instead:
export GRAFT_ARCHIVE_TOKEN='grt_...'Then retry:
graft ls-remote originRow diff is unavailable
Section titled “Row diff is unavailable”Row diff is only available for supported SQLite snapshots and surfaces. Added or deleted database files, missing snapshots, unsupported tables, or internal SQLite surfaces can limit row-level output.
Use the repository path diff as the source of truth and show row-level details
when row_diff_available is true.