You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

setInterval调用Promise首次正常后续报Unexpected identifier错误

问题产生原因

核心错误出在setInterval的参数传递逻辑:

  • 代码中写setInterval(app.playerNow().then(data => { app.dataOnAir(data); }), 5000)时,JS引擎执行到这行代码就会立刻调用app.playerNow(),将该异步方法返回的Promise对象作为第一个参数传给setInterval,而非传入「需要定时执行的函数」。
  • 首次调用能正常返回结果,是因为这行代码初始化运行时就立刻触发了第一次playerNow()请求,能正常走then回调执行后续逻辑。
  • 从第二次定时触发开始,setInterval会尝试将传入的Promise对象当作可执行函数运行,Promise本身不是可执行函数,再加上原代码没有处理请求失败的分支,异常状态的Promise会抛出未捕获错误,最终触发[object Promise] "Uncaught SyntaxError: Unexpected identifier"报错。

额外隐患:原代码中playerNow方法仅在response.ok为真时返回数据,请求失败时会返回值为undefined的Promise,后续执行dataOnAir时也可能触发参数异常问题。

修复方案
  • 将setInterval的第一个参数改为包裹异步请求逻辑的回调函数,保证定时器每次触发时才执行请求,而非初始化时就执行请求把返回值当回调传入。
  • 增加异常捕获逻辑,覆盖网络错误、接口状态异常、JSON解析错误等边界场景,避免未捕获的Promise错误抛到全局。
  • 增加空值判断,避免请求失败返回空值时,后续执行业务逻辑报错。

修复后的完整代码如下:

var app = {
    init : function() {
        app.start();
    },

    start : function() {      
        // 传入可执行回调函数,定时器触发时才执行内部逻辑
        setInterval(async () => {
            try {
                const data = await app.playerNow();
                if (data) {
                    app.dataOnAir(data);
                }
            } catch (err) {
                console.error('定时获取播放数据失败:', err);
            }
        }, 5000);
    },

    playerNow : async function() {
        let url = "https://www.radiomatese.it/script/app/details.php";
        let response = await fetch(url);
        if(response.ok){
            let data = await response.json();
            return data;
        }
        // 请求状态异常时抛出错误,交由外层捕获处理
        throw new Error(`接口请求失败,状态码:${response.status}`);
    },
    dataOnAir : function(data){ 
        // 原有业务逻辑
    }
}

内容的提问来源于stack exchange,提问作者Massimiliano Comunale

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.08.27 10:06:36