mirror of
https://github.com/verdaccio/verdaccio.git
synced 2025-02-17 23:45:29 -05:00
feat: ability to restrict unpublish action to certain users #492
This is a PoC, it needs refactor and unit testing
This commit is contained in:
parent
10370c6eeb
commit
ef503257f3
5 changed files with 37 additions and 2 deletions
|
@ -44,6 +44,7 @@ packages:
|
||||||
# scoped packages
|
# scoped packages
|
||||||
access: $all
|
access: $all
|
||||||
publish: $authenticated
|
publish: $authenticated
|
||||||
|
unpublish: $authenticated
|
||||||
proxy: npmjs
|
proxy: npmjs
|
||||||
|
|
||||||
'**':
|
'**':
|
||||||
|
@ -58,6 +59,8 @@ packages:
|
||||||
# (anyone can register by default, remember?)
|
# (anyone can register by default, remember?)
|
||||||
publish: $authenticated
|
publish: $authenticated
|
||||||
|
|
||||||
|
unpublish: $authenticated
|
||||||
|
|
||||||
# if package is not available locally, proxy requests to 'npmjs' registry
|
# if package is not available locally, proxy requests to 'npmjs' registry
|
||||||
proxy: npmjs
|
proxy: npmjs
|
||||||
|
|
||||||
|
|
|
@ -24,10 +24,10 @@ export default function publish(router: Router, auth: IAuth, storage: IStorageHa
|
||||||
router.put('/:package/:_rev?/:revision?', can('publish'), media(mime.getType('json')), expectJson, publishPackage(storage, config));
|
router.put('/:package/:_rev?/:revision?', can('publish'), media(mime.getType('json')), expectJson, publishPackage(storage, config));
|
||||||
|
|
||||||
// un-publishing an entire package
|
// un-publishing an entire package
|
||||||
router.delete('/:package/-rev/*', can('publish'), unPublishPackage(storage));
|
router.delete('/:package/-rev/*', can('unpublish'), can('publish'), unPublishPackage(storage));
|
||||||
|
|
||||||
// removing a tarball
|
// removing a tarball
|
||||||
router.delete('/:package/-/:filename/-rev/:revision', can('publish'), removeTarball(storage));
|
router.delete('/:package/-/:filename/-rev/:revision', can('unpublish'), can('publish'), removeTarball(storage));
|
||||||
|
|
||||||
// uploading package tarball
|
// uploading package tarball
|
||||||
router.put('/:package/-/:filename/*', can('publish'), media(HEADERS.OCTET_STREAM), uploadPackageTarball(storage));
|
router.put('/:package/-/:filename/*', can('publish'), media(HEADERS.OCTET_STREAM), uploadPackageTarball(storage));
|
||||||
|
|
|
@ -72,6 +72,7 @@ export function getDefaultPlugins() {
|
||||||
|
|
||||||
allow_access: allow_action('access'),
|
allow_access: allow_action('access'),
|
||||||
allow_publish: allow_action('publish'),
|
allow_publish: allow_action('publish'),
|
||||||
|
allow_unpublish: allow_action('unpublish'),
|
||||||
};
|
};
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -190,6 +190,35 @@ class Auth implements IAuth {
|
||||||
})();
|
})();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
allow_unpublish({ packageName, packageVersion }: AuthPluginPackage, user: string, callback: Callback) {
|
||||||
|
const plugins = this.plugins.slice(0);
|
||||||
|
const self = this;
|
||||||
|
// $FlowFixMe
|
||||||
|
const pkg = Object.assign({ name: packageName, version: packageVersion }, getMatchedPackagesSpec(packageName, this.config.packages));
|
||||||
|
this.logger.trace({ packageName }, 'allow unpublish for @{packageName}');
|
||||||
|
|
||||||
|
(function next() {
|
||||||
|
const plugin = plugins.shift();
|
||||||
|
|
||||||
|
if (_.isFunction(plugin.allow_unpublish) === false) {
|
||||||
|
return next();
|
||||||
|
}
|
||||||
|
|
||||||
|
plugin.allow_unpublish(user, pkg, (err, ok: boolean) => {
|
||||||
|
if (err) {
|
||||||
|
self.logger.trace({ packageName }, 'forbidden unpublish for @{packageName}');
|
||||||
|
return callback(err);
|
||||||
|
}
|
||||||
|
|
||||||
|
if (ok) {
|
||||||
|
self.logger.trace({ packageName }, 'allowed unpublish for @{packageName}');
|
||||||
|
return callback(null, ok);
|
||||||
|
}
|
||||||
|
next(); // cb(null, false) causes next plugin to roll
|
||||||
|
});
|
||||||
|
})();
|
||||||
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Allow user to publish a package.
|
* Allow user to publish a package.
|
||||||
*/
|
*/
|
||||||
|
|
|
@ -123,6 +123,8 @@ export function normalisePackageAccess(packages: PackageList): PackageList {
|
||||||
delete normalizedPkgs[pkg].allow_publish;
|
delete normalizedPkgs[pkg].allow_publish;
|
||||||
normalizedPkgs[pkg].proxy = normalizeUserList(packages[pkg].proxy_access, packages[pkg].proxy);
|
normalizedPkgs[pkg].proxy = normalizeUserList(packages[pkg].proxy_access, packages[pkg].proxy);
|
||||||
delete normalizedPkgs[pkg].proxy_access;
|
delete normalizedPkgs[pkg].proxy_access;
|
||||||
|
// $FlowFixMe
|
||||||
|
normalizedPkgs[pkg].unpublish = normalizeUserList([], packages[pkg].unpublish);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
Loading…
Add table
Reference in a new issue