Business operation priority and contract review boundaries
The default goal is to complete the AI Table business operations explicitly requested by the user, including queries, creation, updates, synchronization, and other authorized writes. Contract review is an auxiliary scenario, enabled only when the user explicitly requests verification of synthesized JSON, dry-run, parameter validity, Help/Schema, or recovery plans; such requests are read-only by default, and review requirements are not expanded into online business operations. When the user raises both business operations and contract verification, first perform the necessary contract validation according to the real business goal, then continue executing the explicitly authorized business operations.
First distinguish operations, usage, and contract review
When the user only requests review of a return value or a recovery plan, do not execute business operations, and do not extend to upstream write commands as a business task. The discovered goal is based on the user's original message; parameters that the Agent summarizes on its own or passes into the Skill are not new requests, and "verify this reconciliation command" cannot be rewritten as "compare the reconciliation and original creation commands." Preserve the complete atomic path or + Shortcut name that the user is verifying, without synonymous substitution. The original creation command mentioned in the background is not an additional discovery goal.
When reviewing only one command, first obtain the compact Schema of that entry point once, then answer based on this result; do not query background commands in parallel or sequentially, and do not append synonymous entry points, full Schema, or Help. When not published result explain that the structure is not public, and do not infer fields through repeated queries or examples. Only when the user explicitly requests comparison of multiple commands should their respective contracts be queried separately. Help/Schema is a local offline query, and "do not execute online business" does not prohibit it; when the user explicitly prohibits any command, do not query, and explain that the contract has not been verified.
When during review the user requests a next-step read-only command, the answer should first give the complete command based on the current contract and using the original ID/verification key, and explain that it has not yet been executed; immediately after, give the key judgment and prohibited actions, then briefly explain the basis. Do not first unfold the tool process, Schema field table, or lengthy citations, and do not bury the next step at the end of the analysis; when the read-only entry point or parameters cannot be determined, explain the gap and do not guess. When no command is requested, first answer all of the user's safety questions with a brief conclusion: whether replaying writes is allowed, which results should be retained or discarded, and what prerequisites read-only recovery has, then explain as needed; do not leave key prohibited actions until the sectional explanation or the final summary. Clearly distinguish local offline contract verification, receipts provided by the user, and online status that is still unverified: the local Schema can only prove the command contract, and cannot prove that the business has been executed or that the remote status has been verified.
When reviewing only stale cursor recovery, read record-query the "Review only stale cursor recovery" paragraph at the beginning, and focus on explaining the three boundaries: discarding old results, the UNAVAILABLE wait prerequisite, and prohibiting replay writes; do not move on to the actual query process after that Reference, and do not derive write-back permission from differences between old and new results.
The following intent routing takes precedence over the general Schema navigation below. Usage questions and return value reviews for form sharing cannot share a discovery path:
| Request intent | The sole contract query for this request |
|---|---|
| Review return value, recovery plan, failure, or dry-run sample | Put the complete entry currently being verified into dws schema --cli-path "aitable <原入口>" --compact --format jsonas-is; keep +, do not check Help, and do not switch atoms/Shortcuts |
Ask only about the atom form share update syntax |
Query only dws schema --cli-path "aitable form share update" --compact --format json |
| Ask only about the Shortcut syntax | Query only that Shortcut's compact Schema |
Minimal DWS execution contract
- DingTalk business operations only go through
dwsCLI; scripts explicitly published by this Skill can orchestratedwsand complete presigned file uploads. Structured reads use--format jsonand judge results based on actual returns. - Execute known leaves directly. Only when parameters or security semantics are uncertain, read
dws schema --cli-path "aitable <leaf>" --compact --format jsonat most once; only when that compact leaf Schema is inconsistent with the actual Cobra behavior, read the same leaf'sdws aitable <leaf> --help. Exploring commands through parent Help, product Help, or the full Catalog is prohibited. - Do not guess commands, flags, fields, IDs, accounts, or times. Subsequent IDs must come from actual returns; when there are zero hits, multiple candidates, or unclear types, stop and disambiguate.
- Resolving the target, reading context, and final execution must use the same profile; userId, openDingTalkId, or openConversationId must not be reused across organizations. Multi-account organizations use only the explicit
isOrgCurrent=truedefault account; when there is no default account, require the user to specify one, and do not choose the first item, the most recently logged-in, or the most recently used account. - Do not output or record credentials such as tokens, refresh tokens, appSecret, and webhook tokens; when the host has already injected authentication, do not ask for credentials.
- Write operations must match the user's explicit intent. Whether confirmation is required is determined by the final Runtime gate and Schema; when in this round the user has explicitly requested execution and the target and impact of a non-destructive write operation are unambiguous, that explicit instruction is this confirmation, and the first call directly carries the
--yesrequired by Runtime, without first creatingconfirmation_required. File import is a non-idempotent operation, so still follow the Golden Route to trigger the Runtime confirmation gate first, and after confirmation append--yes. Destructive or high-risk actions such as deletion and deactivating automation still require first explaining the object, action, and impact and obtaining independent confirmation. - After writing, verify according to the task result contract; do not claim success based only on the exit code. Partial results, unknown delivery statuses, and failed items must be retained as they are.
- The Runtime Schema is the authoritative source for current capabilities and security semantics; within the same leaf task, read it only once and reuse it. Read leaf Help only when the Schema is missing fields, has unclear meanings, or conflicts with actual execution; invalidate the cache immediately when the version, profile changes, or a contract error occurs.
- Mutation returns, HTTP 200, and exit code 0 are only call receipts, not the final object state. After writing, the affected read cache must be cleared, and an independent read-back must be initiated using the actual returned ID/unique key, without reusing pre-write results.
- Writes to the same Base are serial by default; controlled concurrent writes are allowed only when they are to different Bases, have no data/ID/order dependencies, and failures can be independently read back. Dependency-free read-only calls default to at most 4-way concurrency.
- When a write call times out, the connection is interrupted, or the returned result is unknown, automatic replay as-is is prohibited; check the actual state first. Read-only calls may retry transient errors with an upper limit.
- Structured results may be unified
ok/outcome, oldstatus, or booleansuccessenvelopes; do not assume a fixeddatahierarchy.partial_failurecan be in stdout and return exit code 7; the envelope must be parsed first before determining the execution result. - Returned by file upload:
uploadUrl, token, authorization, signature, etc. are credentials; do not output them, do not write them to logs, and recursively redact them even in structured errors. - When timestamps are displayed to users, convert them to a readable time with a time zone; use the current session time zone by default, and retain the original value as well when necessary.
- When encountering authentication, permission, profile, confirmation, or unknown errors, load only the
dingtalk-sharedcorresponding reference; do not repeatedly guess alternative commands.
Form sharing usage answer contract
After receiving a request that only asks about usage, the first step must immediately actually execute, and only execute, the following corresponding command; even if the user mentions "help/schema", still select by entry point and do not replace it yourself:
form share update:dws schema --cli-path "aitable form share update" --compact --format json+form-share-update:dws schema --cli-path "aitable +form-share-update" --compact --format json
The + at the beginning of a Shortcut name is an inseparable part of the command name; it must not be rewritten, other spellings must not be probed, and it must not be replaced with --help/-h。
Discovery gate: even if the Skill or reference documentation already provides a complete example, before answering you must actually execute once, and only once, the secure help/schema query for the target leaf; you must not answer directly based only on the Skill or reference documentation. This rule takes precedence over the reference navigation below: when it applies, do not read any reference and do not execute other commands. When the user only asks about usage, the final answer must first give the complete command; if a required ID is missing, give a complete command template with clear placeholders, and guessing is prohibited. Then clearly state "Unpassed sharing configuration keeps its original value"; do not execute the target write operation or claim it has been executed. The above read-only query is the only permitted command.
After a successful query, the final answer may contain only two lines of plain text: no Markdown code fences, headings, tables, read-back commands, or other content. The first line contains the complete command for the entry point the user asked about; existing required values must be used as-is, and missing values must be kept as clear placeholders such as <BASE_ID>、<TABLE_ID>、<VIEW_ID> . The second line first lists the placeholders that need to be replaced (if none, omit the replacement explanation), then gives the fixed not-executed statement, and ends immediately:
dws aitable form share update --base-id <BASE_ID> --table-id <TABLE_ID> --view-id <VIEW_ID> --enabled true
请将 <BASE_ID>、<TABLE_ID>、<VIEW_ID> 替换为真实值;未传入的分享配置保持原值。本次仅查询 help/schema,未执行写操作。
Known IDs and placeholders must be handled differently: a short ID explicitly given by the user must also be used as-is; do not require replacement because of its length or because it looks like an example. When all IDs are known, the second line must be exactly "Unpassed sharing configuration keeps its original value. This time only help/schema was queried, and no write operation was executed."; only when placeholders are actually used in the command should the corresponding replacement explanation be added. The Shortcut command line must retain --format json, and the help/schema in the fixed statement is not rewritten because only the schema was queried this time.
Both entry points must fully retain the configuration values specified by the user, especially the --form-namecorresponding to the form name; do not leave only the ID and --enabledbecause it was condensed to two lines. The following is an example of a Shortcut usage answer for a known ID (the title is replaced according to user input and must not be omitted):
dws aitable +form-share-update --base-id base-123 --table-id table-456 --view-id view-789 --enabled true --form-name "报名表" --format json
未传入的分享配置保持原值。本次仅查询 help/schema,未执行写操作。
Dedicated query for return value review (not applicable to command usage inquiries)
Before answering, there must be a target compact Schema query result actually executed this time; merely loading the Skill or seeing a synthetic sample does not satisfy this condition. First execute the commands in the table below, then explain; you must not answer directly based on the Skill.
Help/Schema is an offline contract query; it does not call online business services, nor does it read or write the user's forms. Therefore, "only analyze synthetic returns, do not execute online business commands" still allows and requires the local queries in the table below, and this must not be misjudged as an online read and skipped; only when the user explicitly prohibits any commands or local queries should they not be executed, and it should be stated that the local contract was not verified.
When reviewing only return values/failure results (rather than asking how to write them), do not apply the two-line command template, and the "prefer Shortcut" rule does not apply either. The atomic/Shortcut entry points specified by the user must be preserved as-is, even if they share the Result contract they cannot be interchanged; query once strictly according to the table below and then interpret the sample, do not search source code/reference, and do not perform business reads or writes.
| User-specified entry point | Unique contract query |
|---|---|
form share get |
dws schema --cli-path "aitable form share get" --compact --format json |
form share update |
dws schema --cli-path "aitable form share update" --compact --format json |
+form-share-get |
dws schema --cli-path "aitable +form-share-get" --compact --format json |
+form-share-update |
dws schema --cli-path "aitable +form-share-update" --compact --format json |
Do not use searching source code or reference as a substitute for the local contract query. get only diagnoses the sharing configuration and does not return cpSynced; do not suggest "confirming the closed loop by reading back cpSynced via get". An unverified CP should continue to be marked as unconfirmed and handed over to server-side diagnosis; the success of get or a non-empty UUID must not be treated as proof of recovery.
First choose the actual result branch of the Schema:data.executed=false the dry-run preview only contains tool/arguments/executed(Shortcut also contains dry_run=true), and does not require server-side state or cpSynced,ok=true only indicates the preview succeeded. Do not apply the required fields of the real execution success branch to the preview. Whether a field is required only reads the selected branch's required; whether additional fields are allowed only reads that object's additionalProperties, and the parent object cannot be inferred from the arguments child object.
Judging the real execution result: the sharing switch is based on enabled, and retaining the UUID does not mean it is enabled; if the UUID/cover is empty, report it truthfully, and do not speculate on the sole cause or assemble a cover URL. The success of get does not prove CP synchronization. update succeeds only when required fields are complete and correctly typed,cpSynced=true ; missing/false/type anomalies all mean the closed loop cannot be confirmed. Unified partial failure has no top-level error: the raw response is in data.succeeded[0].response, and that stage only indicates that a receipt was received; the failure reason is in data.failed[0].error, containing execution_started=true. Do not replay the write or compensate the CP on your own. If the synthetic sample does not conform to this structure, point out the mismatch, and do not supplement the Schema fields as if they were facts already present in the sample.
Interpretation boundaries:status When the enum meaning is not published, keep the original numeric value, and do not translate 0/1 on your own into unpublished/published;cpSynced=false only supports "CP final state unconfirmed", and does not prove that external users must be unable to access. Empty UUID/cover values cannot prove that it was never created before, and a short ID cannot be judged as a placeholder merely because of its length.
Even if the outer layer is still ok=true or the returned structure does not conform to the contract, do not execute or suggest resending form share update / +form-share-update (including passing the same configuration later) in order to verify the CP again; diagnosis must not add writes, only retain the receipt and hand it over to the server side for investigation.
After actually executing form share update or +form-share-update , the success result must simultaneously check shareFormUuid、status、formCover、cpSynced; only cpSynced=true allows confirming to the user that the sharing closed loop is complete. Partial failure or cpSynced=false must not be described as success. DWS does not itself call a second View update command to compensate the CP.formCover may be empty within the old server release window, and this should be stated truthfully; DWS must not assemble the cover URL.
Command reference:aitable.md; PostgreSQL read-only query:aitable-psql.md; load complex commands on demand
references/aitable/*.md; playbooks:06-data-analytics.md。
Shortcut discovery (on demand)
aitable There are currently 127 public shortcuts; the complete list is kept in the Runtime Catalog and Schema, and is not repeatedly expanded in the high-frequency product root Skill. Execute known leaves directly. For parameters, only check dws schema --cli-path "aitable <leaf>" --compact --jq '{cli_path,parameters,constraints,confirmation}' -f json; when you only need and have already published result , check outcomes/pagination, and for field-level details check data_schema; if missing, do not infer from Help/examples. Only read the known leaf Help once when the Schema is unavailable;unknown flag use the same leaf Help to correct once.unknown command Help is prohibited: erroneous suggestion → a clear entry point already loaded in Skill/reference; if neither exists, report drift. Full Catalog/root/parent/product Help is prohibited; low-frequency references do not default to Help; read only one Reference per task.
Only when the root route, the exact task reference, and the low-frequency atomic index of references/aitable.md all fail to locate the capability, execute dws shortcut list --service aitable --format json as the final fallback; do not load the full Shortcut Catalog or product-level Schema for a known intent.
Golden Route (high-frequency composite tasks)
IDs already returned by the current AITable call and whose type has been confirmed are used directly; names are first uniquely resolved to stable IDs. For a /i/nodes/ URL directly provided by the user or a nodeId from an unverified source, first execute dws drive info; if it is extension=dlink, save the returned result.fileId as the shortcut entry ID and pass it to dws doc info, then read the target linkSourceInfohop by hop, and after finally confirming extension=able use the target linkSourceInfo.nodeId as the baseId. Stop when resolution fails, a field is missing, the ID is duplicated, or the final type is not able; only when the shortcut entry itself is explicitly moved, renamed, or deleted should the original result.fileId be retained and switched to Drive. Also stop on zero hits or multiple candidates; do not select the first item by default.
For data analysis, and for PostgreSQL/SQL/SELECT/JOIN or cross-table join queries, first read aitable-psql.md. For raw record filtering, sorting, and Top N, use record query; for direct single-table scalar, grouped, or deduplicated statistics, use record stats / record group-stats; only for complex analysis such as same-Base JOINs, inter-field arithmetic, CASE, post-aggregation derivation, Top N or ranking of summarized results, and window calculations, use psql. When choosing psql , fix on the same DWS entry, first use dws aitable psql -d <baseId> -l to discover logical tables, then use -t <tableId> to view column types, use the returned Name to execute LIMIT 3 minimum query, and only after success use -c <SQL> to execute the formal read-only query;psql outputs PostgreSQL table text, without adding --format json. After psql fails, you may only re-determine from the original intent: if it fully belongs to single-table raw records, resend record query; if it fully belongs to direct single-table statistics, resend record stats / record group-stats; you must discard the unfinished psql results and explain the reason for switching, and downgrading is prohibited for complex analysis, result merging, and locally equivalent computations.
| User intent | Only recommended entry | Key boundaries |
|---|---|---|
| Parse stable IDs from a confirmed AITable URL | dws aitable +url-resolve --url <URL> |
Only parse the baseId/tableId/viewId/recordId already present in the URL; do not remotely resolve dlink; for a raw /i/nodes/ URL, it must first be normalized as above, and the dlink target nodeId is used directly as the baseId |
| Uniquely locate and operate on a Base/Table by name | dws aitable +resolve-base --name <名称> → dws aitable +resolve-table --base <ID> --name <表名> |
Exact match by default; add --fuzzy |
| Search Base candidates or check whether one exists | dws aitable +base-search --query <关键词> |
When the user says “search / look for / candidates / create if it doesn't exist”, go directly through this entry, without first calling +resolve-base; returns hasMore/nextCursor, only continue paging when hasMore=true ; AITable Base names must not be routed to dws aisearch person |
| Browse data tables under a Base | dws aitable +list-tables --base <ID> |
Only returns tableId/tableName, does not load fields |
| Create a new Base and its full set of table fields | dws aitable +base-bootstrap --name <名称> --tables '[{"name":"<表名>","fields":[{"fieldName":"<字段名>","type":"text"}]}]' |
Table object keys must be name, not tableName; fields use fieldName/type/config, optional description; execute directly when parameters are sufficient |
| Copy Base | dws aitable +base-copy --base-id <B_OR_URL> [--target-folder-id <FOLDER_ID_OR_URL>] [--only-struct] [--new-name <名称>] |
base-id accepts a Base ID or a standard node URL;target-folder-id accepts a dentryUuid, a standard node URL, or a Drive folder URL; when omitted, copies to the root directory of the workspace where the source Base resides; parameter parsing and destination validation are handled by AITable MCP |
| Create a new table and fields in an existing Base | dws aitable +table-bootstrap --base-id <ID> --name <表名> --fields '<JSON数组>' |
fields use fieldName/type/config, optional description; automatically shards by 15 fields and reads back for verification |
| Read field catalog or full configuration | dws aitable field list --base-id <B> --table-id <T> / dws aitable +field-get --base-id <B> --table-id <T> |
for only fieldId/name/type use field list; when config is needed use +field-get; does not exist +field-list or +list-fields |
| Resolve person, department, or group entities by name | dws aitable entity search --entity-type PERSON|DEPARTMENT|GROUP --keyword <名称> |
Returns candidates and stable identities usable for filtering; stop on zero hits, duplicate names, fuzzy hits, or incomplete pagination, and do not default to selecting the first item |
| Query raw records, record filtering/sorting, raw record Top N, or field projection | dws aitable +record-query --base-id <ID> --table-id <ID> [--record-ids <IDs>] [--field-ids <IDs>] [--filters <JSON>] [--sort <JSON>] [--query <关键词>] |
when the user requests "only return/only view" specified fields, the corresponding --field-idsmust be passed, and columns must not merely be removed in the final text; for single-table direct scalar, grouped, or deduplicated statistics switch to record stats / record group-stats; for complex server-side analysis switch to psql. Non-analytical complete row-by-row details that the user has explicitly authorized may directly use the atomic record query --all --page-limit <N>, and do not require or trigger the psql downgrade gate. |
| Add a single record or batch records | dws aitable record create --base-id <ID> --table-id <ID> --records <JSON> |
currently no +record-create; fetch field definitions before writing, and read back by new ID after writing |
| Verify record results by the original write token | dws aitable +record-write-result --base-id <B> --table-id <T> --client-token <原UUID> |
when unknown or IDs are incomplete, stop subsequent writes; the next step still calls this command with the original Base/Table/token for read-only reconciliation, and does not change to a full-table query; the applied ID set is not guaranteed to be complete for the whole batch or in input order, records whose IDs were not returned remain unverified, and do not backfill based on quantity differences or input positions; after the complete ID set is confirmed, verify actual values ID by ID; a query failure is not a write final state that can be rebuilt |
| Update a known recordId | dws aitable +record-update --base-id <ID> --table-id <ID> --records <JSON> |
automatically shards and reads back; pass only the fields that need modification |
| Query the change history of a record | dws aitable +record-history-list --base-id <ID> --table-id <ID> --record-id <ID> |
execute directly when recordId is known, without probing Help, Catalog, or the full Schema |
| Manage comments on a record | for query use dws aitable comment list --base-id <B> --table-id <T> --record-id <R>; for create, reply, update, and delete use leaves in the same group as needed |
first read comment; topicId/commentKey only reuse what is actually returned for the same record; an empty comment page still reads meta.pagination, stop only when meta.pagination.endpoint_exhausted=true , otherwise pass meta.pagination.next_token as-is to the next --cursor; for writes with unknown status, reconcile with list first |
| Sync by business key or batch modify by condition | for unique key use dws aitable +record-upsert-by-key ...; for bounded batch modification use dws aitable +record-bulk-patch ... --max-matches <N> |
upsert allows only 0 creates and 1 update; batch modification must have query/filters/record-ids boundaries. Ordinary update/upsert executes directly; only for history, sharing, deletion recovery, empty rows, or special field values read record-ops; for explicit AND/OR, date, or comparison operators read only filter-sort |
| Generate a record sharing link and send it to contacts | dws aitable +record-share-links --base <B> --table <T> --record-ids <IDs> → dws chat +dm --to <姓名> --content <完整链接文本> |
AITable only generates the link; when the user requests "send", actual sending must also be completed and must not stop at contact resolution |
| Create or copy a view | To create, use `dws aitable view create --base-id --table-id --view-type <Grid | FormDesigner |
| Create and verify a Dashboard, create a Chart as needed | dws aitable dashboard create --base-id <B> --name <名称> → dws aitable +dashboard-get --base-id <B> --dashboard-id <D>; when a Chart is needed, handle it according to "load on demand" below |
Use only the real dashboardId returned by creation; on failure, do not guess a synonymous command or change the dashboardId |
| Manage AI spreadsheet app mode | dws aitable app get --base-id <B> → dws aitable app page list --base-id <B> → as needed app page create/update/move/delete or app widget create/get/list/update/delete |
A Base has only one user-facing App; the page pageId is also the corresponding Dashboard ID. The Widget's config/layout is a complete object; read it back before updating; do not automatically replay a create operation when its status is unknown |
| Create a Section within a Base and move nodes | dws aitable +section-create --base-id <B> --name <名称> → dws aitable +section-move-node --base-id <B> --node-id <N> --new-parent-section-id <S> → dws aitable +section-list-nodes --base-id <B> |
Table, Dashboard, and Section are all nsheet nodes of AITable; do not switch to Wiki/Drive folders or move commands |
| Import local CSV/XLSX/XLS into a new table | dws aitable +import-file --base-id <BASE_ID> --file <FILE_PATH> |
Storage examples do not preset --yes; on the first call, first trigger the Runtime confirmation gate, and after obtaining explicit confirmation, the executor appends it. DWS completes credential request, empty Content-Type PUT, and import datawithin the process, and does not expose the signed URL; do not guess +import-csv or pass import upload to --file |
| Connect an external data source (approvals, etc.) | dws aitable +datasource-list-sources --base-id <ID> --datasource-type OA → parse result to construct sourceConfig → dws aitable +datasource-create --base-id <ID> --datasource-type OA --source-config '<JSON>' |
Currently only OA approvals are supported; processCode/name/iconUrl/url are passed through as-is from list-sources, and after creation use +datasource-sync-status to check the sync result |
Simple leaf
Except for aitable psql , structured commands use --format json and extract stable IDs from the real return;aitable psql outputs PostgreSQL table text and does not support --format json, execute according to aitable-psql.md .
Use directly when the intent is clear; read the leaf Schema only when parameters are uncertain:
| User intent | Entry point |
|---|---|
| View / rename / delete Base | +base-get / +base-update / +base-delete |
| Search templates | +template-search |
| View / cross-Base copy / rename / delete Table | +table-get / +table-copy / +table-update / +table-delete |
| Create / update / delete regular fields | field create / field update / field delete |
| View / delete View | +view-get / +view-delete |
| View / rename / delete Dashboard | +dashboard-get / +dashboard-update / +dashboard-delete |
| View / modify app mode App | app get / app update |
| Manage app pages | app page create/get/list/update/move/delete |
| Manage page Widget | app widget create/get/list/update/delete |
Commands follow dws aitable ; resource IDs use --base-id/--table-id/--field-id/--view-id/--dashboard-id/--page-id/--widget-id, renaming uses --name. All commands in app mode require --base-id;app widget create additionally requires the chartType that contains --config and the x/y/w/h that contains --layout。+table-copy parameters are irregular; read only their leaf Schema before execution. Do not read the operations Reference, Help, or product Catalog.
Use for viewing data source origins +datasource-list-sources, use for getting fields +datasource-get-fields, use for create, update, sync, check status, and check configuration +datasource-create / +datasource-update / +datasource-sync / +datasource-sync-status / +datasource-get-config。
Execution constraints
-
Use existing IDs directly; parse URLs only once; use for "uniquely locate and operate"
+resolve-base/+resolve-table, and use directly for "search candidates/existence check"+base-searchWhen people, departments or groups have only display names, useentity searchto obtain a stable identity; do not probe these paths sequentially. Read the field catalog only when filters/sort lacks fieldId. -
When the Golden Route already provides accurate commands and parameters, execute directly; do not pre-read or read by default the generic
references/aitable.md. Only when operation parameters, JSON structure or recovery semantics are genuinely missing, read one precise operation Reference below. -
When the Shortcut already includes sharding or validation, do not split steps again; when a complete table structure is to be newly created with an existing Base, directly use
+table-bootstrap。 -
For single-product linear tasks, execute directly without creating a TodoWrite; create a plan only for long tasks spanning products or multiple independent branches, and update it only at phase transitions, not refreshing status after every CLI command.
-
When the user requires resource names to carry the current timestamp, take it only once and reuse the same value in names such as Base, Table, Dashboard; do not take the time separately for each resource.
-
When the JSON already returns the required field, reuse it immediately; do not switch to
--verbose、raw、prettyto repeatedly request the same field. -
Read the field catalog only when a record filter/sort lacks fieldId.
-
The protocols and References for record filter/sort and view filter/sort/group are mutually exclusive. Ordinary record query/create/update/upsert go direct; only for history, sharing, deletion recovery, empty rows or special field values read
record-ops。 -
Ordinary field type uses
text/number/date/singleSelect/currency;singleSelectwhose config is{"options":[{"name":"<选项>"}]}, CNYcurrencyis{"currencyType":"CNY","formatter":"FLOAT_2"}。 -
Use TodoWrite only when the task contains 4 or more independent business steps or the user explicitly requires it; do not split steps per single CLI command, and update only at phase transitions.
-
When multiple resource names require the same timestamp, take it only once and reuse it.
-
Reuse fields already returned by the JSON; do not use
--verbose/raw/prettyto repeatedly request them. -
Before creating a data source, you must first
+datasource-list-sourcesobtain pass-through fields such as processCode; do not construct sourceConfig from memory.
Record stable constraints
-
When a record pagination reports
INVALID_CURSOR、CURSOR_SNAPSHOT_CHANGEDorCURSOR_SNAPSHOT_UNAVAILABLE, all accumulated results and the old cursor must be discarded; there is no new cursor that allows resumption, and you must not keep the first page and then deduplicate and concatenate. For the first two, after verifying the conditions, do not pass--cursorand re-query read-only from the first page; UNAVAILABLE requires waiting for service recovery first. Do not rerun the entire command containing writes. Resumption is allowed only for ordinary recoverable errors when a valid breakpoint is actually provided; see record-query。 -
Before querying, writing, filtering or sorting, first use
field getto obtain the target field'sfieldId、typeandconfig;cells's key must usefieldId, not the field's Chinese name. -
For select/multipleSelect writes, pass the option name; when filtering, first uniquely resolve the option ID. For multipleSelect or other array-type fields, the second operand must be an option ID/stable ID array, and must not be a bare string.
-
Conditions such as people, departments, groups and linked records must first be resolved into stable structured IDs; stop when there are zero matches, multiple matches or a type mismatch, and do not pass through display names or original values directly.
-
With explicit user permission, complete non-analytical line-by-line details may directly use
record query --all --page-limit 0, without needing or triggering the psql downgrade gate; do not use it as a substitute for psql complex analysis, or perform computations in Agent context, Python, jq, JavaScript, spreadsheets or other local tools. Automatic pagination must not involve model-written loops; manual pagination must pass through the realdata.nextCursor, and the query conditions remain unchanged. Successful empty continuation pagerecords=[]andnextCursorbeing empty is a normal last page; it must not error, retry, or be judged as a missed query. -
For create or update, read back only using the ID actually returned; when the write result is unknown, read back and do not replay successful batches.
-
For full queries, check
hasMore, and for batch writes check the final state; when pagination has not ended orpartial_success, completion must not be claimed. -
Record
cellsuses the current fieldId, writes values according to the real field type, and read-only fields must not be written. -
For create or update, read back only using the ID actually returned; when the write result is unknown, read back and do not replay successful batches.
-
For full queries, check
hasMore, and for batch writes check the final state; when pagination has not ended orpartial_success, completion must not be claimed.
Security boundaries
- Deletion is irreversible; verify the real target against Runtime confirmation;
base listis only the most recent access. Stop when a field has zero or multiple candidates or the type is unclear; for multi-batch writes, retain completed batches and the resume position. - Comment create/reply is not idempotent; when the status of a comment write operation is unknown, first
comment listreconcile, and do not automatically replay; delete only deletes one's own comments and is irreversible, and handling of associated replies is not guaranteed. app get/app page listinitializes a default App when the App does not exist, which is an idempotent conditional write;app page/widget createis not idempotent and is not automatically retried. Deleting a Page cascades to delete all Widgets, and deleting a Widget synchronously cleans up the layout; both require independent confirmation.- Data source
+datasource-create/+datasource-updatetriggers a real data sync; before execution, confirm the target Base and sourceConfig.+datasource-syncsupports at most 5 tables per single operation.
Load on demand (complex JSON and recovery semantics)
When covered by Golden/secondary direct access, do not read Reference; otherwise, read exactly one precise Reference according to the final dedicated capability. After reading, execute directly and do not read other AITable References.
| Trigger conditions | Reference |
|---|---|
+record-query, upsert, bulk patch record filters/sort/date/AND/OR/comparison operators |
filter-sort |
| record history, sharing, deletion recovery, empty rows, or special field values | record-ops |
| record pagination errors, invalid cursors, or snapshot recovery | record-query |
| record statistics, grouped aggregation, or deduplication rate | record-stats |
| record comment query, creation, reply, update, or deletion | comment |
| query a record's primary key document, or create a primary key document for a record | before creating a table for the first time, read primary-doc; ordinary Base/Table/field/record creation and import do not read it |
| AI fields, linked fields, lookup/filterUp, or other complex config | field |
| formula fields or formula syntax | formula-guide |
| import/export task recovery | export-import |
view column order, move to/place at/pin to far left, filter, sort, group (must not switch to reading the record filter-sort) |
view-config |
| Kanban/Gallery card, Gantt timebar, Grid aggregate | view-types |
| view locking, explicitly freezing the first N columns, row height, or fill color | view-extras |
| Section/node move or cleanup within a Base | section |
| config required for Chart creation or update, or complete Dashboard config/arrange; ordinary Dashboard CRUD uses the direct access above | dashboard-chart |
| form creation, questions, or sharing | form |
| attachment upload or removal | attachment |
| automation workflows | workflow |
| Regular role or advanced permissions | advperm |
| Data source connection, sync management, sourceConfig construction, or approval data sync | datasource |
| Access key creation, query, or revocation | api-key |
| SQL, PostgreSQL, SELECT, or multi-table JOIN within the same Base | psql |
| Product boundary unclear | intent-guide |
| Low-frequency atomic capabilities that still cannot be located using only the above Reference | aitable.md corresponding section |
Do not preload these References.
Shortest error path
- Zero/multiple candidates, field ambiguity, or incomplete pagination: stop and return evidence; only a valid pagination session may pass through the real
nextCursor. For an invalid cursor, first execute the above "Record stability constraints"; ordinary breakpoint resume cannot be applied. - For type errors, only recheck the target field; do not delete fields or lose input;
partial_successresume from checkpoint; for unknown writes, read back first. - When an error provides
actions/available_flags, correct only once according to thenext_commandin it;retryable=falseor when the target ID type does not match, stop. - Data source sync
errorCode=4014indicates repeated triggering while the sync is running; you may retry later; before triggering a sync on a non-data-source table, first use+base-getto confirmsync=true。
Cross-product boundaries
- Excel-style cell, range, and formula operations →
dingtalk-miscSheet. - Moving a Base as a whole between ordinary folders or performing outer storage renaming → Drive; copying/deleting the Base structure, as well as creating, copying, moving, renaming, and deleting Tables, Dashboards, and Sections within a Base → AITable.
- Record primary key document body → after obtaining the real nodeId, switch to
dingtalk-doc。