Skip to content

Commit a0d4f45

Browse files
authored
Merge pull request #2799 from devtron-labs/feat/chart-group-card
feat: chart group card
2 parents 526be24 + 611d6c2 commit a0d4f45

19 files changed

+398
-356
lines changed

.eslintignore

Lines changed: 0 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -152,17 +152,12 @@ src/components/charts/discoverChartDetail/About.tsx
152152
src/components/charts/discoverChartDetail/ChartDeploymentList.tsx
153153
src/components/charts/discoverChartDetail/DiscoverChartDetails.tsx
154154
src/components/charts/list/ChartGroup.tsx
155-
src/components/charts/list/ChartListPopUp.tsx
156155
src/components/charts/list/ChartListPopUpRow.tsx
157-
src/components/charts/list/Deployed.tsx
158156
src/components/charts/list/DeployedChartFilters.tsx
159157
src/components/charts/list/DiscoverCharts.tsx
160158
src/components/charts/modal/ChartGroupBasicDeploy.tsx
161159
src/components/charts/modal/CreateChartGroup.tsx
162160
src/components/charts/useChartGroup.ts
163-
src/components/charts/util/ChartGroupCard.tsx
164-
src/components/charts/util/ChartSelect.tsx
165-
src/components/charts/util/ChartValueSelect.tsx
166161
src/components/checkList/AllChartsCheck.tsx
167162
src/components/checkList/AllCheckModal.tsx
168163
src/components/checkList/AppCheckList.tsx

package.json

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -4,7 +4,7 @@
44
"private": true,
55
"homepage": "/dashboard",
66
"dependencies": {
7-
"@devtron-labs/devtron-fe-common-lib": "1.17.0-pre-5",
7+
"@devtron-labs/devtron-fe-common-lib": "1.17.0-pre-6",
88
"@esbuild-plugins/node-globals-polyfill": "0.2.3",
99
"@rjsf/core": "^5.13.3",
1010
"@rjsf/utils": "^5.13.3",

src/components/charts/ChartCard.tsx

Lines changed: 24 additions & 52 deletions
Original file line numberDiff line numberDiff line change
@@ -21,18 +21,17 @@ import {
2121
ComponentSizeType,
2222
handleAnalyticsEvent,
2323
Icon,
24-
ImageWithFallback,
2524
noop,
2625
stopPropagation,
2726
useMainContext,
2827
} from '@devtron-labs/devtron-fe-common-lib'
2928

3029
import { InteractiveCellText } from '@Components/common/helpers/InteractiveCellText/InteractiveCellText'
3130

32-
import { ReactComponent as Helm } from '../../assets/icons/ic-default-chart.svg'
3331
import { SERVER_MODE } from '../../config'
32+
import ChartIcon from './ChartIcon'
3433
import { ChartSelectProps } from './charts.types'
35-
import { renderDeprecatedWarning } from './charts.util'
34+
import { getDescriptionTruncate, renderDeprecatedWarning } from './charts.util'
3635

3736
const ChartCard = ({
3837
chart,
@@ -88,53 +87,6 @@ const ChartCard = ({
8887
ariaLabel="Remove chart from selection"
8988
/>
9089
)
91-
const chartIconClass = 'dc__chart-grid-item__icon chart-icon-dim br-4 dc__no-shrink'
92-
93-
const renderIcon = () => (
94-
<div className="icon-wrapper">
95-
<ImageWithFallback
96-
imageProps={{
97-
height: 32,
98-
width: 32,
99-
src: chart.icon,
100-
alt: 'chart',
101-
className: chartIconClass,
102-
}}
103-
fallbackImage={<Helm className={chartIconClass} />}
104-
/>
105-
</div>
106-
)
107-
108-
const getDescriptionTruncate = () => {
109-
if (isListView) {
110-
return 'dc__truncate--clamp-4'
111-
}
112-
113-
if (chart.deprecated) return 'dc__truncate'
114-
return 'dc__truncate--clamp-2'
115-
}
116-
117-
const renderCardInfo = () => (
118-
<div className="flexbox-col flex-grow-1 dc__gap-8">
119-
<div className="flexbox-col dc__gap-2">
120-
<div className="flex left">
121-
<InteractiveCellText
122-
text={chart.name}
123-
rootClassName="fw-6 chart-grid-item__title cn-9"
124-
fontSize={14}
125-
/>
126-
<div className="chart-name__arrow dc__no-shrink flex">
127-
<Icon name="ic-caret-down-small" color="B500" rotateBy={270} />
128-
</div>
129-
</div>
130-
{chart.deprecated && renderDeprecatedWarning()}
131-
</div>
132-
133-
<span className={`fw-4 fs-13 lh-1-5 ${getDescriptionTruncate()}`}>
134-
{chart.description || 'No description'}
135-
</span>
136-
</div>
137-
)
13890

13991
const renderFooter = () => (
14092
<div className="flex left dc__content-space dc__border-top-n1 px-20 py-16 dc__gap-6">
@@ -163,7 +115,7 @@ const ChartCard = ({
163115
<div
164116
className={`${isListView ? 'dc__grid chart-list-item dc__gap-16' : 'flexbox-col h-166 dc__gap-12'} px-20 pt-20 pb-16`}
165117
>
166-
{renderIcon()}
118+
<ChartIcon icon={chart.icon} />
167119
{serverMode === SERVER_MODE.FULL && addChart && subtractChart && (
168120
<div
169121
className={`devtron-stepper ${selectedCount > 0 ? 'dc__grid devtron-stepper-grid dc__border br-6 fw-6 cursor bg__primary' : ''}`}
@@ -179,7 +131,27 @@ const ChartCard = ({
179131
{renderAddIcon()}
180132
</div>
181133
)}
182-
{renderCardInfo()}
134+
<div className="flexbox-col flex-grow-1 dc__gap-8">
135+
<div className="flexbox-col dc__gap-2">
136+
<div className="flex left">
137+
<InteractiveCellText
138+
text={chart.name}
139+
rootClassName="fw-6 chart-grid-item__title cn-9"
140+
fontSize={14}
141+
/>
142+
<div className="chart-name__arrow dc__no-shrink flex">
143+
<Icon name="ic-caret-down-small" color="B500" rotateBy={270} />
144+
</div>
145+
</div>
146+
{chart.deprecated && renderDeprecatedWarning()}
147+
</div>
148+
149+
<span
150+
className={`fw-4 fs-13 lh-1-5 ${getDescriptionTruncate({ isListView, isDeprecated: chart.deprecated })}`}
151+
>
152+
{chart.description || 'No description'}
153+
</span>
154+
</div>
183155
</div>
184156
{renderFooter()}
185157
</div>
Lines changed: 95 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,95 @@
1+
/*
2+
* Copyright (c) 2024. Devtron Inc.
3+
*
4+
* Licensed under the Apache License, Version 2.0 (the "License");
5+
* you may not use this file except in compliance with the License.
6+
* You may obtain a copy of the License at
7+
*
8+
* http://www.apache.org/licenses/LICENSE-2.0
9+
*
10+
* Unless required by applicable law or agreed to in writing, software
11+
* distributed under the License is distributed on an "AS IS" BASIS,
12+
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13+
* See the License for the specific language governing permissions and
14+
* limitations under the License.
15+
*/
16+
17+
import { Link } from 'react-router-dom'
18+
19+
import { getAlphabetIcon, handleAnalyticsEvent, Icon } from '@devtron-labs/devtron-fe-common-lib'
20+
21+
import { InteractiveCellText } from '@Components/common/helpers/InteractiveCellText/InteractiveCellText'
22+
23+
import ChartIcon from './ChartIcon'
24+
import { getChartGroupURL } from './charts.helper'
25+
import { ChartGroupCardProps } from './charts.types'
26+
import { getChartGroupSubgroup, getDescriptionTruncate } from './charts.util'
27+
import { CHART_CARD_MAX_LENGTH } from './constants'
28+
29+
export const ChartGroupCard = ({ chartGroup }: ChartGroupCardProps) => {
30+
const chartGroupEntries = getChartGroupSubgroup(chartGroup.chartGroupEntries)
31+
32+
const GROUP_EDIT_LINK = getChartGroupURL(chartGroup.id)
33+
34+
const handleClick = () => {
35+
handleAnalyticsEvent({ category: 'Chart Store', action: 'CS_CHART_GROUP_CARD_CLICKED' })
36+
}
37+
38+
return (
39+
<Link
40+
key={chartGroup.id}
41+
className="chart-grid-item dc__visible-hover dc__visible-hover--parent bg__primary border__secondary-translucent cursor dc__position-rel br-8 "
42+
to={GROUP_EDIT_LINK}
43+
onClick={handleClick}
44+
>
45+
<div className="flexbox-col h-166 dc__gap-12 px-20 pt-20 pb-16">
46+
<div className="flexbox">
47+
{chartGroupEntries?.length ? (
48+
<>
49+
{chartGroupEntries.map((chart) => (
50+
<ChartIcon icon={chart.chartMetaData.icon} key={chart.id} isChartGroupCard />
51+
))}
52+
{chartGroup.chartGroupEntries.length > CHART_CARD_MAX_LENGTH && (
53+
<div className="flex chart-group-card__icon-wrapper border__secondary-translucent bg__secondary br-8 p-8 h-50 fs-16 lh-1-5 cn-8 icon-dim-50">
54+
+{chartGroup.chartGroupEntries.length - CHART_CARD_MAX_LENGTH}
55+
</div>
56+
)}
57+
</>
58+
) : (
59+
<div className="dc__border-dashed bg__secondary br-8 p-8 dc__w-fit-content h-50">
60+
<Icon name="ic-folder-color" size={32} color={null} />
61+
</div>
62+
)}
63+
</div>
64+
<div className="flexbox-col flex-grow-1 dc__gap-8">
65+
<div className="flexbox-col dc__gap-2">
66+
<div className="flex left">
67+
<InteractiveCellText
68+
text={chartGroup.name}
69+
rootClassName="fw-6 chart-grid-item__title cn-9"
70+
fontSize={14}
71+
/>
72+
<div className="chart-name__arrow dc__no-shrink flex">
73+
<Icon name="ic-caret-down-small" color="B500" rotateBy={270} />
74+
</div>
75+
</div>
76+
</div>
77+
78+
<span className={`fw-4 fs-13 lh-1-5 ${getDescriptionTruncate({})}`}>
79+
{chartGroup.description || 'No description'}
80+
</span>
81+
</div>
82+
</div>
83+
84+
<div className="flex left dc__content-space dc__border-top-n1 px-20 py-16 dc__gap-6">
85+
<div className="flex">
86+
{getAlphabetIcon(chartGroup.createdBy)}
87+
<InteractiveCellText text={chartGroup.createdBy} rootClassName="cn-7 lh-1-5" fontSize={12} />
88+
</div>
89+
<span className="lh-20 dc__truncate m-0 dc__align-item-left cn-7 lh-1-5 dc__mxw-120 fs-12">
90+
{chartGroup.chartGroupEntries?.length || 0} charts
91+
</span>
92+
</div>
93+
</Link>
94+
)
95+
}

src/components/charts/ChartHeaderFilters.tsx

Lines changed: 2 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -19,7 +19,7 @@ import { useRouteMatch, useHistory, useLocation } from 'react-router-dom'
1919
import { ReactComponent as Grid } from '../../assets/icons/ic-grid-view.svg'
2020
import { ReactComponent as List } from '../../assets/icons/ic-list-view.svg'
2121
import { QueryParams } from './constants'
22-
import { Accordian } from '../common/Accordian/Accordian'
22+
import { ChartSourceAccordion } from './ChartSourceAccordion'
2323
import { URLS } from '../../config'
2424
import { CHART_KEYS } from './constants'
2525
import { ChartHeaderFilterProps } from './charts.types'
@@ -256,12 +256,11 @@ const ChartHeaderFilter = ({
256256
/>
257257
)}
258258
<hr className="mt-8 mb-8" />
259-
<Accordian
259+
<ChartSourceAccordion
260260
header="CHART SOURCE"
261261
options={chartRepoList}
262262
value={selectedChartRepo}
263263
onChange={handleSelection}
264-
onClickViewChartButton={handleViewAllCharts}
265264
dataTestId="chart-store-repository"
266265
/>
267266
</div>

src/components/charts/ChartIcon.tsx

Lines changed: 28 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,28 @@
1+
import { Icon, ImageWithFallback } from '@devtron-labs/devtron-fe-common-lib'
2+
3+
const ChartIcon = ({ icon, isChartGroupCard }: { icon: string; isChartGroupCard?: boolean }) => {
4+
const chartIconClass = `dc__chart-grid-item__icon icon-dim-32 ${isChartGroupCard ? 'chart-group-card__icon' : 'chart-icon-dim'} br-4 dc__no-shrink`
5+
6+
return (
7+
<div
8+
className={`${isChartGroupCard ? 'chart-group-card__icon-wrapper' : 'chart-card__icon-wrapper'} border__secondary-translucent bg__secondary br-8 p-8 dc__w-fit-content h-50`}
9+
>
10+
<ImageWithFallback
11+
imageProps={{
12+
height: 32,
13+
width: 32,
14+
src: icon,
15+
alt: 'chart',
16+
className: chartIconClass,
17+
}}
18+
fallbackImage={
19+
<div className={chartIconClass}>
20+
<Icon name="ic-helm-app" size={32} color={null} />
21+
</div>
22+
}
23+
/>
24+
</div>
25+
)
26+
}
27+
28+
export default ChartIcon

src/components/common/Accordian/Accordian.tsx renamed to src/components/charts/ChartSourceAccordion.tsx

Lines changed: 14 additions & 25 deletions
Original file line numberDiff line numberDiff line change
@@ -14,21 +14,23 @@
1414
* limitations under the License.
1515
*/
1616

17-
import React, { useState } from 'react'
18-
import { CHECKBOX_VALUE, Checkbox } from '@devtron-labs/devtron-fe-common-lib'
19-
import { ReactComponent as Dropdown } from '../../../assets/icons/ic-chevron-down.svg'
20-
import { ReactComponent as AddIcon } from '../../../assets/icons/ic-add.svg'
21-
import AddChartSource from '../../charts/list/AddChartSource'
17+
import { useState } from 'react'
2218

23-
export const Accordian = ({ header, options, value, onChange, onClickViewChartButton, dataTestId }) => {
19+
import { Checkbox, CHECKBOX_VALUE } from '@devtron-labs/devtron-fe-common-lib'
20+
21+
import { ReactComponent as Dropdown } from '@Icons/ic-chevron-down.svg'
22+
import AddChartSource from '@Components/charts/list/AddChartSource'
23+
24+
import { ChartSourceAccordionProps, SelectedChartRepositoryType } from './charts.types'
25+
26+
export const ChartSourceAccordion = ({ header, options, value, onChange, dataTestId }: ChartSourceAccordionProps) => {
2427
const [collapsed, setCollapse] = useState<boolean>(true)
25-
const [showAddSource, toggleAddSource] = useState<boolean>(false)
2628
const toggleDropdown = (): void => {
2729
setCollapse(!collapsed)
2830
}
2931

30-
const handleTogleAddSource = () => {
31-
toggleAddSource(!showAddSource)
32+
const onChangeToggleSource = (option: SelectedChartRepositoryType) => () => {
33+
onChange(option)
3234
}
3335

3436
return (
@@ -47,30 +49,17 @@ export const Accordian = ({ header, options, value, onChange, onClickViewChartBu
4749

4850
{collapsed && (
4951
<div>
50-
<button
51-
type="button"
52-
className="dc__position-rel dc__transparent dc__hover-n50 cursor flex left cb-5 fs-13 fw-6 lh-20 h-32 pl-10 w-100"
53-
onClick={handleTogleAddSource}
54-
>
55-
<AddIcon className="icon-dim-16 fcb-5 mr-8" />
56-
Add chart source
57-
</button>
58-
59-
{showAddSource && (
60-
<div className="dc__transparent-div" onClick={handleTogleAddSource}>
61-
<AddChartSource baseClass="accordian-add-position" />
62-
</div>
63-
)}
52+
<AddChartSource text="Add chart source" />
6453
{options.map((option) => (
6554
<div
6655
className="dc__position-rel flex left cursor dc__hover-n50"
6756
data-testid={`${option.label}-chart-repo`}
6857
>
6958
<Checkbox
7059
rootClassName="ml-7 h-32 fs-13 mb-0 mr-10 w-100"
71-
isChecked={value?.filter((selectedVal) => selectedVal.value === option.value).length}
60+
isChecked={!!value?.filter((selectedVal) => selectedVal.value === option.value).length}
7261
value={CHECKBOX_VALUE.CHECKED}
73-
onChange={() => onChange(option)}
62+
onChange={onChangeToggleSource(option)}
7463
>
7564
<div className="dc__ellipsis-right ml-5 dc__mxw-180">{option.label}</div>
7665
</Checkbox>

0 commit comments

Comments
 (0)