我们的API服务器返回带有错误响应的JSON数据。我找不到处理错误处理方法的JSON数据的标准方法。我目前的解决方案是这个。它正在工作,但我想处理catch()方法中的错误而不是then();
let url = 'http://localhost:8080';
let data = {'field': 'value'};
fetch(url, {
method: 'PUT',
body: JSON.stringify(data),
credentials: 'same-origin',
mode: 'cors',
headers: {
'content-type': 'application/json',
'accept': 'application/json'
}
})
.then(res => {
if (res.status == 400) {
return res.json();
} else if (!res.ok) {
throw (res);
} else {
return res.json();
}
}).then(data => {
if (data.status == 400) {
throw (data);
}
return (data);
}).catch(err => {
if (err.status == 400) {
throw this.handleError(err);
} else {
throw new Error(`HTTP Error ${err.status}`);
}
});
这是来自服务器的JSON响应的示例。
{
"parameters": {
"type": {
"isEmpty": "Field is required and cannot be empty"
},
"from": {
"isEmpty": "Field is required and cannot be empty"
},
"to": {
"isEmpty": "Field is required and cannot be empty"
}
},
"title": "Invalid parameter",
"type": "/api/doc/invalid-parameter",
"status": 400,
"detail": "Invalid parameter"
}
我会在fetch周围创建一个瘦的包装器,它会抛出> = 400个响应,解析后的body会解析成功的响应。
function parse(res) {
const contentType = res.headers.get('Content-Type') || '';
const isJson = contentType.includes('application/json');
return isJson ? res.json() : res;
}
async function throwOnError(res) {
if (res.status >= 400) {
const err = new Error(res.statusText || 'Internal Server Error');
err.status = res.status;
const parsedRes = await parse(res);
err.body = parsedRes;
throw err;
}
return res;
}
async function fetchWrapper({ method, url, data, headers }) {
const combinedHeaders = {
'Content-Type': 'application/json',
'Accept': 'application/json',
};
if (headers) {
Object.assign(combinedHeaders, headers);
}
const options = {
credentials: 'same-origin',
mode: 'cors',
method,
headers: combinedHeaders,
};
if (data) {
options.body = JSON.stringify(data);
}
return fetch(url, options)
.then(throwOnError)
.then(parse);
}
const queryParams = (params) =>
Object.keys(params)
.filter(k => params[k] !== null && typeof params[k] !== 'undefined')
.map(k => `${encodeURIComponent(k)}=${encodeURIComponent(params[k])}`)
.join('&');
export const appendUrlParams = (url, params) => (params ? `${url}?${queryParams(params)}` : url);
export const $get = (url, params, { ...options }) =>
fetchWrapper({ method: 'GET', url: appendUrlParams(url, params), ...options });
export const $del = (url, params, { ...options }) =>
fetchWrapper({ method: 'DELETE', url: appendUrlParams(url, params), ...options });
export const $post = (url, data, { ...options }) =>
fetchWrapper({ method: 'POST', url, data, ...options });
export const $put = (url, data, { ...options }) =>
fetchWrapper({ method: 'PUT', url, data, ...options });
EG
async function fetchSomething() {
try {
const res = await $get('someurl');
// Do something with successful `res`.
} catch (err) {
console.error(err);
// err.status -> the status of the response
// err.body -> the body of the response
}
}
或者使用then / catch如果这是你的偏好。