apsimo 1.3.0__tar.gz → 1.3.2__tar.gz

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (1000) hide show
  1. {apsimo-1.3.0 → apsimo-1.3.2}/PKG-INFO +2 -2
  2. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/api/authority.py +2 -0
  3. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/api/routers/host.py +59 -6
  4. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/cli.py +1 -0
  5. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/intelligence/graph/selection.py +22 -0
  6. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/setup.py +2 -2
  7. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/setup_hermes.py +41 -3
  8. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo.egg-info/PKG-INFO +2 -2
  9. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo.egg-info/SOURCES.txt +3 -0
  10. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo.egg-info/requires.txt +1 -1
  11. {apsimo-1.3.0 → apsimo-1.3.2}/pyproject.toml +2 -2
  12. apsimo-1.3.2/tests/test_enrolled_sender_turns.py +94 -0
  13. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_hermes_turn_outbox.py +4 -1
  14. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_native_setup.py +93 -0
  15. apsimo-1.3.2/tests/test_recall_request_repetition.py +140 -0
  16. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_scoped_api_authority.py +11 -9
  17. apsimo-1.3.2/tests/test_scoped_contact_resolution.py +48 -0
  18. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_source_vectors.py +8 -3
  19. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_tom_p8_server_integration.py +8 -0
  20. {apsimo-1.3.0 → apsimo-1.3.2}/LICENSE +0 -0
  21. {apsimo-1.3.0 → apsimo-1.3.2}/README.md +0 -0
  22. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/__init__.py +0 -0
  23. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/__main__.py +0 -0
  24. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/agent/__init__.py +0 -0
  25. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/agent/client.py +0 -0
  26. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/agent/models.py +0 -0
  27. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/agents/__init__.py +0 -0
  28. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/agents/models.py +0 -0
  29. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/agents/store.py +0 -0
  30. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/agents/websocket.py +0 -0
  31. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/api/__init__.py +0 -0
  32. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/api/auth_telemetry.py +0 -0
  33. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/api/contact_grants.py +0 -0
  34. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/api/middleware.py +0 -0
  35. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/api/routers/__init__.py +0 -0
  36. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/api/routers/commitment_work.py +0 -0
  37. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/api/routers/context_gate.py +0 -0
  38. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/api/routers/executions.py +0 -0
  39. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/api/routers/followup_plans.py +0 -0
  40. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/api/routers/governed_actions.py +0 -0
  41. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/api/routers/initiative_work.py +0 -0
  42. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/api/routers/mining.py +0 -0
  43. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/api/routers/observations.py +0 -0
  44. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/api/routers/social_state.py +0 -0
  45. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/api/routers/task_queue.py +0 -0
  46. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/api/routers/temporal_followups.py +0 -0
  47. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/api/routers/transport.py +0 -0
  48. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/api/routers/transport_ingress_api.py +0 -0
  49. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/api/schemas/__init__.py +0 -0
  50. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/api/schemas/host.py +0 -0
  51. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/autonomy/cli.py +0 -0
  52. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/autonomy/condition_worker.py +0 -0
  53. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/autonomy/config.py +0 -0
  54. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/autonomy/loop.py +0 -0
  55. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/autonomy/registry.py +0 -0
  56. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/autonomy/scheduler.py +0 -0
  57. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/autonomy/synthesis.py +0 -0
  58. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/backup.py +0 -0
  59. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/beliefs/__init__.py +0 -0
  60. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/beliefs/contradictions.py +0 -0
  61. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/beliefs/decay.py +0 -0
  62. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/beliefs/engine.py +0 -0
  63. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/beliefs/models.py +0 -0
  64. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/beliefs/promotion.py +0 -0
  65. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/beliefs/resolve.py +0 -0
  66. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/beliefs/source_claims.py +0 -0
  67. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/beliefs/source_projection.py +0 -0
  68. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/beliefs/source_time.py +0 -0
  69. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/beliefs/store.py +0 -0
  70. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/briefings/aggregators.py +0 -0
  71. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/briefings/composer.py +0 -0
  72. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/briefings/config.py +0 -0
  73. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/briefings/delivery.py +0 -0
  74. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/briefings/engagement.py +0 -0
  75. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/briefings/engine.py +0 -0
  76. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/briefings/enhancer.py +0 -0
  77. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/briefings/models.py +0 -0
  78. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/briefings/scheduler.py +0 -0
  79. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/briefings/store.py +0 -0
  80. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/chain/__init__.py +0 -0
  81. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/chain/block.py +0 -0
  82. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/chain/cli.py +0 -0
  83. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/chain/genesis.py +0 -0
  84. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/chain/identity.py +0 -0
  85. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/chain/keys.py +0 -0
  86. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/chain/local_keys.py +0 -0
  87. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/chain/manager.py +0 -0
  88. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/chain/node.py +0 -0
  89. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/chain/plugin_transactions.py +0 -0
  90. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/chain/protocol.py +0 -0
  91. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/chain/state_machine.py +0 -0
  92. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/chain/storage.py +0 -0
  93. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/chain/transactions.py +0 -0
  94. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/chain/validation.py +0 -0
  95. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/channels/__init__.py +0 -0
  96. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/channels/manifest.py +0 -0
  97. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/channels/migrations/001_channels_schema.sql +0 -0
  98. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/channels/phone_gateways.py +0 -0
  99. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/channels/presence.py +0 -0
  100. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/channels/router.py +0 -0
  101. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/channels/store.py +0 -0
  102. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/cognition/__init__.py +0 -0
  103. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/cognition/charter.py +0 -0
  104. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/cognition/drive_governance.py +0 -0
  105. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/cognition/evidence_pipeline.py +0 -0
  106. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/cognition/external_events.py +0 -0
  107. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/cognition/goal_spine.py +0 -0
  108. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/cognition/introspection.py +0 -0
  109. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/cognition/prompt.py +0 -0
  110. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/cognition/runtime.py +0 -0
  111. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/cognition/trigger.py +0 -0
  112. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/commitments/__init__.py +0 -0
  113. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/commitments/local_work.py +0 -0
  114. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/commitments/store.py +0 -0
  115. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/commitments/work.py +0 -0
  116. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/compat.py +0 -0
  117. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/compression/__init__.py +0 -0
  118. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/connectors/__init__.py +0 -0
  119. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/connectors/base.py +0 -0
  120. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/connectors/caldav_calendar.py +0 -0
  121. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/connectors/fs_documents.py +0 -0
  122. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/connectors/imap_email.py +0 -0
  123. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/connectors/manager.py +0 -0
  124. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/connectors/webhook_pull.py +0 -0
  125. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/contacts/__init__.py +0 -0
  126. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/contacts/comms.py +0 -0
  127. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/contacts/config.py +0 -0
  128. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/contacts/exporters/__init__.py +0 -0
  129. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/contacts/exporters/vcard.py +0 -0
  130. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/contacts/identity_links.py +0 -0
  131. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/contacts/importer.py +0 -0
  132. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/contacts/importers/__init__.py +0 -0
  133. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/contacts/importers/batch.py +0 -0
  134. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/contacts/importers/macos_contacts.py +0 -0
  135. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/contacts/migrations/001_contacts_schema.sql +0 -0
  136. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/contacts/migrations/002_trust_scopes.sql +0 -0
  137. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/contacts/migrations/003_open_gateway_enum.sql +0 -0
  138. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/contacts/migrations/004_contact_provision_operations.sql +0 -0
  139. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/contacts/migrations/005_identity_links.sql +0 -0
  140. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/contacts/models.py +0 -0
  141. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/contacts/scoring.py +0 -0
  142. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/contacts/store.py +0 -0
  143. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/contacts/transport_ingress.py +0 -0
  144. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/contacts/world_bridge.py +0 -0
  145. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/contextgate/__init__.py +0 -0
  146. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/contextgate/chunker.py +0 -0
  147. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/contextgate/estimate.py +0 -0
  148. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/contextgate/gate.py +0 -0
  149. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/contextgate/retrieve.py +0 -0
  150. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/delivery/__init__.py +0 -0
  151. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/delivery/bridge.py +0 -0
  152. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/delivery/channels.py +0 -0
  153. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/delivery/classification.py +0 -0
  154. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/delivery/rate_limiter.py +0 -0
  155. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/delivery/reachout_policy.py +0 -0
  156. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/directed/__init__.py +0 -0
  157. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/directed/audit.py +0 -0
  158. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/directed/intake.py +0 -0
  159. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/directed/models.py +0 -0
  160. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/directed/service.py +0 -0
  161. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/directives/__init__.py +0 -0
  162. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/directives/evidence.py +0 -0
  163. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/directives/extractor.py +0 -0
  164. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/directives/guard.py +0 -0
  165. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/directives/models.py +0 -0
  166. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/directives/service.py +0 -0
  167. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/directives/store.py +0 -0
  168. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/doctor.py +0 -0
  169. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/environment.py +0 -0
  170. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/events/__init__.py +0 -0
  171. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/events/broadcaster.py +0 -0
  172. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/events/bus.py +0 -0
  173. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/events/journal.py +0 -0
  174. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/events/stream.py +0 -0
  175. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/events/types.py +0 -0
  176. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/execution_results.py +0 -0
  177. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/feedback/__init__.py +0 -0
  178. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/feedback/store.py +0 -0
  179. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/feeds/__init__.py +0 -0
  180. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/feeds/cli.py +0 -0
  181. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/feeds/engine.py +0 -0
  182. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/feeds/example-feed.yaml +0 -0
  183. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/feeds/hermes_cron.py +0 -0
  184. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/feeds/manager.py +0 -0
  185. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/feeds/spec.py +0 -0
  186. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/feeds/template.py +0 -0
  187. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/gate/__init__.py +0 -0
  188. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/gate/audit.py +0 -0
  189. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/gate/communication_policy.py +0 -0
  190. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/gate/config.py +0 -0
  191. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/gate/context_provenance.py +0 -0
  192. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/gate/env_risk.py +0 -0
  193. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/gate/guard_audit.py +0 -0
  194. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/gate/layers/__init__.py +0 -0
  195. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/gate/layers/base.py +0 -0
  196. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/gate/layers/l1_recipient.py +0 -0
  197. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/gate/layers/l2_pii.py +0 -0
  198. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/gate/layers/l3_cross_context.py +0 -0
  199. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/gate/layers/l4_trust_tier.py +0 -0
  200. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/gate/layers/l5_injection.py +0 -0
  201. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/gate/layers/l6_review.py +0 -0
  202. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/gate/layers/l7_delay.py +0 -0
  203. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/gate/layers/tom2_epistemic.py +0 -0
  204. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/gate/models.py +0 -0
  205. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/gate/pending_dispatch.py +0 -0
  206. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/gate/pipeline.py +0 -0
  207. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/gate/rejection.py +0 -0
  208. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/gate/response_guard.py +0 -0
  209. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/gate/rulesets/injection_v1.yaml +0 -0
  210. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/gate/surface_policy.py +0 -0
  211. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/gate/taint.py +0 -0
  212. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/genesis.json +0 -0
  213. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/goals/__init__.py +0 -0
  214. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/goals/config.py +0 -0
  215. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/goals/decomposer.py +0 -0
  216. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/goals/engine.py +0 -0
  217. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/goals/inference.py +0 -0
  218. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/goals/models.py +0 -0
  219. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/goals/priority.py +0 -0
  220. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/goals/queue_bridge.py +0 -0
  221. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/goals/replan.py +0 -0
  222. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/goals/schema.sql +0 -0
  223. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/goals/store.py +0 -0
  224. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/governed_actions.py +0 -0
  225. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/harness_integration/__init__.py +0 -0
  226. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/harness_integration/context.py +0 -0
  227. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/harness_integration/skills.py +0 -0
  228. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/identity/__init__.py +0 -0
  229. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/identity/participants.py +0 -0
  230. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/identity/resolver.py +0 -0
  231. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/identity_bootstrap/__init__.py +0 -0
  232. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/identity_bootstrap/builder.py +0 -0
  233. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/identity_bootstrap/corpus.py +0 -0
  234. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/identity_bootstrap/models.py +0 -0
  235. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/identity_bootstrap/runner.py +0 -0
  236. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/identity_bootstrap/seeders/__init__.py +0 -0
  237. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/identity_bootstrap/seeders/briefings.py +0 -0
  238. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/identity_bootstrap/seeders/chain.py +0 -0
  239. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/identity_bootstrap/seeders/goals.py +0 -0
  240. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/identity_bootstrap/seeders/memory.py +0 -0
  241. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/identity_bootstrap/seeders/neo4j_cognition.py +0 -0
  242. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/identity_bootstrap/seeders/relationship.py +0 -0
  243. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/identity_bootstrap/seeders/sessions.py +0 -0
  244. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/identity_bootstrap/seeders/skills.py +0 -0
  245. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/identity_bootstrap/seeders/task_queue.py +0 -0
  246. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/identity_bootstrap/seeders/world_model.py +0 -0
  247. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/identity_bootstrap/self_query.py +0 -0
  248. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/identity_bootstrap/self_reflection.py +0 -0
  249. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/identity_bootstrap/skill.py +0 -0
  250. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/identity_bootstrap/verifier.py +0 -0
  251. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/initiatives/__init__.py +0 -0
  252. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/initiatives/action_registry.py +0 -0
  253. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/initiatives/approval_authority.py +0 -0
  254. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/initiatives/approval_policy.py +0 -0
  255. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/initiatives/assignment.py +0 -0
  256. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/initiatives/backup_evidence.py +0 -0
  257. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/initiatives/context_freshness.py +0 -0
  258. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/initiatives/models.py +0 -0
  259. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/initiatives/native_work.py +0 -0
  260. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/initiatives/standing_approvals.py +0 -0
  261. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/initiatives/store.py +0 -0
  262. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/initiatives/temporal_followup.py +0 -0
  263. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/intelligence/__init__.py +0 -0
  264. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/intelligence/cognition/__init__.py +0 -0
  265. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/intelligence/cognition/gap_detector.py +0 -0
  266. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/intelligence/cognition/metalearner.py +0 -0
  267. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/intelligence/cognition/metrics_collector.py +0 -0
  268. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/intelligence/cognition/performance_index.py +0 -0
  269. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/intelligence/cognition/registry.py +0 -0
  270. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/intelligence/cognition/strategy_adjuster.py +0 -0
  271. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/intelligence/cognition/types.py +0 -0
  272. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/intelligence/components/__init__.py +0 -0
  273. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/intelligence/components/anomaly_detector.py +0 -0
  274. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/intelligence/components/initiative_engine.py +0 -0
  275. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/intelligence/components/preference_learner.py +0 -0
  276. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/intelligence/components/research_orchestrator.py +0 -0
  277. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/intelligence/components/self_directed_thinker.py +0 -0
  278. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/intelligence/components/self_reflector.py +0 -0
  279. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/intelligence/components/session_continuity.py +0 -0
  280. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/intelligence/components/task_planner.py +0 -0
  281. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/intelligence/components/tool_learner.py +0 -0
  282. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/intelligence/graph/__init__.py +0 -0
  283. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/intelligence/graph/client.py +0 -0
  284. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/intelligence/graph/consolidator.py +0 -0
  285. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/intelligence/graph/distiller.py +0 -0
  286. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/intelligence/graph/migrations.py +0 -0
  287. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/intelligence/graph/queries.py +0 -0
  288. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/intelligence/graph/recall.py +0 -0
  289. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/intelligence/graph/reconciler.py +0 -0
  290. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/intelligence/graph/schema.py +0 -0
  291. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/intelligence/learning/__init__.py +0 -0
  292. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/intelligence/learning/continuous_learner.py +0 -0
  293. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/intelligence/learning/feedback_store.py +0 -0
  294. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/intelligence/mind_model/__init__.py +0 -0
  295. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/intelligence/mind_model/graph_baseline.py +0 -0
  296. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/intelligence/mind_model/signal_collector.py +0 -0
  297. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/intelligence/relationships/__init__.py +0 -0
  298. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/intelligence/relationships/profiler.py +0 -0
  299. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/intelligence/relationships/scorer.py +0 -0
  300. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/intelligence/relationships/signal_floor.py +0 -0
  301. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/intelligence/relationships/trust_tiers.py +0 -0
  302. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/intelligence/synthesis/__init__.py +0 -0
  303. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/intelligence/synthesis/connection_discoverer.py +0 -0
  304. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/intelligence/synthesis/cross_domain_analyzer.py +0 -0
  305. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/intelligence/synthesis/insight_deliverer.py +0 -0
  306. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/intelligence/synthesis/insight_store.py +0 -0
  307. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/intelligence/synthesis/insight_validator.py +0 -0
  308. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/intelligence/synthesis/novelty_scorer.py +0 -0
  309. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/intelligence/turn_middleware/__init__.py +0 -0
  310. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/intelligence/turn_middleware/memory_sync.py +0 -0
  311. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/mcp/__init__.py +0 -0
  312. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/mcp/__main__.py +0 -0
  313. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/mcp/config.py +0 -0
  314. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/mcp/server.py +0 -0
  315. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/migrations.py +0 -0
  316. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/mining/__init__.py +0 -0
  317. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/mining/corpus.py +0 -0
  318. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/mining/escalations.py +0 -0
  319. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/mining/models.py +0 -0
  320. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/mining/store.py +0 -0
  321. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/models/__init__.py +0 -0
  322. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/models/memory.py +0 -0
  323. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/models/mesh.py +0 -0
  324. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/models/person.py +0 -0
  325. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/models/signal.py +0 -0
  326. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/observations/__init__.py +0 -0
  327. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/observations/store.py +0 -0
  328. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/patterns/__init__.py +0 -0
  329. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/patterns/extract.py +0 -0
  330. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/patterns/store.py +0 -0
  331. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/persona/__init__.py +0 -0
  332. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/persona/engine.py +0 -0
  333. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/persona/manifest.py +0 -0
  334. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/projects/__init__.py +0 -0
  335. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/projects/engine.py +0 -0
  336. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/projects/event_outbox.py +0 -0
  337. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/projects/models.py +0 -0
  338. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/projects/planner.py +0 -0
  339. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/projects/store.py +0 -0
  340. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/proposals/__init__.py +0 -0
  341. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/proposals/engine.py +0 -0
  342. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/proposals/models.py +0 -0
  343. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/qualification/__init__.py +0 -0
  344. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/qualification/cases.py +0 -0
  345. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/qualification/cli.py +0 -0
  346. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/qualification/memory_cases.py +0 -0
  347. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/qualification/records.py +0 -0
  348. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/qualification/report.py +0 -0
  349. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/qualification/runner.py +0 -0
  350. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/qualification/structured_cases.py +0 -0
  351. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/reasoning/__init__.py +0 -0
  352. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/reasoning/executor.py +0 -0
  353. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/reasoning/loop.py +0 -0
  354. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/reasoning/native_tools/__init__.py +0 -0
  355. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/reasoning/native_tools/calculate.py +0 -0
  356. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/reasoning/native_tools/file_ops.py +0 -0
  357. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/reasoning/native_tools/web_search.py +0 -0
  358. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/reasoning/tool_policy.py +0 -0
  359. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/redact/__init__.py +0 -0
  360. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/repos/__init__.py +0 -0
  361. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/repos/mirrors.py +0 -0
  362. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/research/__init__.py +0 -0
  363. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/research/artifact.py +0 -0
  364. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/research/gatherer.py +0 -0
  365. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/research/pipeline.py +0 -0
  366. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/research/search/__init__.py +0 -0
  367. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/research/search/base.py +0 -0
  368. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/research/search/brave.py +0 -0
  369. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/research/search/cache.py +0 -0
  370. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/research/search/duckduckgo.py +0 -0
  371. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/research/search/orchestrator.py +0 -0
  372. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/research/search/serpapi.py +0 -0
  373. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/research/search/tavily.py +0 -0
  374. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/research/synthesizer.py +0 -0
  375. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/router/__init__.py +0 -0
  376. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/router/complexity_scorer.py +0 -0
  377. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/router/endpoints.py +0 -0
  378. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/router/fallback.py +0 -0
  379. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/router/functions.py +0 -0
  380. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/router/native_policy.py +0 -0
  381. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/router/router.py +0 -0
  382. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/router/self_learning.py +0 -0
  383. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/router/tiers.py +0 -0
  384. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/sandbox/__init__.py +0 -0
  385. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/sandbox/backend.py +0 -0
  386. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/sandbox/manager.py +0 -0
  387. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/scope_bounds.py +0 -0
  388. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/secrets/__init__.py +0 -0
  389. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/secrets/backends/__init__.py +0 -0
  390. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/secrets/backends/base.py +0 -0
  391. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/secrets/backends/env.py +0 -0
  392. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/secrets/backends/keyring.py +0 -0
  393. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/secrets/backends/onepassword.py +0 -0
  394. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/secrets/cli.py +0 -0
  395. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/secrets/manager.py +0 -0
  396. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/secrets/migration.py +0 -0
  397. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/secrets/types.py +0 -0
  398. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/seed.py +0 -0
  399. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/self_model/__init__.py +0 -0
  400. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/self_model/appraisals.py +0 -0
  401. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/self_model/benchmark.py +0 -0
  402. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/self_model/brief.py +0 -0
  403. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/self_model/event_concerns.py +0 -0
  404. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/self_model/execution_forecasts.py +0 -0
  405. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/self_model/expectations.py +0 -0
  406. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/self_model/experiments.py +0 -0
  407. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/self_model/journal.py +0 -0
  408. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/self_model/judgments.py +0 -0
  409. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/self_model/native_outcomes.py +0 -0
  410. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/self_model/params.py +0 -0
  411. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/self_model/perspective.py +0 -0
  412. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/self_model/reconcile.py +0 -0
  413. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/self_model/reply_forecasts.py +0 -0
  414. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/self_model/runtime_forecasts.py +0 -0
  415. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/self_model/runtime_models.py +0 -0
  416. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/self_model/settlement.py +0 -0
  417. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/self_model/situation.py +0 -0
  418. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/self_model/store.py +0 -0
  419. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/self_model/supervised.py +0 -0
  420. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/self_model/thinker.py +0 -0
  421. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/self_model/trust.py +0 -0
  422. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/self_model/workspace.py +0 -0
  423. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/server.py +0 -0
  424. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/services/__init__.py +0 -0
  425. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/services/agent_bridge.py +0 -0
  426. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/services/initiative_executor.py +0 -0
  427. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/services/instance.py +0 -0
  428. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/sessions/__init__.py +0 -0
  429. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/sessions/config.py +0 -0
  430. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/sessions/context_loader.py +0 -0
  431. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/sessions/federation_session.py +0 -0
  432. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/sessions/isolated_session.py +0 -0
  433. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/sessions/reports.py +0 -0
  434. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/sessions/store.py +0 -0
  435. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/setup_local_work.py +0 -0
  436. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/setup_native_goals.py +0 -0
  437. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/setup_native_reviews.py +0 -0
  438. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/skills/__init__.py +0 -0
  439. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/skills/base.py +0 -0
  440. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/skills/budget.py +0 -0
  441. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/skills/executor.py +0 -0
  442. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/skills/executors/__init__.py +0 -0
  443. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/skills/executors/behavioral_correction.py +0 -0
  444. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/skills/executors/capability_gap.py +0 -0
  445. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/skills/executors/data_quality.py +0 -0
  446. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/skills/executors/knowledge_acquisition.py +0 -0
  447. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/skills/executors/operational_hygiene.py +0 -0
  448. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/skills/executors/subsystem_health.py +0 -0
  449. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/skills/hermes_export.py +0 -0
  450. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/skills/index.py +0 -0
  451. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/skills/learning/__init__.py +0 -0
  452. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/skills/learning/novelty_detector.py +0 -0
  453. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/skills/learning/pattern_extractor.py +0 -0
  454. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/skills/learning/triggers.py +0 -0
  455. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/skills/loader.py +0 -0
  456. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/skills/migrations/002_progressive_loading.sql +0 -0
  457. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/skills/migrations/backfill_triggers.py +0 -0
  458. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/skills/models.py +0 -0
  459. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/skills/packager.py +0 -0
  460. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/skills/protocols.py +0 -0
  461. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/skills/registry.py +0 -0
  462. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/skills/runtime.py +0 -0
  463. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/skills/sandbox_runner.py +0 -0
  464. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/skills/scheduler.py +0 -0
  465. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/skills/schema.py +0 -0
  466. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/skills/security/__init__.py +0 -0
  467. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/skills/security/guards.py +0 -0
  468. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/skills/security/scanner.py +0 -0
  469. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/skills_memory/__init__.py +0 -0
  470. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/skills_memory/distill.py +0 -0
  471. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/skills_memory/models.py +0 -0
  472. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/skills_memory/retrieve.py +0 -0
  473. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/skills_memory/store.py +0 -0
  474. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/surprise/__init__.py +0 -0
  475. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/surprise/accumulation.py +0 -0
  476. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/surprise/scorer.py +0 -0
  477. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/surprise/store.py +0 -0
  478. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/task_queue/__init__.py +0 -0
  479. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/task_queue/action_receipts.py +0 -0
  480. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/task_queue/approval_relay_canary.py +0 -0
  481. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/task_queue/config.py +0 -0
  482. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/task_queue/contract.py +0 -0
  483. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/task_queue/events.py +0 -0
  484. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/task_queue/governor.py +0 -0
  485. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/task_queue/handlers/__init__.py +0 -0
  486. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/task_queue/handlers/base.py +0 -0
  487. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/task_queue/handlers/inference.py +0 -0
  488. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/task_queue/handlers/monitoring.py +0 -0
  489. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/task_queue/handlers/registry.py +0 -0
  490. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/task_queue/handlers/subtask_handler.py +0 -0
  491. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/task_queue/handlers/system_maintenance.py +0 -0
  492. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/task_queue/mesh_integration.py +0 -0
  493. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/task_queue/models.py +0 -0
  494. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/task_queue/queue_manager.py +0 -0
  495. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/task_queue/routing.py +0 -0
  496. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/task_queue/scheduler.py +0 -0
  497. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/task_queue/schema.sql +0 -0
  498. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/task_queue/work_control.py +0 -0
  499. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/task_queue/worker.py +0 -0
  500. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/telemetry.py +0 -0
  501. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/tom/__init__.py +0 -0
  502. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/tom/affect.py +0 -0
  503. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/tom/approvals.py +0 -0
  504. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/tom/arcs.py +0 -0
  505. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/tom/asymmetry.py +0 -0
  506. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/tom/eligibility.py +0 -0
  507. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/tom/engagement.py +0 -0
  508. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/tom/exposure.py +0 -0
  509. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/tom/extractor.py +0 -0
  510. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/tom/fact_adapters.py +0 -0
  511. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/tom/facts.py +0 -0
  512. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/tom/integration.py +0 -0
  513. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/tom/leveled.py +0 -0
  514. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/tom/levels.py +0 -0
  515. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/tom/recipient_audit.py +0 -0
  516. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/tom/recipient_simulator.py +0 -0
  517. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/tom/source_lineage.py +0 -0
  518. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/tom/tom2.py +0 -0
  519. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/tom/visibility.py +0 -0
  520. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/tom/visibility_store.py +0 -0
  521. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/tools/__init__.py +0 -0
  522. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/tools/definitions.py +0 -0
  523. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/tools/handlers.py +0 -0
  524. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/toolsmith/__init__.py +0 -0
  525. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/toolsmith/authority.py +0 -0
  526. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/toolsmith/engine.py +0 -0
  527. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/toolsmith/integrity.py +0 -0
  528. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/toolsmith/miner.py +0 -0
  529. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/toolsmith/policy.py +0 -0
  530. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/toolsmith/registry.py +0 -0
  531. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/turns/__init__.py +0 -0
  532. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/turns/audio.py +0 -0
  533. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/turns/documents.py +0 -0
  534. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/turns/executions.py +0 -0
  535. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/turns/hermes_history.py +0 -0
  536. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/turns/hermes_kanban.py +0 -0
  537. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/turns/hermes_work.py +0 -0
  538. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/turns/idempotency.py +0 -0
  539. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/turns/local_work.py +0 -0
  540. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/turns/media.py +0 -0
  541. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/turns/reported_workers.py +0 -0
  542. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/turns/source_annotations.py +0 -0
  543. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/turns/source_attribution.py +0 -0
  544. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/turns/source_read.py +0 -0
  545. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/turns/source_vectors.py +0 -0
  546. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/turns/video.py +0 -0
  547. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/util/autonomy_preset.py +0 -0
  548. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/util/instance.py +0 -0
  549. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/util/model_output.py +0 -0
  550. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/util/quiet_hours.py +0 -0
  551. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/util/session_safety.py +0 -0
  552. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/util/temporal.py +0 -0
  553. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/vector/__init__.py +0 -0
  554. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/vector/backfill.py +0 -0
  555. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/vector/caption.py +0 -0
  556. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/vector/collections.py +0 -0
  557. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/vector/config.py +0 -0
  558. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/vector/embedder.py +0 -0
  559. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/vector/image_preprocess.py +0 -0
  560. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/vector/image_store.py +0 -0
  561. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/vector/indexes.py +0 -0
  562. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/vector/migrate.py +0 -0
  563. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/vector/multimodal_provider.py +0 -0
  564. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/vector/multimodal_types.py +0 -0
  565. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/vector/openai_provider.py +0 -0
  566. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/vector/query.py +0 -0
  567. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/vector/reranker.py +0 -0
  568. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/vector/safety_image.py +0 -0
  569. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/vector/scanner.py +0 -0
  570. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/vector/setup.py +0 -0
  571. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/vector/store.py +0 -0
  572. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/vector/tiers.py +0 -0
  573. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/work_orders.py +0 -0
  574. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/workers/__init__.py +0 -0
  575. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/workers/agent_bridge.py +0 -0
  576. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/workers/colony_worker.py +0 -0
  577. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/workers/queue_worker.py +0 -0
  578. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/workers/skills_sync.py +0 -0
  579. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/world_model/__init__.py +0 -0
  580. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/world_model/causal_maintenance.py +0 -0
  581. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/world_model/causal_policy.py +0 -0
  582. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/world_model/causal_query.py +0 -0
  583. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/world_model/confidence.py +0 -0
  584. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/world_model/config.py +0 -0
  585. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/world_model/constants.py +0 -0
  586. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/world_model/entities.py +0 -0
  587. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/world_model/expectation_resolvers.py +0 -0
  588. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/world_model/extraction/__init__.py +0 -0
  589. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/world_model/extraction/base.py +0 -0
  590. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/world_model/extraction/conversation_extractor.py +0 -0
  591. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/world_model/extraction/detector.py +0 -0
  592. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/world_model/extraction/document_extractor.py +0 -0
  593. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/world_model/extraction/formats/__init__.py +0 -0
  594. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/world_model/extraction/formats/csv_fmt.py +0 -0
  595. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/world_model/extraction/formats/html_fmt.py +0 -0
  596. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/world_model/extraction/formats/json_fmt.py +0 -0
  597. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/world_model/extraction/formats/pdf.py +0 -0
  598. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/world_model/extraction/formats/text.py +0 -0
  599. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/world_model/extraction/llm_extractor.py +0 -0
  600. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/world_model/extraction/pipeline.py +0 -0
  601. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/world_model/integrations/__init__.py +0 -0
  602. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/world_model/integrations/mind_model_bridge.py +0 -0
  603. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/world_model/integrations/social_intel_bridge.py +0 -0
  604. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/world_model/jobs/__init__.py +0 -0
  605. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/world_model/jobs/extraction_job.py +0 -0
  606. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/world_model/llm_extract.py +0 -0
  607. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/world_model/neo4j/__init__.py +0 -0
  608. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/world_model/neo4j/backend.py +0 -0
  609. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/world_model/observations.py +0 -0
  610. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/world_model/populator.py +0 -0
  611. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/world_model/postgres/__init__.py +0 -0
  612. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/world_model/postgres/backend.py +0 -0
  613. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/world_model/relationships.py +0 -0
  614. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/world_model/resolution/__init__.py +0 -0
  615. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/world_model/resolution/entity_resolver.py +0 -0
  616. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/world_model/resolution/merge_audit.py +0 -0
  617. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/world_model/resolution/merge_workflow.py +0 -0
  618. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/world_model/source_reports.py +0 -0
  619. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/world_model/sqlite/__init__.py +0 -0
  620. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/world_model/sqlite/backend.py +0 -0
  621. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/world_model/sqlite/schema.sql +0 -0
  622. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo/world_model/store.py +0 -0
  623. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo.egg-info/dependency_links.txt +0 -0
  624. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo.egg-info/entry_points.txt +0 -0
  625. {apsimo-1.3.0 → apsimo-1.3.2}/apsimo.egg-info/top_level.txt +0 -0
  626. {apsimo-1.3.0 → apsimo-1.3.2}/colony_sidecar/__init__.py +0 -0
  627. {apsimo-1.3.0 → apsimo-1.3.2}/setup.cfg +0 -0
  628. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_accepted_local_work.py +0 -0
  629. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_adaptive_params.py +0 -0
  630. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_affect.py +0 -0
  631. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_agent_action_routing.py +0 -0
  632. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_agent_api.py +0 -0
  633. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_agent_bridge.py +0 -0
  634. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_agent_bridge_service.py +0 -0
  635. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_agent_sdk.py +0 -0
  636. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_agent_sensor_loop.py +0 -0
  637. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_agent_snapshot.py +0 -0
  638. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_agent_store.py +0 -0
  639. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_annotated_recall_reinforcement.py +0 -0
  640. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_answer_source_lineage.py +0 -0
  641. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_appraisal_incident_decisions.py +0 -0
  642. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_approval_gate.py +0 -0
  643. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_approval_relay_canary.py +0 -0
  644. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_apsimo_compat.py +0 -0
  645. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_apsimo_harness_guidance.py +0 -0
  646. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_assignment_engine.py +0 -0
  647. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_audit_cleanup.py +0 -0
  648. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_auth_coverage.py +0 -0
  649. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_auth_migration_readiness.py +0 -0
  650. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_authz_scope_api.py +0 -0
  651. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_autonomy_preset.py +0 -0
  652. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_backup.py +0 -0
  653. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_backup_receipt_evidence.py +0 -0
  654. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_beliefs.py +0 -0
  655. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_bind_auth_guard.py +0 -0
  656. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_boundary_fail_closed.py +0 -0
  657. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_bounded_approval_authority.py +0 -0
  658. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_briefing_aggregators.py +0 -0
  659. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_canonical_scoped_context.py +0 -0
  660. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_canonical_source_read.py +0 -0
  661. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_causal_extract.py +0 -0
  662. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_causal_falsifiability.py +0 -0
  663. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_causal_maintenance.py +0 -0
  664. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_causal_policy.py +0 -0
  665. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_causal_query.py +0 -0
  666. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_causal_query_only_guard.py +0 -0
  667. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_chain_keys.py +0 -0
  668. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_channel_preferences.py +0 -0
  669. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_channel_registry.py +0 -0
  670. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_channel_store.py +0 -0
  671. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_cognition.py +0 -0
  672. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_cognition_evidence_pipeline.py +0 -0
  673. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_cognition_evidence_server_wiring.py +0 -0
  674. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_cognition_goal_spine.py +0 -0
  675. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_cognition_observability.py +0 -0
  676. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_cognition_p4_controlled_learning.py +0 -0
  677. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_cognition_p4_server_integration.py +0 -0
  678. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_cognition_p6_p7_server_wiring.py +0 -0
  679. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_cognition_p7_drive_governance.py +0 -0
  680. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_cognition_phase_b_runtime.py +0 -0
  681. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_cognition_phase_c_scheduler.py +0 -0
  682. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_cognition_server_wiring.py +0 -0
  683. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_colony_memory_provider.py +0 -0
  684. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_commitment_resolution.py +0 -0
  685. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_commitment_resolution_downgrade.py +0 -0
  686. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_commitment_resolution_schema.py +0 -0
  687. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_commitment_work.py +0 -0
  688. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_commitments.py +0 -0
  689. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_competence_reconciliation.py +0 -0
  690. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_compression.py +0 -0
  691. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_concern_resolution_receipts.py +0 -0
  692. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_condition_producer.py +0 -0
  693. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_connectors.py +0 -0
  694. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_contact_fact_recall.py +0 -0
  695. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_contact_policy_projection.py +0 -0
  696. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_contact_provisioning.py +0 -0
  697. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_contact_timezone.py +0 -0
  698. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_contacts_intro.py +0 -0
  699. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_contacts_persistence.py +0 -0
  700. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_context_gate.py +0 -0
  701. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_context_phase1.py +0 -0
  702. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_context_provenance.py +0 -0
  703. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_conversation_presence.py +0 -0
  704. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_conversation_turn_concerns.py +0 -0
  705. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_current_work_recall_selection.py +0 -0
  706. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_delivery_bridge_503.py +0 -0
  707. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_delivery_gateway_identity.py +0 -0
  708. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_delivery_reachout_routing.py +0 -0
  709. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_directed.py +0 -0
  710. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_directed_envelope.py +0 -0
  711. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_directed_reports.py +0 -0
  712. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_directed_trust.py +0 -0
  713. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_directive_sources.py +0 -0
  714. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_directives.py +0 -0
  715. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_distill.py +0 -0
  716. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_doctor.py +0 -0
  717. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_document_memory_guard.py +0 -0
  718. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_duckduckgo_provider.py +0 -0
  719. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_embedding_generations.py +0 -0
  720. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_ensure_channel_id.py +0 -0
  721. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_env_risk.py +0 -0
  722. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_event_broadcasts.py +0 -0
  723. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_event_bus_types.py +0 -0
  724. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_event_concerns.py +0 -0
  725. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_event_stream_reliability.py +0 -0
  726. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_execution_forecasts.py +0 -0
  727. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_execution_input_purpose.py +0 -0
  728. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_execution_registry.py +0 -0
  729. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_expectations.py +0 -0
  730. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_expectations_v2.py +0 -0
  731. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_experiments.py +0 -0
  732. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_external_cognition_events.py +0 -0
  733. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_external_event_concerns.py +0 -0
  734. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_facts_backfill.py +0 -0
  735. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_feedback.py +0 -0
  736. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_followup_plans.py +0 -0
  737. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_forecast_learning.py +0 -0
  738. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_function_routing.py +0 -0
  739. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_gap_generators.py +0 -0
  740. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_genesis_manifest.py +0 -0
  741. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_global_pause.py +0 -0
  742. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_goal_dispatch_availability.py +0 -0
  743. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_goal_inference_provenance.py +0 -0
  744. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_goal_reader_imports.py +0 -0
  745. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_governed_actions.py +0 -0
  746. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_governed_research_handoff.py +0 -0
  747. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_graduated_approvals.py +0 -0
  748. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_grant_envelope.py +0 -0
  749. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_graph_reindex_metadata.py +0 -0
  750. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_guard_audit.py +0 -0
  751. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_guard_chat_mode.py +0 -0
  752. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_guard_derive_context.py +0 -0
  753. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_guard_enforce_policy.py +0 -0
  754. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_hermes_export.py +0 -0
  755. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_hermes_general_governance.py +0 -0
  756. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_hermes_history_import.py +0 -0
  757. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_hermes_native_tool_authority.py +0 -0
  758. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_hermes_plugin_contract.py +0 -0
  759. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_hermes_plugin_event_lifecycle.py +0 -0
  760. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_hermes_plugin_event_replay.py +0 -0
  761. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_hermes_plugin_guard_shadow.py +0 -0
  762. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_hermes_plugin_signals.py +0 -0
  763. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_hermes_plugin_turn_id.py +0 -0
  764. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_hermes_queue_stats_projection.py +0 -0
  765. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_hermes_setup.py +0 -0
  766. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_hermes_work_projection.py +0 -0
  767. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_host_input_provenance.py +0 -0
  768. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_hostworker_agreement.py +0 -0
  769. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_identity_continuity.py +0 -0
  770. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_identity_corrections.py +0 -0
  771. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_inference_context_gate.py +0 -0
  772. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_initiative_engine.py +0 -0
  773. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_initiative_evidence.py +0 -0
  774. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_initiative_executor.py +0 -0
  775. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_initiative_feedback.py +0 -0
  776. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_initiative_pipeline_v016.py +0 -0
  777. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_initiative_retry.py +0 -0
  778. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_initiative_store.py +0 -0
  779. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_input_source_lineage.py +0 -0
  780. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_insight_store.py +0 -0
  781. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_instance_service.py +0 -0
  782. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_instance_service_live.py +0 -0
  783. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_intelligence_components.py +0 -0
  784. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_intelligence_synthesis.py +0 -0
  785. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_introduction_initiatives.py +0 -0
  786. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_job_writeback.py +0 -0
  787. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_journal.py +0 -0
  788. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_legacy_fact_context.py +0 -0
  789. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_local_work_context.py +0 -0
  790. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_loop_stats_accuracy.py +0 -0
  791. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_mcp_config.py +0 -0
  792. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_mcp_server.py +0 -0
  793. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_media_read_reference_presentation.py +0 -0
  794. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_memory_decay.py +0 -0
  795. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_memory_formation.py +0 -0
  796. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_memory_governance.py +0 -0
  797. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_memory_promotion.py +0 -0
  798. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_memory_prune.py +0 -0
  799. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_memory_read_hydration.py +0 -0
  800. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_memory_response_schemas.py +0 -0
  801. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_migrations.py +0 -0
  802. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_mining.py +0 -0
  803. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_model_qualification_cli.py +0 -0
  804. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_model_qualification_memory.py +0 -0
  805. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_model_qualification_runner.py +0 -0
  806. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_model_qualification_structured.py +0 -0
  807. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_native_accepted_local_work.py +0 -0
  808. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_native_initiative_work.py +0 -0
  809. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_native_input_carrier.py +0 -0
  810. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_native_outcome_judgments.py +0 -0
  811. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_native_request_erasure.py +0 -0
  812. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_native_review_recurrence.py +0 -0
  813. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_native_source_image_read.py +0 -0
  814. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_native_source_read.py +0 -0
  815. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_native_source_video_read.py +0 -0
  816. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_neo4j_backend.py +0 -0
  817. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_operator_deck_read_truth.py +0 -0
  818. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_ordinary_context_briefings.py +0 -0
  819. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_owner_preferences.py +0 -0
  820. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_p2_wirings.py +0 -0
  821. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_partial_work_rendering.py +0 -0
  822. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_patterns.py +0 -0
  823. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_pending_work_coverage.py +0 -0
  824. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_persona.py +0 -0
  825. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_persona_setup_result.py +0 -0
  826. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_phase_capability_check.py +0 -0
  827. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_preset_loop_coupling.py +0 -0
  828. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_procedure_source_context.py +0 -0
  829. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_project_event_outbox.py +0 -0
  830. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_project_result_reconciliation_phase.py +0 -0
  831. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_projects.py +0 -0
  832. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_prompt_evals.py +0 -0
  833. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_proposals.py +0 -0
  834. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_provenance_population.py +0 -0
  835. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_pseudo_agi_production_chain.py +0 -0
  836. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_queue_completed_filter.py +0 -0
  837. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_queue_contract.py +0 -0
  838. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_quiet_hours_and_reload.py +0 -0
  839. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_reachout_policy.py +0 -0
  840. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_recall_hybrid.py +0 -0
  841. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_recall_person_boost.py +0 -0
  842. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_recall_ranking.py +0 -0
  843. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_recall_rerank.py +0 -0
  844. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_recall_source_presentation.py +0 -0
  845. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_recall_unified_context.py +0 -0
  846. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_recency.py +0 -0
  847. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_reflection_task_routing.py +0 -0
  848. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_rejection_loop.py +0 -0
  849. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_relationship_calendar_aggregators.py +0 -0
  850. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_relationship_score_refresh.py +0 -0
  851. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_relationship_signal_floor.py +0 -0
  852. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_relationships.py +0 -0
  853. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_reply_forecast_callback_order.py +0 -0
  854. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_reply_forecast_stops.py +0 -0
  855. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_reply_forecasts.py +0 -0
  856. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_repo_tools.py +0 -0
  857. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_reported_worker_status.py +0 -0
  858. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_request_capabilities.py +0 -0
  859. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_request_work_context.py +0 -0
  860. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_reranker_remote.py +0 -0
  861. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_research_orchestrator.py +0 -0
  862. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_resolve_messaging_handle.py +0 -0
  863. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_response_guard.py +0 -0
  864. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_response_guard_communication_policy.py +0 -0
  865. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_response_guard_endpoint.py +0 -0
  866. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_response_guard_surface_policy.py +0 -0
  867. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_router_tiers.py +0 -0
  868. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_runtime_model_observations.py +0 -0
  869. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_sandbox.py +0 -0
  870. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_secondary_review_contract.py +0 -0
  871. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_seed_retirement.py +0 -0
  872. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_selected_autonomy.py +0 -0
  873. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_self_directed_thinker.py +0 -0
  874. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_self_initiatives.py +0 -0
  875. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_self_judgment_opt_in.py +0 -0
  876. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_self_judgment_premises.py +0 -0
  877. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_self_judgments.py +0 -0
  878. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_self_model.py +0 -0
  879. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_self_perspective.py +0 -0
  880. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_selfhood_benchmark.py +0 -0
  881. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_session_reports.py +0 -0
  882. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_shared_facts.py +0 -0
  883. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_shared_local_undertaking.py +0 -0
  884. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_short_source_context.py +0 -0
  885. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_sidecar.py +0 -0
  886. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_signals_attribution.py +0 -0
  887. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_situation_spine.py +0 -0
  888. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_skill_approval.py +0 -0
  889. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_skill_attribution.py +0 -0
  890. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_skill_sandbox.py +0 -0
  891. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_skill_synthesis.py +0 -0
  892. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_skill_synthesis_wiring.py +0 -0
  893. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_skills_memory.py +0 -0
  894. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_social_context_flow.py +0 -0
  895. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_social_transport.py +0 -0
  896. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_source_annotation_claim_survivors.py +0 -0
  897. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_source_annotations.py +0 -0
  898. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_source_appraisals.py +0 -0
  899. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_source_attribution.py +0 -0
  900. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_source_audio.py +0 -0
  901. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_source_audio_claims.py +0 -0
  902. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_source_claim_budget.py +0 -0
  903. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_source_claim_diagnostics.py +0 -0
  904. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_source_claim_media_eligibility.py +0 -0
  905. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_source_claim_projection.py +0 -0
  906. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_source_claim_review.py +0 -0
  907. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_source_claim_subject_basis.py +0 -0
  908. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_source_document_read.py +0 -0
  909. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_source_documents.py +0 -0
  910. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_source_episode_admission.py +0 -0
  911. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_source_episode_memory.py +0 -0
  912. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_source_episode_revisions.py +0 -0
  913. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_source_event_precision.py +0 -0
  914. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_source_excerpt_lineage.py +0 -0
  915. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_source_image_read.py +0 -0
  916. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_source_media.py +0 -0
  917. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_source_memory_backup.py +0 -0
  918. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_source_time_query.py +0 -0
  919. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_source_video.py +0 -0
  920. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_sqlite_connection_ownership.py +0 -0
  921. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_supervised_rung.py +0 -0
  922. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_surprise.py +0 -0
  923. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_sweep_fixes.py +0 -0
  924. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_synthesis.py +0 -0
  925. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_telemetry_staleness.py +0 -0
  926. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_temporal.py +0 -0
  927. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_temporal_followups.py +0 -0
  928. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_temporal_index.py +0 -0
  929. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_test_environment_isolation.py +0 -0
  930. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_thinking_phase.py +0 -0
  931. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_thought_function_routing.py +0 -0
  932. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_tick_phase_budget.py +0 -0
  933. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_tier_endpoints.py +0 -0
  934. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_timeline.py +0 -0
  935. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_tom2_approvals.py +0 -0
  936. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_tom2_asymmetry.py +0 -0
  937. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_tom2_context.py +0 -0
  938. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_tom2_cross_gate.py +0 -0
  939. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_tom2_eligibility.py +0 -0
  940. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_tom2_epistemic_guard.py +0 -0
  941. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_tom2_exposure.py +0 -0
  942. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_tom2_kill_switch.py +0 -0
  943. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_tom2_level_coherence.py +0 -0
  944. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_tom2_leveled.py +0 -0
  945. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_tom2_levels.py +0 -0
  946. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_tom2_source_corrections.py +0 -0
  947. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_tom2_store.py +0 -0
  948. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_tom2_taint.py +0 -0
  949. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_tom2_wiring.py +0 -0
  950. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_tom_event_lineage.py +0 -0
  951. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_tom_extractor.py +0 -0
  952. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_tom_p8_arcs.py +0 -0
  953. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_tom_p8_boundary_corpus.py +0 -0
  954. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_tom_p8_fact_adapters.py +0 -0
  955. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_tom_p8_outbound_integration.py +0 -0
  956. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_tom_p8_recipient_audit.py +0 -0
  957. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_tom_p8_recipient_simulator.py +0 -0
  958. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_tom_p8_visibility.py +0 -0
  959. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_tom_p8_visibility_store.py +0 -0
  960. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_tom_source_lineage.py +0 -0
  961. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_tool_handlers_graph.py +0 -0
  962. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_tool_provenance.py +0 -0
  963. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_tool_surface.py +0 -0
  964. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_toolsmith.py +0 -0
  965. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_transport_ingress.py +0 -0
  966. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_transport_ingress_api.py +0 -0
  967. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_trust_configure.py +0 -0
  968. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_trust_scopes.py +0 -0
  969. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_trust_scopes_p2.py +0 -0
  970. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_turn_idempotency_ledger.py +0 -0
  971. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_turn_idempotency_v2.py +0 -0
  972. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_turn_ner_entities.py +0 -0
  973. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_turn_source_erasure.py +0 -0
  974. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_turn_source_evidence.py +0 -0
  975. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_turn_survivor_delivery.py +0 -0
  976. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_validation_sweep_fixes.py +0 -0
  977. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_vector_vacuum.py +0 -0
  978. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_wizard_autonomy.py +0 -0
  979. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_work_ancestry_projection.py +0 -0
  980. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_work_control_production_blockers.py +0 -0
  981. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_work_control_v1.py +0 -0
  982. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_work_orders.py +0 -0
  983. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_work_read_surface_authority.py +0 -0
  984. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_work_source_coverage.py +0 -0
  985. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_worker_handler_boundaries.py +0 -0
  986. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_worker_heartbeat_truth.py +0 -0
  987. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_worker_http_authority.py +0 -0
  988. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_worker_integration.py +0 -0
  989. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_worker_lifecycle_durability.py +0 -0
  990. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_workers_governor.py +0 -0
  991. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_workers_install.py +0 -0
  992. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_workspace.py +0 -0
  993. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_world_context_query.py +0 -0
  994. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_world_entity_reinforcement.py +0 -0
  995. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_world_llm_extract.py +0 -0
  996. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_world_model_prune.py +0 -0
  997. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_world_observations.py +0 -0
  998. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_world_populator.py +0 -0
  999. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_world_quality.py +0 -0
  1000. {apsimo-1.3.0 → apsimo-1.3.2}/tests/test_world_supervised.py +0 -0
@@ -1,6 +1,6 @@
1
1
  Metadata-Version: 2.4
2
2
  Name: apsimo
3
- Version: 1.3.0
3
+ Version: 1.3.2
4
4
  Summary: Persistent identity, memory and autonomy for AI agents
5
5
  License-Expression: MIT
6
6
  Requires-Python: >=3.11
@@ -28,7 +28,7 @@ Requires-Dist: pandas>=2.0; extra == "vectors"
28
28
  Requires-Dist: pyarrow>=15.0; extra == "vectors"
29
29
  Requires-Dist: lancedb>=0.10; extra == "vectors"
30
30
  Provides-Extra: hermes
31
- Requires-Dist: apsimo-hermes<2,>=1.3.0; extra == "hermes"
31
+ Requires-Dist: apsimo-hermes<2,>=1.3.2; extra == "hermes"
32
32
  Provides-Extra: mcp
33
33
  Requires-Dist: mcp[cli]<2,>=1.0; extra == "mcp"
34
34
  Provides-Extra: lancedb
@@ -961,6 +961,7 @@ def compatible_scopes(method: str, path: str) -> frozenset[str]:
961
961
  if (method.upper(), path) in WORK_READ_SURFACE_V1 or (method.upper(), path) in {
962
962
  ("POST", "/v1/host/learning/correction"),
963
963
  ("POST", "/v1/host/response-guard/check"),
964
+ ("GET", "/v1/host/contacts/resolve"),
964
965
  }:
965
966
  return _API_ACCESS_COMPATIBILITY
966
967
  return _NO_COMPATIBILITY_SCOPES
@@ -1105,6 +1106,7 @@ def required_scope(method: str, path: str) -> str:
1105
1106
  return "charter:approval-decide"
1106
1107
  return "api:access"
1107
1108
  exact = {
1109
+ ("GET", "/v1/host/contacts/resolve"): "turns:resolve-sender",
1108
1110
  ("GET", "/v1/host/admin/auth/status"): "auth:admin",
1109
1111
  ("GET", "/v1/host/contact-policy"): "contacts:policy-read",
1110
1112
  ("POST", "/v1/host/response-guard/check"): "response-guard:check",
@@ -3109,10 +3109,14 @@ async def context_assemble(
3109
3109
  _per = _comms_log.last_per_channel(contact_id)
3110
3110
  if _per:
3111
3111
  _chs = ", ".join(f"{ch} {str(v['ts'])[:10]}" for ch, v in _per.items())
3112
- _bits.append(f"Channels used: {_chs}.")
3112
+ _bits.append(f"Recorded channels: {_chs}.")
3113
3113
  _lo = _comms_log.last_outbound(contact_id)
3114
3114
  if _lo:
3115
- _bits.append(f"I last reached out via {_lo['channel']} on {str(_lo['ts'])[:10]}.")
3115
+ _bits.append(
3116
+ f"Last recorded outgoing message: {_lo['channel']} on {str(_lo['ts'])[:10]}. "
3117
+ "This summary includes conversation replies; it does not establish "
3118
+ "proactive outreach or delivery."
3119
+ )
3116
3120
  if _commitment_store is not None:
3117
3121
  try:
3118
3122
  _cm = _commitment_store.list(person_id=contact_id, status=["pending", "overdue"], limit=5)
@@ -3907,6 +3911,26 @@ async def forget_turn_sources(body: SourceForgetRequest, request: Request = None
3907
3911
  "host_reconciliation": "pending_until_each_host_connects"}
3908
3912
 
3909
3913
 
3914
+ async def _resolve_scoped_sender_contact(authority, gateway: str, address: str):
3915
+ """Read one verified handle within the credential's existing grants."""
3916
+ platform = gateway.strip().lower()
3917
+ if (not authority.authenticated or not authority.has_scope('turns:resolve-sender')
3918
+ or platform not in authority.turn_ingress_platforms):
3919
+ raise HTTPException(status_code=403, detail='Sender resolution is outside this transport grant')
3920
+ if _contacts_store is None:
3921
+ raise HTTPException(status_code=503, detail='Contact store not initialized')
3922
+ from apsimo.contacts.identity_links import normalized_handle
3923
+ try:
3924
+ normalized_gateway, normalized_address = normalized_handle(platform, address)
3925
+ contact = await _contacts_store.resolve_verified_handles(
3926
+ normalized_gateway, [normalized_address])
3927
+ except ValueError:
3928
+ raise HTTPException(status_code=400, detail='Invalid sender handle') from None
3929
+ if contact is None or contact.contact_id not in authority.person_ids:
3930
+ raise HTTPException(status_code=404, detail='No enrolled contact for that handle')
3931
+ return contact
3932
+
3933
+
3910
3934
  async def _ingest_turn_idempotently(
3911
3935
  body: TurnSyncRequest,
3912
3936
  request: Request | None = None,
@@ -3918,9 +3942,23 @@ async def _ingest_turn_idempotently(
3918
3942
  effects run. This is the server's final defense even when a host retries or
3919
3943
  two host integrations accidentally submit the same envelope.
3920
3944
  """
3945
+ resolved_sender_contact_id = None
3946
+ authority = request_authority(request)
3947
+ if (body.sender is not None and not authority.legacy and authority.authenticated
3948
+ and authority.has_scope('turns:resolve-sender')
3949
+ and not (authority.allow_unscoped_api and authority.has_scope('api:access'))
3950
+ and body.sender.platform.strip().lower() not in authority.attested_contact_platforms):
3951
+ # Static transport enrollment cannot inherit the viewer on a failed
3952
+ # lookup, or take the general resolver's canonical-ID/name fallbacks.
3953
+ # Validate before checkpoints, reservations or any source write.
3954
+ contact = await _resolve_scoped_sender_contact(
3955
+ authority, body.sender.platform, body.sender.user_id)
3956
+ resolved_sender_contact_id = contact.contact_id
3957
+ body.context.contact_id = contact.contact_id
3921
3958
  turn_id = (body.context.turn_id or "").strip()
3922
3959
  if not turn_id:
3923
- return await _process_turn_sync(body, request=request), "unkeyed"
3960
+ return await _process_turn_sync(body, request=request,
3961
+ resolved_sender_contact_id=resolved_sender_contact_id), "unkeyed"
3924
3962
  if len(turn_id) > 256:
3925
3963
  raise HTTPException(
3926
3964
  status_code=422,
@@ -4010,7 +4048,8 @@ async def _ingest_turn_idempotently(
4010
4048
  ), "in_progress"
4011
4049
 
4012
4050
  try:
4013
- result = await _process_turn_sync(body, request=request)
4051
+ result = await _process_turn_sync(body, request=request,
4052
+ resolved_sender_contact_id=resolved_sender_contact_id)
4014
4053
  except BaseException as exc:
4015
4054
  ledger.mark_ambiguous(turn_id, digest, exc)
4016
4055
  raise
@@ -4177,6 +4216,8 @@ async def turns_sync_v2(
4177
4216
  async def _process_turn_sync(
4178
4217
  body: TurnSyncRequest,
4179
4218
  request: Request | None = None,
4219
+ *,
4220
+ resolved_sender_contact_id: str | None = None,
4180
4221
  ) -> TurnSyncResponse:
4181
4222
  # Keep direct blocks for canonical source storage. All existing text-only
4182
4223
  # cognition consumers receive only explicit text, never repr(base64/URLs).
@@ -4221,7 +4262,11 @@ async def _process_turn_sync(
4221
4262
  from apsimo.identity.participants import (
4222
4263
  SYSTEM_CONTACT_ID, ParticipantResolver, is_machine_turn,
4223
4264
  )
4224
- if body.sender is not None and _contacts_store is not None:
4265
+ if resolved_sender_contact_id is not None:
4266
+ body.context.contact_id = resolved_sender_contact_id
4267
+ _resolution_method = "verified_handle"
4268
+ _resolved_human_sender = True
4269
+ elif body.sender is not None and _contacts_store is not None:
4225
4270
  _res = await ParticipantResolver(_contacts_store).resolve(
4226
4271
  platform=body.sender.platform,
4227
4272
  user_id=body.sender.user_id,
@@ -6282,7 +6327,7 @@ async def capture_introduction(body: ContactIntroRequest) -> ContactIntroRespons
6282
6327
 
6283
6328
 
6284
6329
  @router.get("/contacts/resolve", response_model=ContactResponse)
6285
- async def resolve_contact_by_handle(gateway: str, address: str, create: bool = False) -> ContactResponse:
6330
+ async def resolve_contact_by_handle(gateway: str, address: str, request: Request, create: bool = False) -> ContactResponse:
6286
6331
  """Resolve a contact from a messaging handle (v0.21.2).
6287
6332
 
6288
6333
  Registered BEFORE /contacts/{contact_id} so it isn't shadowed by the
@@ -6298,6 +6343,14 @@ async def resolve_contact_by_handle(gateway: str, address: str, create: bool = F
6298
6343
  if _contacts_store is None:
6299
6344
  raise HTTPException(status_code=404, detail="Contact store not initialized")
6300
6345
  try:
6346
+ authority = request_authority(request)
6347
+ if not authority.legacy and not (
6348
+ authority.allow_unscoped_api and authority.has_scope('api:access')):
6349
+ # Fresh native profiles resolve only explicitly enrolled accounts.
6350
+ # The memory provider's legacy create=true hint cannot provision a
6351
+ # contact or expand the credential's person/transport grants here.
6352
+ contact = await _resolve_scoped_sender_contact(authority, gateway, address)
6353
+ return ContactResponse(**contact.to_dict())
6301
6354
  # Normalized, cross-gateway phone-identity resolution (a number is one contact regardless of
6302
6355
  # the transport it arrived on). find_by_handle stays exact-match for dedup callers.
6303
6356
  contact = await _contacts_store.resolve_messaging_handle(gateway, address)
@@ -53,6 +53,7 @@ def main() -> None:
53
53
  # Backward compatibility
54
54
  init_p.add_argument("--host-framework", choices=["openclaw", "hermes", "claude-code", "codex", "crush", "standalone"], help="Host framework (deprecated: use --agent-harness or --mcp-harnesses)")
55
55
  init_p.add_argument("--contact-name", help="Contact name for this user")
56
+ init_p.add_argument("--owner-handle", action="append", metavar="CHANNEL=SENDER_ID", help="Enroll your exact Hermes sender ID when creating a private instance; repeat for each account")
56
57
  init_p.add_argument("--bind", default="127.0.0.1", help="Sidecar bind address (0.0.0.0 for all interfaces)")
57
58
  init_p.add_argument("--port", type=int, default=7777, help="Sidecar port")
58
59
  init_p.add_argument("--tier", type=int, choices=range(0, 8), metavar="TIER", help="Embedding tier (0-7)")
@@ -70,6 +70,21 @@ class RecallSelector:
70
70
  seen.add(key)
71
71
  unique.append(row)
72
72
  quotations = unique
73
+ def repeats_request(row):
74
+ # An exact repeat contributes no independent answer evidence. Keep
75
+ # it available as supplementary context, without classifying other
76
+ # questions, promoting speakers or changing its source bytes.
77
+ return bool(isinstance(query, str) and query.strip()
78
+ and row.get("kind") == "source_quote"
79
+ and row.get("epistemic_state") == "quotation"
80
+ and row.get("scope") == "person" and row.get("contact_id")
81
+ and row.get("role") in {"user", "assistant"}
82
+ and isinstance(row.get("content"), str)
83
+ and row["content"].strip() == query.strip()
84
+ and not any(row.get(key) for key in (
85
+ "atomic_evidence", "validity_status", "procedure_context",
86
+ "source_context", "_annotation_ids")))
87
+
73
88
  # Media is an independent candidate producer. Appending its first hit
74
89
  # after every text hit can exclude it from the bounded reranker before
75
90
  # relevance is assessed. Fuse its rank independently; it still shares
@@ -82,10 +97,17 @@ class RecallSelector:
82
97
  candidates = fuse_candidates(
83
98
  beliefs, text, limit=len(beliefs) + len(quotations),
84
99
  confidence_weighting=False, additional=(media,))
100
+ # Do this before bounded reranking, so repeated requests do not crowd
101
+ # out answer-bearing candidates before their relevance can be judged.
102
+ candidates.sort(key=repeats_request)
85
103
  ranked = await self.rerank(
86
104
  query, candidates, limit, confidence_weighting=False,
87
105
  candidate_limit=max(1, 4 * limit))
88
106
  ranked.sort(key=lambda row: row.get("relevance", 0), reverse=True)
107
+ # A semantic reranker can score the identical question highest. Preserve
108
+ # its abstention decisions and substantive order, then place only exact
109
+ # unqualified request repeats after the remaining evidence.
110
+ ranked.sort(key=repeats_request)
89
111
  return pack_memory_context(ranked, limit=limit, max_chars=max_chars)
90
112
 
91
113
  async def rerank(
@@ -1947,11 +1947,11 @@ def run_init(root_dir: str | None = None, args=None) -> int:
1947
1947
  root_dir: Root directory for config files
1948
1948
  args: Parsed argparse Namespace for non-interactive mode
1949
1949
  """
1950
- if (getattr(args, 'preferences_only', False) or getattr(args, 'preview', False)
1950
+ if (getattr(args, 'owner_handle', None) or getattr(args, 'preferences_only', False) or getattr(args, 'preview', False)
1951
1951
  or getattr(args, 'whatsapp_read_receipts', None) is not None):
1952
1952
  if (getattr(args, 'no_harness', False) or getattr(args, 'mcp_harnesses', None)
1953
1953
  or getattr(args, 'host_framework', None) not in (None, 'hermes')):
1954
- print('Hermes profile preferences cannot be combined with another harness setup.')
1954
+ print('Hermes profile options cannot be combined with another harness setup.')
1955
1955
  return 1
1956
1956
  from apsimo.setup_hermes import run
1957
1957
  return run(root_dir, args)
@@ -58,6 +58,33 @@ def _json(value):
58
58
  return json.dumps(value, indent=2, ensure_ascii=False) + '\n'
59
59
 
60
60
 
61
+ def _owner_handles(args, ask, noninteractive):
62
+ """Local enrollment binds exact accounts; it does not configure channels."""
63
+ from .contacts.identity_links import normalized_handle
64
+ supplied = getattr(args, 'owner_handle', None)
65
+ values = list(supplied or [])
66
+ if not supplied and not noninteractive:
67
+ print('Optionally identify your own messaging accounts using Hermes sender IDs, not display names or group IDs.')
68
+ print('For example: telegram=123456789. Hermes continues to configure and authenticate each channel.')
69
+ while value := ask('Your account CHANNEL=SENDER_ID (blank to finish)'):
70
+ values.append(value)
71
+ handles, platforms = [], set()
72
+ for value in values:
73
+ platform, separator, address = value.partition('=')
74
+ platform, address = platform.strip().lower(), address.strip()
75
+ if (not separator or not re.fullmatch(r'[a-z0-9][a-z0-9_.-]{0,63}', platform)
76
+ or platform in {'cli', 'internal', 'system', 'background_review', 'colony_task'}
77
+ or any(ord(char) < 32 or ord(char) == 127 for char in address)):
78
+ raise ValueError('--owner-handle requires CHANNEL=SENDER_ID for your authenticated messaging account')
79
+ gateway, address = normalized_handle(platform, address)
80
+ if not address or address == '+':
81
+ raise ValueError('--owner-handle requires a nonempty sender ID')
82
+ if (gateway, address) not in handles:
83
+ handles.append((gateway, address))
84
+ platforms.add(platform)
85
+ return handles, sorted(platforms)
86
+
87
+
61
88
  def _receipt_preference(config, choice):
62
89
  """Project one native shared key, respecting Hermes' existing YAML layouts.
63
90
 
@@ -563,7 +590,7 @@ def run(root_dir=None, args=None):
563
590
  if root_dir or any(getattr(args, name, None) for name in (
564
591
  'start', 'refresh_adapter', 'replace_memory_provider', 'local_work',
565
592
  'native_goals', 'native_reviews', 'model_url', 'model', 'adapter_wheel', 'agent_name',
566
- 'agent_values', 'timezone', 'quiet_hours', 'contact_name', 'encrypt',
593
+ 'agent_values', 'timezone', 'quiet_hours', 'contact_name', 'owner_handle', 'encrypt',
567
594
  'passphrase', 'claim_genesis', 'mcp_harnesses', 'no_harness')) or (
568
595
  getattr(args, 'host_framework', None) not in (None, 'hermes')):
569
596
  raise ValueError('--preferences-only cannot be combined with instance or setup options')
@@ -593,6 +620,8 @@ def run(root_dir=None, args=None):
593
620
  if any((home/name).exists() for name in ('colony-memory.json', 'apsimo-memory.json')):
594
621
  raise ValueError('Existing native Apsimo settings need an explicit migration; select a new home')
595
622
  if (state/'instance.json').exists():
623
+ if getattr(args, 'owner_handle', None):
624
+ raise ValueError('--owner-handle is for a new private instance; existing owner bindings are retained')
596
625
  manifest = json.loads((state/'instance.json').read_text())
597
626
  if manifest.get('hermes_home') != str(home):
598
627
  raise ValueError('This instance belongs to another Hermes home')
@@ -652,6 +681,7 @@ def run(root_dir=None, args=None):
652
681
  _preflight_outbox(home, resources)
653
682
  binding = _adapter_binding(python, resources)
654
683
  owner_name = ask('Your name', getattr(args, 'contact_name', None) or os.environ.get('USER', 'Owner'), True)
684
+ owner_handles, owner_platforms = _owner_handles(args, ask, noninteractive)
655
685
  agent_name = ask('Agent name', getattr(args, 'agent_name', None) or 'Assistant', True)
656
686
  agent_preferences = _agent_preferences(ask, args, config)
657
687
  endpoint = _endpoint(ask('Local model API root', getattr(args, 'model_url', None), True))
@@ -726,7 +756,11 @@ def run(root_dir=None, args=None):
726
756
  store = SQLiteContactStore(ContactsConfig(sqlite_path=str(staged/'contacts.db')))
727
757
  await store.connect()
728
758
  try:
729
- return await setup.build_owner_contact(store, owner_name)
759
+ contact_id = await setup.build_owner_contact(store, owner_name)
760
+ for index, (gateway, address) in enumerate(owner_handles):
761
+ await store.add_handle(contact_id, gateway, address,
762
+ is_primary=index == 0, source='wizard', verified=True)
763
+ return contact_id
730
764
  finally:
731
765
  await store.close()
732
766
  owner_id = asyncio.run(owner())
@@ -750,9 +784,11 @@ def run(root_dir=None, args=None):
750
784
  values = {('APSIMO_'+key[7:] if key.startswith('COLONY_') else key):value for key,value in values.items()}
751
785
  _private_write(staged/'.env', _native_environment(None, values))
752
786
  principal = {'principal': 'hermes-local', 'status': 'active', 'viewer_person_id': owner_id,
753
- 'audiences': ['viewer'], 'allow_unscoped_api': False, 'turn_ingress_platforms': ['cli'],
787
+ 'audiences': ['viewer'], 'allow_unscoped_api': False, 'turn_ingress_platforms': ['cli', *owner_platforms],
754
788
  'scopes': ['context:read', 'memory:read', 'memory:search', 'memory:write', 'turns:write'],
755
789
  'credentials': [{'id': 'initial', 'secret': key, 'status': 'active'}]}
790
+ if owner_handles:
791
+ principal['scopes'].append('turns:resolve-sender')
756
792
  _private_write(staged/'api-keyring.json', _json({'version': 1, 'principals': [principal]}))
757
793
  model_configuration = {'provider': 'local', 'baseUrl': endpoint,
758
794
  'apiKey': model_key, 'localHosts': local_hosts,
@@ -857,6 +893,8 @@ def run(root_dir=None, args=None):
857
893
  print(f'Private agent configured in {home}; state in {state}.')
858
894
  print('Adapter loading: ' + binding['mode'] + ' (canonical artifact bytes verified).')
859
895
  print('Canonical memory capture and recollection are enabled for new Hermes sessions.')
896
+ if owner_handles:
897
+ print('Owner accounts enrolled for: ' + ', '.join(owner_platforms) + '. Channel configuration and delivery still belong to Hermes.')
860
898
  print('Hermes hook output spill allowance is at least 65536 characters or already disabled; retrieval budgets are unchanged.')
861
899
  print('Source memory, temporal claims, contacts, commitments and self state persist without a graph.')
862
900
  print('Graph/vector recall and consequential background work are optional and currently disabled.')
@@ -1,6 +1,6 @@
1
1
  Metadata-Version: 2.4
2
2
  Name: apsimo
3
- Version: 1.3.0
3
+ Version: 1.3.2
4
4
  Summary: Persistent identity, memory and autonomy for AI agents
5
5
  License-Expression: MIT
6
6
  Requires-Python: >=3.11
@@ -28,7 +28,7 @@ Requires-Dist: pandas>=2.0; extra == "vectors"
28
28
  Requires-Dist: pyarrow>=15.0; extra == "vectors"
29
29
  Requires-Dist: lancedb>=0.10; extra == "vectors"
30
30
  Provides-Extra: hermes
31
- Requires-Dist: apsimo-hermes<2,>=1.3.0; extra == "hermes"
31
+ Requires-Dist: apsimo-hermes<2,>=1.3.2; extra == "hermes"
32
32
  Provides-Extra: mcp
33
33
  Requires-Dist: mcp[cli]<2,>=1.0; extra == "mcp"
34
34
  Provides-Extra: lancedb
@@ -707,6 +707,7 @@ tests/test_doctor.py
707
707
  tests/test_document_memory_guard.py
708
708
  tests/test_duckduckgo_provider.py
709
709
  tests/test_embedding_generations.py
710
+ tests/test_enrolled_sender_turns.py
710
711
  tests/test_ensure_channel_id.py
711
712
  tests/test_env_risk.py
712
713
  tests/test_event_broadcasts.py
@@ -832,6 +833,7 @@ tests/test_reachout_policy.py
832
833
  tests/test_recall_hybrid.py
833
834
  tests/test_recall_person_boost.py
834
835
  tests/test_recall_ranking.py
836
+ tests/test_recall_request_repetition.py
835
837
  tests/test_recall_rerank.py
836
838
  tests/test_recall_source_presentation.py
837
839
  tests/test_recall_unified_context.py
@@ -860,6 +862,7 @@ tests/test_router_tiers.py
860
862
  tests/test_runtime_model_observations.py
861
863
  tests/test_sandbox.py
862
864
  tests/test_scoped_api_authority.py
865
+ tests/test_scoped_contact_resolution.py
863
866
  tests/test_secondary_review_contract.py
864
867
  tests/test_seed_retirement.py
865
868
  tests/test_selected_autonomy.py
@@ -35,7 +35,7 @@ beautifulsoup4>=4.12
35
35
  neo4j>=5.18
36
36
 
37
37
  [hermes]
38
- apsimo-hermes<2,>=1.3.0
38
+ apsimo-hermes<2,>=1.3.2
39
39
 
40
40
  [lancedb]
41
41
  lancedb>=0.6
@@ -4,7 +4,7 @@ build-backend = "setuptools.build_meta"
4
4
 
5
5
  [project]
6
6
  name = "apsimo"
7
- version = "1.3.0"
7
+ version = "1.3.2"
8
8
  description = "Persistent identity, memory and autonomy for AI agents"
9
9
  readme = "README.md"
10
10
  license = "MIT"
@@ -29,7 +29,7 @@ dependencies = [
29
29
  graph = ["neo4j>=5.18"]
30
30
  neo4j = ["neo4j>=5.18"]
31
31
  vectors = ["sentence-transformers>=3.0", "pandas>=2.0", "pyarrow>=15.0", "lancedb>=0.10"]
32
- hermes = ["apsimo-hermes>=1.3.0,<2"]
32
+ hermes = ["apsimo-hermes>=1.3.2,<2"]
33
33
  mcp = ["mcp[cli]>=1.0,<2"]
34
34
  lancedb = ["lancedb>=0.6", "pyarrow>=14.0", "pandas>=2.0"]
35
35
  postgres = ["asyncpg>=0.29"]
@@ -0,0 +1,94 @@
1
+ """Fresh transport grants admit only enrolled senders before source storage."""
2
+ import asyncio
3
+ import json
4
+ import sqlite3
5
+ from pathlib import Path
6
+
7
+ from fastapi import FastAPI
8
+ import httpx
9
+ import pytest
10
+
11
+ from apsimo import setup
12
+ from apsimo.api.middleware import ApiKeyMiddleware
13
+ from apsimo.api.routers import host
14
+ from apsimo.contacts.config import ContactsConfig
15
+ from apsimo.contacts.store import SQLiteContactStore
16
+ from apsimo.turns import TurnIdempotencyLedger
17
+ from test_native_setup import args, isolated_platform_environment # Shared isolated wizard fixtures.
18
+
19
+
20
+ @pytest.mark.parametrize('version', ['v1', 'v2'])
21
+ def test_enrolled_sender_checked_before_turn_reservation(args, monkeypatch, version):
22
+ args.owner_handle = ['telegram=123456789']
23
+ assert setup.run_init(None, args) == 0
24
+ state = Path(args.hermes_home)/'apsimo'
25
+ principal = json.loads((state/'api-keyring.json').read_text())['principals'][0]
26
+ owner = principal['viewer_person_id']
27
+ monkeypatch.setenv('COLONY_STATE_DIR', str(state))
28
+ monkeypatch.setenv('COLONY_IDENTITY_SHADOW_CONTACTS', 'false')
29
+ for name in ('_graph', '_presence_store', '_context_provenance', '_telemetry', '_p8_runtime'):
30
+ monkeypatch.setattr(host, name, None)
31
+ ledger = TurnIdempotencyLedger(state/'turn-idempotency.db')
32
+
33
+ async def exercise():
34
+ store = SQLiteContactStore(ContactsConfig(sqlite_path=str(state/'contacts.db')))
35
+ await store.connect()
36
+ monkeypatch.setattr(host, '_contacts_store', store)
37
+ try:
38
+ guest = await store.create(display_name='Other account')
39
+ await store.add_handle(guest.contact_id, 'telegram', '987654321', verified=True)
40
+ await store.add_handle(owner, 'telegram', 'unverified', verified=False)
41
+ before_contacts = await store.list()
42
+ app = FastAPI()
43
+ app.include_router(host.router)
44
+ app.include_router(host.v2_router)
45
+ app.add_middleware(ApiKeyMiddleware, keyring_path=str(state/'api-keyring.json'))
46
+ headers = {'Authorization': 'Bearer ' + principal['credentials'][0]['secret']}
47
+
48
+ async def send(client, turn_id, platform, sender):
49
+ body = {'identity': {'host_id': 'fixture'},
50
+ 'context': {'contact_id': owner if sender is None else 'body-selected-person',
51
+ 'session_id': 'enrolled-source',
52
+ 'channel_id': platform + ':fixture', 'turn_id': turn_id}}
53
+ if sender is not None:
54
+ body['sender'] = {'platform': platform, 'user_id': sender}
55
+ message = {'role': 'user', 'content': 'The archive reference is violet.'}
56
+ body.update(user_message=message, source_only=True)
57
+ if version == 'v1':
58
+ return await client.post('/v1/host/turns/sync', json=body)
59
+ return await client.put('/v2/host/turns/' + turn_id, json=body)
60
+
61
+ async with httpx.AsyncClient(transport=httpx.ASGITransport(app=app),
62
+ base_url='http://fixture', headers=headers) as client:
63
+ denied = [('unknown', 'telegram', 'unknown', 404),
64
+ ('canonical-id', 'telegram', owner, 404),
65
+ ('other-person', 'telegram', '987654321', 404),
66
+ ('unverified', 'telegram', 'unverified', 404),
67
+ ('wrong-channel', 'whatsapp', '123456789', 403)]
68
+ for turn_id, platform, sender, code in denied:
69
+ response = await send(client, turn_id, platform, sender)
70
+ assert response.status_code == code, (turn_id, response.text)
71
+ with sqlite3.connect(ledger.db_path) as db:
72
+ assert db.execute('SELECT count(*) FROM turn_sources').fetchone()[0] == 0
73
+ assert db.execute('SELECT count(*) FROM turn_ingestion').fetchone()[0] == 0
74
+ assert await store.list() == before_contacts
75
+ response = await send(client, 'known-owner', 'telegram', '123456789')
76
+ assert response.status_code == (200 if version == 'v1' else 201), response.text
77
+ assert response.json()['source_recorded'] is True
78
+ replay = await send(client, 'known-owner', 'telegram', '123456789')
79
+ assert replay.status_code == 200 and replay.json()['source_recorded'] is True
80
+ with sqlite3.connect(ledger.db_path) as db:
81
+ rows = db.execute('SELECT contact_id,messages_json FROM turn_sources').fetchall()
82
+ assert len(rows) == 1 and rows[0][0] == owner
83
+ assert json.loads(rows[0][1])[0]['content'] == 'The archive reference is violet.'
84
+ # Native CLI has no human sender ID. Its exact viewer binding
85
+ # still permits capture without inventing a transport handle.
86
+ response = await send(client, 'senderless-cli', 'cli', None)
87
+ assert response.status_code == (200 if version == 'v1' else 201), response.text
88
+ assert response.json()['source_recorded'] is True
89
+ with sqlite3.connect(ledger.db_path) as db:
90
+ assert db.execute('SELECT contact_id FROM turn_sources WHERE turn_id=?',
91
+ ('senderless-cli',)).fetchone() == (owner,)
92
+ finally:
93
+ await store.close()
94
+ asyncio.run(exercise())
@@ -1197,7 +1197,8 @@ def test_colony_client_uses_one_absolute_deadline_across_http_phases():
1197
1197
  assert elapsed < 0.20
1198
1198
 
1199
1199
 
1200
- def test_colony_client_absolute_deadline_transport_accepts_exact_put():
1200
+ @pytest.mark.parametrize('channel_id', ['', 'email:thread-739'])
1201
+ def test_colony_client_absolute_deadline_transport_accepts_exact_put(channel_id):
1201
1202
  module = _load_client("colony_hermes_client_deadline_success_test")
1202
1203
  listener = socket.socket(socket.AF_INET, socket.SOCK_STREAM)
1203
1204
  listener.setsockopt(socket.SOL_SOCKET, socket.SO_REUSEADDR, 1)
@@ -1242,6 +1243,7 @@ def test_colony_client_absolute_deadline_transport_accepts_exact_put():
1242
1243
  session_id="session-1",
1243
1244
  contact_id="cid-owner",
1244
1245
  turn_id="turn/one",
1246
+ channel_id=channel_id,
1245
1247
  timeout_seconds=0.20,
1246
1248
  ) is True
1247
1249
  finally:
@@ -1260,6 +1262,7 @@ def test_colony_client_absolute_deadline_transport_accepts_exact_put():
1260
1262
  "contact_id": "cid-owner",
1261
1263
  "session_id": "session-1",
1262
1264
  "turn_id": "turn/one",
1265
+ **({"channel_id": channel_id} if channel_id else {}),
1263
1266
  },
1264
1267
  "identity": {"host_id": "hermes"},
1265
1268
  }
@@ -1,5 +1,6 @@
1
1
  """Guided native init preserves profiles and creates one private scoped instance."""
2
2
  import json
3
+ import asyncio
3
4
  import os
4
5
  import socket
5
6
  from pathlib import Path
@@ -152,6 +153,98 @@ def test_new_private_instance_uses_canonical_resources_and_scoped_authority(args
152
153
  assert before == ((home/'config.yaml').read_bytes(), (state/'api-keyring.json').read_bytes())
153
154
 
154
155
 
156
+ def test_enrolled_owner_accounts_resolve_through_the_generated_scoped_api(args, monkeypatch):
157
+ from fastapi import FastAPI
158
+ from apsimo.api.middleware import ApiKeyMiddleware
159
+ from apsimo.api.routers import host
160
+ from apsimo.contacts.config import ContactsConfig
161
+ from apsimo.contacts.store import SQLiteContactStore
162
+
163
+ home = Path(args.hermes_home)
164
+ home.mkdir(mode=0o700)
165
+ channels = {'telegram': {'enabled': True, 'allowed_users': ['123456789']}}
166
+ (home/'config.yaml').write_text(yaml.safe_dump(channels))
167
+ args.owner_handle = ['telegram=123456789', 'sms=+1 (202) 555-0198', 'telegram=123456789']
168
+ assert setup.run_init(None, args) == 0
169
+ state = home/'apsimo'
170
+ config = yaml.safe_load((home/'config.yaml').read_text())
171
+ assert config['telegram'] == channels['telegram']
172
+ assert config['plugins']['apsimo']['attested_system_platforms'] == ['cli']
173
+ principal = json.loads((state/'api-keyring.json').read_text())['principals'][0]
174
+ assert principal['turn_ingress_platforms'] == ['cli', 'sms', 'telegram']
175
+ assert 'turns:resolve-sender' in principal['scopes']
176
+ assert principal['allow_unscoped_api'] is False
177
+ assert 'api:access' not in principal['scopes']
178
+ owner_id = principal['viewer_person_id']
179
+
180
+ async def exercise():
181
+ store = SQLiteContactStore(ContactsConfig(sqlite_path=str(state/'contacts.db')))
182
+ await store.connect()
183
+ monkeypatch.setattr(host, '_contacts_store', store)
184
+ try:
185
+ handles = await store.get_handles(owner_id)
186
+ assert len(handles) == 2 and all(row.verified and row.source == 'wizard' for row in handles)
187
+ guest = await store.create(display_name='Other person')
188
+ await store.add_handle(guest.contact_id, 'telegram', '987654321', verified=True)
189
+ await store.add_handle(owner_id, 'telegram', '111111111', verified=False)
190
+ before = (await store.list(), await store.get_handles(owner_id))
191
+ app = FastAPI()
192
+ app.add_middleware(ApiKeyMiddleware, keyring_path=str(state/'api-keyring.json'))
193
+ app.include_router(host.router)
194
+ headers = {'Authorization': 'Bearer ' + principal['credentials'][0]['secret']}
195
+ async with httpx.AsyncClient(transport=httpx.ASGITransport(app=app), base_url='http://setup') as client:
196
+ for gateway, address, create, status in [
197
+ ('telegram', '123456789', False, 200),
198
+ ('telegram', '123456789', True, 200), # Memory provider's existing read call.
199
+ ('sms', '+1 (202) 555-0198', True, 200),
200
+ ('telegram', 'unknown', True, 404),
201
+ ('telegram', '987654321', False, 404),
202
+ ('telegram', '111111111', False, 404),
203
+ ('telegram', '+12025550198', False, 404), # No inferred cross-channel authority.
204
+ ('whatsapp', '123456789', False, 403),
205
+ ]:
206
+ response = await client.get('/v1/host/contacts/resolve', headers=headers,
207
+ params={'gateway': gateway, 'address': address, 'create': str(create).lower()})
208
+ assert response.status_code == status, response.text
209
+ if status == 200:
210
+ assert response.json()['contact_id'] == owner_id
211
+ denied = await client.get('/v1/host/contacts/resolve',
212
+ params={'gateway': 'telegram', 'address': '123456789'})
213
+ assert denied.status_code == 401
214
+ assert before == (await store.list(), await store.get_handles(owner_id))
215
+ finally:
216
+ await store.close()
217
+ asyncio.run(exercise())
218
+
219
+ retained = ((state/'api-keyring.json').read_bytes(), (home/'config.yaml').read_bytes(),
220
+ (state/'contacts.db').read_bytes())
221
+ assert setup.run_init(None, args) == 1 # Enrollment arguments are never silently ignored on rerun.
222
+ assert retained == ((state/'api-keyring.json').read_bytes(), (home/'config.yaml').read_bytes(),
223
+ (state/'contacts.db').read_bytes())
224
+ args.owner_handle = None
225
+ assert setup.run_init(None, args) == 0
226
+ assert retained == ((state/'api-keyring.json').read_bytes(), (home/'config.yaml').read_bytes(),
227
+ (state/'contacts.db').read_bytes())
228
+
229
+
230
+ @pytest.mark.parametrize('handle', ['telegram', '=123', 'telegram=', 'sms=letters',
231
+ 'cli=owner', 'telegram=abc\n123', 'telegram=' + 'x' * 513])
232
+ def test_bad_owner_enrollment_stops_before_probe_or_state(args, handle, monkeypatch):
233
+ args.owner_handle = [handle]
234
+ probe = Mock(side_effect=AssertionError('Invalid enrollment must precede model probing'))
235
+ monkeypatch.setattr(setup_hermes, '_verify_local_endpoint', probe)
236
+ assert setup.run_init(None, args) == 1
237
+ probe.assert_not_called()
238
+ assert not Path(args.hermes_home).exists()
239
+
240
+
241
+ def test_guided_owner_enrollment_uses_the_same_normalized_bindings():
242
+ answers = iter(['email=Owner@Example.org', 'rcs=+1 (202) 555-0198', ''])
243
+ handles, platforms = setup_hermes._owner_handles(SimpleNamespace(), lambda *a: next(answers), False)
244
+ assert handles == [('email', 'owner@example.org'), ('sms', '+12025550198')]
245
+ assert platforms == ['email', 'rcs']
246
+
247
+
155
248
  def test_writable_ancestor_stops_before_endpoint_probe_or_attachment(args, tmp_path, monkeypatch, capsys):
156
249
  shared = tmp_path/'shared-parent'
157
250
  shared.mkdir(mode=0o775)