是的,对于像同步业务这样的复杂逻辑,封装成 service 是一种良好的实践。这样可以使代码结构更加清晰、模块化,并且便于测试和维护。在 React 应用中,可以将这种复杂的业务逻辑放在一个独立的模块或 service 中,然后通过自定义 hooks 或者直接在组件中调用这个 service。
以下是一个简单的示例,展示如何实现这种封装和调用:
Step 1: 封装 API 调用逻辑
首先,我们需要封装从服务器获取数据的 API 调用逻辑:
// apiService.js
const BASE_URL = 'https://api.example.com';
export async function fetchData() {
const response = await fetch(`${BASE_URL}/data`);
if (!response.ok) {
throw new Error('Network response was not ok');
}
return response.json();
}
Step 2: 封装 SQLite 操作逻辑
然后,我们需要封装 SQLite 的 insert
和 select
逻辑:
// sqliteService.js
import * as SQLite from 'expo-sqlite';
const db = SQLite.openDatabase('app.db');
export function insertData(data) {
return new Promise((resolve, reject) => {
db.transaction(tx => {
tx.executeSql(
'INSERT INTO data (id, value) VALUES (?, ?)',
[data.id, data.value],
(_, result) => resolve(result),
(_, error) => reject(error)
);
});
});
}
export function selectData() {
return new Promise((resolve, reject) => {
db.transaction(tx => {
tx.executeSql(
'SELECT * FROM data',
[],
(_, result) => resolve(result.rows._array),
(_, error) => reject(error)
);
});
});
}
Step 3: 创建同步逻辑的 service
接下来,我们创建一个 service,用于将服务器的数据同步到 SQLite:
// syncService.js
import { fetchData } from './apiService';
import { insertData } from './sqliteService';
export async function syncData() {
try {
const data = await fetchData();
await Promise.all(data.map(item => insertData(item)));
console.log('Data synced successfully');
} catch (error) {
console.error('Failed to sync data:', error);
}
}
Step 4: 使用自定义 Hook 封装业务逻辑
为了在组件中使用同步逻辑,我们可以创建一个自定义 hook:
// useSync.js
import { useState, useEffect } from 'react';
import { syncData } from './syncService';
function useSync() {
const [syncing, setSyncing] = useState(false);
const [error, setError] = useState(null);
useEffect(() => {
async function sync() {
setSyncing(true);
setError(null);
try {
await syncData();
} catch (err) {
setError(err);
} finally {
setSyncing(false);
}
}
sync();
}, []);
return { syncing, error };
}
export default useSync;
Step 5: 在组件中使用自定义 Hook
最后,在组件中使用自定义 hook 来执行同步逻辑:
// SyncComponent.js
import React from 'react';
import useSync from './useSync';
function SyncComponent() {
const { syncing, error } = useSync();
if (syncing) return <div>Syncing data...</div>;
if (error) return <div>Error syncing data: {error.message}</div>;
return <div>Data synced successfully!</div>;
}
export default SyncComponent;
总结
通过以上步骤,我们将复杂的业务逻辑封装在 service 中,并通过自定义 hooks 将这些业务逻辑引入到组件中。这种方式不仅提高了代码的可维护性,还使得业务逻辑更加清晰,组件更加专注于 UI 渲染。
根据你的具体需求,你可以进一步扩展这些模块和 service,加入更多的错误处理、状态管理等功能。希望这个示例能帮助你更好地理解如何在 React 中组织和封装复杂的业务逻辑。