Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Allow using an alternate fs for lookup of sources #68

Closed
wants to merge 8 commits into from
Closed
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
23 changes: 23 additions & 0 deletions .vscode/launch.json
Original file line number Diff line number Diff line change
@@ -0,0 +1,23 @@
{
"version": "0.2.0",
"configurations": [

{
"name": "Run mocha",
"type": "node",
"request": "launch",
"program": "${workspaceRoot}/node_modules/mocha/bin/_mocha",
"stopOnEntry": false,
"args": [
"test/test.js",
"--no-timeouts"
],
"sourceMaps": true,
"cwd": "${workspaceRoot}",
"runtimeExecutable": null,
"env": {
"NODE_ENV": "testing"
}
}
]
}
54 changes: 41 additions & 13 deletions index.js
Original file line number Diff line number Diff line change
Expand Up @@ -45,14 +45,16 @@ const defaultLookups = {
* @param {String} [options.nodeModulesConfig.entry] The new value for "main" in package json
* @param {String} [options.webpackConfig] Path to the webpack config
* @param {Object} [options.ast] A preparsed AST for the file identified by filename.
* @param {Object} [options.tsConfig] Path to a typescript config file
* @param {Object} [options.tsconfig] Path to a typescript config file
* @param {Object} [options.fileSystem] An alternative filesystem / fs implementation to use for locating files.
dazinator marked this conversation as resolved.
Show resolved Hide resolved
*/
module.exports = function cabinet(options) {
const {
partial,
filename,
} = options;

options.fileSystem = options.fileSystem || fs;
debug('Given filename: ' + filename);

const ext = path.extname(filename);
Expand Down Expand Up @@ -123,7 +125,9 @@ module.exports._getJSType = function(options = {}) {
}

debug('using the filename to find the module type');
return getModuleType.sync(options.filename);
// options.fileSystem will be supported after `module-definition` depedendency has this PR merged and is then consumed in package.json:
// https://github.com/dependents/module-definition/pull/28
return getModuleType.sync(options.filename, options);
};

/**
Expand All @@ -137,14 +141,16 @@ module.exports._getJSType = function(options = {}) {
* @param {String} [options.configPath]
* @param {Object} [options.nodeModulesConfig]
* @param {Object} [options.ast]
* @param {Object} [options.fileSystem]
* @return {String}
*/
function jsLookup({dependency, filename, directory, config, webpackConfig, configPath, nodeModulesConfig, ast}) {
function jsLookup({dependency, filename, directory, config, webpackConfig, configPath, nodeModulesConfig, ast, fileSystem}) {
const type = module.exports._getJSType({
config: config,
webpackConfig: webpackConfig,
filename: filename,
ast: ast
ast: ast,
fileSystem: fileSystem
});

switch (type) {
Expand All @@ -160,12 +166,13 @@ function jsLookup({dependency, filename, directory, config, webpackConfig, confi
configPath: configPath,
partial: dependency,
directory: directory,
filename: filename
filename: filename,
fileSystem: fileSystem
});

case 'commonjs':
debug('using commonjs resolver');
return commonJSLookup({dependency, filename, directory, nodeModulesConfig});
return commonJSLookup({dependency, filename, directory, nodeModulesConfig, fileSystem});

case 'webpack':
debug('using webpack resolver for es6');
Expand All @@ -174,11 +181,11 @@ function jsLookup({dependency, filename, directory, config, webpackConfig, confi
case 'es6':
default:
debug('using commonjs resolver for es6');
return commonJSLookup({dependency, filename, directory, nodeModulesConfig});
return commonJSLookup({dependency, filename, directory, nodeModulesConfig, fileSystem});
}
}

function tsLookup({dependency, filename, tsConfig}) {
function tsLookup({dependency, filename, tsConfig, fileSystem}) {
debug('performing a typescript lookup');

const defaultTsConfig = {
Expand All @@ -197,9 +204,8 @@ function tsLookup({dependency, filename, tsConfig}) {

} else if (typeof tsConfig === 'string') {
debug('string tsconfig given, parsing');

try {
tsConfig = JSON.parse(fs.readFileSync(tsConfig, 'utf8'));
tsConfig = JSON.parse(fileSystem.readFileSync(tsConfig, 'utf8'));
debug('successfully parsed tsconfig');
} catch (e) {
debug('could not parse tsconfig');
Expand All @@ -217,7 +223,17 @@ function tsLookup({dependency, filename, tsConfig}) {
options.module = ts.ModuleKind.AMD;
}

const host = ts.createCompilerHost({});
var host = ts.createCompilerHost({});
dazinator marked this conversation as resolved.
Show resolved Hide resolved

// Override host methods, to support finding files in provided fs.
const isDirectory = dirPath => fileSystem.lstatSync(dirPath).isDirectory();
const getDirectories = dirPath => fileSystem.readdirSync(dirPath).map(name => path.join(dirPath, name)).filter(isDirectory);
const pathExists = filePath => fileSystem.existsSync(filePath);

host.getDirectories = getDirectories;
dazinator marked this conversation as resolved.
Show resolved Hide resolved
host.fileExists = pathExists;
host.directoryExists = pathExists;

debug('with options: ', options);

const namedModule = ts.resolveModuleName(dependency, filename, options, host);
Expand All @@ -238,7 +254,7 @@ function tsLookup({dependency, filename, tsConfig}) {
return result ? path.resolve(result) : '';
}

function commonJSLookup({dependency, filename, directory, nodeModulesConfig}) {
function commonJSLookup({dependency, filename, directory, nodeModulesConfig, fileSystem}) {
if (!resolve) {
resolve = require('resolve');
}
Expand Down Expand Up @@ -275,7 +291,19 @@ function commonJSLookup({dependency, filename, directory, nodeModulesConfig}) {
basedir: directory,
packageFilter: nodeModulesConfig && nodeModulesConfig.entry ? packageFilter : undefined,
// Add fileDir to resolve index.js files in that dir
moduleDirectory: ['node_modules', directory]
moduleDirectory: ['node_modules', directory],
readFile: fileSystem.readFile,
isFile: function isFile(file) {
try {
var stat = fileSystem.statSync(file);
} catch (e) {
if (e && (e.code === 'ENOENT' || e.code === 'ENOTDIR')) {
return false;
}
throw e;
}
return stat.isFile() || stat.isFIFO();
}
});
debug('resolved path: ' + result);
} catch (e) {
Expand Down
Loading