NodeJS application for Fabric #fabricca #fabric


Andrei Lovin
 

I've been working on a multi-host, multi-org fabric network, which work pretty good. The next step would be to create a REST API server that will connect the network with the client application. From my research, there aren't to many examples that I could use, but I have found a really good library, which unfortunately doesn't work over my network, or at least I don't know how to use it.

https://github.com/olegabu/fabric-starter-rest


I've been working on a multi-host, multi-org fabric network, which work pretty good. The next step would be to create a REST API server that will connect the network with the client application. From my research, there aren't to many examples that I could use, but I have found a really good library, which unfortunately doesn't work over my network, or at least I don't know how to use it.

https://github.com/olegabu/fabric-starter-rest

What I've tried is:

  • on Host_1 I've cloned the repo, inside the code of my network;
  • updated the network.js from the repo to work with my network;
  • then npm start;

The server starts on port 3000 on my host but with an error:

error: [client-utils.js]: sendPeersProposal - Promise is rejected: Error: 2 UNKNOWN: access denied: channel [] creator org [manager]

If I try to enroll a user with JWT I'm getting:

JWT=`(curl -d '{"username":"user1","password":"pass"}' --header "Content-Type: application/json" http://localhost:3000/users | tr -d '"')`

echo $JWT

fabric-ca request register failed with errors [[{\code\:0,\message\:\Registration of 'user1' failed in affiliation validation: Failed getting affiliation 'manager': : scode: 404, code: 63, msg: Failed to get Affiliation: sql: no rows in result set\}]]

This is my network.js

const fs = require('fs');

const myorg = process.env.ORG || 'manager';
const domain = process.env.DOMAIN || 'test.com';
const cryptoConfigDir = process.env.CRYPTO_CONFIG_DIR || '../crypto-config';
const enrollId = process.env.ENROLL_ID || 'admin';
const enrollSecret = process.env.ENROLL_SECRET || 'adminpw';
// default to peer0.org1.example.com:7051 inside docker-compose or export ORGS='{"org1":"peer0.org1.example.com:7051","org2":"peer0.org2.example.com:7051"}'
let orgs = process.env.ORGS || '"manager":"localhost:7051"';
let cas = process.env.CAS || '"manager":"localhost:7054"';

const t = {
  name: 'Network',
  version: '1.0',
};

function addOrg(t, org) {
  if(!t.organizations) {
    t.organizations = {};
  }
  t.organizations[org] = {
    // mspid: `${org}MSP`,
    mspid: `${org}`,
    peers: [
      `peer0.${org}.${domain}`
    ]
  };

  if(org === myorg) {
    const keystorePath = `${cryptoConfigDir}/peerOrganizations/${org}.${domain}/users/Admin@${org}.${domain}/msp/keystore`;
    const keystoreFiles = fs.readdirSync(keystorePath);
    const keyPath = `${keystorePath}/${keystoreFiles[0]}`;

    t.organizations[org].certificateAuthorities = [org];
    t.organizations[org].adminPrivateKey = {
      path: keyPath
    };
    t.organizations[org].signedCert = {
      path: `${cryptoConfigDir}/peerOrganizations/${org}.${domain}/users/Admin@${org}.${domain}/msp/signcerts/Admin@${org}.${domain}-cert.pem`
    };
  }
}

function addPeer(t, org, i, peerAddress) {
  if(!t.peers) {
    t.peers = {};
  }
  t.peers[`peer${i}.${org}.${domain}`] = {
    url: `grpcs://${peerAddress}`,
    grpcOptions: {
       'ssl-target-name-override': `peer${i}.${org}.${domain}`,
      //'ssl-target-name-override': 'localhost',
      'grpc.keepalive_time_ms': 600000
    },
    tlsCACerts: {
      path: `${cryptoConfigDir}/peerOrganizations/${org}.${domain}/peers/peer${i}.${org}.${domain}/msp/tlscacerts/tlsca.${org}.${domain}-cert.pem`
    }
  };
}

function addCA(t, org, caAddress) {
  if(!t.certificateAuthorities) {
    t.certificateAuthorities = {};
  }

  t.certificateAuthorities[org] = {
    url: `https://${caAddress}`,
    httpOptions: {
      verify: false
    },
    tlsCACerts: {
      path: `${cryptoConfigDir}/peerOrganizations/${org}.${domain}/ca/ca.${org}.${domain}-cert.pem`
    },
    registrar: [
      {
        enrollId: enrollId,
        enrollSecret: enrollSecret
      }
    ],
    caName: 'ca-manager'
  };
}

module.exports = function () {
  t.client = {
    organization: myorg,
    credentialStore: {
      path: `hfc-kvs/${myorg}`,
      cryptoStore: {
        path: `hfc-cvs/${myorg}`
      }
    }
  };

  try {
    orgs = JSON.parse(orgs);
  } catch(e) {
    orgs = JSON.parse('{' + orgs + '}');
  }

  try {
    cas = JSON.parse(cas);
  } catch(e) {
    cas = JSON.parse('{' + cas + '}');
  }

  Object.keys(orgs).forEach(k => {
    addOrg(t, k);
    addPeer(t, k, 0, orgs[k]);
  });

  Object.keys(cas).forEach(k => {
    addCA(t, k, cas[k]);
  });

  return t;
};