diff --git a/frontend/src/assets/icons/link-child.svg b/frontend/src/assets/icons/link-child.svg
new file mode 100644
index 0000000000..0f1a31432f
--- /dev/null
+++ b/frontend/src/assets/icons/link-child.svg
@@ -0,0 +1,4 @@
+
diff --git a/frontend/src/assets/icons/link-parent.svg b/frontend/src/assets/icons/link-parent.svg
new file mode 100644
index 0000000000..89e31eef2d
--- /dev/null
+++ b/frontend/src/assets/icons/link-parent.svg
@@ -0,0 +1,3 @@
+
diff --git a/frontend/src/component/changeRequest/ChangeRequest.test.tsx b/frontend/src/component/changeRequest/ChangeRequest.test.tsx
index e90fcdf9ac..186a349de4 100644
--- a/frontend/src/component/changeRequest/ChangeRequest.test.tsx
+++ b/frontend/src/component/changeRequest/ChangeRequest.test.tsx
@@ -179,6 +179,8 @@ const feature = ({ name, enabled }: { name: string; enabled: boolean }) =>
lastSeenAt: null,
type: 'release',
archived: false,
+ dependencies: [],
+ children: [],
});
const otherRequests = (feature: string) => {
diff --git a/frontend/src/component/changeRequest/ChangeRequestPermissions.test.tsx b/frontend/src/component/changeRequest/ChangeRequestPermissions.test.tsx
index a53f14a7be..ea2140405d 100644
--- a/frontend/src/component/changeRequest/ChangeRequestPermissions.test.tsx
+++ b/frontend/src/component/changeRequest/ChangeRequestPermissions.test.tsx
@@ -170,6 +170,8 @@ const featureEnvironments = (
lastSeenAt: null,
type: 'release',
archived: false,
+ children: [],
+ dependencies: [],
});
};
diff --git a/frontend/src/component/feature/FeatureView/FeatureOverview/FeatureOverviewSidePanel/FeatureOverviewSidePanelDetails/ChildrenTooltip.tsx b/frontend/src/component/feature/FeatureView/FeatureOverview/FeatureOverviewSidePanel/FeatureOverviewSidePanelDetails/ChildrenTooltip.tsx
new file mode 100644
index 0000000000..1ff3de5e9f
--- /dev/null
+++ b/frontend/src/component/feature/FeatureView/FeatureOverview/FeatureOverviewSidePanel/FeatureOverviewSidePanelDetails/ChildrenTooltip.tsx
@@ -0,0 +1,24 @@
+import { StyledLink } from './StyledRow';
+import { TooltipLink } from 'component/common/TooltipLink/TooltipLink';
+import { FC } from 'react';
+
+export const ChildrenTooltip: FC<{
+ childFeatures: string[];
+ project: string;
+}> = ({ childFeatures, project }) => (
+
+ {childFeatures.map(child => (
+
+ {child}
+
+ ))}
+ >
+ }
+ >
+ {childFeatures.length === 1
+ ? '1 feature'
+ : `${childFeatures.length} features`}
+
+);
diff --git a/frontend/src/component/feature/FeatureView/FeatureOverview/FeatureOverviewSidePanel/FeatureOverviewSidePanelDetails/DependencyRow.tsx b/frontend/src/component/feature/FeatureView/FeatureOverview/FeatureOverviewSidePanel/FeatureOverviewSidePanelDetails/DependencyRow.tsx
index 3d55e570df..97e59d5418 100644
--- a/frontend/src/component/feature/FeatureView/FeatureOverview/FeatureOverviewSidePanel/FeatureOverviewSidePanelDetails/DependencyRow.tsx
+++ b/frontend/src/component/feature/FeatureView/FeatureOverview/FeatureOverviewSidePanel/FeatureOverviewSidePanelDetails/DependencyRow.tsx
@@ -9,6 +9,7 @@ import { FlexRow, StyledDetail, StyledLabel, StyledLink } from './StyledRow';
import { DependencyActions } from './DependencyActions';
import { useDependentFeaturesApi } from 'hooks/api/actions/useDependentFeaturesApi/useDependentFeaturesApi';
import { useFeature } from 'hooks/api/getters/useFeature/useFeature';
+import { ChildrenTooltip } from './ChildrenTooltip';
export const DependencyRow: FC<{ feature: IFeatureToggle }> = ({ feature }) => {
const { removeDependencies } = useDependentFeaturesApi(feature.project);
@@ -71,23 +72,10 @@ export const DependencyRow: FC<{ feature: IFeatureToggle }> = ({ feature }) => {
Children:
-
- {feature.children.map(child => (
-
- {child}
-
- ))}
- >
- }
- >
- {feature.children.length === 1
- ? '1 feature'
- : `${feature.children.length} features`}
-
+
}
diff --git a/frontend/src/component/feature/FeatureView/FeatureView.tsx b/frontend/src/component/feature/FeatureView/FeatureView.tsx
index 4d1fd577a5..f675873a42 100644
--- a/frontend/src/component/feature/FeatureView/FeatureView.tsx
+++ b/frontend/src/component/feature/FeatureView/FeatureView.tsx
@@ -1,5 +1,5 @@
import { useState } from 'react';
-import { styled, Tab, Tabs, useMediaQuery } from '@mui/material';
+import { styled, Tab, Tabs, useMediaQuery, Box, Card } from '@mui/material';
import { Archive, FileCopy, Label, WatchLater } from '@mui/icons-material';
import {
Link,
@@ -31,6 +31,11 @@ import { useRequiredPathParam } from 'hooks/useRequiredPathParam';
import { FeatureArchiveDialog } from 'component/common/FeatureArchiveDialog/FeatureArchiveDialog';
import { useFavoriteFeaturesApi } from 'hooks/api/actions/useFavoriteFeaturesApi/useFavoriteFeaturesApi';
import { FavoriteIconButton } from 'component/common/FavoriteIconButton/FavoriteIconButton';
+import { ReactComponent as ChildLinkIcon } from 'assets/icons/link-child.svg';
+import { ReactComponent as ParentLinkIcon } from 'assets/icons/link-parent.svg';
+import { TooltipLink } from '../../common/TooltipLink/TooltipLink';
+import { ChildrenTooltip } from './FeatureOverview/FeatureOverviewSidePanel/FeatureOverviewSidePanelDetails/ChildrenTooltip';
+import { useUiFlag } from '../../../hooks/useUiFlag';
const StyledHeader = styled('div')(({ theme }) => ({
backgroundColor: theme.palette.background.paper,
@@ -53,6 +58,28 @@ const StyledToggleInfoContainer = styled('div')({
alignItems: 'center',
});
+const StyledDependency = styled('div')(({ theme }) => ({
+ display: 'flex',
+ alignItems: 'center',
+ gap: theme.spacing(1),
+ marginTop: theme.spacing(1),
+ fontSize: theme.fontSizes.smallBody,
+ padding: theme.spacing(0.75, 1.5),
+ backgroundColor: theme.palette.background.elevation2,
+ borderRadius: `${theme.shape.borderRadiusMedium}px`,
+ width: 'max-content',
+}));
+
+const StyleChildLinkIcon = styled(ChildLinkIcon)(({ theme }) => ({
+ width: theme.fontSizes.smallBody,
+ height: theme.fontSizes.smallBody,
+}));
+
+const StyledParentLinkIcon = styled(ParentLinkIcon)(({ theme }) => ({
+ width: theme.fontSizes.smallBody,
+ height: theme.fontSizes.smallBody,
+}));
+
const StyledFeatureViewHeader = styled('h1')(({ theme }) => ({
fontSize: theme.fontSizes.mainHeader,
fontWeight: 'normal',
@@ -86,12 +113,21 @@ const StyledTabButton = styled(Tab)(({ theme }) => ({
},
}));
+export const StyledLink = styled(Link)(({ theme }) => ({
+ maxWidth: '100%',
+ textDecoration: 'none',
+ '&:hover, &:focus': {
+ textDecoration: 'underline',
+ },
+}));
+
export const FeatureView = () => {
const projectId = useRequiredPathParam('projectId');
const featureId = useRequiredPathParam('featureId');
const { refetch: projectRefetch } = useProject(projectId);
const { favorite, unfavorite } = useFavoriteFeaturesApi();
const { refetchFeature } = useFeature(projectId, featureId);
+ const dependentFeatures = useUiFlag('dependentFeatures');
const [openTagDialog, setOpenTagDialog] = useState(false);
const [showDelDialog, setShowDelDialog] = useState(false);
@@ -157,13 +193,56 @@ export const FeatureView = () => {
onClick={onFavorite}
isFavorite={feature?.favorite}
/>
-
- {feature.name}{' '}
-
- }
- />
+
+
+
+ {feature.name}{' '}
+
+
+ }
+ />
+
+ 0
+ }
+ show={
+
+ {' '}
+ Child feature
+ {' < '}
+
+ {feature?.dependencies[0]?.feature}
+
+
+ }
+ />
+ 0
+ }
+ show={
+
+ {' '}
+ Parent feature
+ {' > '}
+
+
+ }
+ />
+