useCreatableSelectPersistedBehaviour.ts 1.3 KB

12345678910111213141516171819202122232425262728293031323334353637383940414243444546474849
  1. import { useState } from 'react';
  2. import { SelectableValue } from '@grafana/data';
  3. const hasValue =
  4. <T extends SelectableValue>(searchValue: T['value']) =>
  5. ({ value }: T) =>
  6. value === searchValue;
  7. const getInitialState = (initialOptions: SelectableValue[], initialValue?: string): SelectableValue[] => {
  8. if (initialValue === undefined || initialOptions.some(hasValue(initialValue))) {
  9. return initialOptions;
  10. }
  11. return [
  12. ...initialOptions,
  13. {
  14. value: initialValue,
  15. label: initialValue,
  16. },
  17. ];
  18. };
  19. interface Params {
  20. options: SelectableValue[];
  21. value?: string;
  22. onChange: (s: SelectableValue<string>) => void;
  23. }
  24. /**
  25. * Creates the Props needed by Select to handle custom values and handles custom value creation
  26. * and the initial value when it is not present in the option array.
  27. */
  28. export const useCreatableSelectPersistedBehaviour = ({ options: initialOptions, value, onChange }: Params) => {
  29. const [options, setOptions] = useState(getInitialState(initialOptions, value));
  30. const addOption = (newValue: string) => setOptions([...options, { value: newValue, label: newValue }]);
  31. return {
  32. onCreateOption: (value: string) => {
  33. addOption(value);
  34. onChange({ value });
  35. },
  36. onChange,
  37. allowCustomValue: true,
  38. options,
  39. value,
  40. };
  41. };