import { Errored } from 'dashboard/core/components/errored';
import { Forbidden } from 'dashboard/core/components/forbidden';
import { GrantPermissionsModal } from 'dashboard/core/components/grant-permissions-modal';
import { NotFound } from 'dashboard/core/components/not-found';
import { ModalContext } from 'dashboard/core/contexts/modals';
import { useAuthorizedFieldPublisherGrants } from 'dashboard/core/utils/event-stream';
import { ALL_ENVIRONMENTS } from 'dashboard/definitions/environments';
import { code } from 'dashboard/generated/controlplane';
import * as _ from 'lodash';
import * as React from 'react';
import { Dispatch, SetStateAction, useContext } from 'react';
import {
  Button,
  ButtonSize,
  ButtonType,
  Color,
  CoreLink,
  CoreText,
  Display,
  JustifyContent,
  Layout,
  LoadingSpinner,
  SVGAsset,
  Table,
  TableCell,
  TableHeader,
  TableHeading,
  TableRow,
  TextAlign,
  TextType,
} from 'twitch-core-ui';

import twirp = code.justin.tv.eventbus.controlplane;

export interface Props {
  eventType: string;
}

export const PublishPermissionsTab = ({ eventType }: Props) => {
  const {
    authorizedPublisherDetails,
    setAuthPubDetails,
    loading,
    error,
    forbidden,
    notFound,
  }: {
    authorizedPublisherDetails: twirp.IGrant[],
    setAuthPubDetails: Dispatch<SetStateAction<twirp.IGrant[]>>,
    loading: boolean,
    error: Error | null,
    forbidden: boolean,
    notFound: boolean,
  } = useAuthorizedFieldPublisherGrants(eventType);

  const pubDetailsByEnv = _.groupBy(authorizedPublisherDetails, 'environment');
  const { showModal } = useContext(ModalContext);

  const handleShowGrantPublishPermissionModal = (et: string, environment: string) => {
    return () =>
      showModal({
        component: GrantPermissionsModal,
        props: {
          prefilledEventType: et,
          prefilledEnvironment: environment,
          onSuccess: (publisherGrant: twirp.IAuthorizedFieldPublisherGrant) => {
            const pg: twirp.IPublisherGrant = {
              environment: publisherGrant.environment,
              iamRoleArn: publisherGrant.iamRole!.arn,
              serviceName: '',
            };
            setAuthPubDetails(_.concat(authorizedPublisherDetails, pg));
          },
        },
      });
  };

  return (
    <>
      {loading && <LoadingSpinner/>}
      {error && <Errored text={'Error fetching subscriptions'}/>}
      {forbidden && <Forbidden/>}
      {notFound && <NotFound/>}
      {!loading && !error && !forbidden && !notFound &&
      <Layout padding={0.5}>
        {_.map(ALL_ENVIRONMENTS, (env, i) => {
          return (
            <Layout padding={1} key={i}>
              <Layout display={Display.Flex} justifyContent={JustifyContent.Between} padding={1}>
                <CoreText type={TextType.H4}>{_.capitalize(env)}</CoreText>
                <Button
                  size={ButtonSize.Small}
                  type={ButtonType.Secondary}
                  onClick={handleShowGrantPublishPermissionModal(eventType, env)}
                  icon={SVGAsset.AddReaction}
                >
                  Add Permission
                </Button>
              </Layout>
            <Table>
              <TableHeader>
                <TableHeading label="IAM Role" textAlign={TextAlign.Center} />
                <TableHeading label="Service Name" textAlign={TextAlign.Center} />
              </TableHeader>
              {
                _.size(pubDetailsByEnv[env]) === 0 ? (
                  <TableRow>
                    <td colSpan={4}>
                      <Layout
                        padding={1}
                        justifyContent={JustifyContent.Center}
                        display={Display.Flex}
                        fullWidth
                      >
                        <CoreText type={TextType.P} color={Color.Alt2}>
                          There are no publishers for this environment.{' '}
                          <CoreLink
                            linkTo={
                              'http://git.xarth.tv/pages/eventbus/docs/subscribers/authorized_fields/'
                            }
                          >
                            Learn more
                          </CoreLink>
                        </CoreText>
                      </Layout>
                    </td>
                  </TableRow>
                ) : (
                _.map(pubDetailsByEnv[env], (grant, j) => {
                return (
                  <TableRow key={j}>
                    <TableCell textAlign={TextAlign.Center}>
                      {grant.iamRoleArn}
                    </TableCell>
                    <TableCell textAlign={TextAlign.Center}>
                      {grant.serviceName}
                    </TableCell>
                  </TableRow>
                );
                }))
              }
            </Table>
          </Layout>
          );
        })}
      </Layout>
      }
    </>
  );
};
