MST

星途 面试题库

面试题:SvelteKit 路由与服务器端渲染及数据预取的深度结合

在 SvelteKit 项目中,如何利用路由系统实现高效的服务器端渲染(SSR)和数据预取?请详细描述在页面路由和 API 路由场景下,如何根据路由参数动态决定预取哪些数据,以及如何在 SSR 过程中避免数据获取的重复请求,提高整体性能。
46.9万 热度难度
前端开发Svelte

知识考点

AI 面试

面试题答案

一键面试

页面路由中的 SSR 和数据预取

  1. 设置 +page.server.js 文件
    • 在 SvelteKit 中,每个页面路由对应的目录下可以创建 +page.server.js 文件。这个文件专门用于服务器端逻辑,包括数据预取。例如,假设我们有一个 src/routes/blog/[slug].svelte 页面,用于展示特定博客文章,在 src/routes/blog/[slug]/+page.server.js 中:
    import { error } from '@sveltejs/kit';
    import { getBlogPost } from '$lib/api';
    
    export async function load({ params }) {
        const { slug } = params;
        const post = await getBlogPost(slug);
        if (!post) {
            throw error(404, 'Blog post not found');
        }
        return { post };
    }
    
    • 这里的 load 函数接收一个参数对象,其中 params 包含了路由参数(如 slug)。通过这些参数,我们可以动态决定预取哪些数据。在这个例子中,根据 slug 从 API 中获取特定的博客文章。
  2. 避免重复请求
    • SvelteKit 会自动缓存 load 函数的结果,避免在同一请求周期内的重复请求。例如,如果在一个页面中有多个组件依赖于相同的数据预取逻辑,SvelteKit 只会执行一次 load 函数。
    • 对于不同请求之间的缓存,可以考虑使用服务器端缓存机制,如 node - cache 或者在数据库层面设置适当的缓存策略。如果数据更新频率较低,可以在数据库查询时先检查缓存中是否有数据,若有则直接返回缓存数据。

API 路由场景下的 SSR 和数据预取

  1. 创建 +server.js 文件
    • 在 API 路由目录(如 src/routes/api/[id]/+server.js)下创建 +server.js 文件。例如,假设这个 API 用于获取特定用户的数据:
    import { error } from '@sveltejs/kit';
    import { getUser } from '$lib/api';
    
    export async function GET({ params }) {
        const { id } = params;
        const user = await getUser(id);
        if (!user) {
            throw error(404, 'User not found');
        }
        return new Response(JSON.stringify({ user }));
    }
    
    • GET 函数(也可以是 POSTPUT 等其他 HTTP 方法对应的函数)中,通过 params 获取路由参数,根据参数动态获取数据。这里根据 id 获取特定用户的数据,并返回响应。
  2. 避免重复请求
    • 与页面路由类似,在 API 路由中可以在服务器端实现缓存机制。例如,可以使用 node - cache 来缓存 API 的响应结果。在处理请求时,先检查缓存中是否有对应的数据,如果有则直接返回缓存数据,否则执行数据获取逻辑,并将结果存入缓存。
    import NodeCache from 'node - cache';
    const myCache = new NodeCache();
    
    export async function GET({ params }) {
        const { id } = params;
        const cachedUser = myCache.get(`user_${id}`);
        if (cachedUser) {
            return new Response(JSON.stringify({ user: cachedUser }));
        }
        const user = await getUser(id);
        if (!user) {
            throw error(404, 'User not found');
        }
        myCache.set(`user_${id}`, user);
        return new Response(JSON.stringify({ user }));
    }
    
    • 这样可以显著提高 API 的性能,避免对相同数据的重复获取。同时,要注意缓存的过期时间设置,以确保数据的及时性。