Option Strict On
Option Explicit On

Imports System
Imports System.Collections.Generic
Imports System.Reflection
Imports Nexamas.UI.Architecture
Imports Nexamas.UI.Components

Namespace Nexamas.UI.Quality

    ''' <summary>
    ''' Friend-only commercial readiness matrix for the product-size controls called out by
    ''' Phase 0. It is intentionally diagnostic: it does not create controls, mutate the
    ''' registry, render scenes, or expose public feature switches.
    ''' </summary>
    Friend NotInheritable Class MASCommercialReadinessMatrixBuilder

        Private Sub New()
        End Sub

        Friend Shared Function BuildProductControlsMatrix() As MASCommercialReadinessMatrix
            Dim records As New List(Of MASCommercialReadinessRecord)()

            records.Add(CreateProductionRecord("treegrid", "TreeGrid", GetType(MASTreeGrid), addGatewayName:="AddTreeGrid", hasDedicatedRenderCoverage:=True, hasDataSourceContract:=True, hasVirtualizationContract:=True, hasPerformanceProof:=True, blockerSummary:=String.Empty))
            records.Add(CreateProductionRecord("pivottable", "PivotTable", GetType(MASPivotTable), addGatewayName:="AddPivotTable", hasDedicatedRenderCoverage:=True, hasDataSourceContract:=True, hasVirtualizationContract:=True, hasPerformanceProof:=True, blockerSummary:=String.Empty))
            records.Add(CreateProductionRecord("kanban", "KanbanBoard", GetType(MASKanbanBoard), addGatewayName:="AddKanbanBoard", hasDedicatedRenderCoverage:=True, hasDataSourceContract:=True, hasVirtualizationContract:=True, hasPersistenceContract:=True, hasPerformanceProof:=True, blockerSummary:=String.Empty))
            records.Add(CreateProductionRecord("agenda", "AgendaView", GetType(MASAgendaView), addGatewayName:="AddAgendaView", hasDedicatedRenderCoverage:=True, hasDataSourceContract:=True, hasVirtualizationContract:=True, hasPerformanceProof:=True, blockerSummary:=String.Empty))
            records.Add(CreateProductionRecord("dashboardgrid", "DashboardGrid", GetType(MASDashboardGrid), addGatewayName:="AddDashboardGrid", hasDedicatedRenderCoverage:=True, hasHostingContract:=True, hasVirtualizationContract:=True, hasPersistenceContract:=True, hasPerformanceProof:=True, blockerSummary:=String.Empty))
            records.Add(CreateProductionRecord("masterdetail", "MasterDetailView", GetType(MASMasterDetailView), addGatewayName:="AddMasterDetailView", hasDataSourceContract:=True, hasHostingContract:=True, hasPersistenceContract:=True, hasDedicatedRenderCoverage:=True, hasVirtualizationContract:=True, hasPerformanceProof:=True, blockerSummary:=String.Empty))
            records.Add(CreateProductionRecord("applayout", "AppLayout", GetType(MASAppLayout), addGatewayName:="AddAppLayout", hasDedicatedRenderCoverage:=True, hasHostingContract:=True, hasVirtualizationContract:=True, hasPersistenceContract:=True, hasPerformanceProof:=True, blockerSummary:=String.Empty))
            records.Add(CreateProductionRecord("splitview", "SplitView", GetType(MASSplitView), addGatewayName:="AddSplitView", hasDedicatedRenderCoverage:=True, hasHostingContract:=True, hasPersistenceContract:=True, hasVirtualizationContract:=True, hasPerformanceProof:=True, blockerSummary:=String.Empty))

            Return New MASCommercialReadinessMatrix(records)
        End Function

        Private Shared Function CreatePreviewRecord(id As String,
                                                    displayName As String,
                                                    componentType As Type,
                                                    addGatewayName As String,
                                                    blockerSummary As String,
                                                    Optional hasDedicatedRenderCoverage As Boolean = False,
                                                    Optional hasDataSourceContract As Boolean = False,
                                                    Optional hasHostingContract As Boolean = False,
                                                    Optional hasVirtualizationContract As Boolean = False,
                                                    Optional hasPersistenceContract As Boolean = False,
                                                    Optional hasPerformanceProof As Boolean = False) As MASCommercialReadinessRecord
            Return CreateRecord(id,
                                displayName,
                                componentType,
                                addGatewayName,
                                MASCommercialReadinessStage.CompactPreview,
                                blockerSummary,
                                hasDedicatedRenderCoverage,
                                hasDataSourceContract,
                                hasHostingContract,
                                hasVirtualizationContract,
                                hasPersistenceContract,
                                hasPerformanceProof)
        End Function

        Private Shared Function CreateProductionRecord(id As String,
                                                       displayName As String,
                                                       componentType As Type,
                                                       addGatewayName As String,
                                                       blockerSummary As String,
                                                       Optional hasDedicatedRenderCoverage As Boolean = False,
                                                       Optional hasDataSourceContract As Boolean = False,
                                                       Optional hasHostingContract As Boolean = False,
                                                       Optional hasVirtualizationContract As Boolean = False,
                                                       Optional hasPersistenceContract As Boolean = False,
                                                       Optional hasPerformanceProof As Boolean = False) As MASCommercialReadinessRecord
            Return CreateRecord(id,
                                displayName,
                                componentType,
                                addGatewayName,
                                MASCommercialReadinessStage.ProductionReady,
                                blockerSummary,
                                hasDedicatedRenderCoverage,
                                hasDataSourceContract,
                                hasHostingContract,
                                hasVirtualizationContract,
                                hasPersistenceContract,
                                hasPerformanceProof)
        End Function

        Private Shared Function CreateRecord(id As String,
                                             displayName As String,
                                             componentType As Type,
                                             addGatewayName As String,
                                             stage As MASCommercialReadinessStage,
                                             blockerSummary As String,
                                             hasDedicatedRenderCoverage As Boolean,
                                             hasDataSourceContract As Boolean,
                                             hasHostingContract As Boolean,
                                             hasVirtualizationContract As Boolean,
                                             hasPersistenceContract As Boolean,
                                             hasPerformanceProof As Boolean) As MASCommercialReadinessRecord
            Return New MASCommercialReadinessRecord(
                id:=id,
                displayName:=displayName,
                componentType:=componentType,
                stage:=stage,
                hasArchitectureRegistration:=HasArchitectureRegistration(componentType),
                hasPublicAddGateway:=HasPublicAddGateway(addGatewayName, componentType),
                hasRelationCoverage:=HasRelationCoverage(componentType),
                hasDedicatedRenderCoverage:=hasDedicatedRenderCoverage,
                hasDataSourceContract:=hasDataSourceContract,
                hasHostingContract:=hasHostingContract,
                hasVirtualizationContract:=hasVirtualizationContract,
                hasPersistenceContract:=hasPersistenceContract,
                hasPerformanceProof:=hasPerformanceProof,
                blockerSummary:=blockerSummary)
        End Function

        Private Shared Function HasArchitectureRegistration(componentType As Type) As Boolean
            If componentType Is Nothing Then Return False
            Try
                Return MASArchitectureQuery.FindByType(componentType) IsNot Nothing
            Catch ex As Exception
                Nexamas.UI.Diagnostics.MASExceptionSilencer.SwallowDiagnosticOnly(ex, "MASCommercialReadinessMatrixBuilder.HasArchitectureRegistration")
                Return False
            End Try
        End Function

        Private Shared Function HasPublicAddGateway(addGatewayName As String,
                                                    componentType As Type) As Boolean
            Dim normalizedName As String = If(addGatewayName, String.Empty).Trim()
            If normalizedName.Length = 0 OrElse componentType Is Nothing Then Return False

            Try
                Const flags As BindingFlags = BindingFlags.Instance Or BindingFlags.Public
                For Each method As MethodInfo In GetType(Nexamas.UI.Application.MASApplicationWindowControls).GetMethods(flags)
                    If method Is Nothing Then Continue For
                    If Not String.Equals(method.Name, normalizedName, StringComparison.Ordinal) Then Continue For
                    If componentType.IsAssignableFrom(method.ReturnType) Then Return True
                Next
            Catch ex As Exception
                Nexamas.UI.Diagnostics.MASExceptionSilencer.SwallowDiagnosticOnly(ex, "MASCommercialReadinessMatrixBuilder.HasPublicAddGateway")
            End Try

            Return False
        End Function

        Private Shared Function HasRelationCoverage(componentType As Type) As Boolean
            If componentType Is Nothing Then Return False
            Try
                Return MASProductControlRelationCoverageGate.HasCoverageFor(componentType)
            Catch ex As Exception
                Nexamas.UI.Diagnostics.MASExceptionSilencer.SwallowDiagnosticOnly(ex, "MASCommercialReadinessMatrixBuilder.HasRelationCoverage")
                Return False
            End Try
        End Function

    End Class

End Namespace
