-
Notifications
You must be signed in to change notification settings - Fork 57
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
[Feature] Data sources associated objects tab #1470
Changes from all commits
53190ae
d4be2da
c1e000d
d0a5282
79a7076
065531f
6684bfe
5004ee8
File filter
Filter by extension
Conversations
Jump to
Diff view
Diff view
There are no files selected for viewing
Original file line number | Diff line number | Diff line change |
---|---|---|
|
@@ -13,6 +13,15 @@ export interface PermissionsConfigurationProps { | |
hasSecurityAccess: boolean; | ||
} | ||
|
||
export interface AssociatedObject { | ||
id: string; | ||
name: string; | ||
database: string; | ||
type: string; | ||
createdByIntegration: string; | ||
accelerations: string; | ||
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. would any of these fields be a smaller type than There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. I think for now they should be all strings. |
||
} | ||
|
||
export type Role = EuiComboBoxOptionOption; | ||
|
||
export type DatasourceType = 'S3GLUE' | 'PROMETHEUS'; |
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,16 @@ | ||
/* | ||
* Copyright OpenSearch Contributors | ||
* SPDX-License-Identifier: Apache-2.0 | ||
*/ | ||
|
||
import { EuiCallOut } from '@elastic/eui'; | ||
import React from 'react'; | ||
|
||
export const AccelerationsRecommendationCallout = () => { | ||
return ( | ||
Check warning on line 10 in public/components/datasources/components/manage/accelerations_recommendation_callout.tsx Codecov / codecov/patchpublic/components/datasources/components/manage/accelerations_recommendation_callout.tsx#L10
|
||
<EuiCallOut | ||
title="Accelerations recommended for tables. Setup acceleration or configure integrations" | ||
iconType="iInCircle" | ||
/> | ||
); | ||
}; |
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,197 @@ | ||
/* | ||
* Copyright OpenSearch Contributors | ||
* SPDX-License-Identifier: Apache-2.0 | ||
*/ | ||
|
||
import React, { useEffect, useState } from 'react'; | ||
import { | ||
EuiInMemoryTable, | ||
EuiLink, | ||
EuiPanel, | ||
EuiFlexGroup, | ||
EuiFlexItem, | ||
EuiText, | ||
EuiHorizontalRule, | ||
EuiButton, | ||
EuiSpacer, | ||
EuiEmptyPrompt, | ||
} from '@elastic/eui'; | ||
import { AssociatedObject } from 'common/types/data_connections'; | ||
import { AccelerationsRecommendationCallout } from './accelerations_recommendation_callout'; | ||
|
||
interface AssociatedObjectsTabProps { | ||
associatedObjects: AssociatedObject[]; | ||
} | ||
|
||
export const AssociatedObjectsTab: React.FC<AssociatedObjectsTabProps> = ({ | ||
associatedObjects, | ||
}) => { | ||
const [lastUpdated, setLastUpdated] = useState(''); | ||
|
||
// TODO: FINISH THE REFRESH LOGIC | ||
const fetchAssociatedObjects = async () => { | ||
// Placeholder for data fetching logic | ||
// After fetching data: | ||
// setAssociatedObjects(fetchedData); | ||
const now = new Date(); | ||
setLastUpdated(now.toUTCString()); // Update last updated time | ||
}; | ||
|
||
useEffect(() => { | ||
fetchAssociatedObjects(); | ||
}, []); | ||
|
||
const AssociatedObjectsHeader = () => { | ||
return ( | ||
<EuiFlexGroup direction="row"> | ||
<EuiFlexItem> | ||
<EuiText size="m"> | ||
<h2 className="panel-title">Associated objects</h2> | ||
Manage objects associated with this data sources. | ||
</EuiText> | ||
</EuiFlexItem> | ||
<EuiFlexItem grow={false}> | ||
<div style={{ textAlign: 'right' }}> | ||
<EuiText color="subdued" style={{ fontSize: 'small' }}> | ||
Last updated at: | ||
</EuiText> | ||
<EuiText color="subdued" style={{ fontSize: 'small' }}> | ||
{lastUpdated} | ||
</EuiText> | ||
</div> | ||
</EuiFlexItem> | ||
<EuiFlexItem grow={false}> | ||
<EuiButton | ||
data-test-subj="freshButton" | ||
iconType="refresh" | ||
onClick={fetchAssociatedObjects} | ||
> | ||
Refresh | ||
</EuiButton> | ||
</EuiFlexItem> | ||
</EuiFlexGroup> | ||
); | ||
}; | ||
|
||
const noDataMessage = ( | ||
<EuiEmptyPrompt | ||
title={<h2>You have no associated objects</h2>} | ||
body={<p>Add or config tables from your data source or use Query Workbench.</p>} | ||
actions={ | ||
<EuiButton | ||
color="primary" | ||
fill | ||
onClick={() => window.open('https://example.com', '_blank')} | ||
iconType="popout" | ||
iconSide="left" | ||
> | ||
Query Workbench | ||
</EuiButton> | ||
} | ||
/> | ||
); | ||
|
||
const columns = [ | ||
{ | ||
field: 'name', | ||
name: 'Name', | ||
sortable: true, | ||
'data-test-subj': 'nameCell', | ||
render: (name: string) => ( | ||
<EuiLink href="https://example.com" target="_blank"> | ||
{name} | ||
</EuiLink> | ||
), | ||
}, | ||
{ | ||
field: 'database', | ||
name: 'Database', | ||
truncateText: true, | ||
render: (database: string) => ( | ||
<EuiLink href="https://example.com" target="_blank"> | ||
{database} | ||
</EuiLink> | ||
), | ||
}, | ||
{ | ||
field: 'type', | ||
name: 'Type', | ||
sortable: true, | ||
}, | ||
{ | ||
field: 'createdByIntegration', | ||
name: 'Created by Integration', | ||
sortable: true, | ||
}, | ||
{ | ||
field: 'accelerations', | ||
name: 'Accelerations', | ||
sortable: true, | ||
}, | ||
{ | ||
name: 'Actions', | ||
actions: [ | ||
{ | ||
name: 'Edit', | ||
description: 'Edit this object', | ||
type: 'icon', | ||
icon: 'discoverApp', | ||
onClick: (item: AssociatedObject) => console.log('Edit', item), | ||
}, | ||
{ | ||
name: 'Delete', | ||
description: 'Delete this object', | ||
type: 'icon', | ||
icon: 'bolt', | ||
onClick: (item: AssociatedObject) => console.log('Delete', item), | ||
}, | ||
], | ||
}, | ||
]; | ||
|
||
const search = { | ||
box: { | ||
incremental: true, | ||
schema: { | ||
fields: { name: { type: 'string' }, database: { type: 'string' } }, | ||
}, | ||
}, | ||
}; | ||
|
||
const pagination = { | ||
initialPageSize: 10, | ||
pageSizeOptions: [10, 25, 50], | ||
}; | ||
|
||
const sorting = { | ||
sort: { | ||
field: 'name', | ||
direction: 'asc', | ||
}, | ||
}; | ||
|
||
return ( | ||
<> | ||
<EuiSpacer /> | ||
<EuiPanel> | ||
<AssociatedObjectsHeader /> | ||
<EuiHorizontalRule /> | ||
<AccelerationsRecommendationCallout /> | ||
<EuiSpacer /> | ||
{associatedObjects.length > 0 ? ( | ||
<EuiInMemoryTable | ||
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. would there be a case that There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. Good point, I think for the memory fitting issue, we may need to do something like virtualization with react-window to limit the size of the list. However, since this this is a skeleton for now, and lets just leave like this. I will test it when we connect the actual data content, so that we can decide which approaches we need for addressing the memory issue. I will not resolve this comment btw until we have a concrete solution on this. |
||
items={associatedObjects} | ||
columns={columns} | ||
search={search} | ||
pagination={pagination} | ||
sorting={sorting} | ||
noItemsMessage={associatedObjects.length === 0 ? noDataMessage : undefined} | ||
/> | ||
) : ( | ||
noDataMessage | ||
)} | ||
</EuiPanel> | ||
<EuiSpacer /> | ||
</> | ||
); | ||
}; |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I don't know if
createdByIntegration
is a field thatAssociatedObject
would contain, I'd expect this to be queried from the integrations that store all the contained object information. Do you see us modifying Integrations to add fields like this to arbitrary objects? If so, it might be worth adding this requirement in #1442There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Transferring some of the discussion over here: for now, since we should able to have this field with the source of integration, lets have this field for now for this skeleton PR. We can sync up on this again when we actually do the connection of actual data content.