Feature: Project CLI commands (B0.cli.projects)
  As a CleverAgents user
  I want to manage projects via CLI commands
  So that I can create, list, show, link, unlink, and delete projects

  Background:
    Given a project CLI in-memory database is initialized

  # ── Create ────────────────────────────────────────────────────

  Scenario: Create a project with bare name defaults to local namespace
    When I run project create with name "my-app"
    Then the project "local/my-app" should exist
    And the project namespace should be "local"

  Scenario: Create a project with explicit namespace
    When I run project create with name "team/my-app"
    Then the project "team/my-app" should exist
    And the project namespace should be "team"

  Scenario: Create a project with description
    When I run project create named "my-app" described as "My test project"
    Then the project "local/my-app" should exist
    And the project description should be "My test project"

  Scenario: Create a project with invalid name fails
    When I run project create with invalid name "123bad"
    Then the create command should fail with exit code 1

  Scenario: Create a duplicate project fails
    Given a project "local/dup-test" already exists
    When I run project create with name "dup-test"
    Then the create command should fail with exit code 1

  Scenario: Create a project with reserved namespace fails
    When I run project create with invalid name "system/bad"
    Then the create command should fail with exit code 1

  Scenario: Create a project with invariants
    When I run project create named "inv-proj" with invariants "do not modify tests" plus "keep API stable"
    Then the project "local/inv-proj" should exist

  # ── List ─────────────────────────────────────────────────────

  Scenario: List projects shows created projects
    Given a project "local/proj-a" already exists
    And a project "local/proj-b" already exists
    When I list projects
    Then the project list should contain "local/proj-a"
    And the project list should contain "local/proj-b"

  Scenario: List projects with namespace filter
    Given a project "local/proj-x" already exists
    And a project "team/proj-y" already exists
    When I list projects with namespace "team"
    Then the project list should contain "team/proj-y"
    And the project list should not contain "local/proj-x"

  Scenario: List projects with regex filter
    Given a project "local/api-service" already exists
    And a project "local/web-app" already exists
    When I list projects with regex "api"
    Then the project list should contain "local/api-service"
    And the project list should not contain "local/web-app"

  Scenario: List projects with invalid regex fails
    When I list projects with invalid regex "[invalid"
    Then the list command should fail with exit code 1

  Scenario: List projects when empty shows message
    When I list projects
    Then the project CLI output should contain "No projects found"

  # ── Show ─────────────────────────────────────────────────────

  Scenario: Show project displays details
    Given a project "local/show-test" already exists with description "A test project"
    When I show project "local/show-test"
    Then the show output should contain "local/show-test"
    And the show output should contain "A test project"

  Scenario: Show nonexistent project fails
    When I show project "local/nonexistent"
    Then the show command should fail with exit code 1

  Scenario: Show project with linked resources
    Given a project "local/linked-proj" already exists
    And a resource is linked to project "local/linked-proj"
    When I show project "local/linked-proj"
    Then the show output should contain "linked_resources"

  # ── Link Resource ────────────────────────────────────────────

  Scenario: Link resource to project
    Given a project "local/link-test" already exists
    And a registered resource "my-resource" exists
    When I link resource "my-resource" to project "local/link-test"
    Then the link should succeed

  Scenario: Link resource read-only to project
    Given a project "local/ro-test" already exists
    And a registered resource "ro-resource" exists
    When I link resource "ro-resource" to project "local/ro-test" with read-only
    Then the link should succeed

  Scenario: Link resource to nonexistent project fails
    When I attempt to link to nonexistent project "local/no-such-project"
    Then the link command should fail with exit code 1

  Scenario: Link nonexistent resource to project fails
    Given a project "local/link-fail" already exists
    When I link nonexistent resource "no-such-resource" to project "local/link-fail"
    Then the link command should fail with exit code 1

  # ── Unlink Resource ──────────────────────────────────────────

  Scenario: Unlink resource from project
    Given a project "local/unlink-test" already exists
    And a resource is linked to project "local/unlink-test"
    When I unlink the resource from project "local/unlink-test" with yes
    Then the unlink should succeed

  Scenario: Unlink nonexistent resource from project fails
    Given a project "local/unlink-fail" already exists
    When I unlink nonexistent resource from project "local/unlink-fail" with yes
    Then the unlink command should fail with exit code 1

  # ── Delete ───────────────────────────────────────────────────

  Scenario: Delete project with confirmation
    Given a project "local/del-test" already exists
    When I delete project "local/del-test" with yes
    Then the project "local/del-test" should not exist

  Scenario: Delete nonexistent project fails
    When I delete project "local/never-existed" with yes
    Then the delete command should fail with exit code 1

  Scenario: Delete project with linked resources without force fails
    Given a project "local/del-linked" already exists
    And a resource is linked to project "local/del-linked"
    When I delete project "local/del-linked" with yes but no force
    Then the delete command should fail with exit code 1

  Scenario: Delete project with linked resources with force
    Given a project "local/del-force" already exists
    And a resource is linked to project "local/del-force"
    When I delete project "local/del-force" with yes and force
    Then the project "local/del-force" should not exist

  # ── Format output ────────────────────────────────────────────

  Scenario: List projects with JSON format
    Given a project "local/json-test" already exists
    When I list projects with format "json"
    Then the project CLI output should contain "namespaced_name"

  Scenario: Show project with YAML format
    Given a project "local/yaml-test" already exists
    When I show project details for "local/yaml-test" as "yaml"
    Then the project CLI output should contain "namespaced_name"

  Scenario: Show project with plain format
    Given a project "local/plain-test" already exists
    When I show project details for "local/plain-test" as "plain"
    Then the project CLI output should contain "namespaced_name"

  Scenario: Create project with JSON format
    When I run project create named "fmt-proj" formatted as "json"
    Then the project CLI output should contain "namespaced_name"

  # ── Project spec dict helper ─────────────────────────────────

  Scenario: Project spec dict contains expected keys
    Given a project "local/spec-dict" already exists
    When I generate the project spec dict for "local/spec-dict"
    Then the spec dict should have key "namespaced_name"
    And the spec dict should have key "namespace"
    And the spec dict should have key "name"
    And the spec dict should have key "description"
    And the spec dict should have key "linked_resources"
    And the spec dict should have key "created_at"
    And the spec dict should have key "updated_at"
