{"record":{"id":"48d9691a83c1d908","repo":"mckaywrigley/chatbot-ui","slug":"image-must-be-less-than-imagesizelimit-1000000-48d969","errorCode":null,"errorMessage":"Image must be less than ${imageSizeLimit / 1000000}MB","messagePattern":"Image must be less than (.+?)MB","errorType":"validation","errorClass":null,"httpStatus":null,"severity":"warning","filePath":"db/storage/message-images.ts","lineNumber":9,"sourceCode":"import { supabase } from \"@/lib/supabase/browser-client\"\n\nexport const uploadMessageImage = async (path: string, image: File) => {\n  const bucket = \"message_images\"\n\n  const imageSizeLimit = 6000000 // 6MB\n\n  if (image.size > imageSizeLimit) {\n    throw new Error(`Image must be less than ${imageSizeLimit / 1000000}MB`)\n  }\n\n  const { error } = await supabase.storage.from(bucket).upload(path, image, {\n    upsert: true\n  })\n\n  if (error) {\n    throw new Error(\"Error uploading image\")\n  }\n\n  return path\n}\n\nexport const getMessageImageFromStorage = async (filePath: string) => {\n  const { data, error } = await supabase.storage\n    .from(\"message_images\")\n    .createSignedUrl(filePath, 60 * 60 * 24) // 24hrs\n","sourceCodeStart":1,"sourceCodeEnd":27,"githubUrl":"https://github.com/mckaywrigley/chatbot-ui/blob/81328b61d2a4ab597a7a057be70e785cf756d9f8/db/storage/message-images.ts#L1-L27","documentation":"Thrown by uploadMessageImage when the image File exceeds the hardcoded 6000000-byte (6MB) limit. It's a client-side pre-flight check before any Supabase call, so no network traffic occurs when it throws. The limit is a literal in source, not configurable via env.","triggerScenarios":"Selecting a photo/export/screenshot larger than 6MB for a chat message; HEIC/RAW photos from modern phones that are commonly 8-15MB; using a Blob built from canvas at full resolution. Any image.size > 6000000 triggers it immediately.","commonSituations":"Phone camera originals exceeding 6MB; users pasting large screenshots; the limit differing from other flows (assistant images also 6MB, profile images 2MB) so users get confused about which cap applies; no client-side pre-check in the picker UI so the throw surfaces as an unhandled rejection.","solutions":["Compress or resize the image client-side (e.g. canvas re-encode to JPEG at ~80% quality) before calling uploadMessageImage.","Show an inline file-picker warning when image.size > 6*1000*1000 so the user can pick a smaller file.","If 6MB is too tight for your users, raise the constant in db/storage/message-images.ts (and keep the Supabase bucket cap in mind).","Convert HEIC/RAW to JPEG upstream so typical sizes land under the cap."],"exampleFix":"// before\nconst file = selectedFile // 9MB photo\nconst path = await uploadMessageImage(path, file)\n\n// after\nconst file =\n  selectedFile.size > 6000000\n    ? await compressImage(selectedFile, 0.8) // helper: canvas re-encode\n    : selectedFile\nconst path = await uploadMessageImage(path, file)","handlingStrategy":"validation","validationCode":"const MAX = 6_000_000\nif (image.size > MAX) {\n  toast.error(`Image must be under 6MB — yours is ${(image.size / 1e6).toFixed(1)}MB`)\n  return\n}","typeGuard":"const isValidMessageImage = (f: File): boolean =>\n  f.type.startsWith(\"image/\") && f.size <= 6_000_000","tryCatchPattern":"try {\n  await uploadMessageImage(path, image)\n} catch (e) {\n  if (e instanceof Error && e.message.includes(\"less than 6MB\")) {\n    // prompt user to compress; not a system failure\n  } else { throw e }\n}","preventionTips":["Compress/resize images client-side (canvas re-encode) before upload.","Warn in the picker UI using the same 6MB threshold so users never hit the throw.","Convert HEIC originals to JPEG to stay under the cap."],"tags":["image","file-size","validation","message-images"],"backgroundTag":"file-size-limit-exceeded","analyzedSha":"81328b61d2a4ab597a7a057be70e785cf756d9f8","analyzedAt":"2026-08-27T19:24:42.689Z","schemaVersion":2},"datasetVersion":"2026-08-28T00:17:15.603Z"}