package infra

import (
	"strings"
	"testing"
)

func TestGenerateDockerfile(t *testing.T) {
	t.Run("contiene stage builder con golang:1.23-alpine", func(t *testing.T) {
		got := GenerateDockerfile("myapp", 8080, nil)
		if !strings.Contains(got, "FROM golang:1.23-alpine AS builder") {
			t.Errorf("expected FROM golang:1.23-alpine AS builder, got:\n%s", got)
		}
	})

	t.Run("contiene stage final con alpine:latest", func(t *testing.T) {
		got := GenerateDockerfile("myapp", 8080, nil)
		if !strings.Contains(got, "FROM alpine:latest") {
			t.Errorf("expected FROM alpine:latest, got:\n%s", got)
		}
	})

	t.Run("incluye EXPOSE cuando port mayor a cero", func(t *testing.T) {
		got := GenerateDockerfile("myapp", 8080, nil)
		if !strings.Contains(got, "EXPOSE 8080") {
			t.Errorf("expected EXPOSE 8080, got:\n%s", got)
		}
	})

	t.Run("no incluye EXPOSE cuando port es cero", func(t *testing.T) {
		got := GenerateDockerfile("myapp", 0, nil)
		if strings.Contains(got, "EXPOSE") {
			t.Errorf("expected no EXPOSE directive, got:\n%s", got)
		}
	})

	t.Run("env vars aparecen ordenadas alfabeticamente", func(t *testing.T) {
		got := GenerateDockerfile("myapp", 8080, map[string]string{
			"Z_VAR": "z",
			"A_VAR": "a",
			"M_VAR": "m",
		})
		posA := strings.Index(got, "ENV A_VAR=a")
		posM := strings.Index(got, "ENV M_VAR=m")
		posZ := strings.Index(got, "ENV Z_VAR=z")
		if posA < 0 || posM < 0 || posZ < 0 {
			t.Fatalf("ENV vars no encontradas en:\n%s", got)
		}
		if !(posA < posM && posM < posZ) {
			t.Errorf("ENV vars no ordenadas: A=%d M=%d Z=%d", posA, posM, posZ)
		}
	})

	t.Run("binaryName aparece en ENTRYPOINT", func(t *testing.T) {
		got := GenerateDockerfile("mycli", 9090, nil)
		if !strings.Contains(got, `ENTRYPOINT ["./mycli"]`) {
			t.Errorf("expected ENTRYPOINT with mycli, got:\n%s", got)
		}
	})

	t.Run("env vars vacias no generan instrucciones ENV", func(t *testing.T) {
		got := GenerateDockerfile("myapp", 8080, map[string]string{})
		if strings.Contains(got, "ENV ") {
			t.Errorf("expected no ENV directives for empty map, got:\n%s", got)
		}
	})
}
