I am getting the following error while I define the type of file object inside state, Argument of type 'null' is not assignable to parameter of type 'File | (() => File)'.ts
. I am having a upload component, that basically takes care of selecting the file and sending its value to the parent component. I am trying to this in a typescript way and I am unable to get rid of this.
Link to the sandbox: https://codesandbox.io/s/react-hook-upload-oxqdp2?file=/src/Upload.tsx
Upload
import * as React from "react"; import { Button } from "@material-ui/core"; import { useState } from "react"; interface UploaderProps { fileType?: string | AcceptedFileType[]; } enum AcceptedFileType { Text = ".txt", Gif = ".gif", Jpeg = ".jpg", Png = ".png", Doc = ".doc", AllImages = "image/*", AllVideos = "video/*", AllAudios = "audio/*" } export const Upload = (props: UploaderProps): JSX.Element => { const { fileType } = props; const acceptedFormats: string | AcceptedFileType[] = typeof fileType === "string" ? fileType : Array.isArray(fileType) ? fileType?.join(",") : AcceptedFileType.Text; const [selectedFiles, setSelectedFiles] = useState<File>(null); const handleFileSelect = (event: React.ChangeEvent<HTMLInputElement>) => { setSelectedFiles(event?.target?.files?.[0]); }; const onUpload = () => { // eslint-disable-next-line no-console console.log(selectedFiles); }; return ( <> <Button variant="contained" component="label" style={{ textTransform: "none" }} > <input hidden type="file" accept={acceptedFormats} onChange={handleFileSelect} /> <span> Choose file to upload</span> </Button> <Button color="primary" disabled={!selectedFiles} style={{ textTransform: "none" }} onClick={onUpload} > Upload </Button> </> ); };
Can someone help?
Advertisement
Answer
You should probably stick to undefined
:
const [selectedFiles, setSelectedFiles] = useState<File | undefined>(undefined); const handleFileSelect = (event: React.ChangeEvent<HTMLInputElement>) => { setSelectedFiles(event?.target?.files?.[0]); };
This is because when you set it, the value has the type File | undefined
.
This will also force you to check the value before using it, since it could be undefined.
If you know that there will be a file, you can use an assertion with !
:
setSelectedFiles(event?.target?.files?.[0]!);
and maybe keep the type as File | null
, but even then I’d still use File | undefined
because null
is a bit quirky in JavaScript (typeof null === "object'
).