import { useEffect, useState } from 'react'
import { Meta, ProfileMetadata } from '../../types'
import { SigitCardDisplayInfo, SigitStatus } from '../../utils'
import { Event, kinds } from 'nostr-tools'
import { Link } from 'react-router-dom'
import { MetadataController } from '../../controllers'
import { formatTimestamp, hexToNpub, npubToHex, shorten } from '../../utils'
import { appPublicRoutes, appPrivateRoutes } from '../../routes'
import { Button, Divider, Tooltip } from '@mui/material'
import { DisplaySigner } from '../DisplaySigner'
import {
  faArchive,
  faCalendar,
  faCopy,
  faEye,
  faFile
} from '@fortawesome/free-solid-svg-icons'
import { FontAwesomeIcon } from '@fortawesome/react-fontawesome'
import { UserAvatar } from '../UserAvatar'
import { UserAvatarGroup } from '../UserAvatarGroup'

import styles from './style.module.scss'
import { TooltipChild } from '../TooltipChild'
import { getExtensionIconLabel } from '../getExtensionIconLabel'

type SigitProps = {
  meta: Meta
  parsedMeta: SigitCardDisplayInfo
}

export const DisplaySigit = ({ meta, parsedMeta }: SigitProps) => {
  const {
    title,
    createdAt,
    submittedBy,
    signers,
    signedStatus,
    fileExtensions
  } = parsedMeta

  const [profiles, setProfiles] = useState<{ [key: string]: ProfileMetadata }>(
    {}
  )

  useEffect(() => {
    const hexKeys = new Set<string>([
      ...signers.map((signer) => npubToHex(signer)!)
    ])

    if (submittedBy) {
      hexKeys.add(npubToHex(submittedBy)!)
    }

    const metadataController = new MetadataController()

    const handleMetadataEvent = (key: string) => (event: Event) => {
      const metadataContent =
        metadataController.extractProfileMetadataContent(event)

      if (metadataContent) {
        setProfiles((prev) => ({
          ...prev,
          [key]: metadataContent
        }))
      }
    }

    const handleEventListener =
      (key: string) => (kind: number, event: Event) => {
        if (kind === kinds.Metadata) {
          handleMetadataEvent(key)(event)
        }
      }

    hexKeys.forEach((key) => {
      if (!(key in profiles)) {
        metadataController.on(key, handleEventListener(key))

        metadataController
          .findMetadata(key)
          .then((metadataEvent) => {
            if (metadataEvent) handleMetadataEvent(key)(metadataEvent)
          })
          .catch((err) => {
            console.error(`error occurred in finding metadata for: ${key}`, err)
          })
      }
    })

    return () => {
      hexKeys.forEach((key) => {
        metadataController.off(key, handleEventListener(key))
      })
    }
  }, [submittedBy, signers, profiles])

  return (
    <div className={styles.itemWrapper}>
      <Link
        to={
          signedStatus === SigitStatus.Complete
            ? appPublicRoutes.verify
            : appPrivateRoutes.sign
        }
        state={{ meta }}
        className={styles.insetLink}
      ></Link>
      <p className={`line-clamp-2 ${styles.title}`}>{title}</p>
      <div className={styles.users}>
        {submittedBy &&
          (function () {
            const profile = profiles[submittedBy]
            return (
              <Tooltip
                title={
                  profile?.display_name ||
                  profile?.name ||
                  shorten(hexToNpub(submittedBy))
                }
                placement="top"
                arrow
                disableInteractive
              >
                <TooltipChild>
                  <UserAvatar pubkey={submittedBy} image={profile?.picture} />
                </TooltipChild>
              </Tooltip>
            )
          })()}
        {submittedBy && signers.length ? (
          <Divider orientation="vertical" flexItem />
        ) : null}
        <UserAvatarGroup className={styles.signers} max={7}>
          {signers.map((signer) => {
            const pubkey = npubToHex(signer)!
            const profile = profiles[pubkey]

            return (
              <Tooltip
                key={signer}
                title={
                  profile?.display_name || profile?.name || shorten(pubkey)
                }
                placement="top"
                arrow
                disableInteractive
              >
                <TooltipChild>
                  <DisplaySigner
                    meta={meta}
                    profile={profile}
                    pubkey={pubkey}
                  />
                </TooltipChild>
              </Tooltip>
            )
          })}
        </UserAvatarGroup>
      </div>
      <div className={`${styles.details} ${styles.date} ${styles.iconLabel}`}>
        <FontAwesomeIcon icon={faCalendar} />
        {createdAt ? formatTimestamp(createdAt) : null}
      </div>
      <div className={`${styles.details} ${styles.status}`}>
        <span className={styles.iconLabel}>
          <FontAwesomeIcon icon={faEye} /> {signedStatus}
        </span>
        {fileExtensions.length > 0 ? (
          <span className={styles.iconLabel}>
            {fileExtensions.length > 1 ? (
              <>
                <FontAwesomeIcon icon={faFile} /> Multiple File Types
              </>
            ) : (
              getExtensionIconLabel(fileExtensions[0])
            )}
          </span>
        ) : null}
      </div>
      <div className={styles.itemActions}>
        <Tooltip title="Duplicate" arrow placement="top" disableInteractive>
          <Button
            sx={{
              color: 'var(--primary-main)',
              minWidth: '34px',
              padding: '10px'
            }}
            variant={'text'}
          >
            <FontAwesomeIcon icon={faCopy} />
          </Button>
        </Tooltip>
        <Tooltip title="Archive" arrow placement="top" disableInteractive>
          <Button
            sx={{
              color: 'var(--primary-main)',
              minWidth: '34px',
              padding: '10px'
            }}
            variant={'text'}
          >
            <FontAwesomeIcon icon={faArchive} />
          </Button>
        </Tooltip>
      </div>
    </div>
  )
}
