TypeScript React:使用useRef获取表单值

时间:2020-01-30 10:02:21

标签: reactjs typescript

我想将表单中的任何值发布到API,即时通讯使用useRef来获取这样的表单...

  const formElement = useRef<HTMLFormElement>(null);

提交功能

  const submit = async (event: React.FormEvent) => {
    event.preventDefault();
    const body = new URLSearchParams(new FormData(formElement.current)); // <=== error
    const response = await fetch(baseUrl, { body, method: 'post'});
  };

和表格

<form onSubmit={submit} ref={formElement}>
   <input type='text' id='test' value='testValue'/>
</form>

我得到的错误是在控制台中,然后无法编译

Argument of type 'HTMLFormElement | null' is not assignable to parameter of type 'HTMLFormElement | undefined'. Type 'null' is not assignable to type 'HTMLFormElement | undefined'.ts(2345)

整个组件在这里...

     <Poster
        method='post'
        baseUrl='https://api.funge.it/join'
        auth={false}
        keys='email, fullName, password, username'
      />


import React, { useContext, useRef, useState } from 'react';
import { BEARER_TOKEN, Dispatch, Global } from '../globalState';

interface PropsInterface {
  auth: boolean;
  baseUrl: string;
  keys: string;
  method: string;
}

const Poster: React.FC<PropsInterface> = (props: PropsInterface) => {
  const { global } = useContext(Global);
  const { dispatch } = useContext(Dispatch);

  const [state, setState] = useState({
    auth: props.auth,
    baseUrl: props.baseUrl,
    keys: props.keys.split(','),
    method: props.method,
  });
  const { auth, baseUrl, keys, method } = state;
  const { bearer } = global;
  const baseUrlRef = useRef<HTMLInputElement>(null);
  // const formElement = useRef<HTMLFormElement>(null);
  // const formElement = useRef<HTMLFormElement | null>();
  // const formElement = useRef<HTMLFormElement | undefined>();
  const formElement = React.useRef() as React.MutableRefObject<HTMLFormElement>;

  const submit = async (event: React.FormEvent) => {
    event.preventDefault();
    setState((prev) => ({ ...prev, loading: true }));
    const body = new URLSearchParams(new FormData(formElement.current));
    const response = await fetch(baseUrl, { body, method });
    const content = await response.json();
    setState((prev) => ({ ...prev, response, loading: false }));
    if (response.status === 200 && content.jwtToken) {
      dispatch({ type: BEARER_TOKEN, value: content.jwtToken });
    }
  };
  const copy = (event: React.MouseEvent) => {
    event.preventDefault();
    if (baseUrlRef.current) baseUrlRef.current.select();
    document.execCommand('copy');
    const button = event.target as HTMLButtonElement;
    button.focus();
  };

  return (
    <form className='poster' onSubmit={submit} ref={formElement}>
      <div className='poster--where'>
        <div className='poster--where-container-method'>
          <div className='poster--method'>{method}</div>
          <input type='text' value={baseUrl} ref={baseUrlRef} readOnly className='poster--url' />
        </div>
        <div className='poster--where-container-actions'>
          <button className='poster--send'>Send</button>
          <button className='poster--copy' onClick={copy}>
            Copy
          </button>
        </div>
      </div>
      {auth && (
        <div className='poster--auth'>
          <div className='poster--auth-type'>Bearer Token</div>
          <input type='text' value={bearer} readOnly className='poster--url' />
        </div>
      )}
      {keys.map((item, index) => {
        return (
          <div className='poster--keys-values'>
            <div className='poster--key-title'>{item}:</div>
            <input
              type='text'
              id={item}
              key={index}
              className='poster--value-title'
            />
          </div>
        );
      })}
    </form>
  );
};

export { Poster };

UPDATE Natarich J我现在在输入的ref中得到此错误

I so wish it did but i now get an error in the ref part of the input
`Type 'MutableRefObject<HTMLFormElement | undefined>' is not assignable to type 'string | ((instance: HTMLFormElement | null) => void) | RefObject<HTMLFormElement> | null | undefined'.
  Type 'MutableRefObject<HTMLFormElement | undefined>' is not assignable to type 'RefObject<HTMLFormElement>'.
    Types of property 'current' are incompatible.
      Type 'HTMLFormElement | undefined' is not assignable to type 'HTMLFormElement | null'.
        Type 'undefined' is not assignable to type 'HTMLFormElement | null'.ts(2322)
index.d.ts(106, 9): The expected type comes from property 'ref' which is declared here on type 'DetailedHTMLProps<FormHTMLAttributes<HTMLFormElement>, HTMLFormElement>'`

1 个答案:

答案 0 :(得分:1)

错误日志基本上表明存在类型不匹配。可能是因为您将null分配给formElement

由于FormData仅接收HTMLFormElementundefined类型的数据。但是您为null分配了formElement,这表明formElement的类型也为null,这基本上意味着:

typeof formElement                 ===> <HTMLFormElement> || null
typeof data_that_FormData_receives ===> <HTMLFormElement> || undefined

您看到不匹配。因此,可能的解决方案是

# I forgot whether should be '|' or '||', play around with it...

const formElement = useRef<HTMLFormElement || undefined>(); 

告诉我是否可行


更新:

您也不需要new URLSearchParams(),只需这样做

const body = new FormData(formElement.current)