mirror of
https://github.com/Unleash/unleash.git
synced 2025-02-23 00:22:19 +01:00
feat: add initial setup for tabs (#5586)
This PR sets up the initial tab structure for the new strategy form
This commit is contained in:
parent
d11aedc12f
commit
9dbb7ea9a9
@ -22,6 +22,9 @@ import {
|
|||||||
} from 'component/changeRequest/changeRequest.types';
|
} from 'component/changeRequest/changeRequest.types';
|
||||||
import { SidebarModal } from 'component/common/SidebarModal/SidebarModal';
|
import { SidebarModal } from 'component/common/SidebarModal/SidebarModal';
|
||||||
import { useSegments } from 'hooks/api/getters/useSegments/useSegments';
|
import { useSegments } from 'hooks/api/getters/useSegments/useSegments';
|
||||||
|
import { useUiFlag } from 'hooks/useUiFlag';
|
||||||
|
import { ConditionallyRender } from 'component/common/ConditionallyRender/ConditionallyRender';
|
||||||
|
import { NewFeatureStrategyForm } from 'component/feature/FeatureStrategy/FeatureStrategyForm/NewFeatureStrategyForm';
|
||||||
|
|
||||||
interface IEditChangeProps {
|
interface IEditChangeProps {
|
||||||
change: IChangeRequestAddStrategy | IChangeRequestUpdateStrategy;
|
change: IChangeRequestAddStrategy | IChangeRequestUpdateStrategy;
|
||||||
@ -44,6 +47,8 @@ export const EditChange = ({
|
|||||||
}: IEditChangeProps) => {
|
}: IEditChangeProps) => {
|
||||||
const projectId = useRequiredPathParam('projectId');
|
const projectId = useRequiredPathParam('projectId');
|
||||||
const { editChange } = useChangeRequestApi();
|
const { editChange } = useChangeRequestApi();
|
||||||
|
const [tab, setTab] = useState(0);
|
||||||
|
const newStrategyConfiguration = useUiFlag('newStrategyConfiguration');
|
||||||
|
|
||||||
const [strategy, setStrategy] = useState<Partial<IFeatureStrategy>>(
|
const [strategy, setStrategy] = useState<Partial<IFeatureStrategy>>(
|
||||||
change.payload,
|
change.payload,
|
||||||
@ -146,6 +151,30 @@ export const EditChange = ({
|
|||||||
)
|
)
|
||||||
}
|
}
|
||||||
>
|
>
|
||||||
|
<ConditionallyRender
|
||||||
|
condition={newStrategyConfiguration}
|
||||||
|
show={
|
||||||
|
<NewFeatureStrategyForm
|
||||||
|
projectId={projectId}
|
||||||
|
feature={data}
|
||||||
|
strategy={strategy}
|
||||||
|
setStrategy={setStrategy}
|
||||||
|
segments={segments}
|
||||||
|
setSegments={setSegments}
|
||||||
|
environmentId={environment}
|
||||||
|
onSubmit={onInternalSubmit}
|
||||||
|
onCancel={onClose}
|
||||||
|
loading={false}
|
||||||
|
permission={UPDATE_FEATURE_STRATEGY}
|
||||||
|
errors={errors}
|
||||||
|
isChangeRequest={isChangeRequestConfigured(
|
||||||
|
environment,
|
||||||
|
)}
|
||||||
|
tab={tab}
|
||||||
|
setTab={setTab}
|
||||||
|
/>
|
||||||
|
}
|
||||||
|
elseShow={
|
||||||
<FeatureStrategyForm
|
<FeatureStrategyForm
|
||||||
projectId={projectId}
|
projectId={projectId}
|
||||||
feature={data}
|
feature={data}
|
||||||
@ -159,8 +188,13 @@ export const EditChange = ({
|
|||||||
loading={false}
|
loading={false}
|
||||||
permission={UPDATE_FEATURE_STRATEGY}
|
permission={UPDATE_FEATURE_STRATEGY}
|
||||||
errors={errors}
|
errors={errors}
|
||||||
isChangeRequest={isChangeRequestConfigured(environment)}
|
isChangeRequest={isChangeRequestConfigured(
|
||||||
|
environment,
|
||||||
|
)}
|
||||||
/>
|
/>
|
||||||
|
}
|
||||||
|
/>
|
||||||
|
|
||||||
{staleDataNotification}
|
{staleDataNotification}
|
||||||
</FormTemplate>
|
</FormTemplate>
|
||||||
</SidebarModal>
|
</SidebarModal>
|
||||||
|
@ -0,0 +1,349 @@
|
|||||||
|
import React, { useState } from 'react';
|
||||||
|
import { useNavigate } from 'react-router-dom';
|
||||||
|
import { Alert, Button, styled, Tabs, Tab } from '@mui/material';
|
||||||
|
import {
|
||||||
|
IFeatureStrategy,
|
||||||
|
IFeatureStrategyParameters,
|
||||||
|
IStrategyParameter,
|
||||||
|
} from 'interfaces/strategy';
|
||||||
|
import { FeatureStrategyType } from '../FeatureStrategyType/FeatureStrategyType';
|
||||||
|
import { FeatureStrategyEnabled } from './FeatureStrategyEnabled/FeatureStrategyEnabled';
|
||||||
|
import { FeatureStrategyConstraints } from '../FeatureStrategyConstraints/FeatureStrategyConstraints';
|
||||||
|
import { IFeatureToggle } from 'interfaces/featureToggle';
|
||||||
|
import useUiConfig from 'hooks/api/getters/useUiConfig/useUiConfig';
|
||||||
|
import { ConditionallyRender } from 'component/common/ConditionallyRender/ConditionallyRender';
|
||||||
|
import { STRATEGY_FORM_SUBMIT_ID } from 'utils/testIds';
|
||||||
|
import { useConstraintsValidation } from 'hooks/api/getters/useConstraintsValidation/useConstraintsValidation';
|
||||||
|
import PermissionButton from 'component/common/PermissionButton/PermissionButton';
|
||||||
|
import { FeatureStrategySegment } from 'component/feature/FeatureStrategy/FeatureStrategySegment/FeatureStrategySegment';
|
||||||
|
import { ISegment } from 'interfaces/segment';
|
||||||
|
import { IFormErrors } from 'hooks/useFormErrors';
|
||||||
|
import { validateParameterValue } from 'utils/validateParameterValue';
|
||||||
|
import { useStrategy } from 'hooks/api/getters/useStrategy/useStrategy';
|
||||||
|
import { FeatureStrategyChangeRequestAlert } from './FeatureStrategyChangeRequestAlert/FeatureStrategyChangeRequestAlert';
|
||||||
|
import {
|
||||||
|
FeatureStrategyProdGuard,
|
||||||
|
useFeatureStrategyProdGuard,
|
||||||
|
} from '../FeatureStrategyProdGuard/FeatureStrategyProdGuard';
|
||||||
|
import { formatFeaturePath } from '../FeatureStrategyEdit/FeatureStrategyEdit';
|
||||||
|
import { useChangeRequestInReviewWarning } from 'hooks/useChangeRequestInReviewWarning';
|
||||||
|
import { usePendingChangeRequests } from 'hooks/api/getters/usePendingChangeRequests/usePendingChangeRequests';
|
||||||
|
import { useHasProjectEnvironmentAccess } from 'hooks/useHasAccess';
|
||||||
|
import { FeatureStrategyTitle } from './FeatureStrategyTitle/FeatureStrategyTitle';
|
||||||
|
import { FeatureStrategyEnabledDisabled } from './FeatureStrategyEnabledDisabled/FeatureStrategyEnabledDisabled';
|
||||||
|
import { StrategyVariants } from 'component/feature/StrategyTypes/StrategyVariants';
|
||||||
|
import { usePlausibleTracker } from 'hooks/usePlausibleTracker';
|
||||||
|
|
||||||
|
interface IFeatureStrategyFormProps {
|
||||||
|
feature: IFeatureToggle;
|
||||||
|
projectId: string;
|
||||||
|
environmentId: string;
|
||||||
|
permission: string;
|
||||||
|
onSubmit: () => void;
|
||||||
|
onCancel?: () => void;
|
||||||
|
loading: boolean;
|
||||||
|
isChangeRequest?: boolean;
|
||||||
|
strategy: Partial<IFeatureStrategy>;
|
||||||
|
setStrategy: React.Dispatch<
|
||||||
|
React.SetStateAction<Partial<IFeatureStrategy>>
|
||||||
|
>;
|
||||||
|
segments: ISegment[];
|
||||||
|
setSegments: React.Dispatch<React.SetStateAction<ISegment[]>>;
|
||||||
|
errors: IFormErrors;
|
||||||
|
tab: number;
|
||||||
|
setTab: React.Dispatch<React.SetStateAction<number>>;
|
||||||
|
}
|
||||||
|
|
||||||
|
const StyledForm = styled('form')(({ theme }) => ({
|
||||||
|
display: 'grid',
|
||||||
|
gap: theme.spacing(2),
|
||||||
|
}));
|
||||||
|
|
||||||
|
const StyledHr = styled('hr')(({ theme }) => ({
|
||||||
|
width: '100%',
|
||||||
|
height: '1px',
|
||||||
|
margin: theme.spacing(2, 0),
|
||||||
|
border: 'none',
|
||||||
|
background: theme.palette.background.elevation2,
|
||||||
|
}));
|
||||||
|
|
||||||
|
const StyledButtons = styled('div')(({ theme }) => ({
|
||||||
|
display: 'flex',
|
||||||
|
justifyContent: 'end',
|
||||||
|
gap: theme.spacing(2),
|
||||||
|
paddingBottom: theme.spacing(10),
|
||||||
|
}));
|
||||||
|
|
||||||
|
export const NewFeatureStrategyForm = ({
|
||||||
|
projectId,
|
||||||
|
feature,
|
||||||
|
environmentId,
|
||||||
|
permission,
|
||||||
|
onSubmit,
|
||||||
|
onCancel,
|
||||||
|
loading,
|
||||||
|
strategy,
|
||||||
|
setStrategy,
|
||||||
|
segments,
|
||||||
|
setSegments,
|
||||||
|
errors,
|
||||||
|
isChangeRequest,
|
||||||
|
tab,
|
||||||
|
setTab,
|
||||||
|
}: IFeatureStrategyFormProps) => {
|
||||||
|
const { trackEvent } = usePlausibleTracker();
|
||||||
|
const [showProdGuard, setShowProdGuard] = useState(false);
|
||||||
|
const hasValidConstraints = useConstraintsValidation(strategy.constraints);
|
||||||
|
const enableProdGuard = useFeatureStrategyProdGuard(feature, environmentId);
|
||||||
|
const access = useHasProjectEnvironmentAccess(
|
||||||
|
permission,
|
||||||
|
projectId,
|
||||||
|
environmentId,
|
||||||
|
);
|
||||||
|
const { strategyDefinition } = useStrategy(strategy?.name);
|
||||||
|
|
||||||
|
const { data } = usePendingChangeRequests(feature.project);
|
||||||
|
const { changeRequestInReviewOrApproved, alert } =
|
||||||
|
useChangeRequestInReviewWarning(data);
|
||||||
|
|
||||||
|
const hasChangeRequestInReviewForEnvironment =
|
||||||
|
changeRequestInReviewOrApproved(environmentId || '');
|
||||||
|
|
||||||
|
const changeRequestButtonText = hasChangeRequestInReviewForEnvironment
|
||||||
|
? 'Add to existing change request'
|
||||||
|
: 'Add change to draft';
|
||||||
|
|
||||||
|
const navigate = useNavigate();
|
||||||
|
|
||||||
|
const {
|
||||||
|
uiConfig,
|
||||||
|
error: uiConfigError,
|
||||||
|
loading: uiConfigLoading,
|
||||||
|
} = useUiConfig();
|
||||||
|
|
||||||
|
if (uiConfigError) {
|
||||||
|
throw uiConfigError;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (uiConfigLoading || !strategyDefinition) {
|
||||||
|
return null;
|
||||||
|
}
|
||||||
|
|
||||||
|
const findParameterDefinition = (name: string): IStrategyParameter => {
|
||||||
|
return strategyDefinition.parameters.find((parameterDefinition) => {
|
||||||
|
return parameterDefinition.name === name;
|
||||||
|
})!;
|
||||||
|
};
|
||||||
|
|
||||||
|
const validateParameter = (
|
||||||
|
name: string,
|
||||||
|
value: IFeatureStrategyParameters[string],
|
||||||
|
): boolean => {
|
||||||
|
const parameterValueError = validateParameterValue(
|
||||||
|
findParameterDefinition(name),
|
||||||
|
value,
|
||||||
|
);
|
||||||
|
if (parameterValueError) {
|
||||||
|
errors.setFormError(name, parameterValueError);
|
||||||
|
return false;
|
||||||
|
} else {
|
||||||
|
errors.removeFormError(name);
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
};
|
||||||
|
|
||||||
|
const validateAllParameters = (): boolean => {
|
||||||
|
return strategyDefinition.parameters
|
||||||
|
.map((parameter) => parameter.name)
|
||||||
|
.map((name) => validateParameter(name, strategy.parameters?.[name]))
|
||||||
|
.every(Boolean);
|
||||||
|
};
|
||||||
|
|
||||||
|
const onDefaultCancel = () => {
|
||||||
|
navigate(formatFeaturePath(feature.project, feature.name));
|
||||||
|
};
|
||||||
|
|
||||||
|
const onSubmitWithValidation = async (event: React.FormEvent) => {
|
||||||
|
if (Array.isArray(strategy.variants) && strategy.variants?.length > 0) {
|
||||||
|
trackEvent('strategy-variants', {
|
||||||
|
props: {
|
||||||
|
eventType: 'submitted',
|
||||||
|
},
|
||||||
|
});
|
||||||
|
}
|
||||||
|
event.preventDefault();
|
||||||
|
if (!validateAllParameters()) {
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (enableProdGuard && !isChangeRequest) {
|
||||||
|
setShowProdGuard(true);
|
||||||
|
} else {
|
||||||
|
onSubmit();
|
||||||
|
}
|
||||||
|
};
|
||||||
|
|
||||||
|
const handleChange = (event: React.ChangeEvent<{}>, newValue: number) => {
|
||||||
|
setTab(newValue);
|
||||||
|
};
|
||||||
|
|
||||||
|
return (
|
||||||
|
<StyledForm onSubmit={onSubmitWithValidation}>
|
||||||
|
<Tabs value={tab} onChange={handleChange}>
|
||||||
|
<Tab label='General' />
|
||||||
|
<Tab label='Targeting' />
|
||||||
|
<Tab label='Variants' />
|
||||||
|
</Tabs>
|
||||||
|
<ConditionallyRender
|
||||||
|
condition={tab === 0}
|
||||||
|
show={
|
||||||
|
<>
|
||||||
|
<ConditionallyRender
|
||||||
|
condition={hasChangeRequestInReviewForEnvironment}
|
||||||
|
show={alert}
|
||||||
|
elseShow={
|
||||||
|
<ConditionallyRender
|
||||||
|
condition={Boolean(isChangeRequest)}
|
||||||
|
show={
|
||||||
|
<FeatureStrategyChangeRequestAlert
|
||||||
|
environment={environmentId}
|
||||||
|
/>
|
||||||
|
}
|
||||||
|
/>
|
||||||
|
}
|
||||||
|
/>
|
||||||
|
<FeatureStrategyEnabled
|
||||||
|
projectId={feature.project}
|
||||||
|
featureId={feature.name}
|
||||||
|
environmentId={environmentId}
|
||||||
|
>
|
||||||
|
<ConditionallyRender
|
||||||
|
condition={Boolean(isChangeRequest)}
|
||||||
|
show={
|
||||||
|
<Alert severity='success'>
|
||||||
|
This feature toggle is currently enabled
|
||||||
|
in the <strong>{environmentId}</strong>{' '}
|
||||||
|
environment. Any changes made here will
|
||||||
|
be available to users as soon as these
|
||||||
|
changes are approved and applied.
|
||||||
|
</Alert>
|
||||||
|
}
|
||||||
|
elseShow={
|
||||||
|
<Alert severity='success'>
|
||||||
|
This feature toggle is currently enabled
|
||||||
|
in the <strong>{environmentId}</strong>{' '}
|
||||||
|
environment. Any changes made here will
|
||||||
|
be available to users as soon as you hit{' '}
|
||||||
|
<strong>save</strong>.
|
||||||
|
</Alert>
|
||||||
|
}
|
||||||
|
/>
|
||||||
|
</FeatureStrategyEnabled>
|
||||||
|
<StyledHr />
|
||||||
|
<FeatureStrategyTitle
|
||||||
|
title={strategy.title || ''}
|
||||||
|
setTitle={(title) => {
|
||||||
|
setStrategy((prev) => ({
|
||||||
|
...prev,
|
||||||
|
title,
|
||||||
|
}));
|
||||||
|
}}
|
||||||
|
/>
|
||||||
|
<FeatureStrategyType
|
||||||
|
strategy={strategy}
|
||||||
|
strategyDefinition={strategyDefinition}
|
||||||
|
setStrategy={setStrategy}
|
||||||
|
validateParameter={validateParameter}
|
||||||
|
errors={errors}
|
||||||
|
hasAccess={access}
|
||||||
|
/>
|
||||||
|
<FeatureStrategyEnabledDisabled
|
||||||
|
enabled={!strategy?.disabled}
|
||||||
|
onToggleEnabled={() =>
|
||||||
|
setStrategy((strategyState) => ({
|
||||||
|
...strategyState,
|
||||||
|
disabled: !strategyState.disabled,
|
||||||
|
}))
|
||||||
|
}
|
||||||
|
/>
|
||||||
|
</>
|
||||||
|
}
|
||||||
|
/>
|
||||||
|
|
||||||
|
<ConditionallyRender
|
||||||
|
condition={tab === 1}
|
||||||
|
show={
|
||||||
|
<>
|
||||||
|
<FeatureStrategySegment
|
||||||
|
segments={segments}
|
||||||
|
setSegments={setSegments}
|
||||||
|
projectId={projectId}
|
||||||
|
/>
|
||||||
|
<FeatureStrategyConstraints
|
||||||
|
projectId={feature.project}
|
||||||
|
environmentId={environmentId}
|
||||||
|
strategy={strategy}
|
||||||
|
setStrategy={setStrategy}
|
||||||
|
/>
|
||||||
|
</>
|
||||||
|
}
|
||||||
|
/>
|
||||||
|
|
||||||
|
<ConditionallyRender
|
||||||
|
condition={tab === 2}
|
||||||
|
show={
|
||||||
|
<ConditionallyRender
|
||||||
|
condition={
|
||||||
|
strategy.parameters != null &&
|
||||||
|
'stickiness' in strategy.parameters
|
||||||
|
}
|
||||||
|
show={
|
||||||
|
<StrategyVariants
|
||||||
|
strategy={strategy}
|
||||||
|
setStrategy={setStrategy}
|
||||||
|
environment={environmentId}
|
||||||
|
projectId={projectId}
|
||||||
|
/>
|
||||||
|
}
|
||||||
|
/>
|
||||||
|
}
|
||||||
|
/>
|
||||||
|
|
||||||
|
<StyledButtons>
|
||||||
|
<PermissionButton
|
||||||
|
permission={permission}
|
||||||
|
projectId={feature.project}
|
||||||
|
environmentId={environmentId}
|
||||||
|
variant='contained'
|
||||||
|
color='primary'
|
||||||
|
type='submit'
|
||||||
|
disabled={
|
||||||
|
loading ||
|
||||||
|
!hasValidConstraints ||
|
||||||
|
errors.hasFormErrors()
|
||||||
|
}
|
||||||
|
data-testid={STRATEGY_FORM_SUBMIT_ID}
|
||||||
|
>
|
||||||
|
{isChangeRequest
|
||||||
|
? changeRequestButtonText
|
||||||
|
: 'Save strategy'}
|
||||||
|
</PermissionButton>
|
||||||
|
<Button
|
||||||
|
type='button'
|
||||||
|
color='primary'
|
||||||
|
onClick={onCancel ? onCancel : onDefaultCancel}
|
||||||
|
disabled={loading}
|
||||||
|
>
|
||||||
|
Cancel
|
||||||
|
</Button>
|
||||||
|
<FeatureStrategyProdGuard
|
||||||
|
open={showProdGuard}
|
||||||
|
onClose={() => setShowProdGuard(false)}
|
||||||
|
onClick={onSubmit}
|
||||||
|
loading={loading}
|
||||||
|
label='Save strategy'
|
||||||
|
/>
|
||||||
|
</StyledButtons>
|
||||||
|
</StyledForm>
|
||||||
|
);
|
||||||
|
};
|
@ -33,8 +33,10 @@ import { usePlausibleTracker } from 'hooks/usePlausibleTracker';
|
|||||||
import useQueryParams from 'hooks/useQueryParams';
|
import useQueryParams from 'hooks/useQueryParams';
|
||||||
import { useSegments } from 'hooks/api/getters/useSegments/useSegments';
|
import { useSegments } from 'hooks/api/getters/useSegments/useSegments';
|
||||||
import { useDefaultStrategy } from '../../../project/Project/ProjectSettings/ProjectDefaultStrategySettings/ProjectEnvironment/ProjectEnvironmentDefaultStrategy/EditDefaultStrategy';
|
import { useDefaultStrategy } from '../../../project/Project/ProjectSettings/ProjectDefaultStrategySettings/ProjectEnvironment/ProjectEnvironmentDefaultStrategy/EditDefaultStrategy';
|
||||||
|
import { NewFeatureStrategyForm } from 'component/feature/FeatureStrategy/FeatureStrategyForm/NewFeatureStrategyForm';
|
||||||
|
|
||||||
export const NewFeatureStrategyCreate = () => {
|
export const NewFeatureStrategyCreate = () => {
|
||||||
|
const [tab, setTab] = useState(0);
|
||||||
const projectId = useRequiredPathParam('projectId');
|
const projectId = useRequiredPathParam('projectId');
|
||||||
const featureId = useRequiredPathParam('featureId');
|
const featureId = useRequiredPathParam('featureId');
|
||||||
const environmentId = useRequiredQueryParam('environmentId');
|
const environmentId = useRequiredQueryParam('environmentId');
|
||||||
@ -192,8 +194,7 @@ export const NewFeatureStrategyCreate = () => {
|
|||||||
)
|
)
|
||||||
}
|
}
|
||||||
>
|
>
|
||||||
<h1>NEW CREATE FORM</h1>
|
<NewFeatureStrategyForm
|
||||||
<FeatureStrategyForm
|
|
||||||
projectId={projectId}
|
projectId={projectId}
|
||||||
feature={data}
|
feature={data}
|
||||||
strategy={strategy}
|
strategy={strategy}
|
||||||
@ -206,6 +207,8 @@ export const NewFeatureStrategyCreate = () => {
|
|||||||
permission={CREATE_FEATURE_STRATEGY}
|
permission={CREATE_FEATURE_STRATEGY}
|
||||||
errors={errors}
|
errors={errors}
|
||||||
isChangeRequest={isChangeRequestConfigured(environmentId)}
|
isChangeRequest={isChangeRequestConfigured(environmentId)}
|
||||||
|
tab={tab}
|
||||||
|
setTab={setTab}
|
||||||
/>
|
/>
|
||||||
{staleDataNotification}
|
{staleDataNotification}
|
||||||
</FormTemplate>
|
</FormTemplate>
|
||||||
|
@ -28,6 +28,7 @@ import { useChangeRequestsEnabled } from 'hooks/useChangeRequestsEnabled';
|
|||||||
import { useChangeRequestApi } from 'hooks/api/actions/useChangeRequestApi/useChangeRequestApi';
|
import { useChangeRequestApi } from 'hooks/api/actions/useChangeRequestApi/useChangeRequestApi';
|
||||||
import { usePendingChangeRequests } from 'hooks/api/getters/usePendingChangeRequests/usePendingChangeRequests';
|
import { usePendingChangeRequests } from 'hooks/api/getters/usePendingChangeRequests/usePendingChangeRequests';
|
||||||
import { usePlausibleTracker } from 'hooks/usePlausibleTracker';
|
import { usePlausibleTracker } from 'hooks/usePlausibleTracker';
|
||||||
|
import { NewFeatureStrategyForm } from 'component/feature/FeatureStrategy/FeatureStrategyForm/NewFeatureStrategyForm';
|
||||||
|
|
||||||
const useTitleTracking = () => {
|
const useTitleTracking = () => {
|
||||||
const [previousTitle, setPreviousTitle] = useState<string>('');
|
const [previousTitle, setPreviousTitle] = useState<string>('');
|
||||||
@ -80,6 +81,7 @@ export const NewFeatureStrategyEdit = () => {
|
|||||||
const featureId = useRequiredPathParam('featureId');
|
const featureId = useRequiredPathParam('featureId');
|
||||||
const environmentId = useRequiredQueryParam('environmentId');
|
const environmentId = useRequiredQueryParam('environmentId');
|
||||||
const strategyId = useRequiredQueryParam('strategyId');
|
const strategyId = useRequiredQueryParam('strategyId');
|
||||||
|
const [tab, setTab] = useState(0);
|
||||||
|
|
||||||
const [strategy, setStrategy] = useState<Partial<IFeatureStrategy>>({});
|
const [strategy, setStrategy] = useState<Partial<IFeatureStrategy>>({});
|
||||||
const [segments, setSegments] = useState<ISegment[]>([]);
|
const [segments, setSegments] = useState<ISegment[]>([]);
|
||||||
@ -214,8 +216,7 @@ export const NewFeatureStrategyEdit = () => {
|
|||||||
)
|
)
|
||||||
}
|
}
|
||||||
>
|
>
|
||||||
<h1>NEW EDIT FORM</h1>
|
<NewFeatureStrategyForm
|
||||||
<FeatureStrategyForm
|
|
||||||
projectId={projectId}
|
projectId={projectId}
|
||||||
feature={data}
|
feature={data}
|
||||||
strategy={strategy}
|
strategy={strategy}
|
||||||
@ -228,6 +229,8 @@ export const NewFeatureStrategyEdit = () => {
|
|||||||
permission={UPDATE_FEATURE_STRATEGY}
|
permission={UPDATE_FEATURE_STRATEGY}
|
||||||
errors={errors}
|
errors={errors}
|
||||||
isChangeRequest={isChangeRequestConfigured(environmentId)}
|
isChangeRequest={isChangeRequestConfigured(environmentId)}
|
||||||
|
tab={tab}
|
||||||
|
setTab={setTab}
|
||||||
/>
|
/>
|
||||||
{staleDataNotification}
|
{staleDataNotification}
|
||||||
</FormTemplate>
|
</FormTemplate>
|
||||||
|
Loading…
Reference in New Issue
Block a user