Render images with the official Notion API
Tags: webdev, notion, javascript
Published: 2021-07-09 12:47:30

At the time of writing this post, the official Notion API doesn't yet provide support for image blocks. Since we are building a [blog template](https://github.com/twankruiswijk/Blion), we needed to develop a temporary solution to render images for the posts.

## Solutions that didn't cut it
We've looked at multiple ways to render an image for the posts:

### 1. Wait until the official Notion API adds support for the image blocks
This wasn't an option since having a blog without image support isn't appealing for many people, including myself. Also, it's been over a month, and we've had no updates on when new block types (like the image block) will get added.

### 2. Use the unofficial notion API for the images
We've looked into this, but we didn't want to rely on the unofficial API. We know that other platforms do, but having a mix of official and unofficial API calls would get messy and increase the complexity of the project, which we want to keep low.

## Introducing the `postImageSource` array
Since the Notion API supports text links, we came up with the idea that the template users could specify domains that would render as an image instead of a link when added to their Notion post.

Yes, this does mean that you can't use the same domain to render a text link.

Since we have a configuration file, we added an array `postImageSource` where users can specify which domains they want to render as an image when the template comes across a link with this domain.

```js
// site.config.js
postImageSource: [
  'images.unsplash.com',
  'res.cloudinary.com',
  'dl.dropboxusercontent.com',
],
```

To provide an upgrade path, we recommend that users still upload the image in their Notion document and place the text link below the image. This way, once the image block is ready in the official API, we can offer an option to make the `postImageSource` work backwards, meaning that people can disable rendering text links that include domains from `postImageSource`. Ultimately they can update all their posts and remove the `postImageSource` permanently.

## Don't bore us, get to the ~~chorus~~ code!
So you are working on your project that utilizes the Notion API? Nice, I would love to hear about it in the comments! But I know why you are here, and you want the code. Without further ado, here is the bare minimum of code that is required to display the images.


First, Add an array where you specify the domains you want to render as images

```js
const postImageSource = [
  'images.unsplash.com',
  'res.cloudinary.com',
  'dl.dropboxusercontent.com',
];
``` 

Second, determine if the text object has a link property.

```js
const postImageSource = [
  'images.unsplash.com',
  'res.cloudinary.com',
  'dl.dropboxusercontent.com',
];

if (text.link) {
 ....
}
```

Finally, check if the link includes the domain and determine whether to render an image or a text link.

```js
const postImageSource = [
  'images.unsplash.com',
  'res.cloudinary.com',
  'dl.dropboxusercontent.com',
];

if (text.link) {
  const linkUrl = text.link.url;

  if (postImageSource.some((u) => linkUrl.includes(u))) {
    return <img src={linkUrl} alt="insert alt" />;
  }

  // If the domain is not specified in the postImageSource, render a text link.
  return <a href={linkUrl} target="_blank" rel="noopener noreferrer">{text.content}</a>;
}
```

Hopefully, this guide helps you add image support to your Notion-powered website for the time being. Let's hope that the fantastic developers over at Notion crack the formula and add support for images and videos soon because that would open up a world of beautiful possibilities.