Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
24 changes: 18 additions & 6 deletions packages/middleware-code-coverage/lib/middleware.js
Original file line number Diff line number Diff line change
Expand Up @@ -3,7 +3,9 @@ import {
createInstrumentationConfig,
shouldInstrumentResource,
getLatestSourceMap,
readJsonFile} from "./util.js";
readJsonFile,
getLibraryCoverageExcludePatterns
} from "./util.js";
import {createInstrumenter} from "istanbul-lib-instrument";
import reportCoverage from "./coverage-reporter.js";
import bodyParser from "body-parser";
Expand Down Expand Up @@ -33,10 +35,7 @@ import {promisify} from "node:util";
* @returns {Function} Middleware function to use
*/
export default async function({log, middlewareUtil, options={}, resources}) {
const config = await createInstrumentationConfig(
options.configuration,
resources.all
);
const config = await createInstrumentationConfig(options.configuration);
const {
report: reporterConfig,
instrument: instrumenterConfig,
Expand Down Expand Up @@ -104,9 +103,22 @@ export default async function({log, middlewareUtil, options={}, resources}) {
)
);

let excludePatterns;

router.use(async (req, res, next) => {
// Lazy initialize exclude patterns
if (excludePatterns === undefined) {
// Custom patterns take precedence over .library defined patterns (also when set to null)
if (generalConfig.excludePatterns !== undefined) {
excludePatterns = generalConfig.excludePatterns;
} else {
// Read patterns from .library files, this should only be done if needed and only once
excludePatterns = await getLibraryCoverageExcludePatterns(resources.all);
}
}

// Skip files which should not be instrumented
if (!shouldInstrumentResource(req, generalConfig)) {
if (!shouldInstrumentResource(req, excludePatterns)) {
next();
return;
}
Expand Down
21 changes: 9 additions & 12 deletions packages/middleware-code-coverage/lib/util.js
Original file line number Diff line number Diff line change
Expand Up @@ -7,18 +7,15 @@ import {readFile} from "node:fs/promises";
*
* @public
* @param {object} configuration instrumentation configuration
* @param {@ui5/fs/Resource[]} resources
* @returns {Promise<object>} configuration
*/
export async function createInstrumentationConfig(configuration = {}, resources) {
const excludedPatterns = resources ? await excludePatterns(resources) : [];

export async function createInstrumentationConfig(configuration = {}) {
const {instrument, report, ...generalConfig} = configuration;

return {
// General configuration
cwd: "./",
excludePatterns: excludedPatterns,

// General config overwrites
...generalConfig,

Expand Down Expand Up @@ -55,17 +52,17 @@ export function getLatestSourceMap(instrumenter) {
*
* @public
* @param {object} request
* @param {object} config
* @param {Array<RegExp|string>} excludePatterns Patterns to exclude file from instrumentation (RegExp or string)
* @returns {boolean}
*/
export function shouldInstrumentResource(request, config) {
export function shouldInstrumentResource(request, excludePatterns) {
return (
request.path &&
request.path.endsWith(".js") && // Only .js file requests
!isFalsyValue(request.query.instrument) && // instrument only flagged files, ignore "falsy" values
!(config && config.excludePatterns || []).some((pattern) => {
!(excludePatterns || []).some((pattern) => {
if (pattern instanceof RegExp) {
// The ones comming from .library files are regular expressions
// The ones coming from .library files are regular expressions
return pattern.test(request.path);
} else {
return request.path.includes(pattern);
Expand Down Expand Up @@ -131,13 +128,13 @@ function isFalsyValue(value) {
* Note: We might consider to move this utility into the @ui5/project
*
* @private
* @param {@ui5/fs/Resource[]} resources
* @param {@ui5/fs/AbstractReader} reader
* @returns {Promise<RegExp[]>} exclude patterns
*/
async function excludePatterns(resources) {
export async function getLibraryCoverageExcludePatterns(reader) {
const aExcludes = [];
// Read excludes from .library files
const aDotLibrary = await resources.byGlob(["/resources/**/.library"]);
const aDotLibrary = await reader.byGlob(["/resources/**/.library"]);
for (const oDotLibrary of aDotLibrary) {
const content = await oDotLibrary.getString();
const result = await xml2js.parseStringPromise(content);
Expand Down
Loading