Skip to content

Commit 9b9531a

Browse files
committed
chore: refactor Alert-related components
Chiseling at #31590 that has gotten big / unruly, in this PR is a refactor of Alert-related components, going vanilla AntD. Also. Deprecating colors.alerts since it's ambiguous/redundant with warning/error and does not exist in antd-v5
1 parent 840773e commit 9b9531a

File tree

28 files changed

+481
-646
lines changed

28 files changed

+481
-646
lines changed

superset-frontend/packages/superset-ui-core/src/style/index.tsx

-7
Original file line numberDiff line numberDiff line change
@@ -98,13 +98,6 @@ const defaultTheme = {
9898
light2: '#FAEDEE',
9999
},
100100
warning: {
101-
base: '#FF7F44',
102-
dark1: '#BF5E33',
103-
dark2: '#7F3F21',
104-
light1: '#FEC0A1',
105-
light2: '#FFF2EC',
106-
},
107-
alert: {
108101
base: '#FCC700',
109102
dark1: '#BC9501',
110103
dark2: '#7D6300',

superset-frontend/plugins/legacy-plugin-chart-calendar/src/ReactCalendar.jsx

+4-4
Original file line numberDiff line numberDiff line change
@@ -157,13 +157,13 @@ export default styled(Calendar)`
157157
}
158158
159159
.cal-heatmap-container .q1 {
160-
background-color: ${theme.colors.alert.light2};
161-
fill: ${theme.colors.alert.light2};
160+
background-color: ${theme.colors.warning.light2};
161+
fill: ${theme.colors.warning.light2};
162162
}
163163
164164
.cal-heatmap-container .q2 {
165-
background-color: ${theme.colors.alert.light1};
166-
fill: ${theme.colors.alert.light1};
165+
background-color: ${theme.colors.warning.light1};
166+
fill: ${theme.colors.warning.light1};
167167
}
168168
169169
.cal-heatmap-container .q3 {

superset-frontend/spec/helpers/theming.ts renamed to superset-frontend/spec/helpers/theming.tsx

+6-1
Original file line numberDiff line numberDiff line change
@@ -18,9 +18,11 @@
1818
*/
1919
import { shallow as enzymeShallow, mount as enzymeMount } from 'enzyme';
2020
// eslint-disable-next-line no-restricted-imports
21-
import { supersetTheme } from '@superset-ui/core';
2221
import { ReactElement } from 'react';
22+
import { render } from '@testing-library/react';
23+
import { ThemeProvider, supersetTheme } from '@superset-ui/core';
2324
import { ProviderWrapper } from './ProviderWrapper';
25+
import '@testing-library/jest-dom';
2426

2527
type optionsType = {
2628
wrappingComponentProps?: any;
@@ -55,3 +57,6 @@ export function styledShallow(
5557
},
5658
});
5759
}
60+
61+
export const renderWithTheme = (component: JSX.Element) =>
62+
render(<ThemeProvider theme={supersetTheme}>{component}</ThemeProvider>);

superset-frontend/src/components/Alert/index.tsx

+1-45
Original file line numberDiff line numberDiff line change
@@ -19,8 +19,6 @@
1919
import { PropsWithChildren } from 'react';
2020
import { Alert as AntdAlert } from 'antd-v5';
2121
import { AlertProps as AntdAlertProps } from 'antd-v5/lib/alert';
22-
import { css, useTheme } from '@superset-ui/core';
23-
import Icons from 'src/components/Icons';
2422

2523
export type AlertProps = PropsWithChildren<
2624
Omit<AntdAlertProps, 'children'> & { roomBelow?: boolean }
@@ -32,59 +30,17 @@ export default function Alert(props: AlertProps) {
3230
description,
3331
showIcon = true,
3432
closable = true,
35-
roomBelow = false,
3633
children,
3734
} = props;
3835

39-
const theme = useTheme();
40-
const { colors } = theme;
41-
const { alert: alertColor, error, info, success } = colors;
42-
43-
let baseColor = info;
44-
let AlertIcon = Icons.InfoSolid;
45-
if (type === 'error') {
46-
baseColor = error;
47-
AlertIcon = Icons.ErrorSolid;
48-
} else if (type === 'warning') {
49-
baseColor = alertColor;
50-
AlertIcon = Icons.AlertSolid;
51-
} else if (type === 'success') {
52-
baseColor = success;
53-
AlertIcon = Icons.CircleCheckSolid;
54-
}
55-
5636
return (
5737
<AntdAlert
5838
role="alert"
5939
aria-live={type === 'error' ? 'assertive' : 'polite'}
6040
showIcon={showIcon}
61-
icon={
62-
showIcon && (
63-
<span
64-
role="img"
65-
aria-label={`${type} icon`}
66-
style={{
67-
color: baseColor.base,
68-
}}
69-
>
70-
<AlertIcon />
71-
</span>
72-
)
73-
}
74-
closeIcon={closable && <Icons.XSmall aria-label="close icon" />}
41+
closeIcon={closable}
7542
message={children || 'Default message'}
7643
description={description}
77-
css={css`
78-
margin-bottom: ${roomBelow ? theme.gridUnit * 4 : 0}px;
79-
a {
80-
text-decoration: underline;
81-
}
82-
.antd5-alert-message {
83-
font-weight: ${description
84-
? theme.typography.weights.bold
85-
: 'inherit'};
86-
}
87-
`}
8844
{...props}
8945
/>
9046
);

superset-frontend/src/components/AlteredSliceTag/index.tsx

+1-1
Original file line numberDiff line numberDiff line change
@@ -221,7 +221,7 @@ const AlteredSliceTag: FC<AlteredSliceTagProps> = props => {
221221
<Label
222222
icon={<Icons.Warning iconSize="m" />}
223223
className="label"
224-
type="alert"
224+
type="warning"
225225
onClick={() => {}}
226226
>
227227
{t('Altered')}

superset-frontend/src/components/ErrorMessage/DatabaseErrorMessage.tsx

+11-17
Original file line numberDiff line numberDiff line change
@@ -34,12 +34,16 @@ interface DatabaseErrorExtra {
3434

3535
function DatabaseErrorMessage({
3636
error,
37-
source = 'dashboard',
37+
source,
3838
subtitle,
3939
}: ErrorMessageComponentProps<DatabaseErrorExtra | null>) {
4040
const { extra, level, message } = error;
4141

42-
const isVisualization = ['dashboard', 'explore'].includes(source);
42+
const isVisualization = ['dashboard', 'explore'].includes(source || '');
43+
const [firstLine, ...remainingLines] = message.split('\n');
44+
const alertMessage = firstLine;
45+
const alertDescription =
46+
remainingLines.length > 0 ? remainingLines.join('\n') : null;
4347

4448
const body = extra && (
4549
<>
@@ -75,23 +79,13 @@ function DatabaseErrorMessage({
7579
</>
7680
);
7781

78-
const copyText = extra?.issue_codes
79-
? t('%(message)s\nThis may be triggered by: \n%(issues)s', {
80-
message,
81-
issues: extra.issue_codes
82-
.map(issueCode => issueCode.message)
83-
.join('\n'),
84-
})
85-
: message;
86-
8782
return (
8883
<ErrorAlert
89-
title={t('%s Error', extra?.engine_name || t('DB engine'))}
90-
subtitle={subtitle}
91-
level={level}
92-
source={source}
93-
copyText={copyText}
94-
body={body}
84+
errorType={t('%s Error', extra?.engine_name || t('DB engine'))}
85+
message={alertMessage}
86+
description={alertDescription}
87+
type={level}
88+
descriptionDetails={body}
9589
/>
9690
);
9791
}

superset-frontend/src/components/ErrorMessage/DatasetNotFoundErrorMessage.tsx

+4-8
Original file line numberDiff line numberDiff line change
@@ -23,19 +23,15 @@ import ErrorAlert from './ErrorAlert';
2323

2424
function DatasetNotFoundErrorMessage({
2525
error,
26-
source = 'dashboard',
2726
subtitle,
2827
}: ErrorMessageComponentProps) {
2928
const { level, message } = error;
30-
3129
return (
3230
<ErrorAlert
33-
title={t('Missing dataset')}
34-
subtitle={subtitle}
35-
level={level}
36-
source={source}
37-
copyText={message}
38-
body={null}
31+
errorType={t('Missing dataset')}
32+
message={subtitle}
33+
description={message}
34+
type={level}
3935
/>
4036
);
4137
}
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,151 @@
1+
/**
2+
* Licensed to the Apache Software Foundation (ASF) under one
3+
* or more contributor license agreements. See the NOTICE file
4+
* distributed with this work for additional information
5+
* regarding copyright ownership. The ASF licenses this file
6+
* to you under the Apache License, Version 2.0 (the
7+
* "License"); you may not use this file except in compliance
8+
* with the License. You may obtain a copy of the License at
9+
*
10+
* http://www.apache.org/licenses/LICENSE-2.0
11+
*
12+
* Unless required by applicable law or agreed to in writing,
13+
* software distributed under the License is distributed on an
14+
* "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
15+
* KIND, either express or implied. See the License for the
16+
* specific language governing permissions and limitations
17+
* under the License.
18+
*/
19+
import { Meta, StoryFn } from '@storybook/react';
20+
import { Layout, Row, Col, Card } from 'antd-v5';
21+
import ErrorAlert from './ErrorAlert';
22+
23+
const { Content } = Layout;
24+
25+
const longDescription = `This is a detailed description to test long content display.
26+
Line breaks are included here to demonstrate pre-wrap styling.
27+
This is useful for verbose error messages.`;
28+
29+
const sqlErrorDescription = `SQL Error: Syntax error near unexpected token.
30+
Please check your query and ensure it follows the correct syntax.`;
31+
32+
const detailsExample = `Additional details about the issue are provided here.
33+
This content is shown when the user clicks "Show more".`;
34+
35+
const ErrorCard: React.FC<{ children: React.ReactNode }> = ({ children }) => (
36+
<Card>{children}</Card>
37+
);
38+
39+
export default {
40+
title: 'Components/ErrorAlert',
41+
component: ErrorAlert,
42+
} as Meta;
43+
44+
export const Gallery: StoryFn = () => (
45+
<Layout>
46+
<Content style={{ padding: '24px' }}>
47+
<h2>Non-Compact Errors</h2>
48+
<Row gutter={[16, 16]}>
49+
<Col xs={48} sm={24} md={16} lg={16} xl={12}>
50+
<ErrorCard>
51+
<ErrorAlert message="Only message props was passed here" />
52+
</ErrorCard>
53+
</Col>
54+
<Col xs={48} sm={24} md={16} lg={16} xl={12}>
55+
<ErrorCard>
56+
<ErrorAlert
57+
errorType="Database Connection Error"
58+
type="warning"
59+
message="Failed to connect to database"
60+
descriptionDetails={detailsExample}
61+
descriptionDetailsCollapsed
62+
/>
63+
</ErrorCard>
64+
</Col>
65+
<Col xs={48} sm={24} md={16} lg={16} xl={12}>
66+
<ErrorCard>
67+
<ErrorAlert
68+
errorType="Error"
69+
message="SQL Syntax Error - No defaults set here"
70+
description={sqlErrorDescription}
71+
descriptionDetails={detailsExample}
72+
descriptionDetailsCollapsed
73+
descriptionPre
74+
/>
75+
</ErrorCard>
76+
</Col>
77+
<Col xs={48} sm={24} md={16} lg={16} xl={12}>
78+
<ErrorCard>
79+
<ErrorAlert
80+
errorType="Error"
81+
message="See the details below"
82+
type="error"
83+
description={longDescription}
84+
descriptionDetails={detailsExample}
85+
descriptionDetailsCollapsed={false}
86+
/>
87+
</ErrorCard>
88+
</Col>
89+
<Col xs={48} sm={24} md={16} lg={16} xl={12}>
90+
<ErrorCard>
91+
<ErrorAlert
92+
errorType="Informational Warning"
93+
message="This is a non-pre-wrap styled description"
94+
type="info"
95+
description={longDescription}
96+
descriptionDetails={detailsExample}
97+
descriptionDetailsCollapsed={false}
98+
descriptionPre={false}
99+
/>
100+
</ErrorCard>
101+
</Col>
102+
<Col xs={24} sm={12} md={8} lg={8} xl={6}>
103+
<ErrorCard>
104+
<ErrorAlert
105+
errorType="Error"
106+
message="Something went wrong"
107+
type="error"
108+
/>
109+
</ErrorCard>
110+
</Col>
111+
<Col xs={24} sm={12} md={8} lg={8} xl={6}>
112+
<ErrorCard>
113+
<ErrorAlert
114+
errorType="Warning"
115+
message="Be cautious"
116+
type="warning"
117+
/>
118+
</ErrorCard>
119+
</Col>
120+
</Row>
121+
<h2>Compact Errors (with Modal)</h2>
122+
<Row gutter={[16, 16]}>
123+
<Col xs={24} sm={12} md={8} lg={8} xl={6}>
124+
<ErrorCard>
125+
<ErrorAlert
126+
errorType="Error"
127+
message="Compact mode example"
128+
type="error"
129+
compact
130+
descriptionDetailsCollapsed
131+
description={sqlErrorDescription}
132+
descriptionDetails={detailsExample}
133+
/>
134+
</ErrorCard>
135+
</Col>
136+
<Col xs={24} sm={12} md={8} lg={8} xl={6}>
137+
<ErrorCard>
138+
<ErrorAlert
139+
errorType="Warning"
140+
message="Compact mode example"
141+
type="warning"
142+
compact
143+
descriptionDetails={detailsExample}
144+
descriptionDetailsCollapsed
145+
/>
146+
</ErrorCard>
147+
</Col>
148+
</Row>
149+
</Content>
150+
</Layout>
151+
);

0 commit comments

Comments
 (0)