Remix 中的默认服务器端值会发生什么情况?

发布于 2025-01-13 01:37:05 字数 1513 浏览 2 评论 0原文

我正在使用以下钩子(取自在ReactJS中获取视口/窗口高度)。我已经调整了该钩子,以便可以在服务器上呈现它(通过在条件内限制对 window 的访问)。

import { useState, useEffect } from 'react';

function getWindowDimensions() {
  if (typeof window !== 'undefined') {
    const { innerWidth: width, innerHeight: height } = window;
    return {
      width,
      height
    };
  }
  return { width: -1, height: -1 }
}

export default function useWindowDimensions() {
  const [windowDimensions, setWindowDimensions] = useState(getWindowDimensions());

  useEffect(() => {
    function handleResize() {
      setWindowDimensions(getWindowDimensions());
    }

    window.addEventListener('resize', handleResize);
    return () => window.removeEventListener('resize', handleResize);
  }, []);

  return windowDimensions;
}

我注意到一些有趣/令人困惑的事情:

  1. 当在服务器上呈现时,挂钩确实返回 {width: -1, height: -1} 的默认值
  2. 这些值似乎是由父组件观察到的。示例:
export default function FooComponent() {
    const { width, height} = useWindowDimensions();
    // this invariant fails
    invariant(width > -1 && height > -1);

}

但是,如果我在 invariant(...) 行下方插入 console.log(width, height),我永远不会看到 -1, -1 在浏览器控制台中。

所以看起来 invariant 仅在服务器上触发,而 console.log 仅在客户端上运行。有人能解释一下这是怎么回事吗?即,为什么该组件不遵守默认的服务器端值?

I'm using the following hook (taken from Get viewport/window height in ReactJS). I've adapted the hook so it can be rendered on the server (by gating access to window inside a conditional).

import { useState, useEffect } from 'react';

function getWindowDimensions() {
  if (typeof window !== 'undefined') {
    const { innerWidth: width, innerHeight: height } = window;
    return {
      width,
      height
    };
  }
  return { width: -1, height: -1 }
}

export default function useWindowDimensions() {
  const [windowDimensions, setWindowDimensions] = useState(getWindowDimensions());

  useEffect(() => {
    function handleResize() {
      setWindowDimensions(getWindowDimensions());
    }

    window.addEventListener('resize', handleResize);
    return () => window.removeEventListener('resize', handleResize);
  }, []);

  return windowDimensions;
}

I've noticed something interesting / confusing:

  1. The hook does return the default values of {width: -1, height: -1} when it is rendered on the server
  2. These values are seemingly observed by parent component. Example:
export default function FooComponent() {
    const { width, height} = useWindowDimensions();
    // this invariant fails
    invariant(width > -1 && height > -1);

}

However, if I insert a console.log(width, height), below the invariant(...) line, I never see -1, -1 in the browser console.

So it looks like the invariant is only triggered on the server and console.log is only run on the client. Can someone explain what's going on here? I.e, why does the component not observe default server side values?

如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

扫码二维码加入Web技术交流群

发布评论

需要 登录 才能够评论, 你可以免费 注册 一个本站的账号。

评论(1

时光病人 2025-01-20 01:37:05

它与 https://github.com/zertosh/invariant 不变吗?

自述文件中的注释指出,如果 process.env.NODE_ENV 不是 Production,即使条件为 true,它也会抛出异常。

对于只渲染客户端的组件,SergioDXA(顶级混音贡献者)提供了一个很酷的包: https://github.com/sergiodxa/remix-utils#clientonly

Is it invariant from https://github.com/zertosh/invariant ?

A note on the readme says that if process.env.NODE_ENV is not production it'll throw even if condition is true.

And for component that should only render client side, there is a cool package by SergioDXA (a top remix contributor) : https://github.com/sergiodxa/remix-utils#clientonly

~没有更多了~
我们使用 Cookies 和其他技术来定制您的体验包括您的登录状态等。通过阅读我们的 隐私政策 了解更多相关信息。 单击 接受 或继续使用网站,即表示您同意使用 Cookies 和您的相关数据。
原文