Compare commits

...

7 Commits
0.8.0 ... 0.8.2

Author SHA1 Message Date
fengmk2
c0295ecc77 Release 0.8.2 2014-07-22 01:00:38 +08:00
fengmk2
aaf7f04d08 fix default scope detect 2014-07-22 01:00:22 +08:00
fengmk2
beceac10dc Release 0.8.1 2014-07-21 23:54:45 +08:00
dead_horse
fad58273b6 Merge pull request #377 from cnpm/default-scope
support default @org. close #376
2014-07-21 17:16:21 +08:00
fengmk2
e0361dc1f2 add more test cases 2014-07-21 16:18:28 +08:00
fengmk2
d8c337acc5 support default @org. close #376 2014-07-21 16:13:43 +08:00
dead_horse
9d7683bd61 hotfix redis init error 2014-07-21 14:14:52 +08:00
15 changed files with 249 additions and 89 deletions

View File

@@ -1,4 +1,16 @@
0.8.2 / 2014-07-22
==================
* fix default scope detect
0.8.1 / 2014-07-21
==================
* add more test cases
* support default @org. close #376
* hotfix redis init error
0.8.0 / 2014-07-21
==================

View File

@@ -22,8 +22,7 @@ if (config.redis && config.redis.host && config.redis.port) {
var redis = require('redis');
var wrapper = require('co-redis');
var logger = require('./logger');
var _client = redis.createClient(config.redis);
var _client = redis.createClient(config.redis.port, config.redis.host);
_client.on('error', function (err) {
logger.error(err);

View File

@@ -116,6 +116,7 @@ var config = {
message: 'request frequency limited, any question, please contact fengmk2@gmail.com',
},
enableCompress: false, // enable gzip response or not
defaultScope: '', // default scope name
};
// load config/config.js, everything in config.js will cover the same key in index.js

View File

@@ -46,14 +46,29 @@ var downloadAsReadStream = require('../utils').downloadAsReadStream;
* GET /:name
*/
exports.show = function* (next) {
var name = this.params.name || this.params[0];
var orginalName = this.params.name || this.params[0];
var name = orginalName;
var rs = yield [
Module.getLastModified(name),
Module.listTags(name)
];
var modifiedTime = rs[0];
var tags = rs[1];
debug('show %s, last modified: %s, tags: %j', name, modifiedTime, tags);
var adaptDefaultScope = false;
if (tags.length === 0 && config.defaultScope && name.indexOf(config.defaultScope + '/') === 0) {
// remove default scope name and retry
name = name.split('/')[1];
rs = yield [
Module.getLastModified(name),
Module.listTags(name)
];
modifiedTime = rs[0];
tags = rs[1];
adaptDefaultScope = true;
}
debug('show %s(%s), last modified: %s, tags: %j', name, orginalName, modifiedTime, tags);
if (modifiedTime) {
// find out the latest modfied time
// because update tags only modfied tag, wont change module gmt_modified
@@ -101,8 +116,8 @@ exports.show = function* (next) {
if (unpublishedInfo) {
this.status = 404;
this.body = {
_id: name,
name: name,
_id: orginalName,
name: orginalName,
time: {
modified: unpublishedInfo.package.time,
unpublished: unpublishedInfo.package,
@@ -116,7 +131,7 @@ exports.show = function* (next) {
// if module not exist in this registry,
// sync the module backend and return package info from official registry
if (rows.length === 0) {
if (!this.allowSync) {
if (!this.allowSync || adaptDefaultScope) {
this.status = 404;
this.body = {
error: 'not_found',
@@ -169,6 +184,12 @@ exports.show = function* (next) {
if (!createdTime || t < createdTime) {
createdTime = t;
}
if (adaptDefaultScope) {
// change to orginal name for default scope was removed above
pkg.name = orginalName;
pkg._id = orginalName + '@' + pkg.version;
}
}
if (modifiedTime && createdTime) {
@@ -204,9 +225,9 @@ exports.show = function* (next) {
}
var info = {
_id: name,
_id: orginalName,
_rev: rev,
name: name,
name: orginalName,
description: pkg.description,
"dist-tags": distTags,
maintainers: pkg.maintainers,
@@ -224,7 +245,7 @@ exports.show = function* (next) {
info.bugs = pkg.bugs;
info.license = pkg.license;
debug('show module %s: %s, latest: %s', name, rev, latestMod.version);
debug('show module %s: %s, latest: %s', orginalName, rev, latestMod.version);
this.body = info;
};

View File

@@ -37,7 +37,8 @@ exports.display = function* (next) {
var params = this.params;
// normal: {name: $name, version: $version}
// scope: [$name, $version]
var name = params.name || params[0];
var orginalName = params.name || params[0];
var name = orginalName;
var tag = params.version || params[1];
debug('display %s with %j', name, params);
@@ -51,24 +52,29 @@ exports.display = function* (next) {
getPackageMethod = 'getByTag';
getPackageArgs = [name, tag || 'latest'];
}
var pkg = yield Module[getPackageMethod].apply(Module, getPackageArgs);
if (!pkg && config.defaultScope && name.indexOf(config.defaultScope + '/') === 0) {
name = name.split('/')[1];
pkg = yield Module[getPackageMethod].apply(Module, [name, getPackageArgs[1]]);
}
if (!pkg || !pkg.package) {
return yield* next;
}
var r = yield [
Module[getPackageMethod].apply(Module, getPackageArgs),
down.total(name),
ModuleDeps.list(name),
ModuleStar.listUsers(name),
packageService.listMaintainers(name)
];
var pkg = r[0];
var download = r[1];
var dependents = (r[2] || []).map(function (item) {
var download = r[0];
var dependents = (r[1] || []).map(function (item) {
return item.deps;
});
var users = r[3];
var maintainers = r[4];
if (!pkg || !pkg.package) {
return yield* next;
}
var users = r[2];
var maintainers = r[3];
pkg.package.fromNow = moment(pkg.publish_time).fromNow();
pkg = pkg.package;
@@ -124,6 +130,10 @@ exports.display = function* (next) {
pkg.dist.size = bytes(pkg.dist.size || 0);
}
if (pkg.name !== orginalName) {
pkg.name = orginalName;
}
yield this.render('package', {
title: 'Package - ' + pkg.name,
package: pkg,

View File

@@ -26,7 +26,11 @@ module.exports = function *notFound(next) {
return;
}
var m = /^\/([\w\-\_\.]+)\/?$/.exec(this.url);
var m = /^\/([\w\-\.]+)\/?$/.exec(this.path);
if (!m) {
// scoped packages
m = /^\/(@[\w\-\.]+\/[\w\-\.]+)$/.exec(this.path);
}
debug('%s match %j', this.url, m);
if (m) {
return this.redirect('/package/' + m[1]);

View File

@@ -1,6 +1,6 @@
{
"name": "cnpmjs.org",
"version": "0.8.0",
"version": "0.8.2",
"description": "Private npm registry and web for Enterprise, base on MySQL and Simple Store Service",
"main": "index.js",
"scripts": {

View File

@@ -35,7 +35,7 @@ var fixtures = path.join(path.dirname(path.dirname(__dirname)), 'fixtures');
describe('controllers/registry/module.test.js', function () {
before(function (done) {
app.listen(0, function () {
app = app.listen(0, function () {
done = pedding(2, done);
// name: mk2testmodule
var pkg = utils.getPackage('mk2testmodule', '0.0.1', utils.admin);

View File

@@ -16,6 +16,8 @@
var should = require('should');
var request = require('supertest');
var mm = require('mm');
var config = require('../../../../config');
var app = require('../../../../servers/registry');
var utils = require('../../../utils');
@@ -23,27 +25,31 @@ describe('controllers/registry/module/scope_package.test.js', function () {
var pkgname = '@cnpm/test-scope-package';
var pkgURL = '/@' + encodeURIComponent(pkgname.substring(1));
before(function (done) {
// add scope package
var pkg = utils.getPackage(pkgname, '0.0.1', utils.admin);
app = app.listen(0, function () {
// add scope package
var pkg = utils.getPackage(pkgname, '0.0.1', utils.admin);
request(app.listen())
.put(pkgURL)
.set('authorization', utils.adminAuth)
.send(pkg)
.expect(201, function (err) {
should.not.exist(err);
pkg = utils.getPackage(pkgname, '0.0.2', utils.admin);
// publish 0.0.2
request(app.listen())
request(app)
.put(pkgURL)
.set('authorization', utils.adminAuth)
.send(pkg)
.expect(201, done);
.expect(201, function (err) {
should.not.exist(err);
pkg = utils.getPackage(pkgname, '0.0.2', utils.admin);
// publish 0.0.2
request(app.listen())
.put(pkgURL)
.set('authorization', utils.adminAuth)
.send(pkg)
.expect(201, done);
});
});
});
afterEach(mm.restore);
it('should get scope package info: /@scope%2Fname', function (done) {
request(app.listen())
request(app)
.get(pkgURL)
.expect(200, function (err, res) {
should.not.exist(err);
@@ -75,7 +81,7 @@ describe('controllers/registry/module/scope_package.test.js', function () {
});
it('should get scope package info: /%40scope%2Fname', function (done) {
request(app.listen())
request(app)
.get('/' + encodeURIComponent(pkgname))
.expect(200, function (err, res) {
should.not.exist(err);
@@ -91,7 +97,7 @@ describe('controllers/registry/module/scope_package.test.js', function () {
});
it('should get scope package with version', function (done) {
request(app.listen())
request(app)
.get('/' + pkgname + '/0.0.1')
.expect(200, function (err, res) {
should.not.exist(err);
@@ -105,7 +111,7 @@ describe('controllers/registry/module/scope_package.test.js', function () {
});
it('should get scope package with tag', function (done) {
request(app.listen())
request(app)
.get('/' + pkgname + '/latest')
.expect(200, function (err, res) {
should.not.exist(err);
@@ -117,4 +123,62 @@ describe('controllers/registry/module/scope_package.test.js', function () {
done();
});
});
describe('support defaultScope', function () {
before(function (done) {
var pkg = utils.getPackage('test-default-scope-package', '0.0.1', utils.admin);
request(app)
.put('/' + pkg.name)
.set('authorization', utils.adminAuth)
.send(pkg)
.expect(201, done);
});
it('should adapt /@cnpm/test-default-scope-package => /test-default-scope-package', function (done) {
mm(config, 'defaultScope', '@cnpm');
request(app)
.get('/@cnpm/test-default-scope-package')
.expect(200, function (err, res) {
should.not.exist(err);
var pkg = res.body;
pkg._id.should.equal('@cnpm/test-default-scope-package');
pkg.name.should.equal('@cnpm/test-default-scope-package');
pkg.versions.should.have.keys('0.0.1');
pkg['dist-tags'].latest.should.equal('0.0.1');
pkg.versions['0.0.1'].name.should.equal('@cnpm/test-default-scope-package');
pkg.versions['0.0.1']._id.should.equal('@cnpm/test-default-scope-package@0.0.1');
pkg.versions['0.0.1'].dist.tarball
.should.containEql('/test-default-scope-package/download/test-default-scope-package-0.0.1.tgz');
done();
});
});
it('should not adapt /@cnpm123/test-default-scope-package', function (done) {
mm(config, 'defaultScope', '@cnpm');
request(app)
.get('/@cnpm123/test-default-scope-package')
.expect(404, done);
});
it('should not adapt when defaultScope is empty', function (done) {
mm(config, 'defaultScope', '');
request(app)
.get('/@cnpm/test-default-scope-package')
.expect(404, done);
});
it('should 404 when pkg not exists', function (done) {
mm(config, 'defaultScope', '@cnpm');
request(app)
.get('/@cnpm/test-default-scope-package-not-exists')
.expect(404, done);
});
it('should 404 when scope not match', function (done) {
mm(config, 'defaultScope', '@cnpm123');
request(app)
.get('/@cnpm/test-default-scope-package')
.expect(404, done);
});
});
});

View File

@@ -23,11 +23,7 @@ var mysql = require('../../../common/mysql');
describe('controllers/registry/user.test.js', function () {
before(function (done) {
app.listen(0, done);
});
after(function (done) {
app.close(done);
app = app.listen(0, done);
});
afterEach(mm.restore);

View File

@@ -27,11 +27,6 @@ describe('controllers/total.test.js', function () {
registryApp.listen(0, done);
webApp.listen(0, done);
});
after(function (done) {
done = pedding(2, done);
registryApp.close(done);
webApp.close(done);
});
describe('GET / in registry', function () {
it('should return total info', function (done) {

View File

@@ -23,11 +23,7 @@ var Dist = require('../../../proxy/dist');
describe('controllers/web/dist.test.js', function () {
before(function (done) {
app.listen(0, done);
});
after(function (done) {
app.close(done);
app = app.listen(0, done);
});
afterEach(mm.restore);

View File

@@ -18,31 +18,29 @@ var should = require('should');
var request = require('supertest');
var mm = require('mm');
var path = require('path');
var pedding = require('pedding');
var mysql = require('../../../common/mysql');
var app = require('../../../servers/web');
var registry = require('../../../servers/registry');
var pkg = require('../../../controllers/web/package');
var utils = require('../../utils');
var fixtures = path.join(path.dirname(path.dirname(__dirname)), 'fixtures');
describe('controllers/web/package.test.js', function () {
var baseauth = 'Basic ' + new Buffer('cnpmjstest10:cnpmjstest10').toString('base64');
before(function (done) {
registry.listen(0, function () {
var pkg = require(path.join(fixtures, 'package_and_tgz.json'));
done = pedding(2, done);
registry = registry.listen(0, function () {
// name: mk2testmodule
var pkg = utils.getPackage('mk2testmodule', '0.0.1', utils.admin);
request(registry)
.put('/' + pkg.name)
.set('authorization', baseauth)
.set('authorization', utils.adminAuth)
.send(pkg)
.expect(201, function () {
app.listen(0, done);
});
.end(done);
});
});
after(function (done) {
app.close(done);
app = app.listen(0, done);
});
afterEach(mm.restore);

View File

@@ -16,6 +16,9 @@
var should = require('should');
var request = require('supertest');
var pedding = require('pedding');
var mm = require('mm');
var config = require('../../../../config');
var registry = require('../../../../servers/registry');
var web = require('../../../../servers/web');
var utils = require('../../../utils');
@@ -24,27 +27,32 @@ describe('controllers/web/package/scope_package.test.js', function () {
var pkgname = '@cnpm/test-web-scope-package';
var pkgURL = '/@' + encodeURIComponent(pkgname.substring(1));
before(function (done) {
// add scope package
var pkg = utils.getPackage(pkgname, '0.0.1', utils.admin);
request(registry.listen())
.put(pkgURL)
.set('authorization', utils.adminAuth)
.send(pkg)
.expect(201, function (err) {
should.not.exist(err);
pkg = utils.getPackage(pkgname, '0.0.2', utils.admin);
// publish 0.0.2
request(registry.listen())
done = pedding(2, done);
registry = registry.listen(0, function () {
// add scope package
var pkg = utils.getPackage(pkgname, '0.0.1', utils.admin);
request(registry)
.put(pkgURL)
.set('authorization', utils.adminAuth)
.send(pkg)
.expect(201, done);
.expect(201, function (err) {
should.not.exist(err);
pkg = utils.getPackage(pkgname, '0.0.2', utils.admin);
// publish 0.0.2
request(registry)
.put(pkgURL)
.set('authorization', utils.adminAuth)
.send(pkg)
.expect(201, done);
});
});
web = web.listen(0, done);
});
afterEach(mm.restore);
it('should show scope package info page: /@scope%2Fname', function (done) {
request(web.listen())
request(web)
.get('/package' + pkgURL)
.expect(200, function (err, res) {
should.not.exist(err);
@@ -56,7 +64,7 @@ describe('controllers/web/package/scope_package.test.js', function () {
});
it('should show scope package info page: encodeURIComponent("/@scope/name")', function (done) {
request(web.listen())
request(web)
.get('/package/' + encodeURIComponent(pkgname))
.expect(200, function (err, res) {
should.not.exist(err);
@@ -68,7 +76,7 @@ describe('controllers/web/package/scope_package.test.js', function () {
});
it('should show scope package info page: /@scope/name', function (done) {
request(web.listen())
request(web)
.get('/package/' + pkgname)
.expect(200, function (err, res) {
should.not.exist(err);
@@ -79,14 +87,14 @@ describe('controllers/web/package/scope_package.test.js', function () {
});
});
it('should /@scope/name/ 404', function (done) {
request(web.listen())
it('should /package/@scope/name/ 404', function (done) {
request(web)
.get('/package/' + pkgname + '/')
.expect(404, done);
});
it('should show scope package with version: /@scope/name/0.0.2', function (done) {
request(web.listen())
request(web)
.get('/package/' + pkgname + '/0.0.2')
.expect(200, function (err, res) {
should.not.exist(err);
@@ -96,4 +104,63 @@ describe('controllers/web/package/scope_package.test.js', function () {
done();
});
});
it('should /@scope/name redirect to /package/@scope/name', function (done) {
request(web)
.get('/' + pkgname)
.expect('Location', '/package/' + pkgname)
.expect(302, done);
});
describe('support default scope', function () {
before(function (done) {
var pkg = utils.getPackage('test-default-web-scope-package', '0.0.1', utils.admin);
request(registry)
.put('/' + pkg.name)
.set('authorization', utils.adminAuth)
.send(pkg)
.expect(201, done);
});
it('should adapt /@cnpm/test-default-web-scope-package => /test-default-web-scope-package', function (done) {
mm(config, 'defaultScope', '@cnpm');
request(web)
.get('/package/@cnpm/test-default-web-scope-package')
.expect(200, function (err, res) {
should.not.exist(err);
var body = res.text;
body.should.containEql('@cnpm/test-default-web-scope-package');
body.should.containEql('/test-default-web-scope-package/download/test-default-web-scope-package-0.0.1.tgz');
done();
});
});
it('should not adapt /@cnpm123/test-default-web-scope-package', function (done) {
mm(config, 'defaultScope', '@cnpm');
request(web)
.get('/package/@cnpm123/test-default-web-scope-package')
.expect(404, done);
});
it('should not adapt', function (done) {
mm(config, 'defaultScope', '');
request(web)
.get('/package/@cnpm/test-default-web-scope-package')
.expect(404, done);
});
it('should 404 when scope not match', function (done) {
mm(config, 'defaultScope', '@cnpm123');
request(web)
.get('/package/@cnpm/test-default-web-scope-package')
.expect(404, done);
});
it('should 404 when pkg not exists', function (done) {
mm(config, 'defaultScope', '@cnpm');
request(web)
.get('/package/@cnpm/test-default-web-scope-package-not-exists')
.expect(404, done);
});
});
});

View File

@@ -20,10 +20,7 @@ var app = require('../../../servers/web');
describe('controllers/web/user.test.js', function () {
before(function (done) {
app.listen(0, done);
});
after(function (done) {
app.close(done);
app = app.listen(0, done);
});
describe('GET /~:name', function (done) {