googleapis/mcp-toolbox · error · Error

Toolbox binary not found

Error message

Toolbox binary not found

What it means

JSONToFirestoreValue parses a Firestore typed value with type "timestampValue" and requires an RFC3339Nano-formatted string. time.Parse failed, so the input string is not a valid RFC 3339 timestamp. The original parse error is wrapped with %w so you can inspect it via errors.Unwrap/As.

Source

Thrown at cmd/internal/skills/generator.go:213

		const npxArgs = ["--yes", "@toolbox-sdk/server@{{.ToolboxVersion}}", "--log-level", "error", ...configArgs, "invoke", toolName, "--user-agent-metadata", userAgent, ...processedArgs];

		const child = spawn(command, npxArgs, { shell: os.platform() === 'win32', stdio: 'inherit', env });
		{{else}}
		function getToolboxPath() {
				if (process.env.GEMINI_CLI === '1') {
						const ext = process.platform === 'win32' ? '.exe' : '';
						const localPath = path.resolve(__dirname, '../../../toolbox' + ext);
						if (fs.existsSync(localPath)) {
								return localPath;
						}
				}
				try {
						const checkCommand = process.platform === 'win32' ? 'where toolbox' : 'which toolbox';
						const globalPath = execSync(checkCommand, { stdio: 'pipe', encoding: 'utf-8' }).trim();
						if (globalPath) {
								return globalPath.split('\n')[0].trim();
						}
						throw new Error("Toolbox binary not found");
				} catch (e) {
						throw new Error("Toolbox binary not found");
				}
		}

		let toolboxBinary;
		try {
				toolboxBinary = getToolboxPath();
		} catch (err) {
				console.error("Error:", err.message);
				process.exit(1);
		}

		const toolboxArgs = ["--log-level", "error", ...configArgs, "invoke", toolName, "--user-agent-metadata", userAgent, ...args];
		const child = spawn(toolboxBinary, toolboxArgs, { stdio: 'inherit', env });
		{{end}}

    child.on('close', (code) => {

View on GitHub (pinned to 8cc6e09de2)

Solutions

  1. Reformat the string to a full RFC 3339 timestamp with timezone and fractional seconds, e.g. "2024-01-01T12:00:00.000Z".
  2. If the input is an epoch number, convert it in Go with time.Unix(...).Format(time.RFC3339Nano) before passing it in.
  3. Inspect the wrapped error with errors.As(err, &parseErr) to see the exact parse failure position.

Example fix

// before
v := map[string]any{"timestampValue": "2024-01-01 12:00:00"}
// after
v := map[string]any{"timestampValue": "2024-01-01T12:00:00Z"}
Defensive patterns

Strategy: validation

Validate before calling

func isValidRFC3339(s string) bool { _, err := time.Parse(time.RFC3339Nano, s); return err == nil }

Type guard

func asTimestampString(v any) (string, bool) { s, ok := v.(string); return s, ok && isValidRFC3339(s) }

Try / catch

var v any = ... // converted value
if _, err := JSONToFirestoreValue(map[string]any{"timestampValue": s}, client); err != nil {
    var pe *time.ParseError
    if errors.As(err, &pe) { /* fix format */ }
}

Prevention

When it happens

Trigger: Passing {"timestampValue": "<string>"} into JSONToFirestoreValue where the string is not parseable by time.RFC3339Nano (e.g. "2024-01-01", epoch millis, "2024-01-01T00:00:00" missing timezone, or trailing garbage).

Common situations: Clients send dates produced by JavaScript Date.toLocaleString or date-only inputs from HTML date pickers; timestamps serialized without the UTC 'Z' suffix; unix epoch numbers stringified into the timestamp field.

Related errors


AI-assisted analysis of googleapis/mcp-toolbox@8cc6e09de2 (2026-09-05). Data as JSON: /api/errors/08a80550af44aa50. Report an issue: GitHub.