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

无需外部服务,如何本地追踪Chrome扩展使用时长并触发指定事件?

本地追踪Chrome扩展累计使用时长并触发事件的成熟方案

你的思路方向是对的,基于chrome.storage做本地存储是最直接且轻量的方案,下面是标准化的优化实现,解决计时准确性、后台休眠、重复触发等问题:

核心设计思路

通过监听浏览器激活状态、结合定时任务更新累计时长,用chrome.storage持久化关键数据,达到阈值后触发目标事件。核心存储字段:

  • totalUsageHours: 累计使用小时数(浮点型,保留精度)
  • lastActiveTimestamp: 上次记录活动的时间戳(用于断点续计时)
  • hasTriggeredEvent: 是否已触发目标事件(避免重复执行)

分步实现(Manifest V3为例)

1. 配置权限(manifest.json)

确保扩展拥有必要权限:

{
  "manifest_version": 3,
  "name": "Usage Tracker",
  "version": "1.0",
  "background": {
    "service_worker": "background.js"
  },
  "permissions": ["storage", "alarms", "notifications", "windows"],
  "icons": {
    "48": "icons/icon48.png"
  }
}

2. 后台逻辑实现(background.js)

// 目标触发时长(n小时,自行修改)
const TARGET_HOURS = 5;
// 定时同步间隔(分钟,避免频繁读写storage)
const SYNC_INTERVAL_MINUTES = 1;

let currentActiveTimestamp = null;

// 初始化存储数据(扩展安装/更新时)
chrome.runtime.onInstalled.addListener(() => {
  chrome.storage.local.set({
    totalUsageHours: 0,
    lastActiveTimestamp: null,
    hasTriggeredEvent: false
  });
});

// 浏览器启动时恢复计时状态
chrome.runtime.onStartup.addListener(() => {
  chrome.storage.local.get(['lastActiveTimestamp'], (result) => {
    if (result.lastActiveTimestamp) {
      currentActiveTimestamp = result.lastActiveTimestamp;
    }
  });
});

// 监听窗口焦点变化,记录激活/失活时长
chrome.windows.onFocusChanged.addListener((windowId) => {
  const now = Date.now();
  if (windowId !== chrome.windows.WINDOW_ID_NONE) {
    // 浏览器激活,开始计时
    currentActiveTimestamp = now;
    chrome.storage.local.set({ lastActiveTimestamp: now });
  } else {
    // 浏览器失活,计算并累加时长
    if (currentActiveTimestamp) {
      updateTotalUsage(currentActiveTimestamp, now);
      currentActiveTimestamp = null;
      chrome.storage.local.set({ lastActiveTimestamp: null });
    }
  }
});

// 定时同步时长(解决Service Worker休眠导致的计时中断)
chrome.alarms.create('syncUsage', { periodInMinutes: SYNC_INTERVAL_MINUTES });
chrome.alarms.onAlarm.addListener((alarm) => {
  if (alarm.name === 'syncUsage' && currentActiveTimestamp) {
    const now = Date.now();
    updateTotalUsage(currentActiveTimestamp, now);
    currentActiveTimestamp = now;
    chrome.storage.local.set({ lastActiveTimestamp: now });
  }
});

// 更新累计时长并检查是否触发事件
function updateTotalUsage(startTime, endTime) {
  const durationMs = endTime - startTime;
  const durationHours = durationMs / (1000 * 60 * 60);
  
  chrome.storage.local.get(['totalUsageHours'], (result) => {
    const newTotal = (result.totalUsageHours || 0) + durationHours;
    chrome.storage.local.set({ totalUsageHours: newTotal }, () => {
      checkTriggerCondition(newTotal);
    });
  });
}

// 检查时长是否达标并触发事件
function checkTriggerCondition(totalHours) {
  chrome.storage.local.get(['hasTriggeredEvent'], (result) => {
    if (!result.hasTriggeredEvent && totalHours >= TARGET_HOURS) {
      // 替换为你的目标事件逻辑,比如弹出通知、注入脚本等
      chrome.notifications.create({
        type: 'basic',
        iconUrl: 'icons/icon48.png',
        title: '使用时长达标',
        message: `累计使用已达${totalHours.toFixed(2)}小时,触发专属事件!`
      });
      
      // 标记事件已触发,防止重复执行
      chrome.storage.local.set({ hasTriggeredEvent: true });
    }
  });
}

关键优化点

  • 后台休眠处理:用chrome.alarms定期唤醒Service Worker,避免Chrome休眠后台导致计时中断
  • 存储读写优化:减少不必要的chrome.storage操作,仅在状态变化或定时同步时写入
  • 重复触发防护:通过hasTriggeredEvent标记确保事件只执行一次
  • 断点续计时:记录lastActiveTimestamp,浏览器重启后可恢复之前的计时状态
  • 精度控制:用浮点型存储累计时长,保留足够精度,避免整数计时的误差

可选扩展

  • 若需要跨设备同步时长,将chrome.storage.local替换为chrome.storage.sync(注意sync的存储容量限制,此处数据量极小,完全适配)
  • 可添加重置功能,通过扩展 popup 提供重置累计时长的选项
  • 可对计时场景做更精细的过滤,比如仅统计特定标签页激活的时长(结合chrome.tabs.onActivated事件)

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

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.07.17 07:47:34