2020-06-06 18:04:19 +02:00
|
|
|
import {
|
|
|
|
getRouteToDestination,
|
|
|
|
getWalletInfo,
|
|
|
|
probeForRoute,
|
|
|
|
} from 'ln-service';
|
2020-06-01 08:36:33 +02:00
|
|
|
import { ContextType } from 'server/types/apiTypes';
|
|
|
|
import { logger } from 'server/helpers/logger';
|
|
|
|
import { requestLimiter } from 'server/helpers/rateLimiter';
|
2020-06-07 13:33:47 +02:00
|
|
|
import { toWithError, to } from 'server/helpers/async';
|
2020-07-21 23:31:12 +02:00
|
|
|
import { LndObject, ProbeForRouteType } from 'server/types/ln-service.types';
|
|
|
|
|
|
|
|
type RouteParent = {
|
|
|
|
lnd: LndObject;
|
|
|
|
destination: string;
|
|
|
|
tokens: number;
|
|
|
|
};
|
2020-06-01 08:36:33 +02:00
|
|
|
|
|
|
|
export const routeResolvers = {
|
|
|
|
Query: {
|
|
|
|
getRoutes: async (_: undefined, params: any, context: ContextType) => {
|
|
|
|
await requestLimiter(context.ip, 'getRoutes');
|
|
|
|
|
2020-08-03 16:31:20 +02:00
|
|
|
const { lnd } = context;
|
2020-06-01 08:36:33 +02:00
|
|
|
|
|
|
|
const { public_key } = await getWalletInfo({ lnd });
|
|
|
|
|
2020-06-07 13:33:47 +02:00
|
|
|
const { route } = await to(
|
|
|
|
getRouteToDestination({
|
|
|
|
lnd,
|
|
|
|
outgoing_channel: params.outgoing,
|
|
|
|
incoming_peer: params.incoming,
|
|
|
|
destination: public_key,
|
|
|
|
tokens: params.tokens,
|
|
|
|
...(params.maxFee && { max_fee: params.maxFee }),
|
|
|
|
})
|
|
|
|
);
|
2020-06-01 08:36:33 +02:00
|
|
|
|
|
|
|
if (!route) {
|
|
|
|
throw new Error('NoRouteFound');
|
|
|
|
}
|
|
|
|
|
2020-06-07 13:33:47 +02:00
|
|
|
return route;
|
2020-06-01 08:36:33 +02:00
|
|
|
},
|
|
|
|
},
|
2020-06-06 18:04:19 +02:00
|
|
|
ProbeRoute: {
|
2020-07-21 23:31:12 +02:00
|
|
|
route: async (parent: RouteParent) => {
|
2020-06-06 18:04:19 +02:00
|
|
|
const { lnd, destination, tokens } = parent;
|
|
|
|
|
|
|
|
if (!lnd) {
|
|
|
|
logger.debug('ExpectedLNDToProbeForRoute');
|
|
|
|
return null;
|
|
|
|
}
|
|
|
|
|
|
|
|
if (!destination) {
|
|
|
|
logger.debug('ExpectedDestinationToProbeForRoute');
|
|
|
|
return null;
|
|
|
|
}
|
|
|
|
|
2020-06-21 21:18:50 +02:00
|
|
|
const [info, error] = await toWithError(
|
2020-06-06 18:04:19 +02:00
|
|
|
probeForRoute({ lnd, destination, tokens })
|
|
|
|
);
|
|
|
|
|
2020-06-21 21:37:29 +02:00
|
|
|
if (!info || error) {
|
2020-06-06 18:04:19 +02:00
|
|
|
logger.debug(
|
2020-06-21 21:18:50 +02:00
|
|
|
`Error probing route to destination ${destination} for ${tokens} tokens`
|
2020-06-06 18:04:19 +02:00
|
|
|
);
|
|
|
|
return null;
|
|
|
|
}
|
|
|
|
|
2020-07-21 23:31:12 +02:00
|
|
|
if (!(info as ProbeForRouteType).route) {
|
2020-06-06 18:04:19 +02:00
|
|
|
logger.debug(
|
|
|
|
`No route found to destination ${destination} for ${tokens} tokens`
|
|
|
|
);
|
|
|
|
return null;
|
|
|
|
}
|
|
|
|
|
2020-07-21 23:31:12 +02:00
|
|
|
const hopsWithNodes =
|
|
|
|
(info as ProbeForRouteType).route?.hops.map(h => ({
|
|
|
|
...h,
|
|
|
|
node: { lnd, publicKey: h.public_key },
|
|
|
|
})) || [];
|
2020-06-06 18:04:19 +02:00
|
|
|
|
2020-07-21 23:31:12 +02:00
|
|
|
return { ...(info as ProbeForRouteType).route, hops: hopsWithNodes };
|
2020-06-06 18:04:19 +02:00
|
|
|
},
|
|
|
|
},
|
2020-06-01 08:36:33 +02:00
|
|
|
};
|