Option Strict On
Option Explicit On

Imports System.Collections.Generic
Imports System.Linq

Namespace Nexamas.UI.Virtualization

    ''' <summary>
    ''' Professional hardening gate for MASVirtualizedItemsSystem. It verifies benchmark coverage, variable-extent readiness,
    ''' automatic invalidation contracts, and current heavy-consumer catalog metadata without expanding the public SDK surface.
    ''' </summary>
    Friend NotInheritable Class MASVirtualizationProfessionalReadinessGate

        Friend Const MissingBenchmarkCode As String = "MASVirtualizationProfessional.MissingBenchmark"
        Friend Const FailedBenchmarkCode As String = "MASVirtualizationProfessional.FailedBenchmark"
        Friend Const MissingVariableExtentCode As String = "MASVirtualizationProfessional.MissingVariableExtentReadiness"
        Friend Const MissingAutoInvalidationCode As String = "MASVirtualizationProfessional.MissingAutoInvalidation"
        Friend Const MissingBenchmarkSummaryCode As String = "MASVirtualizationProfessional.MissingBenchmarkSummary"
        Friend Const MissingActiveConsumerCode As String = "MASVirtualizationProfessional.MissingActiveSharedConsumer"
        Friend Const MissingComposedConsumerCode As String = "MASVirtualizationProfessional.MissingComposedSharedConsumer"
        Friend Const ConsumerMetadataCode As String = "MASVirtualizationProfessional.ConsumerMetadata"

        Private Shared ReadOnly RequiredBenchmarkIds As IReadOnlyList(Of String) =
            New String() {
                "items-1000",
                "items-10000",
                "items-100000",
                "fast-scroll",
                "scroll-to-index",
                "resize",
                "theme-dpi-invalidation"
            }

        Private Sub New()
        End Sub

        Friend Shared Function EvaluateDefault() As MASVirtualizationReadinessReport
            Return Evaluate(MASVirtualizationBenchmarkSuite.RunDefault(), MASVirtualizationConsumerCatalog.GetCurrentConsumers())
        End Function

        Friend Shared Function Evaluate(results As IEnumerable(Of MASVirtualizationBenchmarkResult),
                                        bindings As IEnumerable(Of MASVirtualizationConsumerBinding)) As MASVirtualizationReadinessReport
            Dim safeResults = If(results, Enumerable.Empty(Of MASVirtualizationBenchmarkResult)()).Where(Function(result) result IsNot Nothing).ToArray()
            Dim safeBindings = If(bindings, Enumerable.Empty(Of MASVirtualizationConsumerBinding)()).Where(Function(binding) binding IsNot Nothing).ToArray()
            Dim findings = New List(Of MASVirtualizationReadinessFinding)()
            Dim summary = MASVirtualizationBenchmarkSuite.Summarize(safeResults)

            If Not summary.IsCommercialProofReady Then
                findings.Add(New MASVirtualizationReadinessFinding(MissingBenchmarkSummaryCode, "Virtualization benchmark summary must prove 1k/10k/100k, bounded realization, variable extents, fast scroll, scroll-to-index, resize, and auto invalidation.", MASVirtualizationFindingSeverity.Error))
            End If

            Dim resultIds = New HashSet(Of String)(
                safeResults.Where(Function(result) result.Scenario IsNot Nothing).Select(Function(result) result.Scenario.Id),
                StringComparer.Ordinal)

            For Each requiredId In RequiredBenchmarkIds
                If Not resultIds.Contains(requiredId) Then
                    findings.Add(New MASVirtualizationReadinessFinding(MissingBenchmarkCode, "Missing virtualization benchmark scenario: " & requiredId, MASVirtualizationFindingSeverity.Error))
                End If
            Next

            For Each result In safeResults
                If Not result.Passed Then
                    Dim id = If(result.Scenario IsNot Nothing, result.Scenario.Id, "unknown")
                    findings.Add(New MASVirtualizationReadinessFinding(FailedBenchmarkCode, "Virtualization benchmark did not meet bounded realization/correctness requirements: " & id, MASVirtualizationFindingSeverity.Error))
                End If
            Next

            If Not safeResults.Any(Function(result) result.Scenario IsNot Nothing AndAlso result.Scenario.ExtentStrategy = MASVirtualizationExtentStrategy.EstimatedWithMeasuredOverrides AndAlso result.MeasurementRevision > 0) Then
                findings.Add(New MASVirtualizationReadinessFinding(MissingVariableExtentCode, "Virtualization benchmarks must prove measured variable extent readiness.", MASVirtualizationFindingSeverity.Error))
            End If

            If Not safeResults.Any(Function(result) result.Scenario IsNot Nothing AndAlso result.Scenario.Id = "theme-dpi-invalidation" AndAlso result.Diagnostics IsNot Nothing AndAlso result.Diagnostics.LastInvalidationReason <> MASVirtualizationInvalidationReason.None) Then
                findings.Add(New MASVirtualizationReadinessFinding(MissingAutoInvalidationCode, "Virtualization benchmarks must prove automatic environment invalidation.", MASVirtualizationFindingSeverity.Error))
            End If

            If safeBindings.Length = 0 Then
                findings.Add(New MASVirtualizationReadinessFinding(ConsumerMetadataCode, "Virtualization heavy-consumer metadata must not be empty.", MASVirtualizationFindingSeverity.Error))
            End If

            If Not safeBindings.Any(Function(binding) binding.IsActiveOrComposedSharedControllerConsumer) Then
                findings.Add(New MASVirtualizationReadinessFinding(MissingActiveConsumerCode, "Virtualization catalog must record at least one active or composed shared-controller consumer before further consumer expansion.", MASVirtualizationFindingSeverity.Error))
            End If

            Dim activeConsumerIds = New HashSet(Of String)(
                safeBindings.Where(Function(binding) binding.IsActiveOrComposedSharedControllerConsumer).Select(Function(binding) binding.Id),
                StringComparer.Ordinal)

            For Each binding In safeBindings
                If Not System.Enum.IsDefined(GetType(MASVirtualizationExtentStrategy), binding.ExtentStrategy) Then
                    findings.Add(New MASVirtualizationReadinessFinding(ConsumerMetadataCode, "Virtualization consumer binding has undefined extent strategy: " & binding.Id, MASVirtualizationFindingSeverity.Error))
                End If

                If Not binding.RequiresAutoInvalidationCoordinator Then
                    findings.Add(New MASVirtualizationReadinessFinding(ConsumerMetadataCode, "Virtualization consumer binding must require the auto invalidation coordinator: " & binding.Id, MASVirtualizationFindingSeverity.Error))
                End If

                If binding.ConsumesSharedController AndAlso
                   binding.Stage <> MASVirtualizationIntegrationStage.ActiveSharedControllerConsumer AndAlso
                   binding.Stage <> MASVirtualizationIntegrationStage.ComposedSharedControllerConsumer Then
                    findings.Add(New MASVirtualizationReadinessFinding(ConsumerMetadataCode, "Virtualization shared-controller consumer must use the active or composed integration stage: " & binding.Id, MASVirtualizationFindingSeverity.Error))
                End If

                If binding.Stage = MASVirtualizationIntegrationStage.ComposedSharedControllerConsumer Then
                    If Not binding.IsComposedSharedControllerConsumer Then
                        findings.Add(New MASVirtualizationReadinessFinding(MissingComposedConsumerCode, "Composed virtualization consumer must name official child consumers: " & binding.Id, MASVirtualizationFindingSeverity.Error))
                    End If

                    For Each dependencyId As String In binding.ComposedThroughConsumerIds
                        If Not activeConsumerIds.Contains(dependencyId) Then
                            findings.Add(New MASVirtualizationReadinessFinding(MissingComposedConsumerCode, "Composed virtualization consumer depends on a child that is not an active shared-controller consumer: " & binding.Id & " -> " & dependencyId, MASVirtualizationFindingSeverity.Error))
                        End If
                    Next
                End If
            Next

            Return New MASVirtualizationReadinessReport(If(safeResults.Length > 0 AndAlso safeResults(0).Scenario IsNot Nothing, safeResults(0).Scenario.ItemCount, 0),
                                                        If(safeResults.Length > 0 AndAlso safeResults(0).Scenario IsNot Nothing, safeResults(0).Scenario.EstimatedItemExtentPx, 0.0F),
                                                        If(safeResults.Length > 0 AndAlso safeResults(0).Scenario IsNot Nothing, safeResults(0).Scenario.OverscanItemCount, 0),
                                                        findings,
                                                        MASVirtualizationExtentStrategy.EstimatedWithMeasuredOverrides)
        End Function

    End Class

End Namespace
