Skip to content
This repository has been archived by the owner on Jun 10, 2022. It is now read-only.

Commit

Permalink
Added unlocked_account endpoint (#518)
Browse files Browse the repository at this point in the history
* Fixed #516
- Added unlocked_account endpoint
  • Loading branch information
rg911 committed Nov 6, 2020
1 parent cbf18c6 commit 492d449
Show file tree
Hide file tree
Showing 4 changed files with 111 additions and 26 deletions.
3 changes: 3 additions & 0 deletions catapult-sdk/src/packet/PacketType.js
Original file line number Diff line number Diff line change
Expand Up @@ -59,6 +59,9 @@ const PacketType = {
finalizationProofAtEpoch: 0x133,
finalizationProofAtHeight: 0x134,

/** Unlocked account */
unlockedAccount: 0x304,

/** State path has been requested by a peer. */
accountStatePath: statePathBaseType + 0x43,
hashLockStatePath: statePathBaseType + 0x48,
Expand Down
97 changes: 77 additions & 20 deletions rest/src/routes/nodeRoutes.js
Original file line number Diff line number Diff line change
Expand Up @@ -33,13 +33,19 @@ const { BinaryParser } = catapult.parser;

// ATM, both rest and rest sdk share the same version. In the future,
// we will have an open api and sdk dependencies with their given versions.
const restVersion = fs.readFileSync(path.resolve(__dirname, '../../../version.txt'), 'UTF-8').trim();
const restVersion = fs
.readFileSync(path.resolve(__dirname, '../../../version.txt'), 'UTF-8')
.trim();
const sdkVersion = restVersion;

const buildResponse = (packet, codec, resultType) => {
const binaryParser = new BinaryParser();
binaryParser.push(packet.payload);
return { payload: codec.deserialize(binaryParser), type: resultType, formatter: 'ws' };
return {
payload: codec.deserialize(binaryParser),
type: resultType,
formatter: 'ws'
};
};

module.exports = {
Expand All @@ -60,18 +66,31 @@ module.exports = {
});

// Check database status
const dbStatusPromise = new Promise((resolve, reject) => (db.database.serverConfig.isConnected() ? resolve() : reject()));
const dbStatusPromise = new Promise((resolve, reject) =>
(db.database.serverConfig.isConnected() ? resolve() : reject()));

// Check apiNode status
const packetBuffer = packetHeader.createBuffer(PacketType.nodeDiscoveryPullPing, packetHeader.size);
const apiNodeStatusPromise = services.connections.singleUse()
.then(connection => connection.pushPull(packetBuffer, services.config.apiNode.timeout))
const packetBuffer = packetHeader.createBuffer(
PacketType.nodeDiscoveryPullPing,
packetHeader.size
);
const apiNodeStatusPromise = services.connections
.singleUse()
.then(connection =>
connection.pushPull(packetBuffer, services.config.apiNode.timeout))
.then(packet => parseNodeInfoPacket(packet));

return Promise.allSettled([dbStatusPromise, apiNodeStatusPromise])
.then(results => {
const statusCode = results.some(result => 'fulfilled' !== result.status) ? 503 : 200;
const checkResult = result => ('fulfilled' === result.status ? ServiceStatus.up : ServiceStatus.down);
return Promise.allSettled([dbStatusPromise, apiNodeStatusPromise]).then(
results => {
const statusCode = results.some(
result => 'fulfilled' !== result.status
)
? 503
: 200;
const checkResult = result =>
('fulfilled' === result.status
? ServiceStatus.up
: ServiceStatus.down);

res.status(statusCode);
res.send({
Expand All @@ -84,25 +103,38 @@ module.exports = {
type: routeResultTypes.nodeHealth
});
next();
});
}
);
});

server.get('/node/info', (req, res, next) => {
const packetBuffer = packetHeader.createBuffer(PacketType.nodeDiscoveryPullPing, packetHeader.size);
return connections.singleUse()
const packetBuffer = packetHeader.createBuffer(
PacketType.nodeDiscoveryPullPing,
packetHeader.size
);
return connections
.singleUse()
.then(connection => connection.pushPull(packetBuffer, timeout))
.then(packet => {
res.send(buildResponse(packet, nodeInfoCodec, routeResultTypes.nodeInfo));
res.send(
buildResponse(packet, nodeInfoCodec, routeResultTypes.nodeInfo)
);
next();
});
});

server.get('/node/peers', (req, res, next) => {
const packetBuffer = packetHeader.createBuffer(PacketType.nodeDiscoveryPullPeers, packetHeader.size);
return connections.singleUse()
const packetBuffer = packetHeader.createBuffer(
PacketType.nodeDiscoveryPullPeers,
packetHeader.size
);
return connections
.singleUse()
.then(connection => connection.pushPull(packetBuffer, timeout))
.then(packet => {
res.send(buildResponse(packet, nodePeersCodec, routeResultTypes.nodeInfo));
res.send(
buildResponse(packet, nodePeersCodec, routeResultTypes.nodeInfo)
);
next();
});
});
Expand All @@ -127,11 +159,36 @@ module.exports = {
}));

server.get('/node/time', (req, res, next) => {
const packetBuffer = packetHeader.createBuffer(PacketType.timeSyncNodeTime, packetHeader.size);
return connections.singleUse()
const packetBuffer = packetHeader.createBuffer(
PacketType.timeSyncNodeTime,
packetHeader.size
);
return connections
.singleUse()
.then(connection => connection.pushPull(packetBuffer, timeout))
.then(packet => {
res.send(
buildResponse(packet, nodeTimeCodec, routeResultTypes.nodeTime)
);
next();
});
});

server.get('/node/unlockedaccount', (req, res, next) => {
const { convert } = catapult.utils;
const headerBuffer = packetHeader.createBuffer(
PacketType.unlockedAccount,
packetHeader.size
);
const packetBuffer = headerBuffer;
return connections
.singleUse()
.then(connection => connection.pushPull(packetBuffer, timeout))
.then(packet => {
res.send(buildResponse(packet, nodeTimeCodec, routeResultTypes.nodeTime));
const unlockedKeys = convert
.uint8ToHex(packet.payload)
.match(/.{1,64}/g);
res.send({ unlockedAccount: !unlockedKeys ? [] : unlockedKeys });
next();
});
});
Expand Down
9 changes: 3 additions & 6 deletions rest/test/routes/allRoutes_spec.js
Original file line number Diff line number Diff line change
Expand Up @@ -65,6 +65,7 @@ describe('all routes', () => {
'/node/server',
'/node/storage',
'/node/time',
'/node/unlockedaccount',

'/transactions/:group/:transactionId',
'/transactions/:group',
Expand Down Expand Up @@ -97,9 +98,7 @@ describe('all routes', () => {
registerAll(server);

// Assert:
test.assert.assertRoutes(routes, [
'/transactions'
]);
test.assert.assertRoutes(routes, ['/transactions']);
});

it('registers all ws routes', () => {
Expand All @@ -111,8 +110,6 @@ describe('all routes', () => {
registerAll(server);

// Assert:
test.assert.assertRoutes(routes, [
'/ws'
]);
test.assert.assertRoutes(routes, ['/ws']);
});
});
28 changes: 28 additions & 0 deletions rest/test/routes/nodeRoutes_spec.js
Original file line number Diff line number Diff line change
Expand Up @@ -410,5 +410,33 @@ describe('node routes', () => {
}));
});
});

describe('unlocked account', () => {
it('can retrieve unlocked account', () => {
// Arrange:
const packet = {
type: 772,
size: 40,
payload: Buffer.from([0x9b, 0x4E, 0xF2, 0x78, 0x9b, 0x4E, 0xF2, 0x78, 0x9b,
0x4E, 0xF2, 0x78, 0x9b, 0x4E, 0xF2, 0x78, 0x9b, 0x4E, 0xF2, 0x78, 0x9b,
0x4E, 0xF2, 0x78, 0x9b, 0x4E, 0xF2, 0x78, 0x9b, 0x4E, 0xF2, 0x78])
};
const services = serviceCreator(packet);

// Act:
return test.route.prepareExecuteRoute(nodeRoutes.register, '/node/unlockedaccount', 'get', {}, {}, services, routeContext =>
routeContext.routeInvoker().then(() => {
// Assert:
expect(routeContext.numNextCalls).to.equal(1);
expect(routeContext.responses.length).to.equal(1);
expect(routeContext.redirects.length).to.equal(0);
expect(routeContext.responses[0]).to.deep.equal({
unlockedAccount: [
'9B4EF2789B4EF2789B4EF2789B4EF2789B4EF2789B4EF2789B4EF2789B4EF278'
]
});
}));
});
});
});
});

0 comments on commit 492d449

Please sign in to comment.