package com.livingworld.commands;

import static org.junit.jupiter.api.Assertions.assertThrows;
import static org.junit.jupiter.api.Assertions.assertTrue;

import com.livingworld.modules.pollution.PollutionRegionData;
import com.livingworld.modules.recovery.RecoveryRegionData;
import com.livingworld.modules.recovery.SuccessionStage;
import java.util.List;
import org.junit.jupiter.api.Test;
import com.livingworld.regions.Region;
import com.livingworld.regions.RegionCoordinate;
import com.livingworld.regions.RegionFactory;

class RegionInfoFormatterTest {

    private static Region region() {
        return new RegionFactory().createNewRegion(
                new RegionCoordinate("minecraft:overworld", -1, 2), 0);
    }

    @Test
    void headerContainsRegionId() {
        List<String> lines = RegionInfoFormatter.format(region());
        assertTrue(lines.get(0).contains("minecraft:overworld:-1:2"),
                "header should contain stable ID; got: " + lines.get(0));
        assertTrue(lines.get(0).contains("ACTIVE"), lines.get(0));
    }

    @Test
    void metricsLineContainsPollutionScore() {
        Region r = region();
        r.getMetrics().setPollutionScore(75);
        List<String> lines = RegionInfoFormatter.format(r);
        assertTrue(lines.stream().anyMatch(l -> l.contains("poll=75.0")),
                "metrics line should contain poll=75.0");
    }

    @Test
    void flagsLineContainsHighPollution() {
        Region r = region();
        r.getFlags().setHasHighPollution(true);
        List<String> lines = RegionInfoFormatter.format(r);
        assertTrue(lines.stream().anyMatch(l -> l.contains("highPollution=true")),
                "flags line should contain highPollution=true");
    }

    @Test
    void moduleDataSectionPresentForAllModules() {
        List<String> lines = RegionInfoFormatter.format(region());
        assertTrue(lines.stream().anyMatch(l -> l.contains("--- Module Data ---")));
        assertTrue(lines.stream().anyMatch(l -> l.startsWith("  pollution:")));
        assertTrue(lines.stream().anyMatch(l -> l.startsWith("  soil:")));
        assertTrue(lines.stream().anyMatch(l -> l.startsWith("  water:")));
        assertTrue(lines.stream().anyMatch(l -> l.startsWith("  vegetation:")));
        assertTrue(lines.stream().anyMatch(l -> l.startsWith("  resources:")));
        assertTrue(lines.stream().anyMatch(l -> l.startsWith("  recovery:")));
        assertTrue(lines.stream().anyMatch(l -> l.startsWith("  ecosystem:")));
    }

    @Test
    void moduleDataValuesShownWhenPresent() {
        Region r = region();
        r.getModuleData().put("pollution", new PollutionRegionData(33.0, 0.0, 0.0, 20.0));
        r.getModuleData().put("recovery",
                new RecoveryRegionData(SuccessionStage.YOUNG_WOODLAND, 50.0, 0.0));

        List<String> lines = RegionInfoFormatter.format(r);
        assertTrue(lines.stream().anyMatch(l -> l.contains("air=33.0")));
        assertTrue(lines.stream().anyMatch(l -> l.contains("stage=YOUNG_WOODLAND")));
    }

    @Test
    void noDataShownWhenModuleAbsent() {
        List<String> lines = RegionInfoFormatter.format(region());
        assertTrue(lines.stream().anyMatch(l -> l.contains("(no data)")));
    }

    @Test
    void validatesRegion() {
        assertThrows(IllegalArgumentException.class, () -> RegionInfoFormatter.format(null));
    }
}
