Simply understand the forth-related modes in JavaScript

The reverse mode refers to a common weak and inefficient design pattern for repeated design problems. As the saying goes, it is to repeat the same mistakes. This article describes some of JavaScript some of the reverse modes, as well as avoiding them.

Hard coded Hard-Coding string, number, date … all can write dead things will be written . This is a well-known anti-model and the most widely used reverse model. The most typical probably a platform-related code in hard coding, which refers to the code that can run normally in a specific machine or environment, which may be only available on your machine, or it is only in Windows. Can be running.

For example, in NPM SCRIPT, write a deadline path / users / hardtle / bin / fis3, which may be very difficult to install, may be to avoid repeated installation, or may be just because it is good. Anyway, this will let all colleagues come to you asked “Why I will report it here”. The solution is to put it in the dependency management. If there is a specific version requirement, you can use the package-lock if you really do it can be deemed to be put on the local configuration file and remove from version control (such as git).

For example, a special folder / TMP, ~ / .cache, or path separator \\ or / is written, for example, in the CLI tool. Such strings can generally be obtained by Node.js built-in modules (or other runtime APIs), such as Os.Homedir, Os.TMPDIR, Path.sep, etc.

Duplicate code

Duplication is especially common in business code, and the original intention is almost stability of the maintenance business. For example: a beautiful search box is required in page A, and there is one in the page B.At this time, the programmer brother faces a difficult choice (if you are directly copied, there will be some uneasy words):

Copy B and change it to a.

Reconstructing the search box in B to C, B, and A reference this code.

Due to time urgent hopes to go to get off work early, or because it is required to be responsible (PM: Let you do A. 啥 B bad? Answer this question is more complicated, here to skip), after passing After a thinking, I decided to take the program 2.
  • The whole story is naturally very smooth, which is probably the reason for repeating code is widely used. There is a few things to question:
  • B is so easy to change, indicating that the author of B does not take into account multiplexing. At this time, the code should not be multiplexed unless it is decided to maintain it.
b Vacted responsibility More than programmer Xiao Ge: B author has a writing test, is the tester regression test B?

Time urgent does not necessarily lead to the emergence of reverse mode, and cannot be used as a convincing reason. Short-term programs also have an elegant implementation.

The solution is to: extract B code reviscated to form a search box component C, use it on a page. At the same time, it is provided to the later partner used, including the authors that urge B are also migrated to C unified maintenance.
  • Fake AMD
  • The modularity is intended to separate the functions of the software into a separate module, each module contains a complete segment function. . In JavaScript, it is specifically designed to divide the script into independent context, which can be reused code unit.
Since JavaScript initially used as a page script, there are many grammar for reference global scope, and many global variables based practices. For example, jQuery’s $, BOM provides Window, omitted VAR to define variables. AMD is JavaScriptEarlier modular specification in the community. This is a gentleman agreement, the problem is here. There are countless ways to write a fake AMD module:

No return value. Yes, what is the side effect. Direct Require after Define. Yes, it is to be executed immediately.

Generate side effects. Modify Window or other shared variables, such as static properties of other modules.

Concentrated problems. Dependency is unknown to cause concurrency problems.

The influence of global side effects is completely equivalent to global variables, almost all of the shortcomings of global variables: execution logic is not easy to understand; implicit coupling relationship; writing test difficulties. Let’s take a specific example:
  • // file: login.jsdefine (‘login “, function () {fetch (‘ / account / login ‘). Then ( x => {window.login = true})}) Require ([‘login’])
  • This AMD module is written directly in one
  • It is accurately that it is more uncontrollable (Requirejs implementation is asynchronous). It is not possible to be used by other modules (such as logging in again) after logging out, because it does not return any interface. In addition, this module has a concurrent problem: Using Window.login to determine if the login is not reliable.
  • The solution is to abstract it as a module, from the outside to control its execution and obtain the login result. In a modular project, all status is eventually generated by the APP portal, and the state between the modules is extracted to the nearest public level.

Define (Function () {Return Fetch (‘/ Account / Login’) .Then (() => true) .catch (e => {console.Error (e) return false}}
Comment Expansion

The original intention of the annotation is to make the reader better understand the code intent, but the practice may just be opposite. Directly lifted an example:

// Judgment the mobile phone Baidu version is greater than 15IF (Navigator.UserageRagent.match (/ chrome: (\ d +)) [1]

Haha Dang, when you read this paragraph, I believe that the above comments have successfully consumed your time. If you see such a comment, it may be incredible, but Most annotations in real projects are this state. Because maintenance code does not necessarily always remember to maintain annotations, and maintenance code is generally more than one person. The sequelae of C language course is not limited to variables, “often write comments” is also a very bad teaching
  The solution is to replace the annotation with a clear logic. The above examples are rewritten as follows:  

IF (Ishttpssupported ()) {/ / By function extraction + name, avoid add notes} function ishttpssupported () {return navigator.USERAGENT.MATCH (/ chrome: (\ d +)) [1]

 "Usually" believes that the expansion of the functional inflation and global variables are the sequelae of the algorithm. But the complex business and algorithms are indeed different, and there are more the former. The concept and operation need to be interpreted and organized. The most effective means of organizing business logic is not too variable naming and method (of course, there must be corresponding closures.Or object).  But in real business maintenance, it is not easy to keep rationality. When you enter the same file to add business logic, your function will be as stinky and long as the wrap of lazy mother: < 15) {
// ...

Function SubmitForm () {var username = $ (‘formin username’). Val () if (username === ‘Harttle’) {username = ‘god’} else {username = ‘Mortal’if ($ ($ “input # words ‘) .val (). INDEXOF (‘ Harttle ‘)) {username =’ prophet ‘}} $ (‘ form “$ (‘Form’). Submit ()}

This is only used, and more than a dozen lines are far from the point of “stinky and long”. However, you can see the modifications of the various purposes allow submitform ()’s duties far more than a form. One possible reconstruction scheme is such:
  Function SubmitForm () {normalize () $ ('form'). Submit ()} function normalize () {var UserName = PARSEUSERNAME ($ ('Form Input # username'). Val (), $ ('Form Input # words'). Val ()) $ ('formin username'). Val (username)}}}}}}}}}}} Username, Words) IF (username=== 'Harttle') {RETURN 'god'} Return Words.indexof ('Harttle')? 'prophet': 'Mortal'} < 15

After reconstruction In the version, we separate the original input resolution, data normalization, etc., these extraction not only makes SubmitForm () more easily, but also makes further expansion business more convenient. For example, in the Normalize () method, check the Input # Password field, such as adding a PARSEWORDS () method to resolve the Input # Words field, etc. Summary

There are many common inverse modes, such as == and! = Use; expand the native object; there is propision related etc. .

== To mention it. This is the language design defect usually uses the LINT tool to avoid use. Unlike other Lint errors, it is very difficult to do with the start of a large area to use (because it is === really does not equivalent). Therefore, it is highly recommended that the project is initialized to add LINT.

There is a very convincing reason behind these anti-models, but the anti-model has a more serious impact on the long-term development of maintainability and software. According to technical debt, each choice of shortcuts will have an implicit price, and these costs are always repayed in the future. Those postponement refactors will not only affect the next change, but they will continue to superimpose interest like economic debt.
While there is no specific assessment method to calculate the debt size, it can be sure that if you can skilled the various reverse models summarized in the Harttle blog, you can meet each code submit debt greater than the benefit. Realm.
 The above is all the content of this article, I hope to help everyone, I hope everyone will support Tumi Cloud.                      
© Copyright Notice
Just support it if you like
comment Grab the couch

Please log in to comment