This is a submission for the Netlify Dynamic Site Challenge: Visual Feast.
What I Built
I have built a dynamic image gallery using Pexels API and Next.js. Landing page fetches a list of curated images from Pexels API. User can click on the image to view in detailed mode. User can also use the search functionality to find images of any topic. Moreover, authenticated users are allowed to like any image and create his/her own collection of liked images. From the user profile page, user can upload profile picture and change password.
Demo
You can find it here: Photograph.
Don't forget to register and create your favorite collection 🏞️ 🎑 🌄 🌃
Gallery
Download in Desired Size
Collection of Liked Images
User Profile Page
Upload Profile Picture
Platform Primitives
Netlify Image CDN
I have leveraged Netlify Image CDN to display and download optimized image. It is very easy to use and framework agnostic. You just need to send a request to /.netlify/images
endpoint with query parameters specifying the source asset and desired transformation.
My img
element for the gallery looks like below. photo
is the resource from Pexels API.
<img
src={`/.netlify/images?url=${photo.src.original}&fit=cover&position=center&w=250`}
alt={photo.alt}
width={photo.width}
height={photo.height}
className="w-full h-full object-cover object-center"
style={{ backgroundColor: photo.avg_color }}
/>
In the image details modal, I allow users to download the image in different sizes. Once again I leveraged Netlify Image CDN for resizing the image for downloading.
Netlify Blobs
I have leveraged Netlify Blobs for storing user data and profile picture.
Netlify encrypts blobs at rest and in transit. So, it is a secured storage for sensitive data.
When user resister on my site, I create and store a JSON document with the user account information in the Netlify Blobs. Moreover, you can also store metadata with your main data. I store account created timestamp and last password updated timestamp as metadata with the user account data.
Here is a sample code of how you can store user account information in Netlify Blobs.
// user object
const newUser = {
id,
name,
email,
passwordHash,
};
// metadata, can be any arbitrary object.
const userMetadata = {
createdAt: new Date().toISOString(),
passwordUpdatedAt: new Date().toISOString(),
};
// getStore is imported from @netlify/blobs
const userStore = getStore("user");
// save data as JSON
await userStore.setJSON(id, newUser, { metadata: userMetadata });
Whenever user change the password, I update the passwordUpdatedAt
metadata in the backend. That's how I can display last password updated at time in the profile page.
I store users uploaded profile picture in the Netlify Blobs as ArrayBuffer.
const profilePictureStore = getStore("profile-picture");
// save new profile picture
await profilePictureStore.set(randomId, arrayBuffer, {
metadata: { fileName, type },
});
To access the uploaded image, I have created GET endpoint using Next.js API route handler. (BTW, it is also possible to access using Netlify Functions).
For example a GET request at /api/profile-picture?imageId=your-image-id
endpoint reads the file from the Netlify Blobs and returns the raw file. To render the optimized profile picture, I again utilize Netlify Image CDN. A GET request to /.netlify/images?url=/api/profile-picture?imageId=your-image-id&fit=cover&position=center&w=96
returns optimized image for my case.
The img
tag for Avatar component is something like this:
<img
src={`/.netlify/images?url=${user.image}&fit=cover&position=center&w=96`}
alt="avatar"
/>
One more thing I forgot to mention. When user like an image, that image data is stored with the user account data in the Netlify Blobs. That's how I keep track of the liked images of any user.
Conclusion
Code repository: https://github.com/mazid1/photograph
That's all for today 🚀
I hope you enjoyed this article 🙌
Let me know your thoughts in the comment section 👇
Top comments (2)
Great work. The gallery looks really smart.
Thank you for your complement Philip.