mirror of
https://github.com/hyperledger/fabric-samples.git
synced 2026-06-17 15:35:09 +00:00
Use app.locals to store contracts and jobq
“The app.locals object has properties that are local variables within the application.” …which looks like a better option than app.get and app.set for app settings. Also passes app to the initJobQueueWorker function for consistency. Signed-off-by: James Taylor <jamest@uk.ibm.com>
This commit is contained in:
parent
66199000ca
commit
711f1f560b
8 changed files with 49 additions and 46 deletions
|
|
@ -48,7 +48,7 @@ describe('Asset Transfer Besic REST API', () => {
|
|||
mockJob.id = '1';
|
||||
mockJobQueue = mock<Queue>();
|
||||
mockJobQueue.add.mockResolvedValue(mockJob);
|
||||
app.set('jobq', mockJobQueue);
|
||||
app.locals.jobq = mockJobQueue;
|
||||
});
|
||||
|
||||
describe('/ready', () => {
|
||||
|
|
@ -81,17 +81,17 @@ describe('Asset Transfer Besic REST API', () => {
|
|||
mockOrg1QsccContract.evaluateTransaction
|
||||
.calledWith('GetChainInfo')
|
||||
.mockResolvedValue(mockBlockchainInfoBuffer);
|
||||
app.set(config.mspIdOrg1, {
|
||||
app.locals[config.mspIdOrg1] = {
|
||||
qsccContract: mockOrg1QsccContract,
|
||||
});
|
||||
};
|
||||
|
||||
const mockOrg2QsccContract = mock<Contract>();
|
||||
mockOrg2QsccContract.evaluateTransaction
|
||||
.calledWith('GetChainInfo')
|
||||
.mockResolvedValue(mockBlockchainInfoBuffer);
|
||||
app.set(config.mspIdOrg2, {
|
||||
app.locals[config.mspIdOrg2] = {
|
||||
qsccContract: mockOrg2QsccContract,
|
||||
});
|
||||
};
|
||||
|
||||
const response = await request(app).get('/live');
|
||||
expect(response.statusCode).toEqual(200);
|
||||
|
|
@ -115,9 +115,9 @@ describe('Asset Transfer Besic REST API', () => {
|
|||
mockBasicContract.createTransaction
|
||||
.calledWith('GetAllAssets')
|
||||
.mockReturnValue(mockGetAllAssetsTransaction);
|
||||
app.set(config.mspIdOrg1, {
|
||||
app.locals[config.mspIdOrg1] = {
|
||||
assetContract: mockBasicContract,
|
||||
});
|
||||
};
|
||||
});
|
||||
|
||||
it('GET should respond with 401 unauthorized json when an invalid API key is specified', async () => {
|
||||
|
|
@ -276,9 +276,9 @@ describe('Asset Transfer Besic REST API', () => {
|
|||
.calledWith('ReadAsset')
|
||||
.mockReturnValue(mockReadAssetTransaction);
|
||||
|
||||
app.set(config.mspIdOrg1, {
|
||||
app.locals[config.mspIdOrg1] = {
|
||||
assetContract: mockBasicContract,
|
||||
});
|
||||
};
|
||||
});
|
||||
|
||||
it('OPTIONS should respond with 401 unauthorized json when an invalid API key is specified', async () => {
|
||||
|
|
@ -663,9 +663,9 @@ describe('Asset Transfer Besic REST API', () => {
|
|||
mockQsccContract.createTransaction
|
||||
.calledWith('GetTransactionByID')
|
||||
.mockReturnValue(mockGetTransactionByIDTransaction);
|
||||
app.set(config.mspIdOrg1, {
|
||||
app.locals[config.mspIdOrg1] = {
|
||||
qsccContract: mockQsccContract,
|
||||
});
|
||||
};
|
||||
});
|
||||
|
||||
it('GET should respond with 401 unauthorized json when an invalid API key is specified', async () => {
|
||||
|
|
|
|||
|
|
@ -38,7 +38,7 @@ assetsRouter.get('/', async (req: Request, res: Response) => {
|
|||
|
||||
try {
|
||||
const mspId = req.user as string;
|
||||
const contract = req.app.get(mspId).assetContract as Contract;
|
||||
const contract = req.app.locals[mspId]?.assetContract as Contract;
|
||||
|
||||
const data = await evatuateTransaction(contract, 'GetAllAssets');
|
||||
let assets = [];
|
||||
|
|
@ -82,7 +82,7 @@ assetsRouter.post(
|
|||
const assetId = req.body.id;
|
||||
|
||||
try {
|
||||
const submitQueue = req.app.get('jobq') as Queue;
|
||||
const submitQueue = req.app.locals.jobq as Queue;
|
||||
const jobId = await addSubmitTransactionJob(
|
||||
submitQueue,
|
||||
mspId,
|
||||
|
|
@ -120,7 +120,7 @@ assetsRouter.options('/:assetId', async (req: Request, res: Response) => {
|
|||
|
||||
try {
|
||||
const mspId = req.user as string;
|
||||
const contract = req.app.get(mspId).assetContract as Contract;
|
||||
const contract = req.app.locals[mspId]?.assetContract as Contract;
|
||||
|
||||
const data = await evatuateTransaction(contract, 'AssetExists', assetId);
|
||||
const exists = data.toString() === 'true';
|
||||
|
|
@ -160,7 +160,7 @@ assetsRouter.get('/:assetId', async (req: Request, res: Response) => {
|
|||
|
||||
try {
|
||||
const mspId = req.user as string;
|
||||
const contract = req.app.get(mspId).assetContract as Contract;
|
||||
const contract = req.app.locals[mspId]?.assetContract as Contract;
|
||||
|
||||
const data = await evatuateTransaction(contract, 'ReadAsset', assetId);
|
||||
const asset = JSON.parse(data.toString());
|
||||
|
|
@ -222,7 +222,7 @@ assetsRouter.put(
|
|||
const assetId = req.params.assetId;
|
||||
|
||||
try {
|
||||
const submitQueue = req.app.get('jobq') as Queue;
|
||||
const submitQueue = req.app.locals.jobq as Queue;
|
||||
const jobId = await addSubmitTransactionJob(
|
||||
submitQueue,
|
||||
mspId,
|
||||
|
|
@ -284,7 +284,7 @@ assetsRouter.patch(
|
|||
const newOwner = req.body[0].value;
|
||||
|
||||
try {
|
||||
const submitQueue = req.app.get('jobq') as Queue;
|
||||
const submitQueue = req.app.locals.jobq as Queue;
|
||||
const jobId = await addSubmitTransactionJob(
|
||||
submitQueue,
|
||||
mspId,
|
||||
|
|
@ -320,7 +320,7 @@ assetsRouter.delete('/:assetId', async (req: Request, res: Response) => {
|
|||
const assetId = req.params.assetId;
|
||||
|
||||
try {
|
||||
const submitQueue = req.app.get('jobq') as Queue;
|
||||
const submitQueue = req.app.locals.jobq as Queue;
|
||||
const jobId = await addSubmitTransactionJob(
|
||||
submitQueue,
|
||||
mspId,
|
||||
|
|
|
|||
|
|
@ -30,9 +30,9 @@ healthRouter.get('/live', async (req: Request, res: Response) => {
|
|||
logger.debug(req.body, 'Liveness request received');
|
||||
|
||||
try {
|
||||
const submitQueue = req.app.get('jobq') as Queue;
|
||||
const qsccOrg1 = req.app.get(config.mspIdOrg1).qsccContract as Contract;
|
||||
const qsccOrg2 = req.app.get(config.mspIdOrg2).qsccContract as Contract;
|
||||
const submitQueue = req.app.locals.jobq as Queue;
|
||||
const qsccOrg1 = req.app.locals[config.mspIdOrg1]?.qsccContract as Contract;
|
||||
const qsccOrg2 = req.app.locals[config.mspIdOrg2]?.qsccContract as Contract;
|
||||
|
||||
await Promise.all([
|
||||
getBlockHeight(qsccOrg1),
|
||||
|
|
|
|||
|
|
@ -32,7 +32,6 @@
|
|||
* express server implementation details
|
||||
*/
|
||||
|
||||
import { Contract } from 'fabric-network';
|
||||
import * as config from './config';
|
||||
import {
|
||||
createGateway,
|
||||
|
|
@ -62,7 +61,10 @@ async function main() {
|
|||
);
|
||||
}
|
||||
|
||||
logger.info('Connecting to Fabric network');
|
||||
logger.info('Creating REST server');
|
||||
const app = await createServer();
|
||||
|
||||
logger.info('Connecting to Fabric network with org1 mspid');
|
||||
const wallet = await createWallet();
|
||||
|
||||
const gatewayOrg1 = await createGateway(
|
||||
|
|
@ -73,6 +75,9 @@ async function main() {
|
|||
const networkOrg1 = await getNetwork(gatewayOrg1);
|
||||
const contractsOrg1 = await getContracts(networkOrg1);
|
||||
|
||||
app.locals[config.mspIdOrg1] = contractsOrg1;
|
||||
|
||||
logger.info('Connecting to Fabric network with org2 mspid');
|
||||
const gatewayOrg2 = await createGateway(
|
||||
config.connectionProfileOrg2,
|
||||
config.mspIdOrg2,
|
||||
|
|
@ -81,24 +86,18 @@ async function main() {
|
|||
const networkOrg2 = await getNetwork(gatewayOrg2);
|
||||
const contractsOrg2 = await getContracts(networkOrg2);
|
||||
|
||||
const assetContracts = new Map<string, Contract>();
|
||||
assetContracts.set(config.mspIdOrg1, contractsOrg1.assetContract);
|
||||
assetContracts.set(config.mspIdOrg2, contractsOrg2.assetContract);
|
||||
app.locals[config.mspIdOrg2] = contractsOrg2;
|
||||
|
||||
logger.info('Initialising submit job queue');
|
||||
jobQueue = initJobQueue();
|
||||
jobQueueWorker = initJobQueueWorker(assetContracts);
|
||||
jobQueueWorker = initJobQueueWorker(app);
|
||||
if (config.submitJobQueueScheduler === true) {
|
||||
logger.info('Initialising submit job queue scheduler');
|
||||
jobQueueScheduler = initJobQueueScheduler();
|
||||
}
|
||||
app.locals.jobq = jobQueue;
|
||||
|
||||
logger.info('Creating REST server');
|
||||
const app = await createServer();
|
||||
app.set(config.mspIdOrg1, contractsOrg1);
|
||||
app.set(config.mspIdOrg2, contractsOrg2);
|
||||
app.set('jobq', jobQueue);
|
||||
|
||||
logger.info('Starting REST server');
|
||||
app.listen(config.port, () => {
|
||||
logger.info('REST server started on port: %d', config.port);
|
||||
});
|
||||
|
|
|
|||
|
|
@ -17,7 +17,7 @@ jobsRouter.get('/:jobId', async (req: Request, res: Response) => {
|
|||
logger.debug('Read request received for job ID %s', jobId);
|
||||
|
||||
try {
|
||||
const submitQueue = req.app.get('jobq') as Queue;
|
||||
const submitQueue = req.app.locals.jobq as Queue;
|
||||
|
||||
const jobSummary = await getJobSummary(submitQueue, jobId);
|
||||
|
||||
|
|
|
|||
|
|
@ -11,6 +11,7 @@ import {
|
|||
} from './jobs';
|
||||
import { Contract, Transaction } from 'fabric-network';
|
||||
import { mock, MockProxy } from 'jest-mock-extended';
|
||||
import { Application } from 'express';
|
||||
|
||||
describe('initJobQueue', () => {
|
||||
it.todo('write tests');
|
||||
|
|
@ -164,6 +165,7 @@ describe('getJobCounts', () => {
|
|||
const mockSavedState = Buffer.from('MOCK SAVED STATE');
|
||||
let mockTransaction: MockProxy<Transaction>;
|
||||
let mockContract: MockProxy<Contract>;
|
||||
let mockApplication: MockProxy<Application>;
|
||||
let mockJob: MockProxy<Job>;
|
||||
|
||||
beforeEach(() => {
|
||||
|
|
@ -179,6 +181,9 @@ describe('getJobCounts', () => {
|
|||
.mockReturnValue(mockTransaction);
|
||||
mockContracts.set('mockMspid', mockContract);
|
||||
|
||||
mockApplication = mock<Application>();
|
||||
mockApplication.locals.mockMspid = { assetContract: mockContract };
|
||||
|
||||
mockJob = mock<Job>();
|
||||
});
|
||||
|
||||
|
|
@ -188,7 +193,7 @@ describe('getJobCounts', () => {
|
|||
};
|
||||
|
||||
const jobResult = await processSubmitTransactionJob(
|
||||
mockContracts,
|
||||
mockApplication,
|
||||
mockJob
|
||||
);
|
||||
|
||||
|
|
@ -209,7 +214,7 @@ describe('getJobCounts', () => {
|
|||
.mockResolvedValue(mockPayload);
|
||||
|
||||
const jobResult = await processSubmitTransactionJob(
|
||||
mockContracts,
|
||||
mockApplication,
|
||||
mockJob
|
||||
);
|
||||
|
||||
|
|
@ -231,7 +236,7 @@ describe('getJobCounts', () => {
|
|||
.mockResolvedValue(mockPayload);
|
||||
|
||||
const jobResult = await processSubmitTransactionJob(
|
||||
mockContracts,
|
||||
mockApplication,
|
||||
mockJob
|
||||
);
|
||||
|
||||
|
|
@ -257,7 +262,7 @@ describe('getJobCounts', () => {
|
|||
);
|
||||
|
||||
const jobResult = await processSubmitTransactionJob(
|
||||
mockContracts,
|
||||
mockApplication,
|
||||
mockJob
|
||||
);
|
||||
|
||||
|
|
@ -280,7 +285,7 @@ describe('getJobCounts', () => {
|
|||
.mockRejectedValue(new Error('MOCK ERROR'));
|
||||
|
||||
await expect(async () => {
|
||||
await processSubmitTransactionJob(mockContracts, mockJob);
|
||||
await processSubmitTransactionJob(mockApplication, mockJob);
|
||||
}).rejects.toThrow('MOCK ERROR');
|
||||
});
|
||||
});
|
||||
|
|
|
|||
|
|
@ -6,6 +6,7 @@
|
|||
*/
|
||||
|
||||
import { ConnectionOptions, Job, Queue, QueueScheduler, Worker } from 'bullmq';
|
||||
import { Application } from 'express';
|
||||
import { Contract, Transaction } from 'fabric-network';
|
||||
import * as config from './config';
|
||||
import { getRetryAction, RetryAction } from './errors';
|
||||
|
|
@ -69,13 +70,11 @@ export const initJobQueue = (): Queue => {
|
|||
return submitQueue;
|
||||
};
|
||||
|
||||
export const initJobQueueWorker = (
|
||||
contracts: Map<string, Contract>
|
||||
): Worker => {
|
||||
export const initJobQueueWorker = (app: Application): Worker => {
|
||||
const worker = new Worker<JobData, JobResult>(
|
||||
config.JOB_QUEUE_NAME,
|
||||
async (job): Promise<JobResult> => {
|
||||
return await processSubmitTransactionJob(contracts, job);
|
||||
return await processSubmitTransactionJob(app, job);
|
||||
},
|
||||
{ connection, concurrency: config.submitJobConcurrency }
|
||||
);
|
||||
|
|
@ -229,12 +228,12 @@ export const getJobCounts = async (
|
|||
* The job will be retried if this function throws an error
|
||||
*/
|
||||
export const processSubmitTransactionJob = async (
|
||||
contracts: Map<string, Contract>,
|
||||
app: Application,
|
||||
job: Job<JobData, JobResult>
|
||||
): Promise<JobResult> => {
|
||||
logger.debug({ jobId: job.id, jobName: job.name }, 'Processing job');
|
||||
|
||||
const contract = contracts.get(job.data.mspid);
|
||||
const contract = app.locals[job.data.mspid]?.assetContract as Contract;
|
||||
if (contract === undefined) {
|
||||
logger.error(
|
||||
{ jobId: job.id, jobName: job.name },
|
||||
|
|
|
|||
|
|
@ -21,7 +21,7 @@ transactionsRouter.get(
|
|||
logger.debug('Read request received for transaction ID %s', transactionId);
|
||||
|
||||
try {
|
||||
const qsccContract = req.app.get(mspId).qsccContract as Contract;
|
||||
const qsccContract = req.app.locals[mspId]?.qsccContract as Contract;
|
||||
|
||||
const validationCode = await getTransactionValidationCode(
|
||||
qsccContract,
|
||||
|
|
|
|||
Loading…
Reference in a new issue