IT博客汇
  • 首页
  • 精华
  • 技术
  • 设计
  • 资讯
  • 扯淡
  • 权利声明
  • 登录 注册

    Use Synchronous Data Fetching to Speed Up My Gallery Page

    Lynan发表于 2024-01-11 06:20:24
    love 0

    I have a gallery page in my blog directory, hosted by Plesk. Built from vite + react boilerplate, it’s a very simple SPA.

    Why

    Before this, my gallery page works like this:

    It’s a SPA, so runtime files need to load and initiate first. When page document was downloaded and parsed, the browser started loading <link> files and after our needed JavaScript files were downloaded and executed.

    I have the data fetching logic like this:

    index.jsx
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    const [list, setList] = useState([]);
    const [loaded, setLoaded] = useState(false);

    const getData = async () => {
    const response = await (
    await fetch("https://api.lynan.cn/gallery-list")
    ).json();
    const data = response.data.list;
    setList(data);
    setLoaded(true);
    };

    useEffect(() => {
    getData();
    }, []);

    This process could take a lot of time (due to the very limited resources the CMS service can use).

    Besides, I want to make minimum adjustments to make it faster.

    How

    To address this issue and improve the performance of the gallery page, I made the following adjustments:

    1. Generated a static JSON data file to store the gallery data. This file is created or updated whenever new data is added.
    src/api/photo/content-types/photo/lifecycles.js
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    17
    18
    19
    20
    const generateJSON = async () => {
    try {
    const list = await strapi.db.query("api::photo.photo").findMany({
    orderBy: { id: "desc" },
    });
    fs.writeFileSync(
    "./public/photos.js",
    `var photos = ${JSON.stringify(list)}`
    );
    } catch (error) {}
    };

    module.exports = {
    afterUpdate(event) {
    generateJSON();
    },
    afterCreate(event) {
    generateJSON();
    },
    };
    1. Loaded the JSON file using a <script> tag in the HTML head, making the data easily accessible as a global variable on the window object.
    index.html
    1
    2
    3
    4
    <head>
    ...
    <script src="https://nextcms.lynan.cn/public/photos.js"></script>
    </head>
    1. Updated the data fetching logic in the React component to directly use the referenced JSON data.
    index.jsx
    1
    const [list, setList] = useState(window.photos || []);

    By implementing these adjustments, the need for the getData function and useEffect hook was eliminated, resulting in a noticeable improvement in the page loading speed. Additionally, the gallery page can now be hosted by a static files server (like NGINX) without requiring an extra runtime environment (like Node.js).

    Why Not

    use JSON-P

    JSONP, or JSON-P (JSON with Padding), is a historical JavaScript technique for requesting data by loading a <script> element, which is an element intended to load ordinary JavaScript.

    To use JSON-P, we need to wrap our data into a callback function, and declare our callback function before loading the data file.

    index.html
    1
    2
    3
    4
    5
    6
    <script>
    function fetchDataCallback(data) {
    console.log(data);
    }
    </script>
    <script src="https://api.lynan.cn/test-jsonp.js"></script>
    testjsonp.js
    1
    2
    3
    4
    5
    6
    fetchDataCallback([
    {
    id: 182,
    title: null,
    },
    ]);

    It’s no better than just putting the data into a global variable in this case.

    use SSR

    Follow the guide from next.js, then we still need a Node.js environment to run next.js service.

    use SSG

    We can also use next.js to do SSG (Static Site Generation). Use getStaticProps to insert data into a page template.

    We need to rebuild static files when data updates.

    To use SSR or SSG both require some extra modifications on the gallery project, so they are not my first consideration. But in different cases, SSR/SSG might be a good option.

    And

    Potential Disadvantages

    It’s important to note that the approach of using a global variable to store the data may expose the data file and could potentially lead to a security risk.

    Conclusion

    The adjustments made to optimize the gallery page have significantly improved its performance, and while the alternative approaches seems not so good for me, the current solution works great.



沪ICP备19023445号-2号
友情链接