dashboards

Compare original and translation side by side

🇺🇸

Original

English
🇨🇳

Translation

Chinese

Dashboards

仪表板

Dashboards are shared by the whole organization — there is no private one, so anything you add or change, everyone sees. Each holds ordered cards:
FieldWhat it is
measure
One numeric measure, fully qualified:
crm_deals.amount
.
segmentId
A segment whose rows the card counts, or —
filter
the card's own conditions (segment filter syntax). Never both.
joinPaths
The way to each other cube a condition or the breakdown reads:
{ "crm_companies": "crm_deals.crm_companies" }
.
breakdown
Optional dimension: the card shows its top groups instead of one number.
visualization
How a breakdown shows:
bars
(default),
columns
,
donut
,
table
.
title
Shown instead of the measure's name.
position
Order on the dashboard, ascending.
A card stores the question, never the answer. How to pick a metric, scope it, and compute its value is the metrics skill — read it before adding a card or reporting what one shows.
整个组织共享仪表板——不存在私有仪表板,因此你添加或修改的任何内容,所有人都会看到。每个仪表板都包含按顺序排列的 卡片:
字段含义
measure
一个数值型 measure,使用完整限定名:
crm_deals.amount
。
segmentId
卡片所统计的 segment 所包含的行,或——
filter
卡片自身的 conditions(segment 筛选语法)。两者绝不可同时使用。
joinPaths
condition 或 breakdown 读取其他各个 cube 时所用的路径:
{ "crm_companies": "crm_deals.crm_companies" }
。
breakdown
可选的 dimension:卡片显示排名靠前的分组,而不是单个数值。
visualization
breakdown 的展示方式:
bars
(默认)、
columns
、
donut
、
table
。
title
替代 measure 名称显示。
position
仪表板中的顺序,按升序排列。
卡片存储的是问题,而不是答案。如何选择指标、限定范围并计算其值属于 metrics skill 的范畴——在添加卡片或报告卡片所显示的内容之前,应先阅读该 skill。

Calling the tools

调用工具

json
// Dashboards
api_read   { "resource": "dashboards", "params": { "fields": "id,name,description" } }
api_write  { "resource": "dashboards", "data": { "name": "Sales", "description": "…" } }
api_write  { "resource": "dashboards", "id": "<dashboard id>", "data": { "name": "…" } }
api_delete { "resource": "dashboards", "id": "<dashboard id>" }

// Cards — flat, not under the dashboard: list ONE dashboard's with a filter
api_read   { "resource": "dashboard-cards", "params": { "filter": "dashboardId == \"<dashboard id>\"", "pageSize": 200 } }
api_read   { "resource": "dashboard-cards", "id": "<card id>" }
api_write  { "resource": "dashboard-cards", "data": { "dashboardId": "…", "measure": "…" } }
api_write  { "resource": "dashboard-cards", "id": "<card id>", "data": { "title": "…" } }
api_delete { "resource": "dashboard-cards", "id": "<card id>" }
The record always goes under
data
. Dashboards list oldest first — the first is the one people land on; cards come back by
position
.
api_details({ resource: "dashboard-cards", operation: "create" })
is the authority on the body. Reading needs Viewer; any write needs Member — a
403
means the user's role can't change dashboards.
json
// Dashboards
api_read   { "resource": "dashboards", "params": { "fields": "id,name,description" } }
api_write  { "resource": "dashboards", "data": { "name": "Sales", "description": "…" } }
api_write  { "resource": "dashboards", "id": "<dashboard id>", "data": { "name": "…" } }
api_delete { "resource": "dashboards", "id": "<dashboard id>" }

// Cards — flat, not under the dashboard: list ONE dashboard's with a filter
api_read   { "resource": "dashboard-cards", "params": { "filter": "dashboardId == \"<dashboard id>\"", "pageSize": 200 } }
api_read   { "resource": "dashboard-cards", "id": "<card id>" }
api_write  { "resource": "dashboard-cards", "data": { "dashboardId": "…", "measure": "…" } }
api_write  { "resource": "dashboard-cards", "id": "<card id>", "data": { "title": "…" } }
api_delete { "resource": "dashboard-cards", "id": "<card id>" }
记录必须放在
data
下。仪表板列表按最早创建的优先排序——第一个就是用户进入时默认看到的仪表板;卡片则按
position
返回。
api_details({ resource: "dashboard-cards", operation: "create" })
是请求体(body)的权威依据。读取需要 Viewer 角色;任何写入都需要 Member 角色——
403
表示用户的角色无权更改仪表板。

Reading a dashboard

读取仪表板

Find it by name (
filter: "name == \"Sales\""
), list its cards, and for each card the user cares about compute its value as the metrics skill describes — scope from
segmentId
or
filter
, join hints from the segment's paths and then the card's
joinPaths
, breakdown from
breakdown
. Report each card by its
title
(or the measure's title), its value, and what it's counted over.
按名称查找仪表板(
filter: "name == \"Sales\""
),列出其卡片;对于用户关心的每张卡片,按照 metrics skill 的说明计算其值——范围来自
segmentId
或
filter
,join 路径提示先来自 segment 的 paths,然后来自卡片的
joinPaths
,breakdown 则来自
breakdown
。按每张卡片的
title
(或 measure 的 title)、其值以及统计范围来报告卡片。

Adding a card

添加卡片

  1. List the dashboard's cards. If the same measure with the same scope is already there, point to it instead of adding a twin.
  2. Pick the metric and scope with the metrics skill: a numeric measure; a segment rooted at the measure's cube, or conditions, or nothing; a join path per other cube read; no condition on a measure or on a cube the rows have many of.
  3. Write it.
    dashboardId
    and
    measure
    are required; add
    segmentId
    or
    filter
    ,
    joinPaths
    ,
    breakdown
    ,
    visualization
    ,
    title
    as needed. Omit
    position
    to append.
    The server checks that the dashboard and segment exist, that the measure is a numeric measure, the breakdown a dimension, every condition names a
    member
    that exists, and that segment and filter aren't both set — a
    400
    lists every problem at once; fix them all, don't resend unchanged. It does not check the segment's root, measure conditions, fan-out, or
    joinPaths
    : those save fine and the app shows the card as unavailable.
  4. Read it back and compute its value, so the user sees what the card shows — and a broken card is caught now, not by them.
  1. 列出该仪表板的卡片。 如果已经存在 measure 和范围都相同的卡片,应指向现有卡片,而不是再添加一个重复项。
  2. 使用 metrics skill 选择指标和范围: 一个数值型 measure;以 measure 所在 cube 为根的 segment,或 conditions,或不设置任何范围;为每个要读取的其他 cube 设置一条 join path;不要在 measure 上设置 condition,也不要在当前行存在多条关联记录的 cube 上设置 condition。
  3. 写入。
    dashboardId
    和
    measure
    为必填项;按需添加
    segmentId
    或
    filter
    ,以及
    joinPaths
    、
    breakdown
    、
    visualization
    、
    title
    。省略
    position
    即追加到末尾。
    服务器会检查仪表板和 segment 是否存在、measure 是否为数值型 measure、breakdown 是否为 dimension、每个 condition 是否指定了存在的
    member
    ,以及是否未同时设置 segment 和 filter——
    400
    会一次列出所有问题;应将它们全部修复,不要不作修改就重新发送。服务器不会检查 segment 的根、measure conditions、fan-out 或
    joinPaths
    :这些内容仍可顺利保存,但应用会把卡片显示为 unavailable。
  4. 回读并计算其值,这样用户就能看到卡片显示的内容——同时可以立即发现损坏的卡片,而不是留给用户之后发现。

Changing a card

更改卡片

Send only the fields that change.
null
clears
title
,
segmentId
,
breakdown
,
visualization
;
filter
and
joinPaths
are replaced whole, so start from a fresh read.
  • Filter → segment:
    { "segmentId": "…", "filter": {} }
    . Segment → filter:
    { "segmentId": null, "filter": { … } }
    .
  • Dropping a condition or the breakdown on another cube: drop its
    joinPaths
    entry too, unless something else on the card still reads that cube.
  • Reorder: a
    position
    between the new neighbours' (
    1.5
    between
    1
    and
    2
    ).
  • Move: set
    dashboardId
    ; without
    position
    it goes last.
The server checks only what the update names: retitling doesn't re-validate the rest.
仅发送发生变化的字段。
null
会清除
title
、
segmentId
、
breakdown
和
visualization
;
filter
和
joinPaths
会被整体替换,因此应先进行一次全新的读取。
  • Filter → segment:
    { "segmentId": "…", "filter": {} }
    。 Segment → filter:
    { "segmentId": null, "filter": { … } }
    。
  • 移除另一个 cube 上的 condition 或 breakdown 时:也应移除其对应的
    joinPaths
    条目,除非卡片上的其他内容仍会读取该 cube。
  • 重新排序: 设置一个位于新相邻卡片之间的
    position
    (
    1
    和
    2
    之间的
    1.5
    )。
  • 移动: 设置
    dashboardId
    ;不设置
    position
    时会移到末尾。
服务器仅检查更新中明确指定的字段:仅修改标题不会重新验证其余内容。

Why a card is unavailable or looks wrong

卡片为何显示 unavailable 或数值看起来不正确

The model and segments change under cards — nothing repairs them, and a segment or cube can be deleted without touching the cards that use it. Read the card (and its segment), then check in the app's order:
  1. Metric gone —
    measure
    not in
    meta
    .
  2. Segment gone —
    segmentId
    doesn't resolve.
  3. Field gone — a condition's member (the card's or a dynamic segment's), the breakdown, or a static segment's
    segment_…
    cube isn't in
    meta
    .
  4. Condition on a measure — in the card's or a dynamic segment's filter.
  5. Join gone — a hop in
    joinPaths
    or the segment's paths the model no longer declares.
  6. Condition on a fan-out — a condition on a cube the rows have many of.
Fix it with an update (repoint to the renamed member, drop the condition, switch scope), or say what has to change in the model. A number that's flagged by nothing but looks wrong: the other join route, a static segment not re-snapshotted, a string value spelled differently from the stored one, a fanned-out breakdown, or stale data (
metadata.lastRefreshTime
).
模型和 segment 会在卡片存在期间发生变化——系统不会自动修复它们;即使 segment 或 cube 被删除,也不会影响引用它们的卡片。读取卡片(及其 segment),然后按应用中的顺序检查:
  1. 指标已不存在——
    measure
    不在
    meta
    中。
  2. Segment 已不存在——
    segmentId
    无法解析。
  3. 字段已不存在——condition 的
    member
    (卡片自身或 dynamic segment 中的 member)、breakdown,或 static segment 的
    segment_…
    cube 不在
    meta
    中。
  4. Condition 作用于 measure——位于卡片或 dynamic segment 的 filter 中。
  5. Join 已不存在——
    joinPaths
    或 segment paths 中的某个 hop 已不再被模型声明。
  6. Condition 作用于 fan-out——condition 位于当前行存在多条关联记录的 cube 上。
通过更新进行修复(重新指向已重命名的 member、移除 condition、切换范围),或者说明模型必须做出哪些更改。如果某个数值没有触发任何异常提示,却看起来不正确,原因可能是另一条 join 路径、static segment 尚未重新生成快照、字符串值的拼写与已存储的值不同、发生 fan-out 的 breakdown,或数据已过期(
metadata.lastRefreshTime
)。

Creating, renaming, deleting dashboards

创建、重命名和删除仪表板

  • Create:
    name
    (1–255 chars), optional
    description
    . Check for a namesake first and ask if one exists. Everyone sees it — don't create one just to try something.
  • Rename:
    name
    /
    description
    only.
  • Delete a card: name it back (title or measure, scope, dashboard) and get a yes.
  • Delete a dashboard: it removes every card on it. List them, tell the user how many and which, and that the whole organization loses them, then ask for an explicit yes for this dashboard.
No undo for any delete. A card or dashboard you created yourself in a failed attempt is no exception — say so and ask before deleting it.
  • 创建:
    name
    (1–255 个字符),
    description
    可选。先检查是否存在同名仪表板;如果存在,则向用户询问。所有人都会看到它——不要只是为了试验而创建一个。
  • 重命名: 只能修改
    name
    和
    description
    。
  • 删除卡片: 先向用户复述待删除卡片的信息(title 或 measure、scope、dashboard),并获得明确同意。
  • 删除仪表板: 它会删除其上的每一张卡片。列出这些卡片,告知用户卡片数量及具体是哪些,并说明整个组织都将失去它们,然后针对该仪表板获得明确的 yes。
任何删除操作都不可撤销。即使是您在失败尝试中自行创建的卡片或仪表板,也不例外——应说明这一点,并在删除前征求同意。