legate 0.1.0
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.
- checksums.yaml +7 -0
- data/LICENSE +21 -0
- data/README.md +345 -0
- data/bin/legate +13 -0
- data/examples/00_quickstart.rb +51 -0
- data/examples/01_simple_agent.rb +105 -0
- data/examples/02_multi_tool_agent.rb +140 -0
- data/examples/03_custom_tool.rb +93 -0
- data/examples/04_agent_instructions.rb +84 -0
- data/examples/05_state_and_sessions.rb +91 -0
- data/examples/06_callbacks.rb +186 -0
- data/examples/07_async_jobs.rb +112 -0
- data/examples/08_loop_agent.rb +197 -0
- data/examples/09_sequential_workflow.rb +40 -0
- data/examples/10_parallel_workflow.rb +34 -0
- data/examples/11_agent_delegation.rb +24 -0
- data/examples/12_http_client_tool.rb +156 -0
- data/examples/13_authentication.rb +220 -0
- data/examples/14_mcp_client.rb +154 -0
- data/examples/15_mcp_server.rb +79 -0
- data/examples/16_webhooks.rb +91 -0
- data/examples/README_sequential_agents.md +164 -0
- data/examples/advanced/auth/cookie_auth_tool.rb +146 -0
- data/examples/advanced/auth/custom_auth_flows_example.rb +626 -0
- data/examples/advanced/auth/excon_middleware.rb +317 -0
- data/examples/advanced/auth/excon_middleware_auth.rb +399 -0
- data/examples/advanced/auth/fiber_auth_example.rb +281 -0
- data/examples/advanced/auth/fiber_oidc_example.rb +403 -0
- data/examples/advanced/auth/httpbin_bearer_tool.rb +159 -0
- data/examples/advanced/auth/oauth2_auth.rb +419 -0
- data/examples/advanced/auth/oidc_auth.rb +514 -0
- data/examples/advanced/auth/openweather_api.rb +251 -0
- data/examples/advanced/auth/openweather_tool.rb +153 -0
- data/examples/advanced/auth/query_param_middleware_test.rb +138 -0
- data/examples/advanced/auth/service_account.rb +135 -0
- data/examples/advanced/auth/test_with_httpbin.rb +202 -0
- data/examples/advanced/auth/token_lifecycle_example.rb +428 -0
- data/examples/advanced/callback_monitoring.rb +679 -0
- data/examples/advanced/mas/fixed_delegation_example.rb +191 -0
- data/examples/advanced/mas/loop_workflow.rb +28 -0
- data/examples/advanced/mas/mock_planner.rb +77 -0
- data/examples/advanced/mas/proper_delegation_example.rb +276 -0
- data/examples/advanced/mcp/legate_mcp_server_resource_example.rb +182 -0
- data/examples/advanced/mcp/mcp_resource_server_example.rb +309 -0
- data/examples/advanced/mcp/mcp_server_async.rb +76 -0
- data/examples/advanced/mcp/mcp_server_async_tools.rb +122 -0
- data/examples/advanced/mcp/mcp_server_legate_agent.rb +95 -0
- data/examples/advanced/mcp/mcp_server_rack.rb +89 -0
- data/examples/advanced/random_calculator.rb +104 -0
- data/examples/advanced/sleep_agent.rb +153 -0
- data/examples/advanced/webhooks/webhook_e2e_runner.rb +110 -0
- data/examples/advanced/webhooks/webhook_receiver_agent.rb +58 -0
- data/examples/advanced/workflows/task_refinement_loop_agent.rb +278 -0
- data/examples/advanced/workflows/travel_planner_auto_sequential.rb +444 -0
- data/examples/advanced/workflows/travel_planner_parallel.rb +656 -0
- data/examples/advanced/workflows/travel_planner_sequential.rb +512 -0
- data/examples/tools/oauth2_example.rb +136 -0
- data/examples/tools/sleepy_tool.rb +42 -0
- data/lib/legate/activity_log.rb +71 -0
- data/lib/legate/agent.rb +959 -0
- data/lib/legate/agent_code_generator.rb +185 -0
- data/lib/legate/agent_definition.rb +812 -0
- data/lib/legate/agentic/decision.rb +49 -0
- data/lib/legate/agentic/loop.rb +134 -0
- data/lib/legate/agentic.rb +5 -0
- data/lib/legate/agents/loop_agent.rb +248 -0
- data/lib/legate/agents/parallel_agent.rb +163 -0
- data/lib/legate/agents/sequential_agent.rb +190 -0
- data/lib/legate/agents.rb +14 -0
- data/lib/legate/auth/config.rb +148 -0
- data/lib/legate/auth/coordinator.rb +218 -0
- data/lib/legate/auth/coordinators/oauth2_coordinator.rb +99 -0
- data/lib/legate/auth/coordinators/oidc_coordinator.rb +68 -0
- data/lib/legate/auth/coordinators/service_account_coordinator.rb +122 -0
- data/lib/legate/auth/credential.rb +157 -0
- data/lib/legate/auth/encryption.rb +108 -0
- data/lib/legate/auth/error.rb +94 -0
- data/lib/legate/auth/exchanged_credential.rb +180 -0
- data/lib/legate/auth/excon_middleware.rb +285 -0
- data/lib/legate/auth/http_client_utils.rb +364 -0
- data/lib/legate/auth/manager.rb +531 -0
- data/lib/legate/auth/manager_store.rb +394 -0
- data/lib/legate/auth/middleware_factory.rb +290 -0
- data/lib/legate/auth/runner.rb +279 -0
- data/lib/legate/auth/scheme.rb +125 -0
- data/lib/legate/auth/schemes/api_key.rb +212 -0
- data/lib/legate/auth/schemes/google_service_account.rb +108 -0
- data/lib/legate/auth/schemes/http_bearer.rb +98 -0
- data/lib/legate/auth/schemes/oauth2.rb +396 -0
- data/lib/legate/auth/schemes/openid_connect.rb +346 -0
- data/lib/legate/auth/schemes/service_account.rb +388 -0
- data/lib/legate/auth/schemes.rb +40 -0
- data/lib/legate/auth/token_manager.rb +362 -0
- data/lib/legate/auth/token_store.rb +86 -0
- data/lib/legate/auth/tool_context_extension.rb +97 -0
- data/lib/legate/auth/tool_integration.rb +188 -0
- data/lib/legate/auth/url_guard.rb +81 -0
- data/lib/legate/auth.rb +453 -0
- data/lib/legate/callbacks/callback_context.rb +71 -0
- data/lib/legate/cli/agent_commands.rb +950 -0
- data/lib/legate/cli/auth_commands.rb +520 -0
- data/lib/legate/cli/base_command.rb +24 -0
- data/lib/legate/cli/deployment_commands.rb +934 -0
- data/lib/legate/cli/output_helper.rb +108 -0
- data/lib/legate/cli/session_commands.rb +138 -0
- data/lib/legate/cli/skaffold_commands.rb +223 -0
- data/lib/legate/cli/tool_commands.rb +261 -0
- data/lib/legate/cli/web_commands.rb +182 -0
- data/lib/legate/cli.rb +40 -0
- data/lib/legate/configuration/webhooks.rb +113 -0
- data/lib/legate/configuration.rb +39 -0
- data/lib/legate/definition_store.rb +23 -0
- data/lib/legate/errors.rb +118 -0
- data/lib/legate/event.rb +161 -0
- data/lib/legate/gemini_ai_beta_patch.rb +39 -0
- data/lib/legate/generators/agent_generator.rb +412 -0
- data/lib/legate/generators/code_validator.rb +48 -0
- data/lib/legate/generators/legate/install_generator.rb +35 -0
- data/lib/legate/generators/legate/templates/create_legate_tables.rb.tt +36 -0
- data/lib/legate/generators/legate/templates/initializer.rb +18 -0
- data/lib/legate/generators/runtime_tool_loader.rb +76 -0
- data/lib/legate/generators/tool_generator.rb +408 -0
- data/lib/legate/generators.rb +11 -0
- data/lib/legate/global_definition_registry.rb +506 -0
- data/lib/legate/global_tool_manager.rb +135 -0
- data/lib/legate/llm/adapter.rb +69 -0
- data/lib/legate/llm/gemini.rb +172 -0
- data/lib/legate/llm/ollama.rb +80 -0
- data/lib/legate/llm.rb +34 -0
- data/lib/legate/mcp/client.rb +320 -0
- data/lib/legate/mcp/connection/sse.rb +292 -0
- data/lib/legate/mcp/connection/stdio.rb +273 -0
- data/lib/legate/mcp/connection_manager.rb +103 -0
- data/lib/legate/mcp/server/legate_agent_adapter.rb +170 -0
- data/lib/legate/mcp/server/legate_direct_agent_adapter.rb +140 -0
- data/lib/legate/mcp/server/legate_tool_adapter.rb +119 -0
- data/lib/legate/mcp/tool_wrapper.rb +138 -0
- data/lib/legate/mcp/util/schema_converter.rb +134 -0
- data/lib/legate/mcp.rb +23 -0
- data/lib/legate/plan_executor.rb +375 -0
- data/lib/legate/planner.rb +839 -0
- data/lib/legate/rails/railtie.rb +43 -0
- data/lib/legate/rails.rb +9 -0
- data/lib/legate/redaction.rb +32 -0
- data/lib/legate/session.rb +299 -0
- data/lib/legate/session_service/active_record.rb +300 -0
- data/lib/legate/session_service/base.rb +68 -0
- data/lib/legate/session_service/event_broadcast.rb +74 -0
- data/lib/legate/session_service/in_memory.rb +188 -0
- data/lib/legate/tool/metadata_dsl.rb +122 -0
- data/lib/legate/tool.rb +276 -0
- data/lib/legate/tool_code_generator.rb +103 -0
- data/lib/legate/tool_context.rb +350 -0
- data/lib/legate/tool_loader.rb +39 -0
- data/lib/legate/tool_registry.rb +73 -0
- data/lib/legate/tool_result.rb +61 -0
- data/lib/legate/tools/agent_tool.rb +187 -0
- data/lib/legate/tools/base/http_client.rb +319 -0
- data/lib/legate/tools/base/safe_url.rb +56 -0
- data/lib/legate/tools/base_async_job_tool.rb +91 -0
- data/lib/legate/tools/calculator.rb +89 -0
- data/lib/legate/tools/cat_facts.rb +81 -0
- data/lib/legate/tools/check_job_status_tool.rb +48 -0
- data/lib/legate/tools/current_time_tool.rb +64 -0
- data/lib/legate/tools/echo.rb +43 -0
- data/lib/legate/tools/http_request_tool.rb +105 -0
- data/lib/legate/tools/random_number_tool.rb +64 -0
- data/lib/legate/tools/read_webpage_tool.rb +92 -0
- data/lib/legate/tools/sleepy_tool.rb +74 -0
- data/lib/legate/tools/webhook_tool.rb +146 -0
- data/lib/legate/version.rb +5 -0
- data/lib/legate/web/app.rb +984 -0
- data/lib/legate/web/public/css/main.css +4980 -0
- data/lib/legate/web/public/images/favicon-256.png +0 -0
- data/lib/legate/web/public/images/favicon-32.png +0 -0
- data/lib/legate/web/public/images/legate-logo-dark.png +0 -0
- data/lib/legate/web/public/images/legate-logo-light.png +0 -0
- data/lib/legate/web/public/js/legate.js +616 -0
- data/lib/legate/web/public/styles/main.scss +4402 -0
- data/lib/legate/web/routes/agent_authentication_routes.rb +530 -0
- data/lib/legate/web/routes/agent_definition_routes.rb +803 -0
- data/lib/legate/web/routes/agent_generator_routes.rb +80 -0
- data/lib/legate/web/routes/agent_interaction_routes.rb +734 -0
- data/lib/legate/web/routes/agent_runtime_routes.rb +323 -0
- data/lib/legate/web/routes/api_routes.rb +56 -0
- data/lib/legate/web/routes/authentication_routes.rb +1541 -0
- data/lib/legate/web/routes/core_routes.rb +111 -0
- data/lib/legate/web/routes/documentation_routes.rb +220 -0
- data/lib/legate/web/routes/tool_generator_routes.rb +81 -0
- data/lib/legate/web/routes/tools_ui_routes.rb +207 -0
- data/lib/legate/web/sass_compiler.rb +73 -0
- data/lib/legate/web/views/_active_session_info.slim +25 -0
- data/lib/legate/web/views/_activity_list.slim +55 -0
- data/lib/legate/web/views/_agent_card.slim +56 -0
- data/lib/legate/web/views/_agent_generator_modal.slim +382 -0
- data/lib/legate/web/views/_agent_status_controls.slim +71 -0
- data/lib/legate/web/views/_agent_tool_table.slim +74 -0
- data/lib/legate/web/views/_chat_message.slim +95 -0
- data/lib/legate/web/views/_display_agent_configuration.slim +26 -0
- data/lib/legate/web/views/_display_agent_description.slim +11 -0
- data/lib/legate/web/views/_display_agent_fallback.slim +15 -0
- data/lib/legate/web/views/_display_agent_hierarchy.slim +93 -0
- data/lib/legate/web/views/_display_agent_instruction.slim +17 -0
- data/lib/legate/web/views/_display_agent_mcp.slim +13 -0
- data/lib/legate/web/views/_display_agent_model.slim +17 -0
- data/lib/legate/web/views/_display_agent_name.slim +42 -0
- data/lib/legate/web/views/_display_agent_output_key.slim +26 -0
- data/lib/legate/web/views/_display_agent_type.slim +65 -0
- data/lib/legate/web/views/_edit_agent_configuration.slim +74 -0
- data/lib/legate/web/views/_edit_agent_description.slim +16 -0
- data/lib/legate/web/views/_edit_agent_fallback.slim +25 -0
- data/lib/legate/web/views/_edit_agent_hierarchy.slim +98 -0
- data/lib/legate/web/views/_edit_agent_instruction.slim +49 -0
- data/lib/legate/web/views/_edit_agent_mcp.slim +33 -0
- data/lib/legate/web/views/_edit_agent_model.slim +23 -0
- data/lib/legate/web/views/_edit_agent_output_key.slim +36 -0
- data/lib/legate/web/views/_edit_agent_tools.slim +40 -0
- data/lib/legate/web/views/_edit_agent_type.slim +67 -0
- data/lib/legate/web/views/_session_error.slim +4 -0
- data/lib/legate/web/views/_skeleton.slim +69 -0
- data/lib/legate/web/views/_tool_card.slim +9 -0
- data/lib/legate/web/views/_tool_generator_modal.slim +311 -0
- data/lib/legate/web/views/agent.slim +436 -0
- data/lib/legate/web/views/agent_auth.slim +562 -0
- data/lib/legate/web/views/agents.slim +369 -0
- data/lib/legate/web/views/auth.slim +112 -0
- data/lib/legate/web/views/auth_credential_detail.slim +327 -0
- data/lib/legate/web/views/auth_credentials.slim +261 -0
- data/lib/legate/web/views/auth_debug.slim +94 -0
- data/lib/legate/web/views/auth_mapping_detail.slim +151 -0
- data/lib/legate/web/views/auth_mapping_new.slim +123 -0
- data/lib/legate/web/views/auth_mappings.slim +120 -0
- data/lib/legate/web/views/auth_scheme_detail.slim +274 -0
- data/lib/legate/web/views/auth_schemes.slim +259 -0
- data/lib/legate/web/views/auth_test.slim +418 -0
- data/lib/legate/web/views/chat.slim +192 -0
- data/lib/legate/web/views/docs_index.slim +105 -0
- data/lib/legate/web/views/docs_show.slim +105 -0
- data/lib/legate/web/views/error_404.slim +5 -0
- data/lib/legate/web/views/index.slim +148 -0
- data/lib/legate/web/views/layout.slim +144 -0
- data/lib/legate/web/views/tool_detail.slim +87 -0
- data/lib/legate/web/views/tools.slim +50 -0
- data/lib/legate/web/webhook_listener.rb +367 -0
- data/lib/legate/web.rb +9 -0
- data/lib/legate.rb +220 -0
- data/public/docs/advanced/callbacks.md +828 -0
- data/public/docs/advanced/mcp_schema_conversion.md +59 -0
- data/public/docs/authentication/api_reference/config.md +210 -0
- data/public/docs/authentication/api_reference/credential.md +246 -0
- data/public/docs/authentication/api_reference/encryption.md +218 -0
- data/public/docs/authentication/api_reference/exchanged_credential.md +271 -0
- data/public/docs/authentication/api_reference/excon_middleware.md +175 -0
- data/public/docs/authentication/api_reference/index.md +30 -0
- data/public/docs/authentication/api_reference/scheme.md +250 -0
- data/public/docs/authentication/api_reference/schemes/api_key.md +175 -0
- data/public/docs/authentication/api_reference/schemes/google_service_account.md +221 -0
- data/public/docs/authentication/api_reference/schemes/http_bearer.md +169 -0
- data/public/docs/authentication/api_reference/schemes/oauth2.md +343 -0
- data/public/docs/authentication/api_reference/schemes/oidc.md +73 -0
- data/public/docs/authentication/api_reference/schemes/openid_connect.md +311 -0
- data/public/docs/authentication/api_reference/schemes/service_account.md +287 -0
- data/public/docs/authentication/api_reference/token_manager.md +221 -0
- data/public/docs/authentication/api_reference/token_store.md +146 -0
- data/public/docs/authentication/api_reference/tool_context_extension.md +166 -0
- data/public/docs/authentication/guides/api_key.md +190 -0
- data/public/docs/authentication/guides/bearer.md +172 -0
- data/public/docs/authentication/guides/configuration.md +255 -0
- data/public/docs/authentication/guides/custom_flow.md +523 -0
- data/public/docs/authentication/guides/index.md +24 -0
- data/public/docs/authentication/guides/migration.md +435 -0
- data/public/docs/authentication/guides/oauth2.md +252 -0
- data/public/docs/authentication/guides/oidc.md +241 -0
- data/public/docs/authentication/guides/overview.md +155 -0
- data/public/docs/authentication/guides/secure_storage.md +301 -0
- data/public/docs/authentication/guides/service_account.md +228 -0
- data/public/docs/authentication/guides/token_lifecycle.md +295 -0
- data/public/docs/authentication/guides/web_ui_integration.md +504 -0
- data/public/docs/authentication/index.md +58 -0
- data/public/docs/authentication/troubleshooting/credential_storage.md +550 -0
- data/public/docs/authentication/troubleshooting/environment_variables.md +540 -0
- data/public/docs/authentication/troubleshooting/index.md +11 -0
- data/public/docs/authentication/troubleshooting/oauth2_issues.md +220 -0
- data/public/docs/authentication/troubleshooting/oidc_issues.md +412 -0
- data/public/docs/authentication/troubleshooting/token_refresh.md +338 -0
- data/public/docs/cli/legate_cli_usage.md +363 -0
- data/public/docs/core_concepts/legate_agent_lifecycle.md +124 -0
- data/public/docs/core_concepts/legate_architecture_overview.md +110 -0
- data/public/docs/core_concepts/legate_configuration.md +116 -0
- data/public/docs/core_concepts/legate_definition_store.md +102 -0
- data/public/docs/core_concepts/legate_planner.md +94 -0
- data/public/docs/core_concepts/legate_session_service.md +104 -0
- data/public/docs/error_handling/legate_error_handling.md +122 -0
- data/public/docs/examples.md +199 -0
- data/public/docs/getting_started.md +111 -0
- data/public/docs/guides/agentic_agents.md +137 -0
- data/public/docs/guides/ai_code_generators.md +437 -0
- data/public/docs/guides/auto_loading.md +326 -0
- data/public/docs/guides/configuring_agent_webhooks.md +219 -0
- data/public/docs/guides/http_client_usage.md +264 -0
- data/public/docs/guides/llm_providers.md +137 -0
- data/public/docs/guides/mcp_client_integration.md +232 -0
- data/public/docs/guides/mcp_server_exposure.md +206 -0
- data/public/docs/guides/rails_integration.md +128 -0
- data/public/docs/guides/sending_outbound_webhooks.md +227 -0
- data/public/docs/guides/streaming.md +112 -0
- data/public/docs/guides/webhooks.md +288 -0
- data/public/docs/introduction.md +51 -0
- data/public/docs/multi_agent_systems/advanced_features.md +57 -0
- data/public/docs/multi_agent_systems/agent_delegation.md +190 -0
- data/public/docs/multi_agent_systems/agent_hierarchy.md +49 -0
- data/public/docs/multi_agent_systems/state_management.md +47 -0
- data/public/docs/multi_agent_systems/workflow_agents.md +72 -0
- data/public/docs/tools/legate_built_in_tools.md +332 -0
- data/public/docs/tools/legate_tools_and_registry.md +263 -0
- data/public/docs/web_ui/legate_web_ui.md +137 -0
- metadata +823 -0
|
@@ -0,0 +1,59 @@
|
|
|
1
|
+
# MCP Schema Conversion Details
|
|
2
|
+
|
|
3
|
+
This document details the automatic conversion processes between the different schema formats used by Legate, the Model Context Protocol (MCP), and the `fast-mcp` gem. Understanding this is helpful when defining tools or troubleshooting integration issues.
|
|
4
|
+
|
|
5
|
+
## Formats
|
|
6
|
+
|
|
7
|
+
* **Legate Parameters:** Defined within a `Legate::Tool` subclass using the `parameter` DSL (with `tool_description` for the description). Internally these are stored as a Ruby hash like:
|
|
8
|
+
```ruby
|
|
9
|
+
{
|
|
10
|
+
param_name: {
|
|
11
|
+
type: :symbol, # :string, :integer, :numeric, :boolean, :array, :hash
|
|
12
|
+
required: boolean,
|
|
13
|
+
description: string
|
|
14
|
+
},
|
|
15
|
+
# ...
|
|
16
|
+
}
|
|
17
|
+
```
|
|
18
|
+
* **MCP JSON Schema:** Standard JSON Schema objects used in MCP `tools/list` (`inputSchema`) and `resources/list` (`schema`).
|
|
19
|
+
```json
|
|
20
|
+
{
|
|
21
|
+
"type": "object",
|
|
22
|
+
"properties": {
|
|
23
|
+
"param_name": { "type": "string", "description": "..." }
|
|
24
|
+
},
|
|
25
|
+
"required": ["param_name"]
|
|
26
|
+
}
|
|
27
|
+
```
|
|
28
|
+
* **Dry::Schema:** Used by `fast-mcp` within the `arguments` block to define and validate tool parameters.
|
|
29
|
+
```ruby
|
|
30
|
+
arguments do
|
|
31
|
+
required(:param_name).filled(:string).description("...")
|
|
32
|
+
end
|
|
33
|
+
```
|
|
34
|
+
|
|
35
|
+
## Conversion Flows
|
|
36
|
+
|
|
37
|
+
### 1. MCP JSON Schema -> Legate Params
|
|
38
|
+
|
|
39
|
+
* **Where:** Done by `Legate::Mcp::ToolWrapper.from_mcp_schema` using `Legate::Mcp::Util::SchemaConverter.json_to_legate`.
|
|
40
|
+
* **Use Case:** When an Legate Agent connects to an external MCP server and discovers its tools (Client Mode).
|
|
41
|
+
* **Mapping (V1):** Basic types (`string`, `integer`, `number`, `boolean`) are mapped to corresponding Legate types (`:string`, `:integer`, `:numeric`, `:boolean`). `required` status and `description` are preserved.
|
|
42
|
+
* **Limitations (V1):** Complex types (`object`, `array`), constraints (`minLength`, `enum`, `format` etc.) are **ignored** during conversion. Only the basic type, requirement, and description are used.
|
|
43
|
+
|
|
44
|
+
### 2. Legate Params -> Dry::Schema
|
|
45
|
+
|
|
46
|
+
* **Where:** Done by `Legate::Mcp::Server::LegateToolAdapter.wrap` using `Legate::Mcp::Util::SchemaConverter.legate_to_dry_schema`.
|
|
47
|
+
* **Use Case:** When exposing an `Legate::Tool` via `fast-mcp` (Server Mode).
|
|
48
|
+
* **Mapping (V1):** Basic Legate types (`:string`, `:integer`, `:numeric`, `:boolean`) are mapped to appropriate `Dry::Schema` calls (`filled(:string)`, `filled(:integer)`, `filled(Dry::Types['coercible.float'])`, `filled(:bool)`). `:required` status maps to `required()` or `optional()`.
|
|
49
|
+
* **Limitations (V1):** Legate types `:array`, `:hash`, `:object` receive basic mappings (`value(:array)`, `value(:hash)`) **without** nested schema validation. Parameter descriptions from Legate metadata are **not** added to the Dry::Schema block itself (they are set separately on the `fast-mcp` tool using `description` DSL by the adapter).
|
|
50
|
+
|
|
51
|
+
### 3. Legate Params -> JSON for MCP Call (Client)
|
|
52
|
+
|
|
53
|
+
* **Where:** Inside `Legate::Mcp::ToolWrapper#perform_execution`.
|
|
54
|
+
* **Use Case:** When an Legate Agent executes an external MCP tool.
|
|
55
|
+
* **Mapping (V1):** Simple conversion of the Legate params hash (symbol keys) to a JSON hash (string keys). Assumes a flat structure.
|
|
56
|
+
|
|
57
|
+
## Key Takeaway
|
|
58
|
+
|
|
59
|
+
For V1, schema conversion primarily supports basic data types and required fields. Complex nested structures or validation rules defined in one system may not be fully enforced or represented when crossing the Legate <-> MCP boundary.
|
|
@@ -0,0 +1,210 @@
|
|
|
1
|
+
# Legate::Auth::Config
|
|
2
|
+
|
|
3
|
+
The `Config` class represents the configuration for interactive authentication flows. It includes all the necessary information to initiate, track, and complete an authentication process that requires user interaction.
|
|
4
|
+
|
|
5
|
+
## Overview
|
|
6
|
+
|
|
7
|
+
In interactive authentication flows like OAuth2 or OpenID Connect, the user needs to be redirected to an authentication provider to authenticate and grant permissions. The `Config` class encapsulates all the details needed for this interaction, including the scheme, credential, redirect URI, and callback handling.
|
|
8
|
+
|
|
9
|
+
## Class Methods
|
|
10
|
+
|
|
11
|
+
### `new`
|
|
12
|
+
|
|
13
|
+
Creates a new authentication configuration instance.
|
|
14
|
+
|
|
15
|
+
**Parameters:**
|
|
16
|
+
- `scheme` (Legate::Auth::Scheme): The authentication scheme to use
|
|
17
|
+
- `credential` (Legate::Auth::Credential): The credential for the authentication flow
|
|
18
|
+
- `auth_request_id` (String, optional): A unique identifier for this authentication request (default: nil)
|
|
19
|
+
- `options` (Hash, optional): Additional configuration options (default: {})
|
|
20
|
+
|
|
21
|
+
**Examples:**
|
|
22
|
+
|
|
23
|
+
```ruby
|
|
24
|
+
# Create a basic authentication configuration
|
|
25
|
+
config = Legate::Auth::Config.new(
|
|
26
|
+
scheme: oauth2_scheme,
|
|
27
|
+
credential: oauth2_credential
|
|
28
|
+
)
|
|
29
|
+
|
|
30
|
+
# With an explicit request ID and options
|
|
31
|
+
config = Legate::Auth::Config.new(
|
|
32
|
+
scheme: oauth2_scheme,
|
|
33
|
+
credential: oauth2_credential,
|
|
34
|
+
auth_request_id: 'req_123456',
|
|
35
|
+
options: { prompt: 'consent' }
|
|
36
|
+
)
|
|
37
|
+
```
|
|
38
|
+
|
|
39
|
+
### `from_h`
|
|
40
|
+
|
|
41
|
+
Creates a Config instance from a hash representation.
|
|
42
|
+
|
|
43
|
+
**Parameters:**
|
|
44
|
+
- `hash` (Hash): The hash to create the config from
|
|
45
|
+
- `scheme` (Legate::Auth::Scheme, optional): The scheme to associate (default: nil)
|
|
46
|
+
- `credential` (Legate::Auth::Credential, optional): The credential to associate (default: nil)
|
|
47
|
+
|
|
48
|
+
**Returns:**
|
|
49
|
+
- Legate::Auth::Config: A new Config instance
|
|
50
|
+
|
|
51
|
+
**Examples:**
|
|
52
|
+
|
|
53
|
+
```ruby
|
|
54
|
+
config = Legate::Auth::Config.from_h(
|
|
55
|
+
saved_hash,
|
|
56
|
+
scheme: oauth2_scheme,
|
|
57
|
+
credential: oauth2_credential
|
|
58
|
+
)
|
|
59
|
+
```
|
|
60
|
+
|
|
61
|
+
## Instance Attributes
|
|
62
|
+
|
|
63
|
+
### Readers (read-only)
|
|
64
|
+
|
|
65
|
+
- `scheme` - The authentication scheme
|
|
66
|
+
- `credential` - The authentication credential
|
|
67
|
+
- `auth_request_id` - The unique request identifier
|
|
68
|
+
|
|
69
|
+
### Accessors (read/write)
|
|
70
|
+
|
|
71
|
+
- `auth_uri` - The URI to redirect the user to for authentication
|
|
72
|
+
- `redirect_uri` - The redirect URI for the callback
|
|
73
|
+
- `state` - The state parameter for CSRF protection
|
|
74
|
+
- `pkce` - PKCE parameters for the flow
|
|
75
|
+
- `response_uri` - The response URI from the provider callback
|
|
76
|
+
- `options` - Additional configuration options
|
|
77
|
+
|
|
78
|
+
## Instance Methods
|
|
79
|
+
|
|
80
|
+
### `build_authorization_uri`
|
|
81
|
+
|
|
82
|
+
Builds the authorization URI for the authentication flow using the associated scheme.
|
|
83
|
+
|
|
84
|
+
**Parameters:**
|
|
85
|
+
- `redirect_uri` (String, optional): The redirect URI for the callback
|
|
86
|
+
- `state` (String, optional): The state parameter for CSRF protection
|
|
87
|
+
|
|
88
|
+
**Returns:**
|
|
89
|
+
- String: The authorization URI
|
|
90
|
+
|
|
91
|
+
**Examples:**
|
|
92
|
+
|
|
93
|
+
```ruby
|
|
94
|
+
config = Legate::Auth::Config.new(
|
|
95
|
+
scheme: oauth2_scheme,
|
|
96
|
+
credential: oauth2_credential
|
|
97
|
+
)
|
|
98
|
+
|
|
99
|
+
auth_uri = config.build_authorization_uri(
|
|
100
|
+
'https://app.example.com/callback',
|
|
101
|
+
SecureRandom.hex(16)
|
|
102
|
+
)
|
|
103
|
+
```
|
|
104
|
+
|
|
105
|
+
### `to_h`
|
|
106
|
+
|
|
107
|
+
Converts the configuration to a hash.
|
|
108
|
+
|
|
109
|
+
**Parameters:**
|
|
110
|
+
- `include_credentials` (Boolean, optional): Whether to include credential data (default: false)
|
|
111
|
+
|
|
112
|
+
**Returns:**
|
|
113
|
+
- Hash: A hash representation of the configuration
|
|
114
|
+
|
|
115
|
+
**Examples:**
|
|
116
|
+
|
|
117
|
+
```ruby
|
|
118
|
+
config = Legate::Auth::Config.new(
|
|
119
|
+
scheme: oauth2_scheme,
|
|
120
|
+
credential: oauth2_credential,
|
|
121
|
+
auth_request_id: 'req_123456'
|
|
122
|
+
)
|
|
123
|
+
|
|
124
|
+
# Without credentials (safe for logging)
|
|
125
|
+
puts config.to_h
|
|
126
|
+
|
|
127
|
+
# With credentials included
|
|
128
|
+
puts config.to_h(include_credentials: true)
|
|
129
|
+
```
|
|
130
|
+
|
|
131
|
+
### `validate_response!`
|
|
132
|
+
|
|
133
|
+
Validates an authentication response against this request configuration (matching request ID, presence of a response URI, and state).
|
|
134
|
+
|
|
135
|
+
**Parameters:**
|
|
136
|
+
- `response_config` (Legate::Auth::Config): The response configuration to validate against this request
|
|
137
|
+
|
|
138
|
+
**Returns:**
|
|
139
|
+
- Boolean: `true` if the response is valid
|
|
140
|
+
|
|
141
|
+
**Raises:**
|
|
142
|
+
- `Legate::Auth::ConfigurationError`: If the response is invalid (ID mismatch, missing response URI, or state mismatch)
|
|
143
|
+
|
|
144
|
+
**Examples:**
|
|
145
|
+
|
|
146
|
+
```ruby
|
|
147
|
+
# Validate a response Config against the original request Config
|
|
148
|
+
config.validate_response!(response_config)
|
|
149
|
+
```
|
|
150
|
+
|
|
151
|
+
## Usage in Authentication Flows
|
|
152
|
+
|
|
153
|
+
The `Config` class is a key component in interactive authentication flows:
|
|
154
|
+
|
|
155
|
+
1. **Creation**: A `Config` is created with the scheme and credential
|
|
156
|
+
2. **URI Generation**: The config builds the authorization URI via `build_authorization_uri`
|
|
157
|
+
3. **User Redirection**: The application redirects the user to the `auth_uri`
|
|
158
|
+
4. **Callback Handling**: When the user completes authentication, the provider redirects back with an authorization code or token
|
|
159
|
+
5. **Request Matching**: The application matches the callback to the original request using the `auth_request_id`
|
|
160
|
+
|
|
161
|
+
Here's an example of how it's used in a typical OAuth2 flow:
|
|
162
|
+
|
|
163
|
+
```ruby
|
|
164
|
+
# 1. Configure the OAuth2 scheme and credential
|
|
165
|
+
scheme = Legate::Auth::Schemes::OAuth2.new(
|
|
166
|
+
authorization_url: 'https://auth.example.com/authorize',
|
|
167
|
+
token_url: 'https://auth.example.com/token',
|
|
168
|
+
scopes: ['profile', 'email']
|
|
169
|
+
)
|
|
170
|
+
|
|
171
|
+
credential = Legate::Auth::Credential.new(
|
|
172
|
+
auth_type: :oauth2,
|
|
173
|
+
client_id: ENV['CLIENT_ID'],
|
|
174
|
+
client_secret: ENV['CLIENT_SECRET']
|
|
175
|
+
)
|
|
176
|
+
|
|
177
|
+
# 2. Create a Config and build the authorization URI
|
|
178
|
+
config = Legate::Auth::Config.new(
|
|
179
|
+
scheme: scheme,
|
|
180
|
+
credential: credential
|
|
181
|
+
)
|
|
182
|
+
|
|
183
|
+
auth_uri = config.build_authorization_uri(
|
|
184
|
+
'https://app.example.com/callback',
|
|
185
|
+
SecureRandom.hex(16)
|
|
186
|
+
)
|
|
187
|
+
|
|
188
|
+
# 3. In a web application, redirect the user to the auth URI
|
|
189
|
+
# redirect_to auth_uri
|
|
190
|
+
|
|
191
|
+
# 4. When the user is redirected back, set the response URI on the config
|
|
192
|
+
config.response_uri = 'https://app.example.com/callback?code=12345&state=abc123'
|
|
193
|
+
|
|
194
|
+
# 5. Exchange the authorization code for a token
|
|
195
|
+
# (exchange_token reads code/state from config.response_uri and verifies state)
|
|
196
|
+
token = scheme.exchange_token(config, credential)
|
|
197
|
+
```
|
|
198
|
+
|
|
199
|
+
## Security Considerations
|
|
200
|
+
|
|
201
|
+
- The `auth_request_id` should be cryptographically secure to prevent request forgery
|
|
202
|
+
- State parameters should be validated on callback to prevent CSRF attacks
|
|
203
|
+
- The `auth_uri` should always use HTTPS to protect the authentication process
|
|
204
|
+
|
|
205
|
+
## See Also
|
|
206
|
+
|
|
207
|
+
- [Legate::Auth::Scheme](./scheme)
|
|
208
|
+
- [Legate::Auth::Schemes::OAuth2](./schemes/oauth2)
|
|
209
|
+
- [Legate::Auth::Schemes::OpenIDConnect](./schemes/openid_connect)
|
|
210
|
+
- [Legate::Auth::ExchangedCredential](./exchanged_credential)
|
|
@@ -0,0 +1,246 @@
|
|
|
1
|
+
# Legate::Auth::Credential
|
|
2
|
+
|
|
3
|
+
The `Credential` class represents authentication credentials required by different authentication schemes. It handles different types of credentials such as API keys, OAuth2 client credentials, service account keys, and HTTP Bearer tokens.
|
|
4
|
+
|
|
5
|
+
## Overview
|
|
6
|
+
|
|
7
|
+
A credential contains the initial authentication information needed to begin an authentication flow or to directly authenticate requests. It can handle different credential types and supports environment variable resolution for sensitive values.
|
|
8
|
+
|
|
9
|
+
## Class Constants
|
|
10
|
+
|
|
11
|
+
- `VALID_TYPES`: Valid credential types - `:api_key`, `:oauth2`, `:oidc`, `:service_account`, `:google_service_account`, `:http_bearer`, `:basic`
|
|
12
|
+
- `ENV_PREFIX`: Prefix for environment variable references (`'ENV:'`)
|
|
13
|
+
|
|
14
|
+
## Class Methods
|
|
15
|
+
|
|
16
|
+
### `new`
|
|
17
|
+
|
|
18
|
+
Creates a new credential instance.
|
|
19
|
+
|
|
20
|
+
**Parameters:**
|
|
21
|
+
- `auth_type` (Symbol): The type of authentication (:api_key, :oauth2, :oidc, :service_account, :http_bearer)
|
|
22
|
+
- `kwargs` (Hash): Additional attributes for the specific auth type
|
|
23
|
+
|
|
24
|
+
**Raises:**
|
|
25
|
+
- `Legate::Auth::CredentialError`: If the credential is invalid
|
|
26
|
+
|
|
27
|
+
**Examples:**
|
|
28
|
+
|
|
29
|
+
```ruby
|
|
30
|
+
# API Key credential
|
|
31
|
+
credential = Legate::Auth::Credential.new(
|
|
32
|
+
auth_type: :api_key,
|
|
33
|
+
api_key: 'my-api-key'
|
|
34
|
+
)
|
|
35
|
+
|
|
36
|
+
# OAuth2 credential
|
|
37
|
+
credential = Legate::Auth::Credential.new(
|
|
38
|
+
auth_type: :oauth2,
|
|
39
|
+
client_id: 'my-client-id',
|
|
40
|
+
client_secret: 'my-client-secret'
|
|
41
|
+
)
|
|
42
|
+
|
|
43
|
+
# OAuth2 credential with environment variable
|
|
44
|
+
credential = Legate::Auth::Credential.new(
|
|
45
|
+
auth_type: :oauth2,
|
|
46
|
+
client_id: 'my-client-id',
|
|
47
|
+
client_secret: 'ENV:MY_CLIENT_SECRET'
|
|
48
|
+
)
|
|
49
|
+
|
|
50
|
+
# Service Account credential (service_account_key is a raw JSON string)
|
|
51
|
+
credential = Legate::Auth::Credential.new(
|
|
52
|
+
auth_type: :service_account,
|
|
53
|
+
service_account_key: File.read('service-account.json')
|
|
54
|
+
)
|
|
55
|
+
|
|
56
|
+
# Service Account credential from a file path
|
|
57
|
+
credential = Legate::Auth::Credential.new(
|
|
58
|
+
auth_type: :service_account,
|
|
59
|
+
service_account_key_file: '/path/to/service-account.json'
|
|
60
|
+
)
|
|
61
|
+
|
|
62
|
+
# HTTP Bearer token
|
|
63
|
+
credential = Legate::Auth::Credential.new(
|
|
64
|
+
auth_type: :http_bearer,
|
|
65
|
+
bearer_token: 'my-bearer-token'
|
|
66
|
+
)
|
|
67
|
+
```
|
|
68
|
+
|
|
69
|
+
## Instance Methods
|
|
70
|
+
|
|
71
|
+
### `[]`
|
|
72
|
+
|
|
73
|
+
Gets an attribute value, optionally resolving environment variables.
|
|
74
|
+
|
|
75
|
+
**Parameters:**
|
|
76
|
+
- `name` (Symbol, String): The attribute name
|
|
77
|
+
- `resolve_env` (Boolean, optional): Whether to resolve environment variables (default: true)
|
|
78
|
+
|
|
79
|
+
**Returns:**
|
|
80
|
+
- The attribute value, or nil if not present
|
|
81
|
+
|
|
82
|
+
**Raises:**
|
|
83
|
+
- `Legate::Auth::EnvironmentVariableNotFoundError`: If an environment variable is not found
|
|
84
|
+
|
|
85
|
+
**Examples:**
|
|
86
|
+
|
|
87
|
+
```ruby
|
|
88
|
+
# Get a regular attribute
|
|
89
|
+
client_id = credential[:client_id]
|
|
90
|
+
|
|
91
|
+
# Get an attribute without resolving environment variables
|
|
92
|
+
raw_value = credential[:client_secret, resolve_env: false]
|
|
93
|
+
|
|
94
|
+
# Get an attribute with environment variable resolution (default)
|
|
95
|
+
resolved_value = credential[:client_secret]
|
|
96
|
+
```
|
|
97
|
+
|
|
98
|
+
### `[]=`
|
|
99
|
+
|
|
100
|
+
Sets an attribute value.
|
|
101
|
+
|
|
102
|
+
**Parameters:**
|
|
103
|
+
- `name` (Symbol, String): The attribute name
|
|
104
|
+
- `value` (Object): The attribute value
|
|
105
|
+
|
|
106
|
+
**Examples:**
|
|
107
|
+
|
|
108
|
+
```ruby
|
|
109
|
+
# Set an attribute
|
|
110
|
+
credential[:client_id] = 'new-client-id'
|
|
111
|
+
|
|
112
|
+
# Set an environment variable reference
|
|
113
|
+
credential[:client_secret] = 'ENV:NEW_CLIENT_SECRET'
|
|
114
|
+
```
|
|
115
|
+
|
|
116
|
+
### `to_h`
|
|
117
|
+
|
|
118
|
+
Converts the credential to a hash.
|
|
119
|
+
|
|
120
|
+
**Parameters:**
|
|
121
|
+
- `resolve_env` (Boolean, optional): Whether to resolve environment variables (default: false)
|
|
122
|
+
|
|
123
|
+
**Returns:**
|
|
124
|
+
- Hash: A hash representation of the credential
|
|
125
|
+
|
|
126
|
+
**Examples:**
|
|
127
|
+
|
|
128
|
+
```ruby
|
|
129
|
+
# Get hash representation without resolving environment variables
|
|
130
|
+
hash = credential.to_h
|
|
131
|
+
|
|
132
|
+
# Get hash representation with environment variables resolved
|
|
133
|
+
resolved_hash = credential.to_h(resolve_env: true)
|
|
134
|
+
```
|
|
135
|
+
|
|
136
|
+
### `has_attribute?`
|
|
137
|
+
|
|
138
|
+
Checks if the credential has an attribute.
|
|
139
|
+
|
|
140
|
+
**Parameters:**
|
|
141
|
+
- `name` (Symbol, String): The attribute name
|
|
142
|
+
|
|
143
|
+
**Returns:**
|
|
144
|
+
- Boolean: True if the attribute exists
|
|
145
|
+
|
|
146
|
+
**Examples:**
|
|
147
|
+
|
|
148
|
+
```ruby
|
|
149
|
+
# Check if an attribute exists
|
|
150
|
+
if credential.has_attribute?(:client_id)
|
|
151
|
+
# Use the client_id
|
|
152
|
+
end
|
|
153
|
+
```
|
|
154
|
+
|
|
155
|
+
## Required Attributes by Type
|
|
156
|
+
|
|
157
|
+
Each credential type requires specific attributes:
|
|
158
|
+
|
|
159
|
+
| Type | Required Attributes | Description |
|
|
160
|
+
|------|---------------------|-------------|
|
|
161
|
+
| `:api_key` | `:api_key` | The API key for authentication |
|
|
162
|
+
| `:oauth2` | `:client_id` | The OAuth2 client ID |
|
|
163
|
+
| `:oidc` | `:client_id` | The OpenID Connect client ID |
|
|
164
|
+
| `:service_account` | `:service_account_key` or `:service_account_key_file` | The service account key or key file |
|
|
165
|
+
| `:google_service_account` | `:service_account_key` or `:service_account_key_file` | The Google service account key or key file |
|
|
166
|
+
| `:http_bearer` | `:bearer_token` | The Bearer token |
|
|
167
|
+
|
|
168
|
+
## Environment Variable Resolution
|
|
169
|
+
|
|
170
|
+
The Credential class supports referencing environment variables for sensitive values by prefixing the value with `ENV:`:
|
|
171
|
+
|
|
172
|
+
```ruby
|
|
173
|
+
# Reference an environment variable
|
|
174
|
+
credential = Legate::Auth::Credential.new(
|
|
175
|
+
auth_type: :oauth2,
|
|
176
|
+
client_id: 'my-client-id',
|
|
177
|
+
client_secret: 'ENV:MY_CLIENT_SECRET'
|
|
178
|
+
)
|
|
179
|
+
|
|
180
|
+
# When accessing the attribute, the environment variable is resolved
|
|
181
|
+
secret = credential[:client_secret] # Resolves to the value of ENV['MY_CLIENT_SECRET']
|
|
182
|
+
```
|
|
183
|
+
|
|
184
|
+
## Examples
|
|
185
|
+
|
|
186
|
+
### API Key Authentication
|
|
187
|
+
|
|
188
|
+
```ruby
|
|
189
|
+
# Standard API key
|
|
190
|
+
credential = Legate::Auth::Credential.new(
|
|
191
|
+
auth_type: :api_key,
|
|
192
|
+
api_key: 'my-api-key'
|
|
193
|
+
)
|
|
194
|
+
|
|
195
|
+
# API key from environment variable
|
|
196
|
+
credential = Legate::Auth::Credential.new(
|
|
197
|
+
auth_type: :api_key,
|
|
198
|
+
api_key: 'ENV:API_KEY'
|
|
199
|
+
)
|
|
200
|
+
|
|
201
|
+
# API key with additional options
|
|
202
|
+
credential = Legate::Auth::Credential.new(
|
|
203
|
+
auth_type: :api_key,
|
|
204
|
+
api_key: 'my-api-key',
|
|
205
|
+
location: 'header', # Where to place the API key
|
|
206
|
+
name: 'X-Custom-API-Key' # Name of the header or parameter
|
|
207
|
+
)
|
|
208
|
+
```
|
|
209
|
+
|
|
210
|
+
### OAuth2 Authentication
|
|
211
|
+
|
|
212
|
+
```ruby
|
|
213
|
+
credential = Legate::Auth::Credential.new(
|
|
214
|
+
auth_type: :oauth2,
|
|
215
|
+
client_id: 'ENV:OAUTH_CLIENT_ID',
|
|
216
|
+
client_secret: 'ENV:OAUTH_CLIENT_SECRET'
|
|
217
|
+
)
|
|
218
|
+
```
|
|
219
|
+
|
|
220
|
+
### Service Account Authentication
|
|
221
|
+
|
|
222
|
+
```ruby
|
|
223
|
+
# service_account_key takes the raw JSON string (not a parsed Hash)
|
|
224
|
+
credential = Legate::Auth::Credential.new(
|
|
225
|
+
auth_type: :service_account,
|
|
226
|
+
service_account_key: File.read('service-account.json')
|
|
227
|
+
)
|
|
228
|
+
|
|
229
|
+
# Or point at the file directly with service_account_key_file
|
|
230
|
+
credential = Legate::Auth::Credential.new(
|
|
231
|
+
auth_type: :service_account,
|
|
232
|
+
service_account_key_file: '/path/to/service-account.json'
|
|
233
|
+
)
|
|
234
|
+
```
|
|
235
|
+
|
|
236
|
+
## Security Considerations
|
|
237
|
+
|
|
238
|
+
- Always use environment variables (`ENV:` prefix) for sensitive values like client secrets and API keys
|
|
239
|
+
- Never hardcode sensitive credentials in your code
|
|
240
|
+
- The `resolve_env: false` option can be useful for logging to avoid exposing sensitive values
|
|
241
|
+
|
|
242
|
+
## See Also
|
|
243
|
+
|
|
244
|
+
- [Legate::Auth::Scheme](./scheme)
|
|
245
|
+
- [Legate::Auth::ExchangedCredential](./exchanged_credential)
|
|
246
|
+
- [Legate::Auth::TokenManager](./token_manager)
|