mirror of
https://github.com/marko-js/marko.git
synced 2025-12-08 19:26:05 +00:00
188 lines
5.1 KiB
JavaScript
188 lines
5.1 KiB
JavaScript
/*
|
|
* Copyright 2011 eBay Software Foundation
|
|
*
|
|
* Licensed under the Apache License, Version 2.0 (the "License");
|
|
* you may not use this file except in compliance with the License.
|
|
* You may obtain a copy of the License at
|
|
*
|
|
* http://www.apache.org/licenses/LICENSE-2.0
|
|
*
|
|
* Unless required by applicable law or agreed to in writing, software
|
|
* distributed under the License is distributed on an "AS IS" BASIS,
|
|
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
|
* See the License for the specific language governing permissions and
|
|
* limitations under the License.
|
|
*/
|
|
'use strict';
|
|
|
|
var taglibLoader = require('../taglib-loader');
|
|
var nodePath = require('path');
|
|
var fs = require('fs');
|
|
var lassoPackageRoot = require('lasso-package-root');
|
|
var resolveFrom = require('resolve-from');
|
|
var scanTagsDir = require('../taglib-loader/scanTagsDir');
|
|
var Taglib = require('../taglib-loader/Taglib');
|
|
var DependencyChain = require('../taglib-loader/DependencyChain');
|
|
|
|
var existsCache = {};
|
|
var findCache = {};
|
|
var excludedDirs = {};
|
|
var excludedPackages = {};
|
|
var taglibsForNodeModulesDirCache = {};
|
|
|
|
/**
|
|
* Reset all internal state to the default state. This
|
|
* was added for testing purposes.
|
|
*/
|
|
function reset() {
|
|
existsCache = {};
|
|
findCache = {};
|
|
excludedDirs = {};
|
|
excludedPackages = {};
|
|
taglibsForNodeModulesDirCache = {};
|
|
}
|
|
|
|
function existsCached(path) {
|
|
var exists = existsCache[path];
|
|
if (exists === undefined) {
|
|
exists = fs.existsSync(path);
|
|
existsCache[path] = exists;
|
|
}
|
|
return exists;
|
|
}
|
|
|
|
function getModuleRootPackage(dirname) {
|
|
try {
|
|
return lassoPackageRoot.getRootPackage(dirname);
|
|
} catch(e) {
|
|
return undefined;
|
|
}
|
|
}
|
|
|
|
function getAllDependencyNames(pkg) {
|
|
var map = {};
|
|
|
|
if (pkg.dependencies) {
|
|
Object.keys(pkg.dependencies).forEach((name) => {
|
|
map[name] = true;
|
|
});
|
|
}
|
|
|
|
if (pkg.peerDependencies) {
|
|
Object.keys(pkg.peerDependencies).forEach((name) => {
|
|
map[name] = true;
|
|
});
|
|
}
|
|
|
|
if (pkg.devDependencies) {
|
|
Object.keys(pkg.devDependencies).forEach((name) => {
|
|
map[name] = true;
|
|
});
|
|
}
|
|
|
|
return Object.keys(map);
|
|
}
|
|
|
|
function find(dirname, registeredTaglibs) {
|
|
var found = findCache[dirname];
|
|
if (found) {
|
|
return found;
|
|
}
|
|
|
|
found = [];
|
|
|
|
var added = {};
|
|
|
|
var helper = {
|
|
alreadyAdded: function(taglibPath) {
|
|
return added.hasOwnProperty(taglibPath);
|
|
},
|
|
addTaglib: function(taglib) {
|
|
if (added[taglib.path]) {
|
|
return;
|
|
}
|
|
|
|
added[taglib.path] = true;
|
|
found.push(taglib);
|
|
},
|
|
foundTaglibPackages: {}
|
|
};
|
|
|
|
var rootDirname = process.cwd(); // Don't search up past this directory
|
|
var rootPkg = getModuleRootPackage(dirname);
|
|
if (rootPkg) {
|
|
rootDirname = rootPkg.__dirname; // Use the package's root directory as the top-level directory
|
|
}
|
|
|
|
|
|
// First walk up the directory tree looking for marko.json files or components/ directories
|
|
let curDirname = dirname;
|
|
while(true) {
|
|
let taglibPath = nodePath.join(curDirname, 'marko.json');
|
|
if (existsCached(taglibPath) && !excludedDirs[curDirname]) {
|
|
let taglib = taglibLoader.load(taglibPath);
|
|
helper.addTaglib(taglib);
|
|
} else {
|
|
let componentPath = nodePath.join(curDirname, 'components');
|
|
if (existsCached(componentPath) && !excludedDirs[curDirname] && !helper.alreadyAdded(componentPath)) {
|
|
let taglib = new Taglib(componentPath);
|
|
scanTagsDir(componentPath, nodePath.dirname(componentPath), './components', taglib, new DependencyChain([componentPath]));
|
|
helper.addTaglib(taglib);
|
|
}
|
|
}
|
|
|
|
if (curDirname === rootDirname) {
|
|
break;
|
|
}
|
|
|
|
let parentDirname = nodePath.dirname(curDirname);
|
|
if (!parentDirname || parentDirname === curDirname) {
|
|
break;
|
|
}
|
|
curDirname = parentDirname;
|
|
}
|
|
|
|
if (rootPkg) {
|
|
// Now look for `marko.json` from installed packages
|
|
getAllDependencyNames(rootPkg).forEach((name) => {
|
|
if (!excludedPackages[name]) {
|
|
let taglibPath;
|
|
try {
|
|
taglibPath = resolveFrom(rootPkg.__dirname, name + '/marko.json');
|
|
} catch(e) {
|
|
// The installed dependency does not export a taglib... skip it
|
|
return;
|
|
}
|
|
|
|
var taglib = taglibLoader.load(taglibPath);
|
|
helper.addTaglib(taglib);
|
|
}
|
|
});
|
|
}
|
|
|
|
found = found.concat(registeredTaglibs);
|
|
|
|
findCache[dirname] = found;
|
|
|
|
return found;
|
|
}
|
|
|
|
function clearCache() {
|
|
existsCache = {};
|
|
findCache = {};
|
|
taglibsForNodeModulesDirCache = {};
|
|
}
|
|
|
|
function excludeDir(dir) {
|
|
excludedDirs[dir] = true;
|
|
}
|
|
|
|
function excludePackage(name) {
|
|
excludedPackages[name] = true;
|
|
}
|
|
|
|
exports.reset = reset;
|
|
exports.find = find;
|
|
exports.clearCache = clearCache;
|
|
exports.excludeDir = excludeDir;
|
|
exports.excludePackage = excludePackage; |