This time I will bring you a detailed explanation of the practice of the Vue Family Bucket project. What are the precautions for using Vue Family Bucket to implement the project? The following is a practical case, let's take a look.
From a front-end perspective, Vue can be said to be the most ideal front-end MVVM framework at present. Everything serves the interface and is easy to get started. This article will record the reconstruction using Vue Vue-router Vuex. The process of a jQuery template project and what I learned during the process.
getting Started
The official documentation of Vue is the best tutorial for learning Vue. Probably because the author of the framework is from a design background and has no back-end background, various abstract concepts can be explained in the most understandable way in Vue. Here we only briefly introduce the concepts of Vue, Vue-router, and Vuex. For a comprehensive study, it is recommended to go to the official documentation.
Vue
The core function of Vue is two-way binding, which can automatically realize interface-driven data changes and data-driven interface changes, which can greatly reduce the development cost of front-end rich interactive applications. There is more than one similar framework, Vue, but Vue's implementation has certain advantages in performance by leveraging the native features of ES5.
Vue-router
Vue-router is the official route, used to organize the mapping relationship between URLs and components, and automatically respond to changes in URLs to the components, so that developers only need to focus on component development, and routing will help you solve related problems. Trivial questions.
Vuex
Vuex provides a centralized data management model to deal with complex data flow situations. For example, multiple components share data but work independently, which may cause the synchronized data to be out of sync, or due to the Object object# in js. The ## hook points to the same instance in the memory, causing other components to be polluted once the original data is manipulated. At this time, a more organized data operation mode is needed, which is Vuex.
Technical Selection
Comparison with jQuery
After understanding the basic concepts of Vue, I will definitely compare them with the jQuery technology stack unconsciously, wondering whether these things are really necessary for my business. First of all, can the problems solved by MVVM be solved with jQuery? The answer is yes. Do you remember using jQuery to get values from inputs one by one when submitting the form? This is interface-driven data; if you have done any asynchronous interactive functions, you should have experience using jQuery to fill Ajax data into various elements in the interface. This is a data-driven interface. Although it can be done, it is a bit cumbersome. Even if you use a form verification plug-in and a front-end template engine, you still need to manually call the verification method and rendering method on each running node. It is okay to make a website page, but when the requirements are complex to a certain extent, This will be a big burden. Then there is routing. The essence of routing is to achieve interface switching and interface maintenance by operating URLs. It is necessary for single-page applications. This actually has nothing to do with the technology stack. As long as routing requirements are generated, even projects based on jQuery are just recreating a route. That’s it, it’s just that single-page applications are rarely made in the jQuery era. Vuex is completely based on the extension of two-way binding, which is equivalent to adding a broker between the data and the component. The component cannot directly operate the data, but can only submit operation requirements to the broker, and the broker will implement the operation. To solve various unpredictable problems caused by too many people and too many hands, and the data was moved out of the application, a store was specially established to eliminate the problem of data contamination between components. It should be said that jQuery does not have this demand, because jQuery completely operates data manually, and there are no unexpected situations at all.Applicable scene
After comparing with jQuery, the applicable scenarios of Vue are obvious. From a development perspective, projects with more complex interactions are more suitable. Single pages are the most suitable, and content websites are the least suitable. If there are needs for individual pages in the website, they can also be partial. Use, for example, a shopping cart page. Of course, all this must be based on the premise that it is not compatible with IE8. I am a little confused about this, because I saw that some 2C sites are using Vue. How did these front-end ers fool their bosses?Project Analysis
Background of the project
The refactoring project this time is a front-end component management system developed for a previous company. I chose to refactor this project because I am familiar with the requirements. It is a typical single-page application with moderate complexity and is more suitable for use as a hands-on exercise. .
The background of the project is that in outsourcing website building companies, a large number of reusable components are accumulated in the design process. Designers often only need to fine-tune the components to piece together the page and deliver it to the front end. In theory, these components can also be reused in the front end, but in fact the front end The entire page must be re-implemented every time, which wastes a lot of manpower.
Functional Requirements
The idea of this project is to develop all components and input them into a unified platform for management. Designers can go to the platform to select components, and preview and adjust the components in real time. What you see is what you get during the entire process, and the platform will generate an adjustment result. As long as the code is handed over to the front-end, you can use this string of code to reproduce the component modified by the designer on the platform. You can also copy the html/css/js code of the component with one click and quickly apply it to the project. The front-end development cost for the component part is close to zero. The platform needs to implement the following functions:
Manage components, support classification, search, and sorting
Display components, support online preview/editing of components
Component handover, support generation of component codes and Reproduce component
Functional Analysis
The first version was implemented using jQuery template. This technology stack is too flexible. The advantage is that it is easy to do whatever is required. The disadvantage is that it can be done no matter what. It is not conducive to clarifying ideas and is often accompanied by changes while doing it.
Components are uniformly placed in a widgets/ folder, which is called a component library. Because it is a pure front-end project without file operation capabilities, the reading of components relies on a static json file. This file serves as the directory of the component library, which includes components. All information such as categories, tags, names, dates, etc., the data structure is roughly like this:
[{ "title": "导航类", "list": [{ "widget": "bread-1", "title": "图标面包屑", "tag": "面包屑/图标", "author": "UI", "date": "2015-06-04" }, ...] }, ...]
Components are stored in the component library in the form of column/numbered secondary folders, and it is agreed to use the storage directory as the component code. For example, component bread-1 means that the component's storage address is the widgets/bread/1/ folder.
Of course, the internal file structure of the component must also be agreed upon, as follows:
widgets |-bread |-1 |-album.jpg //缩略图 |-config.json //配置文件 |-script.js //脚本模板 |-style.css //样式模板 `-temp.htm //界面模板
With these conventions, the program can obtain the information of all components through directory files, and the acquisition, display, and retrieval of components can also be realized.
The most critical thing in the component is the config.json file, which contains the configurable items of the component and its default values. The platform will read this configuration file when displaying the component and generate a configuration panel based on the configuration information. Here you can Define all variables in the component interface, style, and script. The configuration file probably looks like this:
{ "cssConfig": { "fontSize": { "name": "字号", "value": "12px", "type": "text" }, ... }, "jsConfig": { ... }, "showConfig": { "viewWidth": { "name": "栅格宽度", "value": 12, "type": "number" }, ... } }
The three branches of cssConfig, showConfig, and jsConfig in the configuration file are the collection of all variables that can be modified in the component. If you want to apply these variables to the component, you need to use the front-end template engine, so the three major parts of the component are used during development. The template syntax is written, and after parsing by the template engine, the actual configured html/css/js content can be obtained. For example, the style template may look like this:
.widget-bread-1 { font-size: ${fontSize.value}; color: ${textColor.value}; } .widget-bread-1 a { color: ${textColor.value}; } .widget-bread-1 a:hover{ color:${hoverColor.value}; } .widget-bread-1 .ion { font-size: ${iconSize.value}; margin: 0 ${iconMargin.value}; }
After getting the actual code of the component, just insert the result into the page and update it in time. HTML and CSS can directly replace the text content. Because js is introduced in a modular manner, only the module content will be replaced and the module will not be overloaded. The entire module must be replaced. After the module is renamed, the entire module is replaced, so the name of the js module is random.
There will be a problem here. Some components need to be used multiple times on the page, so the js selector of this component will conflict. This problem can be solved with the help of the random name of the js module. We agree that the id will be used during component development. As a reserved variable, the platform automatically assigns a random string. This string is the same within the component instance and will be different when called multiple times. In this way, as long as ${id} is used as the id or class of the component's parent node, the selector conflict is resolved. Problem, it can also be used as the css namespace of the component, so that possible css naming conflicts can be solved invisible.
The above are the core functions of the project.
In addition, localStorage is used as a storage method to implement data statistics for the stand-alone version. It can collect the component usage records of the current browser and the configuration of each use. This is mainly the operation of local storage, but it is also used for the development of the project itself. When it comes to front-end templates, plus component templates, they will be cached in localStorage after the first load. The caching strategies for these contents are different. User data should be permanently stored, project templates should be manually updated, and component templates need to be determined according to the situation. , if there is too much stored content, it needs to be cleaned. It is unrealistic to delete them one by one during cleaning. Deleting them all may accidentally damage the storage of other applications. The method here is to encapsulate the localStorage operation, and the storage method will be added before the key. When deleting a special prefix, you only need to traverse the locally stored key and determine whether it matches the prefix to know whether it is stored within the application. The corresponding value retrieval method must also add the prefix to the key in reverse and then retrieve the value.
In addition, localStorage only supports string access. In order to facilitate our access to object types, the encapsulation method also supports automatic conversion. However, this conversion cannot blindly convert characters when encountering an object. When the value is matched, it can be converted to an object. The object is automatically transferred, because sometimes the user may actually save an object string and want to get it back as is when taking it out. To solve this problem, you need to make a small hack. When the storage method detects that the value is an object, , will be converted into a string and then an identification string will be spelled in front. The value method will only restore the following string to an object after detecting this identification. Although this method can meet the needs, it is not very safe. Because this prefix is fixed, it is always possible to encounter a lottery winner in theory. I don’t know if there are other better solutions to this problem.
These are the main functional points of the project.
Refactoring
A reconstruction
The first refactoring only used Vue. The first thing I realized during the refactoring process was the various conveniences. What I originally wanted to call the template engine to do was done by the framework. I originally wanted to bind events in js, but now I can do it directly in the template. Bindings, and various other syntactic sugars.
Of course, the most important thing is two-way binding. Based on two-way binding, the interface and data can be automatically associated, making people feel that the program has a certain degree of autonomy. However, in order for this autonomy to operate normally, developers must plan in advance. Every step of the way, this will appear less free than jQuery. Take moving bricks as an example. jQuery is like a particularly flexible crane that can lift bricks with ease and move bricks in a fancy way; Vue is like a universal remote control. You tell it that you want to move bricks from a certain place to a certain place. What happens during the process depends on How to deal with it, the bricks can be moved automatically by pressing the button.
Both methods have their own advantages and disadvantages. If the crane is driven well, it can be very flexible, and it is easy to avoid pits on the road. The disadvantage is that you have to drive it time and time again; the button can be programmed to run automatically at one time, but the disadvantage is that you must set the position on the road in advance. Make on-site inspections, schedule all other cars, and explain all situations clearly, otherwise the car will overturn or crash. When switching from jQuery to Vue, you will definitely feel this sense of restraint, forcing you to "plan before you act." You can't talk about it before getting in the car.
A large part of the work during the reconstruction period is to establish Vue instances, collect data scattered in every corner of js into data, concentrate the process of operating data bit by bit into methods, and concentrate the data filtering process into computed In this whole process, you can clearly review every implementation detail and reflect on whether each implementation method is reasonable. In fact, it is to summarize the original process of driving a crane into remote control buttons one by one. When all the summary is completed, the Vue example It becomes our final project that can run automatically.
After reconstruction, relying on various functions of Vue has reduced the amount of code in the logical part. In addition, there is no improvement to the project itself. Because there is no routing, the problem of losing the status of the page when refreshing still exists; because Vuex is not used, If you encounter a data pollution pit, you can only use deep copy to solve it; and the component-based development model makes the code organization more fragmented. These problems require secondary reconstruction.
Second reconstruction
The goal of the second reconstruction is to improve routing, Vuex, code organization, and Dingo Cloud backend.
Although I have the experience of the first refactoring, I am still a little confused at the beginning of the second refactoring. Which one should be implemented first, routing or Vuex? After thinking about it, what routing does is "tear down", and what Vuex does is "modify". I feel that the workload of dismantling after modification will be smaller, so I use Vuex first.
The concept of Vuex is a bit abstract to understand out of thin air, but once you use it, you feel very comfortable. Moreover, unlike routing, it can be used almost without distinguishing scenarios. After the introduction of Vuex, the problem of data pollution is naturally solved, and Vuex brings action => mutation => store Once the process is accepted, things will really become simpler. The process of introducing Vuex is basically to transfer data to the store and disperse the data operations into actions, getters, and mutations. At the same time, many synchronous data operations are no longer needed, thus making the code The amount has been reduced a bit.
After that, I started to introduce routing. I was not sure how to divide the views at first. The big views must be login, registration, and main interface. The question is whether the main interface needs to be subdivided. In theory, it can be divided very finely, but based on the actual application Usage scenarios found that interface switching is relatively frequent, and frequent loading and unloading of components will cost a lot. Moreover, splitting tightly coupled components into different views requires recording a lot of status information, which is not worth the gain. In the end, we gave up and did not change the main view. Keep dividing. Considering that the access overlap of the three views is not high, it is natural to make the component load asynchronously, and only load the component when it is accessed. Vue itself supports asynchronous components, so this matter becomes very simple, as long as it can return a Promise, you can get components in any way.
Next, we need to access the Wild Dog Cloud to achieve real user management and data statistics. The Wild Dog Cloud can provide a series of functions such as user authentication and data storage. Through it, a complete WEB application can be developed using only js. In this way, all previous operations on localStorage must be changed to operations on Wild Dog Cloud, and the data becomes more reliable when it reaches the cloud.
At this point, the second refactoring is completed. The overall business code feels reduced a lot, but the total code volume is estimated to be not much less. After all, three framework files have been added. However, after many splits, the number of files has dropped from the original three or two js files. It has become about a dozen js, and seajs is used instead of webpack for modularization, because I personally don’t like Webpack still has a wait-and-see attitude, and I don’t feel the need to use it yet. The key is that the code developed based on webpack will be mixed with a lot of private stuff, making your code non-native and unable to run without it. I don’t think so. It’s so acceptable, and in multi-page scenarios, seajs has more advantages than webpack when combined with local caching. Of course, their difference is the same as the difference between jQuery and Vue. They are not the same thing in essence. The key lies in the usage scenario. The one that suits you is the best. of.
Postscript
After two refactoring practices and pitfalls, I have a deeper understanding of the Vue framework. If Vue is to be used flexibly and freely, there is a minimum requirement for developers' project architecture capabilities. If Vue is to be introduced to the bottom layer, the basics There is also a minimum requirement for the planning capabilities of facility builders, which do not exist in the jQuery technology stack. The process of using Vue is also a process of accepting these constraints. They can guide developers to establish their own rule systems. This is a good thing and the general trend. After all, true freedom only exists within rules.
I believe you have mastered the method after reading the case in this article. For more exciting information, please pay attention to other related articles on the php Chinese website!
Recommended reading:
The above is the detailed content of Detailed explanation of Vue family bucket project practice. For more information, please follow other related articles on the PHP Chinese website!