f808abff86
Fix JSON syntax errors in .devcontainer/devcontainer.json (removed
invalid JS-style // comments) and .devcontainer/opencode.json (removed
90+ trailing commas). Apply auto-fixes for end-of-file and trailing
whitespace issues across 100+ files. Fix SIM105 ruff violations in
benchmarks/core_circuit_breaker_bench.py (use contextlib.suppress).
Note: The security fix from issue #7478 (validate_path startswith bypass)
was already delivered to master in commit e18ac5f2. This PR as currently
structured is non-atomic (35 commits across 10+ issues) and needs
significant restructure before merge. This commit only addresses the
CI/pre-commit failures.
ISSUES CLOSED: #7478
849 lines
34 KiB
Gherkin
849 lines
34 KiB
Gherkin
Feature: Consolidated Action
|
|
Combined scenarios from: action_cli_additional_coverage, action_model, action_model_branch_coverage, action_schema
|
|
|
|
# ============================================================
|
|
# Originally from: action_cli_additional_coverage.feature
|
|
# Feature: Action CLI additional coverage
|
|
# ============================================================
|
|
|
|
Scenario: Resolve lifecycle service from container settings
|
|
Given a mocked container settings for action lifecycle
|
|
When I resolve the action lifecycle service
|
|
Then the lifecycle service should use container settings
|
|
|
|
|
|
Scenario: Resolve lifecycle service twice yields new instances
|
|
Given a mocked container settings for action lifecycle
|
|
When I resolve the action lifecycle service twice
|
|
Then the lifecycle service should use container settings
|
|
And the lifecycle service instances should be distinct
|
|
|
|
|
|
# ============================================================
|
|
# Originally from: action_model.feature
|
|
# Feature: Action Domain Model
|
|
# ============================================================
|
|
|
|
Scenario: Parse required string argument
|
|
When I parse the action argument "name:string:required:User name"
|
|
Then the argument name should be "name"
|
|
And the argument type should be "string"
|
|
And the argument should be required
|
|
And the argument description should be "User name"
|
|
|
|
|
|
Scenario: Parse optional integer argument
|
|
When I parse the action argument "count:integer:optional:Number of items"
|
|
Then the argument name should be "count"
|
|
And the argument type should be "integer"
|
|
And the argument should be optional
|
|
|
|
|
|
Scenario: Parse argument without description
|
|
When I parse the action argument "flag:boolean:required"
|
|
Then the argument name should be "flag"
|
|
And the argument type should be "boolean"
|
|
And the argument description should be empty
|
|
|
|
|
|
Scenario: Parse legacy short type names via _missing_
|
|
When I parse the action argument "name:str:required:User name"
|
|
Then the argument type should be "string"
|
|
When I parse the action argument "count:int:optional:Count"
|
|
Then the argument type should be "integer"
|
|
When I parse the action argument "flag:bool:required:Flag"
|
|
Then the argument type should be "boolean"
|
|
|
|
|
|
Scenario: Invalid argument format raises error
|
|
When I try to parse the action argument "invalid"
|
|
Then an argument parse error should be raised
|
|
|
|
|
|
Scenario: Invalid argument type raises error
|
|
When I try to parse the action argument "name:badtype:required:desc"
|
|
Then an argument parse error should be raised
|
|
|
|
|
|
Scenario: Invalid argument requirement raises error
|
|
When I try to parse the action argument "name:string:sometimes:desc"
|
|
Then an argument parse error should be raised
|
|
|
|
|
|
Scenario: Invalid argument name raises error
|
|
When I try to create an action argument with invalid name "1invalid"
|
|
Then a validation error should be raised
|
|
And the error should mention "Argument name must be a valid Python identifier"
|
|
|
|
|
|
Scenario: Invalid argument name with hyphen raises error
|
|
When I try to create an action argument with invalid name "invalid-name"
|
|
Then a validation error should be raised
|
|
And the error should mention "Argument name must be a valid Python identifier"
|
|
|
|
|
|
Scenario: Stringify action argument definition
|
|
When I parse the action argument "limit:integer:required:Limit value"
|
|
And I stringify the action argument
|
|
Then the argument definition string should be "limit:integer:required:Limit value"
|
|
|
|
|
|
Scenario: Stringify optional list argument definition
|
|
When I parse the action argument "targets:list:optional:Targets to check"
|
|
And I stringify the action argument
|
|
Then the argument definition string should be "targets:list:optional:Targets to check"
|
|
|
|
# Action Creation Tests
|
|
|
|
|
|
Scenario: Create minimal action
|
|
When I create an action with name "local/test-action" and definition of done "Tests pass"
|
|
Then the action should be created
|
|
And the action namespace should be "local"
|
|
And the action name should be "test-action"
|
|
And the action state should be "available"
|
|
|
|
|
|
Scenario: Create action with arguments
|
|
Given I have action arguments
|
|
| name | type | requirement | description |
|
|
| coverage | integer | required | Target coverage percent |
|
|
| framework | string | optional | Test framework to use |
|
|
When I create an action with these arguments
|
|
Then the action should have 2 arguments
|
|
And the action should have 1 required argument
|
|
And the action should have 1 optional argument
|
|
|
|
|
|
Scenario: Validate arguments - all required provided
|
|
Given I have an action with required argument "target:integer:required:Target value"
|
|
When I validate arguments with target 85
|
|
Then the validation should pass
|
|
|
|
|
|
Scenario: Validate arguments - missing required
|
|
Given I have an action with required argument "target:integer:required:Target value"
|
|
When I validate arguments without target
|
|
Then the validation should fail with "Missing required argument: target"
|
|
|
|
|
|
Scenario: Validate arguments - unknown argument
|
|
Given I have an action with required argument "target:integer:required:Target value"
|
|
When I validate arguments with target 85 and extra "foo"
|
|
Then the validation should fail with "Unknown argument: extra"
|
|
|
|
|
|
Scenario: Validate arguments - wrong type
|
|
Given I have an action with required argument "target:integer:required:Target value"
|
|
When I validate arguments with target as string "not-a-number"
|
|
Then the validation should fail with "must be an integer"
|
|
|
|
|
|
Scenario: Validate arguments - integer below minimum
|
|
Given I have an action with bounded integer argument "priority" min 1 max 5
|
|
When I validate arguments with "priority" set to 0
|
|
Then the validation should fail with "Argument priority must be >= 1"
|
|
|
|
|
|
Scenario: Validate arguments - integer above maximum
|
|
Given I have an action with bounded integer argument "priority" min 1 max 5
|
|
When I validate arguments with "priority" set to 6
|
|
Then the validation should fail with "Argument priority must be <= 5"
|
|
|
|
|
|
Scenario: Validate arguments - float expects numeric
|
|
Given I have an action with argument "threshold" of type "float"
|
|
When I validate arguments with "threshold" set to "high"
|
|
Then the validation should fail with "Argument threshold must be a number"
|
|
|
|
|
|
Scenario: Validate arguments - boolean expects boolean
|
|
Given I have an action with argument "dry_run" of type "boolean"
|
|
When I validate arguments with "dry_run" set to "yes"
|
|
Then the validation should fail with "Argument dry_run must be a boolean"
|
|
|
|
|
|
Scenario: Validate arguments - list expects list
|
|
Given I have an action with argument "targets" of type "list"
|
|
When I validate arguments with "targets" set to "api,cli"
|
|
Then the validation should fail with "Argument targets must be a list"
|
|
|
|
# Action State Tests
|
|
|
|
|
|
Scenario: New action starts in available state
|
|
When I create a new action
|
|
Then the action state should be "available"
|
|
|
|
|
|
Scenario: Action can be archived from available
|
|
Given I have an available action
|
|
When I set the action state to archived
|
|
Then the action state should be "archived"
|
|
|
|
# Actor Configuration Tests
|
|
|
|
|
|
Scenario: Action requires strategy and execution actors
|
|
When I try to create an action without strategy actor
|
|
Then a validation error should be raised
|
|
|
|
|
|
Scenario: Action can have optional review actor
|
|
When I create an action with review actor "local/code-reviewer"
|
|
Then the action should have a review actor
|
|
|
|
|
|
Scenario: Action can have optional estimation actor
|
|
When I create an action with estimation actor "local/cost-estimator"
|
|
Then the action should have an estimation actor
|
|
|
|
# Reusability Tests
|
|
|
|
|
|
Scenario: Actions are reusable by default
|
|
When I create a new action
|
|
Then the action should be reusable
|
|
|
|
|
|
Scenario: Action can be non-reusable
|
|
When I create a non-reusable action
|
|
Then the action should not be reusable
|
|
|
|
# Read-only Tests
|
|
|
|
|
|
Scenario: Actions are not read-only by default
|
|
When I create a new action
|
|
Then the action should not be read-only
|
|
|
|
|
|
Scenario: Action can be marked read-only
|
|
When I create a read-only action
|
|
Then the action should be read-only
|
|
|
|
# Invariants Sanitization Tests
|
|
|
|
|
|
Scenario: Invariants are sanitized on creation
|
|
When I create an action model with invariants " no secrets " and "" and " no secrets" and "keep data safe"
|
|
Then the action model invariants should be "no secrets" and "keep data safe"
|
|
|
|
|
|
Scenario: Invariants None defaults to empty list
|
|
When I create an action model with null invariants
|
|
Then the action model invariants count should be 0
|
|
|
|
# from_config Factory Tests
|
|
|
|
|
|
Scenario: Create action from config dict
|
|
When I create an action model from config with name "local/my-action" and description "Run tests" and dod "All tests green"
|
|
Then the action should be created
|
|
And the action name should be "my-action"
|
|
And the action model description should be "Run tests"
|
|
And the action state should be "available"
|
|
|
|
|
|
Scenario: from_config with arguments
|
|
When I create an action model from config with arguments
|
|
Then the action should have 2 arguments
|
|
And the action should have 1 required argument
|
|
And the action should have 1 optional argument
|
|
|
|
|
|
Scenario: from_config missing name raises error
|
|
When I try to create an action model from config missing "name"
|
|
Then an action model config error should be raised with "name"
|
|
|
|
|
|
Scenario: from_config missing description raises error
|
|
When I try to create an action model from config missing "description"
|
|
Then an action model config error should be raised with "description"
|
|
|
|
|
|
Scenario: from_config missing strategy_actor raises error
|
|
When I try to create an action model from config missing "strategy_actor"
|
|
Then an action model config error should be raised with "strategy_actor"
|
|
|
|
|
|
Scenario: from_config missing execution_actor raises error
|
|
When I try to create an action model from config missing "execution_actor"
|
|
Then an action model config error should be raised with "execution_actor"
|
|
|
|
|
|
Scenario: from_config missing definition_of_done raises error
|
|
When I try to create an action model from config missing "definition_of_done"
|
|
Then an action model config error should be raised with "definition_of_done"
|
|
|
|
# as_cli_dict Tests
|
|
|
|
|
|
Scenario: as_cli_dict returns stable dict
|
|
When I create an action model and call as_cli_dict
|
|
Then the action model cli dict should have key "name"
|
|
And the action model cli dict should have key "description"
|
|
And the action model cli dict should have key "state"
|
|
And the action model cli dict should have key "strategy_actor"
|
|
And the action model cli dict should have key "execution_actor"
|
|
And the action model cli dict should have key "definition_of_done"
|
|
And the action model cli dict should have key "reusable"
|
|
And the action model cli dict should have key "read_only"
|
|
And the action model cli dict should have key "created_at"
|
|
|
|
|
|
Scenario: as_cli_dict includes optional actors when set
|
|
When I create an action model with review actor and call as_cli_dict
|
|
Then the action model cli dict should have key "review_actor"
|
|
|
|
|
|
Scenario: as_cli_dict includes arguments when present
|
|
When I create an action model with arguments and call as_cli_dict
|
|
Then the action model cli dict should have key "arguments"
|
|
And the action model cli dict arguments count should be 1
|
|
|
|
# from_mapping Tests (ActionArgument)
|
|
|
|
|
|
Scenario: ActionArgument from_mapping basic
|
|
When I create an action argument from basic mapping "coverage" type "integer" required true
|
|
Then the argument name should be "coverage"
|
|
And the argument type should be "integer"
|
|
And the argument should be required
|
|
|
|
|
|
Scenario: ActionArgument from_mapping optional with default
|
|
When I create an action argument from mapping with default "framework" type "string" required false default "pytest"
|
|
Then the argument name should be "framework"
|
|
And the argument should be optional
|
|
And the action model argument default value should be "pytest"
|
|
|
|
|
|
Scenario: ActionArgument from_mapping missing name raises error
|
|
When I try to create an action argument from mapping missing name
|
|
Then an action model argument mapping error should be raised with "name"
|
|
|
|
|
|
Scenario: ActionArgument from_mapping missing type raises error
|
|
When I try to create an action argument from mapping missing type
|
|
Then an action model argument mapping error should be raised with "type"
|
|
|
|
# coerce_value Tests
|
|
|
|
|
|
Scenario: Coerce string value
|
|
Given I have an action model string argument named "label"
|
|
When I coerce action model value "hello" for the argument
|
|
Then the coerced action model value should be string "hello"
|
|
|
|
|
|
Scenario: Coerce integer value
|
|
Given I have an action model integer argument named "count"
|
|
When I coerce action model value "42" for the argument
|
|
Then the coerced action model value should be integer 42
|
|
|
|
|
|
Scenario: Coerce float value
|
|
Given I have an action model float argument named "ratio"
|
|
When I coerce action model value "3.14" for the argument
|
|
Then the coerced action model value should be float 3.14
|
|
|
|
|
|
Scenario: Coerce boolean true values
|
|
Given I have an action model boolean argument named "flag"
|
|
When I coerce action model value "true" for the argument
|
|
Then the coerced action model value should be boolean true
|
|
When I coerce action model value "yes" for the argument
|
|
Then the coerced action model value should be boolean true
|
|
When I coerce action model value "1" for the argument
|
|
Then the coerced action model value should be boolean true
|
|
|
|
|
|
Scenario: Coerce boolean false values
|
|
Given I have an action model boolean argument named "flag"
|
|
When I coerce action model value "false" for the argument
|
|
Then the coerced action model value should be boolean false
|
|
When I coerce action model value "no" for the argument
|
|
Then the coerced action model value should be boolean false
|
|
When I coerce action model value "0" for the argument
|
|
Then the coerced action model value should be boolean false
|
|
|
|
|
|
Scenario: Coerce invalid boolean raises error
|
|
Given I have an action model boolean argument named "flag"
|
|
When I try to coerce action model value "maybe" for the argument
|
|
Then an action model coerce error should be raised
|
|
|
|
|
|
Scenario: Coerce invalid integer raises error
|
|
Given I have an action model integer argument named "count"
|
|
When I try to coerce action model value "abc" for the argument
|
|
Then an action model coerce error should be raised
|
|
|
|
|
|
Scenario: Coerce list value
|
|
Given I have an action model list argument named "items"
|
|
When I coerce action model value "a, b, c" for the argument
|
|
Then the coerced action model value should be list with 3 items
|
|
|
|
# render_template Tests
|
|
|
|
|
|
Scenario: Render template with arguments
|
|
When I create an action model with description "Cover ${target}% for ${module}"
|
|
And I render action model description with target "90" and module "api"
|
|
Then the rendered action model description should be "Cover 90% for api"
|
|
|
|
|
|
Scenario: Render template missing placeholder raises error
|
|
When I create an action model with description "Cover ${target}% for ${module}"
|
|
And I try to render action model description with only target "90"
|
|
Then an action model template error should be raised
|
|
|
|
|
|
Scenario: Render definition of done with arguments
|
|
When I create an action model with dod template for module and target
|
|
And I render action model dod with target "80" and module "core"
|
|
Then the rendered action model dod should be "All tests in core pass with 80% coverage"
|
|
|
|
# inputs_schema Validation Tests
|
|
|
|
|
|
Scenario: inputs_schema accepts valid dict
|
|
When I create an action model with inputs schema type "object" and required "name"
|
|
Then the action should be created
|
|
And the action model inputs schema should not be none
|
|
|
|
|
|
Scenario: inputs_schema accepts None
|
|
When I create an action model with null inputs schema
|
|
Then the action should be created
|
|
And the action model inputs schema should be none
|
|
|
|
|
|
Scenario: inputs_schema rejects non-dict
|
|
When I try to create an action model with inputs schema as string
|
|
Then a validation error should be raised
|
|
|
|
# automation_profile Validation Tests
|
|
|
|
|
|
Scenario: automation_profile trims whitespace
|
|
When I create an action model with automation profile " fast "
|
|
Then the action model automation profile should be "fast"
|
|
|
|
|
|
Scenario: automation_profile blank becomes None
|
|
When I create an action model with automation profile " "
|
|
Then the action model automation profile should be none
|
|
|
|
|
|
Scenario: automation_profile None stays None
|
|
When I create an action model with null automation profile
|
|
Then the action model automation profile should be none
|
|
|
|
|
|
# ============================================================
|
|
# Originally from: action_model_branch_coverage.feature
|
|
# Feature: Action Model Branch Coverage
|
|
# ============================================================
|
|
|
|
Scenario: Validate arguments - valid float value passes validation
|
|
Given I have an action with a float argument named "ratio"
|
|
When I validate the action arguments with "ratio" as float 3.14
|
|
Then the action argument validation should pass with no errors
|
|
|
|
|
|
Scenario: Validate arguments - valid integer value for float argument passes
|
|
Given I have an action with a float argument named "score"
|
|
When I validate the action arguments with "score" as integer 42
|
|
Then the action argument validation should pass with no errors
|
|
|
|
|
|
Scenario: Validate arguments - valid boolean true passes validation
|
|
Given I have an action with a boolean argument named "verbose"
|
|
When I validate the action arguments with "verbose" as boolean true
|
|
Then the action argument validation should pass with no errors
|
|
|
|
|
|
Scenario: Validate arguments - valid boolean false passes validation
|
|
Given I have an action with a boolean argument named "dry_run"
|
|
When I validate the action arguments with "dry_run" as boolean false
|
|
Then the action argument validation should pass with no errors
|
|
|
|
|
|
Scenario: Validate arguments - valid list passes validation
|
|
Given I have an action with a list argument named "targets"
|
|
When I validate the action arguments with "targets" as list "api,cli,web"
|
|
Then the action argument validation should pass with no errors
|
|
|
|
|
|
Scenario: Validate arguments - empty list passes validation
|
|
Given I have an action with a list argument named "items"
|
|
When I validate the action arguments with "items" as an empty list
|
|
Then the action argument validation should pass with no errors
|
|
|
|
# Float type with min/max - the code currently does NOT check min/max for float,
|
|
# so a float with min/max set should still pass (only int has min/max enforcement)
|
|
|
|
|
|
Scenario: Validate arguments - float with min max bounds still passes
|
|
Given I have an action with a bounded float argument "temperature" min 0.0 max 1.0
|
|
When I validate the action arguments with "temperature" as float 0.5
|
|
Then the action argument validation should pass with no errors
|
|
|
|
# Multiple argument types in one action
|
|
|
|
|
|
Scenario: Validate arguments - mixed types all valid
|
|
Given I have an action with mixed argument types
|
|
| name | type | requirement |
|
|
| label | str | required |
|
|
| count | int | required |
|
|
| ratio | float | required |
|
|
| enabled | bool | required |
|
|
| tags | list | optional |
|
|
When I validate the action with all mixed arguments provided correctly
|
|
Then the action argument validation should pass with no errors
|
|
|
|
# ActionArgument.parse for float and list types
|
|
|
|
|
|
Scenario: Parse a float type action argument
|
|
When I parse an action argument definition "ratio:float:required:Ratio value"
|
|
Then the parsed argument name should be "ratio"
|
|
And the parsed argument type should be "float"
|
|
And the parsed argument should be required
|
|
And the parsed argument description should be "Ratio value"
|
|
|
|
|
|
Scenario: Parse a list type action argument
|
|
When I parse an action argument definition "items:list:optional:List of items"
|
|
Then the parsed argument name should be "items"
|
|
And the parsed argument type should be "list"
|
|
And the parsed argument should be optional
|
|
And the parsed argument description should be "List of items"
|
|
|
|
# Action metadata fields
|
|
|
|
|
|
Scenario: Action with tags and created_by metadata
|
|
When I create an action with tags "ci,testing,coverage" and created_by "user-123"
|
|
Then the action should have 3 tags
|
|
And the action created_by should be "user-123"
|
|
|
|
|
|
Scenario: Action with description and long description
|
|
When I create an action with description "Quick summary" and long description "This is a detailed description of the action and what it does."
|
|
Then the action description should be "Quick summary"
|
|
And the action long description should contain "detailed description"
|
|
|
|
|
|
Scenario: Action with apply actor set
|
|
When I create an action with apply_actor "local/merge-bot"
|
|
Then the action apply_actor should be "local/merge-bot"
|
|
|
|
# Validate assignment on ActionArgument model config
|
|
|
|
|
|
Scenario: ActionArgument validates assignment on field change
|
|
Given I have a parsed action argument from "count:int:required:A counter"
|
|
When I change the action argument description to "Updated counter"
|
|
Then the action argument description should now be "Updated counter"
|
|
|
|
# Validate assignment on Action model config
|
|
|
|
|
|
Scenario: Action validates assignment when state is changed
|
|
Given I have a newly created action in available state
|
|
When I change the action state to "archived"
|
|
Then the action current state should be "archived"
|
|
|
|
# String type passes through without type check (default/no-op path)
|
|
|
|
|
|
Scenario: Validate arguments - string value needs no type enforcement
|
|
Given I have an action with a string argument named "label"
|
|
When I validate the action arguments with "label" as string "hello"
|
|
Then the action argument validation should pass with no errors
|
|
|
|
|
|
# ============================================================
|
|
# Originally from: action_schema.feature
|
|
# Feature: Action YAML schema validation
|
|
# ============================================================
|
|
|
|
Scenario: Load a minimal valid action YAML
|
|
Given an action YAML string with only required fields
|
|
When I validate the action schema
|
|
Then the action schema validation should succeed
|
|
And the action config name should be "local/simple-action"
|
|
And the action config strategy_actor should be "openai/gpt-4"
|
|
And the action config execution_actor should be "openai/gpt-4"
|
|
|
|
|
|
Scenario: Load a valid action YAML with all optional fields
|
|
Given an action YAML string with all optional fields populated
|
|
When I validate the action schema
|
|
Then the action schema validation should succeed
|
|
And the action config reusable should be true
|
|
And the action config read_only should be false
|
|
And the action config state should be "available"
|
|
And the action config estimation_actor should be "local/estimator"
|
|
And the action config review_actor should be "local/reviewer"
|
|
And the action config apply_actor should be "local/applier"
|
|
And the action config invariant_actor should be "local/invariant-resolver"
|
|
|
|
|
|
Scenario: Load the simple example YAML
|
|
Given the action YAML file "examples/actions/simple.yaml"
|
|
When I validate the action schema from file
|
|
Then the action schema validation should succeed
|
|
|
|
|
|
Scenario: Load the invariant-heavy example YAML
|
|
Given the action YAML file "examples/actions/invariant-heavy.yaml"
|
|
When I validate the action schema from file
|
|
Then the action schema validation should succeed
|
|
|
|
|
|
Scenario: Load the read-only example YAML
|
|
Given the action YAML file "examples/actions/read-only.yaml"
|
|
When I validate the action schema from file
|
|
Then the action schema validation should succeed
|
|
|
|
|
|
Scenario: Load the estimation-actor example YAML
|
|
Given the action YAML file "examples/actions/estimation-actor.yaml"
|
|
When I validate the action schema from file
|
|
Then the action schema validation should succeed
|
|
|
|
|
|
Scenario: Load the inputs-schema example YAML
|
|
Given the action YAML file "examples/actions/inputs-schema.yaml"
|
|
When I validate the action schema from file
|
|
Then the action schema validation should succeed
|
|
|
|
|
|
Scenario: Optional fields have correct defaults when omitted
|
|
Given an action YAML string with only required fields
|
|
When I validate the action schema
|
|
Then the action schema validation should succeed
|
|
And the action config reusable should be true
|
|
And the action config read_only should be false
|
|
And the action config state should be "available"
|
|
And the action config invariants list should be empty
|
|
And the action config arguments list should be empty
|
|
|
|
|
|
Scenario: Action with arguments validates correctly
|
|
Given an action YAML string with typed arguments
|
|
When I validate the action schema
|
|
Then the action schema validation should succeed
|
|
And the action config should have 2 arguments
|
|
And action argument 0 name should be "target_coverage"
|
|
And action argument 0 type should be "integer"
|
|
And action argument 1 name should be "test_command"
|
|
And action argument 1 type should be "string"
|
|
|
|
# ────────────────────────────────────────────────────────────
|
|
# Invalid schema scenarios
|
|
# ────────────────────────────────────────────────────────────
|
|
|
|
|
|
Scenario: Missing name field produces a clear error
|
|
Given an action YAML string missing the "name" field
|
|
When I validate the action schema expecting failure
|
|
Then the action schema validation should fail
|
|
And the action schema error should mention "name"
|
|
|
|
|
|
Scenario: Missing strategy_actor produces a clear error
|
|
Given an action YAML string missing the "strategy_actor" field
|
|
When I validate the action schema expecting failure
|
|
Then the action schema validation should fail
|
|
And the action schema error should mention "strategy_actor"
|
|
|
|
|
|
Scenario: Missing execution_actor produces a clear error
|
|
Given an action YAML string missing the "execution_actor" field
|
|
When I validate the action schema expecting failure
|
|
Then the action schema validation should fail
|
|
And the action schema error should mention "execution_actor"
|
|
|
|
|
|
Scenario: Missing definition_of_done produces a clear error
|
|
Given an action YAML string missing the "definition_of_done" field
|
|
When I validate the action schema expecting failure
|
|
Then the action schema validation should fail
|
|
And the action schema error should mention "definition_of_done"
|
|
|
|
|
|
Scenario: Missing description produces a clear error
|
|
Given an action YAML string missing the "description" field
|
|
When I validate the action schema expecting failure
|
|
Then the action schema validation should fail
|
|
And the action schema error should mention "description"
|
|
|
|
|
|
Scenario: Invalid namespaced name without slash
|
|
Given an action YAML string with name "invalid-name-no-slash"
|
|
When I validate the action schema expecting failure
|
|
Then the action schema validation should fail
|
|
And the action schema error should mention "namespace/name"
|
|
|
|
|
|
Scenario: Invalid namespaced name with special characters
|
|
Given an action YAML string with name "local/bad name!!"
|
|
When I validate the action schema expecting failure
|
|
Then the action schema validation should fail
|
|
And the action schema error should mention "namespace/name"
|
|
|
|
|
|
Scenario: Uppercase namespace is rejected by ActionConfigSchema
|
|
Given an action YAML string with name "MyOrg/my-action"
|
|
When I validate the action schema expecting failure
|
|
Then the action schema validation should fail
|
|
And the action schema error should mention "namespace/name"
|
|
|
|
|
|
Scenario: Uppercase name part is rejected by ActionConfigSchema
|
|
Given an action YAML string with name "myorg/MyAction"
|
|
When I validate the action schema expecting failure
|
|
Then the action schema validation should fail
|
|
And the action schema error should mention "namespace/name"
|
|
|
|
|
|
Scenario: Fully uppercase namespaced name is rejected by ActionConfigSchema
|
|
Given an action YAML string with name "MyOrg/MyAction"
|
|
When I validate the action schema expecting failure
|
|
Then the action schema validation should fail
|
|
And the action schema error should mention "namespace/name"
|
|
|
|
|
|
Scenario: Invalid argument type
|
|
Given an action YAML string with an argument of type "array"
|
|
When I validate the action schema expecting failure
|
|
Then the action schema validation should fail
|
|
And the action schema error should mention "type"
|
|
|
|
|
|
Scenario: Invalid state value
|
|
Given an action YAML string with state "draft"
|
|
When I validate the action schema expecting failure
|
|
Then the action schema validation should fail
|
|
And the action schema error should mention "state"
|
|
|
|
|
|
Scenario: Invalid argument name
|
|
Given an action YAML string with an argument named "123bad"
|
|
When I validate the action schema expecting failure
|
|
Then the action schema validation should fail
|
|
And the action schema error should mention "identifier"
|
|
|
|
|
|
Scenario: None YAML string raises ValueError
|
|
Given a None action YAML string
|
|
When I validate the action schema expecting failure
|
|
Then the action schema validation should fail
|
|
And the action schema error should mention "None"
|
|
|
|
|
|
Scenario: Empty YAML string raises ValueError
|
|
Given an empty action YAML string
|
|
When I validate the action schema expecting failure
|
|
Then the action schema validation should fail
|
|
And the action schema error should mention "empty"
|
|
|
|
|
|
Scenario: YAML that is a list instead of a mapping
|
|
Given an action YAML string that is a list
|
|
When I validate the action schema expecting failure
|
|
Then the action schema validation should fail
|
|
And the action schema error should mention "mapping"
|
|
|
|
|
|
Scenario: None file path raises ValueError
|
|
Given a None action YAML file path
|
|
When I validate the action schema from file expecting failure
|
|
Then the action schema validation should fail
|
|
And the action schema error should mention "None"
|
|
|
|
|
|
Scenario: Non-existent file raises FileNotFoundError
|
|
Given the action YAML file "examples/actions/nonexistent.yaml"
|
|
When I validate the action schema from file expecting failure
|
|
Then the action schema validation should fail
|
|
And the action schema error should mention "not found"
|
|
|
|
|
|
Scenario: Directory path raises ValueError
|
|
Given the action YAML directory path "examples/actions"
|
|
When I validate the action schema from file expecting failure
|
|
Then the action schema validation should fail
|
|
And the action schema error should mention "not a file"
|
|
|
|
# ────────────────────────────────────────────────────────────
|
|
# Invariant normalization scenarios
|
|
# ────────────────────────────────────────────────────────────
|
|
|
|
|
|
Scenario: Empty invariants are dropped
|
|
Given an action YAML string with empty invariant strings
|
|
When I validate the action schema
|
|
Then the action schema validation should succeed
|
|
And the action config invariants list should be empty
|
|
|
|
|
|
Scenario: Duplicate invariants are de-duplicated preserving order
|
|
Given an action YAML string with duplicate invariants
|
|
When I validate the action schema
|
|
Then the action schema validation should succeed
|
|
And the action config should have 2 invariants
|
|
And action invariant 0 should be "No secrets in code"
|
|
And action invariant 1 should be "All tests must pass"
|
|
|
|
|
|
Scenario: Invariant whitespace is trimmed
|
|
Given an action YAML string with whitespace-padded invariants
|
|
When I validate the action schema
|
|
Then the action schema validation should succeed
|
|
And action invariant 0 should be "Keep it clean"
|
|
|
|
# ────────────────────────────────────────────────────────────
|
|
# Key normalization scenarios
|
|
# ────────────────────────────────────────────────────────────
|
|
|
|
|
|
Scenario: camelCase keys are normalized to snake_case
|
|
Given an action YAML string with camelCase keys
|
|
When I validate the action schema
|
|
Then the action schema validation should succeed
|
|
And the action config strategy_actor should be "openai/gpt-4"
|
|
And the action config execution_actor should be "openai/gpt-4"
|
|
|
|
# ────────────────────────────────────────────────────────────
|
|
# Environment variable interpolation
|
|
# ────────────────────────────────────────────────────────────
|
|
|
|
|
|
Scenario: Environment variable interpolation in YAML values
|
|
Given the environment variable "TEST_ACTOR" is set to "openai/gpt-4"
|
|
And an action YAML string using env var "${TEST_ACTOR}" for strategy_actor
|
|
|
|
When I validate the action schema
|
|
Then the action schema validation should succeed
|
|
And the action config strategy_actor should be "openai/gpt-4"
|
|
|
|
# ────────────────────────────────────────────────────────────
|
|
# Round-trip serialization
|
|
# ────────────────────────────────────────────────────────────
|
|
|
|
|
|
Scenario: Schema model serializes to dict correctly
|
|
Given an action YAML string with all optional fields populated
|
|
When I validate the action schema
|
|
Then the action schema validation should succeed
|
|
And the action config model_dump should contain key "name"
|
|
And the action config model_dump should contain key "strategy_actor"
|