diff --git a/package.json b/package.json index 7f9bf69e016d2327bee9fd1e86f6a335af681de5..d48f3bda3b4538f862b721f763d3ee4065a34654 100644 --- a/package.json +++ b/package.json @@ -2,10 +2,10 @@ "name": "renovate", "description": "Keep npm dependencies up-to-date.", "version": "1.1.0", - "main": "src/index.js", + "main": "renovate.js", "scripts": { "lint": "eslint .", - "start": "node src", + "start": "node renovate", "test": "eslint ." }, "repository": { diff --git a/renovate.js b/renovate.js new file mode 100644 index 0000000000000000000000000000000000000000..e377dc1ac333f639661f57529e91e79c429d6cac --- /dev/null +++ b/renovate.js @@ -0,0 +1,22 @@ +// Initialize config +const config = require('./src/config/parser')(); +// Require main source +const renovate = require('./src')(config); +// Expose logger +const logger = config.logger; + +// Initialize our promise chain +let p = Promise.resolve(); + +// Queue up each repo/package combination +config.repositories.forEach((repo) => { + repo.packageFiles.forEach((packageFile) => { + p = p.then(() => renovate(repo.name, packageFile)); + }); +}); +p.then(() => { // eslint-disable-line promise/always-return + logger.info('Renovate finished'); +}) +.catch((error) => { + logger.error(`Unexpected error: ${error}`); +}); diff --git a/src/defaults.js b/src/config/defaults.js similarity index 100% rename from src/defaults.js rename to src/config/defaults.js diff --git a/src/helpers/config.js b/src/config/parser.js similarity index 97% rename from src/helpers/config.js rename to src/config/parser.js index 30f5148dc38673a34db5f1e413f6dec56e4cfae4..d4747d8ef168e84501f3ee98c915dc519adff2c6 100644 --- a/src/helpers/config.js +++ b/src/config/parser.js @@ -10,7 +10,7 @@ const logger = new (winston.Logger)({ module.exports = function init() { // This function reads in all configs and merges them /* eslint-disable global-require */ - const defaultConfig = require('../defaults'); + const defaultConfig = require('./defaults'); let customConfig = {}; try { customConfig = require('../../config'); diff --git a/src/helpers/github.js b/src/helpers/github.js index 950a9bbbcfe8f301295a8d42fe5481cde8dc338a..5ff9f900060adb84e89fe9527711c5ba0d247314 100644 --- a/src/helpers/github.js +++ b/src/helpers/github.js @@ -3,23 +3,26 @@ const ghGot = require('gh-got'); const config = {}; let logger = null; -module.exports = function github(setLogger) { - logger = setLogger; - this.initRepo = initRepo; +module.exports = { + setLogger, + initRepo, // Package File - this.getPackageFile = getPackageFile; - this.getPackageFileContents = getPackageFileContents; - this.writePackageFile = writePackageFile; + getPackageFile, + getPackageFileContents, + writePackageFile, // Branch - this.createBranch = createBranch; + createBranch, // PR - this.checkForClosedPr = checkForClosedPr; - this.createPr = createPr; - this.getPr = getPr; - this.updatePr = updatePr; - return this; + checkForClosedPr, + createPr, + getPr, + updatePr, }; +function setLogger(l) { + logger = l; +} + // Initialize GitHub by getting base branch and SHA function initRepo(token, repoName) { config.token = token; diff --git a/src/helpers/npm.js b/src/helpers/npm.js index 0249f9186658fb3a7f904b94e2788558e8a820c3..29546c4e256d0726fd32cc212ce64a4455760b6a 100644 --- a/src/helpers/npm.js +++ b/src/helpers/npm.js @@ -4,12 +4,15 @@ const stable = require('semver-stable'); let logger = null; -module.exports = function npm(setLogger) { - logger = setLogger; - this.getAllDependencyUpgrades = getAllDependencyUpgrades; - return this; +module.exports = { + setLogger, + getAllDependencyUpgrades, }; +function setLogger(l) { + logger = l; +} + function getAllDependencyUpgrades(packageContents) { const allDependencyChecks = []; const allDependencyUpgrades = []; @@ -35,6 +38,7 @@ function getAllDependencyUpgrades(packageContents) { currentVersion, upgradeType: upgrade.type, newVersion: upgrade.version, + newVersionMajor: semver.major(upgrade.version), }); }); } else { diff --git a/src/helpers/packageJson.js b/src/helpers/packageJson.js index 411a756e089a4bff05272fae724eda2fb9e02402..f4a62510e3290b9a8ff0eec549f64142f72d42a2 100644 --- a/src/helpers/packageJson.js +++ b/src/helpers/packageJson.js @@ -2,12 +2,15 @@ const _ = require('lodash'); let logger = null; -module.exports = function packageJson(setLogger) { - logger = setLogger; - this.setNewValue = setNewValue; - return this; +module.exports = { + setLogger, + setNewValue, }; +function setLogger(l) { + logger = l; +} + function setNewValue(currentFileContent, depType, depName, newVersion) { logger.debug(`setNewValue: ${depType}.${depName} = ${newVersion}`); const parsedContents = JSON.parse(currentFileContent); diff --git a/src/index.js b/src/index.js index c18ebde782dcd29666bfcd5df5247874f7e9011d..cb60009d096cb3e135ff46a1779b771a7a9743e1 100644 --- a/src/index.js +++ b/src/index.js @@ -1,67 +1,44 @@ -const semver = require('semver'); +const github = require('./helpers/github'); +const npm = require('./helpers/npm'); +const packageJson = require('./helpers/packageJson'); -// Initialize config -const config = require('./helpers/config')(); -// Expose logger -const logger = config.logger; -// Initialize helpers -const github = require('./helpers/github')(logger); -const npm = require('./helpers/npm')(logger); -const packageJson = require('./helpers/packageJson')(logger); +let config = null; +let logger = null; -// Initialize our promise chain -let p = Promise.resolve(); +module.exports = function init(setConfig) { + config = setConfig; + logger = config.logger; -// Queue up each repo/package combination -config.repositories.forEach((repo) => { - repo.packageFiles.forEach((packageFile) => { - p = p.then(() => processRepoPackageFile(repo.name, packageFile)); - }); -}); -p.then(() => { // eslint-disable-line promise/always-return - logger.info('Renovate finished'); -}) -.catch((error) => { - logger.error(`Unexpected error: ${error}`); -}); + // Initialize helpers + github.setLogger(logger); + npm.setLogger(logger); + packageJson.setLogger(logger); + + return processPackageFile; +}; // This function manages the queue per-package file -function processRepoPackageFile(repoName, packageFile) { - return initGitHubRepo(repoName) - .then(() => { // eslint-disable-line arrow-body-style - return packageFile; +function processPackageFile(repoName, packageFile) { + return github.initRepo(config.token, repoName) + .then(() => { + logger.info(`Processing ${repoName} ${packageFile}`); + return github.getPackageFileContents(packageFile); }) - .then(getPackageFileContents) - .then(determineUpgrades) + .then(npm.getAllDependencyUpgrades) .then(processUpgradesSequentially) .then(() => { // eslint-disable-line promise/always-return - logger.info(`Repo ${repoName} ${packageFile} done`); + logger.info(`${repoName} ${packageFile} done`); }) .catch((error) => { logger.error(`renovate caught error: ${error}`); }); } -function initGitHubRepo(repoName) { - logger.info(`Initializing GitHub repo ${repoName}`); - return github.initRepo(config.token, repoName); -} - -function getPackageFileContents(packageFile) { - logger.info(`Getting ${packageFile} contents`); - return github.getPackageFileContents(packageFile); -} - -function determineUpgrades(packageFileContents) { - logger.info('Determining required upgrades'); - return npm.getAllDependencyUpgrades(packageFileContents); -} - function processUpgradesSequentially(upgrades) { if (Object.keys(upgrades).length) { - logger.info('Processing upgrades'); + logger.verbose('Processing upgrades'); } else { - logger.info('No upgrades to process'); + logger.verbose('No upgrades to process'); } logger.verbose(`All upgrades: ${JSON.stringify(upgrades)}`); // We are processing each upgrade sequentially for two major reasons: @@ -71,52 +48,25 @@ function processUpgradesSequentially(upgrades) { (promise, upgrade) => promise.then(() => updateDependency(upgrade)), Promise.resolve()); } -function updateDependency({ upgradeType, depType, depName, currentVersion, newVersion }) { - const newVersionMajor = semver.major(newVersion); - const branchName = config.templates.branchName({ - depType, - depName, - currentVersion, - newVersion, - newVersionMajor, - }); - let prTitle = ''; - if (upgradeType === 'pin') { - prTitle = config.templates.prTitlePin({ - depType, - depName, - currentVersion, - newVersion, - newVersionMajor, - }); - } else if (upgradeType === 'minor') { +function updateDependency(upgrade) { + // Expand upgrade params + const depType = upgrade.depType; + const depName = upgrade.depName; + const newVersion = upgrade.newVersion; + // Use templates to generate strings + const branchName = config.templates.branchName(upgrade); + let prFunction = null; + if (upgrade.upgradeType === 'pin') { + prFunction = config.templates.prTitlePin; + } else if (upgrade.upgradeType === 'minor') { // Use same title for range or minor - prTitle = config.templates.prTitleMinor({ - depType, - depName, - currentVersion, - newVersion, - newVersionMajor, - }); + prFunction = config.templates.prTitleMinor; } else { - prTitle = config.templates.prTitleMajor({ - depType, - depName, - currentVersion, - newVersion, - newVersionMajor, - }); + prFunction = config.templates.prTitleMajor; } - const prBody = config.templates.prBody({ - depName, - currentVersion, - newVersion, - }); - const commitMessage = config.templates.commitMessage({ - depName, - currentVersion, - newVersion, - }); + const prTitle = prFunction(upgrade); + const prBody = config.templates.prBody(upgrade); + const commitMessage = config.templates.commitMessage(upgrade); // Check if same PR already existed and skip if so // This allows users to close an unwanted upgrade PR and not worry about seeing it raised again