mirror of
https://github.com/Unleash/unleash.git
synced 2026-02-04 20:10:52 +01:00
Group playground context fields into global / project (#11244)
Groups project fields in the playground context selector the same way as in the constraint editor. Uses a similar grouping mechanism as in the editable constraint, but simplifies it because there is no need to handle the "current context field", as this is not an editing operation. Also sorts the data by sortOrder. Updates the playground component by using the shared general select component instead of a custom impl. <img width="887" height="875" alt="image" src="https://github.com/user-attachments/assets/b9d30980-91ab-4eeb-a53c-2cfb9b502f83" />
This commit is contained in:
parent
7adc551d41
commit
36aad2556e
@ -1,24 +1,19 @@
|
||||
import {
|
||||
type Dispatch,
|
||||
type FC,
|
||||
type FormEvent,
|
||||
type SetStateAction,
|
||||
useEffect,
|
||||
useMemo,
|
||||
useState,
|
||||
type VFC,
|
||||
} from 'react';
|
||||
import {
|
||||
Box,
|
||||
Button,
|
||||
FormControl,
|
||||
InputLabel,
|
||||
MenuItem,
|
||||
Select,
|
||||
TextField,
|
||||
Typography,
|
||||
useTheme,
|
||||
Autocomplete,
|
||||
type SelectChangeEvent,
|
||||
Checkbox,
|
||||
} from '@mui/material';
|
||||
|
||||
@ -34,23 +29,81 @@ import {
|
||||
import CheckBoxOutlineBlank from '@mui/icons-material/CheckBoxOutlineBlank';
|
||||
import CheckBoxIcon from '@mui/icons-material/CheckBox';
|
||||
import { useFullUnleashContext } from 'hooks/api/getters/useUnleashContext/useFullUnleashContext.ts';
|
||||
import { useUiFlag } from 'hooks/useUiFlag.ts';
|
||||
import type { IUnleashContextDefinition } from 'interfaces/context.ts';
|
||||
import type {
|
||||
ISelectOption,
|
||||
SelectOptionGroup,
|
||||
} from 'component/common/GeneralSelect/GeneralSelect.tsx';
|
||||
import GeneralSelect from 'component/common/GeneralSelect/GeneralSelect.tsx';
|
||||
|
||||
interface IPlaygroundCodeFieldsetProps {
|
||||
context: string | undefined;
|
||||
setContext: Dispatch<SetStateAction<string | undefined>>;
|
||||
}
|
||||
|
||||
export const PlaygroundCodeFieldset: VFC<IPlaygroundCodeFieldsetProps> = ({
|
||||
const createContextFieldOptions = (
|
||||
context: IUnleashContextDefinition[],
|
||||
{ groupOptions }: { groupOptions: boolean },
|
||||
): ISelectOption[] | SelectOptionGroup[] => {
|
||||
const optList = (opts: { name: string; sortOrder: number }[]) =>
|
||||
opts
|
||||
.toSorted((a, b) => a.sortOrder - b.sortOrder)
|
||||
.map((option) => ({
|
||||
key: option.name,
|
||||
label: option.name,
|
||||
}));
|
||||
|
||||
if (!groupOptions) {
|
||||
return optList(context);
|
||||
}
|
||||
|
||||
const fields = context.reduce(
|
||||
({ project, global }, next) => {
|
||||
if (next.project) {
|
||||
project.push(next);
|
||||
} else {
|
||||
global.push(next);
|
||||
}
|
||||
return { project: project, global: global };
|
||||
},
|
||||
{
|
||||
project: [] as IUnleashContextDefinition[],
|
||||
global: [] as IUnleashContextDefinition[],
|
||||
},
|
||||
);
|
||||
|
||||
const groups: SelectOptionGroup[] = [];
|
||||
|
||||
if (fields.project.length) {
|
||||
groups.push({
|
||||
groupHeader: 'Project context fields',
|
||||
options: optList(fields.project),
|
||||
});
|
||||
}
|
||||
if (fields.global.length) {
|
||||
groups.push({
|
||||
groupHeader: 'Global context fields',
|
||||
options: optList(fields.global),
|
||||
});
|
||||
}
|
||||
|
||||
return groups;
|
||||
};
|
||||
|
||||
export const PlaygroundCodeFieldset: FC<IPlaygroundCodeFieldsetProps> = ({
|
||||
context,
|
||||
setContext,
|
||||
}) => {
|
||||
const theme = useTheme();
|
||||
|
||||
const { setToastData } = useToast();
|
||||
const { context: contextData } = useFullUnleashContext();
|
||||
const contextOptions = contextData
|
||||
.sort((a, b) => a.sortOrder - b.sortOrder)
|
||||
.map(({ name }) => name);
|
||||
|
||||
const groupOptions = useUiFlag('projectContextFields');
|
||||
const contextOptions = createContextFieldOptions(contextData, {
|
||||
groupOptions,
|
||||
});
|
||||
|
||||
const [error, setError] = useState<string>();
|
||||
const [fieldExist, setFieldExist] = useState<boolean>(false);
|
||||
const [contextField, setContextField] = useState<string>('');
|
||||
@ -237,10 +290,10 @@ export const PlaygroundCodeFieldset: VFC<IPlaygroundCodeFieldsetProps> = ({
|
||||
);
|
||||
};
|
||||
|
||||
const changeContextField = (event: SelectChangeEvent) => {
|
||||
setContextField(event.target.value || '');
|
||||
const changeContextField = (value: string) => {
|
||||
setContextField(value || '');
|
||||
|
||||
if (event.target.value === 'currentTime') {
|
||||
if (value === 'currentTime') {
|
||||
return setContextValue(new Date().toISOString());
|
||||
}
|
||||
|
||||
@ -260,27 +313,18 @@ export const PlaygroundCodeFieldset: VFC<IPlaygroundCodeFieldsetProps> = ({
|
||||
</Box>
|
||||
|
||||
<Box sx={{ display: 'flex', gap: 2, flexWrap: 'wrap', mb: 2 }}>
|
||||
<FormControl>
|
||||
<InputLabel id='context-field-label' size='small'>
|
||||
Context field
|
||||
</InputLabel>
|
||||
<Select
|
||||
label='Context field'
|
||||
labelId='context-field-label'
|
||||
id='context-field'
|
||||
value={contextField}
|
||||
onChange={changeContextField}
|
||||
variant='outlined'
|
||||
size='small'
|
||||
sx={{ width: 200, maxWidth: '100%' }}
|
||||
>
|
||||
{contextOptions.map((option) => (
|
||||
<MenuItem key={option} value={option}>
|
||||
{option}
|
||||
</MenuItem>
|
||||
))}
|
||||
</Select>
|
||||
</FormControl>
|
||||
<GeneralSelect
|
||||
label='Context field'
|
||||
labelId='context-field-label'
|
||||
id='context-field'
|
||||
value={contextField}
|
||||
onChange={changeContextField}
|
||||
variant='outlined'
|
||||
size='small'
|
||||
sx={{ width: 200, maxWidth: '100%' }}
|
||||
options={contextOptions}
|
||||
/>
|
||||
|
||||
{resolveInput()}
|
||||
<Button
|
||||
variant='outlined'
|
||||
|
||||
Loading…
Reference in New Issue
Block a user