Skip to content

Commit 2d33fdf

Browse files
Roland Grozarolandjitsu
authored andcommitted
fix: apply custom validator on {isDragAccept,isDragReject}
1 parent 1b91e50 commit 2d33fdf

File tree

4 files changed

+64
-3
lines changed

4 files changed

+64
-3
lines changed

src/index.js

Lines changed: 4 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -258,9 +258,9 @@ Dropzone.propTypes = {
258258
onError: PropTypes.func,
259259

260260
/**
261-
* Custom validation function
261+
* Custom validation function. It must return null if there's no errors.
262262
* @param {File} file
263-
* @returns {FileError|FileError[]}
263+
* @returns {FileError|FileError[]|null}
264264
*/
265265
validator: PropTypes.func,
266266
};
@@ -577,6 +577,7 @@ export function useDropzone(props = {}) {
577577
maxSize,
578578
multiple,
579579
maxFiles,
580+
validator,
580581
});
581582
const isDragReject = fileCount > 0 && !isDragAccept;
582583

@@ -604,6 +605,7 @@ export function useDropzone(props = {}) {
604605
maxSize,
605606
multiple,
606607
maxFiles,
608+
validator,
607609
]
608610
);
609611

src/index.spec.js

Lines changed: 28 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -3441,6 +3441,34 @@ describe("useDropzone() hook", () => {
34413441
expect.anything()
34423442
);
34433443
});
3444+
3445+
it("sets {isDragAccept, isDragReject}", async () => {
3446+
const data = createDtWithFiles(images);
3447+
const validator = () => ({
3448+
code: "not-allowed",
3449+
message: "Cannot do this!",
3450+
});
3451+
3452+
const ui = (
3453+
<Dropzone validator={validator} multiple={true}>
3454+
{({ getRootProps, getInputProps, isDragAccept, isDragReject }) => (
3455+
<div {...getRootProps()}>
3456+
<input {...getInputProps()} />
3457+
{isDragAccept && "dragAccept"}
3458+
{isDragReject && "dragReject"}
3459+
</div>
3460+
)}
3461+
</Dropzone>
3462+
);
3463+
3464+
const { container } = render(ui);
3465+
const dropzone = container.querySelector("div");
3466+
3467+
await act(() => fireEvent.dragEnter(dropzone, data));
3468+
3469+
expect(dropzone).not.toHaveTextContent("dragAccept");
3470+
expect(dropzone).toHaveTextContent("dragReject");
3471+
});
34443472
});
34453473

34463474
describe("accessibility", () => {

src/utils/index.js

Lines changed: 25 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -76,13 +76,26 @@ function isDefined(value) {
7676
return value !== undefined && value !== null;
7777
}
7878

79+
/**
80+
*
81+
* @param {object} options
82+
* @param {File[]} options.files
83+
* @param {string|string[]} [options.accept]
84+
* @param {number} [options.minSize]
85+
* @param {number} [options.maxSize]
86+
* @param {boolean} [options.multiple]
87+
* @param {number} [options.maxFiles]
88+
* @param {(f: File) => FileError|FileError[]|null} [options.validator]
89+
* @returns
90+
*/
7991
export function allFilesAccepted({
8092
files,
8193
accept,
8294
minSize,
8395
maxSize,
8496
multiple,
8597
maxFiles,
98+
validator,
8699
}) {
87100
if (
88101
(!multiple && files.length > 1) ||
@@ -94,7 +107,8 @@ export function allFilesAccepted({
94107
return files.every((file) => {
95108
const [accepted] = fileAccepted(file, accept);
96109
const [sizeMatch] = fileMatchSize(file, minSize, maxSize);
97-
return accepted && sizeMatch;
110+
const customErrors = validator ? validator(file) : null;
111+
return accepted && sizeMatch && !customErrors;
98112
});
99113
}
100114

@@ -287,3 +301,13 @@ export function isExt(v) {
287301
/**
288302
* @typedef {Object.<string, string[]>} AcceptProp
289303
*/
304+
305+
/**
306+
* @typedef {object} FileError
307+
* @property {string} message
308+
* @property {ErrorCode|string} code
309+
*/
310+
311+
/**
312+
* @typedef {"file-invalid-type"|"file-too-large"|"file-too-small"|"too-many-files"} ErrorCode
313+
*/

src/utils/index.spec.js

Lines changed: 7 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -344,6 +344,13 @@ describe("allFilesAccepted()", () => {
344344
expect(
345345
utils.allFilesAccepted({ files, multiple: true, maxFiles: 1 })
346346
).toEqual(false);
347+
348+
expect(
349+
utils.allFilesAccepted({
350+
files,
351+
validator: () => ({ code: "not-allowed", message: "Cannot do this!" }),
352+
})
353+
).toEqual(false);
347354
});
348355
});
349356

0 commit comments

Comments
 (0)