Making a Simple Self-Hosted Photo Gallery With IPFS

Alex Shapoval
Kelp.Digital
Published in
8 min readOct 10, 2023

Whether you are a professional or a hobbyist, sharing photos with the world marks a significant milestone in any creative journey. The internet plays an indispensable role for content creators, especially for those who are just starting out and are yet to grow a following. Having an online space to display a curated selection of your best works can be a great help in attracting fans and potential clients.

In this guide, we will make a simple self-hosted photo gallery using a static site generator, free hosting, and IPFS to store images.

Advantages of self-hosted portfolio

Most general-purpose website builders have templates for photography or graphic design portfolios. Besides them, there are also specialized services aimed directly at visual creators. While such services undauntedly have their merits, they still have a number of limitations:

  • Lack of customization options: Most website builders have a set of predefined templates and “building blocks” for specific needs. By using them, it’s easy to get a clean and professional look, but they can only go so far in terms of customization, resulting in a plain-looking, cookie-cutter website.
  • Branding restrictions: Depending on the platform, you can face limitations in representing your brand identity. Some services also display their logo or branding on some plans.
  • Subscription costs: While many of such services have free plans, they often impose major limitations, making it hard or impossible to use and benefit from the portfolio.
  • Vendor lock-in: It’s rare to see a website builder have convenient export options because they are not interested in users leaving, creating vendor lock-ins, and making migrations time-consuming.

Embracing the do-it-yourself approach allows for complete freedom of expression and endless customization options without dependence on a single service.

Choosing the storage for images

There are a number of options when it comes to storing images. One of them is storing the files in the Git repository together with the source code. It certainly has some benefits, such as versioning and backups, but at the same time, it involves many complications.

While the Git versioning system has no explicit limits on file or repository size, platforms that provide repository storage do. GitHub, for example, will block any file that’s larger than 100 MB from uploading. And repositories that grow too big may be asked to scale down, risking deletion otherwise. In addition to platform limitations, oversized repositories make collaboration difficult, requiring users to download a large amount of information to be able to make changes to the source code.

One possible solution to this is Git Large File Storage (Git LFS). It was developed to target this specific problem, but it suffers from a lack of independent storage providers, high storage costs, a complex setup process, and compatibility issues. There are other options besides Git LFS: cloud buckets like AWS S3, specialized storage services, a regular VPS with Nginx or Apache to serve files, and others.

As you may have guessed from the title of the article, there is one more option. We will use IPFS to store and serve images for the portfolio. But traditional solutions, where you pin the file and access it through a public or private gateway, have a number of limitations: little to no control over who accesses the images and how, no sure ability to delete them, and no copyright traceability, among others. We believe there is a better way to enjoy the benefits of IPFS without the caveats associated with it. And to demonstrate our vision, we have built Macula.Link.

Macula.Link is a fully-fledged multimedia platform for storing, managing, and sharing content. Tap into the power of built-in analytics, copyright traceability, and flexible access management, and allow your works to be reused with Unilinks — a unique, new way to share content on your terms.

Learn more about Macula.Link and sign up for early access to be among the first to experience how it can improve your workflow.

Building the portfolio

Preparing the images

A portfolio can’t exist without something to display. When planning what images to include, think about the purpose — is it to attract potential clients, show off your specialty, or something else? Then, consider how many photos you plan to add and whether it makes sense to group them based on theme or type. Finally, make sure that images have metadata in place, including licensing metadata. Doing so properly will reward you with a Google Licensable badge.

Once the selection process is done, the next step is to prepare thumbnails. Thumbnails are smaller, slightly compressed versions of photos used to save loading time and bandwidth for people visiting the portfolio. They are used when a lot of images are present on one page, for example, on the index page or album page. Originals are then used when displaying a page with an individual image. Without thumbnails, pages populated with images will total hundreds of megabytes, leading to slow loading times and search engine penalties.

With Macula, there are two ways to approach this: using on-the-fly image transformations and by generating thumbnails and saving them as individual images.

When on-the-fly transformations are enabled during publishing the image, parameters such as width, height, quality, sharpness, and others can be specified dynamically using query parameters. A URL with query parameters looks like this:

https://u.macula.link/UNILINK_ID?w=800&h=200

Where w=800 and h=200 are parameters for width and height, respectively.

Read Macula.Link documentation for more details on creating and pinning transformations.

On-the-fly transformations allow the image to be reused in various contexts. Instead of saving each version as an individual file and publishing it, the original image is modified according to the specified parameters the moment it is requested, and its temporary version is shown.

This way, you will use the same link for displaying thumbnails and original images, with the only difference being the presence of query parameters. As an added benefit, others can also reuse your images directly from you without downloading the actual file and modifying it themselves, if you allow that. Just imagine the possibilities for licensing without intermediaries!

However, this flexibility comes at a price. On-the-fly image transformation is a computationally intensive task that takes some time. The amount of time to apply the transformation directly correlates to the size of the original image, as well as active transformations and their parameters. For example, resizing, compressing, reformatting, and sharpening a 4K image can take a long time. Multiplied by the number of images on the page, this can negate the purpose of making a site that loads fast, even though the page size will be small.

For situations like this, Macula.Link allows saving transformed versions of the images. By generating and publishing a slightly smaller photo with on-the-fly transformations enabled, you preserve flexibility and reusability without the time concern. Or, if there is no need for on-the-fly transformations, you can prepare thumbnail versions and publish them as is. With this, there will be two links: one for the thumbnail and one for the original image.

Transforming, saving, and publishing a bunch of images sounds like a tedious job, because it is! At the moment of writing this article, Macula.Link is still in its infancy, and many quality-of-life things like batch operations are not here. But they will certainly appear soon enough, together with a lot of other awesome things. But don’t think that we have nothing to show now! Join the private Beta and see what we have in store!

Getting started with Macula.Link is extremely easy! Sign up for a free account (no credit card required) and unlock the power of storage, image transformations, powerful analytics, and copyright traceability.

Learn more about how Macula.Link works:

Once all images are uploaded and ready for sharing, let’s proceed to building the portfolio.

Technical Prerequisites

We will build the portfolio using the Jekyll static site generator and host it on Netlify Drop but you are free to substitute them for tools of your choice. The following prerequisites are required for using Jekyll:

Scaffolding the site

Run the following terminal command to scaffold the basic file structure (--blank scaffolds only a necessary minimum of files instead of a full example site):

jekyll new my_gallery --blank

When scaffolding is complete, change the extension of the index.md file to index.html. This will be the main page of the gallery.

Creating the index page

The gallery will have a single index page with a grid of thumbnails. The grid has to be responsive to look good on different screen sizes. Clicking on each thumbnail will lead the visitor to Macula.Link’s unilink page with all the information about the picture and quick links to share and use it:

Unilink Preview page with information about the image and the author

Jekyll provides a default.html layout after scaffolding, which has a very basic structure of a regular page of the website. For now, this is enough. Let’s add a front matter with information about images to the index page:

---
title: My Awesome Photo Gallery
layout: default
photos:
- photo:
thumbnail_src:
original_href:
- photo:
thumbnail_src:
original_href:
---

Note the photos structure. It lists URLs of thumbnails and original images that Jekyll will loop through to generate the gallery. Images you uploaded to Macula.Link will go here.

Now let’s add the gallery grid.

<div class="gallery">
{% for photo_item in page.photos %}

<div class="gallery-item">
<a href="{{ photo_item.photo.original }}" target="_blank"
><img src="{{ photo_item.photo.thumbnail }}"
/></a>
</div>

{% endfor %}
</div>

If you decided to use on-the-fly transformations for generating thumbnails dynamically, the <img> tag will look similarly to this:

<img src="{{ photo_item.photo.original }}?w=600&q=80" />

Since thumbnails are generated dynamically, the thumbnail key can be omitted from the front matter.

Styling

To display images as a grid, open assets/css/main.scss and add the following:

.gallery {
display: flex;
flex-wrap: wrap;
justify-content: space-between;
}

.gallery-item {
flex: 1;
flex: 0 0 calc(33.33% - 20px);
margin: 10px;
}

.gallery-item img {
width: 100%;
height: auto;
display: block;
}

@media (max-width: 768px) {
.gallery-item {
flex: 0 0 calc(50% - 20px);
}
}

This is enough to have photos displayed in a flexible grid that adapts to the screen size: the larger the screen, the more images will be in a row. It’s a very simple style, the goal of which is to create something that looks decent quickly. Feel free to expand and modify it according to your tastes.

Building and publishing the site

Now the portfolio is ready for deployment. Run the following command in the terminal:

jekyll build

Once the command completes, a new folder named _site will appear in the working directory. This folder has to be uploaded to the hosting provider.

Sign up for Netlify (or an alternative provider) and upload the _site folder. Once the upload is complete, the portfolio will come online!

If you have a domain name, you can use it instead of a subdomain provided by Netlify. To do this, go to Domain Settings and click Add domain alias. Enter the domain you want to assign to the site and follow the instructions to configure the DNS records.

Further steps

This is pretty much it! Once the site is up and running, you may want to customize it more, add more photos, or make the structure more complex by including categories or displaying image metadata on a separate page. Once all changes are made, a good next step is to start including the site link in your social profiles or sharing it with people online.

--

--

Alex Shapoval
Kelp.Digital

I write about tech, copyright, and anything that catches my attention. Doing cool things @ Kelp.Digital