Skip to content

Error Handling

Type (error: UpdogError) => void

Called when the SDK catches an internal error. The SDK recovers where it can, and onError carries the error out to your logging and monitoring (Sentry, Datadog, and the like).

type UpdogError = {
code: UpdogErrorCode;
message: string;
source: string;
originalError?: unknown;
};
Code When
PARSE_ERROR File parsing failed (corrupt CSV, invalid XLSX, etc.)
RENDER_ERROR Component render failed (caught by error boundary)
TRANSFORM_ERROR Data transformation failed (column transform, value mapping)
VALIDATION_ERROR Validation execution failed (validator threw instead of returning)
WORKER_ERROR Web Worker failed (filter worker, chat transform worker)
COMMAND_ERROR Undo/redo command failed
OPERATION_ERROR General operation failed (bulk mutations, imports, clipboard access)
onError={(error) => {
Sentry.captureException(error.originalError ?? error, {
tags: { code: error.code, source: error.source },
});
}}

The browser can refuse a page access to the system clipboard. Both directions report OPERATION_ERROR through onError.

Copy and cut write to the clipboard. When the browser refuses that write, the SDK shows the person a toast, and the copied values stay available for pasting inside the grid.

Paste reads from the clipboard. When the browser refuses that read, the paste stops. Values copied inside the grid still paste.

Remote checks (unique.fn and { type: "asyncFunction" } validators) have failure modes a sync validator does not. When a check throws, returns malformed data, or goes 60 seconds without any activity, the cells still awaiting a verdict become unverified. The SDK leaves them unmarked in the grid, so your backend should re-validate those values at save time.

  • The SDK reports a check failure (rejection or malformed result) through onError as a VALIDATION_ERROR. One sweep produces one report, whatever the number of cells behind it. A timeout is silent.
  • Verdicts streamed through onChunk before a failure stay applied, so a crash at 99% keeps the 99%.
  • Do retries inside your fn. Once it rejects, the SDK marks the remaining cells unverified and does not re-ask.

A malformed row in a CSV, an unclosed quote for example, still imports. The file parses, the rows enter the grid, and the user sees a toast reporting how many rows had formatting issues along with the first few affected row numbers. These warnings stay in the UI and never reach onError. A hard parse failure still raises a PARSE_ERROR.