scriptoria 0.6.1__tar.gz → 0.6.2__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.
- {scriptoria-0.6.1 → scriptoria-0.6.2}/PKG-INFO +1 -1
- {scriptoria-0.6.1 → scriptoria-0.6.2}/pyproject.toml +1 -1
- {scriptoria-0.6.1 → scriptoria-0.6.2}/src/scrip/__init__.py +1 -1
- {scriptoria-0.6.1 → scriptoria-0.6.2}/src/scrip/query.py +19 -10
- {scriptoria-0.6.1 → scriptoria-0.6.2}/tests/test_query.py +24 -0
- {scriptoria-0.6.1 → scriptoria-0.6.2}/uv.lock +1 -1
- {scriptoria-0.6.1 → scriptoria-0.6.2}/.gitignore +0 -0
- {scriptoria-0.6.1 → scriptoria-0.6.2}/README.md +0 -0
- {scriptoria-0.6.1 → scriptoria-0.6.2}/pyrightconfig.json +0 -0
- {scriptoria-0.6.1 → scriptoria-0.6.2}/src/scrip/anchors.py +0 -0
- {scriptoria-0.6.1 → scriptoria-0.6.2}/src/scrip/blocks.py +0 -0
- {scriptoria-0.6.1 → scriptoria-0.6.2}/src/scrip/cli.py +0 -0
- {scriptoria-0.6.1 → scriptoria-0.6.2}/src/scrip/embeddings.py +0 -0
- {scriptoria-0.6.1 → scriptoria-0.6.2}/src/scrip/errors.py +0 -0
- {scriptoria-0.6.1 → scriptoria-0.6.2}/src/scrip/facts.py +0 -0
- {scriptoria-0.6.1 → scriptoria-0.6.2}/src/scrip/frontmatter.py +0 -0
- {scriptoria-0.6.1 → scriptoria-0.6.2}/src/scrip/graph.py +0 -0
- {scriptoria-0.6.1 → scriptoria-0.6.2}/src/scrip/hashing.py +0 -0
- {scriptoria-0.6.1 → scriptoria-0.6.2}/src/scrip/ingest.py +0 -0
- {scriptoria-0.6.1 → scriptoria-0.6.2}/src/scrip/lock.py +0 -0
- {scriptoria-0.6.1 → scriptoria-0.6.2}/src/scrip/manifest.py +0 -0
- {scriptoria-0.6.1 → scriptoria-0.6.2}/src/scrip/pageindex_adapter.py +0 -0
- {scriptoria-0.6.1 → scriptoria-0.6.2}/src/scrip/retrieval.py +0 -0
- {scriptoria-0.6.1 → scriptoria-0.6.2}/src/scrip/similar.py +0 -0
- {scriptoria-0.6.1 → scriptoria-0.6.2}/tests/conftest.py +0 -0
- {scriptoria-0.6.1 → scriptoria-0.6.2}/tests/test_anchor_cmd.py +0 -0
- {scriptoria-0.6.1 → scriptoria-0.6.2}/tests/test_anchors.py +0 -0
- {scriptoria-0.6.1 → scriptoria-0.6.2}/tests/test_blocks.py +0 -0
- {scriptoria-0.6.1 → scriptoria-0.6.2}/tests/test_embeddings.py +0 -0
- {scriptoria-0.6.1 → scriptoria-0.6.2}/tests/test_fact_cmd.py +0 -0
- {scriptoria-0.6.1 → scriptoria-0.6.2}/tests/test_frontmatter.py +0 -0
- {scriptoria-0.6.1 → scriptoria-0.6.2}/tests/test_graph_status.py +0 -0
- {scriptoria-0.6.1 → scriptoria-0.6.2}/tests/test_hashing.py +0 -0
- {scriptoria-0.6.1 → scriptoria-0.6.2}/tests/test_index_cmd.py +0 -0
- {scriptoria-0.6.1 → scriptoria-0.6.2}/tests/test_ingest.py +0 -0
- {scriptoria-0.6.1 → scriptoria-0.6.2}/tests/test_json_shapes.py +0 -0
- {scriptoria-0.6.1 → scriptoria-0.6.2}/tests/test_lock.py +0 -0
- {scriptoria-0.6.1 → scriptoria-0.6.2}/tests/test_manifest.py +0 -0
- {scriptoria-0.6.1 → scriptoria-0.6.2}/tests/test_new_cmd.py +0 -0
- {scriptoria-0.6.1 → scriptoria-0.6.2}/tests/test_pageindex_cmd.py +0 -0
- {scriptoria-0.6.1 → scriptoria-0.6.2}/tests/test_retrieval.py +0 -0
- {scriptoria-0.6.1 → scriptoria-0.6.2}/tests/test_similar_cmd.py +0 -0
- {scriptoria-0.6.1 → scriptoria-0.6.2}/tests/test_span_cmd.py +0 -0
- {scriptoria-0.6.1 → scriptoria-0.6.2}/tests/test_stamp.py +0 -0
- {scriptoria-0.6.1 → scriptoria-0.6.2}/tests/test_status_cmd.py +0 -0
- {scriptoria-0.6.1 → scriptoria-0.6.2}/tests/test_unlock_cmd.py +0 -0
- {scriptoria-0.6.1 → scriptoria-0.6.2}/tests/test_verify.py +0 -0
- {scriptoria-0.6.1 → scriptoria-0.6.2}/tests/test_version.py +0 -0
- {scriptoria-0.6.1 → scriptoria-0.6.2}/tests/test_watch.py +0 -0
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
Metadata-Version: 2.4
|
|
2
2
|
Name: scriptoria
|
|
3
|
-
Version: 0.6.
|
|
3
|
+
Version: 0.6.2
|
|
4
4
|
Summary: Deterministic scriptorium-keeper (the `scrip` CLI): staleness, provenance integrity, and fact queries for an agent-compiled knowledge base
|
|
5
5
|
Project-URL: Homepage, https://github.com/coredipper/scriptorium
|
|
6
6
|
Project-URL: Changelog, https://github.com/coredipper/scriptorium/blob/main/CHANGELOG.md
|
|
@@ -2,7 +2,7 @@
|
|
|
2
2
|
# Distribution name on PyPI is `scriptoria` (scrip/scriptorium were taken); the
|
|
3
3
|
# CLI command and the import package both remain `scrip`.
|
|
4
4
|
name = "scriptoria"
|
|
5
|
-
version = "0.6.
|
|
5
|
+
version = "0.6.2"
|
|
6
6
|
description = "Deterministic scriptorium-keeper (the `scrip` CLI): staleness, provenance integrity, and fact queries for an agent-compiled knowledge base"
|
|
7
7
|
readme = "README.md"
|
|
8
8
|
requires-python = ">=3.10"
|
|
@@ -13,7 +13,7 @@ from __future__ import annotations
|
|
|
13
13
|
|
|
14
14
|
from pathlib import Path
|
|
15
15
|
|
|
16
|
-
__version__ = "0.6.
|
|
16
|
+
__version__ = "0.6.2"
|
|
17
17
|
|
|
18
18
|
# --- canonical vault layout ------------------------------------------------
|
|
19
19
|
# ``root`` is the repo/instance root: the directory containing ``vault/``.
|
|
@@ -55,26 +55,35 @@ _NAMED = {
|
|
|
55
55
|
_FILTERABLE = {"claims", "entities", "edges", "reconciliations"}
|
|
56
56
|
|
|
57
57
|
|
|
58
|
+
def _create_empty_reconciliations_view(con: duckdb.DuckDBPyConnection) -> None:
|
|
59
|
+
# Always present (empty stub) so `contradictions` can anti-join it and raw SQL
|
|
60
|
+
# over its columns works even before any reconciliation exists.
|
|
61
|
+
con.execute(
|
|
62
|
+
"CREATE VIEW reconciliations AS SELECT "
|
|
63
|
+
"NULL::VARCHAR AS reconciliation_id, NULL::VARCHAR AS decision, "
|
|
64
|
+
"NULL::VARCHAR AS claim_a, NULL::VARCHAR AS claim_b, "
|
|
65
|
+
"NULL::VARCHAR AS winner, NULL::VARCHAR AS rationale, "
|
|
66
|
+
"NULL::VARCHAR AS at WHERE FALSE"
|
|
67
|
+
)
|
|
68
|
+
|
|
69
|
+
|
|
70
|
+
def _has_rows(path: Path) -> bool:
|
|
71
|
+
with path.open(encoding="utf-8") as f:
|
|
72
|
+
return any(line.strip() for line in f)
|
|
73
|
+
|
|
74
|
+
|
|
58
75
|
def _connect(root: Path) -> duckdb.DuckDBPyConnection:
|
|
59
76
|
con = duckdb.connect(":memory:")
|
|
60
77
|
fd = facts_dir(root)
|
|
61
78
|
for view, fname in _VIEWS.items():
|
|
62
79
|
p = fd / fname
|
|
63
|
-
if p.exists():
|
|
80
|
+
if p.exists() and (view != "reconciliations" or _has_rows(p)):
|
|
64
81
|
con.execute(
|
|
65
82
|
f"CREATE VIEW {view} AS "
|
|
66
83
|
f"SELECT * FROM read_ndjson_auto('{p.as_posix()}')"
|
|
67
84
|
)
|
|
68
85
|
elif view == "reconciliations":
|
|
69
|
-
|
|
70
|
-
# raw SQL over its columns works even before any reconciliation exists.
|
|
71
|
-
con.execute(
|
|
72
|
-
"CREATE VIEW reconciliations AS SELECT "
|
|
73
|
-
"NULL::VARCHAR AS reconciliation_id, NULL::VARCHAR AS decision, "
|
|
74
|
-
"NULL::VARCHAR AS claim_a, NULL::VARCHAR AS claim_b, "
|
|
75
|
-
"NULL::VARCHAR AS winner, NULL::VARCHAR AS rationale, "
|
|
76
|
-
"NULL::VARCHAR AS at WHERE FALSE"
|
|
77
|
-
)
|
|
86
|
+
_create_empty_reconciliations_view(con)
|
|
78
87
|
return con
|
|
79
88
|
|
|
80
89
|
|
|
@@ -74,6 +74,16 @@ def test_contradictions_works_without_reconciliations_file(kb):
|
|
|
74
74
|
assert len(query.run(kb.root, name="contradictions")[1]) == 1
|
|
75
75
|
|
|
76
76
|
|
|
77
|
+
def test_contradictions_works_with_empty_reconciliations_file(kb):
|
|
78
|
+
# an existing-but-empty file should use the same stub schema as a missing file
|
|
79
|
+
_contradiction_pair(kb)
|
|
80
|
+
(kb.root / "vault" / "facts" / "reconciliations.ndjson").write_text(
|
|
81
|
+
"\n", encoding="utf-8"
|
|
82
|
+
)
|
|
83
|
+
|
|
84
|
+
assert len(query.run(kb.root, name="contradictions")[1]) == 1
|
|
85
|
+
|
|
86
|
+
|
|
77
87
|
def test_query_reconciliations_cli_choice(kb):
|
|
78
88
|
# the named query must be a valid CLI `query` choice, not just in query.run
|
|
79
89
|
_contradiction_pair(kb)
|
|
@@ -88,6 +98,20 @@ def test_reconciliations_stub_exposes_full_schema(kb):
|
|
|
88
98
|
assert "decision" in cols
|
|
89
99
|
|
|
90
100
|
|
|
101
|
+
def test_empty_reconciliations_file_exposes_full_schema(kb):
|
|
102
|
+
_contradiction_pair(kb)
|
|
103
|
+
(kb.root / "vault" / "facts" / "reconciliations.ndjson").write_text(
|
|
104
|
+
"\n", encoding="utf-8"
|
|
105
|
+
)
|
|
106
|
+
|
|
107
|
+
cols, rows = query.run(
|
|
108
|
+
kb.root,
|
|
109
|
+
sql="SELECT decision, winner, reconciliation_id FROM reconciliations",
|
|
110
|
+
)
|
|
111
|
+
assert rows == []
|
|
112
|
+
assert "decision" in cols
|
|
113
|
+
|
|
114
|
+
|
|
91
115
|
def test_where_and_limit(kb):
|
|
92
116
|
kb.add_raw("a", "# A\n\nThe sky is blue.\n")
|
|
93
117
|
kb.add_claim("clm_1", "a", "the sky is blue")
|
|
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
|
|
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
|
|
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
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|