/**
 * Copyright (c) 2023-present Plane Software, Inc. and contributors
 * SPDX-License-Identifier: AGPL-3.0-only
 * See the LICENSE file for details.
 */

import { isRouteErrorResponse } from "react-router";
import { Banner } from "@plane/propel/banner";
import { Button } from "@plane/propel/button";
import { InfoFillIcon } from "@plane/propel/icons";

interface ErrorActionsProps {
  onGoHome: () => void;
  onReload?: () => void;
}

function ErrorActions({ onGoHome, onReload }: ErrorActionsProps) {
  return (
    <div className="flex gap-3 pt-2">
      <Button variant="primary" size="lg" onClick={onGoHome} className="nodedc-error-primary">
        На главную
      </Button>
      {onReload && (
        <Button variant="secondary" size="lg" onClick={onReload} className="nodedc-empty-state-secondary">
          Обновить страницу
        </Button>
      )}
    </div>
  );
}

interface DevErrorComponentProps {
  error: unknown;
  onGoHome: () => void;
  onReload: () => void;
}

const ErrorShell = ({ children }: { children: React.ReactNode }) => (
  <div className="nodedc-error-shell transition-none">{children}</div>
);

export function DevErrorComponent({ error, onGoHome, onReload }: DevErrorComponentProps) {
  if (isRouteErrorResponse(error)) {
    return (
      <div className="flex min-h-screen items-start justify-center bg-surface-2 p-6 transition-none">
        <div className="mt-12 w-full max-w-4xl space-y-4 transition-none">
          <Banner variant="error" icon={<InfoFillIcon className="size-5" />} title="Ошибка маршрута" animationDuration={0} />
          <ErrorShell>
            <div className="space-y-4">
              <div>
                <h2 className="mb-2 text-20 font-semibold text-danger-primary">
                  {error.status} {error.statusText}
                </h2>
                <div className="bg-subtle-1 h-px w-full" />
              </div>

              <div className="space-y-2">
                <h3 className="text-13 font-medium tracking-wide text-tertiary uppercase">Данные ошибки</h3>
                <div className="rounded-[1.1rem] bg-white/5 p-4">
                  <p className="font-code text-13 text-secondary">{error.data}</p>
                </div>
              </div>

              <ErrorActions onGoHome={onGoHome} onReload={onReload} />
            </div>
          </ErrorShell>
        </div>
      </div>
    );
  }

  if (error instanceof Error) {
    return (
      <div className="flex min-h-screen items-start justify-center bg-surface-2 p-6 transition-none">
        <div className="mt-12 w-full max-w-4xl space-y-4 transition-none">
          <Banner
            variant="error"
            icon={<InfoFillIcon className="size-5" />}
            title="Ошибка выполнения"
            animationDuration={0}
          />
          <ErrorShell>
            <div className="space-y-4">
              <div>
                <h2 className="mb-2 text-20 font-semibold text-danger-primary">Ошибка</h2>
                <div className="bg-subtle-1 h-px w-full" />
              </div>

              <div className="space-y-2">
                <h3 className="text-13 font-medium tracking-wide text-tertiary uppercase">Сообщение</h3>
                <div className="rounded-[1.1rem] bg-white/5 p-4">
                  <p className="text-13 font-medium text-primary">{error.message}</p>
                </div>
              </div>

              {error.stack && (
                <div className="space-y-2">
                  <h3 className="text-13 font-medium tracking-wide text-tertiary uppercase">Стек вызовов</h3>
                  <div className="max-h-96 overflow-auto rounded-[1.1rem] bg-white/5">
                    <pre className="p-4 font-code text-11 break-words whitespace-pre-wrap text-secondary">
                      {error.stack}
                    </pre>
                  </div>
                </div>
              )}

              <ErrorActions onGoHome={onGoHome} onReload={onReload} />
            </div>
          </ErrorShell>

          <div className="nodedc-external-panel p-4 transition-none">
            <div className="flex items-start gap-3">
              <InfoFillIcon className="mt-0.5 size-5 flex-shrink-0 text-tertiary" />
              <div className="space-y-1">
                <p className="text-13 font-medium text-secondary">Режим разработки</p>
                <p className="text-11 text-tertiary">
                  Этот подробный экран ошибок виден только в разработке. В production пользователи увидят упрощённую
                  страницу ошибки.
                </p>
              </div>
            </div>
          </div>
        </div>
      </div>
    );
  }

  return (
    <div className="flex min-h-screen items-start justify-center bg-surface-2 p-6 transition-none">
      <div className="mt-12 w-full max-w-4xl space-y-4 transition-none">
        <Banner variant="error" icon={<InfoFillIcon className="size-5" />} title="Неизвестная ошибка" animationDuration={0} />
        <ErrorShell>
          <div className="space-y-4">
            <div>
              <h2 className="mb-2 text-20 font-semibold text-primary">Неизвестная ошибка</h2>
              <div className="bg-subtle-1 h-px w-full" />
            </div>

            <div className="rounded-[1.1rem] bg-white/5 p-4">
              <p className="text-13 text-secondary">
                Произошла неизвестная ошибка. Обновите страницу. Если проблема сохранится, обратитесь в службу
                поддержки.
              </p>
            </div>

            <ErrorActions onGoHome={onGoHome} onReload={onReload} />
          </div>
        </ErrorShell>
      </div>
    </div>
  );
}
