Building private npm repository


Building private npm repository
cnpm is an open source solution for building NPM mirrors and private NPM repositories within an enterprise, and when business logic-related modules may not be suitable for open source. This private module can be managed and maintained in a private NPM repository.

Following are the detailed steps to build a private npm, using the [][href1] open source by Ali's team, which is divided into Server-side configuration and Client configuration:


The Server side is mainly configured with cnpm, mysql and nginx.

Environmental Science:

# system
$ cat /etc/redhat-release 
CentOS Linux release 7.1.1503 (Core) 

# node
$ node -v

# npm
$ npm -v

# nginx
$ nginx -v
nginx version: nginx/1.9.9

# mysql
$ mysql -u yourname -p
$ mysql> s;
Server version: 5.5.38-log MySQL Community Server (GPL)

# server ip


# clone from github
$ git clone git:// $HOME/
$ cd $HOME/

# init mysql
$ mysql -u yourname -p
mysql> create database cnpmjs;
mysql> use cnpmjs;
mysql> source docs/db.sql

To configure:

$ pwd

$ vim config/config.js
module.exports = {
    debug: false,
    // add your own private prefix, you can have more than one. required.
    scopes: ['@test'],  
    enableCluster: true,
    // mysql, required.
    database: {      
        db: 'cnpmjs',
        username: 'username',
        password: 'password',
        dialect: 'mysql',
        host: '',
        port: 3306,
        pool: {
            maxConnections: 10,
            minConnections: 0,
            maxIdleTime: 30000
        logging: !!process.env.SQL_DEBUG,
    mail: {
        enable: false,
        appname: 'appname',
        from: 'from',
        service: 'service',
        auth: {
            user: 'user',
            pass: 'pass'
    // Log directory, cnpm's running log, must be filled.
    logdir: '/data/logs/cnpm/node_logs/',  
    nfs: require('fs-cnpm')({
        // package store directory
        dir: '/data/logs/cnpm/node_nfs/',  
    // Upload directory, must fill in
    uploadDir: '/data/logs/cnpm/node_modules/',  
    enablePrivate: true,
    // Registered domain name must be filled.
    registryHost: '',  
    // Users can publish package must fill in
    admins: {
        admin: 'admin'   
    // The mode of synchronized official package must be filled.
    syncModel: 'exist', // 'none', 'all', 'exist'   
    // Size of package
    jsonLimit: 1073741824, 
    // White list of package with private prefix not managed by cnpm
    privatePackages: ['@remobild/react-native-toast']   

$ vim config/index.js
# Annotate bindingHost, open to external network, otherwise it can only be submitted locally.
bindingHost: ''

# Note that syncModel does not recommend writing all, and all mode synchronizes the entire official repository, requiring large storage space
# Ensure logdir, nfsdir, uploadDir directory permissions can be written.
# Packet size, depending on your package, if you have a particularly large package and are proxied through nginx, then besides jsonLimit, nginx's client_max_body_size needs to be modified as well

Installation dependency:

$  npm install --build-from-source --registry= --disturl=


# debug mode
$ npm run dev

# Backstage start
$ npm start

# Check registry
$ curl

# Check web
$ curl

# The above two ports can also be modified through config. js, with default 7001 and 7002 written in config/index.js

nginx: (this step is optional, and client can directly use ip).

upstream cnpm {

server {
    listen 80;

    location / {
        proxy_set_header X-Real-IP $remote_addr;
        proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for;
        proxy_set_header Host $http_host;
        proxy_pass http://cnpm/;
        proxy_redirect off;

upstream registry_cnpm {

server {
    listen 80;

    location / {
        proxy_set_header X-Real-IP $remote_addr;
        proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for;
        proxy_set_header Host $http_host;
        proxy_pass http://registry_cnpm/;
        proxy_redirect off;

At this point, the Server side configuration is complete, and you can see your npm repository by binding host locally to access


Client side is mainly configure the command line tool to complete the registration, login and other steps, then you can publish the package to your npm repository.

Install cnpm:

# cnpm official has its own cnpm command, but in our actual use process, there have been some problems, and then used to add an alias to the npm official command way
$ echo -e 'n#alias for cnpmnalias cnpm="npm --registry= --cache=$HOME/.npm/.cache/cnpm --disturl= --userconfig=$HOME/.cnpmrc"' >> ~/.bashrc && source ~/.bashrc

To configure:

1. configure cnpmrc
$ vim ~/.cnpmrc

2. registration
 (Before registering, you need to send the mailbox prefix of the person you want to register to the administrator, who can add it to config.js above.)
$ cnpm adduser
 Enter the user, password, mail box in turn.

3. logon
$ cnpm login 
No error indicates successful login.


# publish package
$ mkdir test && cd test
$ cnpm init -y
$ touch test.js
$ cnpm publish

# install package
$ cnpm install @test/test --save

The above is the configuration process of the Client, which is still very simple.

By configuring the Server and Client sides above, we can publish some private packages into our npm repository within our company. In addition, cnpm can also install the package of the official repository. During the installation process, cnpm will go to its repository to find the package to install and if not found, default to
looking for, this is a complete mirroring maintained by Ali team.
, the synchronization frequency is currently 10 minutes, so as to ensure synchronization with official services.


Building private npm repository



理解 Koa 框架中间件原理



Building private npm repository