1

I am using a barcode reader, even though I wait 3 seconds, it sends a lot of requests.

<div id="app">
    <input 
        type="text"
        v-on:keyup="barcode"
    >
</div>

vuejs code:

<script>
    var app = new Vue({
        el: '#app',
        data: {},
        methods: {
            barcode(){
                setTimeout(() => {
                    console.log('number of times executed');
                }, 3000);
            }
        }
    })
</script>

console:

number of times executed                      (17) keyup.html:26:33

I need only once time send a request, for many reasons like error 429 etc.

Thanks for your time!

ErikROCHA
  • 11
  • 3
  • I believe barcode scanners simply insert characters very quickly one after another. Say you have 20 digits. You're invoking your method 20 times after 3 seconds. Error 429 does mean too may requests which makes sense if the endpoint you're calling is sending a too many requests response. What you need is to wait until the last keyup event, then call the api. – Bren Jul 10 '20 at 01:15
  • Check out this https://stackoverflow.com/questions/49711449/how-to-delay-keyup-handler-in-vue-js – Bren Jul 10 '20 at 01:18

1 Answers1

0

Understand What's Happening

  1. A scanner is a peripheral device which functions like a keyboard.
  2. Upon scanning a barcode, the scanner is sending keystrokes in quick succession to your machine.
  3. This causes the method to be called 13 times after the timeout.
  4. Understandably so, the endpoint you are contacting is sending back an error 429 - Too Many Requests.

Solution

  • You need to wait until the last keystroke before contacting your endpoint.
  • Assign a reference to the timeout so that it can be cleared in the next keystroke.
  • Upon the last keystroke, it will timeout and execute your code as intended.
var app = new Vue({
    el: '#app',
    data: {},
    methods: {
        barcode() {
            // We sent a keyup event and a timer is still active
            if(this.timer) {
                // So we clear and null it so it doesn't contact the api
                clearTimeout(this.timer);
                this.timer = null;
            }
            this.timer = setTimeout(() => {
                // contact your endpoint here

                // Assuming your scanner can emit keystrokes
                // within 100 milliseconds from one another
                // otherwise increase this value as necessary
            }, 100);
        }
    }
});
Bren
  • 605
  • 4
  • 15