mirror of
https://github.com/Unleash/unleash.git
synced 2025-01-25 00:07:47 +01:00
feat: welcome to your project component (#8039)
Currently displaying always when flag enabled. ![image](https://github.com/user-attachments/assets/e4c48595-b2d9-4093-af98-360d5856e7d5)
This commit is contained in:
parent
bd25bb633d
commit
e4fcb252d1
@ -39,6 +39,9 @@ import {
|
||||
useProjectFeatureSearchActions,
|
||||
} from './useProjectFeatureSearch';
|
||||
import { AvatarCell } from './AvatarCell';
|
||||
import { ProjectOnboarding } from './ProjectOnboarding/ProjectOnboarding';
|
||||
import { useUiFlag } from 'hooks/useUiFlag';
|
||||
import { styled } from '@mui/material';
|
||||
|
||||
interface IPaginatedProjectFeatureTogglesProps {
|
||||
environments: string[];
|
||||
@ -50,9 +53,16 @@ const formatEnvironmentColumnId = (environment: string) =>
|
||||
const columnHelper = createColumnHelper<FeatureSearchResponseSchema>();
|
||||
const getRowId = (row: { name: string }) => row.name;
|
||||
|
||||
const Container = styled('div')(({ theme }) => ({
|
||||
display: 'flex',
|
||||
flexDirection: 'column',
|
||||
gap: theme.spacing(2),
|
||||
}));
|
||||
|
||||
export const ProjectFeatureToggles = ({
|
||||
environments,
|
||||
}: IPaginatedProjectFeatureTogglesProps) => {
|
||||
const onboardingUIEnabled = useUiFlag('onboardingUI');
|
||||
const projectId = useRequiredPathParam('projectId');
|
||||
|
||||
const {
|
||||
@ -383,7 +393,11 @@ export const ProjectFeatureToggles = ({
|
||||
const selectedData = useSelectedData(features, rowSelection);
|
||||
|
||||
return (
|
||||
<>
|
||||
<Container>
|
||||
<ConditionallyRender
|
||||
condition={onboardingUIEnabled}
|
||||
show={<ProjectOnboarding projectId={projectId} />}
|
||||
/>
|
||||
<PageContent
|
||||
disableLoading
|
||||
disablePadding
|
||||
@ -486,6 +500,6 @@ export const ProjectFeatureToggles = ({
|
||||
onChange={refetch}
|
||||
/>
|
||||
</BatchSelectionActionsBar>
|
||||
</>
|
||||
</Container>
|
||||
);
|
||||
};
|
||||
|
@ -41,7 +41,7 @@ const StyledResponsiveButton = styled(ResponsiveButton)(() => ({
|
||||
whiteSpace: 'nowrap',
|
||||
}));
|
||||
|
||||
const FlagCreationButton: FC = () => {
|
||||
export const FlagCreationButton: FC = () => {
|
||||
const [searchParams] = useSearchParams();
|
||||
const projectId = useRequiredPathParam('projectId');
|
||||
const showCreateDialog = Boolean(searchParams.get('create'));
|
||||
|
@ -0,0 +1,28 @@
|
||||
import { styled } from '@mui/material';
|
||||
import { WelcomeToProject } from './WelcomeToProject';
|
||||
|
||||
interface IProjectOnboardingProps {
|
||||
projectId: string;
|
||||
}
|
||||
|
||||
const Container = styled('div')(({ theme }) => ({
|
||||
display: 'flex',
|
||||
width: '100%',
|
||||
gap: theme.spacing(2),
|
||||
}));
|
||||
|
||||
const SdkExample = styled('div')(({ theme }) => ({
|
||||
flexBasis: '30%',
|
||||
padding: theme.spacing(2),
|
||||
backgroundColor: theme.palette.background.paper,
|
||||
borderRadius: theme.shape.borderRadiusLarge,
|
||||
}));
|
||||
|
||||
export const ProjectOnboarding = ({ projectId }: IProjectOnboardingProps) => {
|
||||
return (
|
||||
<Container>
|
||||
<WelcomeToProject projectId={projectId} />
|
||||
<SdkExample>View SDK example</SdkExample>
|
||||
</Container>
|
||||
);
|
||||
};
|
@ -0,0 +1,104 @@
|
||||
import { styled, Typography } from '@mui/material';
|
||||
import Add from '@mui/icons-material/Add';
|
||||
import { CREATE_FEATURE } from 'component/providers/AccessProvider/permissions';
|
||||
import { FlagCreationButton } from '../ProjectFeatureTogglesHeader/ProjectFeatureTogglesHeader';
|
||||
import ResponsiveButton from 'component/common/ResponsiveButton/ResponsiveButton';
|
||||
|
||||
interface IWelcomeToProjectProps {
|
||||
projectId: string;
|
||||
}
|
||||
|
||||
const Container = styled('div')(({ theme }) => ({
|
||||
display: 'flex',
|
||||
flexDirection: 'column',
|
||||
backgroundColor: theme.palette.background.paper,
|
||||
flexBasis: '70%',
|
||||
borderRadius: theme.shape.borderRadiusLarge,
|
||||
}));
|
||||
|
||||
const TitleBox = styled('div')(({ theme }) => ({
|
||||
padding: theme.spacing(2, 7, 2, 7),
|
||||
borderBottom: '1px solid',
|
||||
borderColor: theme.palette.divider,
|
||||
}));
|
||||
|
||||
const Actions = styled('div')(({ theme }) => ({
|
||||
display: 'flex',
|
||||
flexGrow: 1,
|
||||
}));
|
||||
|
||||
const ActionBox = styled('div')(({ theme }) => ({
|
||||
flexBasis: '50%',
|
||||
padding: theme.spacing(3, 2, 6, 8),
|
||||
display: 'flex',
|
||||
gap: theme.spacing(3),
|
||||
flexDirection: 'column',
|
||||
}));
|
||||
|
||||
const TitleContainer = styled('div')(({ theme }) => ({
|
||||
display: 'flex',
|
||||
flexDirection: 'row',
|
||||
gap: theme.spacing(2),
|
||||
alignItems: 'center',
|
||||
fontSize: theme.spacing(1.75),
|
||||
fontWeight: 'bold',
|
||||
}));
|
||||
|
||||
const CircleContainer = styled('span')(({ theme }) => ({
|
||||
width: '28px',
|
||||
height: '28px',
|
||||
display: 'flex',
|
||||
alignItems: 'center',
|
||||
justifyContent: 'center',
|
||||
backgroundColor: theme.palette.neutral.border,
|
||||
borderRadius: '50%',
|
||||
}));
|
||||
|
||||
export const WelcomeToProject = ({ projectId }: IWelcomeToProjectProps) => {
|
||||
return (
|
||||
<Container>
|
||||
<TitleBox>
|
||||
<Typography fontWeight='bold'>
|
||||
Welcome to your project
|
||||
</Typography>
|
||||
<Typography variant='body2'>
|
||||
Complete the steps below to start working with this project
|
||||
</Typography>
|
||||
</TitleBox>
|
||||
<Actions>
|
||||
<ActionBox>
|
||||
<TitleContainer>
|
||||
<CircleContainer>1</CircleContainer>
|
||||
Create a feature flag
|
||||
</TitleContainer>
|
||||
<Typography>
|
||||
<div>
|
||||
The project currently holds no feature toggles.
|
||||
</div>
|
||||
<div>Create a feature flag to get started.</div>
|
||||
</Typography>
|
||||
<FlagCreationButton />
|
||||
</ActionBox>
|
||||
<ActionBox>
|
||||
<TitleContainer>
|
||||
<CircleContainer>2</CircleContainer>
|
||||
Connect an SDK
|
||||
</TitleContainer>
|
||||
<Typography>
|
||||
We have not detected any connected SDKs on this project.
|
||||
</Typography>
|
||||
<ResponsiveButton
|
||||
onClick={() => {}}
|
||||
maxWidth='200px'
|
||||
projectId={projectId}
|
||||
Icon={Add}
|
||||
disabled={true}
|
||||
permission={CREATE_FEATURE}
|
||||
>
|
||||
Connect SDK
|
||||
</ResponsiveButton>
|
||||
</ActionBox>
|
||||
</Actions>
|
||||
</Container>
|
||||
);
|
||||
};
|
@ -89,6 +89,7 @@ export type UiFlags = {
|
||||
newEventSearch?: boolean;
|
||||
archiveProjects?: boolean;
|
||||
projectListImprovements?: boolean;
|
||||
onboardingUI?: boolean;
|
||||
};
|
||||
|
||||
export interface IVersionInfo {
|
||||
|
@ -134,6 +134,7 @@ exports[`should create default config 1`] = `
|
||||
"navigationSidebar": true,
|
||||
"newEventSearch": false,
|
||||
"onboardingMetrics": false,
|
||||
"onboardingUI": false,
|
||||
"originMiddleware": false,
|
||||
"outdatedSdksBanner": false,
|
||||
"personalAccessTokensKillSwitch": false,
|
||||
|
@ -61,7 +61,8 @@ export type IFlagKey =
|
||||
| 'projectListImprovements'
|
||||
| 'useProjectReadModel'
|
||||
| 'addonUsageMetrics'
|
||||
| 'onboardingMetrics';
|
||||
| 'onboardingMetrics'
|
||||
| 'onboardingUI';
|
||||
|
||||
export type IFlags = Partial<{ [key in IFlagKey]: boolean | Variant }>;
|
||||
|
||||
@ -302,6 +303,10 @@ const flags: IFlags = {
|
||||
process.env.UNLEASH_EXPERIMENTAL_ONBOARDING_METRICS,
|
||||
false,
|
||||
),
|
||||
onboardingUI: parseEnvVarBoolean(
|
||||
process.env.UNLEASH_EXPERIMENTAL_ONBOARDING_UI,
|
||||
false,
|
||||
),
|
||||
};
|
||||
|
||||
export const defaultExperimentalOptions: IExperimentalOptions = {
|
||||
|
@ -56,6 +56,7 @@ process.nextTick(async () => {
|
||||
useProjectReadModel: true,
|
||||
addonUsageMetrics: true,
|
||||
onboardingMetrics: true,
|
||||
onboardingUI: true,
|
||||
},
|
||||
},
|
||||
authentication: {
|
||||
|
Loading…
Reference in New Issue
Block a user