Promise未兑现时的错误处理:离线状态无法捕获异常问题
问题分析与解决方案
你的代码存在几个关键问题,导致离线时无法正确捕获错误和读取缓存:
- catch块存在未定义变量错误:当离线时,
fetch会直接抛出网络错误,try块里的response变量根本没被赋值,进入catch后你直接访问response.headers和data.cache会触发新的引用错误,导致整个catch逻辑执行失败,自然看不到提示。 - 没有实现实际的缓存存储逻辑:你只是尝试检查响应的
cache头,但离线时连响应都拿不到,而且也没把成功请求的数据提前存在本地(比如localStorage),根本没数据可读取。 - 错误处理不完整:
fetch只有在网络错误时才会reject,如果返回4xx/5xx的HTTP错误,它不会抛出异常,你需要手动判断response.ok来处理这类情况。
修正后的代码
确保逻辑包裹在async函数内(因为使用了await),同时实现缓存读写逻辑:
async function fetchWeather() { const grad = input.value ? input.value : "zagreb"; const contentEl = document.getElementById("content"); const cacheKey = `weather_${grad}`; // 用城市名作为缓存键,区分不同城市数据 try { const response = await fetch( `https://api.weatherapi.com/v1/forecast.json?key=bdbf7197ebc24abbb15104932220407&q=${grad}&aqi=yes` ); // 处理HTTP错误(比如404城市不存在、500服务器错误) if (!response.ok) { throw new Error('请求失败'); } const data = await response.json(); if (data.error) { contentEl.innerHTML = `<p id="nodata">No data for the requested city</p>`; return; } // 请求成功时,将数据存入localStorage作为缓存 localStorage.setItem(cacheKey, JSON.stringify(data)); // 渲染最新数据 dayTime(data); let rezultat = `<p id="location">${data.location.name}, ${data.location.country}, ${data.location.localtime}</p><ul id="lista">`; rezultat += weatherConditions(data); rezultat += temperatura(data); rezultat += cloudCover(data); rezultat += uvZracenje(data); rezultat += "</ul>"; contentEl.innerHTML = rezultat; } catch (err) { // 捕获网络错误或其他异常,尝试读取本地缓存 const cachedData = localStorage.getItem(cacheKey); if (cachedData) { // 有缓存时,渲染缓存数据并提示无网络 const data = JSON.parse(cachedData); dayTime(data); let rezultat = `<p id="nointernet">No internet connection - showing cached data</p>`; rezultat += `<p id="location">${data.location.name}, ${data.location.country}, ${data.location.localtime}</p><ul id="lista">`; rezultat += weatherConditions(data); rezultat += temperatura(data); rezultat += cloudCover(data); rezultat += uvZracenje(data); rezultat += "</ul>"; contentEl.innerHTML = rezultat; } else { // 无缓存时,直接提示无网络且无数据 contentEl.innerHTML = `<p id="nointernet">No internet connection and no cached data available</p>`; } } }
关键改进点
- 用
localStorage存储每个城市的缓存数据,通过带城市名的键区分不同城市的缓存 - catch块优先读取本地缓存,有缓存则渲染并提示使用缓存,无缓存则提示无网络且无数据
- 增加
response.ok判断,处理HTTP状态码错误的情况 - 提前获取DOM元素,避免重复查询DOM提升性能
内容的提问来源于stack exchange,提问作者dean89
相关产品推荐
相关产品推荐

