linkedparticles 1.149.0__tar.gz → 1.151.18__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.
Files changed (713) hide show
  1. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/PKG-INFO +3 -3
  2. linkedparticles-1.151.18/alembic/versions/040_backfill_particle_tag_edges.py +88 -0
  3. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/artifacts/openapi.json +2 -1
  4. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/api/app.py +1 -1
  5. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/api/cli/audit.py +1 -1
  6. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/api/cli/benchmark.py +10 -10
  7. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/api/cli/corpus.py +52 -174
  8. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/api/cli/extractor.py +1 -1
  9. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/api/cli/init.py +1 -1
  10. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/api/cli/memory.py +3 -3
  11. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/api/cli/query.py +1 -1
  12. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/benchmark/observer/render.py +1 -1
  13. linkedparticles-1.151.18/particles/corpus/refresh_outcome.py +51 -0
  14. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/corpus/store.py +12 -1
  15. linkedparticles-1.151.18/particles/ingest/conflict_plan.py +348 -0
  16. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/ingest/narrative_merge.py +33 -17
  17. linkedparticles-1.151.18/particles/ingest/pair_selection.py +202 -0
  18. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/ingest/pending_collapse.py +24 -11
  19. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/ingest/pipeline.py +599 -727
  20. linkedparticles-1.151.18/particles/ingest/routing.py +107 -0
  21. linkedparticles-1.151.18/particles/ingest/structure_edges.py +87 -0
  22. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/ingest/subject_resolver.py +28 -18
  23. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/operations/_quarantine.py +21 -6
  24. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/operations/abstraction.py +77 -17
  25. linkedparticles-1.151.18/particles/operations/candidate_pairs.py +137 -0
  26. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/operations/cascade.py +30 -48
  27. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/operations/consolidation.py +21 -26
  28. linkedparticles-1.151.18/particles/operations/corpus_delete.py +278 -0
  29. linkedparticles-1.151.18/particles/operations/corpus_refresh.py +76 -0
  30. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/operations/graph_view.py +130 -34
  31. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/operations/links_suggest.py +108 -84
  32. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/operations/lint/contestedness.py +3 -35
  33. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/operations/lint/contradictions.py +32 -75
  34. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/operations/observer_scope.py +2 -0
  35. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/operations/query/as_of.py +4 -2
  36. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/operations/query/main.py +2 -0
  37. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/operations/reconcile.py +2 -0
  38. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/operations/reindex.py +139 -135
  39. linkedparticles-1.151.18/particles/operations/reindex_scope.py +124 -0
  40. linkedparticles-1.151.18/particles/operations/review.py +262 -0
  41. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/store/event_store.py +10 -4
  42. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/store/particle_store.py +71 -44
  43. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/store/subject_store.py +6 -4
  44. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/store/taxonomy_store.py +12 -0
  45. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/store/utility_store.py +7 -11
  46. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/pyproject.toml +7 -3
  47. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/dogfood/__init__.py +3 -6
  48. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/test_abstraction.py +308 -35
  49. linkedparticles-1.151.18/tests/test_candidate_pairs.py +224 -0
  50. linkedparticles-1.151.18/tests/test_conflict_plan.py +257 -0
  51. linkedparticles-1.151.18/tests/test_conflict_review.py +369 -0
  52. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/test_consolidation.py +3 -2
  53. linkedparticles-1.151.18/tests/test_corpus_delete_operation.py +385 -0
  54. linkedparticles-1.151.18/tests/test_decide_ladder.py +275 -0
  55. linkedparticles-1.151.18/tests/test_graph_layout.py +300 -0
  56. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/test_layer_boundary.py +49 -2
  57. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/test_mcp_write.py +19 -0
  58. linkedparticles-1.151.18/tests/test_migration_040_tag_edges.py +82 -0
  59. linkedparticles-1.151.18/tests/test_narrative_merge.py +245 -0
  60. linkedparticles-1.151.18/tests/test_no_derived_columns.py +82 -0
  61. linkedparticles-1.151.18/tests/test_pair_selection.py +305 -0
  62. linkedparticles-1.151.18/tests/test_plan_collapse.py +78 -0
  63. linkedparticles-1.151.18/tests/test_plan_unmerge_group.py +183 -0
  64. linkedparticles-1.151.18/tests/test_provenance_append_only.py +339 -0
  65. linkedparticles-1.151.18/tests/test_refresh_outcome.py +40 -0
  66. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/test_reindex.py +57 -3
  67. linkedparticles-1.151.18/tests/test_reindex_scope.py +175 -0
  68. linkedparticles-1.151.18/tests/test_resolver_alias_attach.py +179 -0
  69. linkedparticles-1.151.18/tests/test_routing.py +188 -0
  70. linkedparticles-1.151.18/tests/test_structure_edges.py +177 -0
  71. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/test_taxonomy_store.py +15 -0
  72. linkedparticles-1.149.0/particles/operations/review.py +0 -372
  73. linkedparticles-1.149.0/tests/test_narrative_merge.py +0 -142
  74. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/LICENSE +0 -0
  75. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/NOTICE +0 -0
  76. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/README.md +0 -0
  77. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/alembic/env.py +0 -0
  78. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/alembic/script.py.mako +0 -0
  79. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/alembic/versions/001_initial.py +0 -0
  80. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/alembic/versions/002_subjects.py +0 -0
  81. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/alembic/versions/003_wikidata_label_cache.py +0 -0
  82. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/alembic/versions/004_source_trust.py +0 -0
  83. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/alembic/versions/005_structured_properties.py +0 -0
  84. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/alembic/versions/006_extractor_records.py +0 -0
  85. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/alembic/versions/007_domain_hint.py +0 -0
  86. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/alembic/versions/008_content_published_at.py +0 -0
  87. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/alembic/versions/009_provenance_chunk_hash.py +0 -0
  88. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/alembic/versions/010_context_fingerprint.py +0 -0
  89. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/alembic/versions/011_particle_relations.py +0 -0
  90. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/alembic/versions/012_taxonomies.py +0 -0
  91. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/alembic/versions/013_extractor_calibration.py +0 -0
  92. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/alembic/versions/014_corpus_follow_edges.py +0 -0
  93. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/alembic/versions/015_synthesis_cache.py +0 -0
  94. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/alembic/versions/016_snapshot_extraction_started_at.py +0 -0
  95. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/alembic/versions/017_operator_events.py +0 -0
  96. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/alembic/versions/018_contributor_refs.py +0 -0
  97. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/alembic/versions/019_embedding_model_id.py +0 -0
  98. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/alembic/versions/020_trust_lenses.py +0 -0
  99. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/alembic/versions/021_registered_at_string.py +0 -0
  100. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/alembic/versions/022_assertion_modality.py +0 -0
  101. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/alembic/versions/023_url_mentions.py +0 -0
  102. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/alembic/versions/024_corpus_document_supersession.py +0 -0
  103. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/alembic/versions/025_per_provider_calibration.py +0 -0
  104. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/alembic/versions/026_conformance_trust_cap.py +0 -0
  105. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/alembic/versions/027_lens_decay_rules.py +0 -0
  106. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/alembic/versions/028_utility_lens.py +0 -0
  107. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/alembic/versions/029_retired_at.py +0 -0
  108. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/alembic/versions/030_utility_rank_lift.py +0 -0
  109. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/alembic/versions/031_content_norm_hash.py +0 -0
  110. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/alembic/versions/032_utility_event_source.py +0 -0
  111. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/alembic/versions/033_structured_claim.py +0 -0
  112. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/alembic/versions/034_extraction_provider_model.py +0 -0
  113. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/alembic/versions/035_prefix_extraction_properties_keys.py +0 -0
  114. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/alembic/versions/036_curation_snapshots.py +0 -0
  115. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/alembic/versions/037_rekey_reviewer_trust_statements.py +0 -0
  116. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/alembic/versions/038_snapshot_superseded_by.py +0 -0
  117. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/alembic/versions/039_observer_scope_statements.py +0 -0
  118. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/alembic.ini +0 -0
  119. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/artifacts/conformance/README.md +0 -0
  120. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/artifacts/conformance/profile.yaml +0 -0
  121. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/artifacts/conformance/similarity_vectors.json +0 -0
  122. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/artifacts/graph/LICENSE.cytoscape.txt +0 -0
  123. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/artifacts/graph/cytoscape.min.js +0 -0
  124. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/artifacts/schemas/context.jsonld +0 -0
  125. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/artifacts/schemas/interchange.schema.json +0 -0
  126. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/artifacts/schemas/particle.schema.json +0 -0
  127. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/artifacts/schemas/shacl/CorpusSnapshotShape.ttl +0 -0
  128. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/artifacts/schemas/shacl/ParticleShape.ttl +0 -0
  129. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/artifacts/schemas/shacl/ProvenanceChainShape.ttl +0 -0
  130. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/artifacts/schemas/shacl/SubjectShape.ttl +0 -0
  131. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/artifacts/schemas/shacl/TrustStatementShape.ttl +0 -0
  132. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/artifacts/schemas/trust_lens.schema.json +0 -0
  133. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/config.yaml.sample +0 -0
  134. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/constraints.txt +0 -0
  135. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/design/tokens.css +0 -0
  136. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/_orm_modules.py +0 -0
  137. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/api/__init__.py +0 -0
  138. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/api/_middleware.py +0 -0
  139. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/api/_rate_limit.py +0 -0
  140. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/api/auth.py +0 -0
  141. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/api/cli/__init__.py +0 -0
  142. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/api/cli/_claude_code.py +0 -0
  143. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/api/cli/_id_norm.py +0 -0
  144. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/api/cli/_logging.py +0 -0
  145. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/api/cli/_memory_projection.py +0 -0
  146. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/api/cli/_output.py +0 -0
  147. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/api/cli/_progress.py +0 -0
  148. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/api/cli/_projection_git.py +0 -0
  149. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/api/cli/_remote.py +0 -0
  150. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/api/cli/_source_passage.py +0 -0
  151. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/api/cli/config.py +0 -0
  152. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/api/cli/conformance.py +0 -0
  153. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/api/cli/curate.py +0 -0
  154. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/api/cli/db.py +0 -0
  155. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/api/cli/deposit.py +0 -0
  156. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/api/cli/engine.py +0 -0
  157. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/api/cli/events.py +0 -0
  158. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/api/cli/export.py +0 -0
  159. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/api/cli/extract.py +0 -0
  160. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/api/cli/hook.py +0 -0
  161. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/api/cli/import_vault.py +0 -0
  162. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/api/cli/inbox.py +0 -0
  163. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/api/cli/interchange.py +0 -0
  164. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/api/cli/links.py +0 -0
  165. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/api/cli/lint.py +0 -0
  166. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/api/cli/mcp.py +0 -0
  167. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/api/cli/particle.py +0 -0
  168. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/api/cli/project.py +0 -0
  169. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/api/cli/quality.py +0 -0
  170. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/api/cli/reconcile.py +0 -0
  171. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/api/cli/reindex.py +0 -0
  172. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/api/cli/review.py +0 -0
  173. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/api/cli/rules.py +0 -0
  174. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/api/cli/skills.py +0 -0
  175. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/api/cli/structure.py +0 -0
  176. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/api/cli/subjects.py +0 -0
  177. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/api/cli/synthesis_cache.py +0 -0
  178. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/api/cli/trust.py +0 -0
  179. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/api/client/__init__.py +0 -0
  180. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/api/client/base.py +0 -0
  181. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/api/client/http.py +0 -0
  182. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/api/client/local.py +0 -0
  183. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/api/daemon.py +0 -0
  184. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/api/web_app.py +0 -0
  185. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/benchmark/__init__.py +0 -0
  186. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/benchmark/compare.py +0 -0
  187. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/benchmark/equivalence.py +0 -0
  188. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/benchmark/loader.py +0 -0
  189. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/benchmark/memory/__init__.py +0 -0
  190. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/benchmark/memory/comparators.py +0 -0
  191. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/benchmark/memory/loader.py +0 -0
  192. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/benchmark/memory/metrics.py +0 -0
  193. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/benchmark/memory/rejudge.py +0 -0
  194. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/benchmark/memory/runner.py +0 -0
  195. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/benchmark/memory/schema.py +0 -0
  196. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/benchmark/metrics.py +0 -0
  197. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/benchmark/modality/__init__.py +0 -0
  198. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/benchmark/modality/loader.py +0 -0
  199. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/benchmark/modality/metrics.py +0 -0
  200. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/benchmark/modality/runner.py +0 -0
  201. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/benchmark/modality/schema.py +0 -0
  202. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/benchmark/observer/__init__.py +0 -0
  203. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/benchmark/observer/generator.py +0 -0
  204. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/benchmark/observer/oracle.py +0 -0
  205. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/benchmark/observer/runner.py +0 -0
  206. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/benchmark/observer/schema.py +0 -0
  207. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/benchmark/polarity/__init__.py +0 -0
  208. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/benchmark/polarity/loader.py +0 -0
  209. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/benchmark/polarity/metrics.py +0 -0
  210. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/benchmark/polarity/runner.py +0 -0
  211. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/benchmark/polarity/schema.py +0 -0
  212. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/benchmark/relevance_floor/__init__.py +0 -0
  213. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/benchmark/relevance_floor/harvest.py +0 -0
  214. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/benchmark/relevance_floor/metrics.py +0 -0
  215. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/benchmark/relevance_floor/render.py +0 -0
  216. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/benchmark/relevance_floor/runner.py +0 -0
  217. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/benchmark/relevance_floor/schema.py +0 -0
  218. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/benchmark/rot/__init__.py +0 -0
  219. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/benchmark/rot/generator.py +0 -0
  220. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/benchmark/rot/oracle.py +0 -0
  221. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/benchmark/rot/render.py +0 -0
  222. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/benchmark/rot/rescore.py +0 -0
  223. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/benchmark/rot/runner.py +0 -0
  224. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/benchmark/rot/schema.py +0 -0
  225. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/benchmark/rot/scoring.py +0 -0
  226. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/benchmark/runner.py +0 -0
  227. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/benchmark/schema.py +0 -0
  228. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/benchmark/validity/__init__.py +0 -0
  229. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/benchmark/validity/loader.py +0 -0
  230. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/benchmark/validity/metrics.py +0 -0
  231. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/benchmark/validity/runner.py +0 -0
  232. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/benchmark/validity/schema.py +0 -0
  233. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/corpus/__init__.py +0 -0
  234. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/corpus/blob_fsck.py +0 -0
  235. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/corpus/blob_health.py +0 -0
  236. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/corpus/deposit.py +0 -0
  237. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/corpus/fetch.py +0 -0
  238. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/corpus/follow_edges.py +0 -0
  239. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/corpus/rule_sources.py +0 -0
  240. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/corpus/supersession.py +0 -0
  241. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/db.py +0 -0
  242. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/exporters/__init__.py +0 -0
  243. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/exporters/anki.py +0 -0
  244. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/exporters/article_synthesis/__init__.py +0 -0
  245. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/exporters/graph/__init__.py +0 -0
  246. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/exporters/graph/_assets.py +0 -0
  247. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/exporters/graph/exporter.py +0 -0
  248. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/exporters/graph/render.py +0 -0
  249. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/exporters/jsonl.py +0 -0
  250. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/exporters/logseq/__init__.py +0 -0
  251. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/exporters/logseq/exporter.py +0 -0
  252. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/exporters/logseq/format.py +0 -0
  253. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/exporters/logseq/narrative.py +0 -0
  254. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/exporters/logseq/synthesis.py +0 -0
  255. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/exporters/logseq/vault.py +0 -0
  256. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/exporters/markdown.py +0 -0
  257. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/exporters/notion.py +0 -0
  258. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/exporters/obsidian/__init__.py +0 -0
  259. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/exporters/obsidian/exporter.py +0 -0
  260. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/exporters/obsidian/format.py +0 -0
  261. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/exporters/obsidian/narrative.py +0 -0
  262. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/exporters/obsidian/synthesis.py +0 -0
  263. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/exporters/obsidian/vault.py +0 -0
  264. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/exporters/registry.py +0 -0
  265. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/exporters/summaries.py +0 -0
  266. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/exporters/wiki.py +0 -0
  267. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/ingest/__init__.py +0 -0
  268. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/ingest/authorities/__init__.py +0 -0
  269. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/ingest/authorities/_shared.py +0 -0
  270. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/ingest/authorities/registry.py +0 -0
  271. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/ingest/authorities/wikidata.py +0 -0
  272. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/ingest/candidate_dedup.py +0 -0
  273. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/ingest/duplicate_suppression.py +0 -0
  274. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/ingest/generation.py +0 -0
  275. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/ingest/importers/__init__.py +0 -0
  276. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/ingest/importers/github.py +0 -0
  277. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/ingest/importers/hackernews.py +0 -0
  278. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/ingest/importers/mastodon.py +0 -0
  279. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/ingest/importers/nomisma.py +0 -0
  280. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/ingest/importers/numista.py +0 -0
  281. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/ingest/importers/reddit.py +0 -0
  282. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/ingest/importers/registry.py +0 -0
  283. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/ingest/importers/wikidata.py +0 -0
  284. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/ingest/observer_gate.py +0 -0
  285. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/ingest/update_supersession.py +0 -0
  286. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/integrations/__init__.py +0 -0
  287. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/integrations/_mapping.py +0 -0
  288. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/integrations/langchain.py +0 -0
  289. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/interchange/store.py +0 -0
  290. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/mcp/__init__.py +0 -0
  291. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/mcp/memory_compat/__init__.py +0 -0
  292. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/mcp/memory_compat/graph.py +0 -0
  293. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/mcp/memory_compat/ops.py +0 -0
  294. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/mcp/memory_compat/server.py +0 -0
  295. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/mcp/observer.py +0 -0
  296. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/mcp/resources.py +0 -0
  297. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/mcp/server.py +0 -0
  298. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/mcp/tools/__init__.py +0 -0
  299. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/mcp/tools/corpus.py +0 -0
  300. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/mcp/tools/diagnostics.py +0 -0
  301. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/mcp/tools/events.py +0 -0
  302. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/mcp/tools/graph.py +0 -0
  303. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/mcp/tools/links_suggest.py +0 -0
  304. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/mcp/tools/lint.py +0 -0
  305. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/mcp/tools/particles.py +0 -0
  306. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/mcp/tools/query.py +0 -0
  307. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/mcp/tools/subjects.py +0 -0
  308. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/mcp/tools/taxonomy.py +0 -0
  309. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/mcp/tools/write.py +0 -0
  310. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/observability/__init__.py +0 -0
  311. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/observability/setup.py +0 -0
  312. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/observability/spans.py +0 -0
  313. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/operations/__init__.py +0 -0
  314. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/operations/_llm.py +0 -0
  315. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/operations/_scope.py +0 -0
  316. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/operations/agent_write.py +0 -0
  317. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/operations/audit.py +0 -0
  318. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/operations/curation/__init__.py +0 -0
  319. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/operations/curation/cards.py +0 -0
  320. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/operations/curation/collect.py +0 -0
  321. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/operations/curation/leverage.py +0 -0
  322. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/operations/curation/session.py +0 -0
  323. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/operations/curation/snapshot.py +0 -0
  324. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/operations/deposit.py +0 -0
  325. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/operations/deposit_suggest.py +0 -0
  326. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/operations/digest.py +0 -0
  327. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/operations/extract.py +0 -0
  328. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/operations/inbox.py +0 -0
  329. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/operations/lint/__init__.py +0 -0
  330. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/operations/lint/assertion_quality.py +0 -0
  331. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/operations/lint/citation_signal.py +0 -0
  332. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/operations/lint/coverage.py +0 -0
  333. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/operations/lint/granularity.py +0 -0
  334. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/operations/lint/orchestrator.py +0 -0
  335. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/operations/lint/retirement.py +0 -0
  336. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/operations/lint/staleness.py +0 -0
  337. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/operations/lint/wikidata_links.py +0 -0
  338. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/operations/narrative.py +0 -0
  339. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/operations/narrative_synthesis.py +0 -0
  340. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/operations/projection/__init__.py +0 -0
  341. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/operations/projection/manifest.py +0 -0
  342. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/operations/projection/project.py +0 -0
  343. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/operations/quality.py +0 -0
  344. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/operations/query/__init__.py +0 -0
  345. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/operations/query/contested.py +0 -0
  346. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/operations/query/contestedness.py +0 -0
  347. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/operations/query/decay_policy.py +0 -0
  348. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/operations/query/effective_confidence.py +0 -0
  349. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/operations/query/gaps.py +0 -0
  350. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/operations/query/observer_scope.py +0 -0
  351. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/operations/query/owner_policy.py +0 -0
  352. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/operations/query/precedence.py +0 -0
  353. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/operations/query/rank.py +0 -0
  354. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/operations/query/respond.py +0 -0
  355. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/operations/query/source_info.py +0 -0
  356. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/operations/query/source_trust.py +0 -0
  357. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/operations/query/stance.py +0 -0
  358. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/operations/query/structural.py +0 -0
  359. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/operations/query/utility_policy.py +0 -0
  360. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/operations/retract.py +0 -0
  361. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/operations/source_passage.py +0 -0
  362. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/operations/structure.py +0 -0
  363. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/operations/trust.py +0 -0
  364. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/operations/utility_feedback.py +0 -0
  365. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/operations/utility_mining.py +0 -0
  366. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/operations/utility_sweep.py +0 -0
  367. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/operations/version_guard.py +0 -0
  368. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/render/article_synthesis/__init__.py +0 -0
  369. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/render/article_synthesis/cache.py +0 -0
  370. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/render/article_synthesis/layer_a.py +0 -0
  371. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/render/article_synthesis/layer_b.py +0 -0
  372. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/render/article_synthesis/orchestrate.py +0 -0
  373. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/render/article_synthesis/render.py +0 -0
  374. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/render/article_synthesis/topic.py +0 -0
  375. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/skills/__init__.py +0 -0
  376. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/skills/asking-the-store.md +0 -0
  377. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/skills/keeping-it-clean.md +0 -0
  378. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/skills/recording-a-belief.md +0 -0
  379. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/sql_safety.py +0 -0
  380. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/store/__init__.py +0 -0
  381. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/store/curation_snapshot_store.py +0 -0
  382. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/store/extractor_store.py +0 -0
  383. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/store/lens_store.py +0 -0
  384. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/store/observer_scope_join.py +0 -0
  385. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/store/observer_scope_store.py +0 -0
  386. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/store/relation_store.py +0 -0
  387. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/store/subject_cache.py +0 -0
  388. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/store/synthesis_cache_store.py +0 -0
  389. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/store/trust_store.py +0 -0
  390. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/store/url_mention_store.py +0 -0
  391. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/particles/store/wikidata_cache.py +0 -0
  392. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/__init__.py +0 -0
  393. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/_capped_http.py +0 -0
  394. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/_claude_projects.py +0 -0
  395. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/_client_fixtures.py +0 -0
  396. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/_observer_scope.py +0 -0
  397. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/_upstream.py +0 -0
  398. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/benchmark/calibration/numismatic-calibration-001.yaml +0 -0
  399. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/benchmark/calibration/prose-calibration-001.yaml +0 -0
  400. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/benchmark/calibration/rdf-calibration-001.yaml +0 -0
  401. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/benchmark/memory/fixtures/NOTICE +0 -0
  402. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/benchmark/memory/fixtures/longmemeval_oracle_synthetic.json +0 -0
  403. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/benchmark/modality/journal-modality-seed-001.yaml +0 -0
  404. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/benchmark/polarity/adr-polarity-seed-001.yaml +0 -0
  405. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/benchmark/suites/hackernews-seed-001.yaml +0 -0
  406. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/benchmark/suites/numismatic-seed-001.yaml +0 -0
  407. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/benchmark/suites/prose-article-seed-001.yaml +0 -0
  408. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/benchmark/suites/rdf-seed-001.yaml +0 -0
  409. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/benchmark/suites/reddit-seed-001.yaml +0 -0
  410. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/benchmark/suites/wikidata-seed-001.yaml +0 -0
  411. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/benchmark/validity/durability-seed-001.yaml +0 -0
  412. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/conformance/fixtures/MANIFEST.yaml +0 -0
  413. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/conformance/fixtures/hackernews-thread-001/content.bin +0 -0
  414. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/conformance/fixtures/hackernews-thread-001/manifest.yaml +0 -0
  415. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/conformance/fixtures/hackernews-thread-001/snapshot.json +0 -0
  416. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/conformance/fixtures/journal-entry-001/content.bin +0 -0
  417. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/conformance/fixtures/journal-entry-001/manifest.yaml +0 -0
  418. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/conformance/fixtures/journal-entry-001/snapshot.json +0 -0
  419. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/conformance/fixtures/mastodon-thread-001/content.bin +0 -0
  420. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/conformance/fixtures/mastodon-thread-001/manifest.yaml +0 -0
  421. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/conformance/fixtures/mastodon-thread-001/snapshot.json +0 -0
  422. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/conformance/fixtures/mcp-memory-export-001/content.bin +0 -0
  423. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/conformance/fixtures/mcp-memory-export-001/manifest.yaml +0 -0
  424. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/conformance/fixtures/mcp-memory-export-001/snapshot.json +0 -0
  425. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/conformance/fixtures/nomisma-concept-001/content.bin +0 -0
  426. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/conformance/fixtures/nomisma-concept-001/manifest.yaml +0 -0
  427. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/conformance/fixtures/nomisma-concept-001/snapshot.json +0 -0
  428. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/conformance/fixtures/numista-coin-001/content.bin +0 -0
  429. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/conformance/fixtures/numista-coin-001/manifest.yaml +0 -0
  430. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/conformance/fixtures/numista-coin-001/snapshot.json +0 -0
  431. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/conformance/fixtures/numista-issuer-001/content.bin +0 -0
  432. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/conformance/fixtures/numista-issuer-001/manifest.yaml +0 -0
  433. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/conformance/fixtures/numista-issuer-001/snapshot.json +0 -0
  434. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/conformance/fixtures/numista-listing-001/content.bin +0 -0
  435. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/conformance/fixtures/numista-listing-001/manifest.yaml +0 -0
  436. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/conformance/fixtures/numista-listing-001/snapshot.json +0 -0
  437. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/conformance/fixtures/rdf-graph-001/content.bin +0 -0
  438. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/conformance/fixtures/rdf-graph-001/manifest.yaml +0 -0
  439. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/conformance/fixtures/rdf-graph-001/snapshot.json +0 -0
  440. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/conformance/fixtures/reddit-thread-001/content.bin +0 -0
  441. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/conformance/fixtures/reddit-thread-001/manifest.yaml +0 -0
  442. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/conformance/fixtures/reddit-thread-001/snapshot.json +0 -0
  443. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/conformance/fixtures/taxonomy-coins-001/content.bin +0 -0
  444. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/conformance/fixtures/taxonomy-coins-001/manifest.yaml +0 -0
  445. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/conformance/fixtures/taxonomy-coins-001/snapshot.json +0 -0
  446. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/conformance/fixtures/trust-lens-001/content.bin +0 -0
  447. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/conformance/fixtures/trust-lens-001/manifest.yaml +0 -0
  448. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/conformance/fixtures/trust-lens-001/snapshot.json +0 -0
  449. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/conformance/fixtures/web-article-001/content.bin +0 -0
  450. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/conformance/fixtures/web-article-001/manifest.yaml +0 -0
  451. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/conformance/fixtures/web-article-001/snapshot.json +0 -0
  452. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/conformance/fixtures/web-article-002/content.bin +0 -0
  453. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/conformance/fixtures/web-article-002/manifest.yaml +0 -0
  454. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/conformance/fixtures/web-article-002/snapshot.json +0 -0
  455. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/conformance/fixtures/web-essay-001/content.bin +0 -0
  456. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/conformance/fixtures/web-essay-001/manifest.yaml +0 -0
  457. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/conformance/fixtures/web-essay-001/snapshot.json +0 -0
  458. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/conformance/fixtures/web-interview-001/content.bin +0 -0
  459. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/conformance/fixtures/web-interview-001/manifest.yaml +0 -0
  460. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/conformance/fixtures/web-interview-001/snapshot.json +0 -0
  461. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/conformance/fixtures/wikidata-entity-001/content.bin +0 -0
  462. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/conformance/fixtures/wikidata-entity-001/manifest.yaml +0 -0
  463. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/conformance/fixtures/wikidata-entity-001/snapshot.json +0 -0
  464. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/conftest.py +0 -0
  465. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/dogfood/corpus.yaml +0 -0
  466. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/dogfood/llm_responses.yaml +0 -0
  467. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/dogfood/record.py +0 -0
  468. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/fixtures/llm_wiki_vault/.obsidian/app.json +0 -0
  469. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/fixtures/llm_wiki_vault/1933 Double Eagle.md +0 -0
  470. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/fixtures/llm_wiki_vault/Coin Silver Standards.md +0 -0
  471. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/fixtures/llm_wiki_vault/Flowing Hair Dollar.md +0 -0
  472. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/fixtures/llm_wiki_vault/Grading and Condition.md +0 -0
  473. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/fixtures/llm_wiki_vault/Home.md +0 -0
  474. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/fixtures/llm_wiki_vault/Mint Records.md +0 -0
  475. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/fixtures/llm_wiki_vault/Morgan Dollar.md +0 -0
  476. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/fixtures/llm_wiki_vault/Most Expensive Coins.md +0 -0
  477. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/fixtures/llm_wiki_vault/Philadelphia Mint.md +0 -0
  478. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/fixtures/llm_wiki_vault/Seated Liberty Dollar.md +0 -0
  479. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/fixtures/llm_wiki_vault/US Mint History.md +0 -0
  480. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/fixtures/llm_wiki_vault/_GROUND_TRUTH.md +0 -0
  481. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/fixtures/llm_wiki_vault/_templates/Coin Note Template.md +0 -0
  482. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/fixtures/llm_wiki_vault/inventory.csv +0 -0
  483. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/fixtures/memory_dir/MEMORY.md +0 -0
  484. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/fixtures/memory_dir/deploy-pipeline.md +0 -0
  485. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/fixtures/memory_dir/orion-api.md +0 -0
  486. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/fixtures/scope/normative-rule-file.md +0 -0
  487. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/fixtures/scope/normative-rule-file.recorded.json +0 -0
  488. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/fixtures/scope/rule-file-agents-md.md +0 -0
  489. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/fixtures/scope/rule-file-agents-md.recorded.json +0 -0
  490. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/mcp/memory-tool-schema.json +0 -0
  491. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/mcp/resource-schema.json +0 -0
  492. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/mcp/tool-schema.json +0 -0
  493. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/test_account_level_failure.py +0 -0
  494. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/test_agent_write_operator.py +0 -0
  495. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/test_anki.py +0 -0
  496. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/test_api_client.py +0 -0
  497. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/test_api_middleware.py +0 -0
  498. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/test_api_rate_limit.py +0 -0
  499. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/test_app.py +0 -0
  500. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/test_article_synthesis.py +0 -0
  501. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/test_as_of.py +0 -0
  502. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/test_audit.py +0 -0
  503. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/test_auth.py +0 -0
  504. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/test_benchmark_compare.py +0 -0
  505. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/test_benchmark_memory.py +0 -0
  506. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/test_benchmark_memory_comparators.py +0 -0
  507. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/test_benchmark_modality.py +0 -0
  508. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/test_benchmark_observer.py +0 -0
  509. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/test_benchmark_polarity.py +0 -0
  510. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/test_benchmark_relevance_floor.py +0 -0
  511. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/test_benchmark_rot.py +0 -0
  512. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/test_benchmark_runner.py +0 -0
  513. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/test_benchmark_schema.py +0 -0
  514. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/test_benchmark_validity.py +0 -0
  515. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/test_blob_fsck.py +0 -0
  516. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/test_blob_health.py +0 -0
  517. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/test_calibration.py +0 -0
  518. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/test_calibration_integration.py +0 -0
  519. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/test_candidate_dedup.py +0 -0
  520. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/test_cascade.py +0 -0
  521. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/test_cascade_gate.py +0 -0
  522. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/test_claims.py +0 -0
  523. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/test_claude_code_hook.py +0 -0
  524. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/test_claude_code_init.py +0 -0
  525. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/test_claude_code_project.py +0 -0
  526. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/test_cli.py +0 -0
  527. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/test_cli_audit.py +0 -0
  528. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/test_cli_benchmark_memory.py +0 -0
  529. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/test_cli_curate.py +0 -0
  530. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/test_cli_extract.py +0 -0
  531. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/test_cli_lint.py +0 -0
  532. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/test_cli_logging.py +0 -0
  533. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/test_cli_memory.py +0 -0
  534. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/test_cli_memory_useful.py +0 -0
  535. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/test_cli_output.py +0 -0
  536. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/test_cli_particle_retract.py +0 -0
  537. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/test_cli_particle_source.py +0 -0
  538. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/test_cli_progress.py +0 -0
  539. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/test_cli_query.py +0 -0
  540. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/test_cli_structure.py +0 -0
  541. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/test_cli_suggested_commands.py +0 -0
  542. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/test_co_evidential_cli.py +0 -0
  543. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/test_co_evidential_merge.py +0 -0
  544. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/test_co_evidential_query_collapse.py +0 -0
  545. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/test_config.py +0 -0
  546. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/test_conflict_resolution.py +0 -0
  547. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/test_conformance.py +0 -0
  548. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/test_conformance_cli.py +0 -0
  549. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/test_conformance_profile.py +0 -0
  550. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/test_contested_badge.py +0 -0
  551. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/test_context_fingerprint.py +0 -0
  552. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/test_context_schema_sync.py +0 -0
  553. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/test_contributor_ref.py +0 -0
  554. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/test_corpus_cat.py +0 -0
  555. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/test_corpus_delete.py +0 -0
  556. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/test_corpus_fetch.py +0 -0
  557. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/test_corpus_fsck_cli.py +0 -0
  558. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/test_corpus_links_cli.py +0 -0
  559. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/test_corpus_retract.py +0 -0
  560. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/test_corpus_store.py +0 -0
  561. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/test_curation.py +0 -0
  562. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/test_curation_snapshot.py +0 -0
  563. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/test_daemon.py +0 -0
  564. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/test_db.py +0 -0
  565. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/test_decay.py +0 -0
  566. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/test_decay_policy.py +0 -0
  567. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/test_deposit_date.py +0 -0
  568. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/test_deposit_follow.py +0 -0
  569. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/test_deposit_project_keys.py +0 -0
  570. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/test_deposit_routing.py +0 -0
  571. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/test_deposit_suggest.py +0 -0
  572. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/test_deposit_versioned.py +0 -0
  573. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/test_docstrings.py +0 -0
  574. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/test_document_scope.py +0 -0
  575. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/test_dogfood_corpus.py +0 -0
  576. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/test_dogfood_record.py +0 -0
  577. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/test_duplicate_suppression.py +0 -0
  578. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/test_egress_chokepoint.py +0 -0
  579. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/test_embedding_model_marker.py +0 -0
  580. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/test_engine_cli.py +0 -0
  581. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/test_equivalence.py +0 -0
  582. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/test_exporter_quality_threshold.py +0 -0
  583. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/test_exporters_registry.py +0 -0
  584. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/test_extract.py +0 -0
  585. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/test_extraction_provider_model.py +0 -0
  586. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/test_extractor_ref.py +0 -0
  587. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/test_extractor_registry.py +0 -0
  588. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/test_fingerprint.py +0 -0
  589. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/test_generation_cascade.py +0 -0
  590. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/test_github_extractor.py +0 -0
  591. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/test_granularity.py +0 -0
  592. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/test_graph_exporter.py +0 -0
  593. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/test_hackernews_extractor.py +0 -0
  594. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/test_http.py +0 -0
  595. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/test_id_norm.py +0 -0
  596. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/test_inbox.py +0 -0
  597. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/test_incremental.py +0 -0
  598. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/test_integration_audit.py +0 -0
  599. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/test_integration_journal_modality.py +0 -0
  600. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/test_integration_llm.py +0 -0
  601. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/test_integration_memory_benchmark.py +0 -0
  602. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/test_integration_polarity.py +0 -0
  603. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/test_integration_polarity_benchmark.py +0 -0
  604. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/test_integration_rot_benchmark.py +0 -0
  605. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/test_integration_validity_benchmark.py +0 -0
  606. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/test_integrations_langchain.py +0 -0
  607. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/test_interchange.py +0 -0
  608. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/test_journal.py +0 -0
  609. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/test_jsonl_exporter.py +0 -0
  610. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/test_jsonld_context.py +0 -0
  611. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/test_links_dedup.py +0 -0
  612. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/test_links_suggest.py +0 -0
  613. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/test_links_unmerge.py +0 -0
  614. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/test_lint.py +0 -0
  615. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/test_lint_callouts.py +0 -0
  616. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/test_lint_citation_signal.py +0 -0
  617. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/test_lint_contested.py +0 -0
  618. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/test_lint_contestedness.py +0 -0
  619. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/test_lint_granularity.py +0 -0
  620. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/test_llm.py +0 -0
  621. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/test_llm_batch.py +0 -0
  622. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/test_llm_circuit_breaker.py +0 -0
  623. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/test_llm_openai_compat.py +0 -0
  624. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/test_logseq_exporter.py +0 -0
  625. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/test_markdown.py +0 -0
  626. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/test_mastodon_extractor.py +0 -0
  627. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/test_mcp_links_suggest.py +0 -0
  628. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/test_mcp_memory.py +0 -0
  629. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/test_mcp_routing.py +0 -0
  630. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/test_mcp_server.py +0 -0
  631. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/test_memory_compat.py +0 -0
  632. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/test_memory_projection.py +0 -0
  633. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/test_memory_rescope_cli.py +0 -0
  634. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/test_migration_035_properties_keys.py +0 -0
  635. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/test_migration_037_reviewer_statement_key.py +0 -0
  636. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/test_migration_preview.py +0 -0
  637. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/test_narrative.py +0 -0
  638. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/test_narrative_cli.py +0 -0
  639. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/test_narrative_synthesis.py +0 -0
  640. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/test_nomisma.py +0 -0
  641. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/test_notion_exporter.py +0 -0
  642. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/test_numista.py +0 -0
  643. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/test_observability.py +0 -0
  644. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/test_observer_gate.py +0 -0
  645. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/test_observer_scope.py +0 -0
  646. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/test_observer_scope_surfaces.py +0 -0
  647. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/test_obsidian.py +0 -0
  648. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/test_openapi_snapshot.py +0 -0
  649. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/test_operations_scope.py +0 -0
  650. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/test_operator_events.py +0 -0
  651. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/test_operator_verb_routing.py +0 -0
  652. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/test_owner_policy.py +0 -0
  653. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/test_packaging.py +0 -0
  654. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/test_particle_store.py +0 -0
  655. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/test_pending_collapse.py +0 -0
  656. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/test_polarity.py +0 -0
  657. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/test_project_import.py +0 -0
  658. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/test_projection.py +0 -0
  659. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/test_projection_git.py +0 -0
  660. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/test_projection_manifest.py +0 -0
  661. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/test_property_keys.py +0 -0
  662. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/test_quality.py +0 -0
  663. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/test_query.py +0 -0
  664. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/test_query_contestedness.py +0 -0
  665. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/test_query_gaps.py +0 -0
  666. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/test_query_negative_retrieval.py +0 -0
  667. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/test_query_source_trust.py +0 -0
  668. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/test_query_stance.py +0 -0
  669. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/test_rdf.py +0 -0
  670. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/test_reconcile.py +0 -0
  671. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/test_reddit.py +0 -0
  672. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/test_relation_store.py +0 -0
  673. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/test_relevance.py +0 -0
  674. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/test_retired_value_quarantine.py +0 -0
  675. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/test_review.py +0 -0
  676. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/test_rule_sources.py +0 -0
  677. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/test_scope_exemption.py +0 -0
  678. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/test_skills.py +0 -0
  679. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/test_source_passage.py +0 -0
  680. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/test_sql_safety.py +0 -0
  681. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/test_stance.py +0 -0
  682. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/test_store_adjacent_paths.py +0 -0
  683. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/test_store_engine.py +0 -0
  684. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/test_structural_query.py +0 -0
  685. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/test_structured_claim.py +0 -0
  686. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/test_subject_authority.py +0 -0
  687. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/test_subject_scope.py +0 -0
  688. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/test_subjects.py +0 -0
  689. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/test_subjects_split.py +0 -0
  690. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/test_synthesis_cache_integration.py +0 -0
  691. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/test_synthesis_cache_store.py +0 -0
  692. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/test_synthesis_topic.py +0 -0
  693. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/test_taxonomy_extractor.py +0 -0
  694. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/test_taxonomy_schema.py +0 -0
  695. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/test_transitions.py +0 -0
  696. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/test_trust_lens.py +0 -0
  697. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/test_update_supersession.py +0 -0
  698. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/test_url_mention_store.py +0 -0
  699. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/test_url_safety.py +0 -0
  700. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/test_utility.py +0 -0
  701. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/test_utility_feedback.py +0 -0
  702. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/test_utility_mining.py +0 -0
  703. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/test_utility_policy.py +0 -0
  704. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/test_utility_store.py +0 -0
  705. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/test_vault_import.py +0 -0
  706. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/test_version_guard.py +0 -0
  707. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/test_web_app.py +0 -0
  708. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/test_web_clipper_import.py +0 -0
  709. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/test_wiki_exporter.py +0 -0
  710. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/test_wikidata_cache.py +0 -0
  711. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/test_wikidata_extractor.py +0 -0
  712. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/test_wikidata_importer.py +0 -0
  713. {linkedparticles-1.149.0 → linkedparticles-1.151.18}/tests/test_wikidata_link_confidence.py +0 -0
@@ -1,6 +1,6 @@
1
1
  Metadata-Version: 2.5
2
2
  Name: linkedparticles
3
- Version: 1.149.0
3
+ Version: 1.151.18
4
4
  Summary: Auditable, provenance-tracked memory for AI agents — the Particles engine and its API, CLI, and MCP surfaces
5
5
  Project-URL: Homepage, https://linkedparticles.org
6
6
  Project-URL: Documentation, https://docs.linkedparticles.org
@@ -39,11 +39,11 @@ Requires-Dist: fastapi>=0.111
39
39
  Requires-Dist: filelock>=3.13
40
40
  Requires-Dist: greenlet>=3.5.0
41
41
  Requires-Dist: jinja2>=3.1
42
- Requires-Dist: linkedparticles-core==1.149.0
42
+ Requires-Dist: linkedparticles-core==1.151.18
43
43
  Requires-Dist: mcp<2,>=1.27.1
44
44
  Requires-Dist: opentelemetry-api>=1.27
45
45
  Requires-Dist: python-multipart>=0.0.9
46
- Requires-Dist: sqlalchemy>=2.0
46
+ Requires-Dist: sqlalchemy[asyncio]<2.2,>=2.0
47
47
  Requires-Dist: typer>=0.12
48
48
  Requires-Dist: uvicorn[standard]>=0.30
49
49
  Requires-Dist: warcio>=1.7
@@ -0,0 +1,88 @@
1
+ # SPDX-FileCopyrightText: 2026 The Particles authors
2
+ #
3
+ # SPDX-License-Identifier: Apache-2.0
4
+
5
+ """Backfill ``particle_tag_edges`` from ``particles.tags_json``.
6
+
7
+ A particle's tags live in two places: ``particles.tags_json`` (the canonical
8
+ list, round-tripped to ``Particle.tags``) and ``particle_tag_edges`` (one row
9
+ per tag, the index every tag-filtered read joins on). Until this release
10
+ ``insert_particle`` wrote only the JSON column; the edge rows came only from
11
+ ``set_particle_tags`` / ``add_particle_tags``. A particle born with tags (an
12
+ agent assertion with ``tags``, a supersession or subject-assign successor
13
+ inheriting its predecessor's tags, a conversation deposit) was therefore
14
+ invisible to every tag-filtered query.
15
+
16
+ **The backfill.** For every particle with a non-empty ``tags_json``, insert the
17
+ edge rows it is missing. Rows already present are left alone, so the migration
18
+ is idempotent and safe on a store where some particles were retagged by hand.
19
+ Malformed JSON is skipped, not repaired: the column is read as-is by
20
+ ``ParticleRow.to_model``, and this migration does not change what a particle
21
+ says about itself.
22
+
23
+ ``downgrade()`` is a deliberate no-op. A backfilled edge cannot be told apart
24
+ from one ``set_particle_tags`` wrote, and each one agrees with the particle's
25
+ own tag list, so removing them would only reintroduce the defect.
26
+
27
+ Revision ID: 040
28
+ Revises: 039
29
+ """
30
+
31
+ from __future__ import annotations
32
+
33
+ import json
34
+
35
+ import sqlalchemy as sa
36
+
37
+ from alembic import op
38
+
39
+ revision = "040"
40
+ down_revision = "039"
41
+ branch_labels = None
42
+ depends_on = None
43
+
44
+
45
+ def backfill_tag_edges(bind: sa.engine.Connection) -> int:
46
+ """Insert the edge rows each tagged particle is missing.
47
+
48
+ Takes the connection rather than calling ``op.get_bind()`` so the backfill
49
+ is exercisable outside an Alembic context, as in migration 037. See
50
+ ``tests/test_migration_040_tag_edges.py``.
51
+
52
+ Returns the number of edge rows inserted.
53
+ """
54
+ existing = {
55
+ (pid, tag)
56
+ for pid, tag in bind.execute(
57
+ sa.text("SELECT particle_id, tag FROM particle_tag_edges")
58
+ ).fetchall()
59
+ }
60
+ rows = bind.execute(
61
+ sa.text("SELECT id, tags_json FROM particles WHERE tags_json IS NOT NULL")
62
+ ).fetchall()
63
+ missing: list[dict[str, str]] = []
64
+ for pid, tags_json in rows:
65
+ try:
66
+ tags = json.loads(tags_json)
67
+ except (TypeError, ValueError):
68
+ continue
69
+ if not isinstance(tags, list):
70
+ continue
71
+ for tag in dict.fromkeys(t for t in tags if isinstance(t, str) and t):
72
+ if (pid, tag) not in existing:
73
+ existing.add((pid, tag))
74
+ missing.append({"pid": pid, "tag": tag})
75
+ if missing:
76
+ bind.execute(
77
+ sa.text("INSERT INTO particle_tag_edges (particle_id, tag) VALUES (:pid, :tag)"),
78
+ missing,
79
+ )
80
+ return len(missing)
81
+
82
+
83
+ def upgrade() -> None:
84
+ backfill_tag_edges(op.get_bind())
85
+
86
+
87
+ def downgrade() -> None:
88
+ pass
@@ -2656,6 +2656,7 @@
2656
2656
  "description": "The kind of operator action an event records.\n\nOne value per distinct *outcome*: opposite outcomes get distinct types\n(``PARTICLE_TAGGED`` vs ``PARTICLE_UNTAGGED``) so ``--type`` is a precise\nfilter; the *same* outcome reached two ways (``trust set`` /\n``trust statement-set`` both write a SourceTrustStatement) shares one type,\nwith ``actor`` recording which verb. Extensible for later verbs that meet\nthe inclusion criterion.",
2657
2657
  "enum": [
2658
2658
  "SOURCE_RETRACTED",
2659
+ "CORPUS_ENTRY_DELETED",
2659
2660
  "CONFLICT_CANDIDATE_DROPPED",
2660
2661
  "SUBJECTS_SPLIT",
2661
2662
  "SUBJECTS_MERGED",
@@ -7849,7 +7850,7 @@
7849
7850
  },
7850
7851
  "/particles/{particle_id}/source": {
7851
7852
  "get": {
7852
- "description": "Return the source passage behind a particle, with how it was found.\n\n``match`` is ``EXACT`` (the hash-verified chunk the extractor saw),\n``LOCATED`` (best term-overlap paragraph \u2014 a reading aid, not\nverification), ``WHOLE`` (the snapshot text), or ``UNAVAILABLE`` with a\n``note``. Display only: never a ranking input. 404 if the particle does\nnot exist.",
7853
+ "description": "Return the source passage behind a particle, with how it was found.\n\n``match`` is ``EXACT`` (the hash-verified chunk the extractor saw),\n``LOCATED`` (best term-overlap paragraph; a reading aid, not\nverification), ``WHOLE`` (the snapshot text), or ``UNAVAILABLE`` with a\n``note``. Display only: never a ranking input. 404 if the particle does\nnot exist.",
7853
7854
  "operationId": "get_particle_source_particles__particle_id__source_get",
7854
7855
  "parameters": [
7855
7856
  {
@@ -1070,7 +1070,7 @@ async def get_particle_source(
1070
1070
  """Return the source passage behind a particle, with how it was found.
1071
1071
 
1072
1072
  ``match`` is ``EXACT`` (the hash-verified chunk the extractor saw),
1073
- ``LOCATED`` (best term-overlap paragraph — a reading aid, not
1073
+ ``LOCATED`` (best term-overlap paragraph; a reading aid, not
1074
1074
  verification), ``WHOLE`` (the snapshot text), or ``UNAVAILABLE`` with a
1075
1075
  ``note``. Display only: never a ranking input. 404 if the particle does
1076
1076
  not exist."""
@@ -99,7 +99,7 @@ def audit_cmd(
99
99
  ),
100
100
  ),
101
101
  output: Path | None = typer.Option(
102
- None, "--output", help="Also write the Markdown report to FILE."
102
+ None, "--output", help="Write the Markdown report to FILE as well."
103
103
  ),
104
104
  format_: str = typer.Option(
105
105
  "markdown", "--format", help="Terminal format: markdown (default) or json."
@@ -695,13 +695,13 @@ def benchmark_observer_cmd(
695
695
  "suppression); `chunked` sends two lines per chunk through carry-forward.",
696
696
  ),
697
697
  ) -> None:
698
- """The two-project observer fixture — zero LLM calls.
698
+ """The two-project observer fixture, with zero LLM calls.
699
699
 
700
700
  Two repositories' memory files, sharing generic subjects, evolve over
701
701
  `--days` and are harvested into one scratch store through the real
702
702
  pipeline with scripted extraction and a scripted contradiction probe.
703
703
  Each day, every line a project currently states is checked through that
704
- project's observer: in view, or not — and if not, which mechanism retired
704
+ project's observer: in view, or not, and if not, which mechanism retired
705
705
  it (cross-project supersession, the generation cascade, or a surviving
706
706
  particle attested only by the other project) and whether the winner is in
707
707
  view. Report-only; the only number the default flip is decided
@@ -765,7 +765,7 @@ def benchmark_rot_cmd( # noqa: PLR0913 — CLI option list is the API
765
765
  "--arm",
766
766
  help="Perception arm: oracle (scripted extraction + scripted §6.6 probe; "
767
767
  "zero LLM calls, deterministic), probe (scripted extraction, live "
768
- "contradiction probe), or live (the general extractor — the product).",
768
+ "contradiction probe), or live (the general extractor, i.e. the product).",
769
769
  ),
770
770
  seed: list[int] | None = typer.Option(
771
771
  None,
@@ -792,7 +792,7 @@ def benchmark_rot_cmd( # noqa: PLR0913 — CLI option list is the API
792
792
  False, "--yes", "-y", help="Skip the confirmation above the call threshold."
793
793
  ),
794
794
  output: Path | None = typer.Option(
795
- None, "--output", "-o", help="Also write the rendered report to this path."
795
+ None, "--output", "-o", help="Write the rendered report to this path as well."
796
796
  ),
797
797
  output_format: _Format = typer.Option(
798
798
  _Format.table, "--format", help="table (default) or json (the report of record)."
@@ -823,7 +823,7 @@ def benchmark_rot_cmd( # noqa: PLR0913 — CLI option list is the API
823
823
  checkpoint, probes every attribute through the query op's selection half.
824
824
  Reports currency (recall_current@k, current_first), supersession
825
825
  (stale_over_current, stale_retained@k), and poison leakage across three
826
- untrusted channels — separately, with no aggregate score.
826
+ untrusted channels, each reported separately, with no aggregate score.
827
827
  """
828
828
  if ctx.invoked_subcommand is not None:
829
829
  # ``benchmark rot rescore …`` owns the invocation.
@@ -941,7 +941,7 @@ def benchmark_rot_rescore_cmd(
941
941
  ) -> None:
942
942
  """Re-classify a saved rot report under the current scorer.
943
943
 
944
- Free: retrieval is taken as recorded — no store, encoder, or LLM call. The
944
+ Free: retrieval is taken as recorded, with no store, encoder, or LLM call. The
945
945
  output is a complete report of record with ``selection.scorer_version`` set
946
946
  to what ran and a first note naming the source and both versions.
947
947
  """
@@ -1028,8 +1028,8 @@ def benchmark_floor_harvest_cmd(
1028
1028
  prompts: bool = typer.Option(
1029
1029
  True,
1030
1030
  "--prompts/--no-prompts",
1031
- help="Also harvest question-shaped sentences the operator typed to the "
1032
- "agent: a proxy source, reported apart. --no-prompts keeps explicit "
1031
+ help="Harvest question-shaped sentences the operator typed to the agent "
1032
+ "as well: a proxy source, reported apart. --no-prompts keeps explicit "
1033
1033
  "memory queries only.",
1034
1034
  ),
1035
1035
  allow_in_repo: bool = typer.Option(
@@ -1147,7 +1147,7 @@ def benchmark_floor_cmd( # noqa: PLR0913 — CLI option list is the API
1147
1147
  judge: bool = typer.Option(
1148
1148
  False,
1149
1149
  "--judge",
1150
- help="Also run the LLM-priced stage: answer every question with the gate "
1150
+ help="Run the LLM-priced stage too: answer every question with the gate "
1151
1151
  "disabled, then judge the answer grounded-and-useful. Estimate-gated.",
1152
1152
  ),
1153
1153
  estimate: bool = typer.Option(
@@ -1160,7 +1160,7 @@ def benchmark_floor_cmd( # noqa: PLR0913 — CLI option list is the API
1160
1160
  False, "--yes", "-y", help="Skip the confirmation above the call threshold."
1161
1161
  ),
1162
1162
  output: Path | None = typer.Option(
1163
- None, "--output", "-o", help="Also write the rendered report to this path."
1163
+ None, "--output", "-o", help="Write the rendered report to this path as well."
1164
1164
  ),
1165
1165
  output_format: _Format = typer.Option(
1166
1166
  _Format.table,
@@ -355,99 +355,58 @@ def corpus_delete_cmd(
355
355
  entry_id: str = typer.Argument(..., help="Entry ID (prefix OK)"),
356
356
  yes: bool = typer.Option(False, "--yes", "-y", help="Skip confirmation prompt"),
357
357
  ) -> None:
358
- """Delete a corpus entry, its snapshots, and all particles sourced from it."""
358
+ """Delete a corpus entry, its snapshots, and the particles only it supports.
359
+
360
+ A particle that another entry also supports is kept, with this entry's
361
+ source refs removed. When the removed ref was its earliest source, the
362
+ next-earliest one becomes the age anchor. The delete is recorded as a
363
+ CORPUS_ENTRY_DELETED event that holds the entry id and counts, not the
364
+ deleted content.
365
+ """
359
366
  run(_corpus_delete(entry_id, yes))
360
367
 
361
368
 
362
369
  async def _corpus_delete(entry_id_prefix: str, yes: bool) -> None:
363
- from sqlalchemy import delete, select
364
-
365
370
  from particles.api.cli._remote import ensure_local
366
- from particles.corpus.store import CorpusEntryRow, SnapshotRow, get_entry
367
- from particles.store.particle_store import ParticleRow, ProvenanceEdgeRow
368
- from particles.store.subject_store import ParticleSubjectRow
371
+ from particles.corpus.store import get_entry
372
+ from particles.operations.corpus_delete import delete_entry, plan_entry_deletion
369
373
 
370
374
  ensure_local("corpus delete")
371
375
 
372
376
  async with session_scope() as session:
373
- if len(entry_id_prefix) < 36:
374
- result = await session.execute(
375
- select(CorpusEntryRow).where(
376
- CorpusEntryRow.entry_id.like(
377
- f"{escape_like_pattern(entry_id_prefix)}%", escape=LIKE_ESCAPE
378
- )
379
- )
380
- )
381
- row = result.scalar_one_or_none()
382
- if row is None:
383
- typer.echo(f"Entry {entry_id_prefix!r} not found.", err=True)
384
- raise typer.Exit(1)
385
- entry_id = row.entry_id
386
- else:
387
- entry_id = entry_id_prefix
388
-
377
+ entry_id = await _resolve_entry_id(session, entry_id_prefix)
389
378
  entry = await get_entry(session, entry_id)
390
379
  if entry is None:
391
380
  typer.echo(f"Entry {entry_id_prefix!r} not found.", err=True)
392
381
  raise typer.Exit(1)
393
382
 
394
- # Count particles to be deleted
395
- particle_ids_result = await session.execute(
396
- select(ProvenanceEdgeRow.particle_id).where(
397
- ProvenanceEdgeRow.corpus_entry_id == entry_id
398
- )
399
- )
400
- particle_ids = list(particle_ids_result.scalars())
383
+ plan = await plan_entry_deletion(session, entry_id)
384
+ n_delete = len(plan.decision.to_delete)
385
+ n_strip = len(plan.decision.to_strip)
386
+ n_moved = sum(1 for s in plan.decision.to_strip if s.anchor_moved)
401
387
 
402
388
  label = (entry.uri_r or entry_id).replace("file://", "")
403
389
  typer.echo(f"Entry: {entry_id[:8]}… {label}")
404
- typer.echo(f"Snapshots: {len(entry.snapshots)}")
405
- typer.echo(f"Particles: {len(particle_ids)} will be deleted")
390
+ typer.echo(f"Snapshots: {plan.snapshots}")
391
+ typer.echo(f"Particles: {n_delete} will be deleted (this entry is their only source)")
392
+ strip_line = f" {n_strip} kept, other sources remain; this entry's refs removed"
393
+ if n_moved:
394
+ strip_line += f" ({n_moved} with a new earliest source)"
395
+ typer.echo(strip_line)
406
396
 
407
397
  if not yes:
408
398
  typer.confirm("Delete this entry and all its data?", abort=True)
409
399
 
410
- # Subjects linked to the doomed particles — captured *before* we drop
411
- # the join rows, so afterwards we can re-check each for orphanhood.
412
- candidate_subject_ids: set[str] = set()
413
- if particle_ids:
414
- candidate_subject_ids = set(
415
- (
416
- await session.execute(
417
- select(ParticleSubjectRow.subject_id).where(
418
- ParticleSubjectRow.particle_id.in_(particle_ids)
419
- )
420
- )
421
- ).scalars()
422
- )
423
-
424
- # Delete particles + every index row keyed on them. These tables carry
425
- # no FK to ``particles`` (SQLite FK enforcement is off), so they would
426
- # otherwise be left dangling.
427
- if particle_ids:
428
- await session.execute(delete(ParticleRow).where(ParticleRow.id.in_(particle_ids)))
429
- await _purge_particle_index_rows(session, particle_ids)
430
-
431
- # Subjects that lost their last link become orphans; drop them and any
432
- # synthesis-cache rows keyed on them. A subject still linked to a
433
- # surviving particle is left untouched.
434
- subj_removed, synth_removed = await _purge_orphan_subjects(session, candidate_subject_ids)
435
-
436
- # Delete provenance edges
437
- await session.execute(
438
- delete(ProvenanceEdgeRow).where(ProvenanceEdgeRow.corpus_entry_id == entry_id)
439
- )
440
- # Delete snapshots
441
- await session.execute(delete(SnapshotRow).where(SnapshotRow.entry_id == entry_id))
442
- # Delete entry
443
- await session.execute(delete(CorpusEntryRow).where(CorpusEntryRow.entry_id == entry_id))
400
+ result = await delete_entry(session, entry_id)
444
401
  await session.commit()
445
402
 
446
- parts = [f"{len(particle_ids)} particles removed"]
447
- if subj_removed:
448
- parts.append(f"{subj_removed} orphaned subjects")
449
- if synth_removed:
450
- parts.append(f"{synth_removed} synthesis-cache rows")
403
+ parts = [f"{result.particles_deleted} particles removed"]
404
+ if result.particles_stripped:
405
+ parts.append(f"{result.particles_stripped} kept with refs stripped")
406
+ if result.subjects_orphaned:
407
+ parts.append(f"{result.subjects_orphaned} orphaned subjects")
408
+ if result.synthesis_rows_deleted:
409
+ parts.append(f"{result.synthesis_rows_deleted} synthesis-cache rows")
451
410
  typer.echo(f"Deleted entry {entry_id[:8]}… ({', '.join(parts)}).")
452
411
 
453
412
 
@@ -555,83 +514,6 @@ async def _corpus_retract(
555
514
  )
556
515
 
557
516
 
558
- # ---------------------------------------------------------------------------
559
- # Orphan cleanup — shared by ``corpus delete`` and ``corpus prune-orphans``.
560
- # None of the index tables (particle_subjects, particle_tag_edges,
561
- # particle_relations, synthesis_cache) declare a foreign key, and SQLite FK
562
- # enforcement is off, so deleting particles or subjects elsewhere leaves
563
- # dangling rows unless they are swept explicitly here.
564
- # ---------------------------------------------------------------------------
565
-
566
-
567
- async def _purge_particle_index_rows(session: AsyncSession, particle_ids: list[str]) -> None:
568
- """Delete every index row keyed on one of ``particle_ids``.
569
-
570
- Sweeps the ``particle_subjects`` join, ``particle_tag_edges``, and
571
- ``particle_relations`` (either endpoint). Caller deletes the
572
- ``ParticleRow`` rows themselves.
573
- """
574
- from sqlalchemy import delete, or_
575
-
576
- from particles.store.relation_store import ParticleRelationRow
577
- from particles.store.subject_store import ParticleSubjectRow
578
- from particles.store.taxonomy_store import ParticleTagEdgeRow
579
-
580
- if not particle_ids:
581
- return
582
- await session.execute(
583
- delete(ParticleSubjectRow).where(ParticleSubjectRow.particle_id.in_(particle_ids))
584
- )
585
- await session.execute(
586
- delete(ParticleTagEdgeRow).where(ParticleTagEdgeRow.particle_id.in_(particle_ids))
587
- )
588
- await session.execute(
589
- delete(ParticleRelationRow).where(
590
- or_(
591
- ParticleRelationRow.particle_a.in_(particle_ids),
592
- ParticleRelationRow.particle_b.in_(particle_ids),
593
- )
594
- )
595
- )
596
-
597
-
598
- async def _purge_orphan_subjects(
599
- session: AsyncSession, candidate_ids: set[str] | None
600
- ) -> tuple[int, int]:
601
- """Delete subjects with no remaining ``particle_subjects`` link.
602
-
603
- Also drops any ``synthesis_cache`` rows keyed on the removed subjects.
604
- Returns ``(subjects_removed, synthesis_rows_removed)``.
605
-
606
- ``candidate_ids`` restricts the orphan check to a known set — the subjects
607
- that were linked to a just-deleted entry's particles — so a subject still
608
- linked to surviving particles is never touched. Pass ``None`` to scan
609
- every subject (the whole-DB ``prune-orphans`` sweep).
610
- """
611
- from sqlalchemy import delete, select
612
- from sqlalchemy.engine import CursorResult
613
-
614
- from particles.store.subject_store import ParticleSubjectRow, SubjectRow
615
- from particles.store.synthesis_cache_store import SynthesisCacheRow
616
-
617
- if candidate_ids is not None and not candidate_ids:
618
- return (0, 0)
619
-
620
- linked = select(ParticleSubjectRow.subject_id).distinct()
621
- stmt = select(SubjectRow.id).where(SubjectRow.id.not_in(linked))
622
- if candidate_ids is not None:
623
- stmt = stmt.where(SubjectRow.id.in_(candidate_ids))
624
- orphan_ids = list((await session.execute(stmt)).scalars())
625
- if not orphan_ids:
626
- return (0, 0)
627
-
628
- synth_result: CursorResult[None] = await session.execute( # type: ignore[assignment]
629
- delete(SynthesisCacheRow).where(SynthesisCacheRow.subject_id.in_(orphan_ids))
630
- )
631
- await session.execute(delete(SubjectRow).where(SubjectRow.id.in_(orphan_ids)))
632
- return (len(orphan_ids), synth_result.rowcount or 0)
633
-
634
-
635
517
  @corpus_app.command("prune-orphans")
636
518
  def corpus_prune_orphans_cmd(
637
519
  yes: bool = typer.Option(False, "--yes", "-y", help="Skip confirmation prompt"),
@@ -652,6 +534,7 @@ async def _corpus_prune_orphans(yes: bool) -> None:
652
534
  from sqlalchemy.engine import CursorResult
653
535
 
654
536
  from particles.api.cli._remote import ensure_local
537
+ from particles.operations.corpus_delete import purge_orphan_subjects
655
538
  from particles.store.particle_store import ParticleRow
656
539
  from particles.store.relation_store import ParticleRelationRow
657
540
  from particles.store.subject_store import ParticleSubjectRow, SubjectRow
@@ -711,7 +594,7 @@ async def _corpus_prune_orphans(yes: bool) -> None:
711
594
  await session.execute(delete(ParticleRelationRow).where(dangling_rel_q))
712
595
  # Orphan-subject removal must run *after* the dangling join rows are
713
596
  # gone, so a subject linked only via a now-deleted row is detected.
714
- subj_removed, synth_from_subj = await _purge_orphan_subjects(session, None)
597
+ subj_removed, synth_from_subj = await purge_orphan_subjects(session, None)
715
598
  synth_res: CursorResult[None] = await session.execute( # type: ignore[assignment]
716
599
  delete(SynthesisCacheRow).where(dangling_synth_q)
717
600
  )
@@ -820,13 +703,9 @@ async def _corpus_refresh(
820
703
  entry_id: str | None, force: bool, backfill_cascade: bool, yes: bool
821
704
  ) -> None:
822
705
  from particles.api.cli._remote import ensure_local
823
- from particles.core.schema import WarcRecordType
824
- from particles.corpus.fetch import maybe_refetch
825
- from particles.corpus.store import (
826
- list_refreshable_local_entries,
827
- list_snapshots_for_entry,
828
- resolve_entry_id,
829
- )
706
+ from particles.corpus.refresh_outcome import RefreshOutcome
707
+ from particles.corpus.store import list_refreshable_local_entries, resolve_entry_id
708
+ from particles.operations.corpus_refresh import refresh_entries
830
709
 
831
710
  if backfill_cascade:
832
711
  await _corpus_refresh_backfill(yes)
@@ -853,24 +732,23 @@ async def _corpus_refresh(
853
732
  return
854
733
 
855
734
  changed = unchanged = missing = 0
856
- for target_id, _uri in targets:
857
- snapshots = await list_snapshots_for_entry(session, target_id)
858
- before = max(snapshots, key=lambda s: s.captured_at).snapshot_id if snapshots else None
859
- try:
860
- snap = await maybe_refetch(session, target_id, force=force)
861
- except Exception as exc: # noqa: BLE001 — one bad source must not stop the sweep
862
- typer.echo(f" {target_id[:8]} error: {exc}", err=True)
863
- await session.rollback()
864
- continue
865
- if snap is None:
866
- missing += 1
867
- typer.echo(f" {target_id[:8]} missing (source unavailable)")
868
- elif snap.snapshot_id == before or snap.warc_record_type is WarcRecordType.REVISIT:
869
- unchanged += 1
870
- else:
871
- changed += 1
872
- typer.echo(f" {target_id[:8]} changed → snapshot {snap.snapshot_id[:8]} PENDING")
873
- await session.commit()
735
+ async for result in refresh_entries(
736
+ session, (target_id for target_id, _uri in targets), force=force
737
+ ):
738
+ short = result.entry_id[:8]
739
+ match result.outcome:
740
+ case None:
741
+ typer.echo(f" {short} error: {result.error}", err=True)
742
+ case RefreshOutcome.MISSING:
743
+ missing += 1
744
+ typer.echo(f" {short} missing (source unavailable)")
745
+ case RefreshOutcome.UNCHANGED_MTIME | RefreshOutcome.UNCHANGED_HASH:
746
+ unchanged += 1
747
+ case RefreshOutcome.CHANGED:
748
+ changed += 1
749
+ typer.echo(
750
+ f" {short} changed → snapshot {(result.snapshot_id or '')[:8]} PENDING"
751
+ )
874
752
 
875
753
  typer.echo(
876
754
  f"\nChecked {len(targets)} local source(s): {changed} changed, "
@@ -886,7 +764,7 @@ def corpus_fsck_cmd(
886
764
  [],
887
765
  "--search",
888
766
  help=(
889
- "Also look for strays under this blob root, the directory holding the "
767
+ "Look for strays under this blob root too, the directory holding the "
890
768
  "two-character shards (repeatable). Nothing is inferred: the audit tells "
891
769
  "you what is missing so you can point --search at where you think it went."
892
770
  ),
@@ -1229,7 +1229,7 @@ def extractor_benchmark_validity_cmd(
1229
1229
  Reports the dangerous **wrong-expiry rate**: of the aligned claims whose
1230
1230
  gold is durable (no boundary), the fraction the extractor wrongly assigned a
1231
1231
  ``valid_until`` and thereby set up for silent retirement by the §9.3
1232
- staleness lint (the headline, the over-eager-expiry risk). Also reports existence
1232
+ staleness lint (the headline, the over-eager-expiry risk). It also reports existence
1233
1233
  precision/recall of correct date-bounded extraction and date accuracy.
1234
1234
  Discovers every validity suite under --suites-dir the extractor is the
1235
1235
  production routing choice for (or runs only --suite). Report-only
@@ -115,7 +115,7 @@ def init_claude_code_cmd(
115
115
  True,
116
116
  "--skills/--no-skills",
117
117
  help=(
118
- "Also install the shipped agent-onboarding skill files "
118
+ "Install the shipped agent-onboarding skill files too, "
119
119
  "into the harness's skills directory (a Particles-owned subdirectory; "
120
120
  "--remove deletes exactly that). Default on: an agent that has the "
121
121
  "tools but not the guidance is the gap these close."
@@ -229,7 +229,7 @@ def rescope_cmd(
229
229
  A belief is *in view* for a project when one of its sources was harvested
230
230
  there, which is read from the `project:` tag on the source's corpus entry.
231
231
  Older versions stamped a per-worktree name, or nothing at all. This verb
232
- adds the project's real key beside whatever an entry already carries — it
232
+ adds the project's real key beside whatever an entry already carries. It
233
233
  never removes a tag, and running it twice changes nothing.
234
234
 
235
235
  It reports the two things you need to see: harvested entries it could not
@@ -350,7 +350,7 @@ def widen_cmd(
350
350
  judgement, so it is yours to record. The belief and its sources are not
351
351
  touched: the widening is a standing statement the read lens consults, and
352
352
  `--revoke` withdraws it. There is deliberately no agent-facing way to do
353
- this — an agent that could widen its own belief could put it in front of
353
+ this: an agent that could widen its own belief could put it in front of
354
354
  every future session.
355
355
  """
356
356
  configure_output(verbose, debug, quiet, progress)
@@ -692,7 +692,7 @@ def consolidate_cmd(
692
692
  ),
693
693
  ),
694
694
  output: Path | None = typer.Option(
695
- None, "--output", help="Also write the run report as Markdown to FILE."
695
+ None, "--output", help="Write the run report as Markdown to FILE as well."
696
696
  ),
697
697
  format_: str = typer.Option(
698
698
  "markdown", "--format", help="Terminal format: markdown (default) or json."
@@ -68,7 +68,7 @@ def query_cmd(
68
68
  include_ancestors: bool = typer.Option(
69
69
  False,
70
70
  "--include-ancestors",
71
- help="Also match particles tagged with a broader ancestor of each --tag "
71
+ help="Match particles tagged with a broader ancestor of each --tag as well "
72
72
  "(up-expansion over taxonomy parent links)",
73
73
  ),
74
74
  show_particles: bool = typer.Option(
@@ -33,7 +33,7 @@ def _metrics_rows(m: ObserverMetrics) -> list[str]:
33
33
  ]
34
34
  for kind in ("fact", "rule", "own"):
35
35
  if kind in m.by_kind:
36
- rows.append(f"| In view — `{kind}` lines | {_rate(m.by_kind[kind])} |")
36
+ rows.append(f"| In view, `{kind}` lines | {_rate(m.by_kind[kind])} |")
37
37
  return rows
38
38
 
39
39
 
@@ -0,0 +1,51 @@
1
+ # SPDX-FileCopyrightText: 2026 The Particles authors
2
+ #
3
+ # SPDX-License-Identifier: Apache-2.0
4
+
5
+ """Classify one :func:`~particles.corpus.fetch.maybe_refetch` result.
6
+
7
+ The decide half of a refresh, as a pure function over plain values (
8
+ D2). ``particles corpus refresh`` and consolidation pass 0.5 both derive their
9
+ counts from :func:`classify_refresh`. The outcomes are fine-grained, so a report
10
+ that wants one ``unchanged`` total sums the two unchanged outcomes.
11
+ """
12
+
13
+ from __future__ import annotations
14
+
15
+ from enum import StrEnum
16
+
17
+ from particles.core.schema import Snapshot, WarcRecordType
18
+
19
+
20
+ class RefreshOutcome(StrEnum):
21
+ """What one re-check of a corpus entry found."""
22
+
23
+ MISSING = "missing"
24
+ """No snapshot came back: the source is unavailable, or the entry is not refetchable."""
25
+ UNCHANGED_MTIME = "unchanged_mtime"
26
+ """The latest snapshot came back untouched: a tier-1 short-circuit, before any read."""
27
+ UNCHANGED_HASH = "unchanged_hash"
28
+ """A REVISIT was written: the body was read and its hash matched."""
29
+ CHANGED = "changed"
30
+ """A new RESPONSE snapshot landed PENDING."""
31
+
32
+
33
+ def classify_refresh(before_id: str | None, snap: Snapshot | None) -> RefreshOutcome:
34
+ """Classify a refetch result against the entry's latest snapshot id before it.
35
+
36
+ Args:
37
+ before_id: The entry's newest snapshot id before the refetch, or None
38
+ when it had none.
39
+ snap: What ``maybe_refetch`` returned.
40
+
41
+ Returns:
42
+ The outcome. A returned snapshot whose id equals ``before_id`` is
43
+ ``UNCHANGED_MTIME`` whatever its record type, since no new row was written.
44
+ """
45
+ if snap is None:
46
+ return RefreshOutcome.MISSING
47
+ if snap.snapshot_id == before_id:
48
+ return RefreshOutcome.UNCHANGED_MTIME
49
+ if snap.warc_record_type is WarcRecordType.REVISIT:
50
+ return RefreshOutcome.UNCHANGED_HASH
51
+ return RefreshOutcome.CHANGED