GoRegexInput.tsx 1.6 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263
  1. import { useRef, useState } from 'react';
  2. import { Input, Typography } from 'antd';
  3. import { HttpUtil } from '@/utils';
  4. interface GoRegexInputProps {
  5. value: string;
  6. ariaLabel?: string;
  7. placeholder?: string;
  8. maxLength?: number;
  9. onChange: (value: string) => void;
  10. externalError?: string;
  11. }
  12. export async function validateGoRegex(value: string): Promise<string> {
  13. const result = await HttpUtil.post(
  14. '/panel/api/setting/validateRegex',
  15. { regex: value },
  16. { silent: true },
  17. );
  18. return result.success ? '' : result.msg || 'Invalid Go RE2 regular expression';
  19. }
  20. export default function GoRegexInput({
  21. value,
  22. ariaLabel,
  23. placeholder,
  24. maxLength = 2048,
  25. onChange,
  26. externalError,
  27. }: GoRegexInputProps) {
  28. const [error, setError] = useState('');
  29. const validationSequence = useRef(0);
  30. async function validate() {
  31. const sequence = ++validationSequence.current;
  32. const nextError = await validateGoRegex(value);
  33. if (sequence === validationSequence.current) {
  34. setError(nextError);
  35. }
  36. }
  37. const displayError = externalError ?? error;
  38. return (
  39. <div style={{ width: '100%' }}>
  40. <Input
  41. value={value}
  42. aria-label={ariaLabel}
  43. placeholder={placeholder}
  44. maxLength={maxLength}
  45. status={displayError ? 'error' : undefined}
  46. onChange={(event) => {
  47. validationSequence.current += 1;
  48. setError('');
  49. onChange(event.target.value);
  50. }}
  51. onBlur={() => void validate()}
  52. />
  53. {displayError && <Typography.Text type="danger">{displayError}</Typography.Text>}
  54. </div>
  55. );
  56. }