package configs

import (
	"os"
	"path/filepath"
	"testing"

	"github.com/stretchr/testify/assert"
	"github.com/stretchr/testify/require"
)

func TestLoadControllerConfig(t *testing.T) {
	tests := []struct {
		name        string
		yamlContent string
		wantPanic   bool
		validate    func(t *testing.T, tmpFile string)
	}{
		{
			name: "valid config with all fields",
			yamlContent: `integrationTaskConfig:
  jobManagerImage: "test-image:v1.0"
  jobManagerIAMRole: "arn:aws:iam::123456789012:role/test-role"
  sharedBucketTenantIDs:
    - "tenant-a"
    - " tenant-b "`,
			wantPanic: false,
			validate: func(t *testing.T, tmpFile string) {
				config := LoadControllerConfig(tmpFile)
				assert.Equal(t, "test-image:v1.0", config.IntegrationTaskConfig.JobManagerImage)
				assert.Equal(t, "arn:aws:iam::123456789012:role/test-role", config.IntegrationTaskConfig.JobManagerIAMRole)
				assert.Equal(t, []string{"tenant-a", " tenant-b "}, config.IntegrationTaskConfig.SharedBucketTenantIDs)
				assert.True(t, config.IntegrationTaskConfig.IsSharedBucketTenant("tenant-a"))
				assert.True(t, config.IntegrationTaskConfig.IsSharedBucketTenant("tenant-b"))
				assert.False(t, config.IntegrationTaskConfig.IsSharedBucketTenant("tenant-c"))
			},
		},
		{
			name: "valid config with empty fields",
			yamlContent: `integrationTaskConfig:
  jobManagerImage: ""
  jobManagerIAMRole: ""`,
			wantPanic: false,
			validate: func(t *testing.T, tmpFile string) {
				config := LoadControllerConfig(tmpFile)
				assert.Empty(t, config.IntegrationTaskConfig.JobManagerImage)
				assert.Empty(t, config.IntegrationTaskConfig.JobManagerIAMRole)
			},
		},
		{
			name:        "empty yaml file",
			yamlContent: "",
			wantPanic:   false,
			validate: func(t *testing.T, tmpFile string) {
				config := LoadControllerConfig(tmpFile)
				assert.Empty(t, config.IntegrationTaskConfig.JobManagerImage)
				assert.Empty(t, config.IntegrationTaskConfig.JobManagerIAMRole)
			},
		},
		{
			name:        "invalid yaml format",
			yamlContent: "invalid: yaml: content: [unclosed",
			wantPanic:   true,
		},
		{
			name:      "non-existent file",
			wantPanic: true,
			validate: func(t *testing.T, tmpFile string) {
				// Remove the file before calling LoadControllerConfig
				os.Remove(tmpFile)
				LoadControllerConfig(tmpFile)
			},
		},
	}

	for _, tt := range tests {
		t.Run(tt.name, func(t *testing.T) {
			// Create temporary file
			tmpFile := filepath.Join(t.TempDir(), "controller-config.yaml")

			if tt.name != "non-existent file" {
				err := os.WriteFile(tmpFile, []byte(tt.yamlContent), 0644)
				require.NoError(t, err)
			}

			if tt.wantPanic {
				assert.Panics(t, func() {
					if tt.validate != nil {
						tt.validate(t, tmpFile)
					} else {
						LoadControllerConfig(tmpFile)
					}
				})
			} else {
				assert.NotPanics(t, func() {
					if tt.validate != nil {
						tt.validate(t, tmpFile)
					}
				})
			}
		})
	}
}
