Kaynağa Gözat

Tests Failing due to RunsOn Command, Tags and Labels not functioning correctly

James 4 hafta önce
ebeveyn
işleme
2d43446342

+ 14 - 5
RackPeek.Domain/UseCases/Mermaid/MermaidDiagramGenerator.cs

@@ -19,7 +19,7 @@ namespace RackPeek.Domain.UseCases.Mermaid {
             IOrderedEnumerable<IGrouping<string, Resource>> grouped = resources
             IOrderedEnumerable<IGrouping<string, Resource>> grouped = resources
                 .Where(r => resolvedOptions.IncludeTags.Count == 0
                 .Where(r => resolvedOptions.IncludeTags.Count == 0
                             || (r.Tags != null && r.Tags.Any(t => resolvedOptions.IncludeTags.Contains(t, StringComparer.OrdinalIgnoreCase))))
                             || (r.Tags != null && r.Tags.Any(t => resolvedOptions.IncludeTags.Contains(t, StringComparer.OrdinalIgnoreCase))))
-                .GroupBy(r => r.Kind)
+                .GroupBy(r => Resource.KindToPlural(r.Kind))
                 .OrderBy(g => g.Key);
                 .OrderBy(g => g.Key);
 
 
             foreach (IGrouping<string, Resource> group in grouped) {
             foreach (IGrouping<string, Resource> group in grouped) {
@@ -34,11 +34,20 @@ namespace RackPeek.Domain.UseCases.Mermaid {
 
 
             // Map RunsOn relationships if requested
             // Map RunsOn relationships if requested
             if (resolvedOptions.IncludeEdges) {
             if (resolvedOptions.IncludeEdges) {
+                
+                var resourceLookup = resources.ToDictionary(r => r.Name, r => SanitizeId(r.Name), StringComparer.OrdinalIgnoreCase);
+                    
                 foreach (Resource r in resources) {
                 foreach (Resource r in resources) {
                     var nodeId = SanitizeId(r.Name);
                     var nodeId = SanitizeId(r.Name);
-                    foreach (var depName in r.RunsOn ?? new List<string>()) {
-                        var depId = SanitizeId(depName);
-                        sb.AppendLine($"  {nodeId} --> {depId}");
+                    foreach (var depName in r.RunsOn) {
+                        if (resourceLookup.TryGetValue(depName, out var depId))
+                        {
+                            sb.AppendLine($"  {nodeId} --> {depId}");
+                        }
+                        else
+                        {
+                            warnings.Add($"RunsOn reference '{depName}' for '{r.Name}' not found in resources");
+                        }
                     }
                     }
                 }
                 }
             }
             }
@@ -50,7 +59,7 @@ namespace RackPeek.Domain.UseCases.Mermaid {
         }
         }
 
 
         private static string BuildNodeLabel(Resource r, MermaidExportOptions options) {
         private static string BuildNodeLabel(Resource r, MermaidExportOptions options) {
-            if (!options.IncludeLabels || r.Labels.Count == 0)
+            if (!options.IncludeLabels)
                 return r.Name;
                 return r.Name;
 
 
             IEnumerable<KeyValuePair<string, string>> filtered = options.LabelWhitelist is null
             IEnumerable<KeyValuePair<string, string>> filtered = options.LabelWhitelist is null

+ 133 - 0
Tests/EndToEnd/ExporterTests/MermaidExportTests.cs

@@ -0,0 +1,133 @@
+using System.IO;
+using System.Threading.Tasks;
+using Tests.EndToEnd.Infra;
+using Xunit;
+using Xunit.Abstractions;
+
+namespace Tests.EndToEnd.MermaidTests;
+
+[Collection("Yaml CLI tests")]
+public class MermaidExportCommandTests(TempYamlCliFixture fs, ITestOutputHelper outputHelper)
+    : IClassFixture<TempYamlCliFixture>
+{
+    private async Task<(string output, string yaml)> ExecuteAsync(params string[] args)
+    {
+        outputHelper.WriteLine($"rpk {string.Join(" ", args)}");
+
+        var output = await YamlCliTestHost.RunAsync(
+            args,
+            fs.Root,
+            outputHelper,
+            "config.yaml"
+        );
+
+        var yaml = await File.ReadAllTextAsync(Path.Combine(fs.Root, "config.yaml"));
+        return (output, yaml);
+    }
+
+    [Fact]
+    public async Task help_commands_do_not_throw()
+    {
+        (var output, var _) = await ExecuteAsync("mermaid", "export", "--help");
+        Assert.Equal("""
+                        DESCRIPTION:
+                        Generate a Mermaid infrastructure diagram
+                        
+                        USAGE:
+                            rpk mermaid export [OPTIONS]
+                        
+                        OPTIONS:
+                            -h, --help               Prints help information                            
+                                --include-tags       Comma-separated list of tags to include (e.g.      
+                                                     prod,linux)                                        
+                                --diagram-type       Mermaid diagram type (default: "flowchart TD")     
+                                --no-labels          Disable resource label annotations                 
+                                --no-edges           Disable relationship edges                         
+                                --label-whitelist    Comma-separated list of label keys to include      
+                            -o, --output             Write Mermaid diagram to file instead of stdout    
+                        
+                        """, output);
+                       
+        outputHelper.WriteLine(output);
+        
+        (output, _) = await ExecuteAsync("mermaid", "--help");
+        Assert.Equal("""
+                        DESCRIPTION:
+                        Generate Mermaid diagrams from infrastructure
+                        
+                        USAGE:
+                            rpk mermaid [OPTIONS] <COMMAND>
+                        
+                        OPTIONS:
+                            -h, --help    Prints help information
+                        
+                        COMMANDS:
+                            export    Generate a Mermaid infrastructure diagram
+                        
+                        """, output);
+       
+    }
+
+    [Fact]
+    public async Task mermaid_export_creates_expected_diagram()
+    {
+        // Prepare test resources
+        await File.WriteAllTextAsync(Path.Combine(fs.Root, "config.yaml"), "");
+
+        // Add resources
+        await ExecuteAsync("servers", "add", "srv01");
+        await ExecuteAsync("servers", "add", "srv02");
+        await ExecuteAsync("switches", "add", "sw01");
+        await ExecuteAsync("services", "add", "svc01");
+        await ExecuteAsync("systems", "add", "sys01");
+
+        // Define RunsOn relationships
+        await ExecuteAsync("services", "set", "svc01", "--RunsOn", "sys01");
+        await ExecuteAsync("systems", "set", "sys01", "--RunsOn", "srv01");
+
+        // Export Mermaid
+        (var output, var _) = await ExecuteAsync("mermaid", "export");
+
+        outputHelper.WriteLine(output);
+
+        // Assertions: check subgraphs
+        Assert.Contains("subgraph servers", output);
+        Assert.Contains("subgraph switches", output);
+        Assert.Contains("subgraph services", output);
+        Assert.Contains("subgraph systems", output);
+
+        // Assertions: check nodes
+        Assert.Contains("srv01", output);
+        Assert.Contains("srv02", output);
+        Assert.Contains("sw01", output);
+        Assert.Contains("svc01", output);
+        Assert.Contains("sys01", output);
+
+        // Assertions: check edges
+        Assert.Contains("svc01 --> sys01", output);
+        Assert.Contains("sys01 --> srv01", output);
+
+        // Ensure diagram type is included
+        Assert.StartsWith("flowchart TD", output);
+    }
+
+    [Fact]
+    public async Task mermaid_export_with_tags_and_labels()
+    {
+        // Add resources with tags and labels
+        await ExecuteAsync("servers", "add", "srv03", "--Tags", "db,primary", "--Label", "env:prod");
+
+        // Export only resources with tag 'db'
+        (var output, _) = await ExecuteAsync("mermaid", "export", "--IncludeTags", "db");
+
+        outputHelper.WriteLine(output);
+
+        // Only srv03 should appear
+        Assert.Contains("srv03", output);
+        Assert.DoesNotContain("srv01", output);
+        Assert.DoesNotContain("srv02", output);
+
+        // Label should be included
+        Assert.Contains("env: prod", output);
+    }
+}