Manipulating the DOM is only a simple task in the most primitive situations. As soon as you need to implement a full-fledged (albeit small) application, coding it becomes infinitely more difficult. A dozen handlers is enough to get lost. The complexity of your code grows exponentially with each new event, and there are hundreds of events in real-world applications. Why does this happen?
Although it's not just the frontend part that gets affected by the problem, that's where it reaches its apogee. If you don't pay due attention, the DOM and event-driven architecture create waste no time in making your code confusing. It's clear that the architecture shows up here somewhere, but exactly where and how is another question.
Let's look at proper architecture from the perspective of backend development. As you already know or may have guessed, in terms of backend development, applications consist of at least two parts: a database and the code itself. Forms sent to the server change the application state (i.e., its data), which is stored in the database, then a response in the form of an HTML page is generated based on this state.
In a typical web project, the application does essentially two things: it either updates the data in the database or it extracts that data and generates HTML code based on it. The need for a database is fairly obvious and understandable to everyone, but this isn't the case from the perspective of frontend development. The DOM allows you to store the state internally and, in fact, encourages you to do so. Throughout the course, we'll encounter this situation multiple times when we need to perform actions, and those actions depend on what's currently on the screen. To work with this data, you have to use the DOM.
See the Pen js_dom_state_in_dom by Hexlet (@hexlet) on CodePen.
The main problem with this approach is that there is no single source of truth. One piece of data on one page can be used many times, sometimes in different ways. Imagine a situation where you need to display the number of articles shown on a page. In order to count them, you have to write the following code:
// Each article is designated by the .article class
const articles = document.querySelectorAll('.article');
articles.length; // number of articles
And what if some of the articles are displayed in one block and the rest are displayed in a different one? That'll mean that you'll have to access both of these blocks to collect all the articles. The more we add, the more difficult it gets to add to, update, and use the data. If we look at the code, it's not easy for us to figure out where the data is coming from. In addition, the data are strongly tied to a specific layout structure.
Application state separation
The first step in building a proper architecture is to isolate the data that the application manipulates from the DOM. They need to be separated into a separate variable at the application level (not at the global level! Each instance the application is run must be independent of the others). This will allow you to separate working with the data from displaying it.
If you organize your code in this way, this is what you can expect:
- An event occurs
- The event handler changes the state
- The DOM is updated based on new data
Below is an example of how this idea can be implemented using a simple counter. The state in this case is a single number. The plus button increases it by one, the minus button decreases it by one.
See the Pen js_dom_state_simple by Hexlet (@hexlet) on CodePen.
There are no calls to the DOM to retrieve the current value, it's stored in a variable and is available to all handlers. This sort of organization simplifies not only the storage and handling of data, but also debugging. At any time, you can look inside the state and compare it with what's displayed on the screen. The page itself becomes a reflection of the application state on the screen.
Recommended materials
Are there any more questions? Ask them in the Discussion section.
The Hexlet support team or other students will answer you.
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.