@webstudio-is/react-sdk 0.28.0 → 0.29.0

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.
@@ -9,18 +9,24 @@ const isAbsoluteUrl = (href) => {
9
9
  return false;
10
10
  }
11
11
  };
12
+ const isAbsoluteUrlRemix = (href) => /^[a-z+]+:\/\//i.test(href) || href.startsWith("//");
12
13
  const wrapLinkComponent = (BaseLink) => {
13
- const Component = forwardRef(
14
- ({ href = "", ...props }, ref) => isAbsoluteUrl(href) ? /* @__PURE__ */ jsx("a", {
15
- ...props,
16
- href,
17
- ref
18
- }) : /* @__PURE__ */ jsx(Link, {
14
+ const Component = forwardRef(({ href = "", ...props }, ref) => {
15
+ const isAbsolute = isAbsoluteUrl(href);
16
+ const willRemixTryToTreatAsAbsoluteAndCrash = isAbsolute === false && isAbsoluteUrlRemix(href);
17
+ if (isAbsolute || willRemixTryToTreatAsAbsoluteAndCrash) {
18
+ return /* @__PURE__ */ jsx("a", {
19
+ ...props,
20
+ href: willRemixTryToTreatAsAbsoluteAndCrash ? "" : href,
21
+ ref
22
+ });
23
+ }
24
+ return /* @__PURE__ */ jsx(Link, {
19
25
  ...props,
20
26
  to: href,
21
27
  ref
22
- })
23
- );
28
+ });
29
+ });
24
30
  Component.displayName = BaseLink.displayName;
25
31
  return Component;
26
32
  };
@@ -32,18 +32,24 @@ const isAbsoluteUrl = (href) => {
32
32
  return false;
33
33
  }
34
34
  };
35
+ const isAbsoluteUrlRemix = (href) => /^[a-z+]+:\/\//i.test(href) || href.startsWith("//");
35
36
  const wrapLinkComponent = (BaseLink) => {
36
- const Component = (0, import_react2.forwardRef)(
37
- ({ href = "", ...props }, ref) => isAbsoluteUrl(href) ? /* @__PURE__ */ (0, import_jsx_runtime.jsx)("a", {
38
- ...props,
39
- href,
40
- ref
41
- }) : /* @__PURE__ */ (0, import_jsx_runtime.jsx)(import_react.Link, {
37
+ const Component = (0, import_react2.forwardRef)(({ href = "", ...props }, ref) => {
38
+ const isAbsolute = isAbsoluteUrl(href);
39
+ const willRemixTryToTreatAsAbsoluteAndCrash = isAbsolute === false && isAbsoluteUrlRemix(href);
40
+ if (isAbsolute || willRemixTryToTreatAsAbsoluteAndCrash) {
41
+ return /* @__PURE__ */ (0, import_jsx_runtime.jsx)("a", {
42
+ ...props,
43
+ href: willRemixTryToTreatAsAbsoluteAndCrash ? "" : href,
44
+ ref
45
+ });
46
+ }
47
+ return /* @__PURE__ */ (0, import_jsx_runtime.jsx)(import_react.Link, {
42
48
  ...props,
43
49
  to: href,
44
50
  ref
45
- })
46
- );
51
+ });
52
+ });
47
53
  Component.displayName = BaseLink.displayName;
48
54
  return Component;
49
55
  };
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@webstudio-is/react-sdk",
3
- "version": "0.28.0",
3
+ "version": "0.29.0",
4
4
  "description": "Webstudio JavaScript / TypeScript API",
5
5
  "author": "Webstudio <github@webstudio.is>",
6
6
  "homepage": "https://webstudio.is",
@@ -47,12 +47,12 @@
47
47
  "mitt": "^3.0.0",
48
48
  "nanostores": "^0.7.1",
49
49
  "warn-once": "^0.1.1",
50
- "@webstudio-is/asset-uploader": "^0.28.0",
51
- "@webstudio-is/css-data": "^0.28.0",
52
- "@webstudio-is/icons": "^0.28.0",
53
- "@webstudio-is/image": "^0.28.0",
54
- "@webstudio-is/prisma-client": "^0.28.0",
55
- "@webstudio-is/project-build": "^0.28.0"
50
+ "@webstudio-is/asset-uploader": "^0.29.0",
51
+ "@webstudio-is/css-data": "^0.29.0",
52
+ "@webstudio-is/icons": "^0.29.0",
53
+ "@webstudio-is/image": "^0.29.0",
54
+ "@webstudio-is/prisma-client": "^0.29.0",
55
+ "@webstudio-is/project-build": "^0.29.0"
56
56
  },
57
57
  "exports": {
58
58
  "import": "./lib/index.js",
@@ -16,6 +16,11 @@ const isAbsoluteUrl = (href: string) => {
16
16
  }
17
17
  };
18
18
 
19
+ // Remix's check for absolute URL copied from here:
20
+ // https://github.com/remix-run/react-router/blob/react-router-dom%406.8.0/packages/react-router-dom/index.tsx#L423-L424
21
+ const isAbsoluteUrlRemix = (href: string) =>
22
+ /^[a-z+]+:\/\//i.test(href) || href.startsWith("//");
23
+
19
24
  type Props = Omit<ComponentProps<"a">, "href"> & { href?: string };
20
25
 
21
26
  type Ref = ElementRef<"a">;
@@ -25,13 +30,27 @@ export const wrapLinkComponent = (
25
30
  ) => {
26
31
  // We're not actually wrapping BaseLink (no way to wrap with Remix's Link),
27
32
  // but this is still useful because we're making sure that props/ref types are compatible
28
- const Component = forwardRef<Ref, Props>(({ href = "", ...props }, ref) =>
29
- isAbsoluteUrl(href) ? (
30
- <a {...props} href={href} ref={ref} />
31
- ) : (
32
- <Link {...props} to={href} ref={ref} />
33
- )
34
- );
33
+ const Component = forwardRef<Ref, Props>(({ href = "", ...props }, ref) => {
34
+ const isAbsolute = isAbsoluteUrl(href);
35
+
36
+ // This is a workaround for a bug in Remix: https://github.com/remix-run/remix/issues/5440
37
+ // It has a buggy absolute URL detection, which gives false positives on value like "//" or "http://"
38
+ // and causes entire app to crash
39
+ const willRemixTryToTreatAsAbsoluteAndCrash =
40
+ isAbsolute === false && isAbsoluteUrlRemix(href);
41
+
42
+ if (isAbsolute || willRemixTryToTreatAsAbsoluteAndCrash) {
43
+ return (
44
+ <a
45
+ {...props}
46
+ href={willRemixTryToTreatAsAbsoluteAndCrash ? "" : href}
47
+ ref={ref}
48
+ />
49
+ );
50
+ }
51
+
52
+ return <Link {...props} to={href} ref={ref} />;
53
+ });
35
54
 
36
55
  // This is the only part that we use from BaseLink at runtime
37
56
  Component.displayName = BaseLink.displayName;