关于 preview-offline-scope
`preview-offline-scope` 是面向 Dataverse 移动应用配置者的只读诊断技能,可估算离线配置下设备的数据下载量和同步频率。它会检查配置漂移,并按表统计行数与缓存大小。
主要功能
- 01验证离线配置快照及漂移
- 02按作用范围估算各表行数
- 03依据列类型估算缓存大小
- 04估算每日数据传输量
- 05只读运行,不修改配置
适用场景
- 01设置离线配置后进行最终检查
- 02分配配置前评估用户数据流量
- 03调整列列表时比较缓存影响
安装
复制下面的命令,在终端中运行。
npx skills add https:/ / github.com/ microsoft/ power-platform-skills --skill preview-offline-scope安装后在 Claude Code 中输入/preview-offline-scope确认已加载。
详细介绍
共享说明:shared-instructions.md — 请先阅读。
预览离线范围
只读诊断。告诉你“如果现在将此配置文件推送给用户,他们的设备会下载哪些内容,以及会以多频繁的频率重新同步。”不会进行任何修改。
适用于以下操作之前:
/setup-offline-profile,用于最终检查/assign-offline-profile(避免用户对数据流量上限感到意外)/edit-offline-profile,用于评估列列表变更的影响
读取任何项目或执行任何命令之前,请应用
app-working-directory.md。
为本次直接调用解析一个绝对路径的 working_dir,或要求所有者提供子项目的根目录。所有 Shell 调用、文件读取和重试都必须使用该根目录,以及相同的已解析环境/租户。读取
<working_dir>/offline-profile.json;提供的配置文件 ID 必须与快照匹配,然后才能验证。上下文缺失或冲突时,返回 NEEDS_CONTEXT。
工作流
- 验证项目 + 定位配置文件 → 2. 运行 verify(漂移检查)→ 3. 按表统计行数 → 4. 估算缓存大小 → 5. 报告
步骤 1 — 验证项目 + 定位配置文件
与 /edit-offline-profile 步骤 1 相同。从 offline-profile.json 或 $ARGUMENTS --profile-id 读取 profileId。不要从 power.config.json 读取配置文件元数据;该文件由 pa app init 管理。
cd -- '<working_dir>' || { echo "BLOCKED: cannot enter working_dir" >&2; exit 1; }
environment_id=$(node -p "require('./power.config.json').environmentId || ''") || {
echo "BLOCKED: unreadable power.config.json" >&2; exit 1;
}
if [ -z "$environment_id" ]; then
echo "NEEDS_CONTEXT: selected app has no environmentId" >&2; exit 1;
fi
node "${PLUGIN_ROOT}/scripts/resolve-environment.js" "$environment_id" --no-cache --require-tenant
记录 <envUrl> 和 <tenantId>,并要求它们与所有者身份匹配。
在验证、行数统计、身份读取和重试时,显式传入该租户。
步骤 2 — 运行 verify
遥测检查点:verify_offline_profile_snapshot
cd -- '<working_dir>' || { echo "BLOCKED: cannot enter working_dir" >&2; exit 1; }
node "${PLUGIN_ROOT}/scripts/verify-offline-profile.js" <envUrl> \
--project-root '<working_dir>' --tenant-id "<tenantId>"
如果 status: drift,请原样呈现漂移列表。后续估算仍然有参考价值,但要标明实时配置文件与 offline-profile.json 不一致——建议重新运行 /setup-offline-profile 或 /edit-offline-profile 以协调一致。
步骤 3 — 按表统计行数(应用范围筛选条件)
遥测检查点:count_offline_profile_rows
对于配置文件中的每个表,运行 count 查询,并应用运行时会使用的相同筛选条件:
recorddistributioncriteria | recordsownedby* 标志 | 有效筛选条件 |
|---|---|---|
| 1(所有记录) | 不适用 | ?$count=true&$top=0(整个表) |
| 2 + 我 | recordsownedbyme=true | ?$count=true&$top=0&$filter=_ownerid_value eq <current-user-id> |
| 2 + 团队 | recordsownedbymyteam=true | 近似值:_ownerid_value 属于(当前用户团队拥有的 ID);估算时,使用 teamroles_association 中的团队计数 |
| 2 + 业务部门 | recordsownedbymybusinessunit=true | ?$count=true&$top=0&$filter=_owningbusinessunit_value eq <current-bu-id> |
| 0(仅相关记录) | 不适用 | 无法独立估算——取决于父记录。报告 ~depends on parent counts。 |
对于当前用户/当前业务部门筛选条件,仅在此技能中通过 scripts/dataverse-request.js,针对已解析的 <envUrl> 调用 Dataverse WhoAmI 来解析身份,并从同一受保护根目录传入 --tenant-id "<tenantId>"。如果调用失败,请将受影响的范围报告为 unknown — current user/BU unavailable,不要因此阻止整个预览。不要指望 scripts/resolve-environment.js 或 auth.config.json.environment 提供 UserId/BusinessUnitId。
对于每个表:
cd -- '<working_dir>' || { echo "BLOCKED: cannot enter working_dir" >&2; exit 1; }
node "${PLUGIN_ROOT}/scripts/dataverse-request.js" <envUrl> GET \
"<entitysetname>?\$count=true&\$top=0&<scope-filter>" --tenant-id "<tenantId>"
上限为 5000(Dataverse 非聚合计数上限)。结果恰好为 5000 时,在报告中添加前缀 ≥。
步骤 4 — 缓存大小估算
遥测检查点:estimate_offline_cache_size
每行字节数的粗略估算值(可配置;有真实同步基准测试数据后请替换为实测值):
| 列类型 | 字节数 |
|---|---|
| Uniqueidentifier | 40 |
| 字符串(平均 80 个字符) | 100 |
| 整数 / 十进制数 | 12 |
| 日期时间 | 28 |
| 布尔值 / 状态 / 状况 | 4 |
| 选项集(仅选项值) | 8 |
| 备注(平均 500 个字符) | 600 |
| 查找(仅外键) | 40 |
| 图像(仅 URL + 缩略图元数据——完整图像的字节数请参阅下方注释) | 200 |
| 文件(URL + 名称元数据) | 200 |
对于每个表,计算:estimatedBytesPerRow = sum(bytesForEach column in selectedcolumns)。然后计算 tableTotalBytes = rows × estimatedBytesPerRow。
每个表的同步开销:每个 syncintervalinminutes 间隔会触发一次增量查询 → 假设典型日期内约有 20% 的总行数被访问。dailyTransferBytes = (totalBytes × 0.20 × intervalsPerDay)。
步骤 5 — 报告
═════════════════════════════════════════════════════════════
Offline Scope Preview — <profileName>
═════════════════════════════════════════════════════════════
Drift status: ok | drift (see verify output)
Per-table breakdown:
| Table | Scope | Rows | Cols | Est. bytes | Sync (min) |
|--------------------|----------------|----------|------|------------|------------|
| chnl_region | All records | 12 | 7 | 4 KB | 60 |
| chnl_product | All records | 312 | 13 | 280 KB | 60 |
| chnl_rmprofile | Org+me | 1 | 10 | 1 KB | 10 |
| chnl_store | Org+me | 84 | 17 | 112 KB | 10 |
| chnl_storevisit | Org+me | 412 | 13 | 220 KB | 5 |
| chnl_order | Org+me | 156 | 14 | 95 KB | 10 |
| chnl_orderline | Related only | ~depends | 11 | ~150 KB | 10 |
Total initial download : ~860 KB (5000-rows cap not hit)
Daily transfer estimate: ~12 MB / device / day (assuming 20% delta rate)
Sync intervals per day:
chnl_storevisit (5 min) → 288 syncs/day ⚠ high
chnl_store (10 min) → 144 syncs/day
chnl_order (10 min) → 144 syncs/day
chnl_rmprofile (10 min) → 144 syncs/day
chnl_region (60 min) → 24 syncs/day
chnl_product (60 min) → 24 syncs/day
Concerns:
- chnl_storevisit at 5 min could exceed mobile data caps in low-signal areas
(battery drain too). Consider 10 min unless 5 min is mission-critical.
Image / File bytes NOT counted by these heuristics. The metadata (URL +
thumbnail size) IS counted at 200 bytes/row, but the JPEG/file payload
itself transfers separately at runtime sync time. To estimate image
storage, multiply expected non-empty image rows × average JPEG size
(typically 10–500 KB per thumbnail).
状态代码(最后一行)
DONE— 已生成估算值,无需关注DONE_WITH_CONCERNS: <list>— 已生成估算值,但标记了相关问题(同步频率高、行数接近上限、检测到漂移等)NEEDS_CONTEXT: <missing>— 没有可用于估算的配置文件BLOCKED: <reason>— 身份验证或查询失败
注释
此技能有意提供的是估算级别的结果,而非精确值。字节数估算是经验值;实际缓存大小取决于 Dataverse 的存储布局、JSON 序列化以及每台设备的缓存压缩。此类数字适用于比较(一个范围与另一个范围相比、一组列与另一组列相比),不适用于绝对容量规划。
如需精确数据,唯一可信来源是运行时同步日志——只有在应用部署且 RM 已登录后才能获取。