ndi-cli 0.28.0__tar.gz → 0.29.0__tar.gz
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- {ndi_cli-0.28.0 → ndi_cli-0.29.0}/PKG-INFO +3 -3
- {ndi_cli-0.28.0 → ndi_cli-0.29.0}/README.md +1 -1
- {ndi_cli-0.28.0 → ndi_cli-0.29.0}/pyproject.toml +2 -2
- {ndi_cli-0.28.0 → ndi_cli-0.29.0}/pyproject.toml.orig +2 -2
- {ndi_cli-0.28.0 → ndi_cli-0.29.0}/src/ndi_cli/__init__.py +1 -1
- {ndi_cli-0.28.0 → ndi_cli-0.29.0}/src/ndi_cli/_output.py +1 -1
- {ndi_cli-0.28.0 → ndi_cli-0.29.0}/src/ndi_cli/_render.py +21 -1
- {ndi_cli-0.28.0 → ndi_cli-0.29.0}/LICENSE +0 -0
- {ndi_cli-0.28.0 → ndi_cli-0.29.0}/src/ndi_cli/_cli.py +0 -0
- {ndi_cli-0.28.0 → ndi_cli-0.29.0}/src/ndi_cli/_config.py +0 -0
- {ndi_cli-0.28.0 → ndi_cli-0.29.0}/src/ndi_cli/_docops.py +0 -0
- {ndi_cli-0.28.0 → ndi_cli-0.29.0}/src/ndi_cli/_entrypoint.py +0 -0
- {ndi_cli-0.28.0 → ndi_cli-0.29.0}/src/ndi_cli/_jobs.py +0 -0
- {ndi_cli-0.28.0 → ndi_cli-0.29.0}/src/ndi_cli/_local.py +0 -0
- {ndi_cli-0.28.0 → ndi_cli-0.29.0}/src/ndi_cli/_login.py +0 -0
- {ndi_cli-0.28.0 → ndi_cli-0.29.0}/src/ndi_cli/_sources.py +0 -0
- {ndi_cli-0.28.0 → ndi_cli-0.29.0}/src/ndi_cli/_systemone.py +0 -0
- {ndi_cli-0.28.0 → ndi_cli-0.29.0}/src/ndi_cli/_tools.py +0 -0
- {ndi_cli-0.28.0 → ndi_cli-0.29.0}/src/ndi_cli/_workspace.py +0 -0
- {ndi_cli-0.28.0 → ndi_cli-0.29.0}/src/ndi_cli/commands.py +0 -0
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
Metadata-Version: 2.4
|
|
2
2
|
Name: ndi-cli
|
|
3
|
-
Version: 0.
|
|
3
|
+
Version: 0.29.0
|
|
4
4
|
Summary: NDI platform CLI: document operations, jobs, workspaces, and the agent workspace tools
|
|
5
5
|
Keywords: ndi,cli,document-intelligence,coding-agents
|
|
6
6
|
Author: Nace AI
|
|
@@ -16,7 +16,7 @@ Classifier: Programming Language :: Python :: 3.13
|
|
|
16
16
|
Classifier: Programming Language :: Python :: 3.14
|
|
17
17
|
Classifier: Topic :: Software Development :: Libraries :: Python Modules
|
|
18
18
|
Classifier: Typing :: Typed
|
|
19
|
-
Requires-Dist: ndi-sdk>=0.
|
|
19
|
+
Requires-Dist: ndi-sdk>=0.50,<1
|
|
20
20
|
Requires-Dist: truststore>=0.10.4,<1
|
|
21
21
|
Requires-Python: >=3.11
|
|
22
22
|
Project-URL: Homepage, https://ndi-api.nace.ai
|
|
@@ -98,7 +98,7 @@ to **stderr**. `-o auto|md|json|payload|id` picks the shape. `--json` is an
|
|
|
98
98
|
alias for `-o json`.
|
|
99
99
|
|
|
100
100
|
The default (`auto`) prints the full JSON response. When that is over
|
|
101
|
-
`$NDI_OUTPUT_LIMIT` characters (default
|
|
101
|
+
`$NDI_OUTPUT_LIMIT` characters (default 400,000), the compact text rendering
|
|
102
102
|
prints instead and stderr carries `note: output shortened …` with the full
|
|
103
103
|
size. `--json` always prints it whole, and `--save` / `--out-dir` always write
|
|
104
104
|
it whole. Commands whose output is the content itself (`ws context`, parse
|
|
@@ -74,7 +74,7 @@ to **stderr**. `-o auto|md|json|payload|id` picks the shape. `--json` is an
|
|
|
74
74
|
alias for `-o json`.
|
|
75
75
|
|
|
76
76
|
The default (`auto`) prints the full JSON response. When that is over
|
|
77
|
-
`$NDI_OUTPUT_LIMIT` characters (default
|
|
77
|
+
`$NDI_OUTPUT_LIMIT` characters (default 400,000), the compact text rendering
|
|
78
78
|
prints instead and stderr carries `note: output shortened …` with the full
|
|
79
79
|
size. `--json` always prints it whole, and `--save` / `--out-dir` always write
|
|
80
80
|
it whole. Commands whose output is the content itself (`ws context`, parse
|
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
[project]
|
|
2
2
|
name = "ndi-cli"
|
|
3
|
-
version = "0.
|
|
3
|
+
version = "0.29.0"
|
|
4
4
|
description = "NDI platform CLI: document operations, jobs, workspaces, and the agent workspace tools"
|
|
5
5
|
readme = "README.md"
|
|
6
6
|
license = "MIT"
|
|
@@ -24,7 +24,7 @@ classifiers = [
|
|
|
24
24
|
"Typing :: Typed",
|
|
25
25
|
]
|
|
26
26
|
dependencies = [
|
|
27
|
-
"ndi-sdk>=0.
|
|
27
|
+
"ndi-sdk>=0.50,<1",
|
|
28
28
|
"truststore>=0.10.4,<1",
|
|
29
29
|
]
|
|
30
30
|
|
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
[project]
|
|
2
2
|
name = "ndi-cli"
|
|
3
|
-
version = "0.
|
|
3
|
+
version = "0.29.0"
|
|
4
4
|
description = "NDI platform CLI: document operations, jobs, workspaces, and the agent workspace tools"
|
|
5
5
|
authors = [
|
|
6
6
|
{ name = "Nace AI", email = "engineering@nace.ai" }
|
|
@@ -27,7 +27,7 @@ classifiers = [
|
|
|
27
27
|
"Typing :: Typed",
|
|
28
28
|
]
|
|
29
29
|
dependencies = [
|
|
30
|
-
"ndi-sdk>=0.
|
|
30
|
+
"ndi-sdk>=0.50,<1",
|
|
31
31
|
"truststore>=0.10.4,<1",
|
|
32
32
|
]
|
|
33
33
|
|
|
@@ -15,7 +15,7 @@ OUTPUT_CHOICES = ("auto", "md", "json", "payload", "id")
|
|
|
15
15
|
#: Default output is the full JSON response while it stays within this many
|
|
16
16
|
#: characters on stdout. Past it the compact text rendering stands in, so one
|
|
17
17
|
#: command cannot flood a reading agent's context; a stderr note says so.
|
|
18
|
-
FULL_OUTPUT_LIMIT =
|
|
18
|
+
FULL_OUTPUT_LIMIT = 400_000
|
|
19
19
|
OUTPUT_LIMIT_ENV = "NDI_OUTPUT_LIMIT"
|
|
20
20
|
|
|
21
21
|
|
|
@@ -324,6 +324,8 @@ def file_metadata(response: FileMetadataToolResponse) -> str:
|
|
|
324
324
|
lines.append(f"summary: {response.summary}")
|
|
325
325
|
if response.components:
|
|
326
326
|
lines.append(f"components ({len(response.components)}):")
|
|
327
|
+
# A document's long-table sections share one rows table: its schema and preamble print once.
|
|
328
|
+
shown_tables: set[str] = set()
|
|
327
329
|
for comp in response.components:
|
|
328
330
|
if comp.kind == "media":
|
|
329
331
|
seconds = comp.duration_ms / 1000
|
|
@@ -353,8 +355,20 @@ def file_metadata(response: FileMetadataToolResponse) -> str:
|
|
|
353
355
|
lines.append(f" [{comp.kind}] {name} — {tail}")
|
|
354
356
|
if comp.summary:
|
|
355
357
|
lines.append(f" {comp.summary}")
|
|
356
|
-
|
|
358
|
+
shared = comp.kind == "section" and comp.columns and any(col.name == "origin" for col in comp.columns)
|
|
359
|
+
shown = comp.table_name in shown_tables
|
|
360
|
+
if shared and not shown:
|
|
361
|
+
lines.append(
|
|
362
|
+
f" {comp.table_name}: one SQL table for every section that lists it; "
|
|
363
|
+
"a section's rows are the ones printed on its pages"
|
|
364
|
+
)
|
|
365
|
+
if comp.columns and not (shared and shown):
|
|
357
366
|
lines.extend(_column_lines(comp.columns, bool(comp.columns_truncated)))
|
|
367
|
+
if comp.table_preamble and not shown:
|
|
368
|
+
lines.append(" printed above its first table:")
|
|
369
|
+
lines.extend(f" {text}" for text in comp.table_preamble.splitlines())
|
|
370
|
+
if comp.table_name:
|
|
371
|
+
shown_tables.add(comp.table_name)
|
|
358
372
|
if comp.error:
|
|
359
373
|
lines.append(f" error: {comp.error}")
|
|
360
374
|
return "\n".join(lines)
|
|
@@ -737,6 +751,7 @@ def search_job(job: Job) -> str:
|
|
|
737
751
|
result.answer,
|
|
738
752
|
result.clarification,
|
|
739
753
|
result.evidences,
|
|
754
|
+
reasoning=result.reasoning,
|
|
740
755
|
receipts=len(result.sql_receipts),
|
|
741
756
|
grounding_job_ids=result.grounding_job_ids,
|
|
742
757
|
)
|
|
@@ -747,6 +762,7 @@ def search_job(job: Job) -> str:
|
|
|
747
762
|
result.answer,
|
|
748
763
|
result.clarification,
|
|
749
764
|
result.evidences,
|
|
765
|
+
reasoning=result.reasoning,
|
|
750
766
|
receipts=0,
|
|
751
767
|
grounding_job_ids=result.grounding_job_ids,
|
|
752
768
|
)
|
|
@@ -1025,6 +1041,7 @@ def _search_result(
|
|
|
1025
1041
|
clarification: str | None,
|
|
1026
1042
|
evidences: list,
|
|
1027
1043
|
*,
|
|
1044
|
+
reasoning: str | None = None,
|
|
1028
1045
|
receipts: int,
|
|
1029
1046
|
grounding_job_ids: list[uuid.UUID] | None = None,
|
|
1030
1047
|
) -> str:
|
|
@@ -1033,6 +1050,9 @@ def _search_result(
|
|
|
1033
1050
|
lines.append(f"clarification: {clarification}")
|
|
1034
1051
|
if answer:
|
|
1035
1052
|
lines.append(answer.strip())
|
|
1053
|
+
if reasoning:
|
|
1054
|
+
# An agent answer cites the evidences numbered below as [1], [2], ….
|
|
1055
|
+
lines.append(f"reasoning: {reasoning.strip()}")
|
|
1036
1056
|
lines.append(f"evidences ({len(evidences)}):")
|
|
1037
1057
|
for index, evidence in enumerate(evidences, start=1):
|
|
1038
1058
|
page = f", page {evidence.page}" if evidence.page is not None else ""
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|