Skip to content

Commit

Permalink
feat: ListSwaps gRPC method (#607)
Browse files Browse the repository at this point in the history
Allows a list of swap IDs to be queried from the backend. A filter by
swap status and a limit for how many entries should be queried can be
applied.
  • Loading branch information
michael1011 committed Jul 12, 2024
1 parent 3b652be commit c6e2e4b
Show file tree
Hide file tree
Showing 18 changed files with 1,060 additions and 34 deletions.
34 changes: 34 additions & 0 deletions lib/cli/commands/ListSwaps.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,34 @@
import { Arguments } from 'yargs';
import { ListSwapsRequest } from '../../proto/boltzrpc_pb';
import { ApiType, BuilderTypes } from '../BuilderComponents';
import { callback, loadBoltzClient } from '../Command';

export const command = 'listswaps [status] [limit]';

export const describe = 'lists swaps';

export const builder = {
status: {
type: 'string',
describe: 'status of the swaps to list',
},
limit: {
type: 'number',
describe: 'limit of the swaps to list per type',
default: 100,
},
};

export const handler = (
argv: Arguments<BuilderTypes<typeof builder> & ApiType>,
): void => {
const request = new ListSwapsRequest();

request.setLimit(argv.limit);

if (argv.status) {
request.setStatus(argv.status);
}

loadBoltzClient(argv).listSwaps(request, callback());
};
12 changes: 9 additions & 3 deletions lib/db/repositories/ChainSwapRepository.ts
Original file line number Diff line number Diff line change
@@ -1,4 +1,4 @@
import { Op, WhereOptions } from 'sequelize';
import { Op, Order, WhereOptions } from 'sequelize';
import {
getHexString,
getSendingReceivingCurrency,
Expand Down Expand Up @@ -102,13 +102,19 @@ class ChainSwapRepository {

public static getChainSwaps = async (
options?: WhereOptions,
order?: Order,
limit?: number,
): Promise<ChainSwapInfo[]> => {
const chainSwaps = await ChainSwap.findAll({ where: options });
const chainSwaps = await ChainSwap.findAll({
limit,
order,
where: options,
});
return Promise.all(chainSwaps.map(this.fetchChainSwapData));
};

/**
* Get a chain swap to with **both** options applies
* Get a chain swap to with **both** options apply
*/
public static getChainSwapByData = async (
dataOptions: WhereOptions,
Expand Down
6 changes: 5 additions & 1 deletion lib/db/repositories/ReverseSwapRepository.ts
Original file line number Diff line number Diff line change
@@ -1,12 +1,16 @@
import { Op, WhereOptions } from 'sequelize';
import { Op, Order, WhereOptions } from 'sequelize';
import { SwapUpdateEvent } from '../../consts/Enums';
import ReverseSwap, { ReverseSwapType } from '../models/ReverseSwap';

class ReverseSwapRepository {
public static getReverseSwaps = (
options?: WhereOptions,
order?: Order,
limit?: number,
): Promise<ReverseSwap[]> => {
return ReverseSwap.findAll({
limit,
order,
where: options,
});
};
Expand Down
10 changes: 8 additions & 2 deletions lib/db/repositories/SwapRepository.ts
Original file line number Diff line number Diff line change
@@ -1,10 +1,16 @@
import { Op, WhereOptions } from 'sequelize';
import { Op, Order, WhereOptions } from 'sequelize';
import { SwapUpdateEvent } from '../../consts/Enums';
import Swap, { SwapType } from '../models/Swap';

class SwapRepository {
public static getSwaps = (options?: WhereOptions): Promise<Swap[]> => {
public static getSwaps = (
options?: WhereOptions,
order?: Order,
limit?: number,
): Promise<Swap[]> => {
return Swap.findAll({
limit,
order,
where: options,
});
};
Expand Down
6 changes: 5 additions & 1 deletion lib/grpc/GrpcServer.ts
Original file line number Diff line number Diff line change
Expand Up @@ -5,6 +5,7 @@ import { BoltzService } from '../proto/boltzrpc_grpc_pb';
import { CertificatePrefix, getCertificate } from './Certificates';
import Errors from './Errors';
import GrpcService from './GrpcService';
import { loggingInterceptor } from './Interceptors';

class GrpcServer {
public static readonly certificateSubject = 'boltz';
Expand All @@ -16,7 +17,9 @@ class GrpcServer {
private config: GrpcConfig,
grpcService: GrpcService,
) {
this.server = new Server();
this.server = new Server({
interceptors: [loggingInterceptor(this.logger)],
});

this.server.addService(BoltzService, {
getInfo: grpcService.getInfo,
Expand All @@ -29,6 +32,7 @@ class GrpcServer {
updateTimeoutBlockDelta: grpcService.updateTimeoutBlockDelta,
addReferral: grpcService.addReferral,
sweepSwaps: grpcService.sweepSwaps,
listSwaps: grpcService.listSwaps,
rescan: grpcService.rescan,
setSwapStatus: grpcService.setSwapStatus,
devHeapDump: grpcService.devHeapDump,
Expand Down
21 changes: 21 additions & 0 deletions lib/grpc/GrpcService.ts
Original file line number Diff line number Diff line change
Expand Up @@ -289,6 +289,27 @@ class GrpcService {
});
};

public listSwaps: handleUnaryCall<
boltzrpc.ListSwapsRequest,
boltzrpc.ListSwapsResponse
> = async (call, callback) => {
await this.handleCallback(call, callback, async () => {
const { status, limit } = call.request.toObject();

const swaps = await this.service.listSwaps(
status !== undefined && status !== '' ? status : undefined,
limit,
);

const response = new boltzrpc.ListSwapsResponse();
response.setChainSwapsList(swaps.chain);
response.setReverseSwapsList(swaps.reverse);
response.setSubmarineSwapsList(swaps.submarine);

return response;
});
};

public rescan: handleUnaryCall<
boltzrpc.RescanRequest,
boltzrpc.RescanResponse
Expand Down
12 changes: 12 additions & 0 deletions lib/grpc/Interceptors.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,12 @@
import { ServerInterceptingCall, ServerInterceptor } from '@grpc/grpc-js';
import Logger from '../Logger';

export const loggingInterceptor =
(logger: Logger): ServerInterceptor =>
(methodDescriptor, call) =>
new ServerInterceptingCall(call, {
start: (next) => {
logger.debug(`Got gRPC call ${methodDescriptor.path}`);
return next();
},
});
41 changes: 40 additions & 1 deletion lib/notifications/CommandHandler.ts
Original file line number Diff line number Diff line change
Expand Up @@ -36,6 +36,7 @@ enum Command {
GetFees = 'getfees',
SwapInfo = 'swapinfo',
GetStats = 'getstats',
ListSwaps = 'listswaps',
GetBalance = 'getbalance',
LockedFunds = 'lockedfunds',
PendingSwaps = 'pendingswaps',
Expand Down Expand Up @@ -119,6 +120,13 @@ class CommandHandler {
],
},
],
[
Command.ListSwaps,
{
executor: this.listSwaps,
description: 'lists swaps',
},
],
[
Command.GetBalance,
{
Expand Down Expand Up @@ -197,7 +205,16 @@ class CommandHandler {
this.logger.debug(
`Executing ${this.notificationClient.serviceName} command: ${command} ${args.join(', ')}`,
);
await commandInfo.executor(args);
try {
await commandInfo.executor(args);
} catch (e) {
this.logger.warn(
`${this.notificationClient.serviceName} command failed: ${formatError(e)}`,
);
await this.notificationClient.sendMessage(
`Command failed: ${formatError(e)}`,
);
}
}
}
});
Expand Down Expand Up @@ -364,6 +381,28 @@ class CommandHandler {
);
};

private listSwaps = async (args: string[]) => {
let status: string | undefined;
let limit: number = 100;

if (args.length > 0) {
status = args[0];
}

if (args.length > 1) {
limit = Number(args[1]);
if (isNaN(limit)) {
throw 'invalid limit';
}

limit = Math.round(limit);
}

await this.notificationClient.sendMessage(
`${codeBlock}${stringify(await this.service.listSwaps(status, limit))}${codeBlock}`,
);
};

private getBalance = async () => {
const balances = (await this.service.getBalance()).toObject().balancesMap;

Expand Down
17 changes: 17 additions & 0 deletions lib/proto/boltzrpc_grpc_pb.d.ts

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

33 changes: 33 additions & 0 deletions lib/proto/boltzrpc_grpc_pb.js

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

Loading

0 comments on commit c6e2e4b

Please sign in to comment.