package pgdump

import (
	"errors"
	"fmt"
	"testing"
)

func TestErrPgDumpFailed_Error(t *testing.T) {
	cases := []struct {
		name     string
		exitCode int
		want     string
	}{
		{name: "zero", exitCode: 0, want: "pg_dump failed with exit code 0"},
		{name: "one", exitCode: 1, want: "pg_dump failed with exit code 1"},
		{name: "large", exitCode: 137, want: "pg_dump failed with exit code 137"},
	}

	for _, tc := range cases {
		t.Run(tc.name, func(t *testing.T) {
			err := ErrPgDumpFailed(tc.exitCode)
			if err == nil {
				t.Fatalf("ErrPgDumpFailed(%d) returned nil, want error", tc.exitCode)
			}
			if got := err.Error(); got != tc.want {
				t.Fatalf("Error() = %q, want %q", got, tc.want)
			}
		})
	}
}

func TestErrPgDumpFailed_Is(t *testing.T) {
	base := ErrPgDumpFailed(1)

	cases := []struct {
		name   string
		target error
		want   bool
	}{
		{
			name:   "same exit code",
			target: ErrPgDumpFailed(1),
			want:   true,
		},
		{
			name:   "different exit code",
			target: ErrPgDumpFailed(2),
			want:   false,
		},
		{
			name:   "unrelated error type",
			target: errors.New("something else"),
			want:   false,
		},
		{
			// Is does not unwrap target: a fmt.Errorf-wrapped pgDumpFailedError
			// fails the exact type check, so errors.Is reports false here.
			name:   "wrapped same-type error",
			target: fmt.Errorf("wrapped: %w", ErrPgDumpFailed(1)),
			want:   false,
		},
	}

	for _, tc := range cases {
		t.Run(tc.name, func(t *testing.T) {
			if got := errors.Is(base, tc.target); got != tc.want {
				t.Fatalf("errors.Is(%v, %v) = %v, want %v", base, tc.target, got, tc.want)
			}
		})
	}
}
