package main

import (
	"io"
	"os"
	"strings"
	"testing"
)

func runCLI(t *testing.T, args ...string) (string, error) {
	t.Helper()
	oldArgs, oldOut := os.Args, os.Stdout
	reader, writer, err := os.Pipe()
	if err != nil {
		t.Fatal(err)
	}
	os.Args, os.Stdout = append([]string{"harness"}, args...), writer
	defer func() { os.Args, os.Stdout = oldArgs, oldOut; reader.Close(); writer.Close() }()
	result := make(chan string, 1)
	go func() { data, _ := io.ReadAll(reader); result <- string(data) }()
	runErr := run()
	writer.Close()
	return <-result, runErr
}

func TestHelpDoesNotNeedDatabaseOrExposeCredentials(t *testing.T) {
	t.Setenv("DATABASE_URL", "postgres://test:secret-help-sentinel@127.0.0.1:1/nonexistent")
	for _, args := range [][]string{{"--help"}, {"-h"}, {"help"}} {
		text, err := runCLI(t, args...)
		if err != nil {
			t.Fatal(err)
		}
		for _, command := range commandOrder {
			if !strings.Contains(text, command) {
				t.Errorf("top-level help omits %s", command)
			}
		}
	}
	for _, command := range commandOrder {
		for _, args := range [][]string{{command, "--help"}, {command, "-h"}, {"help", command}} {
			text, err := runCLI(t, args...)
			if err != nil {
				t.Fatalf("%v: %v", args, err)
			}
			for _, want := range []string{"Usage: harness " + command, "Example", commands[command].description} {
				if !strings.Contains(text, want) {
					t.Errorf("%v missing %q", args, want)
				}
			}
			if strings.Contains(text, "secret-help-sentinel") {
				t.Fatalf("%v leaked credentials", args)
			}
		}
	}
	text, err := runCLI(t, "seed", "--help")
	if err != nil || !strings.Contains(text, "100,000 posts") || !strings.Contains(text, "REPLACES") {
		t.Fatalf("seed help: %s, %v", text, err)
	}
	if strings.Contains(text, "-url") || strings.Contains(text, "-golden") {
		t.Fatal("seed help contains unrelated options")
	}
}

func TestInvalidArgumentsFailBeforeDatabaseWork(t *testing.T) {
	t.Setenv("DATABASE_URL", "invalid connection string")
	for _, args := range [][]string{{"unknown"}, {"seed", "unexpected"}, {"seed", "--url", "http://localhost"}} {
		_, err := runCLI(t, args...)
		if err == nil {
			t.Fatalf("%v succeeded", args)
		}
		if strings.Contains(err.Error(), "connect") {
			t.Fatalf("%v attempted database work: %v", args, err)
		}
	}
}

func TestHelpDocumentsDefaultDatabase(t *testing.T) {
	t.Setenv("DATABASE_URL", "")
	text, err := runCLI(t, "fixture", "--help")
	if err != nil {
		t.Fatal(err)
	}
	if !strings.Contains(text, "dbname=assignment_harness_native") {
		t.Fatal("help omits database default")
	}
}
