AbsolutePaths: written findEtherpadRoot()

This is just a function (with an ugly side effect for caching purposes) that
heuristically tries to compute the Etherpad installation path when running under
Unix and win32 (they have different file system layouts).

This path can be used by Etherpad as a base for all the relative paths, in order
to be deterministic and not depending on cwd.
pull/3473/head
muxator 2018-08-22 00:38:13 +02:00 committed by muxator
parent cbce3c1b08
commit b1a0e14ee2
2 changed files with 66 additions and 0 deletions

View File

@ -19,10 +19,17 @@
*/
var log4js = require('log4js');
var path = require('path');
var _ = require('underscore');
var absPathLogger = log4js.getLogger('AbsolutePaths');
/*
* findEtherpadRoot() computes its value only on first invocation.
* Subsequent invocations are served from this variable.
*/
var etherpadRoot = null;
/**
* If stringArray's last elements are exactly equal to lastDesiredElements,
* returns a copy in which those last elements are popped, or false otherwise.
@ -49,3 +56,61 @@ var popIfEndsWith = function(stringArray, lastDesiredElements) {
absPathLogger.debug(`${stringArray.join(path.sep)} does not end with "${lastDesiredElements.join(path.sep)}"`);
return false;
};
/**
* Heuristically computes the directory in which Etherpad is installed.
*
* All the relative paths have to be interpreted against this absolute base
* path. Since the Unix and Windows install have a different layout on disk,
* they are treated as two special cases.
*
* The path is computed only on first invocation. Subsequent invocations return
* a cached value.
*
* The cached value is stored in AbsolutePaths.etherpadRoot via a side effect.
*
* @return {string} The identified absolute base path. If such path cannot be
* identified, prints a log and exits the application.
*/
exports.findEtherpadRoot = function() {
if (etherpadRoot !== null) {
return etherpadRoot;
}
const findRoot = require('find-root');
const foundRoot = findRoot(__dirname);
var directoriesToStrip;
if (process.platform === 'win32') {
/*
* Given the structure of our Windows package, foundRoot's value
* will be the following on win32:
*
* <BASE_DIR>\node_modules\ep_etherpad-lite
*/
directoriesToStrip = ['node_modules', 'ep_etherpad-lite'];
} else {
/*
* On Unix platforms, foundRoot's value will be:
*
* <BASE_DIR>\src
*/
directoriesToStrip = ['src'];
}
const maybeEtherpadRoot = popIfEndsWith(foundRoot.split(path.sep), directoriesToStrip);
if (maybeEtherpadRoot === false) {
absPathLogger.error(`Could not identity Etherpad base path in this ${process.platform} installation in "${foundRoot}"`);
process.exit(1);
}
// SIDE EFFECT on this module-level variable
etherpadRoot = maybeEtherpadRoot.join(path.sep);
if (path.isAbsolute(etherpadRoot)) {
return etherpadRoot;
}
absPathLogger.error(`To run, Etherpad has to identify an absolute base path. This is not: "${etherpadRoot}"`);
process.exit(1);
};

View File

@ -38,6 +38,7 @@
"etherpad-yajsml": "0.0.2",
"express": "4.16.3",
"express-session": "1.15.6",
"find-root": "1.1.0",
"formidable": "1.2.1",
"graceful-fs": "4.1.3",
"jsonminify": "0.4.1",