using Sdt.Config;
using Xunit;

namespace DevTool.Tests;

public sealed class WorkspaceDefaultsTests
{
    [Fact]
    public void ConfigLoader_AppliesWorkspaceDefaults_FromAncestorDirectory()
    {
        var workspaceRoot = CreateTempDir("sdt-ws-defaults-");
        var projectRoot = Path.Combine(workspaceRoot, "proj-a");
        Directory.CreateDirectory(projectRoot);
        File.WriteAllText(Path.Combine(workspaceRoot, WorkspaceLoader.FileName), """
{
  "name": "Test Workspace",
  "projects": []
}
""");

        File.WriteAllText(Path.Combine(workspaceRoot, ConfigLoader.WorkspaceDefaultsFileName), """
{
  "toolchains": {
    "node": {
      "packageManager": "pnpm",
      "workingDir": "frontend"
    }
  },
  "env": [
    { "key": "DOTNET_ENVIRONMENT", "description": "default env", "default": "Development", "options": ["Development", "Production"] }
  ]
}
""");

        File.WriteAllText(Path.Combine(projectRoot, "devtool.json"), """
{
  "name": "Project A",
  "version": "1.0.0",
  "workflows": [
    {
      "id": "build",
      "label": "Build",
      "description": "Build app",
      "group": "Build",
      "dependsOn": [],
      "steps": [
        { "id": "build-step", "label": "dotnet build", "command": "dotnet", "args": ["build"], "workingDir": "." }
      ]
    }
  ]
}
""");

        var loaded = ConfigLoader.FindAndLoad(projectRoot);

        Assert.NotNull(loaded);
        Assert.Equal("pnpm", loaded!.Config.Toolchains?.Node?.PackageManager);
        Assert.Equal("frontend", loaded.Config.Toolchains?.Node?.WorkingDir);
        Assert.Single(loaded.Config.Env);
        Assert.Contains(loaded.Warnings, w => w.Contains("Applied workspace defaults", StringComparison.OrdinalIgnoreCase));
    }

    [Fact]
    public void ConfigLoader_ProjectValuesOverrideWorkspaceDefaults()
    {
        var workspaceRoot = CreateTempDir("sdt-ws-override-");
        var projectRoot = Path.Combine(workspaceRoot, "proj-b");
        Directory.CreateDirectory(projectRoot);
        File.WriteAllText(Path.Combine(workspaceRoot, WorkspaceLoader.FileName), """
{
  "name": "Test Workspace",
  "projects": []
}
""");

        File.WriteAllText(Path.Combine(workspaceRoot, ConfigLoader.WorkspaceDefaultsFileName), """
{
  "name": "Workspace Defaults",
  "workflows": [
    {
      "id": "from-defaults",
      "label": "Defaults Workflow",
      "description": "",
      "group": "General",
      "dependsOn": [],
      "steps": []
    }
  ],
  "debug": {
    "diagnostics": {
      "enabled": true,
      "outputDir": ".sdt/workspace-debug",
      "includeAllEnv": true,
      "bundleOnFailure": true
    }
  }
}
""");

        File.WriteAllText(Path.Combine(projectRoot, "devtool.json"), """
{
  "name": "Project B",
  "version": "1.0.0",
  "workflows": [
    {
      "id": "project-workflow",
      "label": "Project Workflow",
      "description": "Only this one should remain",
      "group": "Build",
      "dependsOn": [],
      "steps": []
    }
  ],
  "debug": {
    "diagnostics": {
      "enabled": false
    }
  }
}
""");

        var loaded = ConfigLoader.FindAndLoad(projectRoot);

        Assert.NotNull(loaded);
        Assert.Equal("Project B", loaded!.Config.Name);
        Assert.Single(loaded.Config.Workflows);
        Assert.Equal("project-workflow", loaded.Config.Workflows[0].Id);
        Assert.NotNull(loaded.Config.Debug);
        Assert.NotNull(loaded.Config.Debug!.Diagnostics);
        Assert.False(loaded.Config.Debug.Diagnostics.Enabled);
        Assert.Equal(".sdt/workspace-debug", loaded.Config.Debug.Diagnostics.OutputDir);
        Assert.True(loaded.Config.Debug.Diagnostics.IncludeAllEnv);
    }

    private static string CreateTempDir(string prefix)
    {
        var path = Path.Combine(Path.GetTempPath(), prefix + Guid.NewGuid().ToString("N"));
        Directory.CreateDirectory(path);
        return path;
    }
}
