mirror of
https://github.com/open-metadata/OpenMetadata.git
synced 2025-08-25 17:37:57 +00:00
revamp table constraint modal design (#18455)
This commit is contained in:
parent
aea12fe4d5
commit
843f8439ce
@ -10,6 +10,16 @@
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*/
|
||||
|
||||
import { EntityTabs } from '../../../enums/entity.enum';
|
||||
|
||||
export interface TabProps {
|
||||
label: JSX.Element;
|
||||
key: EntityTabs;
|
||||
children?: JSX.Element;
|
||||
isHidden?: boolean;
|
||||
}
|
||||
|
||||
export interface TabsLabelProps {
|
||||
name: string;
|
||||
id: string;
|
||||
|
@ -84,7 +84,7 @@ const TableConstraints: FC<TableConstraintsProps> = ({
|
||||
})}>
|
||||
<Button
|
||||
className="cursor-pointer hover-cell-icon w-fit-content"
|
||||
data-testid="edit-displayName-button"
|
||||
data-testid="edit-table-constraint-button"
|
||||
style={{
|
||||
color: DE_ACTIVE_COLOR,
|
||||
padding: 0,
|
||||
@ -103,7 +103,7 @@ const TableConstraints: FC<TableConstraintsProps> = ({
|
||||
{hasPermission && supportedConstraints.length === 0 && (
|
||||
<TagButton
|
||||
className="text-primary cursor-pointer"
|
||||
dataTestId="synonym-add-button"
|
||||
dataTestId="table-constraints-add-button"
|
||||
icon={<PlusIcon height={16} name="plus" width={16} />}
|
||||
label={t('label.add')}
|
||||
tooltip=""
|
||||
|
@ -10,13 +10,12 @@
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*/
|
||||
import Icon from '@ant-design/icons/lib/components/Icon';
|
||||
import { Button, Col, Form, Modal, Row, Select } from 'antd';
|
||||
import { CloseOutlined } from '@ant-design/icons';
|
||||
import { Button, Form, Modal, Select } from 'antd';
|
||||
import { AxiosError } from 'axios';
|
||||
import { debounce, isEmpty } from 'lodash';
|
||||
import React, { useCallback, useEffect, useMemo, useState } from 'react';
|
||||
import { useTranslation } from 'react-i18next';
|
||||
import { ReactComponent as IconDelete } from '../../../../assets/svg/ic-delete.svg';
|
||||
import { ReactComponent as PlusIcon } from '../../../../assets/svg/plus-primary.svg';
|
||||
import { PAGE_SIZE } from '../../../../constants/constants';
|
||||
import { RELATIONSHIP_TYPE_OPTION } from '../../../../constants/Table.constants';
|
||||
@ -25,6 +24,7 @@ import { ConstraintType, Table } from '../../../../generated/entity/data/table';
|
||||
import { searchQuery } from '../../../../rest/searchAPI';
|
||||
import { getServiceNameQueryFilter } from '../../../../utils/ServiceUtils';
|
||||
import { showErrorToast } from '../../../../utils/ToastUtils';
|
||||
import './table-constraint.style.less';
|
||||
import {
|
||||
SelectOptions,
|
||||
TableConstraintForm,
|
||||
@ -171,7 +171,6 @@ const TableConstraintsModal = ({
|
||||
title={t(`label.${isEmpty(constraint) ? 'add' : 'update'}-entity`, {
|
||||
entity: t('label.table-constraint-plural'),
|
||||
})}
|
||||
width={600}
|
||||
onCancel={onClose}>
|
||||
<Form
|
||||
className="table-constraint-form"
|
||||
@ -182,106 +181,91 @@ const TableConstraintsModal = ({
|
||||
{(fields, { add, remove }) => (
|
||||
<>
|
||||
{fields.map(({ key, name, ...restField }) => (
|
||||
<Row gutter={8} key={key}>
|
||||
<Col span={12}>
|
||||
<Form.Item
|
||||
className="w-full"
|
||||
{...restField}
|
||||
label={t('label.entity-name', {
|
||||
entity: t('label.column'),
|
||||
})}
|
||||
name={[name, 'columns']}
|
||||
rules={[
|
||||
{
|
||||
required: true,
|
||||
message: t('label.field-required', {
|
||||
field: t('label.entity-name', {
|
||||
entity: t('label.column'),
|
||||
}),
|
||||
<div className="table-constraint-form-container" key={key}>
|
||||
<Form.Item
|
||||
className="w-full"
|
||||
{...restField}
|
||||
label={t('label.entity-name', {
|
||||
entity: t('label.column'),
|
||||
})}
|
||||
name={[name, 'columns']}
|
||||
rules={[
|
||||
{
|
||||
required: true,
|
||||
message: t('label.field-required', {
|
||||
field: t('label.entity-name', {
|
||||
entity: t('label.column'),
|
||||
}),
|
||||
},
|
||||
]}>
|
||||
<Select
|
||||
data-testid={`${key}-column-type-select`}
|
||||
options={tableColumnNameOptions}
|
||||
/>
|
||||
</Form.Item>
|
||||
</Col>
|
||||
<Col span={12}>
|
||||
<Form.Item
|
||||
{...restField}
|
||||
label={t('label.entity-type-plural', {
|
||||
entity: t('label.relationship'),
|
||||
})}
|
||||
name={[name, 'relationshipType']}
|
||||
rules={[
|
||||
{
|
||||
required: true,
|
||||
message: t('label.field-required', {
|
||||
field: t('label.entity-type-plural', {
|
||||
entity: t('label.relationship'),
|
||||
}),
|
||||
}),
|
||||
},
|
||||
]}>
|
||||
<Select
|
||||
data-testid={`${key}-relationship-type-select`}
|
||||
options={RELATIONSHIP_TYPE_OPTION}
|
||||
/>
|
||||
</Form.Item>
|
||||
</Col>
|
||||
|
||||
<Col span={23}>
|
||||
<Form.Item
|
||||
{...restField}
|
||||
label={t('label.related-column')}
|
||||
name={[name, 'referredColumns']}
|
||||
rules={[
|
||||
{
|
||||
required: true,
|
||||
message: t('label.field-required', {
|
||||
field: t('label.related-column'),
|
||||
}),
|
||||
},
|
||||
]}>
|
||||
<Select
|
||||
showSearch
|
||||
data-testid={`${key}-related-column-select`}
|
||||
loading={isRelatedColumnLoading}
|
||||
options={relatedColumns}
|
||||
onClick={(e) => e.stopPropagation()}
|
||||
onSearch={handleSearch}
|
||||
/>
|
||||
</Form.Item>
|
||||
</Col>
|
||||
|
||||
<Col span={1}>
|
||||
<Button
|
||||
data-testid={`${key}-delete-constraint-button`}
|
||||
icon={
|
||||
<Icon
|
||||
className="align-middle"
|
||||
component={IconDelete}
|
||||
style={{ fontSize: '16px' }}
|
||||
/>
|
||||
}
|
||||
size="small"
|
||||
type="text"
|
||||
onClick={() => remove(name)}
|
||||
}),
|
||||
},
|
||||
]}>
|
||||
<Select
|
||||
data-testid={`${key}-column-type-select`}
|
||||
options={tableColumnNameOptions}
|
||||
/>
|
||||
</Col>
|
||||
</Row>
|
||||
</Form.Item>
|
||||
<Form.Item
|
||||
{...restField}
|
||||
className="w-full"
|
||||
label={t('label.entity-type-plural', {
|
||||
entity: t('label.relationship'),
|
||||
})}
|
||||
name={[name, 'relationshipType']}
|
||||
rules={[
|
||||
{
|
||||
required: true,
|
||||
message: t('label.field-required', {
|
||||
field: t('label.entity-type-plural', {
|
||||
entity: t('label.relationship'),
|
||||
}),
|
||||
}),
|
||||
},
|
||||
]}>
|
||||
<Select
|
||||
data-testid={`${key}-relationship-type-select`}
|
||||
options={RELATIONSHIP_TYPE_OPTION}
|
||||
/>
|
||||
</Form.Item>
|
||||
<Form.Item
|
||||
{...restField}
|
||||
className="w-full"
|
||||
label={t('label.related-column')}
|
||||
name={[name, 'referredColumns']}
|
||||
rules={[
|
||||
{
|
||||
required: true,
|
||||
message: t('label.field-required', {
|
||||
field: t('label.related-column'),
|
||||
}),
|
||||
},
|
||||
]}>
|
||||
<Select
|
||||
showSearch
|
||||
data-testid={`${key}-related-column-select`}
|
||||
loading={isRelatedColumnLoading}
|
||||
options={relatedColumns}
|
||||
onClick={(e) => e.stopPropagation()}
|
||||
onSearch={handleSearch}
|
||||
/>
|
||||
</Form.Item>
|
||||
<Button
|
||||
className="delete-constraint-button"
|
||||
data-testid={`${key}-delete-constraint-button`}
|
||||
icon={<CloseOutlined className="text-grey-muted" />}
|
||||
size="small"
|
||||
type="text"
|
||||
onClick={() => remove(name)}
|
||||
/>
|
||||
</div>
|
||||
))}
|
||||
<Form.Item>
|
||||
<Button
|
||||
className="text-primary d-flex items-center"
|
||||
data-testid="add-constraint-button"
|
||||
icon={<PlusIcon className="anticon" />}
|
||||
size="small"
|
||||
onClick={() => add()}>
|
||||
{t('label.add')}
|
||||
</Button>
|
||||
</Form.Item>
|
||||
<Button
|
||||
className="text-primary d-flex items-center m-t-md"
|
||||
data-testid="add-constraint-button"
|
||||
icon={<PlusIcon className="anticon" />}
|
||||
size="small"
|
||||
onClick={() => add()}>
|
||||
{t('label.add')}
|
||||
</Button>
|
||||
</>
|
||||
)}
|
||||
</Form.List>
|
||||
|
@ -0,0 +1,39 @@
|
||||
/*
|
||||
* Copyright 2024 Collate.
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*/
|
||||
|
||||
@import url('../../../../styles/variables.less');
|
||||
|
||||
.table-constraint-form-container {
|
||||
margin-bottom: 20px;
|
||||
position: relative;
|
||||
background: @grey-6;
|
||||
padding: 20px;
|
||||
border-radius: 10px;
|
||||
border: @global-border;
|
||||
|
||||
.ant-form-item {
|
||||
&:last-child {
|
||||
margin-bottom: 0;
|
||||
}
|
||||
}
|
||||
|
||||
.delete-constraint-button {
|
||||
position: absolute;
|
||||
top: 10px;
|
||||
right: 12px;
|
||||
}
|
||||
|
||||
&:last-child {
|
||||
margin-bottom: 0;
|
||||
}
|
||||
}
|
@ -10,9 +10,9 @@
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*/
|
||||
import { TabsProps } from 'antd';
|
||||
import { EntityTags, PagingResponse } from 'Models';
|
||||
import { PagingHandlerParams } from '../components/common/NextPrevious/NextPrevious.interface';
|
||||
import { TabProps } from '../components/common/TabsLabel/TabsLabel.interface';
|
||||
import { EntityTabs } from '../enums/entity.enum';
|
||||
import { DatabaseSchema } from '../generated/entity/data/databaseSchema';
|
||||
import { Table } from '../generated/entity/data/table';
|
||||
@ -56,7 +56,7 @@ export interface DatabaseSchemaPageTabProps {
|
||||
class DatabaseSchemaClassBase {
|
||||
public getDatabaseSchemaPageTabs(
|
||||
databaseSchemaTabData: DatabaseSchemaPageTabProps
|
||||
): TabsProps['items'] {
|
||||
): TabProps[] {
|
||||
return getDataBaseSchemaPageBaseTabs(databaseSchemaTabData);
|
||||
}
|
||||
}
|
||||
|
@ -19,6 +19,7 @@ import { ActivityFeedTab } from '../components/ActivityFeed/ActivityFeedTab/Acti
|
||||
import { CustomPropertyTable } from '../components/common/CustomPropertyTable/CustomPropertyTable';
|
||||
import ResizablePanels from '../components/common/ResizablePanels/ResizablePanels';
|
||||
import TabsLabel from '../components/common/TabsLabel/TabsLabel.component';
|
||||
import { TabProps } from '../components/common/TabsLabel/TabsLabel.interface';
|
||||
import EntityRightPanel from '../components/Entity/EntityRightPanel/EntityRightPanel';
|
||||
import { COMMON_RESIZABLE_PANEL_CONFIG } from '../constants/ResizablePanel.constants';
|
||||
import { EntityTabs, EntityType, TabSpecificField } from '../enums/entity.enum';
|
||||
@ -57,7 +58,7 @@ export const getDataBaseSchemaPageBaseTabs = ({
|
||||
getEntityFeedCount,
|
||||
fetchDatabaseSchemaDetails,
|
||||
handleFeedCount,
|
||||
}: DatabaseSchemaPageTabProps) => {
|
||||
}: DatabaseSchemaPageTabProps): TabProps[] => {
|
||||
return [
|
||||
{
|
||||
label: (
|
||||
|
@ -10,6 +10,7 @@
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*/
|
||||
import { TabProps } from '../components/common/TabsLabel/TabsLabel.interface';
|
||||
import { OperationPermission } from '../context/PermissionProvider/PermissionProvider.interface';
|
||||
import { EntityTabs } from '../enums/entity.enum';
|
||||
import { Table } from '../generated/entity/data/table';
|
||||
@ -43,7 +44,7 @@ export interface TableDetailPageTabProps {
|
||||
class TableClassBase {
|
||||
public getTableDetailPageTabs(
|
||||
tableDetailsPageProps: TableDetailPageTabProps
|
||||
) {
|
||||
): TabProps[] {
|
||||
return getTableDetailPageBaseTabs(tableDetailsPageProps);
|
||||
}
|
||||
}
|
||||
|
@ -85,6 +85,7 @@ import { CustomPropertyTable } from '../components/common/CustomPropertyTable/Cu
|
||||
import ErrorPlaceHolder from '../components/common/ErrorWithPlaceholder/ErrorPlaceHolder';
|
||||
import QueryViewer from '../components/common/QueryViewer/QueryViewer.component';
|
||||
import TabsLabel from '../components/common/TabsLabel/TabsLabel.component';
|
||||
import { TabProps } from '../components/common/TabsLabel/TabsLabel.interface';
|
||||
import TableProfiler from '../components/Database/Profiler/TableProfiler/TableProfiler';
|
||||
import SampleDataTableComponent from '../components/Database/SampleDataTable/SampleDataTable.component';
|
||||
import TableQueries from '../components/Database/TableQueries/TableQueries';
|
||||
@ -643,7 +644,7 @@ export const getTableDetailPageBaseTabs = ({
|
||||
fetchTableDetails,
|
||||
testCaseSummary,
|
||||
isViewTableType,
|
||||
}: TableDetailPageTabProps) => {
|
||||
}: TableDetailPageTabProps): TabProps[] => {
|
||||
return [
|
||||
{
|
||||
label: <TabsLabel id={EntityTabs.SCHEMA} name={t('label.schema')} />,
|
||||
|
Loading…
x
Reference in New Issue
Block a user