diff --git a/src/components/notifications/ConfigTableRowActionButton.tsx b/src/components/notifications/ConfigTableRowActionButton.tsx
index fb087179d3..447c67f9a7 100644
--- a/src/components/notifications/ConfigTableRowActionButton.tsx
+++ b/src/components/notifications/ConfigTableRowActionButton.tsx
@@ -14,11 +14,18 @@
* limitations under the License.
*/
-import { Button, ButtonStyleType, ButtonVariantType, ComponentSizeType } from '@devtron-labs/devtron-fe-common-lib'
+import { useHistory } from 'react-router-dom'
-import { ReactComponent as Edit } from '@Icons/ic-pencil.svg'
-import { Trash } from '@Components/common'
+import {
+ Button,
+ ButtonStyleType,
+ ButtonVariantType,
+ ComponentSizeType,
+ Icon,
+ useSearchString,
+} from '@devtron-labs/devtron-fe-common-lib'
+import { ConfigurationsTabTypes } from './constants'
import { ConfigTableRowActionButtonProps } from './types'
export const ConfigTableRowActionButton = ({
@@ -33,7 +40,7 @@ export const ConfigTableRowActionButton = ({
variant={ButtonVariantType.borderLess}
size={ComponentSizeType.xs}
dataTestId={`${modal}-config-edit-button`}
- icon={}
+ icon={}
ariaLabel="Edit"
style={ButtonStyleType.neutral}
/>
@@ -42,10 +49,42 @@ export const ConfigTableRowActionButton = ({
variant={ButtonVariantType.borderLess}
size={ComponentSizeType.xs}
dataTestId={`${modal}-config-delete-button`}
- icon={}
+ icon={}
ariaLabel="Delete"
style={ButtonStyleType.negativeGrey}
/>
)
+
+export const ConfigurationRowActionButtonWrapper = ({
+ row,
+ deleteClickHandler,
+ modal,
+}: {
+ row: any
+ deleteClickHandler: (id: number, modal: ConfigurationsTabTypes) => () => void
+ modal: ConfigurationsTabTypes
+}) => {
+ const { searchParams } = useSearchString()
+ const history = useHistory()
+
+ const onClickEditRow = () => () => {
+ const newParams = {
+ ...searchParams,
+ configId: row.id,
+ modal,
+ }
+ history.push({
+ search: new URLSearchParams(newParams).toString(),
+ })
+ }
+
+ return (
+
+ )
+}
diff --git a/src/components/notifications/ConfigurationTables.tsx b/src/components/notifications/ConfigurationTables.tsx
index c31905834d..30286c659b 100644
--- a/src/components/notifications/ConfigurationTables.tsx
+++ b/src/components/notifications/ConfigurationTables.tsx
@@ -18,8 +18,6 @@ import { Route, Switch, useRouteMatch } from 'react-router-dom'
import { showError } from '@devtron-labs/devtron-fe-common-lib'
-import { DeleteComponentsName } from '@Config/constantMessaging'
-
import { ConfigurationsTabTypes } from './constants'
import {
getSESConfiguration,
@@ -77,7 +75,7 @@ export const ConfigurationTables = ({ activeTab, state, setState }: Configuratio
...state,
webhookConfig: {
...result,
- channel: DeleteComponentsName.WebhookConfigurationTab,
+ channel: ConfigurationsTabTypes.WEBHOOK,
},
confirmation: true,
activeTab: ConfigurationsTabTypes.WEBHOOK,
diff --git a/src/components/notifications/SESConfigurationTable.tsx b/src/components/notifications/SESConfigurationTable.tsx
index 0fc2bc6a66..e26b221d20 100644
--- a/src/components/notifications/SESConfigurationTable.tsx
+++ b/src/components/notifications/SESConfigurationTable.tsx
@@ -14,17 +14,21 @@
* limitations under the License.
*/
+import { useMemo } from 'react'
import { useHistory } from 'react-router-dom'
-import { useSearchString } from '@devtron-labs/devtron-fe-common-lib'
+import {
+ FiltersTypeEnum,
+ InteractiveCellText,
+ PaginationEnum,
+ Table,
+ useSearchString,
+} from '@devtron-labs/devtron-fe-common-lib'
-import { InteractiveCellText } from '@Components/common/helpers/InteractiveCellText/InteractiveCellText'
-import { DeleteComponentsName } from '@Config/constantMessaging'
-
-import { ConfigTableRowActionButton } from './ConfigTableRowActionButton'
-import { ConfigurationsTabTypes } from './constants'
-import { getConfigTabIcons, renderDefaultTag } from './notifications.util'
-import { ConfigurationTableProps } from './types'
+import { ConfigurationRowActionButtonWrapper } from './ConfigTableRowActionButton'
+import { BASE_CONFIG, ConfigurationsTabTypes, SES_TABLE_COLUMNS } from './constants'
+import { renderDefaultTag } from './notifications.util'
+import { ConfigurationTableProps, SESConfigurationTableRowType } from './types'
import './notifications.scss'
@@ -32,7 +36,7 @@ const SESConfigurationTable = ({ state, deleteClickHandler }: ConfigurationTable
const { searchParams } = useSearchString()
const history = useHistory()
- const onClickSESConfigEdit = (id: number) => () => {
+ const onClickEditRow = (id: number) => () => {
const newParams = {
...searchParams,
configId: id.toString(),
@@ -43,43 +47,56 @@ const SESConfigurationTable = ({ state, deleteClickHandler }: ConfigurationTable
})
}
- return (
-
-
-
-
Name
-
Access Key Id
-
Sender's Email
-
-
-
- {state.sesConfigurationList.map((sesConfig) => (
-
- {getConfigTabIcons(ConfigurationsTabTypes.SES)}
-
-
+ const tableRows = useMemo(
+ () =>
+ state.sesConfigurationList.map((sesConfig) => ({
+ id: `${sesConfig.id}`,
+ data: {
+ name: (
+
+
{renderDefaultTag(sesConfig.isDefault)}
-
-
-
-
- ))}
-
-
+ ),
+ accessKeyId: sesConfig.accessKeyId,
+ email: sesConfig.email,
+ },
+ })),
+ [state.sesConfigurationList],
+ )
+
+ const onRowClick = (rowData) => {
+ onClickEditRow(Number(rowData.id))()
+ }
+
+ return (
+
+ id="table__ses-configuration"
+ columns={SES_TABLE_COLUMNS}
+ rows={tableRows}
+ emptyStateConfig={{
+ noRowsConfig: {
+ title: 'No SES Configurations Found',
+ },
+ }}
+ filtersVariant={FiltersTypeEnum.STATE}
+ additionalFilterProps={{
+ initialSortKey: BASE_CONFIG[0].field,
+ }}
+ paginationVariant={PaginationEnum.NOT_PAGINATED}
+ filter={null}
+ rowStartIconConfig={{
+ name: 'ic-ses',
+ color: null,
+ size: 24,
+ }}
+ rowActionOnHoverConfig={{
+ width: 100,
+ Component: ConfigurationRowActionButtonWrapper,
+ }}
+ additionalProps={{ deleteClickHandler, modal: ConfigurationsTabTypes.SES }}
+ onRowClick={onRowClick}
+ />
)
}
diff --git a/src/components/notifications/SMTPConfigurationTable.tsx b/src/components/notifications/SMTPConfigurationTable.tsx
index d07fe05789..525d1a0c49 100644
--- a/src/components/notifications/SMTPConfigurationTable.tsx
+++ b/src/components/notifications/SMTPConfigurationTable.tsx
@@ -14,27 +14,27 @@
* limitations under the License.
*/
+import { useMemo } from 'react'
import { useHistory } from 'react-router-dom'
-import { useSearchString } from '@devtron-labs/devtron-fe-common-lib'
+import { FiltersTypeEnum, PaginationEnum, Table, useSearchString } from '@devtron-labs/devtron-fe-common-lib'
import { InteractiveCellText } from '@Components/common/helpers/InteractiveCellText/InteractiveCellText'
-import { DeleteComponentsName } from '@Config/constantMessaging'
-import { ConfigTableRowActionButton } from './ConfigTableRowActionButton'
-import { ConfigurationsTabTypes } from './constants'
-import { getConfigTabIcons, renderDefaultTag } from './notifications.util'
-import { ConfigurationTableProps } from './types'
+import { ConfigurationRowActionButtonWrapper } from './ConfigTableRowActionButton'
+import { BASE_CONFIG, ConfigurationsTabTypes, SMTP_TABLE_COLUMNS } from './constants'
+import { renderDefaultTag } from './notifications.util'
+import { ConfigurationTableProps, SMTPConfigurationTableRowType } from './types'
export const SMTPConfigurationTable = ({ state, deleteClickHandler }: ConfigurationTableProps) => {
const { smtpConfigurationList } = state
const { searchParams } = useSearchString()
const history = useHistory()
- const onClickEditRow = (configId) => () => {
+ const onClickEditRow = (id: number) => () => {
const newParams = {
...searchParams,
- configId: configId.toString(),
+ configId: id.toString(),
modal: ConfigurationsTabTypes.SMTP,
}
history.push({
@@ -42,51 +42,59 @@ export const SMTPConfigurationTable = ({ state, deleteClickHandler }: Configurat
})
}
- return (
-
-
-
-
Name
-
Host
-
Port
-
Sender' Email
-
-
-
- {smtpConfigurationList.map((smtpConfig) => (
-
- {getConfigTabIcons(ConfigurationsTabTypes.SMTP)}
-
+ const tableRows = useMemo(
+ () =>
+ smtpConfigurationList.map((smtpConfig) => ({
+ id: `${smtpConfig.id}`,
+ data: {
+ name: (
+
{renderDefaultTag(smtpConfig.isDefault)}
-
-
-
-
-
- ))}
-
-
+ ),
+ host: smtpConfig.host,
+ port: smtpConfig.port.toString(),
+ email: smtpConfig.email,
+ },
+ })),
+ [smtpConfigurationList],
+ )
+
+ const onRowClick = (rowData) => {
+ onClickEditRow(Number(rowData.id))()
+ }
+
+ return (
+
+ id="table__smtp-configuration"
+ columns={SMTP_TABLE_COLUMNS}
+ rows={tableRows}
+ emptyStateConfig={{
+ noRowsConfig: {
+ title: 'No SMTP Configurations Found',
+ },
+ }}
+ filtersVariant={FiltersTypeEnum.STATE}
+ additionalFilterProps={{
+ initialSortKey: BASE_CONFIG[0].field,
+ }}
+ paginationVariant={PaginationEnum.NOT_PAGINATED}
+ filter={null}
+ rowStartIconConfig={{
+ name: 'ic-smtp',
+ color: null,
+ size: 24,
+ }}
+ rowActionOnHoverConfig={{
+ width: 100,
+ Component: ConfigurationRowActionButtonWrapper,
+ }}
+ additionalProps={{ deleteClickHandler, modal: ConfigurationsTabTypes.SMTP }}
+ onRowClick={onRowClick}
+ />
)
}
diff --git a/src/components/notifications/SlackConfigurationTable.tsx b/src/components/notifications/SlackConfigurationTable.tsx
index 0918182f0d..b791de075c 100644
--- a/src/components/notifications/SlackConfigurationTable.tsx
+++ b/src/components/notifications/SlackConfigurationTable.tsx
@@ -14,17 +14,16 @@
* limitations under the License.
*/
+import { useMemo } from 'react'
import { useHistory } from 'react-router-dom'
-import { useSearchString } from '@devtron-labs/devtron-fe-common-lib'
+import { FiltersTypeEnum, PaginationEnum, Table, useSearchString } from '@devtron-labs/devtron-fe-common-lib'
import { InteractiveCellText } from '@Components/common/helpers/InteractiveCellText/InteractiveCellText'
-import { DeleteComponentsName } from '@Config/constantMessaging'
-import { ConfigTableRowActionButton } from './ConfigTableRowActionButton'
-import { ConfigurationsTabTypes } from './constants'
-import { getConfigTabIcons } from './notifications.util'
-import { ConfigurationTableProps } from './types'
+import { ConfigurationRowActionButtonWrapper } from './ConfigTableRowActionButton'
+import { BASE_CONFIG, ConfigurationsTabTypes, SLACK_WEBHOOK_TABLE_COLUMNS } from './constants'
+import { ConfigurationTableProps, SlackWebhookConfigurationTableRowType } from './types'
import './notifications.scss'
@@ -33,7 +32,7 @@ const SlackConfigurationTable = ({ state, deleteClickHandler }: ConfigurationTab
const history = useHistory()
const { slackConfigurationList } = state
- const onClickSlackConfigEdit = (id: number) => () => {
+ const onClickEditRow = (id: number) => () => {
const newParams = {
...searchParams,
configId: id.toString(),
@@ -44,40 +43,57 @@ const SlackConfigurationTable = ({ state, deleteClickHandler }: ConfigurationTab
})
}
- return (
-
-
-
-
Name
-
Webhook URL
-
-
-
- {slackConfigurationList.map((slackConfig) => (
-
- {getConfigTabIcons(ConfigurationsTabTypes.SLACK)}
-
+ const tableRow = useMemo(
+ () =>
+ slackConfigurationList.map((slackConfig) => ({
+ id: `${slackConfig.id}`,
+ data: {
+ name: (
+
-
-
-
- ))}
-
-
+ ),
+ webhookUrl: slackConfig.webhookUrl,
+ },
+ })),
+ [state.slackConfigurationList],
+ )
+
+ const onRowClick = (rowData) => {
+ onClickEditRow(Number(rowData.id))()
+ }
+
+ return (
+
+ id="table__slack-configuration"
+ columns={SLACK_WEBHOOK_TABLE_COLUMNS}
+ rows={tableRow}
+ emptyStateConfig={{
+ noRowsConfig: {
+ title: 'No Slack Configurations Found',
+ },
+ }}
+ filtersVariant={FiltersTypeEnum.STATE}
+ additionalFilterProps={{
+ initialSortKey: BASE_CONFIG[0].field,
+ }}
+ paginationVariant={PaginationEnum.NOT_PAGINATED}
+ filter={null}
+ rowStartIconConfig={{
+ name: 'ic-slack',
+ color: null,
+ size: 24,
+ }}
+ rowActionOnHoverConfig={{
+ width: 100,
+ Component: ConfigurationRowActionButtonWrapper,
+ }}
+ additionalProps={{ deleteClickHandler, modal: ConfigurationsTabTypes.SLACK }}
+ onRowClick={onRowClick}
+ />
)
}
diff --git a/src/components/notifications/WebhookConfigurationTable.tsx b/src/components/notifications/WebhookConfigurationTable.tsx
index 8eeb174c9e..685858209c 100644
--- a/src/components/notifications/WebhookConfigurationTable.tsx
+++ b/src/components/notifications/WebhookConfigurationTable.tsx
@@ -14,17 +14,16 @@
* limitations under the License.
*/
+import { useMemo } from 'react'
import { useHistory } from 'react-router-dom'
-import { useSearchString } from '@devtron-labs/devtron-fe-common-lib'
+import { FiltersTypeEnum, PaginationEnum, Table, useSearchString } from '@devtron-labs/devtron-fe-common-lib'
import { InteractiveCellText } from '@Components/common/helpers/InteractiveCellText/InteractiveCellText'
-import { DeleteComponentsName } from '@Config/constantMessaging'
-import { ConfigTableRowActionButton } from './ConfigTableRowActionButton'
-import { ConfigurationsTabTypes } from './constants'
-import { getConfigTabIcons } from './notifications.util'
-import { ConfigurationTableProps } from './types'
+import { ConfigurationRowActionButtonWrapper } from './ConfigTableRowActionButton'
+import { BASE_CONFIG, ConfigurationsTabTypes, SLACK_WEBHOOK_TABLE_COLUMNS } from './constants'
+import { ConfigurationTableProps, SlackWebhookConfigurationTableRowType } from './types'
export const WebhookConfigurationTable = ({ state, deleteClickHandler }: ConfigurationTableProps) => {
const { webhookConfigurationList } = state
@@ -42,42 +41,56 @@ export const WebhookConfigurationTable = ({ state, deleteClickHandler }: Configu
})
}
+ const tableRows = useMemo(
+ () =>
+ webhookConfigurationList.map((webhookConfig) => ({
+ id: `${webhookConfig.id}`,
+ data: {
+ name: (
+
+
+
+ ),
+ webhookUrl: webhookConfig.webhookUrl,
+ },
+ })),
+ [webhookConfigurationList],
+ )
+
+ const onRowClick = (rowData) => {
+ onClickWebhookConfigEdit(Number(rowData.id))()
+ }
+
return (
-
-
-
-
Name
-
Webhook URL
-
-
-
- {webhookConfigurationList.map((webhookConfig) => (
-
- {getConfigTabIcons(ConfigurationsTabTypes.WEBHOOK)}
-
-
-
-
- ))}
-
-
+
+ id="table__webhook-configuration"
+ columns={SLACK_WEBHOOK_TABLE_COLUMNS}
+ rows={tableRows}
+ emptyStateConfig={{
+ noRowsConfig: {
+ title: 'No Webhook Configurations Found',
+ },
+ }}
+ filtersVariant={FiltersTypeEnum.STATE}
+ additionalFilterProps={{
+ initialSortKey: BASE_CONFIG[0].field,
+ }}
+ paginationVariant={PaginationEnum.NOT_PAGINATED}
+ filter={null}
+ rowStartIconConfig={{
+ name: 'ic-webhook-config',
+ color: null,
+ size: 24,
+ }}
+ rowActionOnHoverConfig={{
+ width: 100,
+ Component: ConfigurationRowActionButtonWrapper,
+ }}
+ additionalProps={{ deleteClickHandler, modal: ConfigurationsTabTypes.WEBHOOK }}
+ onRowClick={onRowClick}
+ />
)
}
diff --git a/src/components/notifications/constants.ts b/src/components/notifications/constants.ts
index f52e27c2c7..e10d669e93 100644
--- a/src/components/notifications/constants.ts
+++ b/src/components/notifications/constants.ts
@@ -16,7 +16,14 @@
// ------------ Configuration Constants ------------
-import { SlackFormType } from './types'
+import { FiltersTypeEnum, TableProps } from '@devtron-labs/devtron-fe-common-lib'
+
+import {
+ SESConfigurationTableRowType,
+ SlackFormType,
+ SlackWebhookConfigurationTableRowType,
+ SMTPConfigurationTableRowType,
+} from './types'
export enum ConfigurationsTabTypes {
SES = 'ses',
@@ -120,3 +127,59 @@ export const DefaultWebhookValidations = {
}
export const SlackIncomingWebhookUrl = 'https://slack.com/marketplace/A0F7XDUAZ-incoming-webhooks'
+
+// ------------ Common Configuration Constants ------------
+
+export const BASE_CONFIG = [
+ {
+ label: 'Name',
+ field: 'name',
+ size: null,
+ },
+]
+
+export const SES_TABLE_COLUMNS: TableProps['columns'] = [
+ ...BASE_CONFIG,
+ {
+ label: 'Access Key Id',
+ field: 'accessKeyId',
+ size: null,
+ },
+ {
+ label: "Sender's Email",
+ field: 'email',
+ size: null,
+ },
+]
+
+export const SMTP_TABLE_COLUMNS: TableProps['columns'] = [
+ ...BASE_CONFIG,
+ {
+ label: 'Host',
+ field: 'host',
+ size: null,
+ },
+ {
+ label: 'Port',
+ field: 'port',
+ size: null,
+ },
+ {
+ label: "Sender's Email",
+ field: 'email',
+ size: null,
+ },
+]
+
+export const SLACK_WEBHOOK_TABLE_COLUMNS: TableProps<
+ SlackWebhookConfigurationTableRowType,
+ FiltersTypeEnum.STATE,
+ {}
+>['columns'] = [
+ ...BASE_CONFIG,
+ {
+ label: 'Webhook URL',
+ field: 'webhookUrl',
+ size: null,
+ },
+]
diff --git a/src/components/notifications/notifications.util.tsx b/src/components/notifications/notifications.util.tsx
index fbf8364c9f..8207368621 100644
--- a/src/components/notifications/notifications.util.tsx
+++ b/src/components/notifications/notifications.util.tsx
@@ -22,21 +22,26 @@ import { ReactComponent as CI } from '@Icons/ic-CI.svg'
import { ReactComponent as CD } from '@Icons/ic-CD.svg'
import { ReactComponent as Rocket } from '@Icons/ic-paper-rocket.svg'
import { ReactComponent as Slack } from '@Icons/slack-logo.svg'
-import { ReactComponent as SES } from '@Icons/ic-aws-ses.svg'
import { ReactComponent as Webhook } from '@Icons/ic-CIWebhook.svg'
-import { ReactComponent as SMTP } from '@Icons/ic-smtp.svg'
import {
commonSelectStyles,
DynamicDataTableHeaderType,
DynamicDataTableRowDataType,
getUniqueId,
+ Icon,
+ IconBaseSizeType,
ToastManager,
ToastVariantType,
- Tooltip,
} from '@devtron-labs/devtron-fe-common-lib'
import { ConfigurationFieldKeys, ConfigurationsTabTypes, ConfigurationTabText } from './constants'
import { validateEmail } from '../common'
-import { FormError, SESFormType, SMTPFormType, WebhookDataRowType, WebhookHeaderKeyType } from './types'
+import {
+ FormError,
+ SESFormType,
+ SMTPFormType,
+ WebhookDataRowType,
+ WebhookHeaderKeyType,
+} from './types'
import { REQUIRED_FIELD_MSG } from '@Config/constantMessaging'
export const multiSelectStyles = {
@@ -166,17 +171,17 @@ export const renderPipelineTypeIcon = (row) => {
return
}
-export const getConfigTabIcons = (tab: ConfigurationsTabTypes, size: number = 24) => {
+export const getConfigTabIcons = (tab: ConfigurationsTabTypes, size: IconBaseSizeType = 24) => {
switch (tab) {
case ConfigurationsTabTypes.SMTP:
- return
+ return
case ConfigurationsTabTypes.SLACK:
- return
+ return
case ConfigurationsTabTypes.WEBHOOK:
- return
+ return
case ConfigurationsTabTypes.SES:
default:
- return
+ return
}
}
@@ -224,8 +229,6 @@ export const getSMTPDefaultConfiguration = (shouldBeDefault: boolean): SMTPFormT
isLoading: false,
})
-
-
export const renderDefaultTag = (isDefault: boolean) => {
if (isDefault) {
return Default
@@ -353,3 +356,4 @@ export const getValidationFormConfig = (formConfig) => {
)
return { allValid, formValidations }
}
+
diff --git a/src/components/notifications/types.tsx b/src/components/notifications/types.tsx
index 092c76f169..cf35c12a69 100644
--- a/src/components/notifications/types.tsx
+++ b/src/components/notifications/types.tsx
@@ -303,3 +303,22 @@ export interface NotificationTabState {
singleDeletedId: number
disableEdit: boolean
}
+
+export interface BaseConfigurationTableRowType {
+ name: React.ReactNode
+}
+
+export interface SESConfigurationTableRowType extends BaseConfigurationTableRowType {
+ accessKeyId: string
+ email: string
+}
+
+export interface SMTPConfigurationTableRowType extends BaseConfigurationTableRowType {
+ host: string
+ port: string
+ email: string
+}
+
+export interface SlackWebhookConfigurationTableRowType extends BaseConfigurationTableRowType {
+ webhookUrl: string
+}
diff --git a/src/config/constantMessaging.ts b/src/config/constantMessaging.ts
index 7b4fab911f..152c7b03b4 100644
--- a/src/config/constantMessaging.ts
+++ b/src/config/constantMessaging.ts
@@ -67,10 +67,6 @@ export const enum DeleteComponentsName {
LinkedBuildPipeline = 'linked build pipeline',
MaterialView = 'git repository',
Node = 'node',
- SlackConfigurationTab = 'slack',
- SesConfigurationTab = 'ses',
- SMTPConfigurationTab = 'smtp',
- WebhookConfigurationTab = 'webhook',
Preset = 'preset value',
Project = 'project',
Override = 'override',