Using image URL in images/edits request

does anyone have any tips for using a URL returned from images/generations as the image passed into images/edits? i’ve been going in circles trying to figure it out. i think i need to convert the image url to a png, but i haven’t been able to figure out a clean way of doing it, and the API doesn’t tell me if i’m sending a valid png or not

2 Likes

Welcome to the community!

I would recommend receiving as binary then storing it locally.

Hope this helps!

sadly this wont work in my use case, as i’m creating a web app. users shouldn’t/can’t be forced to save an image only used to generate other images

The URL of the image generation only lasts about an hour or so, and is not intended to be used to store the images. If you’re just using the generated image to create another one, you just need to send the binary data back…

1 Like

so theoretically, i should be able to convert the images/generations response url or b64 to a blob, convert the blob to binary, then pass it into the request? because that’s what i’m doing, and i’m still getting error 400

It’s even easier! You just need to tell it to originally send the binary…

Each image can be returned as either a URL or Base64 data, using the response_format parameter. URLs will expire after an hour.

Note to @logankilpatrick — sent a chat to help about broken link in the API docs… points to localhost rather than the page…

2 Likes

i’m no expert, but i thought there was a difference between binary and b64. i also didn’t know binary and/or b64 suffices as a ‘valid PNG’ (per the docs). but now i think the issue is that ‘mask’ is not an optional parameter, even though the docs say it should be

Mask is only needed on edit endpoint, I believe.

I think it’s b64, and I just used binary interchangeably. Sorry!

no worries at all. still a very new API. we are figuring this out together. thanks a ton for the help!

1 Like

i’ve now tried posting to images/edits/ with a b64 transparent mask in conjunction with a b64 image, but still get bad request error. i’ve tried without a mask as well, no dice.

my whole idea is to create a ‘cover’ image, then use that image to generate images for a story book’s individual pages. i feel like it shouldn’t be as difficult as i’m making it out to be, but the docs really don’t give much help in terms of how to programmatically post a ‘valid png’

i’ve also tried converting the b64_json response from image/generations to a PNG file using javascripts ‘File’ class, but i’m still getting no where

update: i’m fairly certain i’m sending the correct data in my request now, but i’m getting the following error:
‘Uncaught (in promise) TypeError: localVarFormParams.getHeaders is not a function’

i’ve spent a good amount of time googling solutions, but nothing really seems to work. here’s my request:

export const fetchEdits = async (image, prompt) => {
  const mask = await getBase64();
  const imageFile = dataType64toFile(image, "image");
  const maskFile = dataType64toFile(mask, "mask");
  const response = await openai.createImageEdit(
    imageFile,
    maskFile,
    prompt,
    1,
    "256x256"
  );
  return response.data.data[0]["url"];
};

export const dataType64toFile = (b64Data, filename) => {
  const mime = "image/png";
  const bstr = atob(b64Data);
  let n = bstr.length;
  const u8arr = new Uint8Array(n);
  while (n--) {
    u8arr[n] = bstr.charCodeAt(n);
  }
  const newFile = new File([u8arr], filename, {
    type: mime,
  });
  return newFile;
};

export const getBase64 = () => {
  const img = document.getElementById("mask") as any;
  const canvas = document.getElementById("canvas") as any;
  canvas.width = img.width;
  canvas.height = img.height;
  const context = canvas.getContext("2d");
  if (context && img) {
    img.onload = () => {
      context.drawImage(img, 0, 0);
    };
  }
  const dataURL = canvas.toDataURL("image/png");
  return dataURL.replace(/^data:image\/(png);base64,/, "");
};

and here’s what the error looks like in dev tools console:

has anyone out there figured out this particular use case yet? i’d be thrilled to finally get this figured out :slight_smile:

Sorry for stupid question, but are you using Node or Typescript or something else?

I have some notes for handling the image bit in various languages. They haven’t been tested - but they may help you

not a stupid question at all! i’m using react with typescript, and i’d be absolutely thrilled with anything you can share

OK, so casting may be part of your problem.

OpenAI requires you to cast things as Any when you pass images. It is a Typescript specific issue.

Here are two code snippets.

Like I said, they are untested and they are from a course I am working on.

But the key thing with this slide is that Typescript is the same as Node but it requires the “Any” casting


Snippet 1: (This is for an edit with a mask and refers back to a file)

const response = await openai.createImageEdit(
fs.createReadStream(“sunlit_lounge.png”) as any,
fs.createReadStream(“mask.png”) as any,
“A sunlit indoor lounge area with a pool containing a flamingo”,
1,
“1024x1024”
);


Here is snippet 2 - (It uses binary data - it is for a variation image - but the way you need to recast the buffer to a new object with type any and then you also need to name the new object is important. If you don’t use the name, it also tends to fail)

// This is the Buffer object that contains your image data
const buffer: Buffer = [your image data];

// Cast the buffer to any so that we can set the name property
const file: any = buffer;

// Set a name that ends with .png so that the API knows it’s a PNG image
file.name = “image.png”;

const response = await openai.createImageVariation(
file,
1,
“1024x1024”
);

Hope it helps

i appreciate the help, because you’re clarifying things i was unsure about. after diving back in, i’ve concluded that i don’t think this is my root issue (sadly)… i’m pretty sure sending an API request with the ‘image’ paramater as data from an open ai API response is triggering a CORS issue. my guess is that my api key would be exposed in the image data, thus visible to the front end(??)

it’s a bummer because i was hoping to use js to programmatically create story books. a cover image would be created first, then several others created through the images/edits endpoint, using the cover image as a ‘home base’. but i don’t think i can do it without creating a db to store the image, or a backend API to call open ai as a third party API, or something along those lines(??)

hopefully open AI can do something in the future to make this use case easier to achieve, and if it’s already possible (which i’m sure is likely the case) that the docs be refreshed for future development

It’s even easier! You just need to tell it to originally send the binary…

Each image can be returned as either a URL or Base64 data, using the response_format parameter. URLs will expire after an hour.

Note to @logankilpatrick — sent a chat to help about broken link in the API docs… points to localhost rather than the page…

It looks like this is fixed now on this page: https://beta.openai.com/docs/guides/images/generations

Let me know if it is still an issue on your end @PaulBellow

1 Like

Looks fine here now. Raf responded a while back.

Happy New Year. We’ve been trying to hold down the fort, so to speak. :wink:

1 Like

i’m still encountering issues with this endpoint. i’m now passing my PNGs exactly like the reference in the docs, but i’m getting
error: { code: null, message: "Invalid input image - format must be in ['RGBA', 'LA', 'L'], got 1.", param: null, type: 'invalid_request_error' }

image

Did you try the solution up-thread?

@PaulBellow yes. those return ‘message: ‘Uploaded image must be a PNG and less than 4 MB.’’, which is even further away from the last error i posted