Register to get access to free programming courses with interactive exercises

Forms JS: DOM API

There are two approaches to working with forms In modern frontend applications. In some cases, data on the page changes immediately as the form changes. This kind of form doesn't have a “save” or “send” button. Here, each element of the form is associated with a handler that tracks any changes. A typical example could be filtering data on a page.

In a more classic version, the form is sent by button. In this case, you need to use the submit event of the form itself.

const form = document.querySelector(/* form selector */);
form.addEventListener('submit', (e) => {
   // If we want to work with a form via JavaScript, then we need to stop it from sending(default action)
  e.preventDefault();
  // doing something
});

Why not put a click event on the form submit button? Technically, this can be done, but it'll break the standard behavior. Browsers allow you to send forms from the keyboard by pressing the Enter key. In this case, there's no button press, but the form is still built.

Processing the form is usually set up like this (simplified):

  • The data from the form are extracted
  • A request is made to the server / Data in the application are changed
  • The appearance changes

We'll look at the second and third points in future lessons when we talk about AJAX, here we'll talk about the first. How to get the form data.

There are two approaches: the right one and the wrong one. Let's look at the wrong one:

const input = document.querySelector(/* input field selector */);
form.addEventListener('submit', (e) => {
  e.preventDefault();
  const { value } = input;
  // Doing something with the data
});

With this approach, you need to work with each element of the form individually. First extract them from the DOM, then collect the values. There's no need to do this, however; you can do it the right way instead.

The correct way is to use a special FormData object, which is available in the browser:

<form method="post">
  <input name="email" value="example@example.com">
  <input name="password" value="supersecret">
  <input type="submit" value="Sign Up">
</form>
const form = document.querySelector(/* the required form's selector */);
form.addEventListener('submit', (e) => {
  e.preventDefault();
  // The form data are extracted from DOM automatically 
  // A form element taken from the event is passed to the input
  const formData = new FormData(e.target);
  // Now you can work with them 
  formData.get('email'); // example@example.com
  // values() returns an iterator, so we convert it to an array
  [...formData.values()]; // ['example@example.com', 'supersecret']
  // Also an iterator
  [...formData.entries()];
  // [['email', 'example@example.com'], ['password', 'supersecret']]

  // Conversion to a regular object
  Object.fromEntries(formData);
  // { email: 'example@example.com', password: 'supersecret' }
});

Extracting form elements

Sometimes, however, you have to access the form elements directly. For example, when implementing validation while changing the form, rather than when sending it. In such cases, work with the elements of the form goes directly:

const input = document.querySelector(/* selector before the input field */);
input.addEventListener('change', (e) => {
  // Logic
});

If there are a lot of elements, then the code executing queries in the DOM will get cumbersome. This can be avoided by using the DOM features that related to forms. Each form contains the elements property, which returns an object with all the elements of that form. The object keys are the names of the elements, and the values are the elements themselves.

<form method="post">
  <input name="email" value="example@example.com">
  <input name="password" value="supersecret">
  <input type="submit" value="Sign Up">
</form>
const form = document.querySelector(/* selector to form */);
form.elements.email // <input name="email" ...
form.elements.password // <input name="password" ...

// Processing
form.elements.email.addEventListener('change', () => {
  // Processing
});

Hexlet Experts

Are there any more questions? Ask them in the Discussion section.

The Hexlet support team or other students will answer you.

About Hexlet learning process

For full access to the course you need a professional subscription.

A professional subscription will give you full access to all Hexlet courses, projects and lifetime access to the theory of lessons learned. You can cancel your subscription at any time.

Get access
130
courses
1000
exercises
2000+
hours of theory
3200
tests

Sign up

Programming courses for beginners and experienced developers. Start training for free

  • 130 courses, 2000+ hours of theory
  • 1000 practical tasks in a browser
  • 360 000 students
By sending this form, you agree to our Personal Policy and Service Conditions

Our graduates work in companies:

<span class="translation_missing" title="translation missing: en.web.courses.lessons.registration.bookmate">Bookmate</span>
<span class="translation_missing" title="translation missing: en.web.courses.lessons.registration.healthsamurai">Healthsamurai</span>
<span class="translation_missing" title="translation missing: en.web.courses.lessons.registration.dualboot">Dualboot</span>
<span class="translation_missing" title="translation missing: en.web.courses.lessons.registration.abbyy">Abbyy</span>
Suggested learning programs

From a novice to a developer. Get a job or your money back!

Frontend Developer icon
Profession
beginner
Development of front-end components for web applications
start anytime 10 months

Use Hexlet to the fullest extent!

  • Ask questions about the lesson
  • Test your knowledge in quizzes
  • Practice in your browser
  • Track your progress

Sign up or sign in

By sending this form, you agree to our Personal Policy and Service Conditions
Toto Image

Ask questions if you want to discuss a theory or an exercise. Hexlet Support Team and experienced community members can help find answers and solve a problem.