1
0
mirror of https://github.com/Unleash/unleash.git synced 2024-12-22 19:07:54 +01:00

feat: show changes that would be overwritten in change request overview UI (#5964)

This PR adds a first, rough iteration of what it could look like to show
changes that would be overwritten by applying a PR.

The changes are listed in a table (semantically; looks more like a list
visually) and show the property, the current live value and the version
that you have in your changes. The changes are hidden by default, but
can be shown by expanding a details element.

@nicolaesocaciu Suggested that we merge this version for now and iterate
on the design later.

Here's what it looks like closed:

![image](https://github.com/Unleash/unleash/assets/17786332/3a641642-0537-4e7a-aeca-b3d3df6b8e31)

Here's what it looks like with a typical change load:

![image](https://github.com/Unleash/unleash/assets/17786332/b7aa7265-d1c7-4b6b-a9a2-f58cb966f25c)


Here's what it looks like if you change more or less every property
changed:

![image](https://github.com/Unleash/unleash/assets/17786332/4d94ab69-86ed-4c3e-be6a-6890c654e37e)
This commit is contained in:
Thomas Heartman 2024-01-22 11:13:38 +04:00 committed by GitHub
parent 8f4780c52f
commit 0bb709a718
No known key found for this signature in database
GPG Key ID: B5690EEEBB952194
3 changed files with 160 additions and 0 deletions

View File

@ -17,6 +17,7 @@ import { Badge } from 'component/common/Badge/Badge';
import { ConditionallyRender } from 'component/common/ConditionallyRender/ConditionallyRender';
import { flexRow } from 'themes/themeStyles';
import { EnvironmentVariantsTable } from 'component/feature/FeatureView/FeatureVariants/FeatureEnvironmentVariants/EnvironmentVariantsCard/EnvironmentVariantsTable/EnvironmentVariantsTable';
import { ChangesToOverwrite } from './StrategyChangeOverwriteWarning';
export const ChangeItemWrapper = styled(Box)({
display: 'flex',
@ -209,6 +210,10 @@ export const StrategyChange: VFC<{
)}
{change.action === 'updateStrategy' && (
<>
<ChangesToOverwrite
currentStrategy={currentStrategy}
change={change}
/>
<ChangeItemCreateEditWrapper>
<ChangeItemInfo>
<EditHeader

View File

@ -0,0 +1,154 @@
import { Box, styled } from '@mui/material';
import { IChangeRequestUpdateStrategy } from 'component/changeRequest/changeRequest.types';
import { useUiFlag } from 'hooks/useUiFlag';
import { IFeatureStrategy } from 'interfaces/strategy';
import { getChangesThatWouldBeOverwritten } from './strategy-change-diff-calculation';
const ChangesToOverwriteWarning = styled(Box)(({ theme }) => ({
color: theme.palette.warning.dark,
backgroundColor: theme.palette.warning.light,
fontSize: theme.fontSizes.smallBody,
borderRadius: theme.shape.borderRadiusLarge,
padding: theme.spacing(2),
marginBottom: theme.spacing(2),
}));
const OverwriteTable = styled('table')(({ theme }) => ({
'&,td,tr,thead': {
display: 'block',
textAlign: 'margin-inline-start',
},
thead: {
clip: 'rect(0 0 0 0)',
clipPath: 'inset(50%)',
height: '1px',
overflow: 'hidden',
position: 'absolute',
whiteSpace: 'nowrap',
width: '1px',
},
'tr + tr': {
marginBlockStart: theme.spacing(2),
},
'td:first-of-type': {
fontWeight: 'bold',
'::after': {
content: '":"',
},
textTransform: 'capitalize',
fontSize: theme.fontSizes.bodySize,
},
'td + td::before': {
content: 'attr(data-column)',
marginInlineEnd: theme.spacing(1),
fontWeight: 'bold',
},
pre: {
background: theme.palette.background.default,
padding: theme.spacing(2),
borderRadius: theme.shape.borderRadius,
width: '100%',
'ins, del': {
textDecoration: 'none',
'code::before': {
marginInlineEnd: theme.spacing(1),
},
},
'del code::before': {
content: '"-"',
},
'ins code::before': {
content: '"+"',
},
},
}));
export const ChangesToOverwrite: React.FC<{
currentStrategy?: IFeatureStrategy;
change: IChangeRequestUpdateStrategy;
}> = ({ change, currentStrategy }) => {
const checkForChanges = useUiFlag('changeRequestConflictHandling');
const changesThatWouldBeOverwritten = checkForChanges
? getChangesThatWouldBeOverwritten(currentStrategy, change)
: null;
if (!changesThatWouldBeOverwritten) {
return null;
}
return (
<ChangesToOverwriteWarning>
<p>
<strong>Heads up!</strong> The strategy has been updated since
you made your changes. Applying this change now would overwrite
the configuration that is currently live.
</p>
<details>
<summary>Changes that would be overwritten</summary>
<OverwriteTable>
<thead>
<tr>
<th>Property</th>
<th>Current value</th>
<th>Value after change</th>
</tr>
</thead>
<tbody>
{changesThatWouldBeOverwritten.map(
({ property, oldValue, newValue }) => (
<tr key={property}>
<td data-column='Property'>{property}</td>
<td data-column='Current value'>
<pre>
<del>
{JSON.stringify(
oldValue,
null,
2,
)
.split('\n')
.map((line, index) => (
<code
key={`${property}${line}${index}`}
>
{`${line}\n`}
</code>
))}
</del>
</pre>
</td>
<td data-column='Value after change'>
<pre>
<ins>
{JSON.stringify(
newValue,
null,
2,
)
.split('\n')
.map((line, index) => (
<code
key={`${property}${line}${index}`}
>
{`${line}\n`}
</code>
))}
</ins>
</pre>
</td>
</tr>
),
)}
</tbody>
</OverwriteTable>
</details>
</ChangesToOverwriteWarning>
);
};

View File

@ -76,6 +76,7 @@ export type UiFlags = {
extendedUsageMetricsUI?: boolean;
adminTokenKillSwitch?: boolean;
executiveDashboard?: boolean;
changeRequestConflictHandling?: boolean;
};
export interface IVersionInfo {