initCustomBlock() rejects when initialization fails. Data and page operations return errors in their results.
The error shape
Every error, thrown or returned, carries the same three fields:
Branch on
code and use message for display or logging only — messages are not part of the contract and can change between versions.
Handling operation errors
isRetryable is the SDK telling you whether a retry is meaningful. A transient host failure is retryable; a permission denial or an invalid property value is not, and retrying it only burns time. Do not retry on a non-retryable code.
Common non-retryable causes across the page and data source APIs:
- The viewing user lacks access to the page or data source.
- A property key is not declared in the block’s manifest, or its ID does not match the bound data source.
- A property value does not match its property’s type.
- A data source key is not declared, or is declared but not bound.
- The requested parent is not a valid parent for a new page.
Handling initialization errors
NotionCustomBlock renders errorFallback instead of its children when initialization fails, except for NotInIframeError as described below:
useCustomBlockInit() or catch the rejection from initCustomBlock(). Both APIs report a CustomBlockInitializationError with the fields listed above.
NotInIframeError
This error has code not_in_iframe and is never retryable. It means you opened the block directly in a browser tab without a host to supply real context.
NotionCustomBlock handles this error by rendering its children with placeholder context and a standalone preview warning. It does not render errorFallback. Use ntn workers customblocks dev to test host behavior and data source bindings.
Other initialization codes
Initialization codes describe what the host could not provide:
A protocol mismatch means the installed SDK and the host disagree on the bridge version. Because custom blocks are pre-1.0, the fix is generally to upgrade
@notionhq/custom-blocks and redeploy.
Binding codes mean the block declared a data source or property that the block’s configuration in Notion does not satisfy. Either the block instance needs to be reconfigured, or the manifest declares something the bound data source does not have.
Designing for failure
A block runs inside someone else’s page, against a data source you did not choose, for a user whose permissions you do not control. Assume every read can come back empty and every write can be refused. Render something useful when a data source is empty rather than treating it as an error, keep the failure visible inside the block rather than silently swallowing it, and never assume a write succeeded because it was accepted.Error code reference
The exported error code unions are exhaustive per API, and they track the SDK version, so the full list ships with the package rather than here. Seenode_modules/@notionhq/custom-blocks/docs/errors.md.