import CartMismatchBanner from "@modules/layout/components/cart-mismatch-banner"
import FreeShippingPriceNudge from "@modules/shipping/components/free-shipping-price-nudge"
import { DynamicLayoutRenderer } from "./renderer"
import React from "react"
import VtNav from "@modules/layout/templates/vt-nav"
import VtFooter from "@modules/layout/templates/vt-footer"
import HomeButton from "@modules/layout/components/vt-homebutton"
import AccountButton from "@modules/layout/components/vt-accountbutton"
import VtCartButton from "@modules/layout/components/vt-cartbutton"
import VtHeader from "@modules/layout/templates/vt-header"
import Banner from "@modules/layout/templates/vt-banner"
import VtMegaMenu from "@modules/layout/components/vt-mega-menu"
import VtLink from "@modules/layout/components/vt-linkbutton"
import VtSideMenu from "@modules/layout/components/vt-sidemenu"
import VtImage from "@modules/layout/templates/vt-image"
import VtDropdown from "@modules/layout/templates/vt-dropdown"
import VtButton from "@modules/layout/templates/vt-button"
import VtSearchInput from "@modules/layout/templates/vt-search-input"
import VtSection from "@modules/layout/templates/vt-section"
import VtText from "@modules/layout/templates/vt-text"
import VtInput from "@modules/layout/templates/vt-input"
import VtCurrencySelect from "@modules/layout/templates/vt-currency-select"
import VtMenuItem from "@modules/layout/templates/vt-menu-item"
import VtCountryCodeSelect from "@modules/layout/templates/vt-country-select/server"
import VtSocialLinks from "@modules/layout/templates/vt-social-link"

type ComponentConfig = Record<string, any>;

export interface LayoutComponentDefinition {
  config?: ComponentConfig
  children?: LayoutComponentNode[]
}

export interface LayoutContext { 
  customer: any; 
  cart: any;
  shippingOptions: any[]; 
  contentChildren: React.ReactNode; 
}

export type ComponentRenderer = {
  render: (entry: LayoutComponentDefinition, ctx: LayoutContext) => React.ReactNode
}

// Utility methods
const   configOnly = (Component: React.ComponentType<any>): ComponentRenderer => ({
  render: (entry) => <Component {...entry.config} />
})

const nodesContextRenderer = (Component: React.ComponentType<any>): ComponentRenderer => ({
  render: (entry: any, ctx: LayoutContext) => <Component nodes={entry} context={ctx} />
});

const renderChildren = (entry: LayoutComponentDefinition, ctx: LayoutContext) =>
  entry.children ? <DynamicLayoutRenderer nodes={entry.children} context={ctx} /> : null


// Component Map
export const componentMap: Record<string, ComponentRenderer> = {
  Header:    nodesContextRenderer(VtHeader),
  Nav: nodesContextRenderer(VtNav),
  VtMegaMenu: nodesContextRenderer(VtMegaMenu),
  VtSideMenu: nodesContextRenderer(VtSideMenu),
  Banner: nodesContextRenderer(Banner),
  HomeButton: nodesContextRenderer(HomeButton),
  AccountButton: nodesContextRenderer(AccountButton),
  Button: nodesContextRenderer(VtButton),
  Section: nodesContextRenderer(VtSection),
  SearchInput: nodesContextRenderer(VtSearchInput),
  VtCartButton: nodesContextRenderer(VtCartButton),
  VtCurrencySelect: nodesContextRenderer(VtCurrencySelect),
  VtCountryCodeSelect: nodesContextRenderer(VtCountryCodeSelect),
  VtSocialLinks: nodesContextRenderer(VtSocialLinks),
  Link: nodesContextRenderer(VtLink),
  Input: nodesContextRenderer(VtInput),
  Image: nodesContextRenderer(VtImage),
  Text: nodesContextRenderer(VtText),
  Dropdown: nodesContextRenderer(VtDropdown),
  VtMenuItem: nodesContextRenderer(VtMenuItem),
  CartMismatchBanner: configOnly(CartMismatchBanner),
  FreeShippingPriceNudge: configOnly(FreeShippingPriceNudge),
  PropsChildren: {
    render: (_props, ctx) => ctx.contentChildren,  // PageLayout's props.children 
  },
  Footer: nodesContextRenderer(VtFooter)
}


export type ComponentName = keyof typeof componentMap

// //maps key = componentName to value = props + children
// export type LayoutComponentNode = Record<string, LayoutComponentDefinition>
export type LayoutComponentNode = { [K in ComponentName]: LayoutComponentDefinition }[ComponentName]