Meteor Form Submission


#1

Hello fellow Meteor developers. I am hoping a Meteor guru can please review my code below and verify if I am making proper use of return false and event.preventDefault(), especially in the context of form submission. The reason being, the Meteor docs use this approach:

// Prevent default form submit
return false;

While other tutorials use this approach:

event.preventDefault(); //prevent page reload

So I want to be sure that I am on the correct path before I proceed with the rest of my code.

Basically, my code gets the value of the username input and checks if the value exists in the database:

HTML

<template name="registration">
    <p class="message {{#if message_defined}}display_element{{/if}}">{{message}}</p>
    <form id="register_form">
        <input type="text" name="username" placeholder="username">
    </form>
</template>

JS

if (Meteor.isClient) {
    // This code only runs on the client

    Meteor.subscribe("users");

    Template.registration.helpers({
        message: function () {
            return Session.get("message");
        },
        message_defined: function () {
            return Session.equals("message", undefined) ? false : true;
        }
    });

    Template.registration.events({
        "submit #register_form": function (event) {
            // This function is called when the registration form is submitted.

            event.preventDefault(); // Correct usage?

            var form_data = {
                username: event.target.username.value,
            };

            if (!Match.test(form_data.username, String)) {
                Session.set("message", "username must be a string");
                return false;  // Correct usage?
            } 

            if (form_data.username.length < 6) {
                Session.set("message", "username must be at least 6 characters");
                return false;  // Correct usage?
            }

            Meteor.call("check_username",form_data.username,function(error, result){
                if (error) {
                    Session.set("message", error);
                    return false;  // Correct usage?
                }
                if (result) {
                    Session.set("message", result);
                    return false;  // Correct usage?
                }
            });
        }
    });
}


Meteor.methods({
    check_username: function (username) {
        // If user exists, return error.

        var user = Meteor.users.findOne({username:username});
        if (user) {
            throw new Meteor.Error("username exists", "That username is already in use.");
        }

        return "username not found";
    }
});


if (Meteor.isServer) {
    Meteor.publish("users", function () {
        return Meteor.users.find();  // This publishes everything - be careful!
    });
}

#2

The differences are documented in the docs:

preventDefault()
Prevents the action the browser would normally take in response to this event, such as following a link or submitting a form. Further handlers are still called, but cannot reverse the effect.

[…]

Returning false from a handler is the same as calling both stopImmediatePropagation and preventDefault on the event.


#3

If it works for you then it should be fine. If you get any peculiar unintended behaviour you should read up on event bubbling and propagation to get a better understanding.


#4

My response is going to be a bit controversial, but if you’re having problems with submit and event.preventDefault(), consider forgoing all that together, and submitting your form via a click event on a button instead. Because of how DDP and livedata and minimongo all work, the submit method is a bit… redundant? old-school? unnecessary?

I’ve worked on dozens of apps now and have never needed either submit or event.preventDefault() in them. $0.02


#5

I disagree; submitting a form via a focused <input> (pressing enter on a computer keyboard or “send”-button on a smartphone’s keyboard) element is a nice feature. Of course this is capturable in JavaScript, but it requires extra work.

And what do a web crawlers think about inputs without forms?


#6

TBH I haven’t used a “traditional” form submission for a couple of years now. I’ve used the on click method suggested by @awatson1978 (originally with AJAX, now with DDP).

I do think you may have a point regarding crawlers, but my forms are behind a login and invisible to those, anyway.