{
    "sourceFile": "cleanroom/tests/bdd/steps/backend_autodetect_steps.rs",
    "activeCommit": 0,
    "commits": [
        {
            "activePatchIndex": 0,
            "patches": [
                {
                    "date": 1760261841872,
                    "content": "Index: \n===================================================================\n--- \n+++ \n"
                }
            ],
            "date": 1760261841872,
            "name": "Commit-0",
            "content": "use super::super::world::CleanroomWorld;\nuse assert_cmd::Command;\nuse cucumber::{given, then, when};\nuse std::process::Output;\n\n/// Backend auto-detection step definitions for Cleanroom BDD tests\n///\n/// These steps handle backend auto-detection and preference ordering\n/// for different container engines and local execution.\n\n// ============================================================================\n// GIVEN steps - Setup preconditions\n// ============================================================================\n\n#[given(regex = r\"^docker is \"([^\"]+)\" available$\")]\nfn docker_availability(world: &mut CleanroomWorld, availability: String) {\n    match availability.as_str() {\n        \"available\" => {\n            // Check if Docker is actually available\n            let output = Command::new(\"docker\")\n                .arg(\"version\")\n                .output();\n            \n            let available = output.map(|o| o.status.success()).unwrap_or(false);\n            world.docker_available = Some(available);\n            \n            if !available {\n                panic!(\"Docker is marked as available but not found\");\n            }\n        }\n        \"unavailable\" => {\n            world.docker_available = Some(false);\n        }\n        \"maybe\" => {\n            // Check if Docker is available\n            let output = Command::new(\"docker\")\n                .arg(\"version\")\n                .output();\n            \n            let available = output.map(|o| o.status.success()).unwrap_or(false);\n            world.docker_available = Some(available);\n        }\n        _ => {\n            panic!(\"Unknown Docker availability: {}\", availability);\n        }\n    }\n}\n\n#[given(regex = r\"^podman is \"([^\"]+)\" available$\")]\nfn podman_availability(world: &mut CleanroomWorld, availability: String) {\n    match availability.as_str() {\n        \"available\" => {\n            // Check if Podman is actually available\n            let output = Command::new(\"podman\")\n                .arg(\"version\")\n                .output();\n            \n            let available = output.map(|o| o.status.success()).unwrap_or(false);\n            world.podman_available = Some(available);\n            \n            if !available {\n                panic!(\"Podman is marked as available but not found\");\n            }\n        }\n        \"unavailable\" => {\n            world.podman_available = Some(false);\n        }\n        \"maybe\" => {\n            // Check if Podman is available\n            let output = Command::new(\"podman\")\n                .arg(\"version\")\n                .output();\n            \n            let available = output.map(|o| o.status.success()).unwrap_or(false);\n            world.podman_available = Some(available);\n        }\n        _ => {\n            panic!(\"Unknown Podman availability: {}\", availability);\n        }\n    }\n}\n\n#[given(regex = r\"^environment CLEANROOM_BACKEND is unset$\")]\nfn cleanroom_backend_unset(world: &mut CleanroomWorld) {\n    world.unset_env(\"CLEANROOM_BACKEND\".to_string());\n}\n\n#[given(regex = r#\"^environment CLEANROOM_BACKEND=\"([^\"]+)\"$\"#)]\nfn cleanroom_backend_set(world: &mut CleanroomWorld, backend: String) {\n    world.set_env(\"CLEANROOM_BACKEND\".to_string(), backend);\n}\n\n// ============================================================================\n// WHEN steps - Execute actions\n// ============================================================================\n\n#[when(regex = r\"^I request backend \"([^\"]+)\"$\")]\nfn request_backend(world: &mut CleanroomWorld, backend: String) {\n    // Auto-detect backend based on availability and preferences\n    let resolved_backend = match backend.as_str() {\n        \"auto\" => {\n            // Check environment variable first\n            if let Some(env_backend) = world.environment.get(\"CLEANROOM_BACKEND\") {\n                env_backend.clone()\n            } else {\n                // Auto-detect based on availability\n                if world.docker_available.unwrap_or(false) {\n                    \"docker\".to_string()\n                } else if world.podman_available.unwrap_or(false) {\n                    \"podman\".to_string()\n                } else {\n                    \"local\".to_string()\n                }\n            }\n        }\n        \"docker\" => {\n            if world.docker_available.unwrap_or(false) {\n                \"docker\".to_string()\n            } else {\n                panic!(\"Docker backend requested but not available\");\n            }\n        }\n        \"podman\" => {\n            if world.podman_available.unwrap_or(false) {\n                \"podman\".to_string()\n            } else {\n                panic!(\"Podman backend requested but not available\");\n            }\n        }\n        \"local\" => \"local\".to_string(),\n        _ => {\n            panic!(\"Unknown backend: {}\", backend);\n        }\n    };\n    \n    world.set_backend(resolved_backend);\n}\n\n// ============================================================================\n// THEN steps - Verify outcomes\n// ============================================================================\n\n#[then(regex = r#\"^the resolved backend is one of \"([^\"]+)\"$\"#)]\nfn resolved_backend_is_one_of(world: &mut CleanroomWorld, expected_backends: String) {\n    let resolved_backend = world.current_backend.as_ref()\n        .expect(\"Backend should be resolved\");\n    \n    let backends: Vec<&str> = expected_backends.split(',').map(|s| s.trim()).collect();\n    \n    assert!(\n        backends.contains(&resolved_backend.as_str()),\n        \"Expected resolved backend to be one of {:?}, but got '{}'\",\n        backends, resolved_backend\n    );\n}\n\n#[then(regex = r\"^the resolved backend is \"([^\"]+)\"$\")]\nfn resolved_backend_is(world: &mut CleanroomWorld, expected_backend: String) {\n    let resolved_backend = world.current_backend.as_ref()\n        .expect(\"Backend should be resolved\");\n    \n    assert_eq!(\n        resolved_backend, &expected_backend,\n        \"Expected resolved backend '{}', but got '{}'\",\n        expected_backend, resolved_backend\n    );\n}\n\n#[then(regex = r\"^preference order is docker > podman > local given availability$\")]\nfn preference_order_is_docker_podman_local(world: &mut CleanroomWorld) {\n    let resolved_backend = world.current_backend.as_ref()\n        .expect(\"Backend should be resolved\");\n    \n    // Verify that the resolved backend follows the preference order\n    match resolved_backend.as_str() {\n        \"docker\" => {\n            // Docker should only be chosen if it's available\n            assert!(\n                world.docker_available.unwrap_or(false),\n                \"Docker should be available if chosen\"\n            );\n        }\n        \"podman\" => {\n            // Podman should only be chosen if Docker is not available but Podman is\n            assert!(\n                !world.docker_available.unwrap_or(false),\n                \"Docker should not be available if Podman is chosen\"\n            );\n            assert!(\n                world.podman_available.unwrap_or(false),\n                \"Podman should be available if chosen\"\n            );\n        }\n        \"local\" => {\n            // Local should only be chosen if neither Docker nor Podman are available\n            assert!(\n                !world.docker_available.unwrap_or(false),\n                \"Docker should not be available if local is chosen\"\n            );\n            assert!(\n                !world.podman_available.unwrap_or(false),\n                \"Podman should not be available if local is chosen\"\n            );\n        }\n        _ => {\n            panic!(\"Unknown resolved backend: {}\", resolved_backend);\n        }\n    }\n}\n\n#[then(regex = r\"^resolved backend is not \"([^\"]+)\" if a container engine is available$\")]\nfn resolved_backend_is_not_if_container_available(world: &mut CleanroomWorld, backend: String) {\n    let resolved_backend = world.current_backend.as_ref()\n        .expect(\"Backend should be resolved\");\n    \n    let container_available = world.docker_available.unwrap_or(false) || \n                             world.podman_available.unwrap_or(false);\n    \n    if container_available {\n        assert_ne!(\n            resolved_backend, &backend,\n            \"Resolved backend should not be '{}' when container engine is available\",\n            backend\n        );\n    }\n}\n\n#[then(regex = r\"^the scenario is skipped with reason \"([^\"]+)\"$\")]\nfn scenario_skipped_with_reason(world: &mut CleanroomWorld, expected_reason: String) {\n    let current_scenario = world.current_scenario.as_ref()\n        .expect(\"Current scenario should be set\");\n    \n    let skip_reason = world.skip_reasons.get(current_scenario)\n        .expect(\"Scenario should have skip reason\");\n    \n    assert!(\n        skip_reason.contains(&expected_reason),\n        \"Expected skip reason to contain '{}', but got '{}'\",\n        expected_reason, skip_reason\n    );\n}\n\n#[then(regex = r\"^podman-tagged scenarios are skipped$\")]\nfn podman_tagged_scenarios_are_skipped(world: &mut CleanroomWorld) {\n    // Check if Podman is unavailable\n    if !world.podman_available.unwrap_or(false) {\n        // Verify that Podman scenarios would be skipped\n        // In a real implementation, this would check scenario tags\n        assert!(\n            world.skip_reasons.values().any(|reason| reason.contains(\"podman\")),\n            \"Podman-tagged scenarios should be skipped when Podman is unavailable\"\n        );\n    }\n}\n\n#[then(regex = r\"^other scenarios run$\")]\nfn other_scenarios_run(world: &mut CleanroomWorld) {\n    // Verify that non-Podman scenarios can still run\n    // In a real implementation, this would check that other scenarios are not skipped\n    \n    let total_scenarios = world.scenarios.len();\n    let skipped_scenarios = world.skip_reasons.len();\n    \n    assert!(\n        skipped_scenarios < total_scenarios,\n        \"Some scenarios should still run, but all are skipped\"\n    );\n}\n"
        }
    ]
}