1

I am building an app in Next.js, which fetches dynamic data from a Supabase table. The table (called product) has several data points (title, description, image). My table in Supabase looks like this: enter image description here

My problem is that both the description and the title are being pulled in dynamically, populating my home page properly. What is failing is the image. Images are stored in a public bucket that looks like this:

enter image description here

The way I'm attempting to pull the image in dynamically is as follows:

import { supabase } from "../utils/supabase";
import Link from "next/link";
import { useUser } from "../context/user";
import Image from "next/dist/client/image";

export default function Home({ products, tile_url }) {
  const { user } = useUser();

  const {data:image_url} = supabase.storage.from("games").getPublicUrl(tile_url);
  console.log(image_url.publicURL);

  return (
    <div className="body w-full h-screen py-16">
      <div className="w-full max-w-3xl mx-auto px-2">
        {products.map((product) => (
          <Link
            key={product.id}
            href={`/${product.id}`}
          >
            <a className="p-8 h-40 mb-4 rounded element text-xl flex">
             
              <img src={image_url.publicURL} alt="" />
              {product.title}
            </a>
          </Link>
        ))}
      </div>
    </div>
  );
}

export const getStaticProps = async () => {
  const { data: products } = await supabase.from("product").select("*");

  return {
    props: {
      products,
    },
  };
};

The image is not returned in the frontend. The console.log returns the url, but instead of the image name, it pastes undefined a the end:

https://[project_identifier].supabase.co/storage/v1/object/public/games/undefined

The expected outcome would be:

https://[project_identifier].supabase.co/storage/v1/object/public/games/gameOneGameTile.jpeg

Any ideas as to what I am doing wrong? Thank you in advance!

EDIT:

Based on a response from @dshukertjr on this question, I have included the path to the image in the table, to be able to use the column name to fetch the data. However, nothing has changed. enter image description here

nelakay
  • 103
  • 1
  • 11
  • you should specify the folder name in `.getPublicUrl("/game_one/${tile_url}")` – mocherfaoui Dec 11 '22 at 16:09
  • @mocherfaoui, thank you very much for your comment! Unfortunately, this doesn't work. It returns the same url (appending 'undefined'). Also, if I have to specify the folder, is there a way to do this dynamically as well, since there will be more than one game...? Again, thank you very much for your input, appreciate your time. – nelakay Dec 11 '22 at 16:17
  • if you're not using Next.js 13 with app directory then you need to fetch the image inside a `useEffect`, see this [example](https://supabase.com/docs/guides/with-nextjs#create-an-upload-widget) – mocherfaoui Dec 11 '22 at 16:25

2 Answers2

1

What you need to pass to the getPublicUrl() function is the path to the image within the bucket for example like this:

  const pathToImage = 'game_one/gameOneGameTile.jpeg'

  const {data:image_url} = supabase.storage.from("games").getPublicUrl(pathToImage);

You are passing tile_url in your code. If you want to keep it that way, the path to the image needs to be saved in your product table under tile_url column for each row to be able to display an image.

dshukertjr
  • 15,244
  • 11
  • 57
  • 94
  • Thank your for your comment. I am trying this, by placing the url for each image in the cell for each row, but it still appends "undefined" to the url when I log it. Nothing happens in the frontend (no images are shown) I am updating the question as well, to show this option. – nelakay Dec 12 '22 at 21:12
  • @nelakay Thanks for updating the question and adding the updated screenshot of your table. What you have in the `tile_url` column is the cause. You want to have the path to the image, and not the url. You want to have literally `game_one/gameOneGameTile.jpeg` in there, and not anything that starts with `https://your_supabase_url...`. – dshukertjr Dec 13 '22 at 01:56
0

For working with private storages, I had to create a signed url that I could use as an image src. There aren't a lot of good alternatives unfortunately, as there isn't a way to pass in the authorizer to an image src.

Michael Eliot
  • 831
  • 8
  • 18