diff --git a/README.md b/README.md index 1e2378650..2c59666d9 100644 --- a/README.md +++ b/README.md @@ -1,7 +1,7 @@ cnpmjs.org ======= -[![Build Status](https://secure.travis-ci.org/cnpm/cnpmjs.org.png)](http://travis-ci.org/cnpm/cnpmjs.org) [![Coverage Status](https://coveralls.io/repos/cnpm/cnpmjs.org/badge.png)](https://coveralls.io/r/cnpm/cnpmjs.org)[![Dependency Status](https://gemnasium.com/cnpm/cnpmjs.org.png)](https://gemnasium.com/cnpm/cnpmjs.org) +[![Build Status](https://secure.travis-ci.org/cnpm/cnpmjs.org.png)](http://travis-ci.org/cnpm/cnpmjs.org) [![Coverage Status](https://coveralls.io/repos/cnpm/cnpmjs.org/badge.png)](https://coveralls.io/r/cnpm/cnpmjs.org) [![Dependency Status](https://gemnasium.com/cnpm/cnpmjs.org.png)](https://gemnasium.com/cnpm/cnpmjs.org) [![NPM](https://nodei.co/npm/cnpmjs.org.png?downloads=true&stars=true)](https://nodei.co/npm/cnpmjs.org/) @@ -28,6 +28,11 @@ $ npm install $ node dispatch.js ``` +## Guide + +* [How to deploy cnpmjs.org](https://github.com/cnpm/cnpmjs.org/wiki/Deploy) +* [NFS guide](https://github.com/cnpm/cnpmjs.org/wiki/NFS-Guide) + ## Authors ```bash diff --git a/controllers/registry/module.js b/controllers/registry/module.js index ba8a9d704..46f8123ce 100644 --- a/controllers/registry/module.js +++ b/controllers/registry/module.js @@ -665,12 +665,14 @@ exports.removeWithVersions = function (req, res, next) { var ep = eventproxy.create(); ep.fail(next); + // step1: list all the versions Module.listByName(name, ep.doneLater('list')); ep.once('list', function (mods) { if (!mods || !mods.length) { return next(); } + // step2: check permission var firstMod = mods[0]; if (!common.isMaintainer(req, firstMod.package.maintainers) || firstMod.name !== name) { return res.json(403, { @@ -679,20 +681,78 @@ exports.removeWithVersions = function (req, res, next) { }); } + // step3: calculate which versions need to remove and + // which versions need to remain var removeVersions = []; + var removeVersionMaps = {}; + var remainVersions = []; + for (var i = 0; i < mods.length; i++) { var v = mods[i].version; - if (v !== 'next' && !versions[v]) { + if (v === 'next') { + continue; + } + if (!versions[v]) { removeVersions.push(v); + removeVersionMaps[v] = true; + } else { + remainVersions.push(v); } } + if (!removeVersions.length) { - return res.json(201, {ok: true}); - } - Module.removeByNameAndVersions(name, removeVersions, ep.done(function () { - res.json(201, {ok: true}); + debug('no versions need to remove'); + return res.json(201, { ok: true }); + } + debug('remove versions: %j, remain versions: %j', removeVersions, remainVersions); + + // step 4: remove all the versions which need to remove + Module.removeByNameAndVersions(name, removeVersions, ep.done('removeModules')); + + // step5: list all the tags + Module.listTags(name, ep.done(function (tags) { + var removeTags = []; + var latestRemoved = false; + tags.forEach(function (tag) { + // this tag need be removed + if (removeVersionMaps[tag.version]) { + removeTags.push(tag.id); + if (tag.tag === 'latest') { + latestRemoved = true; + } + } + }); + + if (!removeTags.length) { + debug('no tag need be remove'); + ep.emit('removeTags'); + ep.emit('latest'); + return; + } + + debug('remove tags: %j', removeTags); + // step 6: remove all the tags which need to remove + Module.removeTagsByIds(removeTags, ep.done('removeTags')); + + // step 7: check if latest tag being removed. + // need generate a new latest tag + if (!latestRemoved) { + ep.emit('latest'); + } else { + debug('latest tags removed, generate a new latest tag with new version: %s', + remainVersions[0]); + ep.emit('newLatestVersion', remainVersions[0]); + } })); }); + + ep.all('newLatestVersion', 'removeTags', function (version) { + Module.addTag(name, 'latest', version, ep.done('latest')); + }); + + ep.all('removeModules', 'removeTags', 'latest', function () { + return res.json(201, { ok: true }); + }); }; diff --git a/proxy/module.js b/proxy/module.js index 77cce38ff..fed6ec241 100644 --- a/proxy/module.js +++ b/proxy/module.js @@ -255,7 +255,12 @@ exports.removeTags = function (name, callback) { mysql.query(DELETE_TAGS_SQL, [name], callback); }; -var SELECT_ALL_TAGS_SQL = 'SELECT tag, version, gmt_modified, module_id FROM tag WHERE name=?;'; +var DELETE_TAGS_BY_IDS_SQL = 'DELETE FROM tag WHERE id in (?)'; +exports.removeTagsByIds = function (ids, callback) { + mysql.query(DELETE_TAGS_BY_IDS_SQL, [ids], callback); +}; + +var SELECT_ALL_TAGS_SQL = 'SELECT id, tag, version, gmt_modified, module_id FROM tag WHERE name=?;'; exports.listTags = function (name, callback) { mysql.query(SELECT_ALL_TAGS_SQL, [name], callback);