topos-node 1.3.28__tar.gz → 1.3.30__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 (721) hide show
  1. {topos_node-1.3.28/topos_node.egg-info → topos_node-1.3.30}/PKG-INFO +1 -1
  2. {topos_node-1.3.28 → topos_node-1.3.30}/pyproject.toml +1 -1
  3. {topos_node-1.3.28 → topos_node-1.3.30}/topos/__version__.py +2 -2
  4. topos_node-1.3.30/topos/api/community_naming_config.py +52 -0
  5. {topos_node-1.3.28 → topos_node-1.3.30}/topos/api/signal.py +103 -0
  6. {topos_node-1.3.28 → topos_node-1.3.30}/topos/app.py +2 -0
  7. {topos_node-1.3.28 → topos_node-1.3.30}/topos/config/model_packs.py +6 -1
  8. {topos_node-1.3.28 → topos_node-1.3.30}/topos/core/handlers/derivation.py +77 -0
  9. {topos_node-1.3.28 → topos_node-1.3.30}/topos/core/handlers/signal_features.py +46 -0
  10. {topos_node-1.3.28 → topos_node-1.3.30}/topos/enrichment/jobs/canonical/derivation_job.py +127 -4
  11. {topos_node-1.3.28 → topos_node-1.3.30}/topos/features/derivation/bundled_packs/relationships.social.yaml +5 -2
  12. topos_node-1.3.30/topos/features/derivation/report_card.py +60 -0
  13. topos_node-1.3.30/topos/features/derivation/router.py +82 -0
  14. topos_node-1.3.30/topos/features/derivation/surfaces.py +412 -0
  15. {topos_node-1.3.28 → topos_node-1.3.30}/topos/features/derivation/synthesize.py +68 -0
  16. {topos_node-1.3.28 → topos_node-1.3.30}/topos/features/derivation/writer.py +125 -12
  17. topos_node-1.3.30/topos/features/entities/community_names.py +114 -0
  18. topos_node-1.3.30/topos/features/entities/community_naming.py +111 -0
  19. {topos_node-1.3.28 → topos_node-1.3.30}/topos/features/entities/maintenance.py +107 -2
  20. {topos_node-1.3.28 → topos_node-1.3.30}/topos/features/facts/reads.py +3 -0
  21. {topos_node-1.3.28 → topos_node-1.3.30}/topos/protocol/handled_message_types.json +5 -0
  22. {topos_node-1.3.28 → topos_node-1.3.30}/topos/protocol/narrowing_vocabulary.json +1 -0
  23. {topos_node-1.3.28 → topos_node-1.3.30}/topos/query/game_layer.py +17 -0
  24. {topos_node-1.3.28 → topos_node-1.3.30}/topos/query/narrowing.py +1 -0
  25. {topos_node-1.3.28 → topos_node-1.3.30}/topos/query/packet_resolution.py +17 -2
  26. {topos_node-1.3.28 → topos_node-1.3.30}/topos/query/pipeline.py +2 -1
  27. {topos_node-1.3.28 → topos_node-1.3.30}/topos/query/retrieval.py +52 -2
  28. {topos_node-1.3.28 → topos_node-1.3.30}/topos/storage/adapters/sqlite/stores.py +41 -9
  29. topos_node-1.3.30/topos/storage/db/migrations/community_names_v1.py +47 -0
  30. topos_node-1.3.30/topos/storage/db/migrations/conflict_provenance_v1.py +35 -0
  31. {topos_node-1.3.28 → topos_node-1.3.30}/topos/storage/db/migrations/registry.py +10 -0
  32. {topos_node-1.3.28 → topos_node-1.3.30}/topos/storage/db/migrations/registry_checksums.json +2 -0
  33. {topos_node-1.3.28 → topos_node-1.3.30}/topos/upgrades/manifests.json +12 -0
  34. {topos_node-1.3.28 → topos_node-1.3.30/topos_node.egg-info}/PKG-INFO +1 -1
  35. {topos_node-1.3.28 → topos_node-1.3.30}/topos_node.egg-info/SOURCES.txt +7 -0
  36. topos_node-1.3.28/topos/features/derivation/surfaces.py +0 -123
  37. {topos_node-1.3.28 → topos_node-1.3.30}/LICENSE +0 -0
  38. {topos_node-1.3.28 → topos_node-1.3.30}/MANIFEST.in +0 -0
  39. {topos_node-1.3.28 → topos_node-1.3.30}/README.md +0 -0
  40. {topos_node-1.3.28 → topos_node-1.3.30}/setup.cfg +0 -0
  41. {topos_node-1.3.28 → topos_node-1.3.30}/shared/__init__.py +0 -0
  42. {topos_node-1.3.28 → topos_node-1.3.30}/shared/filtering.py +0 -0
  43. {topos_node-1.3.28 → topos_node-1.3.30}/shared/schema_registry.py +0 -0
  44. {topos_node-1.3.28 → topos_node-1.3.30}/tests/test_active_database_binding.py +0 -0
  45. {topos_node-1.3.28 → topos_node-1.3.30}/tests/test_active_ingestion_binding.py +0 -0
  46. {topos_node-1.3.28 → topos_node-1.3.30}/tests/test_extensions.py +0 -0
  47. {topos_node-1.3.28 → topos_node-1.3.30}/tests/test_gate_leg_hermeticity.py +0 -0
  48. {topos_node-1.3.28 → topos_node-1.3.30}/tests/test_llm_integrations_storage.py +0 -0
  49. {topos_node-1.3.28 → topos_node-1.3.30}/tests/test_local_gate_composition.py +0 -0
  50. {topos_node-1.3.28 → topos_node-1.3.30}/tests/test_owner_database_hermeticity.py +0 -0
  51. {topos_node-1.3.28 → topos_node-1.3.30}/tests/test_prewarm_first_run.py +0 -0
  52. {topos_node-1.3.28 → topos_node-1.3.30}/tests/test_profile_hygiene.py +0 -0
  53. {topos_node-1.3.28 → topos_node-1.3.30}/tests/test_profiles.py +0 -0
  54. {topos_node-1.3.28 → topos_node-1.3.30}/tests/test_protocol_handled_types.py +0 -0
  55. {topos_node-1.3.28 → topos_node-1.3.30}/tests/test_query_field_contract.py +0 -0
  56. {topos_node-1.3.28 → topos_node-1.3.30}/tests/test_system_computer_name.py +0 -0
  57. {topos_node-1.3.28 → topos_node-1.3.30}/topos/__init__.py +0 -0
  58. {topos_node-1.3.28 → topos_node-1.3.30}/topos/analytics/__init__.py +0 -0
  59. {topos_node-1.3.28 → topos_node-1.3.30}/topos/analytics/duckdb_adapter.py +0 -0
  60. {topos_node-1.3.28 → topos_node-1.3.30}/topos/analytics/messenger_communities.py +0 -0
  61. {topos_node-1.3.28 → topos_node-1.3.30}/topos/analytics/messenger_graph.py +0 -0
  62. {topos_node-1.3.28 → topos_node-1.3.30}/topos/analytics/messenger_labels.py +0 -0
  63. {topos_node-1.3.28 → topos_node-1.3.30}/topos/analytics/profiles.py +0 -0
  64. {topos_node-1.3.28 → topos_node-1.3.30}/topos/analytics/query_engine.py +0 -0
  65. {topos_node-1.3.28 → topos_node-1.3.30}/topos/analytics/raw_queries.py +0 -0
  66. {topos_node-1.3.28 → topos_node-1.3.30}/topos/api/__init__.py +0 -0
  67. {topos_node-1.3.28 → topos_node-1.3.30}/topos/api/analytics.py +0 -0
  68. {topos_node-1.3.28 → topos_node-1.3.30}/topos/api/app_registry.py +0 -0
  69. {topos_node-1.3.28 → topos_node-1.3.30}/topos/api/backup.py +0 -0
  70. {topos_node-1.3.28 → topos_node-1.3.30}/topos/api/compute_remote.py +0 -0
  71. {topos_node-1.3.28 → topos_node-1.3.30}/topos/api/conversation_context.py +0 -0
  72. {topos_node-1.3.28 → topos_node-1.3.30}/topos/api/data_commit.py +0 -0
  73. {topos_node-1.3.28 → topos_node-1.3.30}/topos/api/data_explorer_table_prefs.py +0 -0
  74. {topos_node-1.3.28 → topos_node-1.3.30}/topos/api/database_explorer.py +0 -0
  75. {topos_node-1.3.28 → topos_node-1.3.30}/topos/api/db.py +0 -0
  76. {topos_node-1.3.28 → topos_node-1.3.30}/topos/api/device.py +0 -0
  77. {topos_node-1.3.28 → topos_node-1.3.30}/topos/api/engine_run.py +0 -0
  78. {topos_node-1.3.28 → topos_node-1.3.30}/topos/api/enrichment.py +0 -0
  79. {topos_node-1.3.28 → topos_node-1.3.30}/topos/api/enrichment_lab.py +0 -0
  80. {topos_node-1.3.28 → topos_node-1.3.30}/topos/api/facts_llm_config.py +0 -0
  81. {topos_node-1.3.28 → topos_node-1.3.30}/topos/api/filter_lab.py +0 -0
  82. {topos_node-1.3.28 → topos_node-1.3.30}/topos/api/health.py +0 -0
  83. {topos_node-1.3.28 → topos_node-1.3.30}/topos/api/home_chat.py +0 -0
  84. {topos_node-1.3.28 → topos_node-1.3.30}/topos/api/ingestion_api.py +0 -0
  85. {topos_node-1.3.28 → topos_node-1.3.30}/topos/api/ingestion_compat.py +0 -0
  86. {topos_node-1.3.28 → topos_node-1.3.30}/topos/api/ingestion_sources.py +0 -0
  87. {topos_node-1.3.28 → topos_node-1.3.30}/topos/api/intelligence_lifecycle.py +0 -0
  88. {topos_node-1.3.28 → topos_node-1.3.30}/topos/api/llm.py +0 -0
  89. {topos_node-1.3.28 → topos_node-1.3.30}/topos/api/local_mcp.py +0 -0
  90. {topos_node-1.3.28 → topos_node-1.3.30}/topos/api/messenger_analytics.py +0 -0
  91. {topos_node-1.3.28 → topos_node-1.3.30}/topos/api/privacy_disclose.py +0 -0
  92. {topos_node-1.3.28 → topos_node-1.3.30}/topos/api/query_api.py +0 -0
  93. {topos_node-1.3.28 → topos_node-1.3.30}/topos/api/runtime_bootstrap.py +0 -0
  94. {topos_node-1.3.28 → topos_node-1.3.30}/topos/api/sanitization_ollama_config.py +0 -0
  95. {topos_node-1.3.28 → topos_node-1.3.30}/topos/api/shell.py +0 -0
  96. {topos_node-1.3.28 → topos_node-1.3.30}/topos/api/signal_extraction_config.py +0 -0
  97. {topos_node-1.3.28 → topos_node-1.3.30}/topos/api/source_install.py +0 -0
  98. {topos_node-1.3.28 → topos_node-1.3.30}/topos/api/source_scrub.py +0 -0
  99. {topos_node-1.3.28 → topos_node-1.3.30}/topos/api/sources.py +0 -0
  100. {topos_node-1.3.28 → topos_node-1.3.30}/topos/api/sources_overview.py +0 -0
  101. {topos_node-1.3.28 → topos_node-1.3.30}/topos/api/sync.py +0 -0
  102. {topos_node-1.3.28 → topos_node-1.3.30}/topos/api/tool_index.py +0 -0
  103. {topos_node-1.3.28 → topos_node-1.3.30}/topos/api/ui_config.py +0 -0
  104. {topos_node-1.3.28 → topos_node-1.3.30}/topos/api/uma_data.py +0 -0
  105. {topos_node-1.3.28 → topos_node-1.3.30}/topos/api/upgrades.py +0 -0
  106. {topos_node-1.3.28 → topos_node-1.3.30}/topos/api/usage.py +0 -0
  107. {topos_node-1.3.28 → topos_node-1.3.30}/topos/api/user_identity.py +0 -0
  108. {topos_node-1.3.28 → topos_node-1.3.30}/topos/auth.py +0 -0
  109. {topos_node-1.3.28 → topos_node-1.3.30}/topos/canonicalization/__init__.py +0 -0
  110. {topos_node-1.3.28 → topos_node-1.3.30}/topos/canonicalization/declared_field_map.py +0 -0
  111. {topos_node-1.3.28 → topos_node-1.3.30}/topos/canonicalization/mappers/__init__.py +0 -0
  112. {topos_node-1.3.28 → topos_node-1.3.30}/topos/canonicalization/mappers/base.py +0 -0
  113. {topos_node-1.3.28 → topos_node-1.3.30}/topos/canonicalization/mappers/browser_activity_mapper.py +0 -0
  114. {topos_node-1.3.28 → topos_node-1.3.30}/topos/canonicalization/mappers/chatgpt_mapper.py +0 -0
  115. {topos_node-1.3.28 → topos_node-1.3.30}/topos/canonicalization/mappers/demo_mappers.py +0 -0
  116. {topos_node-1.3.28 → topos_node-1.3.30}/topos/canonicalization/mappers/documents_mapper.py +0 -0
  117. {topos_node-1.3.28 → topos_node-1.3.30}/topos/canonicalization/mappers/github_activity_mapper.py +0 -0
  118. {topos_node-1.3.28 → topos_node-1.3.30}/topos/canonicalization/mappers/google_calendar_mapper.py +0 -0
  119. {topos_node-1.3.28 → topos_node-1.3.30}/topos/canonicalization/mappers/grok_mapper.py +0 -0
  120. {topos_node-1.3.28 → topos_node-1.3.30}/topos/canonicalization/mappers/messenger_mapper.py +0 -0
  121. {topos_node-1.3.28 → topos_node-1.3.30}/topos/canonicalization/models.py +0 -0
  122. {topos_node-1.3.28 → topos_node-1.3.30}/topos/canonicalization/resolver.py +0 -0
  123. {topos_node-1.3.28 → topos_node-1.3.30}/topos/cli/__init__.py +0 -0
  124. {topos_node-1.3.28 → topos_node-1.3.30}/topos/cli/__main__.py +0 -0
  125. {topos_node-1.3.28 → topos_node-1.3.30}/topos/cli/assets/topos_blk_rounded.png +0 -0
  126. {topos_node-1.3.28 → topos_node-1.3.30}/topos/cli/assets/topos_white.png +0 -0
  127. {topos_node-1.3.28 → topos_node-1.3.30}/topos/cli/commands.py +0 -0
  128. {topos_node-1.3.28 → topos_node-1.3.30}/topos/cli/profile_cmd.py +0 -0
  129. {topos_node-1.3.28 → topos_node-1.3.30}/topos/cli/reprocess_cmd.py +0 -0
  130. {topos_node-1.3.28 → topos_node-1.3.30}/topos/cli/setup_models_cmd.py +0 -0
  131. {topos_node-1.3.28 → topos_node-1.3.30}/topos/cli/tray.py +0 -0
  132. {topos_node-1.3.28 → topos_node-1.3.30}/topos/config/__init__.py +0 -0
  133. {topos_node-1.3.28 → topos_node-1.3.30}/topos/config/conversation_context_llm.py +0 -0
  134. {topos_node-1.3.28 → topos_node-1.3.30}/topos/config/facts_llm.py +0 -0
  135. {topos_node-1.3.28 → topos_node-1.3.30}/topos/config/local_model_builds.py +0 -0
  136. {topos_node-1.3.28 → topos_node-1.3.30}/topos/config/node_function_providers.py +0 -0
  137. {topos_node-1.3.28 → topos_node-1.3.30}/topos/config/sanitization_ollama.py +0 -0
  138. {topos_node-1.3.28 → topos_node-1.3.30}/topos/config/settings.py +0 -0
  139. {topos_node-1.3.28 → topos_node-1.3.30}/topos/config/signal_extraction.py +0 -0
  140. {topos_node-1.3.28 → topos_node-1.3.30}/topos/config/uvicorn_logging.json +0 -0
  141. {topos_node-1.3.28 → topos_node-1.3.30}/topos/contacts/__init__.py +0 -0
  142. {topos_node-1.3.28 → topos_node-1.3.30}/topos/contacts/identity.py +0 -0
  143. {topos_node-1.3.28 → topos_node-1.3.30}/topos/control_plane_client.py +0 -0
  144. {topos_node-1.3.28 → topos_node-1.3.30}/topos/core/__init__.py +0 -0
  145. {topos_node-1.3.28 → topos_node-1.3.30}/topos/core/api_models.py +0 -0
  146. {topos_node-1.3.28 → topos_node-1.3.30}/topos/core/connection_resilience.py +0 -0
  147. {topos_node-1.3.28 → topos_node-1.3.30}/topos/core/db_health.py +0 -0
  148. {topos_node-1.3.28 → topos_node-1.3.30}/topos/core/device_helpers.py +0 -0
  149. {topos_node-1.3.28 → topos_node-1.3.30}/topos/core/errors.py +0 -0
  150. {topos_node-1.3.28 → topos_node-1.3.30}/topos/core/events.py +0 -0
  151. {topos_node-1.3.28 → topos_node-1.3.30}/topos/core/handlers/__init__.py +0 -0
  152. {topos_node-1.3.28 → topos_node-1.3.30}/topos/core/handlers/common.py +0 -0
  153. {topos_node-1.3.28 → topos_node-1.3.30}/topos/core/handlers/complexity.py +0 -0
  154. {topos_node-1.3.28 → topos_node-1.3.30}/topos/core/handlers/config.py +0 -0
  155. {topos_node-1.3.28 → topos_node-1.3.30}/topos/core/handlers/contacts_import.py +0 -0
  156. {topos_node-1.3.28 → topos_node-1.3.30}/topos/core/handlers/database_explorer.py +0 -0
  157. {topos_node-1.3.28 → topos_node-1.3.30}/topos/core/handlers/device.py +0 -0
  158. {topos_node-1.3.28 → topos_node-1.3.30}/topos/core/handlers/enrichment.py +0 -0
  159. {topos_node-1.3.28 → topos_node-1.3.30}/topos/core/handlers/enrichment_lab.py +0 -0
  160. {topos_node-1.3.28 → topos_node-1.3.30}/topos/core/handlers/filter_lab.py +0 -0
  161. {topos_node-1.3.28 → topos_node-1.3.30}/topos/core/handlers/graph_query.py +0 -0
  162. {topos_node-1.3.28 → topos_node-1.3.30}/topos/core/handlers/home_chat.py +0 -0
  163. {topos_node-1.3.28 → topos_node-1.3.30}/topos/core/handlers/ingest.py +0 -0
  164. {topos_node-1.3.28 → topos_node-1.3.30}/topos/core/handlers/messages.py +0 -0
  165. {topos_node-1.3.28 → topos_node-1.3.30}/topos/core/handlers/messenger_analytics.py +0 -0
  166. {topos_node-1.3.28 → topos_node-1.3.30}/topos/core/handlers/query.py +0 -0
  167. {topos_node-1.3.28 → topos_node-1.3.30}/topos/core/handlers/registry.py +0 -0
  168. {topos_node-1.3.28 → topos_node-1.3.30}/topos/core/handlers/routines.py +0 -0
  169. {topos_node-1.3.28 → topos_node-1.3.30}/topos/core/handlers/sources.py +0 -0
  170. {topos_node-1.3.28 → topos_node-1.3.30}/topos/core/handlers/timeline_daily.py +0 -0
  171. {topos_node-1.3.28 → topos_node-1.3.30}/topos/core/handlers/tool_index.py +0 -0
  172. {topos_node-1.3.28 → topos_node-1.3.30}/topos/core/handlers/uma.py +0 -0
  173. {topos_node-1.3.28 → topos_node-1.3.30}/topos/core/logging.py +0 -0
  174. {topos_node-1.3.28 → topos_node-1.3.30}/topos/core/metrics.py +0 -0
  175. {topos_node-1.3.28 → topos_node-1.3.30}/topos/core/routine_access.py +0 -0
  176. {topos_node-1.3.28 → topos_node-1.3.30}/topos/core/startup_banner.py +0 -0
  177. {topos_node-1.3.28 → topos_node-1.3.30}/topos/core/state.py +0 -0
  178. {topos_node-1.3.28 → topos_node-1.3.30}/topos/core/table_layers.py +0 -0
  179. {topos_node-1.3.28 → topos_node-1.3.30}/topos/core/types.py +0 -0
  180. {topos_node-1.3.28 → topos_node-1.3.30}/topos/data_explorer_row_delete.py +0 -0
  181. {topos_node-1.3.28 → topos_node-1.3.30}/topos/data_explorer_table_prefs.py +0 -0
  182. {topos_node-1.3.28 → topos_node-1.3.30}/topos/data_explorer_tables.py +0 -0
  183. {topos_node-1.3.28 → topos_node-1.3.30}/topos/disclosure/__init__.py +0 -0
  184. {topos_node-1.3.28 → topos_node-1.3.30}/topos/disclosure/canonical_writer.py +0 -0
  185. {topos_node-1.3.28 → topos_node-1.3.30}/topos/disclosure/content_policy.py +0 -0
  186. {topos_node-1.3.28 → topos_node-1.3.30}/topos/disclosure/field_registry.py +0 -0
  187. {topos_node-1.3.28 → topos_node-1.3.30}/topos/disclosure/privacy_layer.py +0 -0
  188. {topos_node-1.3.28 → topos_node-1.3.30}/topos/disclosure/tier.py +0 -0
  189. {topos_node-1.3.28 → topos_node-1.3.30}/topos/engine/__init__.py +0 -0
  190. {topos_node-1.3.28 → topos_node-1.3.30}/topos/engine/backends/__init__.py +0 -0
  191. {topos_node-1.3.28 → topos_node-1.3.30}/topos/engine/backends/base.py +0 -0
  192. {topos_node-1.3.28 → topos_node-1.3.30}/topos/engine/backends/generative_prompts.py +0 -0
  193. {topos_node-1.3.28 → topos_node-1.3.30}/topos/engine/backends/generative_response.py +0 -0
  194. {topos_node-1.3.28 → topos_node-1.3.30}/topos/engine/backends/huggingface.py +0 -0
  195. {topos_node-1.3.28 → topos_node-1.3.30}/topos/engine/backends/ollama.py +0 -0
  196. {topos_node-1.3.28 → topos_node-1.3.30}/topos/engine/backends/openai.py +0 -0
  197. {topos_node-1.3.28 → topos_node-1.3.30}/topos/engine/backends/openai_compatible.py +0 -0
  198. {topos_node-1.3.28 → topos_node-1.3.30}/topos/engine/backends/redpill.py +0 -0
  199. {topos_node-1.3.28 → topos_node-1.3.30}/topos/engine/backends/stub.py +0 -0
  200. {topos_node-1.3.28 → topos_node-1.3.30}/topos/engine/client.py +0 -0
  201. {topos_node-1.3.28 → topos_node-1.3.30}/topos/engine/disk_space.py +0 -0
  202. {topos_node-1.3.28 → topos_node-1.3.30}/topos/engine/engine.py +0 -0
  203. {topos_node-1.3.28 → topos_node-1.3.30}/topos/engine/intake.py +0 -0
  204. {topos_node-1.3.28 → topos_node-1.3.30}/topos/engine/memory_utils.py +0 -0
  205. {topos_node-1.3.28 → topos_node-1.3.30}/topos/engine/model_cache.py +0 -0
  206. {topos_node-1.3.28 → topos_node-1.3.30}/topos/engine/ollama_install.py +0 -0
  207. {topos_node-1.3.28 → topos_node-1.3.30}/topos/engine/ollama_pull.py +0 -0
  208. {topos_node-1.3.28 → topos_node-1.3.30}/topos/engine/ollama_setup_guidance.py +0 -0
  209. {topos_node-1.3.28 → topos_node-1.3.30}/topos/engine/pipeline_memory.py +0 -0
  210. {topos_node-1.3.28 → topos_node-1.3.30}/topos/engine/queue_manager.py +0 -0
  211. {topos_node-1.3.28 → topos_node-1.3.30}/topos/engine/registration.py +0 -0
  212. {topos_node-1.3.28 → topos_node-1.3.30}/topos/engine/result_formatter.py +0 -0
  213. {topos_node-1.3.28 → topos_node-1.3.30}/topos/engine/router.py +0 -0
  214. {topos_node-1.3.28 → topos_node-1.3.30}/topos/engine/scoped_token.py +0 -0
  215. {topos_node-1.3.28 → topos_node-1.3.30}/topos/engine/tasks.py +0 -0
  216. {topos_node-1.3.28 → topos_node-1.3.30}/topos/engine/torch_runtime.py +0 -0
  217. {topos_node-1.3.28 → topos_node-1.3.30}/topos/engine/transport.py +0 -0
  218. {topos_node-1.3.28 → topos_node-1.3.30}/topos/engine/usage_guard.py +0 -0
  219. {topos_node-1.3.28 → topos_node-1.3.30}/topos/engine/usage_observation.py +0 -0
  220. {topos_node-1.3.28 → topos_node-1.3.30}/topos/engine/validator.py +0 -0
  221. {topos_node-1.3.28 → topos_node-1.3.30}/topos/enrichment/__init__.py +0 -0
  222. {topos_node-1.3.28 → topos_node-1.3.30}/topos/enrichment/catalog.py +0 -0
  223. {topos_node-1.3.28 → topos_node-1.3.30}/topos/enrichment/derivation_recovery.py +0 -0
  224. {topos_node-1.3.28 → topos_node-1.3.30}/topos/enrichment/derived_tables.py +0 -0
  225. {topos_node-1.3.28 → topos_node-1.3.30}/topos/enrichment/job_readiness.py +0 -0
  226. {topos_node-1.3.28 → topos_node-1.3.30}/topos/enrichment/job_writer.py +0 -0
  227. {topos_node-1.3.28 → topos_node-1.3.30}/topos/enrichment/jobs/__init__.py +0 -0
  228. {topos_node-1.3.28 → topos_node-1.3.30}/topos/enrichment/jobs/base.py +0 -0
  229. {topos_node-1.3.28 → topos_node-1.3.30}/topos/enrichment/jobs/canonical/__init__.py +0 -0
  230. {topos_node-1.3.28 → topos_node-1.3.30}/topos/enrichment/jobs/canonical/_batch_limits.py +0 -0
  231. {topos_node-1.3.28 → topos_node-1.3.30}/topos/enrichment/jobs/canonical/_engine_runner.py +0 -0
  232. {topos_node-1.3.28 → topos_node-1.3.30}/topos/enrichment/jobs/canonical/attention_triage_job.py +0 -0
  233. {topos_node-1.3.28 → topos_node-1.3.30}/topos/enrichment/jobs/canonical/availability_scores_job.py +0 -0
  234. {topos_node-1.3.28 → topos_node-1.3.30}/topos/enrichment/jobs/canonical/brief_fallback.py +0 -0
  235. {topos_node-1.3.28 → topos_node-1.3.30}/topos/enrichment/jobs/canonical/complexity_snapshot_job.py +0 -0
  236. {topos_node-1.3.28 → topos_node-1.3.30}/topos/enrichment/jobs/canonical/dimension_summary_job.py +0 -0
  237. {topos_node-1.3.28 → topos_node-1.3.30}/topos/enrichment/jobs/canonical/embeddings_job.py +0 -0
  238. {topos_node-1.3.28 → topos_node-1.3.30}/topos/enrichment/jobs/canonical/emo_27_job.py +0 -0
  239. {topos_node-1.3.28 → topos_node-1.3.30}/topos/enrichment/jobs/canonical/entities_job.py +0 -0
  240. {topos_node-1.3.28 → topos_node-1.3.30}/topos/enrichment/jobs/canonical/fact_extraction_job.py +0 -0
  241. {topos_node-1.3.28 → topos_node-1.3.30}/topos/enrichment/jobs/canonical/goal_extraction_job.py +0 -0
  242. {topos_node-1.3.28 → topos_node-1.3.30}/topos/enrichment/jobs/canonical/pii_redaction_job.py +0 -0
  243. {topos_node-1.3.28 → topos_node-1.3.30}/topos/enrichment/jobs/canonical/relationship_edges_job.py +0 -0
  244. {topos_node-1.3.28 → topos_node-1.3.30}/topos/enrichment/jobs/canonical/sentiment_job.py +0 -0
  245. {topos_node-1.3.28 → topos_node-1.3.30}/topos/enrichment/jobs/canonical/statistics_job.py +0 -0
  246. {topos_node-1.3.28 → topos_node-1.3.30}/topos/enrichment/jobs/canonical/timeline_job.py +0 -0
  247. {topos_node-1.3.28 → topos_node-1.3.30}/topos/enrichment/jobs/canonical/topic_clusters_job.py +0 -0
  248. {topos_node-1.3.28 → topos_node-1.3.30}/topos/enrichment/jobs/canonical/topics_job.py +0 -0
  249. {topos_node-1.3.28 → topos_node-1.3.30}/topos/enrichment/jobs/raw/__init__.py +0 -0
  250. {topos_node-1.3.28 → topos_node-1.3.30}/topos/enrichment/jobs/raw/attachments_job.py +0 -0
  251. {topos_node-1.3.28 → topos_node-1.3.30}/topos/enrichment/jobs/raw/language_job.py +0 -0
  252. {topos_node-1.3.28 → topos_node-1.3.30}/topos/enrichment/jobs/raw/time_normalization_job.py +0 -0
  253. {topos_node-1.3.28 → topos_node-1.3.30}/topos/enrichment/jobs/raw/tool_calls_job.py +0 -0
  254. {topos_node-1.3.28 → topos_node-1.3.30}/topos/enrichment/model_overrides.py +0 -0
  255. {topos_node-1.3.28 → topos_node-1.3.30}/topos/enrichment/models/__init__.py +0 -0
  256. {topos_node-1.3.28 → topos_node-1.3.30}/topos/enrichment/models/manager.py +0 -0
  257. {topos_node-1.3.28 → topos_node-1.3.30}/topos/enrichment/models/mvp_defaults.py +0 -0
  258. {topos_node-1.3.28 → topos_node-1.3.30}/topos/enrichment/models/registry.py +0 -0
  259. {topos_node-1.3.28 → topos_node-1.3.30}/topos/enrichment/models/versioning.py +0 -0
  260. {topos_node-1.3.28 → topos_node-1.3.30}/topos/enrichment/orchestrator.py +0 -0
  261. {topos_node-1.3.28 → topos_node-1.3.30}/topos/enrichment/pipeline_activity.py +0 -0
  262. {topos_node-1.3.28 → topos_node-1.3.30}/topos/enrichment/processor.py +0 -0
  263. {topos_node-1.3.28 → topos_node-1.3.30}/topos/enrichment/progress_bar.py +0 -0
  264. {topos_node-1.3.28 → topos_node-1.3.30}/topos/enrichment/registry_contract.py +0 -0
  265. {topos_node-1.3.28 → topos_node-1.3.30}/topos/enrichment/signal_derivation_config.json +0 -0
  266. {topos_node-1.3.28 → topos_node-1.3.30}/topos/enrichment/source_overrides.py +0 -0
  267. {topos_node-1.3.28 → topos_node-1.3.30}/topos/enrichment_lab/__init__.py +0 -0
  268. {topos_node-1.3.28 → topos_node-1.3.30}/topos/enrichment_lab/bundles.py +0 -0
  269. {topos_node-1.3.28 → topos_node-1.3.30}/topos/enrichment_lab/model_resolve.py +0 -0
  270. {topos_node-1.3.28 → topos_node-1.3.30}/topos/enrichment_lab/schema.py +0 -0
  271. {topos_node-1.3.28 → topos_node-1.3.30}/topos/enrichment_lab/service.py +0 -0
  272. {topos_node-1.3.28 → topos_node-1.3.30}/topos/enrichment_lab/store.py +0 -0
  273. {topos_node-1.3.28 → topos_node-1.3.30}/topos/enrichment_lab/worker.py +0 -0
  274. {topos_node-1.3.28 → topos_node-1.3.30}/topos/evals/__init__.py +0 -0
  275. {topos_node-1.3.28 → topos_node-1.3.30}/topos/evals/enrichment_eval.py +0 -0
  276. {topos_node-1.3.28 → topos_node-1.3.30}/topos/extensions.py +0 -0
  277. {topos_node-1.3.28 → topos_node-1.3.30}/topos/features/complexity/__init__.py +0 -0
  278. {topos_node-1.3.28 → topos_node-1.3.30}/topos/features/complexity/canonical.py +0 -0
  279. {topos_node-1.3.28 → topos_node-1.3.30}/topos/features/complexity/engine.py +0 -0
  280. {topos_node-1.3.28 → topos_node-1.3.30}/topos/features/complexity/entropy.py +0 -0
  281. {topos_node-1.3.28 → topos_node-1.3.30}/topos/features/complexity/focus.py +0 -0
  282. {topos_node-1.3.28 → topos_node-1.3.30}/topos/features/complexity/graph_metrics.py +0 -0
  283. {topos_node-1.3.28 → topos_node-1.3.30}/topos/features/complexity/influence.py +0 -0
  284. {topos_node-1.3.28 → topos_node-1.3.30}/topos/features/complexity/projection.py +0 -0
  285. {topos_node-1.3.28 → topos_node-1.3.30}/topos/features/complexity/snapshots.py +0 -0
  286. {topos_node-1.3.28 → topos_node-1.3.30}/topos/features/complexity/store.py +0 -0
  287. {topos_node-1.3.28 → topos_node-1.3.30}/topos/features/complexity/topic_merge.py +0 -0
  288. {topos_node-1.3.28 → topos_node-1.3.30}/topos/features/complexity/topics.py +0 -0
  289. {topos_node-1.3.28 → topos_node-1.3.30}/topos/features/complexity/topics_daily.py +0 -0
  290. {topos_node-1.3.28 → topos_node-1.3.30}/topos/features/complexity/volatility.py +0 -0
  291. {topos_node-1.3.28 → topos_node-1.3.30}/topos/features/derivation/__init__.py +0 -0
  292. {topos_node-1.3.28 → topos_node-1.3.30}/topos/features/derivation/bundled_packs/_scales.yaml +0 -0
  293. {topos_node-1.3.28 → topos_node-1.3.30}/topos/features/derivation/bundled_packs/admin.legal.yaml +0 -0
  294. {topos_node-1.3.28 → topos_node-1.3.30}/topos/features/derivation/bundled_packs/aspirations.goals.yaml +0 -0
  295. {topos_node-1.3.28 → topos_node-1.3.30}/topos/features/derivation/bundled_packs/behavior.habits.yaml +0 -0
  296. {topos_node-1.3.28 → topos_node-1.3.30}/topos/features/derivation/bundled_packs/behavior.preferences.yaml +0 -0
  297. {topos_node-1.3.28 → topos_node-1.3.30}/topos/features/derivation/bundled_packs/beliefs.civic.yaml +0 -0
  298. {topos_node-1.3.28 → topos_node-1.3.30}/topos/features/derivation/bundled_packs/beliefs.spiritual.yaml +0 -0
  299. {topos_node-1.3.28 → topos_node-1.3.30}/topos/features/derivation/bundled_packs/communication.style.yaml +0 -0
  300. {topos_node-1.3.28 → topos_node-1.3.30}/topos/features/derivation/bundled_packs/community.membership.yaml +0 -0
  301. {topos_node-1.3.28 → topos_node-1.3.30}/topos/features/derivation/bundled_packs/craft.tooling.yaml +0 -0
  302. {topos_node-1.3.28 → topos_node-1.3.30}/topos/features/derivation/bundled_packs/expertise.knowledge.yaml +0 -0
  303. {topos_node-1.3.28 → topos_node-1.3.30}/topos/features/derivation/bundled_packs/finances.economics.yaml +0 -0
  304. {topos_node-1.3.28 → topos_node-1.3.30}/topos/features/derivation/bundled_packs/health.lifestyle.yaml +0 -0
  305. {topos_node-1.3.28 → topos_node-1.3.30}/topos/features/derivation/bundled_packs/health.mental.yaml +0 -0
  306. {topos_node-1.3.28 → topos_node-1.3.30}/topos/features/derivation/bundled_packs/health.physical.yaml +0 -0
  307. {topos_node-1.3.28 → topos_node-1.3.30}/topos/features/derivation/bundled_packs/household.pets.yaml +0 -0
  308. {topos_node-1.3.28 → topos_node-1.3.30}/topos/features/derivation/bundled_packs/identity.core.yaml +0 -0
  309. {topos_node-1.3.28 → topos_node-1.3.30}/topos/features/derivation/bundled_packs/interests.taste.yaml +0 -0
  310. {topos_node-1.3.28 → topos_node-1.3.30}/topos/features/derivation/bundled_packs/life.events.yaml +0 -0
  311. {topos_node-1.3.28 → topos_node-1.3.30}/topos/features/derivation/bundled_packs/narrative.self.yaml +0 -0
  312. {topos_node-1.3.28 → topos_node-1.3.30}/topos/features/derivation/bundled_packs/personality.traits.yaml +0 -0
  313. {topos_node-1.3.28 → topos_node-1.3.30}/topos/features/derivation/bundled_packs/places.mobility.yaml +0 -0
  314. {topos_node-1.3.28 → topos_node-1.3.30}/topos/features/derivation/bundled_packs/possessions.assets.yaml +0 -0
  315. {topos_node-1.3.28 → topos_node-1.3.30}/topos/features/derivation/bundled_packs/values.motivation.yaml +0 -0
  316. {topos_node-1.3.28 → topos_node-1.3.30}/topos/features/derivation/bundled_packs/vocab/dispositions.yaml +0 -0
  317. {topos_node-1.3.28 → topos_node-1.3.30}/topos/features/derivation/bundled_packs/vocab/expertise.yaml +0 -0
  318. {topos_node-1.3.28 → topos_node-1.3.30}/topos/features/derivation/bundled_packs/vocab/habits.yaml +0 -0
  319. {topos_node-1.3.28 → topos_node-1.3.30}/topos/features/derivation/bundled_packs/vocab/interests.yaml +0 -0
  320. {topos_node-1.3.28 → topos_node-1.3.30}/topos/features/derivation/bundled_packs/vocab/preferences.yaml +0 -0
  321. {topos_node-1.3.28 → topos_node-1.3.30}/topos/features/derivation/bundled_packs/vocab/stances.yaml +0 -0
  322. {topos_node-1.3.28 → topos_node-1.3.30}/topos/features/derivation/bundled_packs/vocab/tools.yaml +0 -0
  323. {topos_node-1.3.28 → topos_node-1.3.30}/topos/features/derivation/bundled_packs/vocab/values.yaml +0 -0
  324. {topos_node-1.3.28 → topos_node-1.3.30}/topos/features/derivation/bundled_packs/work.career.yaml +0 -0
  325. {topos_node-1.3.28 → topos_node-1.3.30}/topos/features/derivation/candidates.py +0 -0
  326. {topos_node-1.3.28 → topos_node-1.3.30}/topos/features/derivation/guard.py +0 -0
  327. {topos_node-1.3.28 → topos_node-1.3.30}/topos/features/derivation/packs.py +0 -0
  328. {topos_node-1.3.28 → topos_node-1.3.30}/topos/features/derivation/prefilter.py +0 -0
  329. {topos_node-1.3.28 → topos_node-1.3.30}/topos/features/derivation/registry.py +0 -0
  330. {topos_node-1.3.28 → topos_node-1.3.30}/topos/features/derivation/template.py +0 -0
  331. {topos_node-1.3.28 → topos_node-1.3.30}/topos/features/derivation/verify.py +0 -0
  332. {topos_node-1.3.28 → topos_node-1.3.30}/topos/features/entities/__init__.py +0 -0
  333. {topos_node-1.3.28 → topos_node-1.3.30}/topos/features/entities/affinity.py +0 -0
  334. {topos_node-1.3.28 → topos_node-1.3.30}/topos/features/entities/affinity_owner.py +0 -0
  335. {topos_node-1.3.28 → topos_node-1.3.30}/topos/features/entities/affinity_quality.py +0 -0
  336. {topos_node-1.3.28 → topos_node-1.3.30}/topos/features/entities/consolidation.py +0 -0
  337. {topos_node-1.3.28 → topos_node-1.3.30}/topos/features/entities/context_vectors.py +0 -0
  338. {topos_node-1.3.28 → topos_node-1.3.30}/topos/features/entities/cypher.py +0 -0
  339. {topos_node-1.3.28 → topos_node-1.3.30}/topos/features/entities/declared_mappings.py +0 -0
  340. {topos_node-1.3.28 → topos_node-1.3.30}/topos/features/entities/dossier.py +0 -0
  341. {topos_node-1.3.28 → topos_node-1.3.30}/topos/features/entities/edges.py +0 -0
  342. {topos_node-1.3.28 → topos_node-1.3.30}/topos/features/entities/fact_materializer.py +0 -0
  343. {topos_node-1.3.28 → topos_node-1.3.30}/topos/features/entities/graph_enrichers.py +0 -0
  344. {topos_node-1.3.28 → topos_node-1.3.30}/topos/features/entities/graph_refresh.py +0 -0
  345. {topos_node-1.3.28 → topos_node-1.3.30}/topos/features/entities/graph_search.py +0 -0
  346. {topos_node-1.3.28 → topos_node-1.3.30}/topos/features/entities/linking.py +0 -0
  347. {topos_node-1.3.28 → topos_node-1.3.30}/topos/features/entities/reads.py +0 -0
  348. {topos_node-1.3.28 → topos_node-1.3.30}/topos/features/entities/rebuild_subprocess.py +0 -0
  349. {topos_node-1.3.28 → topos_node-1.3.30}/topos/features/entities/resolver.py +0 -0
  350. {topos_node-1.3.28 → topos_node-1.3.30}/topos/features/facts/__init__.py +0 -0
  351. {topos_node-1.3.28 → topos_node-1.3.30}/topos/features/facts/extract.py +0 -0
  352. {topos_node-1.3.28 → topos_node-1.3.30}/topos/features/facts/llm_extract.py +0 -0
  353. {topos_node-1.3.28 → topos_node-1.3.30}/topos/features/facts/store.py +0 -0
  354. {topos_node-1.3.28 → topos_node-1.3.30}/topos/features/facts/verdicts.py +0 -0
  355. {topos_node-1.3.28 → topos_node-1.3.30}/topos/features/fit/evaluator.py +0 -0
  356. {topos_node-1.3.28 → topos_node-1.3.30}/topos/features/fit/opportunity_types.json +0 -0
  357. {topos_node-1.3.28 → topos_node-1.3.30}/topos/features/lifecycle/__init__.py +0 -0
  358. {topos_node-1.3.28 → topos_node-1.3.30}/topos/features/lifecycle/blackhole.py +0 -0
  359. {topos_node-1.3.28 → topos_node-1.3.30}/topos/features/lifecycle/blackhole_guard.py +0 -0
  360. {topos_node-1.3.28 → topos_node-1.3.30}/topos/features/lifecycle/blackhole_llm.py +0 -0
  361. {topos_node-1.3.28 → topos_node-1.3.30}/topos/features/lifecycle/blackhole_rebuild.py +0 -0
  362. {topos_node-1.3.28 → topos_node-1.3.30}/topos/features/lifecycle/derived_scrub.py +0 -0
  363. {topos_node-1.3.28 → topos_node-1.3.30}/topos/features/lifecycle/exclusions.py +0 -0
  364. {topos_node-1.3.28 → topos_node-1.3.30}/topos/features/lifecycle/gc.py +0 -0
  365. {topos_node-1.3.28 → topos_node-1.3.30}/topos/features/provenance/__init__.py +0 -0
  366. {topos_node-1.3.28 → topos_node-1.3.30}/topos/features/provenance/posture.py +0 -0
  367. {topos_node-1.3.28 → topos_node-1.3.30}/topos/features/provenance/roles.py +0 -0
  368. {topos_node-1.3.28 → topos_node-1.3.30}/topos/features/signal/__init__.py +0 -0
  369. {topos_node-1.3.28 → topos_node-1.3.30}/topos/features/signal/brief_canonical_loader.py +0 -0
  370. {topos_node-1.3.28 → topos_node-1.3.30}/topos/features/signal/brief_ontology.py +0 -0
  371. {topos_node-1.3.28 → topos_node-1.3.30}/topos/features/signal/brief_renderer.py +0 -0
  372. {topos_node-1.3.28 → topos_node-1.3.30}/topos/features/signal/brief_schemas.py +0 -0
  373. {topos_node-1.3.28 → topos_node-1.3.30}/topos/features/signal/chunking.py +0 -0
  374. {topos_node-1.3.28 → topos_node-1.3.30}/topos/features/signal/cluster_labels.py +0 -0
  375. {topos_node-1.3.28 → topos_node-1.3.30}/topos/features/signal/conversation_context.py +0 -0
  376. {topos_node-1.3.28 → topos_node-1.3.30}/topos/features/signal/data_health.py +0 -0
  377. {topos_node-1.3.28 → topos_node-1.3.30}/topos/features/signal/definitions/brief_ontologies.json +0 -0
  378. {topos_node-1.3.28 → topos_node-1.3.30}/topos/features/signal/definitions/intentions.json +0 -0
  379. {topos_node-1.3.28 → topos_node-1.3.30}/topos/features/signal/definitions/interests.json +0 -0
  380. {topos_node-1.3.28 → topos_node-1.3.30}/topos/features/signal/definitions/memory.json +0 -0
  381. {topos_node-1.3.28 → topos_node-1.3.30}/topos/features/signal/definitions/places.json +0 -0
  382. {topos_node-1.3.28 → topos_node-1.3.30}/topos/features/signal/definitions/profile.json +0 -0
  383. {topos_node-1.3.28 → topos_node-1.3.30}/topos/features/signal/definitions/relationships.json +0 -0
  384. {topos_node-1.3.28 → topos_node-1.3.30}/topos/features/signal/definitions/resources.json +0 -0
  385. {topos_node-1.3.28 → topos_node-1.3.30}/topos/features/signal/definitions/schema/dimension_definition.schema.json +0 -0
  386. {topos_node-1.3.28 → topos_node-1.3.30}/topos/features/signal/definitions/time.json +0 -0
  387. {topos_node-1.3.28 → topos_node-1.3.30}/topos/features/signal/definitions/wellbeing.json +0 -0
  388. {topos_node-1.3.28 → topos_node-1.3.30}/topos/features/signal/definitions/work.json +0 -0
  389. {topos_node-1.3.28 → topos_node-1.3.30}/topos/features/signal/derived_spec.py +0 -0
  390. {topos_node-1.3.28 → topos_node-1.3.30}/topos/features/signal/dimension_briefs.py +0 -0
  391. {topos_node-1.3.28 → topos_node-1.3.30}/topos/features/signal/dimension_definition_loader.py +0 -0
  392. {topos_node-1.3.28 → topos_node-1.3.30}/topos/features/signal/dimension_profiles.py +0 -0
  393. {topos_node-1.3.28 → topos_node-1.3.30}/topos/features/signal/dimension_registry.py +0 -0
  394. {topos_node-1.3.28 → topos_node-1.3.30}/topos/features/signal/embed_context.py +0 -0
  395. {topos_node-1.3.28 → topos_node-1.3.30}/topos/features/signal/extraction/artifact_router.py +0 -0
  396. {topos_node-1.3.28 → topos_node-1.3.30}/topos/features/signal/extraction/artifact_store.py +0 -0
  397. {topos_node-1.3.28 → topos_node-1.3.30}/topos/features/signal/extraction/rule_extractors.py +0 -0
  398. {topos_node-1.3.28 → topos_node-1.3.30}/topos/features/signal/graph_sanitize.py +0 -0
  399. {topos_node-1.3.28 → topos_node-1.3.30}/topos/features/signal/hybrid_search.py +0 -0
  400. {topos_node-1.3.28 → topos_node-1.3.30}/topos/features/signal/incremental_clustering.py +0 -0
  401. {topos_node-1.3.28 → topos_node-1.3.30}/topos/features/signal/model_recommendations.py +0 -0
  402. {topos_node-1.3.28 → topos_node-1.3.30}/topos/features/signal/query_embed_cache.py +0 -0
  403. {topos_node-1.3.28 → topos_node-1.3.30}/topos/features/signal/schemas.py +0 -0
  404. {topos_node-1.3.28 → topos_node-1.3.30}/topos/features/signal/service.py +0 -0
  405. {topos_node-1.3.28 → topos_node-1.3.30}/topos/features/signal/signal_object_store.py +0 -0
  406. {topos_node-1.3.28 → topos_node-1.3.30}/topos/features/signal/source_hydration.py +0 -0
  407. {topos_node-1.3.28 → topos_node-1.3.30}/topos/features/signal/structured_signal.py +0 -0
  408. {topos_node-1.3.28 → topos_node-1.3.30}/topos/features/signal/tool_index.py +0 -0
  409. {topos_node-1.3.28 → topos_node-1.3.30}/topos/features/signal/topic_clustering.py +0 -0
  410. {topos_node-1.3.28 → topos_node-1.3.30}/topos/features/signal/typed_stores/aggregates.py +0 -0
  411. {topos_node-1.3.28 → topos_node-1.3.30}/topos/features/signal/typed_stores/commitments.py +0 -0
  412. {topos_node-1.3.28 → topos_node-1.3.30}/topos/features/signal/typed_stores/rhythm.py +0 -0
  413. {topos_node-1.3.28 → topos_node-1.3.30}/topos/features/signal/typed_stores/scope_materializer.py +0 -0
  414. {topos_node-1.3.28 → topos_node-1.3.30}/topos/features/signal/vector_codec.py +0 -0
  415. {topos_node-1.3.28 → topos_node-1.3.30}/topos/features/signal/vector_math.py +0 -0
  416. {topos_node-1.3.28 → topos_node-1.3.30}/topos/features/signal/vector_settings.py +0 -0
  417. {topos_node-1.3.28 → topos_node-1.3.30}/topos/features/stats/__init__.py +0 -0
  418. {topos_node-1.3.28 → topos_node-1.3.30}/topos/features/stats/definitions.py +0 -0
  419. {topos_node-1.3.28 → topos_node-1.3.30}/topos/features/stats/engine.py +0 -0
  420. {topos_node-1.3.28 → topos_node-1.3.30}/topos/features/stats/fold.py +0 -0
  421. {topos_node-1.3.28 → topos_node-1.3.30}/topos/features/stats/insights.py +0 -0
  422. {topos_node-1.3.28 → topos_node-1.3.30}/topos/features/timeline_projection.py +0 -0
  423. {topos_node-1.3.28 → topos_node-1.3.30}/topos/features/timeline_rollup.py +0 -0
  424. {topos_node-1.3.28 → topos_node-1.3.30}/topos/features/triage/__init__.py +0 -0
  425. {topos_node-1.3.28 → topos_node-1.3.30}/topos/features/triage/badges.py +0 -0
  426. {topos_node-1.3.28 → topos_node-1.3.30}/topos/features/triage/daily.py +0 -0
  427. {topos_node-1.3.28 → topos_node-1.3.30}/topos/features/triage/dashboard.py +0 -0
  428. {topos_node-1.3.28 → topos_node-1.3.30}/topos/features/triage/instruments.py +0 -0
  429. {topos_node-1.3.28 → topos_node-1.3.30}/topos/features/triage/intents.py +0 -0
  430. {topos_node-1.3.28 → topos_node-1.3.30}/topos/features/triage/readiness.py +0 -0
  431. {topos_node-1.3.28 → topos_node-1.3.30}/topos/filter_lab/__init__.py +0 -0
  432. {topos_node-1.3.28 → topos_node-1.3.30}/topos/filter_lab/bundles.py +0 -0
  433. {topos_node-1.3.28 → topos_node-1.3.30}/topos/filter_lab/schema.py +0 -0
  434. {topos_node-1.3.28 → topos_node-1.3.30}/topos/filter_lab/service.py +0 -0
  435. {topos_node-1.3.28 → topos_node-1.3.30}/topos/filter_lab/store.py +0 -0
  436. {topos_node-1.3.28 → topos_node-1.3.30}/topos/filter_lab/worker.py +0 -0
  437. {topos_node-1.3.28 → topos_node-1.3.30}/topos/home_chat/__init__.py +0 -0
  438. {topos_node-1.3.28 → topos_node-1.3.30}/topos/home_chat/schema.py +0 -0
  439. {topos_node-1.3.28 → topos_node-1.3.30}/topos/home_chat/store.py +0 -0
  440. {topos_node-1.3.28 → topos_node-1.3.30}/topos/hosted_pool_lease.py +0 -0
  441. {topos_node-1.3.28 → topos_node-1.3.30}/topos/ingestion/__init__.py +0 -0
  442. {topos_node-1.3.28 → topos_node-1.3.30}/topos/ingestion/canonical_pipeline.py +0 -0
  443. {topos_node-1.3.28 → topos_node-1.3.30}/topos/ingestion/checkpoints/__init__.py +0 -0
  444. {topos_node-1.3.28 → topos_node-1.3.30}/topos/ingestion/checkpoints/checkpoint_store.py +0 -0
  445. {topos_node-1.3.28 → topos_node-1.3.30}/topos/ingestion/checkpoints/sqlite_checkpoint_store.py +0 -0
  446. {topos_node-1.3.28 → topos_node-1.3.30}/topos/ingestion/inbox_crypto.py +0 -0
  447. {topos_node-1.3.28 → topos_node-1.3.30}/topos/ingestion/inbox_drain.py +0 -0
  448. {topos_node-1.3.28 → topos_node-1.3.30}/topos/ingestion/ingest_helpers.py +0 -0
  449. {topos_node-1.3.28 → topos_node-1.3.30}/topos/ingestion/jobs.py +0 -0
  450. {topos_node-1.3.28 → topos_node-1.3.30}/topos/ingestion/journal_location_fanout.py +0 -0
  451. {topos_node-1.3.28 → topos_node-1.3.30}/topos/ingestion/journal_time_log_normalize.py +0 -0
  452. {topos_node-1.3.28 → topos_node-1.3.30}/topos/ingestion/local_sync.py +0 -0
  453. {topos_node-1.3.28 → topos_node-1.3.30}/topos/ingestion/log_preview.py +0 -0
  454. {topos_node-1.3.28 → topos_node-1.3.30}/topos/ingestion/manager.py +0 -0
  455. {topos_node-1.3.28 → topos_node-1.3.30}/topos/ingestion/parser.py +0 -0
  456. {topos_node-1.3.28 → topos_node-1.3.30}/topos/ingestion/parsers/__init__.py +0 -0
  457. {topos_node-1.3.28 → topos_node-1.3.30}/topos/ingestion/parsers/base.py +0 -0
  458. {topos_node-1.3.28 → topos_node-1.3.30}/topos/ingestion/parsers/browser_parser.py +0 -0
  459. {topos_node-1.3.28 → topos_node-1.3.30}/topos/ingestion/parsers/calendar_parser.py +0 -0
  460. {topos_node-1.3.28 → topos_node-1.3.30}/topos/ingestion/parsers/chatgpt_conversation_flattener.py +0 -0
  461. {topos_node-1.3.28 → topos_node-1.3.30}/topos/ingestion/parsers/chatgpt_parser.py +0 -0
  462. {topos_node-1.3.28 → topos_node-1.3.30}/topos/ingestion/parsers/demo_file_parsers.py +0 -0
  463. {topos_node-1.3.28 → topos_node-1.3.30}/topos/ingestion/parsers/documents_parser.py +0 -0
  464. {topos_node-1.3.28 → topos_node-1.3.30}/topos/ingestion/parsers/github_activity_parser.py +0 -0
  465. {topos_node-1.3.28 → topos_node-1.3.30}/topos/ingestion/parsers/google_calendar_parser.py +0 -0
  466. {topos_node-1.3.28 → topos_node-1.3.30}/topos/ingestion/parsers/grok_parser.py +0 -0
  467. {topos_node-1.3.28 → topos_node-1.3.30}/topos/ingestion/parsers/messenger_parser.py +0 -0
  468. {topos_node-1.3.28 → topos_node-1.3.30}/topos/ingestion/parsers/voxterm_parser.py +0 -0
  469. {topos_node-1.3.28 → topos_node-1.3.30}/topos/ingestion/progress.py +0 -0
  470. {topos_node-1.3.28 → topos_node-1.3.30}/topos/ingestion/reprocess.py +0 -0
  471. {topos_node-1.3.28 → topos_node-1.3.30}/topos/ingestion/sources/__init__.py +0 -0
  472. {topos_node-1.3.28 → topos_node-1.3.30}/topos/ingestion/sources/base.py +0 -0
  473. {topos_node-1.3.28 → topos_node-1.3.30}/topos/ingestion/sources/calendar.py +0 -0
  474. {topos_node-1.3.28 → topos_node-1.3.30}/topos/ingestion/sources/chatgpt.py +0 -0
  475. {topos_node-1.3.28 → topos_node-1.3.30}/topos/ingestion/sources/contact_importers.py +0 -0
  476. {topos_node-1.3.28 → topos_node-1.3.30}/topos/ingestion/sources/grok.py +0 -0
  477. {topos_node-1.3.28 → topos_node-1.3.30}/topos/ingestion/sources/imessage_reader.py +0 -0
  478. {topos_node-1.3.28 → topos_node-1.3.30}/topos/ingestion/sources/signal_export_parser.py +0 -0
  479. {topos_node-1.3.28 → topos_node-1.3.30}/topos/ingestion/sources/signal_reader.py +0 -0
  480. {topos_node-1.3.28 → topos_node-1.3.30}/topos/ingestion/state_machine.py +0 -0
  481. {topos_node-1.3.28 → topos_node-1.3.30}/topos/ingestion/triggers/__init__.py +0 -0
  482. {topos_node-1.3.28 → topos_node-1.3.30}/topos/ingestion/triggers/file_trigger.py +0 -0
  483. {topos_node-1.3.28 → topos_node-1.3.30}/topos/ingestion/triggers/sqlite_trigger.py +0 -0
  484. {topos_node-1.3.28 → topos_node-1.3.30}/topos/ingestion/usage_inbox_dedupe.py +0 -0
  485. {topos_node-1.3.28 → topos_node-1.3.30}/topos/ingestion/validation/__init__.py +0 -0
  486. {topos_node-1.3.28 → topos_node-1.3.30}/topos/ingestion/validation/base.py +0 -0
  487. {topos_node-1.3.28 → topos_node-1.3.30}/topos/ingestion/validation/schema_registry.py +0 -0
  488. {topos_node-1.3.28 → topos_node-1.3.30}/topos/ingestion/validation/schema_validator.py +0 -0
  489. {topos_node-1.3.28 → topos_node-1.3.30}/topos/lineage/__init__.py +0 -0
  490. {topos_node-1.3.28 → topos_node-1.3.30}/topos/lineage/provenance.py +0 -0
  491. {topos_node-1.3.28 → topos_node-1.3.30}/topos/lineage/tracker.py +0 -0
  492. {topos_node-1.3.28 → topos_node-1.3.30}/topos/llm_integrations_storage.py +0 -0
  493. {topos_node-1.3.28 → topos_node-1.3.30}/topos/mcp_stdio_proxy.py +0 -0
  494. {topos_node-1.3.28 → topos_node-1.3.30}/topos/observability/__init__.py +0 -0
  495. {topos_node-1.3.28 → topos_node-1.3.30}/topos/observability/alerts.py +0 -0
  496. {topos_node-1.3.28 → topos_node-1.3.30}/topos/observability/metrics.py +0 -0
  497. {topos_node-1.3.28 → topos_node-1.3.30}/topos/observability/tracing.py +0 -0
  498. {topos_node-1.3.28 → topos_node-1.3.30}/topos/openai_client.py +0 -0
  499. {topos_node-1.3.28 → topos_node-1.3.30}/topos/pipeline/__init__.py +0 -0
  500. {topos_node-1.3.28 → topos_node-1.3.30}/topos/pipeline/audit.py +0 -0
  501. {topos_node-1.3.28 → topos_node-1.3.30}/topos/pipeline/envelope.py +0 -0
  502. {topos_node-1.3.28 → topos_node-1.3.30}/topos/pipeline/job_runner.py +0 -0
  503. {topos_node-1.3.28 → topos_node-1.3.30}/topos/pipeline/job_store.py +0 -0
  504. {topos_node-1.3.28 → topos_node-1.3.30}/topos/pipeline/stages.py +0 -0
  505. {topos_node-1.3.28 → topos_node-1.3.30}/topos/pipeline/stub_enqueue.py +0 -0
  506. {topos_node-1.3.28 → topos_node-1.3.30}/topos/profiles.py +0 -0
  507. {topos_node-1.3.28 → topos_node-1.3.30}/topos/projections/__init__.py +0 -0
  508. {topos_node-1.3.28 → topos_node-1.3.30}/topos/projections/vector_index/__init__.py +0 -0
  509. {topos_node-1.3.28 → topos_node-1.3.30}/topos/projections/vector_index/base.py +0 -0
  510. {topos_node-1.3.28 → topos_node-1.3.30}/topos/projections/vector_index/builders.py +0 -0
  511. {topos_node-1.3.28 → topos_node-1.3.30}/topos/projections/vector_index/health_checks.py +0 -0
  512. {topos_node-1.3.28 → topos_node-1.3.30}/topos/protocol/__init__.py +0 -0
  513. {topos_node-1.3.28 → topos_node-1.3.30}/topos/protocol/query_field_contract.json +0 -0
  514. {topos_node-1.3.28 → topos_node-1.3.30}/topos/query/__init__.py +0 -0
  515. {topos_node-1.3.28 → topos_node-1.3.30}/topos/query/audit.py +0 -0
  516. {topos_node-1.3.28 → topos_node-1.3.30}/topos/query/cohort_resolvers.py +0 -0
  517. {topos_node-1.3.28 → topos_node-1.3.30}/topos/query/ddr.py +0 -0
  518. {topos_node-1.3.28 → topos_node-1.3.30}/topos/query/disclosure.py +0 -0
  519. {topos_node-1.3.28 → topos_node-1.3.30}/topos/query/entity_window.py +0 -0
  520. {topos_node-1.3.28 → topos_node-1.3.30}/topos/query/exclusion.py +0 -0
  521. {topos_node-1.3.28 → topos_node-1.3.30}/topos/query/facts_direct.py +0 -0
  522. {topos_node-1.3.28 → topos_node-1.3.30}/topos/query/fingerprint.py +0 -0
  523. {topos_node-1.3.28 → topos_node-1.3.30}/topos/query/grant_cache.py +0 -0
  524. {topos_node-1.3.28 → topos_node-1.3.30}/topos/query/inference.py +0 -0
  525. {topos_node-1.3.28 → topos_node-1.3.30}/topos/query/intent.py +0 -0
  526. {topos_node-1.3.28 → topos_node-1.3.30}/topos/query/manifest.py +0 -0
  527. {topos_node-1.3.28 → topos_node-1.3.30}/topos/query/manifest_validation.py +0 -0
  528. {topos_node-1.3.28 → topos_node-1.3.30}/topos/query/minimizer.py +0 -0
  529. {topos_node-1.3.28 → topos_node-1.3.30}/topos/query/negotiation.py +0 -0
  530. {topos_node-1.3.28 → topos_node-1.3.30}/topos/query/planner.py +0 -0
  531. {topos_node-1.3.28 → topos_node-1.3.30}/topos/query/runtime.py +0 -0
  532. {topos_node-1.3.28 → topos_node-1.3.30}/topos/query/scope_arbiter.py +0 -0
  533. {topos_node-1.3.28 → topos_node-1.3.30}/topos/query/scope_classifier.py +0 -0
  534. {topos_node-1.3.28 → topos_node-1.3.30}/topos/query/scope_head.py +0 -0
  535. {topos_node-1.3.28 → topos_node-1.3.30}/topos/query/scope_registry.json +0 -0
  536. {topos_node-1.3.28 → topos_node-1.3.30}/topos/query/scope_registry_loader.py +0 -0
  537. {topos_node-1.3.28 → topos_node-1.3.30}/topos/query/scope_shadow.py +0 -0
  538. {topos_node-1.3.28 → topos_node-1.3.30}/topos/query/session.py +0 -0
  539. {topos_node-1.3.28 → topos_node-1.3.30}/topos/query/session_utils.py +0 -0
  540. {topos_node-1.3.28 → topos_node-1.3.30}/topos/query/source_generation.py +0 -0
  541. {topos_node-1.3.28 → topos_node-1.3.30}/topos/query/truth_facts.py +0 -0
  542. {topos_node-1.3.28 → topos_node-1.3.30}/topos/query/truth_prompts.py +0 -0
  543. {topos_node-1.3.28 → topos_node-1.3.30}/topos/query/turn_classifier.py +0 -0
  544. {topos_node-1.3.28 → topos_node-1.3.30}/topos/query/types.py +0 -0
  545. {topos_node-1.3.28 → topos_node-1.3.30}/topos/query/verify.py +0 -0
  546. {topos_node-1.3.28 → topos_node-1.3.30}/topos/query/verify_modes.py +0 -0
  547. {topos_node-1.3.28 → topos_node-1.3.30}/topos/rate_limit.py +0 -0
  548. {topos_node-1.3.28 → topos_node-1.3.30}/topos/routines/__init__.py +0 -0
  549. {topos_node-1.3.28 → topos_node-1.3.30}/topos/routines/schema.py +0 -0
  550. {topos_node-1.3.28 → topos_node-1.3.30}/topos/routines/store.py +0 -0
  551. {topos_node-1.3.28 → topos_node-1.3.30}/topos/runtime_housekeeping.py +0 -0
  552. {topos_node-1.3.28 → topos_node-1.3.30}/topos/runtime_shutdown.py +0 -0
  553. {topos_node-1.3.28 → topos_node-1.3.30}/topos/runtime_update.py +0 -0
  554. {topos_node-1.3.28 → topos_node-1.3.30}/topos/sanitization/__init__.py +0 -0
  555. {topos_node-1.3.28 → topos_node-1.3.30}/topos/sanitization/nsfw_classifier.py +0 -0
  556. {topos_node-1.3.28 → topos_node-1.3.30}/topos/sanitization/ollama_transforms.py +0 -0
  557. {topos_node-1.3.28 → topos_node-1.3.30}/topos/sanitization/prewarm.py +0 -0
  558. {topos_node-1.3.28 → topos_node-1.3.30}/topos/sanitization/privacy_filter.py +0 -0
  559. {topos_node-1.3.28 → topos_node-1.3.30}/topos/scope_resolution.py +0 -0
  560. {topos_node-1.3.28 → topos_node-1.3.30}/topos/services/__init__.py +0 -0
  561. {topos_node-1.3.28 → topos_node-1.3.30}/topos/services/container.py +0 -0
  562. {topos_node-1.3.28 → topos_node-1.3.30}/topos/services/embeddings/__init__.py +0 -0
  563. {topos_node-1.3.28 → topos_node-1.3.30}/topos/services/embeddings/base.py +0 -0
  564. {topos_node-1.3.28 → topos_node-1.3.30}/topos/services/embeddings/local.py +0 -0
  565. {topos_node-1.3.28 → topos_node-1.3.30}/topos/services/embeddings/remote.py +0 -0
  566. {topos_node-1.3.28 → topos_node-1.3.30}/topos/services/interfaces.py +0 -0
  567. {topos_node-1.3.28 → topos_node-1.3.30}/topos/services/llm/__init__.py +0 -0
  568. {topos_node-1.3.28 → topos_node-1.3.30}/topos/services/llm/base.py +0 -0
  569. {topos_node-1.3.28 → topos_node-1.3.30}/topos/services/llm/openai.py +0 -0
  570. {topos_node-1.3.28 → topos_node-1.3.30}/topos/services/local.py +0 -0
  571. {topos_node-1.3.28 → topos_node-1.3.30}/topos/services/postgres.py +0 -0
  572. {topos_node-1.3.28 → topos_node-1.3.30}/topos/sources/__init__.py +0 -0
  573. {topos_node-1.3.28 → topos_node-1.3.30}/topos/sources/bundled_canonical_triples.py +0 -0
  574. {topos_node-1.3.28 → topos_node-1.3.30}/topos/sources/canonical_signal_defaults.py +0 -0
  575. {topos_node-1.3.28 → topos_node-1.3.30}/topos/sources/declared_field_map_spec.py +0 -0
  576. {topos_node-1.3.28 → topos_node-1.3.30}/topos/sources/definitions.py +0 -0
  577. {topos_node-1.3.28 → topos_node-1.3.30}/topos/sources/install_service.py +0 -0
  578. {topos_node-1.3.28 → topos_node-1.3.30}/topos/sources/registry.py +0 -0
  579. {topos_node-1.3.28 → topos_node-1.3.30}/topos/sources/runtime_install.py +0 -0
  580. {topos_node-1.3.28 → topos_node-1.3.30}/topos/sources/scrub_attribution.py +0 -0
  581. {topos_node-1.3.28 → topos_node-1.3.30}/topos/sources/scrub_service.py +0 -0
  582. {topos_node-1.3.28 → topos_node-1.3.30}/topos/startup_banner.py +0 -0
  583. {topos_node-1.3.28 → topos_node-1.3.30}/topos/storage/__init__.py +0 -0
  584. {topos_node-1.3.28 → topos_node-1.3.30}/topos/storage/adapters/__init__.py +0 -0
  585. {topos_node-1.3.28 → topos_node-1.3.30}/topos/storage/adapters/factory.py +0 -0
  586. {topos_node-1.3.28 → topos_node-1.3.30}/topos/storage/adapters/fakes.py +0 -0
  587. {topos_node-1.3.28 → topos_node-1.3.30}/topos/storage/adapters/postgres/stores.py +0 -0
  588. {topos_node-1.3.28 → topos_node-1.3.30}/topos/storage/adapters/protocols.py +0 -0
  589. {topos_node-1.3.28 → topos_node-1.3.30}/topos/storage/adapters/sqlite/__init__.py +0 -0
  590. {topos_node-1.3.28 → topos_node-1.3.30}/topos/storage/adapters/sqlite/vector_search.py +0 -0
  591. {topos_node-1.3.28 → topos_node-1.3.30}/topos/storage/canonical/__init__.py +0 -0
  592. {topos_node-1.3.28 → topos_node-1.3.30}/topos/storage/canonical/activity_tables.py +0 -0
  593. {topos_node-1.3.28 → topos_node-1.3.30}/topos/storage/canonical/ai_chat/__init__.py +0 -0
  594. {topos_node-1.3.28 → topos_node-1.3.30}/topos/storage/canonical/ai_chat/canonicalizer.py +0 -0
  595. {topos_node-1.3.28 → topos_node-1.3.30}/topos/storage/canonical/ai_chat/mapper.py +0 -0
  596. {topos_node-1.3.28 → topos_node-1.3.30}/topos/storage/canonical/ai_chat/model.py +0 -0
  597. {topos_node-1.3.28 → topos_node-1.3.30}/topos/storage/canonical/ai_chat/tables.py +0 -0
  598. {topos_node-1.3.28 → topos_node-1.3.30}/topos/storage/canonical/calendar_contacts_tables.py +0 -0
  599. {topos_node-1.3.28 → topos_node-1.3.30}/topos/storage/canonical/canonical_store.py +0 -0
  600. {topos_node-1.3.28 → topos_node-1.3.30}/topos/storage/canonical/conversations_tables.py +0 -0
  601. {topos_node-1.3.28 → topos_node-1.3.30}/topos/storage/canonical/journal_repair.py +0 -0
  602. {topos_node-1.3.28 → topos_node-1.3.30}/topos/storage/canonical/mapping_store.py +0 -0
  603. {topos_node-1.3.28 → topos_node-1.3.30}/topos/storage/canonical/postgres.py +0 -0
  604. {topos_node-1.3.28 → topos_node-1.3.30}/topos/storage/db/__init__.py +0 -0
  605. {topos_node-1.3.28 → topos_node-1.3.30}/topos/storage/db/client.py +0 -0
  606. {topos_node-1.3.28 → topos_node-1.3.30}/topos/storage/db/connection_tuning.py +0 -0
  607. {topos_node-1.3.28 → topos_node-1.3.30}/topos/storage/db/migrations/__init__.py +0 -0
  608. {topos_node-1.3.28 → topos_node-1.3.30}/topos/storage/db/migrations/activity_events_content_v1.py +0 -0
  609. {topos_node-1.3.28 → topos_node-1.3.30}/topos/storage/db/migrations/actor_role_v1.py +0 -0
  610. {topos_node-1.3.28 → topos_node-1.3.30}/topos/storage/db/migrations/affinity_pair_labels_v1.py +0 -0
  611. {topos_node-1.3.28 → topos_node-1.3.30}/topos/storage/db/migrations/attention_triage_v1.py +0 -0
  612. {topos_node-1.3.28 → topos_node-1.3.30}/topos/storage/db/migrations/attention_triage_v2.py +0 -0
  613. {topos_node-1.3.28 → topos_node-1.3.30}/topos/storage/db/migrations/backup.py +0 -0
  614. {topos_node-1.3.28 → topos_node-1.3.30}/topos/storage/db/migrations/calendar_events_scheduling_v1.py +0 -0
  615. {topos_node-1.3.28 → topos_node-1.3.30}/topos/storage/db/migrations/canonical_address_book_v1.py +0 -0
  616. {topos_node-1.3.28 → topos_node-1.3.30}/topos/storage/db/migrations/canonical_disclosure_v1.py +0 -0
  617. {topos_node-1.3.28 → topos_node-1.3.30}/topos/storage/db/migrations/canonical_nsfw_v1.py +0 -0
  618. {topos_node-1.3.28 → topos_node-1.3.30}/topos/storage/db/migrations/complexity_v1.py +0 -0
  619. {topos_node-1.3.28 → topos_node-1.3.30}/topos/storage/db/migrations/conversation_context_v1.py +0 -0
  620. {topos_node-1.3.28 → topos_node-1.3.30}/topos/storage/db/migrations/derivation_factory_v1.py +0 -0
  621. {topos_node-1.3.28 → topos_node-1.3.30}/topos/storage/db/migrations/derivation_ledger_v1.py +0 -0
  622. {topos_node-1.3.28 → topos_node-1.3.30}/topos/storage/db/migrations/derivation_provenance_v1.py +0 -0
  623. {topos_node-1.3.28 → topos_node-1.3.30}/topos/storage/db/migrations/documents_v1.py +0 -0
  624. {topos_node-1.3.28 → topos_node-1.3.30}/topos/storage/db/migrations/enrichment_record_progress_v1.py +0 -0
  625. {topos_node-1.3.28 → topos_node-1.3.30}/topos/storage/db/migrations/enrichment_spec_version_v1.py +0 -0
  626. {topos_node-1.3.28 → topos_node-1.3.30}/topos/storage/db/migrations/entity_affinity_v1.py +0 -0
  627. {topos_node-1.3.28 → topos_node-1.3.30}/topos/storage/db/migrations/entity_blackhole_v1.py +0 -0
  628. {topos_node-1.3.28 → topos_node-1.3.30}/topos/storage/db/migrations/entity_context_vectors_v1.py +0 -0
  629. {topos_node-1.3.28 → topos_node-1.3.30}/topos/storage/db/migrations/entity_context_vectors_v2.py +0 -0
  630. {topos_node-1.3.28 → topos_node-1.3.30}/topos/storage/db/migrations/entity_edges_validity_v1.py +0 -0
  631. {topos_node-1.3.28 → topos_node-1.3.30}/topos/storage/db/migrations/entity_mentions_authored_v1.py +0 -0
  632. {topos_node-1.3.28 → topos_node-1.3.30}/topos/storage/db/migrations/entity_review_candidate_bar_v1.py +0 -0
  633. {topos_node-1.3.28 → topos_node-1.3.30}/topos/storage/db/migrations/entity_review_dedup_v1.py +0 -0
  634. {topos_node-1.3.28 → topos_node-1.3.30}/topos/storage/db/migrations/entity_review_provenance_v1.py +0 -0
  635. {topos_node-1.3.28 → topos_node-1.3.30}/topos/storage/db/migrations/episodes_v1.py +0 -0
  636. {topos_node-1.3.28 → topos_node-1.3.30}/topos/storage/db/migrations/extraction_artifacts.py +0 -0
  637. {topos_node-1.3.28 → topos_node-1.3.30}/topos/storage/db/migrations/journal_entries_duration_v1.py +0 -0
  638. {topos_node-1.3.28 → topos_node-1.3.30}/topos/storage/db/migrations/journal_entries_ends_at_v1.py +0 -0
  639. {topos_node-1.3.28 → topos_node-1.3.30}/topos/storage/db/migrations/journal_entries_people_v1.py +0 -0
  640. {topos_node-1.3.28 → topos_node-1.3.30}/topos/storage/db/migrations/journal_entries_place_name_v1.py +0 -0
  641. {topos_node-1.3.28 → topos_node-1.3.30}/topos/storage/db/migrations/journal_entries_starts_at_v1.py +0 -0
  642. {topos_node-1.3.28 → topos_node-1.3.30}/topos/storage/db/migrations/journal_origin_dimension_v1.py +0 -0
  643. {topos_node-1.3.28 → topos_node-1.3.30}/topos/storage/db/migrations/message_emotions_role_backfill_v1.py +0 -0
  644. {topos_node-1.3.28 → topos_node-1.3.30}/topos/storage/db/migrations/message_emotions_role_v1.py +0 -0
  645. {topos_node-1.3.28 → topos_node-1.3.30}/topos/storage/db/migrations/pack_registry_v1.py +0 -0
  646. {topos_node-1.3.28 → topos_node-1.3.30}/topos/storage/db/migrations/pipeline_jobs_v1.py +0 -0
  647. {topos_node-1.3.28 → topos_node-1.3.30}/topos/storage/db/migrations/query_artifacts_duration_ms_v1.py +0 -0
  648. {topos_node-1.3.28 → topos_node-1.3.30}/topos/storage/db/migrations/remediation_person_model.py +0 -0
  649. {topos_node-1.3.28 → topos_node-1.3.30}/topos/storage/db/migrations/retire_url_classification_v1.py +0 -0
  650. {topos_node-1.3.28 → topos_node-1.3.30}/topos/storage/db/migrations/scope_source_generation.py +0 -0
  651. {topos_node-1.3.28 → topos_node-1.3.30}/topos/storage/db/migrations/signal_dimension_backfill_v1.py +0 -0
  652. {topos_node-1.3.28 → topos_node-1.3.30}/topos/storage/db/migrations/signal_dimension_harness.py +0 -0
  653. {topos_node-1.3.28 → topos_node-1.3.30}/topos/storage/db/migrations/signal_objects.py +0 -0
  654. {topos_node-1.3.28 → topos_node-1.3.30}/topos/storage/db/migrations/signal_objects_period_v1.py +0 -0
  655. {topos_node-1.3.28 → topos_node-1.3.30}/topos/storage/db/migrations/signal_objects_updated_by_v1.py +0 -0
  656. {topos_node-1.3.28 → topos_node-1.3.30}/topos/storage/db/migrations/signal_summaries_drop_v1.py +0 -0
  657. {topos_node-1.3.28 → topos_node-1.3.30}/topos/storage/db/migrations/stage9_column_renames.py +0 -0
  658. {topos_node-1.3.28 → topos_node-1.3.30}/topos/storage/db/migrations/vector_storage_v1.py +0 -0
  659. {topos_node-1.3.28 → topos_node-1.3.30}/topos/storage/db/migrations/vector_storage_v2.py +0 -0
  660. {topos_node-1.3.28 → topos_node-1.3.30}/topos/storage/db/migrations/vector_storage_v3.py +0 -0
  661. {topos_node-1.3.28 → topos_node-1.3.30}/topos/storage/db/migrations/vector_storage_v4.py +0 -0
  662. {topos_node-1.3.28 → topos_node-1.3.30}/topos/storage/db/migrations/wiki_clusters_v2.py +0 -0
  663. {topos_node-1.3.28 → topos_node-1.3.30}/topos/storage/db/migrations/wiki_entities_v1.py +0 -0
  664. {topos_node-1.3.28 → topos_node-1.3.30}/topos/storage/db/migrations/wiki_entity_review_v2.py +0 -0
  665. {topos_node-1.3.28 → topos_node-1.3.30}/topos/storage/db/migrations/wiki_facts_v1.py +0 -0
  666. {topos_node-1.3.28 → topos_node-1.3.30}/topos/storage/db/migrations/wiki_lifecycle_v1.py +0 -0
  667. {topos_node-1.3.28 → topos_node-1.3.30}/topos/storage/db/migrations/wiki_mvp_phase0.py +0 -0
  668. {topos_node-1.3.28 → topos_node-1.3.30}/topos/storage/db/migrations/wiki_mvp_phase1.py +0 -0
  669. {topos_node-1.3.28 → topos_node-1.3.30}/topos/storage/db/migrations/wiki_mvp_phase4_messages_cutover.py +0 -0
  670. {topos_node-1.3.28 → topos_node-1.3.30}/topos/storage/db/migrations/wiki_mvp_phase5_topic_clusters.py +0 -0
  671. {topos_node-1.3.28 → topos_node-1.3.30}/topos/storage/db/migrations/wiki_mvp_phase6_dimension_briefs.py +0 -0
  672. {topos_node-1.3.28 → topos_node-1.3.30}/topos/storage/db/migrations/wiki_mvp_query_quality.py +0 -0
  673. {topos_node-1.3.28 → topos_node-1.3.30}/topos/storage/db/migrations/wiki_mvp_topic_clusters_coordination.py +0 -0
  674. {topos_node-1.3.28 → topos_node-1.3.30}/topos/storage/db/migrations/wiki_stats_v1.py +0 -0
  675. {topos_node-1.3.28 → topos_node-1.3.30}/topos/storage/db/migrations/wiki_timeline_v1.py +0 -0
  676. {topos_node-1.3.28 → topos_node-1.3.30}/topos/storage/db/paths.py +0 -0
  677. {topos_node-1.3.28 → topos_node-1.3.30}/topos/storage/db/postgres.py +0 -0
  678. {topos_node-1.3.28 → topos_node-1.3.30}/topos/storage/db/schema.py +0 -0
  679. {topos_node-1.3.28 → topos_node-1.3.30}/topos/storage/db/schema_probe.py +0 -0
  680. {topos_node-1.3.28 → topos_node-1.3.30}/topos/storage/db/storage_breakdown.py +0 -0
  681. {topos_node-1.3.28 → topos_node-1.3.30}/topos/storage/db/write_gate.py +0 -0
  682. {topos_node-1.3.28 → topos_node-1.3.30}/topos/storage/enrichment/__init__.py +0 -0
  683. {topos_node-1.3.28 → topos_node-1.3.30}/topos/storage/enrichment/canonical_enrichment_store.py +0 -0
  684. {topos_node-1.3.28 → topos_node-1.3.30}/topos/storage/enrichment/raw_enrichment_store.py +0 -0
  685. {topos_node-1.3.28 → topos_node-1.3.30}/topos/storage/normalized/__init__.py +0 -0
  686. {topos_node-1.3.28 → topos_node-1.3.30}/topos/storage/normalized/normalized_store.py +0 -0
  687. {topos_node-1.3.28 → topos_node-1.3.30}/topos/storage/oplog/__init__.py +0 -0
  688. {topos_node-1.3.28 → topos_node-1.3.30}/topos/storage/oplog/decision.py +0 -0
  689. {topos_node-1.3.28 → topos_node-1.3.30}/topos/storage/oplog/oplog_store.py +0 -0
  690. {topos_node-1.3.28 → topos_node-1.3.30}/topos/storage/oplog/postgres.py +0 -0
  691. {topos_node-1.3.28 → topos_node-1.3.30}/topos/storage/person/identity_resolver.py +0 -0
  692. {topos_node-1.3.28 → topos_node-1.3.30}/topos/storage/projections/__init__.py +0 -0
  693. {topos_node-1.3.28 → topos_node-1.3.30}/topos/storage/projections/index_ops_store.py +0 -0
  694. {topos_node-1.3.28 → topos_node-1.3.30}/topos/storage/projections/vector_index_store.py +0 -0
  695. {topos_node-1.3.28 → topos_node-1.3.30}/topos/storage/raw/__init__.py +0 -0
  696. {topos_node-1.3.28 → topos_node-1.3.30}/topos/storage/raw/browser_flat_tables.py +0 -0
  697. {topos_node-1.3.28 → topos_node-1.3.30}/topos/storage/raw/file_store.py +0 -0
  698. {topos_node-1.3.28 → topos_node-1.3.30}/topos/storage/raw/raw_store.py +0 -0
  699. {topos_node-1.3.28 → topos_node-1.3.30}/topos/storage/raw/raw_tables_manager.py +0 -0
  700. {topos_node-1.3.28 → topos_node-1.3.30}/topos/storage/raw/sqlite_raw_store.py +0 -0
  701. {topos_node-1.3.28 → topos_node-1.3.30}/topos/storage/security/encryption.py +0 -0
  702. {topos_node-1.3.28 → topos_node-1.3.30}/topos/storage/signal_identity.py +0 -0
  703. {topos_node-1.3.28 → topos_node-1.3.30}/topos/storage/source_settings.py +0 -0
  704. {topos_node-1.3.28 → topos_node-1.3.30}/topos/storage/user_identity.py +0 -0
  705. {topos_node-1.3.28 → topos_node-1.3.30}/topos/sync/__init__.py +0 -0
  706. {topos_node-1.3.28 → topos_node-1.3.30}/topos/sync/client.py +0 -0
  707. {topos_node-1.3.28 → topos_node-1.3.30}/topos/sync_handlers.py +0 -0
  708. {topos_node-1.3.28 → topos_node-1.3.30}/topos/testing/__init__.py +0 -0
  709. {topos_node-1.3.28 → topos_node-1.3.30}/topos/testing/lifespan.py +0 -0
  710. {topos_node-1.3.28 → topos_node-1.3.30}/topos/uma_contact_enrichment.py +0 -0
  711. {topos_node-1.3.28 → topos_node-1.3.30}/topos/uma_filters.py +0 -0
  712. {topos_node-1.3.28 → topos_node-1.3.30}/topos/uma_resource_id.py +0 -0
  713. {topos_node-1.3.28 → topos_node-1.3.30}/topos/uma_rpt.py +0 -0
  714. {topos_node-1.3.28 → topos_node-1.3.30}/topos/upgrades/__init__.py +0 -0
  715. {topos_node-1.3.28 → topos_node-1.3.30}/topos/upgrades/runner.py +0 -0
  716. {topos_node-1.3.28 → topos_node-1.3.30}/topos/utils/base_object.py +0 -0
  717. {topos_node-1.3.28 → topos_node-1.3.30}/topos/websocket_client.py +0 -0
  718. {topos_node-1.3.28 → topos_node-1.3.30}/topos_node.egg-info/dependency_links.txt +0 -0
  719. {topos_node-1.3.28 → topos_node-1.3.30}/topos_node.egg-info/entry_points.txt +0 -0
  720. {topos_node-1.3.28 → topos_node-1.3.30}/topos_node.egg-info/requires.txt +0 -0
  721. {topos_node-1.3.28 → topos_node-1.3.30}/topos_node.egg-info/top_level.txt +0 -0
@@ -1,6 +1,6 @@
1
1
  Metadata-Version: 2.4
2
2
  Name: topos-node
3
- Version: 1.3.28
3
+ Version: 1.3.30
4
4
  Summary: Topos personal AI engine (FastAPI): local data, sync, control plane WebSocket client
5
5
  License-Expression: Apache-2.0
6
6
  Project-URL: Homepage, https://topos.dialogues.ai
@@ -4,7 +4,7 @@ build-backend = "setuptools.build_meta"
4
4
 
5
5
  [project]
6
6
  name = "topos-node"
7
- version = "1.3.28"
7
+ version = "1.3.30"
8
8
  description = "Topos personal AI engine (FastAPI): local data, sync, control plane WebSocket client"
9
9
  readme = "README.md"
10
10
  license = "Apache-2.0"
@@ -1,6 +1,6 @@
1
1
  """Topos Control Plane Version Information."""
2
2
 
3
- __version__ = "1.3.28"
4
- __version_info__ = (1, 3, 28)
3
+ __version__ = "1.3.30"
4
+ __version_info__ = (1, 3, 30)
5
5
 
6
6
  __all__ = ["__version__", "__version_info__"]
@@ -0,0 +1,52 @@
1
+ """Read/update the owner-selected community-naming model (engine_config).
2
+
3
+ PLAN_COMMUNITY_NAMING S4: surfaced under Settings → Node functions. Default is
4
+ the local extraction model — naming stays on-device unless the owner points it
5
+ elsewhere. Empty PUT clears the override.
6
+ """
7
+
8
+ from __future__ import annotations
9
+
10
+ import logging
11
+ from typing import Any
12
+
13
+ from fastapi import APIRouter, Body, Depends, HTTPException
14
+
15
+ from ..auth import require_api_key
16
+ from ..core.state import get_db_connection, set_engine_config_value
17
+ from ..features.entities.community_naming import (
18
+ ENGINE_CONFIG_KEY_NAMING_MODEL,
19
+ resolve_naming_model,
20
+ )
21
+
22
+ logger = logging.getLogger("topos.api.community_naming_config")
23
+
24
+ router = APIRouter(tags=["community-naming"])
25
+
26
+
27
+ def _payload(conn) -> dict[str, Any]:
28
+ from ..core.state import get_engine_config_value
29
+
30
+ override = get_engine_config_value(conn, ENGINE_CONFIG_KEY_NAMING_MODEL)
31
+ return {
32
+ "model": resolve_naming_model(conn),
33
+ "override": str(override).strip() if override else None,
34
+ }
35
+
36
+
37
+ @router.get("/v1/community-naming-config", dependencies=[Depends(require_api_key)])
38
+ async def get_community_naming_config() -> dict[str, Any]:
39
+ conn = get_db_connection()
40
+ if not conn:
41
+ raise HTTPException(status_code=503, detail="Database not available")
42
+ return {"status": "ok", **_payload(conn)}
43
+
44
+
45
+ @router.put("/v1/community-naming-config", dependencies=[Depends(require_api_key)])
46
+ async def put_community_naming_config(body: dict[str, Any] = Body(default=None)) -> dict[str, Any]:
47
+ conn = get_db_connection()
48
+ if not conn:
49
+ raise HTTPException(status_code=503, detail="Database not available")
50
+ model = str((body or {}).get("model") or "").strip()
51
+ set_engine_config_value(conn, ENGINE_CONFIG_KEY_NAMING_MODEL, model or None)
52
+ return {"status": "ok", **_payload(conn)}
@@ -1103,3 +1103,106 @@ async def post_pack_offer_resolution(
1103
1103
  if not out:
1104
1104
  raise HTTPException(status_code=404, detail=f"unknown offer {offer_id}")
1105
1105
  return out
1106
+
1107
+
1108
+ @router.post("/derivation/packs/{pack_id}/backfill")
1109
+ async def post_pack_backfill(
1110
+ pack_id: str,
1111
+ limit: int = Body(200, embed=True, ge=1, le=1000),
1112
+ _api_key: str = Depends(require_api_key),
1113
+ ):
1114
+ """Bounded owner-initiated history backfill (lens catalog control)."""
1115
+ import asyncio as _asyncio
1116
+
1117
+ from ..features.derivation.surfaces import run_pack_backfill
1118
+
1119
+ try:
1120
+ stats = await _asyncio.to_thread(run_pack_backfill, _entities_conn(), pack_id, limit)
1121
+ except ValueError as exc:
1122
+ raise HTTPException(status_code=400, detail=str(exc)) from exc
1123
+ return {"pack_id": pack_id, **stats}
1124
+
1125
+
1126
+ @router.put("/entities/communities/{community_id}/name")
1127
+ async def put_community_name_route(
1128
+ community_id: int,
1129
+ name: str = Body(..., embed=True),
1130
+ _api_key: str = Depends(require_api_key),
1131
+ ):
1132
+ """Owner rename for a graph community (stable-naming S3)."""
1133
+ from ..features.entities.community_names import core_fingerprint, rename_community
1134
+ from ..features.entities.community_naming import valid_label
1135
+
1136
+ if not valid_label(name):
1137
+ raise HTTPException(status_code=400, detail="a short name (2-4 words, letters) required")
1138
+ conn = _entities_conn()
1139
+ rows = conn.execute(
1140
+ "SELECT entity_id, json_extract(metadata_json,'$.centrality.eigen')"
1141
+ " FROM entities WHERE json_extract(metadata_json,'$.community_id')=?",
1142
+ (community_id,),
1143
+ ).fetchall()
1144
+ if not rows:
1145
+ raise HTTPException(status_code=404, detail=f"unknown community {community_id}")
1146
+ ranked = [x[0] for x in sorted(rows, key=lambda x: -(x[1] or 0.0))]
1147
+ weights = {x[0]: float(x[1] or 0.0) for x in rows}
1148
+ from ..storage.db.write_gate import commit_connection, with_db_write
1149
+ with with_db_write():
1150
+ rename_community(conn, core_fingerprint(ranked, weights), name)
1151
+ conn.execute(
1152
+ "UPDATE entities SET metadata_json=json_patch(COALESCE(metadata_json,'{}'),"
1153
+ " json_object('community_label', ?))"
1154
+ " WHERE json_extract(metadata_json,'$.community_id')=?",
1155
+ (name, community_id),
1156
+ )
1157
+ commit_connection(conn)
1158
+ return {"community_id": community_id, "name": name, "members": len(rows)}
1159
+
1160
+
1161
+ @router.get("/derivation/schema")
1162
+ async def get_derivation_schema(_api_key: str = Depends(require_api_key)):
1163
+ """Per-predicate field schemas for the Fact Editor (W4.6)."""
1164
+ from ..features.derivation.surfaces import predicate_schemas
1165
+
1166
+ return {"predicates": predicate_schemas(_entities_conn())}
1167
+
1168
+
1169
+ @router.post("/facts/conflicts/promote")
1170
+ async def post_conflict_promotion(
1171
+ conflict_id: str = Body(...),
1172
+ subject_entity_id: str = Body(""),
1173
+ new_person_name: str = Body(""),
1174
+ to_owner: bool = Body(False),
1175
+ value: Any = Body(None),
1176
+ _api_key: str = Depends(require_api_key),
1177
+ ):
1178
+ """Edit & add a quarantined extraction: the owner supplies the identity the
1179
+ machine refused to guess; ledgered as gold (W4.6)."""
1180
+ from ..features.derivation.surfaces import promote_conflict
1181
+
1182
+ try:
1183
+ return promote_conflict(_entities_conn(), conflict_id,
1184
+ subject_entity_id=subject_entity_id,
1185
+ new_person_name=new_person_name,
1186
+ value=value, to_owner=to_owner)
1187
+ except ValueError as exc:
1188
+ raise HTTPException(status_code=400, detail=str(exc)) from exc
1189
+
1190
+
1191
+ @router.post("/facts/{object_id}/revise")
1192
+ async def post_fact_revision(
1193
+ object_id: str,
1194
+ value: Any = Body(None),
1195
+ subject_entity_id: str = Body(""),
1196
+ evidence_date: str = Body(""),
1197
+ asserted_by: str = Body(""),
1198
+ _api_key: str = Depends(require_api_key),
1199
+ ):
1200
+ """Owner revision of a live pack fact: field/subject/date, never its kind (W4.6)."""
1201
+ from ..features.derivation.surfaces import revise_fact
1202
+
1203
+ try:
1204
+ return revise_fact(_entities_conn(), object_id, value=value,
1205
+ subject_entity_id=subject_entity_id,
1206
+ evidence_date=evidence_date, asserted_by=asserted_by)
1207
+ except ValueError as exc:
1208
+ raise HTTPException(status_code=400, detail=str(exc)) from exc
@@ -42,6 +42,7 @@ from .api import (
42
42
  data_explorer_table_prefs as data_explorer_table_prefs_routes,
43
43
  sanitization_ollama_config as sanitization_ollama_config_routes,
44
44
  facts_llm_config as facts_llm_config_routes,
45
+ community_naming_config as community_naming_config_routes,
45
46
  signal_extraction_config as signal_extraction_config_routes,
46
47
  filter_lab as filter_lab_routes,
47
48
  enrichment_lab as enrichment_lab_routes,
@@ -144,6 +145,7 @@ app.include_router(data_explorer_table_prefs_routes.router)
144
145
  app.include_router(user_identity_routes.router)
145
146
  app.include_router(sanitization_ollama_config_routes.router)
146
147
  app.include_router(facts_llm_config_routes.router)
148
+ app.include_router(community_naming_config_routes.router)
147
149
  app.include_router(signal_extraction_config_routes.router)
148
150
  app.include_router(filter_lab_routes.router)
149
151
  app.include_router(enrichment_lab_routes.router)
@@ -271,7 +271,12 @@ def _as_binding(raw: Any) -> Optional[Dict[str, str]]:
271
271
  def _local_model_present(binding: Mapping[str, str], installed_local_models: Optional[Any]) -> bool:
272
272
  if installed_local_models is None:
273
273
  return True
274
- if str(binding.get("provider") or "").strip().lower() not in LOCAL_PROVIDERS:
274
+ provider = str(binding.get("provider") or "").strip().lower()
275
+ # Horos is local but not an Ollama tag; `default` must not look like a
276
+ # missing download. Mirrors control_plane.model_pack_resolution.
277
+ if provider == SCOPE_HEAD_PROVIDER:
278
+ return True
279
+ if provider not in LOCAL_PROVIDERS:
275
280
  return True
276
281
  installed = {str(name or "").strip().lower() for name in installed_local_models}
277
282
  wanted = str(binding.get("model") or "").strip().lower()
@@ -97,3 +97,80 @@ async def handle_put_pack_offer(message):
97
97
  return {"id": req_id, "status": "error", "error": str(exc)}
98
98
  except Exception as exc: # noqa: BLE001
99
99
  return {"id": req_id, "status": "error", "error": str(exc)}
100
+
101
+
102
+ @handles("run_pack_backfill")
103
+ async def handle_run_pack_backfill(message):
104
+ """Owner-initiated bounded history backfill for one enabled pack (W-B #4).
105
+ Runs in a worker thread; bounded by `limit` hit-records per call."""
106
+ import asyncio as _asyncio
107
+ req_id = message.get("id")
108
+ conn = hub.get_db_connection()
109
+ if not conn:
110
+ return {"id": req_id, "status": "error", "error": "Database not available"}
111
+ payload = message.get("payload") or {}
112
+ pack_id = str(payload.get("pack_id") or "").strip()
113
+ limit = min(int(payload.get("limit") or 200), 1000)
114
+ try:
115
+ from ...features.derivation.surfaces import run_pack_backfill
116
+ stats = await _asyncio.to_thread(run_pack_backfill, conn, pack_id, limit)
117
+ return {"id": req_id, "status": "ok", "payload": {"status": "ok", "pack_id": pack_id, **stats}}
118
+ except ValueError as exc:
119
+ return {"id": req_id, "status": "error", "error": str(exc)}
120
+ except Exception as exc: # noqa: BLE001
121
+ return {"id": req_id, "status": "error", "error": str(exc)}
122
+
123
+
124
+ @handles("get_derivation_schema")
125
+ async def handle_get_derivation_schema(message):
126
+ req_id = message.get("id")
127
+ conn = hub.get_db_connection()
128
+ if not conn:
129
+ return {"id": req_id, "status": "error", "error": "Database not available"}
130
+ try:
131
+ from ...features.derivation.surfaces import predicate_schemas
132
+ return {"id": req_id, "status": "ok",
133
+ "payload": {"status": "ok", "predicates": predicate_schemas(conn)}}
134
+ except Exception as exc: # noqa: BLE001
135
+ return {"id": req_id, "status": "error", "error": str(exc)}
136
+
137
+
138
+ @handles("promote_fact_conflict")
139
+ async def handle_promote_fact_conflict(message):
140
+ req_id = message.get("id")
141
+ conn = hub.get_db_connection()
142
+ if not conn:
143
+ return {"id": req_id, "status": "error", "error": "Database not available"}
144
+ p = message.get("payload") or {}
145
+ try:
146
+ from ...features.derivation.surfaces import promote_conflict
147
+ out = promote_conflict(conn, str(p.get("conflict_id") or ""),
148
+ subject_entity_id=str(p.get("subject_entity_id") or ""),
149
+ new_person_name=str(p.get("new_person_name") or ""),
150
+ value=p.get("value"), to_owner=bool(p.get("to_owner")))
151
+ return {"id": req_id, "status": "ok", "payload": {"status": "ok", **out}}
152
+ except ValueError as exc:
153
+ return {"id": req_id, "status": "error", "error": str(exc)}
154
+ except Exception as exc: # noqa: BLE001
155
+ return {"id": req_id, "status": "error", "error": str(exc)}
156
+
157
+
158
+ @handles("revise_pack_fact")
159
+ async def handle_revise_pack_fact(message):
160
+ req_id = message.get("id")
161
+ conn = hub.get_db_connection()
162
+ if not conn:
163
+ return {"id": req_id, "status": "error", "error": "Database not available"}
164
+ p = message.get("payload") or {}
165
+ try:
166
+ from ...features.derivation.surfaces import revise_fact
167
+ out = revise_fact(conn, str(p.get("object_id") or ""),
168
+ value=p.get("value"),
169
+ subject_entity_id=str(p.get("subject_entity_id") or ""),
170
+ evidence_date=str(p.get("evidence_date") or ""),
171
+ asserted_by=str(p.get("asserted_by") or ""))
172
+ return {"id": req_id, "status": "ok", "payload": {"status": "ok", **out}}
173
+ except ValueError as exc:
174
+ return {"id": req_id, "status": "error", "error": str(exc)}
175
+ except Exception as exc: # noqa: BLE001
176
+ return {"id": req_id, "status": "error", "error": str(exc)}
@@ -1192,3 +1192,49 @@ async def handle_signal_retire_intent(message: Dict[str, Any]) -> Optional[Dict[
1192
1192
  return {"id": req_id, "status": "ok", "payload": {"intents": active_intents(conn)}}
1193
1193
  except Exception as exc: # noqa: BLE001
1194
1194
  return {"id": req_id, "status": "error", "error": str(exc)}
1195
+
1196
+
1197
+ @handles("put_community_name")
1198
+ async def handle_put_community_name(message: Dict[str, Any]) -> Optional[Dict[str, Any]]:
1199
+ """Owner rename for a graph community (PLAN_COMMUNITY_NAMING S3): retires
1200
+ any derived name for the community's core and records the owner's, which
1201
+ wins ties forever after. Stamps the label onto members immediately."""
1202
+ req_id = message.get("id")
1203
+ if not req_id:
1204
+ return None
1205
+ payload = message.get("payload") or {}
1206
+ community_id = payload.get("community_id")
1207
+ new_name = str(payload.get("name") or "").strip()
1208
+ try:
1209
+ from ...features.entities.community_names import core_fingerprint, rename_community
1210
+ from ...features.entities.community_naming import valid_label
1211
+
1212
+ if not isinstance(community_id, int) or not valid_label(new_name):
1213
+ return {"id": req_id, "status": "error",
1214
+ "error": "community_id (int) and a short name (2-4 words, letters) required"}
1215
+ conn = hub.get_db_connection()
1216
+ rows = conn.execute(
1217
+ "SELECT entity_id, json_extract(metadata_json,'$.centrality.eigen')"
1218
+ " FROM entities WHERE json_extract(metadata_json,'$.community_id')=?",
1219
+ (community_id,),
1220
+ ).fetchall()
1221
+ if not rows:
1222
+ return {"id": req_id, "status": "error", "error": f"unknown community {community_id}"}
1223
+ ranked = [r[0] for r in sorted(rows, key=lambda r: -(r[1] or 0.0))]
1224
+ weights = {r[0]: float(r[1] or 0.0) for r in rows}
1225
+ fp = core_fingerprint(ranked, weights)
1226
+ from ...storage.db.write_gate import commit_connection, with_db_write
1227
+ with with_db_write():
1228
+ rename_community(conn, fp, new_name)
1229
+ conn.execute(
1230
+ "UPDATE entities SET metadata_json=json_patch(COALESCE(metadata_json,'{}'),"
1231
+ " json_object('community_label', ?))"
1232
+ " WHERE json_extract(metadata_json,'$.community_id')=?",
1233
+ (new_name, community_id),
1234
+ )
1235
+ commit_connection(conn)
1236
+ return {"id": req_id, "status": "ok",
1237
+ "payload": {"status": "ok", "community_id": community_id, "name": new_name,
1238
+ "members": len(rows)}}
1239
+ except Exception as exc: # noqa: BLE001
1240
+ return {"id": req_id, "status": "error", "error": str(exc)}
@@ -161,6 +161,8 @@ def run_derivation_batch(
161
161
  temperature=0.0, num_ctx=8192, timeout=180)
162
162
  return str(out.get("text") or "") if isinstance(out, dict) else str(out or "")
163
163
 
164
+ from ....features.derivation.router import router_mode
165
+ _router_hybrid = router_mode() == "hybrid"
164
166
  verify_mode = _verify_mode()
165
167
  if verify_mode == "required" and packs:
166
168
  try:
@@ -176,19 +178,42 @@ def run_derivation_batch(
176
178
  writer = DerivationWriter(conn, model=model)
177
179
  done = {r[0] for r in conn.execute("SELECT key FROM derivation_progress")}
178
180
 
181
+ HARM_ROLES = {"partner", "spouse", "child", "sibling", "ex_partner"}
182
+ HARM_EVENTS = {"loss", "conflict", "reconnected", "ended", "estranged"}
183
+
184
+ def _is_high_harm(a):
185
+ v = a.get("value") if isinstance(a.get("value"), dict) else {}
186
+ if a.get("predicate") == "rel.relationship" and str(v.get("role")) in HARM_ROLES:
187
+ return True
188
+ if a.get("predicate") == "rel.relationship_event" and str(v.get("event")) in HARM_EVENTS:
189
+ return True
190
+ return False
191
+
179
192
  def judge(pack, rec, a, stage):
180
- """Verify one assertion; ledger it; return the annotated assertion."""
193
+ """Verify one assertion; high-harm predicate classes get 3-vote majority
194
+ (measured 2026-08-26: single quantized-verifier votes are variance-exposed
195
+ exactly where errors hurt most). Everything else keeps one vote."""
181
196
  if verify_mode == "off":
182
197
  a = dict(a); a["verifier_status"] = "skipped"
183
- else:
198
+ return a
199
+ votes_needed = 3 if _is_high_harm(a) else 1
200
+ accepts = 0
201
+ last_verdict = None
202
+ for _ in range(votes_needed):
184
203
  try:
185
204
  verdict = parse_verdict(llm(vmodel, build_verify_prompt(
186
205
  rec["text"], rec["role"], rec["date"],
187
206
  a["predicate"], a["value"], a.get("about", "owner")), n=250))
188
207
  except Exception: # noqa: BLE001
189
208
  verdict = None
190
- a = apply_verdict(a, verdict)
191
- return a
209
+ last_verdict = verdict or last_verdict
210
+ if verdict and verdict["supported"] and verdict["fields_ok"]:
211
+ accepts += 1
212
+ if votes_needed > 1 and accepts < 2:
213
+ a = dict(a); a["verifier_status"] = "rejected"
214
+ a["verifier_reason"] = f"majority {accepts}/{votes_needed} against"
215
+ return a
216
+ return apply_verdict(a, last_verdict)
192
217
 
193
218
  written = 0
194
219
  for row in rows:
@@ -198,8 +223,15 @@ def run_derivation_batch(
198
223
  rec = _row_to_record(row)
199
224
  if rec is None:
200
225
  continue
226
+ _rec_vec = None
227
+ if _router_hybrid:
228
+ from ....features.derivation.router import embed_record
229
+ _rec_vec = embed_record(rec["text"])
201
230
  for pid, pack in all_packs.items():
202
231
  hit = rec["role"] in pack.allowed_roles() and filters[pid].passes(rec["text"])
232
+ if not hit and _router_hybrid and rec["role"] in pack.allowed_roles():
233
+ from ....features.derivation.router import semantic_passes
234
+ hit = semantic_passes(pack, _rec_vec)
203
235
  if hit:
204
236
  _bump_yield(conn, pid, prefilter_hits=1)
205
237
  if pid not in packs:
@@ -247,6 +279,9 @@ def run_derivation_batch(
247
279
  conn.execute("INSERT OR REPLACE INTO derivation_progress (key) VALUES (?)", (key,))
248
280
  conn.commit()
249
281
 
282
+ _drip_catchup(conn, packs=packs, filters=filters, llm=llm, judge=judge,
283
+ writer=writer, owner=owner, done=done, st=st, cancel=cancel)
284
+
250
285
  _self_gate(conn, all_packs=all_packs, enabled=set(packs), filters=filters,
251
286
  llm=llm, judge=judge, model=model, vmodel=vmodel, st=st,
252
287
  cancel=cancel)
@@ -259,6 +294,94 @@ def run_derivation_batch(
259
294
  return written
260
295
 
261
296
 
297
+ #: history records drip-processed per batch — the dark delta self-heals without
298
+ #: a scheduler; a fresh enablement's history closes over days, or immediately
299
+ #: via the owner's backfill control.
300
+ CATCHUP_PER_BATCH = 25
301
+
302
+
303
+ def _iter_history(conn, limit=2000):
304
+ import sqlite3 as _sqlite3
305
+ def _rows(sql):
306
+ try:
307
+ return conn.execute(sql).fetchall()
308
+ except _sqlite3.OperationalError:
309
+ return []
310
+ out = []
311
+ for tbl, rid, text, at, role in _rows(
312
+ f"SELECT 'journal_entries', entry_id, content, entry_at, 'authored'"
313
+ f" FROM journal_entries WHERE content IS NOT NULL AND LENGTH(content)>15"
314
+ f" ORDER BY entry_at DESC LIMIT {int(limit)}"):
315
+ out.append({"table": tbl, "record_id": rid, "text": (text or "")[:6000],
316
+ "date": str(at or "")[:10], "role": role or "authored", "source_id": ""})
317
+ for tbl, rid, text, at, role in _rows(
318
+ f"SELECT 'conversation_messages', message_id, content, event_at, actor_role"
319
+ f" FROM conversation_messages WHERE content IS NOT NULL AND LENGTH(content)>15"
320
+ f" ORDER BY event_at DESC LIMIT {int(limit)}"):
321
+ out.append({"table": tbl, "record_id": rid, "text": (text or "")[:6000],
322
+ "date": str(at or "")[:10], "role": role or "observed", "source_id": ""})
323
+ return out
324
+
325
+
326
+ def _drip_catchup(conn, *, packs, filters, llm, judge, writer, owner, done, st, cancel):
327
+ """Process up to CATCHUP_PER_BATCH unprocessed HISTORY (record, pack) pairs
328
+ per batch. Newest-first: recent history answers queries soonest."""
329
+ if not packs:
330
+ return
331
+ from ....features.derivation.template import build_prompt, parse_output
332
+ from ....features.facts.llm_extract import _resolved_extraction_model
333
+ from ....config.settings import settings as _settings
334
+ model = _resolved_extraction_model(_settings, conn)
335
+ budget = CATCHUP_PER_BATCH
336
+ for rec in _iter_history(conn):
337
+ if budget <= 0 or (cancel is not None and cancel.is_set()):
338
+ return
339
+ for pid, pack in packs.items():
340
+ key = f"{pid}@{pack.version}:{rec['table']}:{rec['record_id']}"
341
+ if key in done:
342
+ continue
343
+ if rec["role"] not in pack.allowed_roles() or not filters[pid].passes(rec["text"]):
344
+ conn.execute("INSERT OR REPLACE INTO derivation_progress (key) VALUES (?)", (key,))
345
+ done.add(key)
346
+ continue
347
+ budget -= 1
348
+ try:
349
+ raw = llm(model, build_prompt(pack, rec["text"], rec["date"], rec["role"]))
350
+ _bump_yield(conn, pid, llm_calls=1, prefilter_hits=1)
351
+ except Exception: # noqa: BLE001
352
+ st["llm_errors"] = st.get("llm_errors", 0) + 1
353
+ continue
354
+ valid, _rej = parse_output(raw, pack, record_text=rec["text"])
355
+ _bump_yield(conn, pid, assertions=len(valid))
356
+ for a in valid:
357
+ a = judge(pack, rec, a, "catchup")
358
+ if a.get("verifier_status") == "rejected":
359
+ _ledger_write(conn, stage="catchup", pack=pack, rec=rec, a=a,
360
+ model=model, vmodel="(job)", )
361
+ continue
362
+ _bump_yield(conn, pid, accepted=1)
363
+ out = writer.assert_pack_fact(
364
+ pack=pack, predicate=a["predicate"], subject_entity_id=owner,
365
+ value=a["value"], actor_role=rec["role"],
366
+ source_refs=[{"table": rec["table"], "record_id": rec["record_id"]}],
367
+ confidence=a["confidence"], occurrence=a["occurrence"],
368
+ quote=a.get("quote", ""), about=a.get("about", "owner"),
369
+ event_date=rec["date"] or None)
370
+ stored = out.get("outcome") in ("written", "corroborated", "retelling_merged",
371
+ "field_update", "corrected", "superseded")
372
+ if stored:
373
+ _bump_yield(conn, pid, written=1)
374
+ st["catchup_written"] = st.get("catchup_written", 0) + 1
375
+ _ledger_write(conn, stage="catchup", pack=pack, rec=rec, a=a,
376
+ model=model, vmodel="(job)",
377
+ written_id=out.get("object_id") if stored else None)
378
+ conn.execute("INSERT OR REPLACE INTO derivation_progress (key) VALUES (?)", (key,))
379
+ done.add(key)
380
+ if budget <= 0:
381
+ break
382
+ conn.commit()
383
+
384
+
262
385
  def _self_gate(conn, *, all_packs, enabled, filters, llm, judge, model, vmodel, st, cancel):
263
386
  """Per-node self-gating (owner design, 2026-08-26): the node OFFERS, never
264
387
  switches. Enable offers come from a capped shadow trial on a disabled pack
@@ -4,7 +4,7 @@
4
4
  # KG NOTE: this pack's relationship predicate adds ROLE-TYPED edges between person
5
5
  # entities — the single biggest graph upgrade in the catalog (today: communicates_with only).
6
6
  pack: relationships.social
7
- version: 0.2.3
7
+ version: 0.2.5
8
8
  status: draft
9
9
  title: "Relationships"
10
10
  author: topos
@@ -68,7 +68,10 @@ guidance:
68
68
  - "Entity resolution first: an unresolvable 'Alex' gets a mention, not a relationship fact."
69
69
  - "Others' relationships to each other belong in their dossiers, not in rel.* (which is owner-centric)."
70
70
 
71
- revision: # Tier-2 declarative rules (§1.6) — added for the shadow pilot (v0.2.1)
71
+ revision: # Tier-2 declarative rules
72
+ exclusive_with: # Tier-2 completion (v0.2.5): contradictions queue, never auto-supersede
73
+ rel.relationship: [[partner, ex_partner], [spouse, ex_partner]]
74
+ _field: {rel.relationship: role}
72
75
  supersedes_on: {rel.relationship: [status, role]} # role/status transitions keep history (friend->close_friend is a revision)
73
76
  noop_when: "re-statement within 7d at equal confidence"
74
77
 
@@ -0,0 +1,60 @@
1
+ """WA.E derivation report card as CODE (protects: attribution of person-facts
2
+ to the correct subject; junk gates; gold retention — PLAN_DERIVATION_WAVE2 §WA.E).
3
+
4
+ Three scores per pack over a window, computed from the training ledger + owner
5
+ verdicts. Any one alone is gameable; together they describe the pipeline:
6
+
7
+ acceptance — verifier-accepted / judged (the pipeline's own precision proxy)
8
+ owner_upheld — 1 - (owner-rejected stored facts / stored facts owner reviewed)
9
+ (the human-gold correction rate; verified_by_owner counts as upheld)
10
+ reroute_rate — rerouted / judged (attribution catches — visibility, not a gate)
11
+
12
+ The full junk/attribution/retention batteries remain offline instruments run
13
+ against graded corpora; this card is the LIVE, always-on shadow of them.
14
+ """
15
+
16
+ from __future__ import annotations
17
+
18
+ import sqlite3
19
+ from typing import Any, Dict
20
+
21
+
22
+ def compute_report_card(conn: sqlite3.Connection, days: int = 30) -> Dict[str, Any]:
23
+ out: Dict[str, Any] = {"window_days": days, "packs": {}}
24
+ try:
25
+ rows = conn.execute(
26
+ "SELECT pack_id, vstatus, COUNT(*) FROM derivation_training_ledger"
27
+ " WHERE ts >= datetime('now', ?) GROUP BY pack_id, vstatus",
28
+ (f"-{int(days)} day",)).fetchall()
29
+ except sqlite3.OperationalError:
30
+ return out
31
+ per: Dict[str, Dict[str, int]] = {}
32
+ for pack_id, vstatus, n in rows:
33
+ per.setdefault(pack_id, {})[str(vstatus)] = int(n)
34
+ for pack_id, counts in per.items():
35
+ judged = sum(counts.values())
36
+ accepted = counts.get("accepted", 0) + counts.get("rerouted", 0)
37
+ card = {
38
+ "judged": judged,
39
+ "acceptance": round(accepted / judged, 3) if judged else None,
40
+ "reroute_rate": round(counts.get("rerouted", 0) / judged, 3) if judged else None,
41
+ "rejected": counts.get("rejected", 0) + counts.get("rejected_majority", 0),
42
+ "grounding_rejects": counts.get("grounding_reject", 0),
43
+ }
44
+ out["packs"][pack_id] = card
45
+ # owner verdicts over stored pack facts (gold)
46
+ try:
47
+ for pack_id, upheld, rejected in conn.execute(
48
+ """SELECT ontology_id,
49
+ SUM(CASE WHEN json_extract(payload_json,'$.verified_by_owner')=1 THEN 1 ELSE 0 END),
50
+ SUM(CASE WHEN json_extract(payload_json,'$.excluded_by_owner')=1
51
+ OR (valid_to IS NOT NULL AND updated_by LIKE '%reject%') THEN 1 ELSE 0 END)
52
+ FROM signal_objects WHERE object_type='fact' AND ontology_id IS NOT NULL
53
+ GROUP BY ontology_id"""):
54
+ card = out["packs"].setdefault(pack_id, {})
55
+ reviewed = int(upheld or 0) + int(rejected or 0)
56
+ card["owner_reviewed"] = reviewed
57
+ card["owner_upheld"] = round(int(upheld or 0) / reviewed, 3) if reviewed else None
58
+ except sqlite3.OperationalError:
59
+ pass
60
+ return out