A Feasible Application of Code Coverage in Performance Optimization

What is code coverage


1. Dead code
Dead code is also called useless code. This concept should be statically analyzed code that has no effect on execution at compile time. For example:
// a.js
const a = 1;
const b = 2; /* dead code */
export default a;
// index.js
import a from './a.js';
export default function() {
console.log(a);
}
Usually we use Tree Shaking to remove these dead code at compile time to reduce the code size.
2. Redundant code
The redundant code mentioned in code coverage is slightly different from Dead Code. In short, Dead code applies to compile time, while Code coverage applies to runtime.
Dead code is code that will not be executed under any circumstances, so it can be eliminated in the compilation stage.
Redundant code is that some specific business logic does not execute these code logic (for example: when the first screen is loaded, a front-end component will not be loaded at all, so for the "first screen" business logic use case , the front-end code is redundant)
3. Code coverage
Code coverage is a measure in software testing. That is to describe the proportion of the source code executed during the test (runtime) to the total source code.
How to measure code coverage
1. Chrome Browser Dev Tools
The DevTools of the chrome browser provides us with a tool Coverage to measure the coverage of page code (JS, CSS).
• How to use: Dev tools —— More tools —— Coverage
• Measurable code type: JS CSS
• Statistical visualization:
• The usage rate is calculated in bytes;
• When we select a script resource, we can see the current resource running code (blue) and non-running code (red) when loading the page in the Source column;
• Disadvantage: Obviously, most of the JS scripts on web pages are basically obfuscated, compressed and packaged products. For developers, this coverage has little readability and reference value.

TIPS: Of course, if you have a source map, you can also use the browser to view the coverage of the source code:
1. Find the js resource file of the current page in the source tab (of course it has been obfuscated beyond recognition)
2. Enter the sourcemap URL (take the def publishing platform as an example, which can be found in the build result)
3. You can view the approximate coverage of the corresponding source code in the webpack:// directory (but there is no consumption value)
So the question is, is there a way for developers to understand the value of the code coverage of the source code?
2. Istanbul (NYC)
This software is named after Istanbul, the largest city in Turkey, because Turkish carpets are world-famous, and carpets are used to cover.
Istanbul or NYC (New York City, based on istanbul implementation) is a code coverage tool for measuring JavaScript programs. Currently, most node code testing frameworks use this tool to obtain test reports, which have four measurement dimensions:
line coverage (line coverage - whether each line is executed) [Generally we pay attention to this information]
function coverage (function coverage - whether each function was called)
branch coverage (Branch coverage - whether every if block was executed)
statement coverage (statement coverage - whether each statement was executed)
• Code types that can be measured: JS TS
• Form of statistical visualization:
• HTML
• terminal
• Disadvantage: Currently, there is no non-intrusive solution to use istanbul to measure the JS code coverage on the front-end of the web page. The method is to modify the build result during compilation and build and embed the statistical code, and then perform statistical display at runtime.

We can use the babel-plugin-istanbul plugin to package and rewrite the source code at the AST level. This compilation method is also called code instrumentation / instrumentation (instrument)
3. Instrumentation construction
If we want to measure which code is executed and which code is not executed in this piece of code, what would we do?
// add.js
function add(a, b) {
return a + b
}
module.exports = { add }
We can easily think of adding some "decorative" code to our source code, then when the code is executed line by line somewhere, then we record it in the global environment variable:
// The global object records __coverage__ records the execution times of the statements and functions in the above code
const c = (window.__coverage__ = {
// "f" represents the number of times each function was executed
// The current code has only one function, so the f array has only one and the record value is 0
f: [0],
// "s" represents the number of times each statement was executed
// 3 statements are all assigned 0
s: [0, 0, 0],
})
// function definition is a statement, then we +1
c.s[0]++
function add(a, b) {
// If the add function (function) is called, f +1, and change the call statement s +1
c.f[0]++
c.s[1]++
return a + b
}
// add is called out of statement s +1
c.s[2]++
module.exports = { add }
And istabul does the same. babel-plugin-istanbul analyzes the AST during the construction process and adds the corresponding statistical units (statements, functions, branches, etc.) to the decorative code, and finally outputs a json format after the code runs. data:
{
"/Users/bairuobing/test/istanbul.js":{
"path":"/Users/bairuobing/test/istanbul.js",
"s":{
"1":1,
"2":0,
"3":1
},
"b":{
},
"f":{
"1":0
},
"fnMap":{ // function start and end position information
"1":{
"name":"add",
"line":1,
"loc":{
"start":{
"line":1,
"column":0
},
"end":{
"line":1,
"column":19
}
}
}
},
"statementMap":{ // start and end position information of statement
"1":{
"start":{
"line":1,
"column":0
},
"end":{
"line":3,
"column":1
}
},
"2":{
"start":{
"line":2,
"column":4
},
"end":{
"line":2,
"column":16
}
},
"3":{
"start":{
"line":4,
"column":0
},
"end":{
"line":4,
"column": 24
}
}
},
"branchMap":{ // branch start and end position information
}
}
}
When we run the code, we get the above json and we can consume it.
# terminal form output
nyc report --reporter=text
# HTML format output
nyc report --reporter=lcov --exclude-after-remap=false
• terminal
• HTML

Related Articles

Explore More Special Offers

  1. Short Message Service(SMS) & Mail Service

    50,000 email package starts as low as USD 1.99, 120 short messages start at only USD 1.00