/******************************************************************************* * Copyright (c) 2012 IBM Corporation and others. * All rights reserved. This program and the accompanying materials are made * available under the terms of the Eclipse Public License v1.0 * (http://www.eclipse.org/legal/epl-v10.html), and the Eclipse Distribution * License v1.0 (http://www.eclipse.org/org/documents/edl-v10.html). * * Contributors: * IBM Corporation - initial API and implementation *******************************************************************************/ /*eslint-env node*/ var fs = require('fs'); var nodePath = require('path'); var Promise = require('bluebird'); var mkdirp = require('mkdirp'); var mkdirpAsync = Promise.promisify(mkdirp); /** * @param {Array} argv * @returns {Object} */ exports.parseArgs = function(argv) { argv = argv.slice(2); // skip 'node', 'index.js' var args = {}, match; for (var i=0; i < argv.length; i++) { if ((match = /-(\w+)/.exec(argv[i]))) { var name = match[1], value = argv[i+1]; args[name] = value; } } return args; }; /** * @param {Array} Directories to be created. They're created serially to allow subdirs of an earlier entry to appear later in the list. */ exports.createDirs = function(dirs, callback) { var path = nodePath.join.apply(null, dirs); return mkdirpAsync(path, {}).asCallback(callback); }; /** * @param {Function} callback Invoked as function(password), the password is null if the file couldn't be read. */ exports.readPasswordFile = function(passwordFile, callback) { if (passwordFile) { fs.readFile(passwordFile, function(err, data) { if (err) { throw err; } callback(String.prototype.trim.call(data)); }); } else { callback(null); } }; function parseConfig(err, content) { if (err) { return null; } var lines = content.toString().split(/\r?\n/); var result = {}, current = result; lines.forEach(function(line) { var first = line.trim().charAt(0); if (first === '#' || first === ";") { return; } var parsed = /^\[([^\]]*)\]|([^=]*)(=?)(.*)/.exec(line); if (parsed[1]) { var sectionKey = parsed[1].trim(); var subsection = /([^\s;#]+)\s*"(.*)"/.exec(sectionKey); if (subsection) { sectionKey = subsection[1].trim(); var subsectionKey = subsection[2].trim(); var section = result[sectionKey] = result[sectionKey] || {}; current = section[subsectionKey] = section[subsectionKey] || {}; } else { current = result[sectionKey] = result[sectionKey] || {}; } } else { var name = (parsed[2] || "").trim(); var value = (parsed[4] || "").trim(); if (name !== "") { if (value.charAt(0) === '"') { value = value.substring(1); if (value.charAt(value.length - 1) === '"') value = value.substring(0, value.length - 1); } if (value === "true") value = true; if (value === "false") value = false; if (current[name]) { if (!Array.isArray(current[name])) current[name] = [current[name]]; current[name].push(value); } else { current[name] = value; } } } }); return result; } /** * @param {Function} callback Invoked as function(err, configObject), the err param is not null if the file couldn't be read. */ exports.readConfigFile = function(configFile, callback) { if (!configFile) { return callback(new Error()); } fs.readFile(configFile, function(err, content) { callback(null, parseConfig(err, content)); }); }; /** * @param {Function} callback Invoked as function(err, configObject), the err param is not null if the file couldn't be read. */ exports.readConfigFileSync = function(configFile) { if (!configFile) { return null; } return parseConfig(null, fs.readFileSync(configFile, "utf8")); }; exports.writeConfigFile = function(configFile, contents, callback) { var lines = []; function writeSection(sectionKey, contents) { var sections = []; var sectionLines = []; var indentation = sectionKey ? " " : ""; Object.keys(contents).forEach(function(key) { if (!key) return; if (Array.isArray(contents[key])) { contents[key].forEach(function(k) { sectionLines.push(indentation + key + " = " + k); }); } else if (typeof contents[key] !== "object") { sectionLines.push(indentation + key + " = " + contents[key]); } else { sections.push(key); } }); if (sectionLines.length) { if (sectionKey) { lines.push("[" + sectionKey + "]"); } sectionLines.forEach(function(l) { lines.push(l); }); } sections.forEach(function(key) { var title = key; if (sectionKey) { title = sectionKey + ' "' + title + '"'; } writeSection(title, contents[key]); }); } writeSection("", contents); fs.writeFile(configFile, lines.join("\n"), callback); };