can1357/oh-my-pi · error · ToolError

Unsupported SQLite selector

Error message

Unsupported SQLite selector

What it means

readSqlite dispatches on a parsed SQLite selector (list/schema/row/query/raw). If the selector object carries none of the known variants, control falls past the switch and throws ToolError 'Unsupported SQLite selector'. It is an internal-exhaustiveness guard: user input should normally have been parsed into one of the supported shapes earlier.

Source

Thrown at packages/coding-agent/src/tools/read-sqlite.ts:206

				const result = executeReadQuery(db, selector.sql);
				let output = renderTable(result.columns, result.rows, {
					totalCount: result.rows.length,
					offset: 0,
					limit: result.rows.length || DEFAULT_MAX_LINES,
					table: "query",
					dbPath: resolvedSqlitePath.absolutePath,
				});
				if (result.truncated) {
					output += `\n[Output capped at ${MAX_RAW_QUERY_ROWS} rows; add a LIMIT/OFFSET clause to the query to page through more]`;
				}
				return toolResult<ReadToolDetails>(details)
					.text(prependSuffixResolutionNotice(output, resolvedSqlitePath.suffixResolution))
					.sourcePath(resolvedSqlitePath.absolutePath)
					.done();
			}
		}

		throw new ToolError("Unsupported SQLite selector");
	} catch (error) {
		if (error instanceof ToolError) {
			throw error;
		}
		throw new ToolError(error instanceof Error ? error.message : String(error));
	} finally {
		db?.close();
	}
}

View on GitHub (pinned to 9690622007)

Solutions

  1. Check the path suffix / selector construction — use a documented form (table list, :schema, :table?limit, raw query, conflict selector).
  2. Inspect what selector value reached readSqlite (log or debugger) and map it to a supported variant.
  3. Update the parser/switch if a new selector kind was added without a case.
  4. Pin package versions so selector producers and consumers agree.

Example fix

// before
dbPath = 'file.db:unknown-selector';
// after: use a supported suffix
dbPath = 'file.db:mytable?limit=20'; // or 'file.db' for table list, 'file.db:mytable:schema'
Defensive patterns

Strategy: validation

Validate before calling

const SUPPORTED = new Set(['list', 'schema', 'row', 'query', 'raw']);
if (!SUPPORTED.has(selector.kind)) throw new Error(`Unsupported selector: ${selector.kind}`);
return readSqlite(path, selector);

Type guard

function isSupportedSelector(s: unknown): s is { kind: 'list'|'schema'|'row'|'query'|'raw' } {
  return typeof s === 'object' && s !== null &&
    ['list','schema','row','query','raw'].includes((s as { kind?: string }).kind ?? '');
}

Try / catch

try {
  return await readSqlite(dbPath, selector);
} catch (e) {
  if (e instanceof ToolError && e.message === 'Unsupported SQLite selector') {
    console.error('Selector kind not supported; use list/schema/row/query/raw');
    return null;
  }
  throw e;
}

Prevention

When it happens

Trigger: A selector parsed by the suffix parser that matches no case in the switch (e.g. a new/unknown selector variant reached readSqlite); programmatic callers constructing a malformed selector object; a selector type widened by a refactor without updating the switch.

Common situations: Plugin or SDK code passing a hand-built selector; version mismatch where a newer selector kind is fed to an older reader; typos in the path suffix that survive parsing into an unrecognized shape.

Related errors


AI-assisted analysis of can1357/oh-my-pi@9690622007 (2026-08-31). Data as JSON: /api/errors/7931d6b20c8f4ac2. Report an issue: GitHub.