@flowselections/actie-mail-kwekers-erp-mathot 1.0.18 → 1.0.20

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
@@ -1 +1 @@
1
- {"version":3,"file":"HuisstijlSettingsCard.d.ts","sourceRoot":"","sources":["../../../src/components/settings/HuisstijlSettingsCard.tsx"],"names":[],"mappings":"AA0BA,wBAAgB,qBAAqB,gCA8PpC"}
1
+ {"version":3,"file":"HuisstijlSettingsCard.d.ts","sourceRoot":"","sources":["../../../src/components/settings/HuisstijlSettingsCard.tsx"],"names":[],"mappings":"AA+BA,wBAAgB,qBAAqB,gCAkPpC"}
@@ -3,14 +3,17 @@ import { useEffect, useRef, useState } from "react";
3
3
  import { Card, CardContent, CardDescription, CardHeader, CardTitle, Button, Input, Label, supabase, toast, useAuth, } from "@flowselections/core";
4
4
  import { Palette, Upload, Trash2, Image as ImageIcon, Loader2 } from "lucide-react";
5
5
  import { resolveBranding, isValidHex, DEFAULT_PRIMARY } from "../../lib/branding";
6
+ import { uploadBrandingLogo, deleteBrandingLogo } from "../../lib/branding.functions";
6
7
  const BUCKET = "offer-branding";
7
- const TEN_YEARS = 60 * 60 * 24 * 365 * 10;
8
8
  const MAX_BYTES = 2 * 1024 * 1024;
9
9
  const ALLOWED = ["image/png", "image/jpeg", "image/webp", "image/svg+xml"];
10
- /** Haalt het opslagpad uit een (ondertekende) storage-URL van deze bucket. */
11
- function storagePathFromUrl(url) {
12
- const m = url.match(new RegExp(`/${BUCKET}/([^?]+)`));
13
- return m?.[1] ? decodeURIComponent(m[1]) : null;
10
+ /** Vertaalt technische opslagfouten naar begrijpelijke tekst. */
11
+ function friendlyError(message) {
12
+ const m = (message || "").toLowerCase();
13
+ if (m.includes("bucket not found")) {
14
+ return "De opslagmap voor logo's bestond nog niet en kon niet automatisch worden aangemaakt. Vraag een beheerder om de map \"offer-branding\" aan te maken in Supabase Storage, of vul hieronder een logo-link in.";
15
+ }
16
+ return message || "Uploaden mislukt";
14
17
  }
15
18
  export function HuisstijlSettingsCard() {
16
19
  const { isAdmin } = useAuth();
@@ -50,11 +53,6 @@ export function HuisstijlSettingsCard() {
50
53
  if (error)
51
54
  throw error;
52
55
  };
53
- const removeOldFile = async (url) => {
54
- const path = url && url.includes(`/${BUCKET}/`) ? storagePathFromUrl(url) : null;
55
- if (path)
56
- await supabase.storage.from(BUCKET).remove([path]);
57
- };
58
56
  const onFile = async (file) => {
59
57
  if (!ALLOWED.includes(file.type)) {
60
58
  toast.error("Alleen PNG, JPG, WEBP of SVG");
@@ -65,30 +63,21 @@ export function HuisstijlSettingsCard() {
65
63
  return;
66
64
  }
67
65
  setUploading(true);
68
- const previous = state.logo_url;
69
66
  try {
70
- const ext = (file.name.split(".").pop() || "png").toLowerCase().replace(/[^a-z0-9]/g, "");
71
- const path = `logo/${crypto.randomUUID()}.${ext}`;
72
- const { error: upErr } = await supabase.storage
73
- .from(BUCKET)
74
- .upload(path, file, { contentType: file.type, upsert: false });
75
- if (upErr)
76
- throw upErr;
77
- const { data: signed, error: signErr } = await supabase.storage
78
- .from(BUCKET)
79
- .createSignedUrl(path, TEN_YEARS);
80
- if (signErr || !signed?.signedUrl)
81
- throw signErr ?? new Error("Kon geen logo-link maken");
82
- const absolute = signed.signedUrl.startsWith("http")
83
- ? signed.signedUrl
84
- : `${import.meta.env?.VITE_SUPABASE_URL ?? ""}${signed.signedUrl}`;
85
- await persistLogoUrl(absolute);
86
- setState((s) => ({ ...s, logo_url: absolute }));
87
- await removeOldFile(previous);
67
+ const form = new FormData();
68
+ form.append("file", file);
69
+ if (state.logo_url)
70
+ form.append("previousUrl", state.logo_url);
71
+ const result = await uploadBrandingLogo({ data: form });
72
+ const url = result?.url;
73
+ if (!url)
74
+ throw new Error("Kon geen logo-link maken");
75
+ await persistLogoUrl(url);
76
+ setState((s) => ({ ...s, logo_url: url }));
88
77
  toast.success("Logo geüpload");
89
78
  }
90
79
  catch (e) {
91
- toast.error(e?.message ?? "Uploaden mislukt");
80
+ toast.error(friendlyError(e?.message ?? ""));
92
81
  }
93
82
  finally {
94
83
  setUploading(false);
@@ -101,7 +90,9 @@ export function HuisstijlSettingsCard() {
101
90
  try {
102
91
  await persistLogoUrl("");
103
92
  setState((s) => ({ ...s, logo_url: "" }));
104
- await removeOldFile(previous);
93
+ if (previous.includes(`/${BUCKET}/`)) {
94
+ await deleteBrandingLogo({ data: { url: previous } }).catch(() => undefined);
95
+ }
105
96
  toast.success("Logo verwijderd");
106
97
  }
107
98
  catch (e) {