import {Fragment} from 'react';
import styled from '@emotion/styled';

import {Button} from 'sentry/components/button';
import Confirm from 'sentry/components/confirm';
import Link from 'sentry/components/links/link';
import LoadingIndicator from 'sentry/components/loadingIndicator';
import Placeholder from 'sentry/components/placeholder';
import TimeSince from 'sentry/components/timeSince';
import {Tooltip} from 'sentry/components/tooltip';
import {IconSubtract} from 'sentry/icons';
import {t, tct} from 'sentry/locale';
import {space} from 'sentry/styles/space';
import type {Organization, OrgAuthToken, Project} from 'sentry/types';
import getDynamicText from 'sentry/utils/getDynamicText';
import {tokenPreview} from 'sentry/views/settings/organizationAuthTokens';

function LastUsed({
  organization,
  dateLastUsed,
  projectLastUsed,
}: {
  organization: Organization;
  dateLastUsed?: Date;
  projectLastUsed?: Project;
}) {
  if (dateLastUsed && projectLastUsed) {
    return (
      <Fragment>
        {tct('[date] in project [project]', {
          date: (
            <TimeSince
              date={getDynamicText({
                value: dateLastUsed,
                fixed: new Date(1508208080000), // National Pasta Day
              })}
            />
          ),
          project: (
            <Link to={`/settings/${organization.slug}/${projectLastUsed.slug}/`}>
              {projectLastUsed.name}
            </Link>
          ),
        })}
      </Fragment>
    );
  }

  if (dateLastUsed) {
    return (
      <Fragment>
        <TimeSince
          date={getDynamicText({
            value: dateLastUsed,
            fixed: new Date(1508208080000), // National Pasta Day
          })}
        />
      </Fragment>
    );
  }

  if (projectLastUsed) {
    return (
      <Fragment>
        {tct('in project [project]', {
          project: (
            <Link to={`/settings/${organization.slug}/${projectLastUsed.slug}/`}>
              {projectLastUsed.name}
            </Link>
          ),
        })}
      </Fragment>
    );
  }

  return <NeverUsed>{t('never used')}</NeverUsed>;
}

export function OrganizationAuthTokensAuthTokenRow({
  organization,
  isRevoking,
  token,
  revokeToken,
  projectLastUsed,
  isProjectLoading,
}: {
  isRevoking: boolean;
  organization: Organization;
  token: OrgAuthToken;
  isProjectLoading?: boolean;
  projectLastUsed?: Project;
  revokeToken?: (token: OrgAuthToken) => void;
}) {
  return (
    <Fragment>
      <div>
        <Label>
          <Link to={`/settings/${organization.slug}/auth-tokens/${token.id}/`}>
            {token.name}
          </Link>
        </Label>

        {token.tokenLastCharacters && (
          <TokenPreview aria-label={t('Token preview')}>
            {tokenPreview(
              getDynamicText({
                value: token.tokenLastCharacters,
                fixed: 'ABCD',
              }),
              'sntrys_'
            )}
          </TokenPreview>
        )}
      </div>

      <DateTime>
        {isProjectLoading ? (
          <Placeholder height="1.25em" />
        ) : (
          <Fragment>
            <TimeSince
              date={getDynamicText({
                value: token.dateCreated,
                fixed: new Date(1508208080000), // National Pasta Day
              })}
            />
          </Fragment>
        )}
      </DateTime>

      <DateTime>
        {isProjectLoading ? (
          <Placeholder height="1.25em" />
        ) : (
          <LastUsed
            dateLastUsed={token.dateLastUsed}
            projectLastUsed={projectLastUsed}
            organization={organization}
          />
        )}
      </DateTime>

      <Actions>
        <Tooltip
          title={t(
            'You must be an organization owner, manager or admin to revoke a token.'
          )}
          disabled={!!revokeToken}
        >
          <Confirm
            disabled={!revokeToken || isRevoking}
            onConfirm={revokeToken ? () => revokeToken(token) : undefined}
            message={t(
              'Are you sure you want to revoke %s token? It will not be usable anymore, and this cannot be undone.',
              tokenPreview(token.tokenLastCharacters || '', 'sntrys_')
            )}
          >
            <Button
              size="sm"
              disabled={isRevoking || !revokeToken}
              aria-label={t('Revoke %s', token.name)}
              icon={
                isRevoking ? (
                  <LoadingIndicator mini />
                ) : (
                  <IconSubtract isCircled size="xs" />
                )
              }
            >
              {t('Revoke')}
            </Button>
          </Confirm>
        </Tooltip>
      </Actions>
    </Fragment>
  );
}

const Label = styled('div')``;

const Actions = styled('div')`
  display: flex;
  justify-content: flex-end;
`;

const DateTime = styled('div')`
  display: flex;
  align-items: center;
  gap: ${space(0.5)};
`;

const NeverUsed = styled('div')`
  color: ${p => p.theme.gray300};
`;

const TokenPreview = styled('div')`
  color: ${p => p.theme.gray300};
`;