mainsequence 4.4.15__tar.gz → 4.4.18__tar.gz

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (161) hide show
  1. {mainsequence-4.4.15/mainsequence.egg-info → mainsequence-4.4.18}/PKG-INFO +1 -1
  2. {mainsequence-4.4.15 → mainsequence-4.4.18}/agent_scaffold/skills/a2a_communication/SKILL.md +4 -0
  3. {mainsequence-4.4.15 → mainsequence-4.4.18}/agent_scaffold/skills/data_access/exploration/SKILL.md +68 -8
  4. {mainsequence-4.4.15 → mainsequence-4.4.18}/mainsequence/cli/api.py +75 -210
  5. {mainsequence-4.4.15 → mainsequence-4.4.18}/mainsequence/cli/cli.py +80 -756
  6. {mainsequence-4.4.15 → mainsequence-4.4.18}/mainsequence/cli/config.py +42 -5
  7. {mainsequence-4.4.15 → mainsequence-4.4.18}/mainsequence/client/agent_runtime_models.py +255 -76
  8. {mainsequence-4.4.15 → mainsequence-4.4.18}/mainsequence/client/metatables/core.py +26 -14
  9. {mainsequence-4.4.15 → mainsequence-4.4.18}/mainsequence/meta_tables/compiled_sql/v1.py +22 -3
  10. {mainsequence-4.4.15 → mainsequence-4.4.18}/mainsequence/meta_tables/data_nodes/persist_managers.py +4 -2
  11. {mainsequence-4.4.15 → mainsequence-4.4.18/mainsequence.egg-info}/PKG-INFO +1 -1
  12. {mainsequence-4.4.15 → mainsequence-4.4.18}/pyproject.toml +1 -1
  13. {mainsequence-4.4.15 → mainsequence-4.4.18}/tests/test_cli.py +279 -569
  14. {mainsequence-4.4.15 → mainsequence-4.4.18}/tests/test_filter_normalization.py +337 -33
  15. {mainsequence-4.4.15 → mainsequence-4.4.18}/tests/test_meta_tables_client_models.py +41 -0
  16. {mainsequence-4.4.15 → mainsequence-4.4.18}/tests/test_run_configuration.py +37 -0
  17. {mainsequence-4.4.15 → mainsequence-4.4.18}/LICENSE +0 -0
  18. {mainsequence-4.4.15 → mainsequence-4.4.18}/README.md +0 -0
  19. {mainsequence-4.4.15 → mainsequence-4.4.18}/agent_scaffold/AGENTS.md +0 -0
  20. {mainsequence-4.4.15 → mainsequence-4.4.18}/agent_scaffold/skills/application_surfaces/api_surfaces/SKILL.md +0 -0
  21. {mainsequence-4.4.15 → mainsequence-4.4.18}/agent_scaffold/skills/command_center/adapter_from_api/SKILL.md +0 -0
  22. {mainsequence-4.4.15 → mainsequence-4.4.18}/agent_scaffold/skills/command_center/api_mock_prototyping/SKILL.md +0 -0
  23. {mainsequence-4.4.15 → mainsequence-4.4.18}/agent_scaffold/skills/command_center/connections/SKILL.md +0 -0
  24. {mainsequence-4.4.15 → mainsequence-4.4.18}/agent_scaffold/skills/command_center/widgets/app_components/SKILL.md +0 -0
  25. {mainsequence-4.4.15 → mainsequence-4.4.18}/agent_scaffold/skills/command_center/widgets/tables/SKILL.md +0 -0
  26. {mainsequence-4.4.15 → mainsequence-4.4.18}/agent_scaffold/skills/command_center/widgets/tabular_transform/SKILL.md +0 -0
  27. {mainsequence-4.4.15 → mainsequence-4.4.18}/agent_scaffold/skills/command_center/workspace_analysis/SKILL.md +0 -0
  28. {mainsequence-4.4.15 → mainsequence-4.4.18}/agent_scaffold/skills/command_center/workspace_builder/SKILL.md +0 -0
  29. {mainsequence-4.4.15 → mainsequence-4.4.18}/agent_scaffold/skills/command_center/workspace_design/SKILL.md +0 -0
  30. {mainsequence-4.4.15 → mainsequence-4.4.18}/agent_scaffold/skills/dashboards/streamlit/SKILL.md +0 -0
  31. {mainsequence-4.4.15 → mainsequence-4.4.18}/agent_scaffold/skills/data_publishing/data_nodes/SKILL.md +0 -0
  32. {mainsequence-4.4.15 → mainsequence-4.4.18}/agent_scaffold/skills/data_publishing/meta_table_migrations/SKILL.md +0 -0
  33. {mainsequence-4.4.15 → mainsequence-4.4.18}/agent_scaffold/skills/data_publishing/meta_tables/SKILL.md +0 -0
  34. {mainsequence-4.4.15 → mainsequence-4.4.18}/agent_scaffold/skills/maintenance/bug_auditor/SKILL.md +0 -0
  35. {mainsequence-4.4.15 → mainsequence-4.4.18}/agent_scaffold/skills/ms-markets/SKILL.md +0 -0
  36. {mainsequence-4.4.15 → mainsequence-4.4.18}/agent_scaffold/skills/platform_operations/access_control_and_sharing/SKILL.md +0 -0
  37. {mainsequence-4.4.15 → mainsequence-4.4.18}/agent_scaffold/skills/platform_operations/orchestration_and_releases/SKILL.md +0 -0
  38. {mainsequence-4.4.15 → mainsequence-4.4.18}/agent_scaffold/skills/project_builder/SKILL.md +0 -0
  39. {mainsequence-4.4.15 → mainsequence-4.4.18}/agent_scaffold/skills/project_to_agent/SKILL.md +0 -0
  40. {mainsequence-4.4.15 → mainsequence-4.4.18}/mainsequence/__init__.py +0 -0
  41. {mainsequence-4.4.15 → mainsequence-4.4.18}/mainsequence/__main__.py +0 -0
  42. {mainsequence-4.4.15 → mainsequence-4.4.18}/mainsequence/bootstrap.py +0 -0
  43. {mainsequence-4.4.15 → mainsequence-4.4.18}/mainsequence/cli/__init__.py +0 -0
  44. {mainsequence-4.4.15 → mainsequence-4.4.18}/mainsequence/cli/browser_auth.py +0 -0
  45. {mainsequence-4.4.15 → mainsequence-4.4.18}/mainsequence/cli/docker_utils.py +0 -0
  46. {mainsequence-4.4.15 → mainsequence-4.4.18}/mainsequence/cli/doctor.py +0 -0
  47. {mainsequence-4.4.15 → mainsequence-4.4.18}/mainsequence/cli/local_ops.py +0 -0
  48. {mainsequence-4.4.15 → mainsequence-4.4.18}/mainsequence/cli/migrations.py +0 -0
  49. {mainsequence-4.4.15 → mainsequence-4.4.18}/mainsequence/cli/model_filters.py +0 -0
  50. {mainsequence-4.4.15 → mainsequence-4.4.18}/mainsequence/cli/project_status.py +0 -0
  51. {mainsequence-4.4.15 → mainsequence-4.4.18}/mainsequence/cli/pydantic_cli.py +0 -0
  52. {mainsequence-4.4.15 → mainsequence-4.4.18}/mainsequence/cli/sdk_utils.py +0 -0
  53. {mainsequence-4.4.15 → mainsequence-4.4.18}/mainsequence/cli/ssh_utils.py +0 -0
  54. {mainsequence-4.4.15 → mainsequence-4.4.18}/mainsequence/cli/ui.py +0 -0
  55. {mainsequence-4.4.15 → mainsequence-4.4.18}/mainsequence/client/__init__.py +0 -0
  56. {mainsequence-4.4.15 → mainsequence-4.4.18}/mainsequence/client/base.py +0 -0
  57. {mainsequence-4.4.15 → mainsequence-4.4.18}/mainsequence/client/client.py +0 -0
  58. {mainsequence-4.4.15 → mainsequence-4.4.18}/mainsequence/client/command_center/__init__.py +0 -0
  59. {mainsequence-4.4.15 → mainsequence-4.4.18}/mainsequence/client/command_center/app_component.py +0 -0
  60. {mainsequence-4.4.15 → mainsequence-4.4.18}/mainsequence/client/command_center/connections.py +0 -0
  61. {mainsequence-4.4.15 → mainsequence-4.4.18}/mainsequence/client/command_center/contracts/__init__.py +0 -0
  62. {mainsequence-4.4.15 → mainsequence-4.4.18}/mainsequence/client/command_center/contracts/adapter_from_api.py +0 -0
  63. {mainsequence-4.4.15 → mainsequence-4.4.18}/mainsequence/client/command_center/contracts/response_mapping.py +0 -0
  64. {mainsequence-4.4.15 → mainsequence-4.4.18}/mainsequence/client/command_center/contracts/table_visuals.py +0 -0
  65. {mainsequence-4.4.15 → mainsequence-4.4.18}/mainsequence/client/command_center/contracts/tabular.py +0 -0
  66. {mainsequence-4.4.15 → mainsequence-4.4.18}/mainsequence/client/command_center/contracts/ui.py +0 -0
  67. {mainsequence-4.4.15 → mainsequence-4.4.18}/mainsequence/client/command_center/data_models.py +0 -0
  68. {mainsequence-4.4.15 → mainsequence-4.4.18}/mainsequence/client/command_center/providers/__init__.py +0 -0
  69. {mainsequence-4.4.15 → mainsequence-4.4.18}/mainsequence/client/command_center/providers/adapter_from_api.py +0 -0
  70. {mainsequence-4.4.15 → mainsequence-4.4.18}/mainsequence/client/command_center/widgets/__init__.py +0 -0
  71. {mainsequence-4.4.15 → mainsequence-4.4.18}/mainsequence/client/command_center/widgets/bindings.py +0 -0
  72. {mainsequence-4.4.15 → mainsequence-4.4.18}/mainsequence/client/command_center/widgets/connection_query.py +0 -0
  73. {mainsequence-4.4.15 → mainsequence-4.4.18}/mainsequence/client/command_center/widgets/registry.py +0 -0
  74. {mainsequence-4.4.15 → mainsequence-4.4.18}/mainsequence/client/command_center/widgets/table.py +0 -0
  75. {mainsequence-4.4.15 → mainsequence-4.4.18}/mainsequence/client/command_center/widgets/tabular_transform.py +0 -0
  76. {mainsequence-4.4.15 → mainsequence-4.4.18}/mainsequence/client/command_center/workspace.py +0 -0
  77. {mainsequence-4.4.15 → mainsequence-4.4.18}/mainsequence/client/command_center/workspace_snapshot.py +0 -0
  78. {mainsequence-4.4.15 → mainsequence-4.4.18}/mainsequence/client/command_center/workspaces/__init__.py +0 -0
  79. {mainsequence-4.4.15 → mainsequence-4.4.18}/mainsequence/client/command_center/workspaces/documents.py +0 -0
  80. {mainsequence-4.4.15 → mainsequence-4.4.18}/mainsequence/client/command_center/workspaces/mounted_widgets.py +0 -0
  81. {mainsequence-4.4.15 → mainsequence-4.4.18}/mainsequence/client/compute_validation.py +0 -0
  82. {mainsequence-4.4.15 → mainsequence-4.4.18}/mainsequence/client/data_sources_interfaces/__init__.py +0 -0
  83. {mainsequence-4.4.15 → mainsequence-4.4.18}/mainsequence/client/data_sources_interfaces/duckdb.py +0 -0
  84. {mainsequence-4.4.15 → mainsequence-4.4.18}/mainsequence/client/data_sources_interfaces/local_paths.py +0 -0
  85. {mainsequence-4.4.15 → mainsequence-4.4.18}/mainsequence/client/data_sources_interfaces/sqlite.py +0 -0
  86. {mainsequence-4.4.15 → mainsequence-4.4.18}/mainsequence/client/dtype_codec.py +0 -0
  87. {mainsequence-4.4.15 → mainsequence-4.4.18}/mainsequence/client/exceptions.py +0 -0
  88. {mainsequence-4.4.15 → mainsequence-4.4.18}/mainsequence/client/fastapi/__init__.py +0 -0
  89. {mainsequence-4.4.15 → mainsequence-4.4.18}/mainsequence/client/fastapi/auth.py +0 -0
  90. {mainsequence-4.4.15 → mainsequence-4.4.18}/mainsequence/client/metatables/__init__.py +0 -0
  91. {mainsequence-4.4.15 → mainsequence-4.4.18}/mainsequence/client/models_foundry.py +0 -0
  92. {mainsequence-4.4.15 → mainsequence-4.4.18}/mainsequence/client/models_helpers.py +0 -0
  93. {mainsequence-4.4.15 → mainsequence-4.4.18}/mainsequence/client/models_user.py +0 -0
  94. {mainsequence-4.4.15 → mainsequence-4.4.18}/mainsequence/client/utils.py +0 -0
  95. {mainsequence-4.4.15 → mainsequence-4.4.18}/mainsequence/defaults.py +0 -0
  96. {mainsequence-4.4.15 → mainsequence-4.4.18}/mainsequence/instrumentation/__init__.py +0 -0
  97. {mainsequence-4.4.15 → mainsequence-4.4.18}/mainsequence/instrumentation/utils.py +0 -0
  98. {mainsequence-4.4.15 → mainsequence-4.4.18}/mainsequence/logconf.py +0 -0
  99. {mainsequence-4.4.15 → mainsequence-4.4.18}/mainsequence/meta_tables/__init__.py +0 -0
  100. {mainsequence-4.4.15 → mainsequence-4.4.18}/mainsequence/meta_tables/__main__.py +0 -0
  101. {mainsequence-4.4.15 → mainsequence-4.4.18}/mainsequence/meta_tables/compiled_sql/__init__.py +0 -0
  102. {mainsequence-4.4.15 → mainsequence-4.4.18}/mainsequence/meta_tables/data_nodes/__init__.py +0 -0
  103. {mainsequence-4.4.15 → mainsequence-4.4.18}/mainsequence/meta_tables/data_nodes/build_operations.py +0 -0
  104. {mainsequence-4.4.15 → mainsequence-4.4.18}/mainsequence/meta_tables/data_nodes/data_nodes.py +0 -0
  105. {mainsequence-4.4.15 → mainsequence-4.4.18}/mainsequence/meta_tables/data_nodes/models.py +0 -0
  106. {mainsequence-4.4.15 → mainsequence-4.4.18}/mainsequence/meta_tables/data_nodes/namespacing.py +0 -0
  107. {mainsequence-4.4.15 → mainsequence-4.4.18}/mainsequence/meta_tables/data_nodes/run_operations.py +0 -0
  108. {mainsequence-4.4.15 → mainsequence-4.4.18}/mainsequence/meta_tables/data_nodes/utils.py +0 -0
  109. {mainsequence-4.4.15 → mainsequence-4.4.18}/mainsequence/meta_tables/future_registry.py +0 -0
  110. {mainsequence-4.4.15 → mainsequence-4.4.18}/mainsequence/meta_tables/hashing.py +0 -0
  111. {mainsequence-4.4.15 → mainsequence-4.4.18}/mainsequence/meta_tables/migrations/__init__.py +0 -0
  112. {mainsequence-4.4.15 → mainsequence-4.4.18}/mainsequence/meta_tables/migrations/alembic.py +0 -0
  113. {mainsequence-4.4.15 → mainsequence-4.4.18}/mainsequence/meta_tables/migrations/env.py +0 -0
  114. {mainsequence-4.4.15 → mainsequence-4.4.18}/mainsequence/meta_tables/migrations/provider.py +0 -0
  115. {mainsequence-4.4.15 → mainsequence-4.4.18}/mainsequence/meta_tables/migrations/registry.py +0 -0
  116. {mainsequence-4.4.15 → mainsequence-4.4.18}/mainsequence/meta_tables/migrations/scaffold.py +0 -0
  117. {mainsequence-4.4.15 → mainsequence-4.4.18}/mainsequence/meta_tables/migrations/templates/__init__.py +0 -0
  118. {mainsequence-4.4.15 → mainsequence-4.4.18}/mainsequence/meta_tables/migrations/templates/env.py.mako +0 -0
  119. {mainsequence-4.4.15 → mainsequence-4.4.18}/mainsequence/meta_tables/migrations/templates/script.py.mako +0 -0
  120. {mainsequence-4.4.15 → mainsequence-4.4.18}/mainsequence/meta_tables/pydantic_metadata.py +0 -0
  121. {mainsequence-4.4.15 → mainsequence-4.4.18}/mainsequence/meta_tables/schema_names.py +0 -0
  122. {mainsequence-4.4.15 → mainsequence-4.4.18}/mainsequence/meta_tables/sqlalchemy_contracts.py +0 -0
  123. {mainsequence-4.4.15 → mainsequence-4.4.18}/mainsequence/runtime_flags.py +0 -0
  124. {mainsequence-4.4.15 → mainsequence-4.4.18}/mainsequence/scaffold_skills.py +0 -0
  125. {mainsequence-4.4.15 → mainsequence-4.4.18}/mainsequence.egg-info/SOURCES.txt +0 -0
  126. {mainsequence-4.4.15 → mainsequence-4.4.18}/mainsequence.egg-info/dependency_links.txt +0 -0
  127. {mainsequence-4.4.15 → mainsequence-4.4.18}/mainsequence.egg-info/entry_points.txt +0 -0
  128. {mainsequence-4.4.15 → mainsequence-4.4.18}/mainsequence.egg-info/requires.txt +0 -0
  129. {mainsequence-4.4.15 → mainsequence-4.4.18}/mainsequence.egg-info/top_level.txt +0 -0
  130. {mainsequence-4.4.15 → mainsequence-4.4.18}/setup.cfg +0 -0
  131. {mainsequence-4.4.15 → mainsequence-4.4.18}/tests/test_auth_precedence.py +0 -0
  132. {mainsequence-4.4.15 → mainsequence-4.4.18}/tests/test_build_operations_hashing.py +0 -0
  133. {mainsequence-4.4.15 → mainsequence-4.4.18}/tests/test_cli_browser_auth.py +0 -0
  134. {mainsequence-4.4.15 → mainsequence-4.4.18}/tests/test_cli_migrations.py +0 -0
  135. {mainsequence-4.4.15 → mainsequence-4.4.18}/tests/test_client.py +0 -0
  136. {mainsequence-4.4.15 → mainsequence-4.4.18}/tests/test_command_center_app_component_models.py +0 -0
  137. {mainsequence-4.4.15 → mainsequence-4.4.18}/tests/test_command_center_data_models.py +0 -0
  138. {mainsequence-4.4.15 → mainsequence-4.4.18}/tests/test_command_center_models.py +0 -0
  139. {mainsequence-4.4.15 → mainsequence-4.4.18}/tests/test_command_center_table_contracts.py +0 -0
  140. {mainsequence-4.4.15 → mainsequence-4.4.18}/tests/test_command_center_tabular_transform.py +0 -0
  141. {mainsequence-4.4.15 → mainsequence-4.4.18}/tests/test_data_access_mixin_dimension_audit.py +0 -0
  142. {mainsequence-4.4.15 → mainsequence-4.4.18}/tests/test_data_node_storage_dimension_queries.py +0 -0
  143. {mainsequence-4.4.15 → mainsequence-4.4.18}/tests/test_data_node_update_flow.py +0 -0
  144. {mainsequence-4.4.15 → mainsequence-4.4.18}/tests/test_dependency_extras.py +0 -0
  145. {mainsequence-4.4.15 → mainsequence-4.4.18}/tests/test_duckdb_interface_dimensions.py +0 -0
  146. {mainsequence-4.4.15 → mainsequence-4.4.18}/tests/test_instrumentation.py +0 -0
  147. {mainsequence-4.4.15 → mainsequence-4.4.18}/tests/test_logconf.py +0 -0
  148. {mainsequence-4.4.15 → mainsequence-4.4.18}/tests/test_meta_table_migrations.py +0 -0
  149. {mainsequence-4.4.15 → mainsequence-4.4.18}/tests/test_meta_tables_sqlalchemy_contracts.py +0 -0
  150. {mainsequence-4.4.15 → mainsequence-4.4.18}/tests/test_models_user_request_bound_auth.py +0 -0
  151. {mainsequence-4.4.15 → mainsequence-4.4.18}/tests/test_pod_project_resolution.py +0 -0
  152. {mainsequence-4.4.15 → mainsequence-4.4.18}/tests/test_project_batch_jobs_from_file.py +0 -0
  153. {mainsequence-4.4.15 → mainsequence-4.4.18}/tests/test_scaffold_skills.py +0 -0
  154. {mainsequence-4.4.15 → mainsequence-4.4.18}/tests/test_schema_names.py +0 -0
  155. {mainsequence-4.4.15 → mainsequence-4.4.18}/tests/test_secret_client_model.py +0 -0
  156. {mainsequence-4.4.15 → mainsequence-4.4.18}/tests/test_source_table_configuration.py +0 -0
  157. {mainsequence-4.4.15 → mainsequence-4.4.18}/tests/test_sqlite_interface_dimensions.py +0 -0
  158. {mainsequence-4.4.15 → mainsequence-4.4.18}/tests/test_update_runner_uid_runtime.py +0 -0
  159. {mainsequence-4.4.15 → mainsequence-4.4.18}/tests/test_update_statistics.py +0 -0
  160. {mainsequence-4.4.15 → mainsequence-4.4.18}/tests/test_update_uid_guards.py +0 -0
  161. {mainsequence-4.4.15 → mainsequence-4.4.18}/tests/test_workspace_snapshot.py +0 -0
@@ -1,6 +1,6 @@
1
1
  Metadata-Version: 2.4
2
2
  Name: mainsequence
3
- Version: 4.4.15
3
+ Version: 4.4.18
4
4
  Summary: Main Sequence SDK
5
5
  Author-email: Main Sequence GmbH <dev@main-sequence.io>
6
6
  License: MainSequence GmbH SDK License Agreement
@@ -83,6 +83,10 @@ mainsequence agent session a2a send \
83
83
  - Parse the CLI output as the standard A2A JSON response.
84
84
  - Consume only `message.parts` from the A2A response.
85
85
  - Do not depend on reasoning, tool traces, runtime paths, or transport metadata.
86
+ - If a send times out or disconnects and must be retried, reuse the same
87
+ `--message-id` value so the target can treat it as the same logical message.
88
+ - If the CLI generated the message id and the send failed, reuse the
89
+ `A2A message id for exact retry` value printed with the error.
86
90
 
87
91
  ## Deterministic Execution Path
88
92
 
@@ -92,22 +92,81 @@ For platform discovery, start with the `mainsequence` CLI.
92
92
 
93
93
  Discovery priority:
94
94
 
95
- - use search first when the surface supports search
96
- - use list and filters when the surface does not support search
95
+ - use semantic description search first when the user describes a dataset in natural language
96
+ - use list and filters only when the user already knows a structured field to constrain by
97
+ - use column lookup only when the user is specifically searching for a schema or column name
97
98
  - use detail only after you have identified the candidate object you want to inspect
98
99
 
99
- Typical commands include:
100
+ Semantic description discovery searches `MetaTable` metadata rows through:
101
+
102
+ - `GET /orm/api/ts_manager/meta_table/description-search/?q=<text>`
103
+
104
+ The same discovery surface applies to `MetaTable` metadata and to published
105
+ `DataNode` storage tables, because `DataNode` storage is represented by
106
+ `TimeIndexMetaTable` metadata.
107
+
108
+ Typical semantic discovery commands:
100
109
 
101
110
  - `mainsequence data-node search "<keyword>"`
102
- - `mainsequence data-node search "<keyword>" --mode description`
103
- - `mainsequence data-node search "<keyword>" --mode column`
104
- - `mainsequence data-node search "<keyword>" --show-filters`
105
- - `mainsequence data-node search "<keyword>" --filter KEY=VALUE`
111
+
112
+ Optional ranking knobs for description discovery:
113
+
114
+ - `--trigram-k 200`
115
+ - `--embed-k 200`
116
+ - `--w-trgm 0.65`
117
+ - `--w-emb 0.35`
118
+
119
+ The response is paginated metadata:
120
+
121
+ ```json
122
+ {
123
+ "count": 2,
124
+ "next": null,
125
+ "previous": null,
126
+ "results": [
127
+ {
128
+ "orm_class": "TimeIndexMetaTable",
129
+ "uid": "0b0f5733-b1ee-4d09-b51f-9e29073007fd",
130
+ "data_source_uid": "864e7c22-482a-464a-8758-0d3408abd77f",
131
+ "identifier": "ms_markets__externalpricests__mainsequence_examples",
132
+ "namespace": "mainsequence.examples",
133
+ "description": "...",
134
+ "physical_table_name": "ms_markets__externalpricests__mainsequence_examples",
135
+ "table_contract": {},
136
+ "columns": [],
137
+ "indexes_meta": [],
138
+ "foreign_keys": [],
139
+ "cadence": "1d",
140
+ "time_indexed_profile": {}
141
+ }
142
+ ]
143
+ }
144
+ ```
145
+
146
+ Structured filtering is a different path. Use it only when you already know the
147
+ field to filter by:
148
+
106
149
  - `mainsequence data-node list`
107
150
  - `mainsequence data-node list --show-filters`
108
151
  - `mainsequence data-node list --filter KEY=VALUE`
109
152
  - `mainsequence data-node detail <DATA_NODE_STORAGE_UID>`
110
153
 
154
+ Column lookup is also a different path. Use it only for schema-name discovery,
155
+ not as the default dataset discovery flow:
156
+
157
+ - `mainsequence data-node search "<column-name>" --mode column`
158
+
159
+ Raw SQL inspection is only for targeted exploration after you have a UID:
160
+
161
+ - `mainsequence meta-table run_query <META_TABLE_UID> "SELECT * FROM public.some_table LIMIT 100"`
162
+ - `mainsequence data-node run_query <DATA_NODE_STORAGE_UID> "SELECT * FROM public.some_table LIMIT 100"`
163
+
164
+ Use the MetaTable command for `MetaTable` UIDs. Use the DataNode command only
165
+ for `DataNode` storage UIDs. Do not confuse the two surfaces.
166
+
167
+ For direct SDK/backend usage, MetaTable raw SQL is sent as a JSON string body,
168
+ not as an object. Do not send `{ "sql": "SELECT ..." }`.
169
+
111
170
  ### 2. Stop at discovery boundaries
112
171
 
113
172
  Use the CLI or SDK client to identify what exists and collect the relevant identifiers, object UIDs, and metadata.
@@ -117,7 +176,8 @@ Do not define code-level read patterns here.
117
176
  For `DataNode` discovery specifically:
118
177
 
119
178
  - start with `mainsequence data-node search`
120
- - use `mainsequence data-node list` when you need broader enumeration or structured filters
179
+ - use `mainsequence data-node list` only when you need broader enumeration or structured filters
180
+ - use `mainsequence data-node search "<column-name>" --mode column` only for schema-name lookup
121
181
  - use `mainsequence data-node detail` only after search or list identified the target storage
122
182
 
123
183
  ### 3. Report platform objects with evidence
@@ -24,7 +24,14 @@ from urllib.parse import urlencode
24
24
 
25
25
  import requests
26
26
 
27
- from .config import backend_url, get_tokens, save_tokens
27
+ from .config import (
28
+ backend_url,
29
+ clear_runtime_access_cache,
30
+ get_runtime_access_cache,
31
+ get_tokens,
32
+ save_runtime_access_cache,
33
+ save_tokens,
34
+ )
28
35
 
29
36
  AUTH_PATHS = {
30
37
  "authorize": "/auth/cli/authorize/",
@@ -39,7 +46,6 @@ CLI_BROWSER_CLIENT_ID = "mainsequence-cli"
39
46
  S = requests.Session()
40
47
  S.headers.update({"Content-Type": "application/json"})
41
48
 
42
- DEFAULT_AGENT_RUNTIME_READY_TIMEOUT_SECONDS = 900.0
43
49
  _UNSET = object()
44
50
 
45
51
 
@@ -1332,135 +1338,33 @@ def get_agent_session(
1332
1338
  raise ApiError(f"Agent session fetch failed: {e}") from e
1333
1339
 
1334
1340
 
1335
- def resolve_agent_session_runtime_access(
1336
- agent_session_uid: str,
1337
- *,
1338
- wait_for_runtime: bool = False,
1339
- timeout: int | None = None,
1340
- ) -> dict[str, Any]:
1341
- """
1342
- Resolve runtime access for one agent session via SDK client model.
1343
- """
1344
- try:
1345
- runtime_access = _run_sdk_model_operation(
1346
- module_name="mainsequence.client.agent_runtime_models",
1347
- class_name="AgentSession",
1348
- operation=lambda ClientAgentSession: ClientAgentSession.resolve_runtime_access(
1349
- str(agent_session_uid),
1350
- wait_for_runtime=wait_for_runtime,
1351
- timeout=timeout,
1352
- ),
1353
- )
1354
- return _sdk_object_to_dict(runtime_access)
1355
- except Exception as e:
1356
- err_name = type(e).__name__
1357
- if err_name == "NotFoundError":
1358
- raise ApiError(f"Agent session not found: {agent_session_uid}") from e
1359
- if isinstance(e, (ApiError, NotLoggedIn)):
1360
- raise
1361
- raise ApiError(f"Agent session runtime access resolve failed: {e}") from e
1362
-
1363
-
1364
- def wait_agent_session_runtime_ready(
1365
- agent_session_uid: str,
1366
- *,
1367
- timeout_seconds: float = DEFAULT_AGENT_RUNTIME_READY_TIMEOUT_SECONDS,
1368
- timeout: int | None = None,
1369
- ) -> dict[str, Any]:
1370
- """
1371
- Wait for one agent session runtime through SDK client model.
1372
- """
1373
- try:
1374
- ready = _run_sdk_model_operation(
1375
- module_name="mainsequence.client.agent_runtime_models",
1376
- class_name="AgentSession",
1377
- operation=lambda ClientAgentSession: ClientAgentSession.wait_until_runtime_ready(
1378
- str(agent_session_uid),
1379
- timeout_seconds=timeout_seconds,
1380
- timeout=timeout,
1381
- ),
1382
- )
1383
- return _sdk_object_to_dict(ready)
1384
- except Exception as e:
1385
- err_name = type(e).__name__
1386
- if err_name == "NotFoundError":
1387
- raise ApiError(f"Agent session not found: {agent_session_uid}") from e
1388
- if isinstance(e, (ApiError, NotLoggedIn)):
1389
- raise
1390
- raise ApiError(f"Agent session runtime readiness failed: {e}") from e
1391
-
1392
-
1393
- def send_agent_session_a2a_chat(
1394
- agent_session_uid: str,
1395
- *,
1396
- message: str | None = None,
1397
- a2a_payload: dict[str, Any] | None = None,
1398
- wait_for_runtime: bool = True,
1399
- runtime_ready_timeout_seconds: float = DEFAULT_AGENT_RUNTIME_READY_TIMEOUT_SECONDS,
1400
- poll_task_until_stable: bool | None = None,
1401
- runtime_turn_timeout_seconds: float | None = None,
1402
- omit_reasoning: bool | None = None,
1403
- response_format: dict[str, Any] | None = None,
1404
- json_repair: dict[str, Any] | None = None,
1405
- timeout: int | None = None,
1406
- ) -> dict[str, Any]:
1407
- """
1408
- Send an A2A request through the legacy backend compatibility endpoint.
1409
- """
1410
- try:
1411
- chat = _run_sdk_model_operation(
1412
- module_name="mainsequence.client.agent_runtime_models",
1413
- class_name="AgentSession",
1414
- operation=lambda ClientAgentSession: ClientAgentSession.send_a2a_chat(
1415
- str(agent_session_uid),
1416
- message=message,
1417
- a2a_payload=a2a_payload,
1418
- wait_for_runtime=wait_for_runtime,
1419
- runtime_ready_timeout_seconds=runtime_ready_timeout_seconds,
1420
- poll_task_until_stable=poll_task_until_stable,
1421
- runtime_turn_timeout_seconds=runtime_turn_timeout_seconds,
1422
- omit_reasoning=omit_reasoning,
1423
- response_format=response_format,
1424
- json_repair=json_repair,
1425
- timeout=timeout,
1426
- ),
1427
- )
1428
- return _sdk_object_to_dict(chat)
1429
- except Exception as e:
1430
- err_name = type(e).__name__
1431
- if err_name == "NotFoundError":
1432
- raise ApiError(f"Agent session not found: {agent_session_uid}") from e
1433
- if isinstance(e, (ApiError, NotLoggedIn)):
1434
- raise
1435
- raise ApiError(f"Agent session A2A chat failed: {e}") from e
1436
-
1437
-
1438
1341
  def send_agent_session_a2a_message(
1439
1342
  agent_session_uid: str,
1440
1343
  *,
1441
1344
  message: str,
1345
+ message_id: str | None = None,
1442
1346
  strict_dictionary: bool = False,
1443
1347
  json_repair_attempts: int = 3,
1444
- history_length: int = 0,
1445
1348
  return_immediately: bool = False,
1446
- wait_for_runtime: bool = True,
1447
1349
  timeout: int | None = None,
1448
1350
  ) -> dict[str, Any]:
1449
1351
  """
1450
1352
  Send one standard A2A message through the target session runtime.
1451
1353
  """
1452
1354
  try:
1355
+ cached_runtime_access = get_runtime_access_cache(str(agent_session_uid))
1453
1356
  payload = _run_sdk_model_operation(
1454
1357
  module_name="mainsequence.client.agent_runtime_models",
1455
1358
  class_name="AgentSession",
1456
- operation=lambda ClientAgentSession: ClientAgentSession.send_a2a_message(
1457
- str(agent_session_uid),
1359
+ operation=lambda ClientAgentSession: _send_agent_session_a2a_message_with_cache(
1360
+ ClientAgentSession,
1361
+ agent_session_uid=str(agent_session_uid),
1458
1362
  message=message,
1363
+ message_id=message_id,
1364
+ cached_runtime_access=cached_runtime_access,
1459
1365
  strict_dictionary=strict_dictionary,
1460
1366
  json_repair_attempts=json_repair_attempts,
1461
- history_length=history_length,
1462
1367
  return_immediately=return_immediately,
1463
- wait_for_runtime=wait_for_runtime,
1464
1368
  timeout=timeout,
1465
1369
  ),
1466
1370
  )
@@ -1471,112 +1375,43 @@ def send_agent_session_a2a_message(
1471
1375
  raise ApiError(f"Agent session not found: {agent_session_uid}") from e
1472
1376
  if isinstance(e, (ApiError, NotLoggedIn)):
1473
1377
  raise
1378
+ if "401" in str(e) or "403" in str(e) or "unauthorized" in str(e).lower():
1379
+ clear_runtime_access_cache(str(agent_session_uid))
1474
1380
  raise ApiError(f"Agent session A2A message send failed: {e}") from e
1475
1381
 
1476
1382
 
1477
- def chat_agent_session_runtime(
1478
- agent_session_uid: str,
1383
+ def _send_agent_session_a2a_message_with_cache(
1384
+ ClientAgentSession,
1479
1385
  *,
1480
- message: str,
1481
- runtime_access: dict[str, Any] | None = None,
1482
- wait_for_runtime: bool = True,
1483
- runtime_turn_timeout_seconds: float | None = None,
1484
- omit_reasoning: bool | None = True,
1485
- response_format: dict[str, Any] | None = None,
1486
- json_repair: dict[str, Any] | None = None,
1487
- timeout: int | None = None,
1488
- ) -> dict[str, Any]:
1489
- """
1490
- Send one message through the resolved A2A runtime chat stream.
1491
- """
1492
- operation_kwargs: dict[str, Any] = {
1493
- "message": message,
1494
- "wait_for_runtime": wait_for_runtime,
1495
- "runtime_turn_timeout_seconds": runtime_turn_timeout_seconds,
1496
- "omit_reasoning": omit_reasoning,
1497
- "response_format": response_format,
1498
- "json_repair": json_repair,
1499
- "timeout": timeout,
1500
- }
1501
- if runtime_access is not None:
1502
- operation_kwargs["runtime_access"] = runtime_access
1503
- try:
1504
- payload = _run_sdk_model_operation(
1505
- module_name="mainsequence.client.agent_runtime_models",
1506
- class_name="AgentSession",
1507
- operation=lambda ClientAgentSession: ClientAgentSession.a2a_chat(
1508
- str(agent_session_uid),
1509
- **operation_kwargs,
1510
- ),
1511
- )
1512
- return _sdk_object_to_dict(payload)
1513
- except Exception as e:
1514
- err_name = type(e).__name__
1515
- if err_name == "NotFoundError":
1516
- raise ApiError(f"Agent session not found: {agent_session_uid}") from e
1517
- if isinstance(e, (ApiError, NotLoggedIn)):
1518
- raise
1519
- raise ApiError(f"Agent session runtime chat failed: {e}") from e
1520
-
1521
-
1522
- def cancel_agent_session_runtime(
1523
1386
  agent_session_uid: str,
1524
- *,
1525
- reason: str = "client_requested",
1526
- message: str | None = None,
1527
- timeout: int | None = None,
1528
- ) -> dict[str, Any]:
1529
- """
1530
- Cancel the active turn on the resolved A2A runtime.
1531
- """
1532
- try:
1533
- payload = _run_sdk_model_operation(
1534
- module_name="mainsequence.client.agent_runtime_models",
1535
- class_name="AgentSession",
1536
- operation=lambda ClientAgentSession: ClientAgentSession.cancel_runtime(
1537
- str(agent_session_uid),
1538
- reason=reason,
1539
- message=message,
1540
- timeout=timeout,
1541
- ),
1542
- )
1543
- return _sdk_object_to_dict(payload)
1544
- except Exception as e:
1545
- err_name = type(e).__name__
1546
- if err_name == "NotFoundError":
1547
- raise ApiError(f"Agent session not found: {agent_session_uid}") from e
1548
- if isinstance(e, (ApiError, NotLoggedIn)):
1549
- raise
1550
- raise ApiError(f"Agent session runtime cancel failed: {e}") from e
1551
-
1387
+ message: str,
1388
+ message_id: str | None,
1389
+ cached_runtime_access: dict[str, Any] | None,
1390
+ strict_dictionary: bool,
1391
+ json_repair_attempts: int,
1392
+ return_immediately: bool,
1393
+ timeout: int | None,
1394
+ ):
1395
+ if cached_runtime_access is not None:
1396
+ ClientAgentSession.cache_runtime_access(agent_session_uid, cached_runtime_access)
1397
+
1398
+ payload = ClientAgentSession.send_a2a_message(
1399
+ agent_session_uid,
1400
+ message=message,
1401
+ message_id=message_id,
1402
+ strict_dictionary=strict_dictionary,
1403
+ json_repair_attempts=json_repair_attempts,
1404
+ return_immediately=return_immediately,
1405
+ timeout=timeout,
1406
+ )
1552
1407
 
1553
- def detach_agent_session_runtime(
1554
- agent_session_uid: str,
1555
- *,
1556
- reason: str = "client_done",
1557
- timeout: int | None = None,
1558
- ) -> dict[str, Any]:
1559
- """
1560
- Detach the resolved A2A runtime for one agent session.
1561
- """
1562
- try:
1563
- payload = _run_sdk_model_operation(
1564
- module_name="mainsequence.client.agent_runtime_models",
1565
- class_name="AgentSession",
1566
- operation=lambda ClientAgentSession: ClientAgentSession.detach_runtime(
1567
- str(agent_session_uid),
1568
- reason=reason,
1569
- timeout=timeout,
1570
- ),
1408
+ resolved_access = ClientAgentSession.get_cached_runtime_access(agent_session_uid)
1409
+ if resolved_access is not None:
1410
+ save_runtime_access_cache(
1411
+ agent_session_uid,
1412
+ _sdk_object_to_dict(resolved_access),
1571
1413
  )
1572
- return _sdk_object_to_dict(payload)
1573
- except Exception as e:
1574
- err_name = type(e).__name__
1575
- if err_name == "NotFoundError":
1576
- raise ApiError(f"Agent session not found: {agent_session_uid}") from e
1577
- if isinstance(e, (ApiError, NotLoggedIn)):
1578
- raise
1579
- raise ApiError(f"Agent session runtime detach failed: {e}") from e
1414
+ return payload
1580
1415
 
1581
1416
 
1582
1417
  def list_agent_users_can_view(
@@ -4686,6 +4521,36 @@ def run_data_node_storage_query(
4686
4521
  raise ApiError(f"Data node query failed: {e}") from e
4687
4522
 
4688
4523
 
4524
+ def run_meta_table_query(
4525
+ meta_table_uid: str,
4526
+ sql: str,
4527
+ *,
4528
+ timeout: int | None = None,
4529
+ ) -> dict[str, Any]:
4530
+ """
4531
+ Run a raw SQL query against one MetaTable via SDK client model.
4532
+ """
4533
+ try:
4534
+
4535
+ def _run_query(ClientMetaTable):
4536
+ meta_table = ClientMetaTable.get(uid=str(meta_table_uid), timeout=timeout)
4537
+ payload = meta_table.run_query(sql, timeout=timeout)
4538
+ return dict(payload) if isinstance(payload, dict) else {"ok": True, "results": payload}
4539
+
4540
+ return _run_sdk_model_operation(
4541
+ module_name="mainsequence.client.metatables",
4542
+ class_name="MetaTable",
4543
+ operation=_run_query,
4544
+ )
4545
+ except Exception as e:
4546
+ err_name = type(e).__name__
4547
+ if err_name == "NotFoundError":
4548
+ raise ApiError(f"MetaTable not found: {meta_table_uid}") from e
4549
+ if isinstance(e, (ApiError, NotLoggedIn)):
4550
+ raise
4551
+ raise ApiError(f"MetaTable query failed: {e}") from e
4552
+
4553
+
4689
4554
  def delete_data_node_storage(
4690
4555
  storage_uid: str,
4691
4556
  *,