refactor(workspace): fold internal packages into cli

This commit is contained in:
Andrey Avtomonov 2026-05-21 03:27:33 +02:00
parent 8c2333cc15
commit ac3885b652
945 changed files with 517 additions and 2686 deletions

View file

@ -83,36 +83,8 @@ jobs:
- name: Run TypeScript checks
run: pnpm run check
slow-context-tests:
name: Slow context tests
runs-on: ubuntu-latest
steps:
- name: Checkout repository
uses: actions/checkout@de0fac2e4500dabe0009e67214ff5f5447ce83dd # v6.0.2
- name: Setup pnpm
uses: pnpm/action-setup@0e279bb959325dab635dd2c09392533439d90093 # v6.0.8
with:
run_install: false
- name: Setup Node.js
uses: actions/setup-node@48b55a011bda9f5d6aeb4c2d9c7362e8dae4041e # v6.4.0
with:
node-version: "24"
cache: "pnpm"
cache-dependency-path: "pnpm-lock.yaml"
- name: Install TypeScript dependencies
run: pnpm install --frozen-lockfile
- name: Build TypeScript packages
run: pnpm run build
- name: Run slow context tests
run: pnpm --filter @ktx/context run test:slow
slow-cli-tests:
name: Slow CLI tests
name: Slow TypeScript tests
runs-on: ubuntu-latest
steps:
- name: Checkout repository
@ -236,7 +208,7 @@ jobs:
with:
token: ${{ secrets.CODECOV_TOKEN }}
slug: Kaelio/ktx
files: ./packages/cli/coverage/lcov.info,./packages/connector-bigquery/coverage/lcov.info,./packages/connector-clickhouse/coverage/lcov.info,./packages/connector-mysql/coverage/lcov.info,./packages/connector-postgres/coverage/lcov.info,./packages/connector-snowflake/coverage/lcov.info,./packages/connector-sqlite/coverage/lcov.info,./packages/connector-sqlserver/coverage/lcov.info,./packages/context/coverage/lcov.info,./packages/llm/coverage/lcov.info
files: ./packages/cli/coverage/lcov.info
flags: typescript
name: typescript
disable_search: true

View file

@ -63,11 +63,10 @@ When rules conflict, follow this order:
**ktx** is a pnpm + uv workspace.
- TypeScript packages: `packages/*`
- CLI package: `packages/cli`
- Core context package: `packages/context`
- LLM package: `packages/llm`
- Database connectors: `packages/connector-*`
- TypeScript package: `packages/cli` (the sole npm-published package source)
- Core context modules: `packages/cli/src/context/`
- LLM provider modules: `packages/cli/src/llm/`
- Database connector modules: `packages/cli/src/connectors/<driver>/`
- Python semantic layer: `python/ktx-sl`
- **ktx** daemon: `python/ktx-daemon`
- Examples and fixtures: `examples/`
@ -76,9 +75,8 @@ When rules conflict, follow this order:
commit `.agents/`, `.claude/`, or `docs/superpowers/` to this public
repository.
Some package names still contain `ktx` during the split. Do not mass-rename
symbols, package names, paths, or docs to `ktx` unless the task asks for that
rename.
Some source identifiers still contain historical package-oriented names. Do not
mass-rename symbols, paths, or docs unless the task asks for that rename.
## Quick Commands
@ -154,11 +152,11 @@ pnpm run test 2>&1 | tee /tmp/ktx-test-output.log
- Keep package exports, `types`, and built `dist` expectations aligned when
changing public APIs.
- Use `zod` schemas for runtime validation at CLI/config/API boundaries.
- Keep connector packages thin: connector-specific scanning/auth behavior
belongs in `packages/connector-*`; shared types and orchestration belong in
`packages/context`.
- Avoid circular package dependencies. Shared code should move to the lowest
sensible package, not be duplicated across connectors.
- Keep connector modules thin: connector-specific scanning/auth behavior
belongs in `packages/cli/src/connectors/<driver>/`; shared types and
orchestration belong in `packages/cli/src/context/`.
- Avoid circular module dependencies. Shared code should move to the lowest
sensible module, not be duplicated across connectors.
- Do not manually edit generated or built output under `dist/`; edit source and
rebuild.

View file

@ -162,20 +162,14 @@ commands to run. If the output includes `ktx mcp start --project-dir ...`, run
it before opening your agent. Claude Desktop uses its own launcher and prints
separate skill upload steps under `.ktx/agents/claude/`.
## Workspace packages
## Workspace layout
| Package | Purpose |
|---------|---------|
| `packages/cli` | CLI entry point |
| `packages/context` | Core context engine |
| `packages/llm` | LLM and embedding providers |
| `packages/connector-bigquery` | BigQuery scan connector |
| `packages/connector-clickhouse` | ClickHouse scan connector |
| `packages/connector-mysql` | MySQL scan connector |
| `packages/connector-postgres` | Postgres scan connector |
| `packages/connector-snowflake` | Snowflake scan connector |
| `packages/connector-sqlite` | SQLite scan connector |
| `packages/connector-sqlserver` | SQL Server scan connector |
| Path | Purpose |
|------|---------|
| `packages/cli` | TypeScript CLI package and published npm package source |
| `packages/cli/src/context` | Core context engine |
| `packages/cli/src/llm` | LLM and embedding providers |
| `packages/cli/src/connectors` | Database scan connectors |
| `python/ktx-sl` | Semantic-layer query planning |
| `python/ktx-daemon` | Portable compute service |

View file

@ -22,8 +22,8 @@ documentation, connector coverage, and examples.
| Area | Good first context |
|------|--------------------|
| CLI and setup | `packages/cli`, especially setup steps, command definitions, status checks, and smoke tests |
| Context engine | `packages/context`, including project config, ingest orchestration, and semantic search |
| Connectors | `packages/connector-*`, plus connector-specific tests and integration docs |
| Context engine | `packages/cli/src/context`, including project config, ingest orchestration, and semantic search |
| Connectors | `packages/cli/src/connectors/<driver>`, plus connector-specific tests and integration docs |
| Python semantic layer | `python/ktx-sl` for planning and SQL compilation |
| **ktx** daemon | `python/ktx-daemon` for the portable runtime API |
| Documentation | `docs-site/content/docs` for public docs and `docs-site/tests` for docs behavior |
@ -50,7 +50,7 @@ pnpm install
uv sync --all-groups
```
`pnpm install` sets up all TypeScript packages in the workspace.
`pnpm install` sets up the TypeScript workspace.
`uv sync --all-groups` installs Python dependencies for the semantic layer and
daemon, including dev and test groups.
@ -60,11 +60,10 @@ daemon, including dev and test groups.
pnpm run build
```
This builds all TypeScript packages. You can also build individual packages:
This builds the TypeScript package. You can also build the package directly:
```bash
pnpm --filter @ktx/cli run build
pnpm --filter @ktx/context run build
```
### Link the CLI for local testing
@ -80,21 +79,15 @@ changes.
## Repository structure
**ktx** is a pnpm + uv workspace. TypeScript packages live in `packages/`, Python
projects in `python/`.
**ktx** is a pnpm + uv workspace. TypeScript source lives in `packages/cli`,
and Python projects live in `python/`.
```text
packages/
cli/ # CLI entry point and commands
context/ # Core context engine (scan, ingest, MCP, semantic layer)
llm/ # LLM client abstraction
connector-postgres/ # PostgreSQL connector
connector-snowflake/ # Snowflake connector
connector-bigquery/ # BigQuery connector
connector-mysql/ # MySQL connector
connector-sqlserver/ # SQL Server connector
connector-sqlite/ # SQLite connector
connector-posthog/ # PostHog connector
cli/ # CLI package and published npm package source
src/context/ # Core context engine (scan, ingest, MCP, semantic layer)
src/llm/ # LLM client abstraction
src/connectors/ # Database connectors
python/
ktx-sl/ # Semantic layer - grain-aware query planning and SQL compilation
@ -105,7 +98,7 @@ scripts/ # Workspace scripts (benchmarks, verification, release)
docs-site/ # Documentation site (Fumadocs)
```
All TypeScript packages are ESM (`"type": "module"`) and use `NodeNext` module
The TypeScript package is ESM (`"type": "module"`) and uses `NodeNext` module
resolution. The Python projects use `pyproject.toml` for dependency management.
## Running tests
@ -116,15 +109,14 @@ resolution. The Python projects use `pyproject.toml` for dependency management.
# Run all tests
pnpm run test
# Run tests for a specific package
# Run tests for the TypeScript package
pnpm --filter @ktx/cli run test
pnpm --filter @ktx/context run test
# Type-check all packages
pnpm run type-check
# Type-check a specific package
pnpm --filter @ktx/context run type-check
# Type-check the TypeScript package
pnpm --filter @ktx/cli run type-check
# CLI smoke test
pnpm --filter @ktx/cli run smoke
@ -164,43 +156,22 @@ uv run pytest -q
## Adding a connector
Database connectors live in `packages/connector-<name>/`. Each connector
implements the `KtxScanConnector` interface from `@ktx/context`.
Database connectors live in `packages/cli/src/connectors/<name>/`. Each
connector implements the `KtxScanConnector` interface from the internal context
modules.
### Step 1: Scaffold the package
### Step 1: Scaffold the connector
Create a new directory at `packages/connector-<name>/` with:
Create a new directory at `packages/cli/src/connectors/<name>/` with:
```text
packages/connector-<name>/
package.json
tsconfig.json
src/
index.ts # Public exports
connector.ts # KtxScanConnector implementation
dialect.ts # SQL dialect handling
packages/cli/src/connectors/<name>/
index.ts # Internal connector exports
connector.ts # KtxScanConnector implementation
dialect.ts # SQL dialect handling
```
The `package.json` should follow the pattern of existing connectors:
```json
{
"name": "@ktx/connector-<name>",
"private": true,
"type": "module",
"main": "dist/index.js",
"types": "dist/index.d.ts",
"exports": {
".": {
"types": "./dist/index.d.ts",
"import": "./dist/index.js"
}
},
"dependencies": {
"@ktx/context": "workspace:*"
}
}
```
Add any driver-specific npm dependency to `packages/cli/package.json`.
### Step 2: Implement the connector
@ -226,20 +197,20 @@ and statistics.
### Step 4: Wire it up
Register the new connector in `packages/context` so the CLI and scan
engine can instantiate it. Look at how existing connectors are registered for
the pattern.
Register the new connector in `packages/cli/src/local-scan-connectors.ts` and
`packages/cli/src/local-adapters.ts` so the CLI and scan engine can instantiate
it. Keep runtime loading dynamic when the driver is optional.
### Step 5: Test
```bash
pnpm --filter @ktx/connector-<name> run build
pnpm --filter @ktx/connector-<name> run type-check
pnpm --filter @ktx/connector-<name> run test
pnpm --filter @ktx/cli run build
pnpm --filter @ktx/cli run type-check
pnpm --filter @ktx/cli run test
```
Use `packages/connector-sqlite/` as a minimal reference and
`packages/connector-postgres/` as a full-featured one.
Use `packages/cli/src/connectors/sqlite/` as a minimal reference and
`packages/cli/src/connectors/postgres/` as a full-featured one.
## Code conventions

View file

@ -16,47 +16,16 @@
"entry": [
"src/index.ts",
"src/bin.ts",
"src/llm/index.ts",
"src/context/index.ts",
"src/context/**/index.ts",
"src/connectors/*/index.ts",
"src/**/*.test.ts",
"src/**/*.test.tsx",
"scripts/**/*.mjs"
],
"project": ["src/**/*.{ts,tsx}", "scripts/**/*.mjs", "vitest.config.ts"]
},
"packages/context": {
"entry": [
"src/index.ts",
"src/agent/index.ts",
"src/core/index.ts",
"src/connections/index.ts",
"src/daemon/index.ts",
"src/ingest/index.ts",
"src/ingest/memory-flow/index.ts",
"src/ingest/metabase-mapping.ts",
"src/scan/index.ts",
"src/search/index.ts",
"src/sql-analysis/index.ts",
"src/memory/index.ts",
"src/mcp/index.ts",
"src/project/index.ts",
"src/prompts/index.ts",
"src/skills/index.ts",
"src/sl/index.ts",
"src/sl/descriptions.ts",
"src/tools/index.ts",
"src/wiki/index.ts",
"src/**/*.test.ts",
"scripts/**/*.mjs"
],
"project": ["src/**/*.ts", "scripts/**/*.mjs", "vitest.config.ts"]
},
"packages/llm": {
"entry": ["src/index.ts", "src/**/*.test.ts"],
"project": ["src/**/*.ts", "vitest.config.ts"]
},
"packages/connector-*": {
"entry": ["src/index.ts", "src/**/*.test.ts"],
"project": ["src/**/*.ts"]
},
"docs-site": {
"entry": [
"app/**/*.{ts,tsx}",
@ -106,17 +75,17 @@
"packages/cli/src/setup-project.ts": ["types"],
"packages/cli/src/setup-ready-menu.ts": ["types"],
"packages/cli/src/setup-sources.ts": ["types"],
"packages/context/src/ingest/adapters/historic-sql/pattern-inputs.ts": ["exports", "types"],
"packages/context/src/ingest/adapters/lookml/pull-config.ts": ["exports"],
"packages/context/src/ingest/adapters/metabase/serialize-card.ts": ["types"],
"packages/context/src/ingest/adapters/metabase/types.ts": ["exports"],
"packages/context/src/ingest/adapters/metricflow/parse.ts": ["types"],
"packages/context/src/ingest/ports.ts": ["types"],
"packages/context/src/ingest/stages/stage-3-work-units.ts": ["types"],
"packages/context/src/ingest/stages/stage-index.types.ts": ["types"],
"packages/context/src/project/config.ts": ["types"],
"packages/context/src/scan/relationship-candidates.ts": ["types"],
"packages/context/src/scan/relationship-diagnostics.ts": ["types"],
"packages/context/src/tools/context-evidence-tool-store.ts": ["types"]
"packages/cli/src/context/ingest/adapters/historic-sql/pattern-inputs.ts": ["exports", "types"],
"packages/cli/src/context/ingest/adapters/lookml/pull-config.ts": ["exports"],
"packages/cli/src/context/ingest/adapters/metabase/serialize-card.ts": ["types"],
"packages/cli/src/context/ingest/adapters/metabase/types.ts": ["exports"],
"packages/cli/src/context/ingest/adapters/metricflow/parse.ts": ["types"],
"packages/cli/src/context/ingest/ports.ts": ["types"],
"packages/cli/src/context/ingest/stages/stage-3-work-units.ts": ["types"],
"packages/cli/src/context/ingest/stages/stage-index.types.ts": ["types"],
"packages/cli/src/context/project/config.ts": ["types"],
"packages/cli/src/context/scan/relationship-candidates.ts": ["types"],
"packages/cli/src/context/scan/relationship-diagnostics.ts": ["types"],
"packages/cli/src/context/tools/context-evidence-tool-store.ts": ["types"]
}
}

View file

@ -44,11 +44,13 @@
"test:coverage": "pnpm run test:coverage:ts && pnpm run test:coverage:py",
"test:coverage:py": "uv run pytest --cov=python/ktx-sl/semantic_layer --cov=python/ktx-daemon/src/ktx_daemon --cov-report=xml:coverage/python.xml --cov-report=term",
"test:coverage:ts": "pnpm --filter './packages/*' run build && pnpm --filter './packages/*' run test --coverage --coverage.reporter=lcov --coverage.exclude='dist/**' && node scripts/normalize-lcov-paths.mjs packages/*/coverage/lcov.info",
"test:slow": "pnpm --filter @ktx/context run test:slow && pnpm --filter @ktx/cli run test:slow",
"test:slow": "pnpm --filter @ktx/cli run test:slow",
"type-check": "pnpm --filter './packages/*' run type-check"
},
"devDependencies": {
"@biomejs/biome": "^2.4.15",
"@electric-sql/pglite": "^0.4.5",
"@electric-sql/pglite-socket": "^0.1.5",
"@semantic-release/commit-analyzer": "^13.0.1",
"@semantic-release/exec": "^7.1.0",
"@semantic-release/git": "^10.0.1",
@ -59,6 +61,7 @@
"better-sqlite3": "^12.10.0",
"conventional-changelog-conventionalcommits": "^9.3.1",
"knip": "^6.12.2",
"pg": "^8.20.0",
"semantic-release": "^25.0.3",
"typescript": "^6.0.3",
"yaml": "^2.9.0"

View file

@ -1,7 +1,7 @@
{
"name": "@ktx/cli",
"version": "0.4.1",
"description": "CLI wrapper for ktx context packages",
"description": "Standalone ktx context layer CLI",
"private": true,
"type": "module",
"engines": {
@ -30,40 +30,58 @@
"clean": "node -e \"fs.rmSync('dist', { recursive: true, force: true }); fs.rmSync('node_modules/.cache/tsc.tsbuildinfo', { force: true })\"",
"docs:commands": "pnpm run build && node dist/print-command-tree.js",
"smoke": "vitest run src/standalone-smoke.test.ts src/example-smoke.test.ts --testTimeout 30000",
"test": "vitest run --exclude src/standalone-smoke.test.ts --exclude src/example-smoke.test.ts --exclude src/setup-databases.test.ts --exclude src/scan.test.ts --exclude src/commands/connection-metabase-setup.test.ts --exclude src/setup-models.test.ts --exclude src/setup-sources.test.ts --exclude src/setup.test.ts --exclude src/connection.test.ts --exclude src/setup-embeddings.test.ts --exclude src/ingest.test.ts --exclude src/commands/connection-mapping.test.ts --exclude src/ingest-viz.test.ts --exclude src/demo.test.ts --exclude src/setup-project.test.ts --exclude src/sl.test.ts --exclude src/local-scan-connectors.test.ts --exclude src/commands/connection-notion.test.ts",
"test:slow": "vitest run src/setup-databases.test.ts src/scan.test.ts src/commands/connection-metabase-setup.test.ts src/setup-models.test.ts src/setup-sources.test.ts src/setup.test.ts src/connection.test.ts src/setup-embeddings.test.ts src/ingest.test.ts src/commands/connection-mapping.test.ts src/ingest-viz.test.ts src/demo.test.ts src/setup-project.test.ts src/sl.test.ts src/local-scan-connectors.test.ts src/commands/connection-notion.test.ts --testTimeout 30000",
"type-check": "tsc -p tsconfig.json --noEmit"
"test": "vitest run --exclude src/standalone-smoke.test.ts --exclude src/example-smoke.test.ts --exclude src/setup-databases.test.ts --exclude src/scan.test.ts --exclude src/commands/connection-metabase-setup.test.ts --exclude src/setup-models.test.ts --exclude src/setup-sources.test.ts --exclude src/setup.test.ts --exclude src/connection.test.ts --exclude src/setup-embeddings.test.ts --exclude src/ingest.test.ts --exclude src/commands/connection-mapping.test.ts --exclude src/ingest-viz.test.ts --exclude src/demo.test.ts --exclude src/setup-project.test.ts --exclude src/sl.test.ts --exclude src/local-scan-connectors.test.ts --exclude src/commands/connection-notion.test.ts --exclude src/context/scan/local-scan.test.ts --exclude src/context/mcp/local-project-ports.test.ts --exclude src/context/ingest/local-stage-ingest.test.ts --exclude src/context/sl/pglite-sl-search-prototype.test.ts --exclude src/context/core/git.service.test.ts --exclude src/context/ingest/local-adapters.test.ts --exclude src/context/ingest/local-bundle-ingest.test.ts --exclude src/context/ingest/local-metabase-ingest.test.ts --exclude src/context/sl/local-sl.test.ts --exclude src/context/search/pglite-owner-process.test.ts --exclude src/context/scan/local-enrichment-artifacts.test.ts --exclude src/context/search/pglite-spike.test.ts --exclude src/context/wiki/local-knowledge.test.ts --exclude src/context/sl/local-query.test.ts --exclude src/context/scan/relationship-review-decisions.test.ts --exclude src/context/scan/relationship-profiling.test.ts",
"test:slow": "vitest run src/setup-databases.test.ts src/scan.test.ts src/commands/connection-metabase-setup.test.ts src/setup-models.test.ts src/setup-sources.test.ts src/setup.test.ts src/connection.test.ts src/setup-embeddings.test.ts src/ingest.test.ts src/commands/connection-mapping.test.ts src/ingest-viz.test.ts src/demo.test.ts src/setup-project.test.ts src/sl.test.ts src/local-scan-connectors.test.ts src/commands/connection-notion.test.ts src/context/scan/local-scan.test.ts src/context/mcp/local-project-ports.test.ts src/context/ingest/local-stage-ingest.test.ts src/context/sl/pglite-sl-search-prototype.test.ts src/context/core/git.service.test.ts src/context/ingest/local-adapters.test.ts src/context/ingest/local-bundle-ingest.test.ts src/context/ingest/local-metabase-ingest.test.ts src/context/sl/local-sl.test.ts src/context/search/pglite-owner-process.test.ts src/context/scan/local-enrichment-artifacts.test.ts src/context/search/pglite-spike.test.ts src/context/wiki/local-knowledge.test.ts src/context/sl/local-query.test.ts src/context/scan/relationship-review-decisions.test.ts src/context/scan/relationship-profiling.test.ts --testTimeout 30000",
"type-check": "tsc -p tsconfig.json --noEmit",
"relationships:benchmarks": "pnpm --silent run build && node ../../scripts/relationship-benchmark-report.mjs",
"relationships:benchmarks:test": "KTX_RUN_RELATIONSHIP_BENCHMARKS=1 vitest run src/context/scan/relationship-benchmarks.test.ts",
"search:pglite-spike": "node ../../scripts/pglite-hybrid-search-spike.mjs",
"search:pglite-owner-prototype": "node ../../scripts/pglite-owner-process-prototype.mjs",
"search:pglite-sl-prototype": "node ../../scripts/pglite-sl-search-prototype.mjs"
},
"dependencies": {
"@ai-sdk/anthropic": "3.0.77",
"@ai-sdk/devtools": "0.0.17",
"@ai-sdk/google-vertex": "^4.0.128",
"@anthropic-ai/claude-agent-sdk": "0.3.142",
"@clack/prompts": "1.4.0",
"@clickhouse/client": "^1.18.4",
"@commander-js/extra-typings": "14.0.0",
"@ktx/connector-bigquery": "workspace:*",
"@ktx/connector-clickhouse": "workspace:*",
"@ktx/connector-mysql": "workspace:*",
"@ktx/connector-postgres": "workspace:*",
"@ktx/connector-snowflake": "workspace:*",
"@ktx/connector-sqlite": "workspace:*",
"@ktx/connector-sqlserver": "workspace:*",
"@ktx/context": "workspace:*",
"@ktx/llm": "workspace:*",
"@google-cloud/bigquery": "^8.3.1",
"@looker/sdk": "^26.8.0",
"@looker/sdk-node": "^26.8.0",
"@looker/sdk-rtl": "^21.6.5",
"@modelcontextprotocol/sdk": "^1.29.0",
"@notionhq/client": "^5.21.0",
"ai": "^6.0.180",
"better-sqlite3": "^12.10.0",
"commander": "14.0.3",
"fflate": "^0.8.2",
"handlebars": "^4.7.9",
"ink": "^7.0.2",
"lookml-parser": "7.1.0",
"minimatch": "^10.2.5",
"mssql": "^12.5.2",
"mysql2": "^3.22.3",
"openai": "^6.37.0",
"p-limit": "^7.3.0",
"pg": "^8.20.0",
"react": "^19.2.6",
"simple-git": "3.36.0",
"snowflake-sdk": "^2.4.1",
"yaml": "^2.9.0",
"zod": "^4.4.3"
},
"devDependencies": {
"@electric-sql/pglite": "^0.4.5",
"@electric-sql/pglite-socket": "^0.1.5",
"@types/better-sqlite3": "^7.6.13",
"@types/mssql": "^12.3.0",
"@types/node": "^25.7.0",
"@types/pg": "^8.20.0",
"@types/react": "^19.2.14",
"@vitest/coverage-v8": "^4.1.6",
"better-sqlite3": "^12.10.0",
"ajv": "8.20.0",
"ink-testing-library": "^4.0.0",
"typescript": "^6.0.3",
"vitest": "^4.1.6"

View file

@ -3,9 +3,14 @@ import { dirname, join } from 'node:path';
import { fileURLToPath } from 'node:url';
const packageRoot = fileURLToPath(new URL('..', import.meta.url));
const promptsSource = join(packageRoot, 'src', 'prompts');
const promptsTarget = join(packageRoot, 'dist', 'prompts');
const skillsSource = join(packageRoot, 'src', 'skills');
const skillsTarget = join(packageRoot, 'dist', 'skills');
await rm(promptsTarget, { recursive: true, force: true });
await rm(skillsTarget, { recursive: true, force: true });
await mkdir(dirname(promptsTarget), { recursive: true });
await mkdir(dirname(skillsTarget), { recursive: true });
await cp(promptsSource, promptsTarget, { recursive: true });
await cp(skillsSource, skillsTarget, { recursive: true });

View file

@ -1,6 +1,6 @@
import { createRequire } from 'node:module';
import type { ReindexSummary } from '@ktx/context/index-sync';
import type { ReindexSummary } from './context/index-sync/index.js';
import { describe, expect, it, vi } from 'vitest';
import { renderReindexJson, renderReindexPlain, reindexHasErrors } from './admin-reindex.js';
import { runKtxCli } from './index.js';

View file

@ -1,6 +1,6 @@
import { KtxIngestEmbeddingPortAdapter, type KtxEmbeddingPort } from '@ktx/context';
import { reindexLocalIndexes, type ReindexScopeResult, type ReindexSummary } from '@ktx/context/index-sync';
import { loadKtxProject } from '@ktx/context/project';
import { KtxIngestEmbeddingPortAdapter, type KtxEmbeddingPort } from './context/index.js';
import { reindexLocalIndexes, type ReindexScopeResult, type ReindexSummary } from './context/index-sync/index.js';
import { loadKtxProject } from './context/project/index.js';
import { Option, type Command } from '@commander-js/extra-typings';
import { cancel, intro, log, note, outro } from '@clack/prompts';
import type { KtxCliCommandContext } from './cli-program.js';

View file

@ -50,7 +50,7 @@ export function registerAdminCommands(program: Command, context: KtxCliCommandCo
.description('Print a JSON Schema describing ktx.yaml (for editors and LLM agents)')
.option('--output <file>', 'Write the schema to a file instead of stdout')
.action(async (options: { output?: string }) => {
const { generateKtxProjectConfigJsonSchema } = await import('@ktx/context/project');
const { generateKtxProjectConfigJsonSchema } = await import('./context/project/index.js');
const json = `${JSON.stringify(generateKtxProjectConfigJsonSchema(), null, 2)}\n`;
if (options.output) {
const { writeFile } = await import('node:fs/promises');

View file

@ -1,4 +1,4 @@
import type { KtxProjectLlmConfig } from '@ktx/context/project';
import type { KtxProjectLlmConfig } from './context/project/index.js';
const CLAUDE_CODE_IGNORED_PROMPT_CACHING_FIELDS = [
'systemTtl',

View file

@ -14,7 +14,6 @@ function stubPackageInfo(): KtxCliPackageInfo {
return {
name: '@ktx/cli',
version: '0.0.0-test',
contextPackageName: '@ktx/context',
};
}

View file

@ -1,5 +1,5 @@
import { describe, expect, it, vi } from 'vitest';
import { buildDefaultKtxProjectConfig, type KtxLocalProject, type KtxProjectConfig } from '@ktx/context/project';
import { buildDefaultKtxProjectConfig, type KtxLocalProject, type KtxProjectConfig } from './context/project/index.js';
import { loadKtxCliProject } from './cli-project.js';
function projectWithConfig(config: KtxProjectConfig): KtxLocalProject {

View file

@ -1,4 +1,4 @@
import { loadKtxProject, type KtxLocalProject } from '@ktx/context/project';
import { loadKtxProject, type KtxLocalProject } from './context/project/index.js';
export interface LoadKtxCliProjectOptions {
projectDir: string;

View file

@ -20,7 +20,6 @@ const requirePackageJson = createRequire(import.meta.url);
export interface KtxCliPackageInfo {
name: string;
version: string;
contextPackageName: '@ktx/context';
}
export interface KtxCliIo {
@ -67,12 +66,11 @@ export function packageInfoFromJson(packageJson: unknown): KtxCliPackageInfo {
return {
name: packageJson.name,
version: assertCliVersion(packageJson.version, `${packageJson.name}/package.json`),
contextPackageName: '@ktx/context',
};
}
async function runInit(args: { projectDir: string; force: boolean }, io: KtxCliIo): Promise<number> {
const { initKtxProject } = await import('@ktx/context/project');
const { initKtxProject } = await import('./context/project/index.js');
const result = await initKtxProject({
projectDir: args.projectDir,
force: args.force,

View file

@ -11,7 +11,7 @@ function makeContext(overrides: Partial<KtxCliCommandContext> = {}): KtxCliComma
stderr: { write: vi.fn() },
},
deps: {},
packageInfo: { name: '@ktx/cli', version: '0.0.0-test', contextPackageName: '@ktx/context' },
packageInfo: { name: '@ktx/cli', version: '0.0.0-test' },
setExitCode: (code) => {
exitCode = code;
},

View file

@ -11,7 +11,7 @@ function makeContext(overrides: Partial<KtxCliCommandContext> = {}): KtxCliComma
stderr: { write: vi.fn() },
},
deps: {},
packageInfo: { name: '@ktx/cli', version: '0.0.0-test', contextPackageName: '@ktx/context' },
packageInfo: { name: '@ktx/cli', version: '0.0.0-test' },
setExitCode: (code) => {
exitCode = code;
},

View file

@ -1,9 +1,9 @@
import { mkdtemp, readFile, rm, writeFile } from 'node:fs/promises';
import { tmpdir } from 'node:os';
import { join } from 'node:path';
import type { LookerClient, MetabaseRuntimeClient, NotionClient } from '@ktx/context/ingest';
import { initKtxProject, parseKtxProjectConfig, serializeKtxProjectConfig } from '@ktx/context/project';
import type { KtxConnectionDriver, KtxScanConnector } from '@ktx/context/scan';
import type { LookerClient, MetabaseRuntimeClient, NotionClient } from './context/ingest/index.js';
import { initKtxProject, parseKtxProjectConfig, serializeKtxProjectConfig } from './context/project/index.js';
import type { KtxConnectionDriver, KtxScanConnector } from './context/scan/index.js';
import { afterEach, beforeEach, describe, expect, it, vi } from 'vitest';
import { runKtxConnection } from './connection.js';

View file

@ -9,11 +9,11 @@ import {
createLocalLookerCredentialResolver,
metabaseRuntimeConfigFromLocalConnection,
testRepoConnection,
} from '@ktx/context/ingest';
import { parseNotionConnectionConfig, resolveNotionConnectionAuthToken } from '@ktx/context/connections';
import { resolveKtxConfigReference } from '@ktx/context/core';
import { type KtxLocalProject, loadKtxProject } from '@ktx/context/project';
import type { KtxScanConnector } from '@ktx/context/scan';
} from './context/ingest/index.js';
import { parseNotionConnectionConfig, resolveNotionConnectionAuthToken } from './context/connections/index.js';
import { resolveKtxConfigReference } from './context/core/index.js';
import { type KtxLocalProject, loadKtxProject } from './context/project/index.js';
import type { KtxScanConnector } from './context/scan/index.js';
import type { KtxCliIo } from './index.js';
import { bold, dim, green, red, SYMBOLS } from './io/symbols.js';
import { createKtxCliScanConnector } from './local-scan-connectors.js';

View file

@ -1,5 +1,5 @@
import { BigQuery, type TableField } from '@google-cloud/bigquery';
import { assertReadOnlySql, limitSqlForExecution } from '@ktx/context/connections';
import { assertReadOnlySql, limitSqlForExecution } from '../../context/connections/index.js';
import {
createKtxConnectorCapabilities,
type KtxColumnSampleInput,
@ -18,7 +18,7 @@ import {
type KtxTableRef,
type KtxTableSampleInput,
type KtxTableSampleResult,
} from '@ktx/context/scan';
} from '../../context/scan/index.js';
import { readFileSync } from 'node:fs';
import { homedir } from 'node:os';
import { resolve } from 'node:path';

View file

@ -1,4 +1,4 @@
import type { KtxSchemaDimensionType, KtxTableRef } from '@ktx/context/scan';
import type { KtxSchemaDimensionType, KtxTableRef } from '../../context/scan/index.js';
type BigQueryTableNameRef = Pick<KtxTableRef, 'name'> & Partial<Pick<KtxTableRef, 'catalog' | 'db'>>;

View file

@ -1,5 +1,5 @@
import type { LiveDatabaseIntrospectionPort } from '@ktx/context/ingest';
import type { KtxProjectConnectionConfig } from '@ktx/context/project';
import type { LiveDatabaseIntrospectionPort } from '../../context/ingest/index.js';
import type { KtxProjectConnectionConfig } from '../../context/project/index.js';
import {
KtxBigQueryScanConnector,
type KtxBigQueryClientFactory,

View file

@ -1,5 +1,5 @@
import { createClient } from '@clickhouse/client';
import { assertReadOnlySql, limitSqlForExecution } from '@ktx/context/connections';
import { assertReadOnlySql, limitSqlForExecution } from '../../context/connections/index.js';
import {
createKtxConnectorCapabilities,
type KtxColumnSampleInput,
@ -18,7 +18,7 @@ import {
type KtxTableSampleInput,
type KtxTableListEntry,
type KtxTableSampleResult,
} from '@ktx/context/scan';
} from '../../context/scan/index.js';
import { readFileSync } from 'node:fs';
import { Agent as HttpsAgent } from 'node:https';
import { homedir } from 'node:os';

View file

@ -1,4 +1,4 @@
import type { KtxSchemaDimensionType, KtxTableRef } from '@ktx/context/scan';
import type { KtxSchemaDimensionType, KtxTableRef } from '../../context/scan/index.js';
type ClickHouseTableNameRef = Pick<KtxTableRef, 'name'> & Partial<Pick<KtxTableRef, 'catalog' | 'db'>>;

View file

@ -1,5 +1,5 @@
import type { LiveDatabaseIntrospectionPort } from '@ktx/context/ingest';
import type { KtxProjectConnectionConfig } from '@ktx/context/project';
import type { LiveDatabaseIntrospectionPort } from '../../context/ingest/index.js';
import type { KtxProjectConnectionConfig } from '../../context/project/index.js';
import {
KtxClickHouseScanConnector,
type KtxClickHouseClientFactory,

View file

@ -2,7 +2,7 @@ import mysql, { type FieldPacket, type Pool, type RowDataPacket } from 'mysql2/p
import { readFileSync } from 'node:fs';
import { homedir } from 'node:os';
import { resolve } from 'node:path';
import { assertReadOnlySql, limitSqlForExecution } from '@ktx/context/connections';
import { assertReadOnlySql, limitSqlForExecution } from '../../context/connections/index.js';
import {
createKtxConnectorCapabilities,
type KtxColumnSampleInput,
@ -22,7 +22,7 @@ import {
type KtxTableRef,
type KtxTableSampleInput,
type KtxTableSampleResult,
} from '@ktx/context/scan';
} from '../../context/scan/index.js';
import { KtxMysqlDialect } from './dialect.js';
export interface KtxMysqlConnectionConfig {

View file

@ -1,4 +1,4 @@
import type { KtxSchemaDimensionType, KtxTableRef } from '@ktx/context/scan';
import type { KtxSchemaDimensionType, KtxTableRef } from '../../context/scan/index.js';
type MysqlTableNameRef = Pick<KtxTableRef, 'name'> & Partial<Pick<KtxTableRef, 'catalog' | 'db'>>;

View file

@ -1,5 +1,5 @@
import type { LiveDatabaseIntrospectionPort } from '@ktx/context/ingest';
import type { KtxProjectConnectionConfig } from '@ktx/context/project';
import type { LiveDatabaseIntrospectionPort } from '../../context/ingest/index.js';
import type { KtxProjectConnectionConfig } from '../../context/project/index.js';
import {
KtxMysqlScanConnector,
type KtxMysqlConnectionConfig,

View file

@ -1,7 +1,7 @@
import { readFileSync } from 'node:fs';
import { homedir } from 'node:os';
import { resolve } from 'node:path';
import { assertReadOnlySql, limitSqlForExecution } from '@ktx/context/connections';
import { assertReadOnlySql, limitSqlForExecution } from '../../context/connections/index.js';
import {
createKtxConnectorCapabilities,
type KtxColumnSampleInput,
@ -21,7 +21,7 @@ import {
type KtxTableRef,
type KtxTableSampleInput,
type KtxTableSampleResult,
} from '@ktx/context/scan';
} from '../../context/scan/index.js';
import { Pool } from 'pg';
import { KtxPostgresDialect } from './dialect.js';

View file

@ -1,4 +1,4 @@
import type { KtxSchemaDimensionType, KtxTableRef } from '@ktx/context/scan';
import type { KtxSchemaDimensionType, KtxTableRef } from '../../context/scan/index.js';
type PostgresTableNameRef = Pick<KtxTableRef, 'name'> & Partial<Pick<KtxTableRef, 'catalog' | 'db'>>;

View file

@ -1,4 +1,4 @@
import type { KtxPostgresQueryClient } from '@ktx/context/ingest';
import type { KtxPostgresQueryClient } from '../../context/ingest/index.js';
import { KtxPostgresScanConnector, type KtxPostgresScanConnectorOptions } from './connector.js';
export type KtxPostgresHistoricSqlQueryClientOptions = KtxPostgresScanConnectorOptions;

View file

@ -1,5 +1,5 @@
import type { LiveDatabaseIntrospectionPort } from '@ktx/context/ingest';
import type { KtxProjectConnectionConfig } from '@ktx/context/project';
import type { LiveDatabaseIntrospectionPort } from '../../context/ingest/index.js';
import type { KtxProjectConnectionConfig } from '../../context/project/index.js';
import {
KtxPostgresScanConnector,
type KtxPostgresConnectionConfig,

View file

@ -2,7 +2,7 @@ import { createPrivateKey } from 'node:crypto';
import { readFileSync } from 'node:fs';
import { homedir } from 'node:os';
import { resolve } from 'node:path';
import { assertReadOnlySql, limitSqlForExecution } from '@ktx/context/connections';
import { assertReadOnlySql, limitSqlForExecution } from '../../context/connections/index.js';
import {
createKtxConnectorCapabilities,
type KtxColumnSampleInput,
@ -21,7 +21,7 @@ import {
type KtxTableSampleInput,
type KtxTableListEntry,
type KtxTableSampleResult,
} from '@ktx/context/scan';
} from '../../context/scan/index.js';
import * as snowflake from 'snowflake-sdk';
import { KtxSnowflakeDialect } from './dialect.js';

View file

@ -1,4 +1,4 @@
import type { KtxSchemaDimensionType, KtxTableRef } from '@ktx/context/scan';
import type { KtxSchemaDimensionType, KtxTableRef } from '../../context/scan/index.js';
type SnowflakeTableNameRef = Pick<KtxTableRef, 'name'> & Partial<Pick<KtxTableRef, 'catalog' | 'db'>>;

View file

@ -1,5 +1,5 @@
import type { LiveDatabaseIntrospectionPort } from '@ktx/context/ingest';
import type { KtxProjectConnectionConfig } from '@ktx/context/project';
import type { LiveDatabaseIntrospectionPort } from '../../context/ingest/index.js';
import type { KtxProjectConnectionConfig } from '../../context/project/index.js';
import {
KtxSnowflakeScanConnector,
type KtxSnowflakeConnectionConfig,

View file

@ -3,7 +3,7 @@ import { existsSync, readFileSync, statSync } from 'node:fs';
import { homedir } from 'node:os';
import { isAbsolute, resolve } from 'node:path';
import { fileURLToPath } from 'node:url';
import { assertReadOnlySql, limitSqlForExecution, normalizeQueryRows } from '@ktx/context/connections';
import { assertReadOnlySql, limitSqlForExecution, normalizeQueryRows } from '../../context/connections/index.js';
import {
createKtxConnectorCapabilities,
type KtxColumnSampleInput,
@ -21,7 +21,7 @@ import {
type KtxTableRef,
type KtxTableSampleInput,
type KtxTableSampleResult,
} from '@ktx/context/scan';
} from '../../context/scan/index.js';
import { KtxSqliteDialect } from './dialect.js';
export interface KtxSqliteConnectionConfig {

View file

@ -1,4 +1,4 @@
import type { KtxSchemaDimensionType, KtxTableRef } from '@ktx/context/scan';
import type { KtxSchemaDimensionType, KtxTableRef } from '../../context/scan/index.js';
type SqliteTableNameRef = Pick<KtxTableRef, 'name'> & Partial<Pick<KtxTableRef, 'catalog' | 'db'>>;

View file

@ -1,5 +1,5 @@
import type { LiveDatabaseIntrospectionPort } from '@ktx/context/ingest';
import type { KtxProjectConnectionConfig } from '@ktx/context/project';
import type { LiveDatabaseIntrospectionPort } from '../../context/ingest/index.js';
import type { KtxProjectConnectionConfig } from '../../context/project/index.js';
import { KtxSqliteScanConnector, type KtxSqliteConnectionConfig } from './connector.js';
export interface CreateSqliteLiveDatabaseIntrospectionOptions {

View file

@ -1,4 +1,4 @@
import { assertReadOnlySql } from '@ktx/context/connections';
import { assertReadOnlySql } from '../../context/connections/index.js';
import {
createKtxConnectorCapabilities,
type KtxColumnSampleInput,
@ -18,7 +18,7 @@ import {
type KtxTableRef,
type KtxTableSampleInput,
type KtxTableSampleResult,
} from '@ktx/context/scan';
} from '../../context/scan/index.js';
import { readFileSync } from 'node:fs';
import { homedir } from 'node:os';
import { resolve } from 'node:path';

View file

@ -1,4 +1,4 @@
import type { KtxSchemaDimensionType, KtxTableRef } from '@ktx/context/scan';
import type { KtxSchemaDimensionType, KtxTableRef } from '../../context/scan/index.js';
type SqlServerTableNameRef = Pick<KtxTableRef, 'name'> & Partial<Pick<KtxTableRef, 'catalog' | 'db'>>;

View file

@ -1,5 +1,5 @@
import type { LiveDatabaseIntrospectionPort } from '@ktx/context/ingest';
import type { KtxProjectConnectionConfig } from '@ktx/context/project';
import type { LiveDatabaseIntrospectionPort } from '../../context/ingest/index.js';
import type { KtxProjectConnectionConfig } from '../../context/project/index.js';
import {
KtxSqlServerScanConnector,
type KtxSqlServerConnectionConfig,

View file

@ -1,4 +1,4 @@
import { buildDefaultKtxProjectConfig, type KtxProjectConfig } from '@ktx/context/project';
import { buildDefaultKtxProjectConfig, type KtxProjectConfig } from './context/project/index.js';
import { describe, expect, it, vi } from 'vitest';
import type { KtxPublicIngestProject, KtxPublicIngestTargetResult } from './public-ingest.js';
import {

View file

@ -1,4 +1,4 @@
import type { KtxProgressPort, KtxProgressUpdateOptions } from '@ktx/context/scan';
import type { KtxProgressPort, KtxProgressUpdateOptions } from './context/scan/index.js';
import type { KtxCliIo } from './index.js';
import type { KtxIngestProgressUpdate } from './ingest.js';
import type { KtxManagedPythonInstallPolicy } from './managed-python-command.js';

Some files were not shown because too many files have changed in this diff Show more