Skip to content

Commit

Permalink
fix(form): prevent infinite rerenders when calling useFileUpload's re…
Browse files Browse the repository at this point in the history
…set in useEffect
  • Loading branch information
mlaursen committed Sep 10, 2021
1 parent 4746d26 commit b2875b1
Show file tree
Hide file tree
Showing 2 changed files with 31 additions and 9 deletions.
20 changes: 19 additions & 1 deletion packages/form/src/file-input/__tests__/useFileUpload.tsx
Original file line number Diff line number Diff line change
@@ -1,4 +1,4 @@
import React, { Fragment, ReactElement } from "react";
import React, { Fragment, ReactElement, useEffect } from "react";
import filesize from "filesize";
import {
act,
Expand Down Expand Up @@ -436,6 +436,24 @@ describe("useFileUpload", () => {
expect(() => getAllByRole("listitem")).toThrow();
});

it("should not cause infinite rerenders if the reset function is added to a useEffect's dependency array", () => {
let renders = 0;
function Test(): null {
const { reset } = useFileUpload();
renders += 1;
useEffect(() => {
if (renders < 10) {
reset();
}
}, [reset]);

return null;
}

render(<Test />);
expect(renders).toBe(2);
});

it("should abort any FileReaders when the reset function is called", () => {
const file = new File(["pretend-bytes"], "README.txt");
const { getByLabelText, getByRole } = render(<SingleFileTest />);
Expand Down
20 changes: 12 additions & 8 deletions packages/form/src/file-input/useFileUpload.ts
Original file line number Diff line number Diff line change
Expand Up @@ -188,7 +188,9 @@ export interface FileUploadHookReturnValue<
}

/** @internal */
const DEFAULT_EXTENSIONS = [] as const;
const EMPTY_LIST = [] as const;
/** @internal */
const EMPTY_OBJECT = {} as const;

/**
* This hook is generally used to upload files **to the browser** in different
Expand All @@ -209,7 +211,7 @@ const DEFAULT_EXTENSIONS = [] as const;
*/
export function useFileUpload<E extends HTMLElement, CustomError = never>({
maxFiles = -1,
extensions = DEFAULT_EXTENSIONS,
extensions = EMPTY_LIST,
minFileSize = -1,
maxFileSize = -1,
totalFileSize = -1,
Expand All @@ -228,10 +230,12 @@ export function useFileUpload<E extends HTMLElement, CustomError = never>({
) {
switch (action.type) {
case "reset":
// need to reuse constants so that calling reset doesn't cause an
// infinite loop in an effect
return {
stats: {},
errors: [],
readers: {},
stats: EMPTY_OBJECT,
errors: EMPTY_LIST,
readers: EMPTY_OBJECT,
};
case "remove":
return {
Expand Down Expand Up @@ -337,9 +341,9 @@ export function useFileUpload<E extends HTMLElement, CustomError = never>({
}
},
{
stats: {},
errors: [],
readers: {},
stats: EMPTY_OBJECT,
errors: EMPTY_LIST,
readers: EMPTY_OBJECT,
}
);
const { stats, errors, readers } = state;
Expand Down

0 comments on commit b2875b1

Please sign in to comment.