Svelte/SvelteKit中如何基于可写值返回含数据库数据的派生函数
问题核心
getTypography函数内部的异步操作没有正确返回结果——.then()回调里的return无法传递到函数外部,导致derived store拿到的是undefined。另外derived支持直接返回Promise,Svelte会自动解析其结果,只要调整异步逻辑的写法即可解决问题。
修改后的store.js代码
import { writable, derived } from 'svelte/store'; import axios from 'axios'; // 补全axios导入 const baseAPI = '你的API基础地址'; // 替换为实际API地址 export async function getData(endpoint){ try { const res = await axios.get(`${baseAPI}${endpoint}`); return res.data; } catch (e) { console.error('获取数据失败:', e); throw e; // 抛出错误让上层处理 } } // 改为async函数,用await处理异步逻辑,直接返回Promise async function getTypography(lang){ try { const texts = await getData('/language'); const typography = texts.payload; return filterTypography(typography, lang); } catch (error) { console.error('处理语言数据失败:', error); return []; // 返回空数组作为默认值,避免页面显示undefined } } // 用map简化数组处理逻辑 function filterTypography(typography, lang){ return typography.map(element => ({ keyword: element.keyword, value: element[lang] })); } export const key = writable('en'); export const updateKey = (lang) => { key.set(lang); }; // derived接收异步函数,返回的Promise会被Svelte自动解析 export const data = derived(key, async ($key) => { return await getTypography($key); });
修改后的+page.svelte代码
<script> import { key, data, updateKey } from '$lib/store.js'; function changeLang(lang){ console.log("切换语言:", lang); updateKey(lang); } $: console.log("当前语言:", $key); </script> <!-- 用{#await}处理异步数据的加载状态 --> {#await $data} <p>加载中...</p> {:then processedData} <pre>{JSON.stringify(processedData, null, 2)}</pre> {:catch error} <p>加载失败: {error.message}</p> {/await} <button on:click={() => changeLang('dk')}>切换到丹麦语</button> <button on:click={() => changeLang('en')}>切换到英语</button>
关键修改点说明
- 异步逻辑标准化:把
getTypography改为async函数,用await替代.then()链式调用,让函数直接返回包含处理后数据的Promise,确保derived能正确捕获异步结果。 - 数组处理简化:用
Array.map替代forEach手动构建数组,代码更简洁高效。 - 错误处理完善:在
getData中抛出错误,上层try/catch捕获后返回默认值,避免页面显示undefined;页面中通过{#await}块展示加载、成功、失败三种状态,提升体验。
内容的提问来源于stack exchange,提问作者adeab
相关产品推荐
相关产品推荐

