---
import config from 'virtual:starlight/user-config';
import {
  stripLeadingAndTrailingSlashes,
  ensureTrailingSlash,
} from 'node_modules/@astrojs/starlight/utils/path';
import { CardGrid } from '@astrojs/starlight/components';
import { routes } from 'node_modules/@astrojs/starlight/utils/routing';

// custom component copied from starlight/components/LinkCard
import CustomLinkCard from '@components/plugins/CustomLinkCard.astro';
import type { Route } from 'node_modules/@astrojs/starlight/utils/routing/types';

interface Props {
  /**
   * Slug relative to /src - e.g "/zh-cn/features"
   *
   * Note: leading and trailing slashes are dropped "/features/" === "features"
   */
  slug: string;
  /**
   *  Filter out pages by title - case insensitive
   */
  filterOutByTitle?: string[];
  /**
   *  Filter out pages by file name - case insensitive
   */
  filterOutByFileName?: string[];
  /**
   * Force alphabetical order - by default it sorts by `frontmatter.sidebar.order`, then alphabetically.
   *
   * Use this to ignore sidebar order
   */
  sortAlphabetically?: boolean;

  /*
   * specifically to support compatibility footer in CustomLink card
   */
  callback?: Function;
}

function hasSidebarOrder(page: Route): number | undefined {
  return page.entry.data.sidebar.order;
}

function alphaSort(a: Route, b: Route): number {
  return a.entry.data.title.localeCompare(b.entry.data.title);
}

function compareOrder(a: Route, b: Route): boolean {
  const orderA = a.entry.data.sidebar?.order ?? 0;
  const orderB = b.entry.data.sidebar?.order ?? 0;
  return orderA > orderB;
}

let { slug }: Props = Astro.props;

const {
  filterOutByTitle = [],
  filterOutByFileName = [],
  sortAlphabetically = false,
  callback,
} = Astro.props;

const defaultLocale = config.defaultLocale.lang || 'en';
const localesList = config.isMultilingual ? Object.keys(config.locales) : [defaultLocale];

slug = stripLeadingAndTrailingSlashes(slug.toLowerCase());
let [currentPageLocale] = stripLeadingAndTrailingSlashes(Astro.url.pathname).split('/');

// Ensure currentPageLocale is a locale when it's page is on default locale
if (!localesList.includes(currentPageLocale)) {
  currentPageLocale = defaultLocale;
}

const locale = currentPageLocale;
const pageLang = ensureTrailingSlash(locale);

// Ensure the locale is ignore if passed on `slug`
let [sliceLocale] = stripLeadingAndTrailingSlashes(slug).split('/');
if (localesList.includes(sliceLocale)) {
  slug = slug.slice(sliceLocale.length + 1);
}
// Localize `slug` to the current page locale
slug = locale === defaultLocale ? slug : pageLang + slug;

let fallbackList: Route[] = [];
let mainList: Route[] = [];

routes.forEach((page) => {
  // `page.id` is the slug of the current page being looped, `slug` is component prop
  if (page.id.startsWith(slug)) {
    if (page.isFallback) {
      fallbackList.push(page);
    } else if (page.id !== slug) {
      mainList.push(page);
    }
  }
});

/**
 * Filter items if any filter is set
 */

if (filterOutByTitle.length > 0) {
  fallbackList = fallbackList.filter(
    (page) => !filterOutByTitle.some((val) => page.entry.data.title.includes(val))
  );
  mainList = mainList.filter(
    (page) => !filterOutByTitle.some((val) => page.entry.data.title.includes(val))
  );
}

if (filterOutByFileName.length > 0) {
  fallbackList = fallbackList.filter(
    (page) => !filterOutByFileName.some((val) => page.entry.id.includes(val))
  );
  mainList = mainList.filter(
    (page) => !filterOutByFileName.some((val) => page.entry.id.includes(val))
  );
}

if (!sortAlphabetically) {
  // dumb luck this works, now why?
  const sortVal = locale === defaultLocale ? 1 : -1;
  // Sort list following sidebar order
  mainList.sort((a, b) => {
    if (!hasSidebarOrder(a) && !hasSidebarOrder(b)) {
      return alphaSort(a, b);
    }
    if (compareOrder(a, b)) {
      return sortVal;
    } else {
      return -sortVal;
    }
  });
  // Sort list following sidebar order
  fallbackList.sort((a, b) => {
    if (!hasSidebarOrder(a) && !hasSidebarOrder(b)) {
      return alphaSort(a, b);
    }
    if (compareOrder(a, b)) {
      return -sortVal;
    } else {
      return sortVal;
    }
  });
} else {
  // Sort alphabetically
  mainList.sort((a, b) => alphaSort(a, b));
  fallbackList.sort((a, b) => alphaSort(a, b));
}
---

<CardGrid>
  {
    mainList.map((item) => {
      return (
        <CustomLinkCard
          title={item.entry.data.title}
          href={`/${item.id}/`}
          description={item.entry.data.description}
          footer={callback instanceof Function && callback(item.id)}
        />
      );
    })
  }
  {
    locale !== defaultLocale &&
      fallbackList.map((item) => (
        <CustomLinkCard
          class="fallback-badge"
          title={item.entry.data.title}
          href={`/${item.id}/`}
          description={item.entry.data.description}
          footer={callback instanceof Function && callback(item.id)}
        />
      ))
  }
</CardGrid>

<style>
  .fallback-badge:after {
    /* now how can this match the defaultLocale? */
    /* try with attr() */
    content: 'EN';
    vertical-align: super;
    font-size: 0.75em;
    font-weight: 700;
    margin-left: 1ch;
  }
</style>
