(t *testing.T)
| 559 | } |
| 560 | |
| 561 | func TestGraphCommand_RootUpstream(t *testing.T) { |
| 562 | tmpDir := createTestTaskFiles(t) |
| 563 | |
| 564 | // Reset flags |
| 565 | graphFormat = "json" |
| 566 | graphExcludeStatus = []string{} |
| 567 | graphRoot = "003" |
| 568 | graphFocus = "" |
| 569 | graphUpstream = true |
| 570 | graphDownstream = false |
| 571 | graphOut = "" |
| 572 | |
| 573 | // Capture stdout |
| 574 | oldStdout := os.Stdout |
| 575 | r, w, _ := os.Pipe() |
| 576 | os.Stdout = w |
| 577 | |
| 578 | // Run command |
| 579 | err := runGraph(graphCmd, []string{tmpDir}) |
| 580 | if err != nil { |
| 581 | t.Fatalf("runGraph failed: %v", err) |
| 582 | } |
| 583 | |
| 584 | // Restore stdout |
| 585 | w.Close() |
| 586 | os.Stdout = oldStdout |
| 587 | |
| 588 | // Read output |
| 589 | var buf bytes.Buffer |
| 590 | buf.ReadFrom(r) |
| 591 | output := buf.String() |
| 592 | |
| 593 | // Parse JSON |
| 594 | var result map[string]any |
| 595 | err = json.Unmarshal([]byte(output), &result) |
| 596 | if err != nil { |
| 597 | t.Fatalf("Failed to parse JSON output: %v", err) |
| 598 | } |
| 599 | |
| 600 | // Verify only upstream tasks are included |
| 601 | nodes, ok := result["nodes"].([]any) |
| 602 | if !ok { |
| 603 | t.Fatal("Expected 'nodes' to be an array") |
| 604 | } |
| 605 | |
| 606 | // Should include: 003 (root), 002, 001 (dependencies) |
| 607 | // Should NOT include: 004, 005 |
| 608 | if len(nodes) != 3 { |
| 609 | t.Errorf("Expected 3 nodes (003 and its upstream), got %d", len(nodes)) |
| 610 | } |
| 611 | |
| 612 | // Verify correct tasks are included |
| 613 | includedIDs := make(map[string]bool) |
| 614 | for _, node := range nodes { |
| 615 | nodeMap := node.(map[string]any) |
| 616 | includedIDs[nodeMap["id"].(string)] = true |
| 617 | } |
| 618 |
nothing calls this directly
no test coverage detected