最新消息:雨落星辰是一个专注网站SEO优化、网站SEO诊断、搜索引擎研究、网络营销推广、网站策划运营及站长类的自媒体原创博客

javascript - Using lodash debounce to return a promise - Stack Overflow

programmeradmin1浏览0评论

Using React, react-final-form, and the lodash debounce function I would like to validate that a username has not already been used (the field is using react-final-form).

I'm having problems getting the debounce function to return a resolved promise from a fetch request.

I have provide the following codesandbox link to demonstrate my problem:

Please could anyone show me why my code is not working.

The entry point to the validation is from this.isNameUnique call referenced in the validate attribute in

import React from "react";
import { Field, Form } from "react-final-form";
import { debounce } from "lodash";

class DemoForm extends React.Component {
  getIsNameUnique = name => {
    console.log("getIsNameUnique", name);

    // fake fetch request
    return async name => {
      const asyncResponse = await new Promise(resolve =>
        setTimeout(resolve({ name: true }), 1000)
      );
      console.log("async api response", asyncResponse);
      return asyncResponse;
    };
  };

  debounceCreativeName = name => {
    console.log("debounceCreativeName", name);
    return new Promise(resolve => {
      debounce(() => resolve(this.getIsNameUnique(name)), 2000);
    });
  };

  isNameUnique = async name => {
    const isNameAvailable = await this.debounceCreativeName(name);
    console.log("isNameAvailable", isNameAvailable);
    return isNameAvailable;
  };

  render() {
    return (
      <Form
        onSubmit={() => null}
        render={({ handleSubmit, reset, submitting, pristine, values }) => {
          return (
            <form onSubmit={handleSubmit}>
              <Field name="name" validate={this.isNameUnique}>
                {({ input, meta }) => {
                  return (
                    <input
                      style={{
                        display: "flex",
                        height: "40px",
                        fontSize: "24px"
                      }}
                      autoComplete="off"
                      {...input}
                      type="text"
                      placeholder="Enter the name"
                    />
                  );
                }}
              </Field>
            </form>
          );
        }}
      />
    );
  }
}

export default DemoForm;

Using React, react-final-form, and the lodash debounce function I would like to validate that a username has not already been used (the field is using react-final-form).

I'm having problems getting the debounce function to return a resolved promise from a fetch request.

I have provide the following codesandbox link to demonstrate my problem:

Please could anyone show me why my code is not working.

The entry point to the validation is from this.isNameUnique call referenced in the validate attribute in

import React from "react";
import { Field, Form } from "react-final-form";
import { debounce } from "lodash";

class DemoForm extends React.Component {
  getIsNameUnique = name => {
    console.log("getIsNameUnique", name);

    // fake fetch request
    return async name => {
      const asyncResponse = await new Promise(resolve =>
        setTimeout(resolve({ name: true }), 1000)
      );
      console.log("async api response", asyncResponse);
      return asyncResponse;
    };
  };

  debounceCreativeName = name => {
    console.log("debounceCreativeName", name);
    return new Promise(resolve => {
      debounce(() => resolve(this.getIsNameUnique(name)), 2000);
    });
  };

  isNameUnique = async name => {
    const isNameAvailable = await this.debounceCreativeName(name);
    console.log("isNameAvailable", isNameAvailable);
    return isNameAvailable;
  };

  render() {
    return (
      <Form
        onSubmit={() => null}
        render={({ handleSubmit, reset, submitting, pristine, values }) => {
          return (
            <form onSubmit={handleSubmit}>
              <Field name="name" validate={this.isNameUnique}>
                {({ input, meta }) => {
                  return (
                    <input
                      style={{
                        display: "flex",
                        height: "40px",
                        fontSize: "24px"
                      }}
                      autoComplete="off"
                      {...input}
                      type="text"
                      placeholder="Enter the name"
                    />
                  );
                }}
              </Field>
            </form>
          );
        }}
      />
    );
  }
}

export default DemoForm;

Share Improve this question asked Aug 15, 2019 at 10:41 user2190690user2190690 2,0444 gold badges26 silver badges32 bronze badges 1
  • A solution without lodash - 30secondsofcode/js/s/debounce-promise – Tushar Walzade Commented Jul 22, 2022 at 15:29
Add a ment  | 

1 Answer 1

Reset to default 9

This sandbox fixes your problem.

You should not create a new debounce function on every render with:

return new Promise(resolve => {
  debounce(() => resolve(this.getIsNameUnique(name)), 2000);
});

Instead you should just wrap your whole function isNameUnique with the debounce (see my sandbox). By creating a new debounce function on every hit, it cannot 'remember' that is was called or that is will be called again. This will prevent the debouncing.

Additionally, by making async getIsNameUnique you can reduce the plexity of it be just using await.

发布评论

评论列表(0)

  1. 暂无评论