面试题答案
一键面试异常处理机制
- try - catch 块:
- 在
async
函数内部使用try - catch
块来捕获异步操作中抛出的错误。例如:
async function asyncTask() { try { let result1 = await someAsyncFunction1(); let result2 = await someAsyncFunction2(result1); // 更多异步操作 } catch (error) { // 记录错误信息 console.error('捕获到错误:', error); // 可以在这里进行一些恢复操作,比如返回默认值 return defaultResult; } }
- 这样可以捕获
someAsyncFunction1
和someAsyncFunction2
执行过程中抛出的错误,确保错误不会导致整个系统崩溃。
- 在
- Promise.catch:
- 对于不使用
async/await
的Promise
链式调用,可以在链的末尾使用.catch
方法捕获错误。例如:
someAsyncFunction1() .then(result1 => someAsyncFunction2(result1)) .then(result2 => { // 处理结果 }) .catch(error => { console.error('捕获到错误:', error); // 进行错误处理 });
- 对于不使用
- 全局异常处理:
- 在 Node.js 应用中,可以使用
process.on('uncaughtException')
来捕获未被try - catch
或.catch
处理的异常。
process.on('uncaughtException', (error) => { console.error('全局捕获到未处理异常:', error); // 可以进行紧急日志记录,甚至优雅停机等操作 });
- 同时,对于未被处理的 Promise 拒绝,可以使用
process.on('unhandledRejection')
。
process.on('unhandledRejection', (reason, promise) => { console.error('全局捕获到未处理的 Promise 拒绝:', reason, 'Promise:', promise); });
- 在 Node.js 应用中,可以使用
- 错误记录:
- 使用日志库(如
winston
或pino
)来记录错误信息。这些库可以将错误信息记录到文件、控制台等不同的目标,方便调试。例如,使用winston
:
const winston = require('winston'); const logger = winston.createLogger({ level: 'error', format: winston.format.json(), transports: [ new winston.transport.Console(), new winston.transport.File({ filename: 'error.log' }) ] }); async function asyncTask() { try { // 异步操作 } catch (error) { logger.error('发生错误:', error.message, { stack: error.stack }); return defaultResult; } }
- 使用日志库(如
提升网络服务可靠性
- 应对网络波动:
- 重试机制:在网络请求失败时,使用
Promise
实现重试逻辑。例如:
async function retryAsyncFunction(func, maxRetries = 3, delay = 1000) { let retries = 0; while (retries < maxRetries) { try { return await func(); } catch (error) { retries++; if (retries === maxRetries) { throw error; } await new Promise(resolve => setTimeout(resolve, delay)); } } } async function networkRequest() { // 网络请求函数 return new Promise((resolve, reject) => { // 模拟网络请求 setTimeout(() => { Math.random() > 0.5? resolve('成功') : reject('失败'); }, 1000); }); } retryAsyncFunction(networkRequest).then(result => { console.log('最终结果:', result); }).catch(error => { console.error('经过重试仍失败:', error); });
- 重试机制:在网络请求失败时,使用
- 超时处理:
- 使用
Promise.race
来实现超时机制。例如:
async function timeoutAsyncFunction(func, timeout = 5000) { return Promise.race([ func(), new Promise((_, reject) => { setTimeout(() => { reject(new Error('操作超时')); }, timeout); }) ]); } async function longRunningNetworkRequest() { return new Promise((resolve) => { setTimeout(() => { resolve('成功'); }, 8000); }); } timeoutAsyncFunction(longRunningNetworkRequest, 5000).then(result => { console.log('结果:', result); }).catch(error => { console.log('错误:', error.message); });
- 使用
通过上述方法,使用 Promise
和 async/await
能够构建全面且健壮的异常处理机制,并提升网络服务在复杂情况下的可靠性。