can1357/oh-my-pi · error · Error

plik upload metadata did not include an id and upload token

Error message

plik upload metadata did not include an id and upload token

What it means

Thrown by the plikUpload validator when the Plik upload server's JSON response is missing either the 'id' or 'uploadToken' field (or is not an object). Both are required to finalize a Plik upload: id identifies the upload session and uploadToken authorizes subsequent calls.

Source

Thrown at packages/coding-agent/src/blob-broker/uploaders-self-hosted.ts:73

		throw new Error("owncloud share response did not include OCS metadata and data");
	}
	const meta = ocs.meta;
	const data = ocs.data;
	if (typeof meta !== "object" || meta === null || !("statuscode" in meta)) {
		throw new Error("owncloud share response did not include an OCS status");
	}
	if (typeof data !== "object" || data === null || !("url" in data)) {
		throw new Error("owncloud share response did not include a URL");
	}
	const url = nonEmptyString(data.url);
	if (!url) throw new Error("owncloud share response did not include a URL");
	const id = "id" in data ? identifier(data.id) : undefined;
	return { statusCode: meta.statuscode, url, ...(id ? { id } : {}) };
}

function plikUpload(value: unknown): PlikUpload {
	if (typeof value !== "object" || value === null || !("id" in value) || !("uploadToken" in value)) {
		throw new Error("plik upload metadata did not include an id and upload token");
	}
	const id = identifier(value.id);
	const uploadToken = nonEmptyString(value.uploadToken);
	if (!id || !uploadToken) throw new Error("plik upload metadata did not include an id and upload token");
	let downloadBase: string | undefined;
	if ("downloadURL" in value) downloadBase = nonEmptyString(value.downloadURL);
	if (!downloadBase && "downloadDomain" in value) downloadBase = nonEmptyString(value.downloadDomain);
	return { id, uploadToken, ...(downloadBase ? { downloadBase } : {}) };
}

function requiredStringOption(config: DestinationRuntimeConfig, key: string): string {
	const value = requireOption(config, key);
	if (typeof value !== "string" || value.trim() === "") {
		throw new Error(`Destination option ${key} must be a non-empty string`);
	}
	return value.trim();
}

View on GitHub (pinned to 9690622007)

Solutions

  1. Check that the configured plik apiUrl points to the Plik API root (e.g. https://plik.example.com) not a UI route
  2. Verify the server's response with curl (curl -F file=@x https://plik.example.com) — it should contain id and uploadToken
  3. Check Plik server logs for rejection reasons (size limits, auth requirements, expired tokens)
  4. Ensure any required Plik authentication options are set in the destination config

Example fix

// before: hitting the UI path returns HTML/JSON without tokens
apiUrl = "https://plik.example.com/" // if behind a path-mangling proxy this can route wrong
// after: verify the API answers directly
const resp = await fetch("https://plik.example"); const meta = await resp.json(); if (!meta.id || !meta.uploadToken) throw new Error(meta.message ?? "plik rejected upload");
Defensive patterns

Strategy: validation

Validate before calling

const res = await fetch(plikApi, { method: "POST", body: form });
const meta = await res.json();
if (typeof meta?.id === "undefined" || typeof meta?.uploadToken !== "string" || !meta.uploadToken) {
  throw new Error(`plik rejected upload: ${JSON.stringify(meta).slice(0, 200)}`);
}

Type guard

function isPlikUploadMeta(value: unknown): value is { id: string | number; uploadToken: string } {
  if (typeof value !== "object" || value === null) return false;
  const v = value as { id?: unknown; uploadToken?: unknown };
  const idOk = typeof v.id === "string" || typeof v.id === "number";
  return idOk && typeof v.uploadToken === "string" && v.uploadToken.length > 0;
}

Try / catch

try {
  const up = await uploader.upload(blob);
} catch (err) {
  if ((err as Error).message.includes("id and upload token")) {
    throw new Error("plik server response lacked id/uploadToken — check apiUrl points to the Plik API and auth options are set");
  }
  throw err;
}

Prevention

When it happens

Trigger: POSTing the file to a Plik server (createPlikUploader -> metadata -> plikUpload) and receiving a JSON body without id/uploadToken — e.g. the server returned an error JSON like { message: "invalid upload" } with 200, or the endpoint URL is wrong so a different route answered.

Common situations: Misconfigured plikd URL (hitting the UI instead of the API), Plik server rejecting the request due to missing/invalid upload token header while still returning JSON, or a proxy returning a JSON error page.

Related errors


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