-
Notifications
You must be signed in to change notification settings - Fork 71
Commit
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.
✨ 461 adding the test results new UX (#491)
- Loading branch information
Showing
33 changed files
with
537 additions
and
299 deletions.
There are no files selected for viewing
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,48 @@ | ||
import {CloseCircleOutlined, EditOutlined} from '@ant-design/icons'; | ||
import {Typography} from 'antd'; | ||
import styled, {css} from 'styled-components'; | ||
|
||
export const AssertionCard = styled.div` | ||
border-radius: 2px; | ||
border: 1px solid rgba(3, 24, 73, 0.1); | ||
`; | ||
|
||
export const Header = styled.div` | ||
display: flex; | ||
background: #fbfbff; | ||
border-bottom: 1px solid rgba(3, 24, 73, 0.1); | ||
padding: 8px 14px; | ||
justify-content: space-between; | ||
border-radius: 2px 2px 0px 0px; | ||
`; | ||
|
||
export const Body = styled.div` | ||
padding: 12px 14px; | ||
display: flex; | ||
flex-direction: column; | ||
gap: 9px; | ||
`; | ||
|
||
export const SelectorListText = styled(Typography.Text).attrs({ | ||
strong: true, | ||
})` | ||
margin-right: 14px; | ||
`; | ||
|
||
export const SpanCountText = styled(Typography.Text)` | ||
font-size: 12; | ||
`; | ||
const baseIcon = css` | ||
font-size: 18px; | ||
color: #61175e; | ||
cursor: pointer; | ||
`; | ||
|
||
export const EditIcon = styled(EditOutlined)` | ||
${baseIcon} | ||
`; | ||
|
||
export const DeleteIcon = styled(CloseCircleOutlined)` | ||
${baseIcon} | ||
margin-left: 12px; | ||
`; |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,69 @@ | ||
import {useCallback, useMemo} from 'react'; | ||
import {useStore} from 'react-flow-renderer'; | ||
import {IAssertionResult} from '../../types/Assertion.types'; | ||
import AssertionCheckRow from '../AssertionCheckRow'; | ||
import * as S from './AssertionCard.styled'; | ||
|
||
interface IAssertionCardProps { | ||
assertionResult: IAssertionResult; | ||
onSelectSpan(spanId: string): void; | ||
onDelete(assertionId: string): void; | ||
onEdit(assertionResult: IAssertionResult): void; | ||
} | ||
|
||
const AssertionCard: React.FC<IAssertionCardProps> = ({ | ||
assertionResult: {assertion: {selectors = [], assertionId = ''} = {}, spanListAssertionResult}, | ||
assertionResult, | ||
onSelectSpan, | ||
onDelete, | ||
onEdit, | ||
}) => { | ||
const store = useStore(); | ||
|
||
const spanCountText = useMemo(() => { | ||
const spanCount = spanListAssertionResult.length; | ||
|
||
return `${spanCount} ${spanCount > 1 ? 'spans' : 'span'}`; | ||
}, [spanListAssertionResult.length]); | ||
|
||
const getIsSelectedSpan = useCallback( | ||
(id: string): boolean => { | ||
const {selectedElements} = store.getState(); | ||
const found = selectedElements ? selectedElements.find(element => element.id === id) : undefined; | ||
|
||
return Boolean(found); | ||
}, | ||
[store] | ||
); | ||
|
||
return ( | ||
<S.AssertionCard data-cy="assertion-card"> | ||
<S.Header> | ||
<div> | ||
<S.SelectorListText>{selectors.map(({value}) => value).join(' ')}</S.SelectorListText> | ||
<S.SpanCountText>{spanCountText}</S.SpanCountText> | ||
</div> | ||
<div> | ||
<S.EditIcon onClick={() => onEdit(assertionResult)} /> | ||
<S.DeleteIcon onClick={() => onDelete(assertionId)} /> | ||
</div> | ||
</S.Header> | ||
<S.Body> | ||
{spanListAssertionResult.flatMap(({span, resultList}) => | ||
resultList.map(result => ( | ||
<AssertionCheckRow | ||
key={`${result.propertyName}-${span.spanId}`} | ||
result={result} | ||
span={span} | ||
onSelectSpan={onSelectSpan} | ||
getIsSelectedSpan={getIsSelectedSpan} | ||
assertionSelectorList={selectors.map(({value}) => value)} | ||
/> | ||
)) | ||
)} | ||
</S.Body> | ||
</S.AssertionCard> | ||
); | ||
}; | ||
|
||
export default AssertionCard; |
43 changes: 43 additions & 0 deletions
43
web/src/components/AssertionCard/__stories__/AssertionCard.stories.tsx
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,43 @@ | ||
import faker from '@faker-js/faker'; | ||
import {ComponentStory, ComponentMeta} from '@storybook/react'; | ||
import {LOCATION_NAME} from '../../../constants/Span.constants'; | ||
import {SELECTOR_DEFAULT_ATTRIBUTES} from '../../../constants/SemanticGroupNames.constants'; | ||
|
||
import AssertionCard from '../AssertionCard'; | ||
import SpanMock from '../../../models/__mocks__/Span.mock'; | ||
|
||
export default { | ||
title: 'Assertion Card', | ||
component: AssertionCard, | ||
argTypes: {onSelectSpan: {action: 'noSelectSpan'}}, | ||
} as ComponentMeta<typeof AssertionCard>; | ||
|
||
const Template: ComponentStory<typeof AssertionCard> = args => <AssertionCard {...args} />; | ||
|
||
export const Default = Template.bind({}); | ||
Default.args = { | ||
assertionResult: { | ||
assertion: { | ||
assertionId: faker.datatype.uuid(), | ||
selectors: [ | ||
{ | ||
locationName: LOCATION_NAME.SPAN_ATTRIBUTES, | ||
propertyName: faker.random.arrayElement(SELECTOR_DEFAULT_ATTRIBUTES[0].attributes), | ||
value: 'http', | ||
valueType: faker.random.word(), | ||
}, | ||
{ | ||
locationName: LOCATION_NAME.SPAN_ATTRIBUTES, | ||
propertyName: faker.random.arrayElement(SELECTOR_DEFAULT_ATTRIBUTES[0].attributes), | ||
value: 'pokeshop', | ||
valueType: faker.random.word(), | ||
}, | ||
], | ||
spanAssertions: [], | ||
}, | ||
spanListAssertionResult: faker.datatype.array(faker.datatype.number({min: 1, max: 10})).map(() => ({ | ||
span: SpanMock.model(), | ||
resultList: [], | ||
})), | ||
}, | ||
}; |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,2 @@ | ||
// eslint-disable-next-line no-restricted-exports | ||
export {default} from './AssertionCard'; |
21 changes: 21 additions & 0 deletions
21
web/src/components/AssertionCardList/AssertionCardList.styled.ts
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,21 @@ | ||
import styled from 'styled-components'; | ||
import noResultsIcon from '../../assets/SpanAssertionsEmptyState.svg'; | ||
|
||
export const AssertionCardList = styled.div` | ||
display: flex; | ||
flex-direction: column; | ||
gap: 24px; | ||
`; | ||
|
||
export const EmptyStateContainer = styled.div` | ||
display: flex; | ||
justify-content: center; | ||
align-items: center; | ||
margin-top: 40px; | ||
flex-direction: column; | ||
gap: 14px; | ||
`; | ||
|
||
export const EmptyStateIcon = styled.img.attrs({ | ||
src: noResultsIcon, | ||
})``; |
63 changes: 63 additions & 0 deletions
63
web/src/components/AssertionCardList/AssertionCardList.tsx
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,63 @@ | ||
import {Typography} from 'antd'; | ||
import {useCallback} from 'react'; | ||
import {useDeleteAssertionMutation} from '../../redux/apis/Test.api'; | ||
import {IAssertionResult} from '../../types/Assertion.types'; | ||
import AssertionCard from '../AssertionCard/AssertionCard'; | ||
import {useCreateAssertionModal} from '../CreateAssertionModal/CreateAssertionModalProvider'; | ||
import * as S from './AssertionCardList.styled'; | ||
|
||
interface IAssertionCardListProps { | ||
assertionResultList: IAssertionResult[]; | ||
onSelectSpan(spanId: string): void; | ||
resultId: string; | ||
testId: string; | ||
} | ||
|
||
const AssertionCardList: React.FC<IAssertionCardListProps> = ({ | ||
assertionResultList, | ||
onSelectSpan, | ||
testId, | ||
resultId, | ||
}) => { | ||
const {open} = useCreateAssertionModal(); | ||
const [deleteAssertion] = useDeleteAssertionMutation(); | ||
|
||
const handleEdit = useCallback( | ||
({assertion, spanListAssertionResult}: IAssertionResult) => { | ||
const [{span}] = spanListAssertionResult; | ||
|
||
open({ | ||
span, | ||
testId, | ||
assertion, | ||
resultId, | ||
}); | ||
}, | ||
[open, resultId, testId] | ||
); | ||
|
||
return ( | ||
<S.AssertionCardList> | ||
{assertionResultList.length ? ( | ||
assertionResultList.map(assertionResult => | ||
assertionResult.spanListAssertionResult.length ? ( | ||
<AssertionCard | ||
key={assertionResult.assertion?.assertionId} | ||
assertionResult={assertionResult} | ||
onSelectSpan={onSelectSpan} | ||
onEdit={handleEdit} | ||
onDelete={assertionId => deleteAssertion({testId, assertionId})} | ||
/> | ||
) : null | ||
) | ||
) : ( | ||
<S.EmptyStateContainer> | ||
<S.EmptyStateIcon /> | ||
<Typography.Text disabled>No Data</Typography.Text> | ||
</S.EmptyStateContainer> | ||
)} | ||
</S.AssertionCardList> | ||
); | ||
}; | ||
|
||
export default AssertionCardList; |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,2 @@ | ||
// eslint-disable-next-line no-restricted-exports | ||
export {default} from './AssertionCardList'; |
43 changes: 43 additions & 0 deletions
43
web/src/components/AssertionCheckRow/AssertionCheckRow.styled.ts
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,43 @@ | ||
import {Badge, Typography} from 'antd'; | ||
import styled from 'styled-components'; | ||
|
||
export const AssertionCheckRow = styled.div` | ||
display: grid; | ||
grid-template-columns: 1.5fr 1fr .8fr 1fr 1fr; | ||
gap: 14px; | ||
cursor: pointer; | ||
`; | ||
|
||
export const Entry = styled.div` | ||
display: flex; | ||
flex-direction: column; | ||
text-overflow: ellipsis; | ||
white-space: nowrap; | ||
overflow: hidden; | ||
`; | ||
|
||
export const Label = styled(Typography.Text).attrs({ | ||
type: 'secondary', | ||
})` | ||
font-size: 12px; | ||
`; | ||
|
||
export const Value = styled(Typography.Text)` | ||
font-size: 12px; | ||
`; | ||
|
||
export const LabelBadge = styled(Badge)` | ||
> sup { | ||
background-color: #f0f0f0; | ||
color: black; | ||
margin-right: 6px; | ||
border-radius: 2px; | ||
} | ||
`; | ||
|
||
export const SelectedLabelBadge = styled(LabelBadge)` | ||
> sup { | ||
color: #61175e; | ||
border: 1px solid #61175e; | ||
} | ||
`; |
62 changes: 62 additions & 0 deletions
62
web/src/components/AssertionCheckRow/AssertionCheckRow.tsx
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,62 @@ | ||
import {useMemo} from 'react'; | ||
import {difference} from 'lodash'; | ||
import OperatorService from '../../services/Operator.service'; | ||
import {ISpanAssertionResult} from '../../types/Assertion.types'; | ||
import {ISpan} from '../../types/Span.types'; | ||
import * as S from './AssertionCheckRow.styled'; | ||
import AttributeValue from '../AttributeValue'; | ||
|
||
interface IAssertionCheckRowProps { | ||
result: ISpanAssertionResult; | ||
span: ISpan; | ||
assertionSelectorList: string[]; | ||
getIsSelectedSpan(spanId: string): boolean; | ||
onSelectSpan(spanId: string): void; | ||
} | ||
|
||
const AssertionCheckRow: React.FC<IAssertionCheckRowProps> = ({ | ||
result: {propertyName, comparisonValue, operator, actualValue, hasPassed, spanId}, | ||
span: {signature}, | ||
assertionSelectorList, | ||
getIsSelectedSpan, | ||
onSelectSpan, | ||
}) => { | ||
const signatureSelectorList = signature.map(({value}) => value).concat([`#${spanId.slice(-4)}`]) || []; | ||
const spanLabelList = difference(signatureSelectorList, assertionSelectorList); | ||
const badgeList = useMemo(() => { | ||
const isSelected = getIsSelectedSpan(spanId); | ||
|
||
return (isSelected ? [<S.SelectedLabelBadge count="selected" key="selected" />] : []).concat( | ||
spanLabelList | ||
// eslint-disable-next-line react/no-array-index-key | ||
.map((label, index) => <S.LabelBadge count={label} key={`${label}-${index}`} />) | ||
); | ||
}, [getIsSelectedSpan, spanId, spanLabelList]); | ||
|
||
return ( | ||
<S.AssertionCheckRow onClick={() => onSelectSpan(spanId)}> | ||
<S.Entry> | ||
<S.Label>Span Labels</S.Label> | ||
<S.Value>{badgeList}</S.Value> | ||
</S.Entry> | ||
<S.Entry> | ||
<S.Label>Attribute</S.Label> | ||
<S.Value>{propertyName}</S.Value> | ||
</S.Entry> | ||
<S.Entry> | ||
<S.Label>Assertion Type</S.Label> | ||
<S.Value>{OperatorService.getOperatorName(operator)}</S.Value> | ||
</S.Entry> | ||
<S.Entry> | ||
<S.Label>Expected Value</S.Label> | ||
<AttributeValue value={comparisonValue} /> | ||
</S.Entry> | ||
<S.Entry> | ||
<S.Label>Actual Value</S.Label> | ||
<AttributeValue strong type={hasPassed ? 'success' : 'danger'} value={actualValue || '<Empty Value>'} /> | ||
</S.Entry> | ||
</S.AssertionCheckRow> | ||
); | ||
}; | ||
|
||
export default AssertionCheckRow; |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,2 @@ | ||
// eslint-disable-next-line no-restricted-exports | ||
export {default} from './AssertionCheckRow'; |
Oops, something went wrong.