dsh-aw-viz: Converting ActivityWatch habit data into model-readable metrics

前言

做 DeepSeek Harness(DSH)智能体开发时,常见的一个场景是:会话里挂着一个助手,但它并不知道你这一天在屏幕上花了什么时间。你要它针对「开会太多、碎片太多」给点建议,它只能靠你自己复述。已有的屏幕使用时间工具大多只给人类看图表,或者口径各不相同,模型拿不到可读、有定义的指标。

dsh-aw-viz 解决的就是这一步:把你本机 ActivityWatch 的原始记录聚合成一组有明确定义的指标,并通过一个只读工具暴露给模型,让同一会话里的智能体能读到数字,再给出针对你用屏方式的具体建议。插件是第三方维护者 woshijing1991-cloud 写的,定位是只读、本地、不联网。它只负责「让数据可读」,判断和建议仍由模型做。

下面介绍它是什么、怎么装、怎么用。

这是什么

一句话定位:一个面向 DSH 桌面版(Harness 0.2.x,Web frontend)的 ActivityWatch 习惯面板,自带五个视角和模型工具。仓库名是 woshijing1991-cloud/dsh-aw-viz,README 中的版本号是 0.1.0,许可证是 MIT,package.json 的 engines.node 要求 >=20。

它和「又一个看板」的区别在于:面板每打开一次都会向本地 aw-server 取事件并在内存里聚合,插件自己不落盘、不存历史,请求只发往 loopback。所以它读的是你 ActivityWatch 已有的库,而不是另起一套存储。

需要先说清楚边界:插件默认端点是 http://127.0.0.1:5600(aw-server / aw-server-rust 的 REST API)。ActivityWatch 必须先装好并在运行,面板是它的只读视图,自己不采集任何数据。如果 ActivityWatch 没跑,插件不会编数字:/api/health 会返回 200 且 body 为 {"ok": false, "error": "fetch failed"},summary 路由返回 500,界面显示空状态。

核心功能

README 把指标分成六组,每组都标了外部参照,不是自造口径。

时间分配:按类别的占比、Top 应用、PC 与手机拆分。参照 RescueTime 的 productivity-pulse / category-share 惯例。

碎片化:分段时长中位数、每小时有效活动中的切换次数、小于 30 秒的分段占比。参照 Mark et al. 2008 的《The Cost of Interrupted Work》和 Leroy 2009 的 attention residue。这里特意用中位数而不是均值,因为少数几个长分段会把均值抬高,反而掩盖「一段典型连续时间」的样子。

专注:最长的同类别不间断区间,以及时长大于等于 25 分钟的区间数量。参照 Newport 的《Deep Work》和约 90 分钟的 ultradian rhythm。具体算法是把同类别的分段合并,间隔不超过 2 分钟算作一次连续块——它衡量的是「你有多长没有被打断」,不是「你觉得多专注」。

节奏:工作日 × 小时的 7×24 热力图和逐日趋势。参照 chronotype 框架和 Digital Wellbeing 的小时视图。

双设备:PC 分钟数 / 手机分钟数 / PC 占比、手机解锁次数。手机解锁次数对应 Apple Screen Time 的 pickups 口径。手机端粒度只到应用级(Android 限制),拿不到应用内的页面。

完整性:断电/离线时段的数量和时长。插件在本地写一个 aw-offline 标记,避免把「没有记录」误当成「没有活动」。

几个容易读错的定义:活跃时间等于窗口事件与「非 AFK 区间」的交集。PC 有 AFK watcher,手机没有,所以手机时间直接按事件时长计。

数据来源方面,插件从不保存使用历史。每次打开面板,它向本地 aw-server 要事件并在内存里聚合;自身不写磁盘,请求只到 loopback,没有出站网络行为。ActivityWatch 自己保留原始数据库,路径取决于你的安装方式,这个仓库不假定也不要求任何特定路径。

接口与模型工具

宿主侧注册了两个只读路由,挂在 basePath(默认 /dsh-aw-viz)下:

GET /dsh-aw-viz/api/summary?days=7   # 汇总所有指标
GET /dsh-aw-viz/api/health           # 探测 aw-server 是否在运行

模型侧另有一个只读工具 aw_habit_report,可以直接在对话里问它要数字:

工具 参数 返回
aw_habit_report days(1–90,默认取配置)、format(text 或 json) 可读摘要或原始指标

安装与启用

前置条件:DSH 桌面版(Harness 0.2.x,Web frontend)、Node 20+、以及一个正在运行且有数据的 ActivityWatch。因为面板的 HTML/JS 是在宿主启动时打进页面的,所以所有安装路径最后都要重启一次应用。

推荐的本地方式是把仓库拉下来当 file: 插件装,让宿主自己写 profile:

git clone https://github.com/woshijing1991-cloud/dsh-aw-viz.git
cd dsh-aw-viz

# 让宿主替你写好 profile(推荐)
dsh plugin --profile <your-profile> add "$(pwd)"

然后重启 DSH。checkout 要放在稳定路径:profile 以 file: 依赖引用它,移动或删除目录会导致 profile 加载失败。

如果 DSH 构建带插件市场且这个包在列表里,也可以直接从市场界面装,再重启。

手动配置

如果你要手工搭 profile,README 提醒三处必须一致:依赖、bundles、以及 cordis.patch.yml 里的 insert 条目。少了 insert 时依赖能加载但永远不会挂载,现象和「装了没反应」一模一样。

~/.dsh/profiles/<profile>/package.json:

{
  "dependencies": {
    "dsh-aw-viz": "file:/absolute/path/to/dsh-aw-viz"
  },
  "dsh": {
    "profile": {
      "bundles": ["dsh-aw-viz"]
    }
  }
}

~/.dsh/profiles/<profile>/cordis.patch.yml:

- insert:
    - id: dsh-aw-viz
      name: 'dsh-aw-viz'
      config:
        activityWatchBase: 'http://127.0.0.1:5600'
        basePath: '/dsh-aw-viz'
        defaultRangeDays: 7

然后:

cd ~/.dsh/profiles/<profile> && pnpm install

再重启 DSH。卸载时删掉 dependencies 条目、dsh.profile.bundles 条目和 insert 块,重新跑 pnpm install,重启。

配置项

profile 配置写入 patch 层,README 给出三个键:

键 默认值 含义
activityWatchBase http://127.0.0.1:5600 本地 aw-server 的基础 URL;ActivityWatch 监听别处时改这个
basePath /dsh-aw-viz 两个路由的 URL 前缀;与其他插件冲突时可改
defaultRangeDays 7 请求未指定 days 时的默认窗口

另外 tools/ 下的可选脚本会用到环境变量(插件运行时不用):AW_BASE 默认同上,AW_DATA_DIR 默认 <repo>/aw-data(脚本写 CSV / JSON / 周报的位置,已 gitignore),AW_TZ_CONFIG 默认 $AW_DATA_DIR/user-tz.json。这些是给导出脚本用的,不是运行时依赖。

挂载方式

插件按宿主自己的 plugin / automation / context 面板同款模式做了两处注册:

部分 槽位 说明
侧边栏条目 sidebar.panellist { id: 'aw-viz', order: 20, label: () => '使用习惯' } 加图标组件;行由宿主渲染,所以字号和 hover 状态与相邻项一致
面板主体 main { key: 'aw-viz' },点击行时用 ctx.layout.selectPanel('aw-viz') 选中

order 的排序是:plugins = 0,automation = 10,本面板 = 20,skills = 31。README 还提到早期版本试过注册进 sidebar.brand.mark(24px 品牌位),但那是图标槽不是列表,已废弃。

典型用法

面板装好后,直接在对话里让模型自己取数即可,不用手工先看图表。比如让它看最近七天并给建议:

用 aw_habit_report 看我最近 7 天的屏幕使用,按时间分配和碎片化两方面给一轮改进建议

如果要原始指标给程序用,可以让 format 返回 json;想在本地脚本里拉汇总,也可以直接请求路由:

GET /dsh-aw-viz/api/summary?days=7

需要先确认 ActivityWatch 是否在线时,调 /api/health 或用 aw_habit_report 看它是否报错即可。

适用场景与注意

适合这样的人:本机已经在跑 ActivityWatch、希望同一会话里的 DSH 助手能读到自己真实用屏数据,而不是听自己口述;并且接受「指标先聚合、建议后生成」这条分工。

有几点要在装之前想清楚。插件以当前 DSH 进程的权限运行,并且通过 file: 依赖引用本地 checkout,所以目录会被宿主加载执行——装之前应当自己通读源码、确认仓库内容与许可证(MIT)符合预期,不要把目录放在不受控的位置。它需要 ActivityWatch 已在运行时才能出数,没跑就只显示空状态。手机端只有应用级粒度。

它也不是官方项目:README 明确写着是 DeepSeek Harness 生态的第三方插件,非官方。

小结

dsh-aw-viz 做的事很窄也很清楚:把你本机 ActivityWatch 的记录聚合成有定义、可读的指标,再通过 aw_habit_report 交给同一会话里的模型,判断和建议仍然由模型做。它不判断你的一天,只保证数字可读、来源可查、行为只读。

目录页:https://www.skillhub.cn/plugins/woshijing1991-cloud/dsh-aw-viz
GitHub:https://github.com/woshijing1991-cloud/dsh-aw-viz

羽毛球分组比赛记分
小程序二维码

欢迎使用《羽毛球分组比赛记分》微信小程序

Xiaoye