Skip to content

re-fix splitSql function, and implement dry-run in sql subcommand - #5

Merged
suibianwanwank merged 1 commit into
mainfrom
feat/dryrun
May 14, 2026
Merged

suibianwanwank merged 1 commit into
mainfrom
feat/dryrun

Conversation

@lyman

@lyman lyman commented May 14, 2026

Copy link
Copy Markdown
Member

Type of change

  • Bug fix
  • New feature
  • Refactor / code improvement
  • Documentation

What does this PR do?

Previous fix on splitSql just ignores empty sqls and behaves differently from python sdk.

This patch is an alignment to python sdk implementation, with corresponding test cases.

Also, a --dry-run is added to sql subcommand, to make further debug easier.

Checklist

  • I have tested my changes locally
  • I have not included unrelated changes in this PR

@suibianwanwank
suibianwanwank merged commit 38964a0 into main May 14, 2026
6 of 11 checks passed
hellozepp pushed a commit that referenced this pull request Jun 3, 2026
…er, #9 rerun -y

Co-Authored-By: cz-cli <noreply@clickzetta.com>
hellozepp pushed a commit that referenced this pull request Jul 23, 2026
…, one-step upload (#60)

* feat(analytics-agent): smoother table add, join notes, answer-builder --sql, one-step knowledge upload

Address v1.17.18 hands-on findings:

- domain table add: accept a fully-qualified `--table workspace.schema.table`
  and auto-split it, so lakehouse datasources no longer force trial-and-error
  --workspace/--schema. Surface the assigned dataset ID via ai_message and flag
  the soft-failure case where the backend returns success but did not attach
  the table (#1, #2, #6).
- domain join create/update: when the backend normalizes the relation by
  cardinality (e.g. n:1 -> 1:n), note it in ai_message so the direction change
  isn't mistaken for an error (#7).
- answer-builder create/update/validate: add `--sql` that injects into the
  content DSL's top-level sql field, so SQL quotes don't collide with the
  --content JSON escaping. Require at least one of --content/--sql (#9).
- knowledge file upload: document (examples + epilogue) that --target-path
  auto-creates the folder path and --domain-id binds at upload, collapsing the
  old create -> folder -> move -> bind sequence into one command (#3).

Not addressed (backend/doc): targetCounts.knowledge counting (#4), physical vs
v_gpt view column names (#5), bulk create APIs (#8).

Specs and tests updated alongside the code.

Co-Authored-By: cz-cli <noreply@clickzetta.com>

* fix(analytics-agent): set a display name when adding a table to a domain

A dataset created via `domain table add` had no display name, so it rendered
blank in the UI and broke page-level operations. Default displayName to the
fully-qualified physical table name (view name with the `v_gpt_` prefix
stripped), matching the UI convention, and add `--display-name` to override.

Verified live: adding a fresh dataset (createdDataset=true) now persists the
display name; when the backend reuses an existing dataset it keeps the prior
name, which is the intended backend behavior.

Co-Authored-By: cz-cli <noreply@clickzetta.com>

* feat(analytics-agent): add `table set-display-name` to rename an existing table

`domain table add --display-name` only sets the display name when the dataset
is newly created; the backend ignores it for an existing dataset. There was no
way to fix a blank/wrong display name on a table already in a domain.

Add `table set-display-name <dataset-id> --name`, using the dataset endpoints
the UI uses: read-modify-write against `GET /api/v1/dataset/detail` +
`POST /api/v1/dataset/update`, which require the full dataset object — fetch
it, change only displayName, post it back.

Verified live (reversibly) against Shanghai: renamed dataset 82's display name
and restored it; the other fields (description, schema, joins) are preserved.

Co-Authored-By: cz-cli <noreply@clickzetta.com>

* feat(analytics-agent): generalize table rename into `table update` (name + description)

The dataset/update endpoint sets both displayName and description in one call,
so replace the single-purpose `set-display-name` with `table update <dataset-id>
--name --description` (at least one required). Same read-modify-write against
dataset detail + update, now patching whichever fields the caller supplies.

Verified live (reversibly): updated dataset 82's display name and description
together, then restored both; other fields preserved.

Co-Authored-By: cz-cli <noreply@clickzetta.com>

* fix(analytics-agent): read table update source via dataset/list, not the broken dataset/detail

`dataset/detail?datasetId=<id>` returns CZD-20009 "dataset not found" for
datasets in some domains (the list endpoint sees them, detail does not — a
backend inconsistency the UI hits too). Switch `table update`'s read-modify-
write read step to `POST /api/v1/dataset/list {domainIds:[<id>]}`, locating the
full object by datasetId. Adds a required --domain-id.

Verified live: `table update 97 --domain-id 29` (a domain whose datasets fail
via dataset/detail) now renames successfully and restores; full object fields
preserved.

Co-Authored-By: cz-cli <noreply@clickzetta.com>

---------

Co-authored-by: cz-cli <noreply@clickzetta.com>
suibianwanwank pushed a commit that referenced this pull request Aug 13, 2026
Three defects with one shared symptom — a configured ClickZetta gateway entry
that the agent could not use — and one shared root cause: cz writes process.env
from inside main(), long after opencode's modules load.

1. Lazy flag reads (packages/core/src/flag/flag.ts, INTRUSIVE #5)

   `Flag` snapshotted 26 of 34 env-backed entries at module import; the other 8
   were already getters carrying the comment "Evaluated at access time ...
   because tests, the CLI, and external tooling set these env vars at runtime".
   Which half a var landed in was accident. OPENCODE_CONFIG /
   OPENCODE_CONFIG_CONTENT were in the eager half, so opencode's config loader
   never read llm.json in-process:

     - `agent llm models <entry>` -> MODEL_DISCOVERY_FAILED for a healthy entry
     - `agent llm models`         -> zero llm.json providers listed
     - `agent run --model <entry>/<id>` -> "Model not found"
     - `agent llm show`           -> default model resolved from a provider set
                                     with no llm.json entries

   The TUI was unaffected: its server runs in a Bun Worker whose fresh module
   registry re-evaluates flag.ts after the env is set. Now every env-backed flag
   reads at access time; the 7 that callers assign to keep write-through setters
   (getter-only broke httpapi-listen.test.ts). test/flag-injection-visibility
   scans the tree for `Flag.X =` and fails if an assigned flag loses its setter,
   so a re-baseline drop is loud instead of silent.

2. Normalized gateway base (bootstrap/runtime-config.ts)

   providerNpmStubs carried only `npm`, discarding the normalized baseURL
   rewriteProviders had already computed, so opencode read llm.json's raw
   base_url. A bare host — what `ai-gateway --add-to-llm` writes — made model
   discovery request {host}/models, which the gateway answers with 400 "Invalid
   API key", blaming the credential for a path bug. Inference still worked
   (the provider package normalizes its own options.baseURL), so the symptom was
   "chat works, model picker empty".

3. MCP tool calls report the real failure (commands/mcp.ts, INTRUSIVE #6)

   `cz` / `cz-reply` answered "Unexpected server error. Check server logs for
   details." for everything. Two causes: the server's defect boundary replaces
   the error with a ref (and Logger.toFile batches, so the line is not on disk
   when the response goes out), and cz's formatter ran
   `err instanceof Error ? err.message : String(err)` on a value that is
   neither — the SDK's throwOnError throws the parsed response body, which
   stringified to "[object Object]".

   The boundary now attaches the real error and cause as `data.detail` when
   OPENCODE_ERROR_DETAIL is set; runMcpServe sets it (loopback server, single
   local client) and never applyAgentRuntimeInjection, since `cz-cli serve`
   binds a real port. formatToolError renders every shape both paths produce.
   checkModelResolvable preflights the model and distinguishes "gateway returned
   no catalog, only the seeded fallback is present" (overdue tenant / blocked
   key) from "stale pin, here is what the entry serves". It never falls back to
   another provider: env-detected openai/anthropic sit in the same list and
   silently rerouting would bill and expose data on the wrong path.

Also: `agent llm test` now probes a model the gateway just reported instead of a
hardcoded id, so it cannot fail on a tenant that does not serve that id while
the TUI works.

Verified on a built binary, before and after, against a live gateway: bare-host,
/v1 and /gateway/v1 entries all resolve the full 37-model catalog; an
overdue-tenant entry keeps its seeded fallback and now reports why. cz-cli suite
4102 tests green; core 1016 green (2 pre-existing failures unchanged);
opencode test/provider 399 green.

Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

3 participants