面试题答案
一键面试设计思路
- 数据缓存:使用内存缓存来存储从 API 获取的商品数据,避免重复请求相同数据。
- 更新策略:提供手动更新和自动定时更新机制。手动更新适用于特定场景触发,如用户手动刷新;自动定时更新用于在一定时间间隔后更新数据,确保数据的实时性。
- 模块解耦:通过 Svelte 自定义 store 来管理数据,使得不同模块可以订阅和使用商品数据,而不需要直接依赖其他模块。各模块之间通过 store 进行数据交互,实现解耦。
- 性能优化:在数据获取时采用防抖和节流技术,减少不必要的 API 请求。同时,对缓存的数据进行合理的管理,如设置过期时间,避免数据长期占用内存。
关键技术点
- Svelte 自定义 store:利用 Svelte 的
writable
和derived
等函数来创建自定义 store。writable
用于创建可写的 store,derived
可基于其他 store 创建衍生 store。 - API 调用:使用
fetch
或第三方库(如axios
)来进行 API 调用。在调用时,可结合async/await
来处理异步操作。 - 缓存管理:创建一个对象来存储缓存数据,并为每个缓存数据设置过期时间。在获取数据时,先检查缓存是否有效,若有效则直接返回缓存数据。
- 防抖和节流:可使用 Lodash 库中的
debounce
和throttle
函数来控制 API 请求频率。
代码架构示例
<script>
import { writable, derived } from'svelte/store';
import { throttle } from 'lodash';
// 商品数据缓存对象
let productCache = {};
// 缓存过期时间(毫秒)
const CACHE_EXPIRATION = 60 * 1000;
// 用于存储商品数据的 writable store
const productStore = writable({});
// 自动定时更新
const autoUpdateInterval = 10 * 1000;
let autoUpdateTimer;
const fetchProducts = async () => {
try {
// 从多个 API 获取数据
const api1Response = await fetch('api1-url');
const api1Data = await api1Response.json();
const api2Response = await fetch('api2-url');
const api2Data = await api2Response.json();
// 整合数据
const combinedData = {
...api1Data,
...api2Data
};
// 更新缓存
productCache = {
data: combinedData,
timestamp: new Date().getTime()
};
// 更新 store
productStore.set(combinedData);
} catch (error) {
console.error('Error fetching products:', error);
}
};
// 手动更新函数
const updateProducts = throttle(() => {
fetchProducts();
}, 1000);
// 初始化时获取数据
if (!productCache.data || new Date().getTime() - productCache.timestamp > CACHE_EXPIRATION) {
fetchProducts();
} else {
productStore.set(productCache.data);
}
// 启动自动更新
autoUpdateTimer = setInterval(() => {
updateProducts();
}, autoUpdateInterval);
// 衍生 store,可用于特定模块的定制数据
const filteredProductStore = derived(productStore, ($productStore) => {
// 例如,过滤出价格大于 100 的商品
return Object.values($productStore).filter(product => product.price > 100);
});
// 在组件销毁时清除定时器
$: onDestroy(() => {
clearInterval(autoUpdateTimer);
});
</script>
{#if $productStore}
<ul>
{#each Object.entries($productStore) as [key, product]}
<li>{product.name} - {product.price}</li>
{/each}
</ul>
{/if}
<button on:click={updateProducts}>手动更新</button>
在上述代码中:
productStore
是一个writable
store,用于存储商品数据。fetchProducts
函数负责从多个 API 获取数据并整合,同时更新缓存和 store。updateProducts
函数使用throttle
进行防抖处理,控制手动更新频率。filteredProductStore
是一个derived
store,用于展示过滤后的商品数据,体现了不同模块可基于基础数据定制自己所需的数据。- 缓存管理通过
productCache
对象和CACHE_EXPIRATION
过期时间实现。 - 自动更新通过
setInterval
结合updateProducts
函数实现,并在组件销毁时清除定时器。