Fetch请求封装与Transform处理
下面是一个完整的fetch请求封装,包含请求和响应的transform处理:
class HttpRequest {
constructor(baseURL = '', timeout = 10000) {
this.baseURL = baseURL;
this.timeout = timeout;
}
/**
* 请求拦截器(请求transform)
* @param {Request} request - 请求对象
* @returns {Request} 处理后的请求
*/
requestInterceptor(request) {
// 在这里可以添加全局请求头、认证token等
request.headers.set('Content-Type', 'application/json');
// request.headers.set('Authorization', `Bearer ${localStorage.getItem('token')}`);
return request;
}
/**
* 响应拦截器(响应transform)
* @param {Response} response - 响应对象
* @returns {Promise} 处理后的响应数据
*/
async responseInterceptor(response) {
// 检查HTTP状态码
if (!response.ok) {
const error = await response.json();
throw new Error(error.message || `HTTP error! status: ${response.status}`);
}
// 根据Content-Type处理不同响应类型
const contentType = response.headers.get('content-type');
if (contentType && contentType.includes('application/json')) {
return response.json();
} else if (contentType && contentType.includes('text/plain')) {
return response.text();
} else {
return response.blob();
}
}
/**
* 发送请求
* @param {string} url - 请求URL
* @param {Object} options - 请求选项
* @returns {Promise} 请求结果
*/
async request(url, options = {}) {
const controller = new AbortController();
const timeoutId = setTimeout(() => controller.abort(), this.timeout);
try {
const fullUrl = this.baseURL + url;
let request = new Request(fullUrl, {
...options,
signal: controller.signal
});
// 请求transform
request = this.requestInterceptor(request);
const response = await fetch(request);
// 响应transform
const data = await this.responseInterceptor(response);
return data;
} catch (error) {
if (error.name === 'AbortError') {
throw new Error('请求超时');
}
throw error;
} finally {
clearTimeout(timeoutId);
}
}
// 封装常用HTTP方法
get(url, params = {}, options = {}) {
const query = new URLSearchParams(params).toString();
const fullUrl = query ? `${url}?${query}` : url;
return this.request(fullUrl, {
...options,
method: 'GET'
});
}
post(url, body = {}, options = {}) {
return this.request(url, {
...options,
method: 'POST',
body: JSON.stringify(body)
});
}
put(url, body = {}, options = {}) {
return this.request(url, {
...options,
method: 'PUT',
body: JSON.stringify(body)
});
}
delete(url, options = {}) {
return this.request(url, {
...options,
method: 'DELETE'
});
}
// 可以添加patch等其他方法
}
// 使用示例
const api = new HttpRequest('https://api.example.com');
// 发送GET请求
api.get('/users', { page: 1, limit: 10 })
.then(data => console.log(data))
.catch(error => console.error(error));
// 发送POST请求
api.post('/users', { name: 'John', age: 30 })
.then(data => console.log(data))
.catch(error => console.error(error));
主要特点
-
请求transform处理:
- 统一设置请求头(如Content-Type、Authorization)
- 可以添加全局请求参数
- 请求超时处理
-
响应transform处理:
- 统一错误处理(HTTP状态码非200-299时抛出错误)
- 根据Content-Type自动解析响应数据(JSON/Text/Blob)
- 可以添加统一的响应数据处理逻辑
-
其他功能:
- 支持常用HTTP方法(GET/POST/PUT/DELETE)
- 支持请求参数自动序列化
- 支持请求超时取消
扩展建议
- 可以添加请求/响应日志记录
- 可以添加请求重试机制
- 可以添加请求缓存功能
- 可以添加更完善的错误分类处理
- 可以添加请求取消功能(使用AbortController)
这个封装提供了良好的扩展性,你可以根据项目需求进一步定制transform逻辑。