Skip to content

Commit

Permalink
Merge pull request #1914 from ExchangeUnion/fix/checking-invoices-sup…
Browse files Browse the repository at this point in the history
…port-lnd

fix: checking for invoice support on lnd clients while verifying connection
  • Loading branch information
Karl Ranna authored Sep 30, 2020
2 parents 5360f09 + 532a332 commit c4c411c
Show file tree
Hide file tree
Showing 3 changed files with 32 additions and 2 deletions.
21 changes: 20 additions & 1 deletion lib/lndclient/LndClient.ts
Original file line number Diff line number Diff line change
@@ -1,4 +1,5 @@
import assert from 'assert';
import crypto from 'crypto';
import { promises as fs, watch } from 'fs';
import grpc, { ChannelCredentials, ClientReadableStream } from 'grpc';
import path from 'path';
Expand Down Expand Up @@ -242,6 +243,10 @@ class LndClient extends SwapClient {

private unaryCall = <T, U>(methodName: Exclude<keyof LightningClient, ClientMethods>, params: T): Promise<U> => {
return new Promise((resolve, reject) => {
if (this.hasNoInvoiceSupport()) {
reject(errors.NO_HOLD_INVOICE_SUPPORT);
return;
}
if (!this.isOperational()) {
reject(errors.DISABLED);
return;
Expand Down Expand Up @@ -337,7 +342,9 @@ class LndClient extends SwapClient {
let version: string | undefined;
let alias: string | undefined;
let status = 'Ready';
if (!this.isOperational()) {
if (this.hasNoInvoiceSupport()) {
status = errors.NO_HOLD_INVOICE_SUPPORT(this.currency).message;
} else if (!this.isOperational()) {
status = errors.DISABLED(this.currency).message;
} else if (this.isDisconnected()) {
status = errors.UNAVAILABLE(this.currency, this.status).message;
Expand Down Expand Up @@ -493,6 +500,18 @@ class LndClient extends SwapClient {
}

this.invoices = new InvoicesClient(this.uri, this.credentials);
try {
const randomHash = crypto.randomBytes(32).toString('hex');
this.logger.debug(`checking hold invoice support with hash: ${randomHash}`);

await this.addInvoice({ rHash: randomHash, units: 1 });
await this.removeInvoice(randomHash);
} catch (err) {
const errStr = typeof(err) === 'string' ? err : JSON.stringify(err);

this.logger.error(`could not add hold invoice, error: ${errStr}`);
this.setStatus(ClientStatus.NoHoldInvoiceSupport);
}

if (this.walletUnlocker) {
// WalletUnlocker service is disabled when the main Lightning service is available
Expand Down
5 changes: 5 additions & 0 deletions lib/lndclient/errors.ts
Original file line number Diff line number Diff line change
Expand Up @@ -6,6 +6,7 @@ const errorCodes = {
DISABLED: codesPrefix.concat('.1'),
UNAVAILABLE: codesPrefix.concat('.2'),
NO_ACTIVE_CHANNELS: codesPrefix.concat('.3'),
NO_HOLD_INVOICE_SUPPORT: codesPrefix.concat('.4'),
};

const errors = {
Expand All @@ -21,6 +22,10 @@ const errors = {
message: `lnd-${currency} has no active channels`,
code: errorCodes.NO_ACTIVE_CHANNELS,
}),
NO_HOLD_INVOICE_SUPPORT: (currency: string) => ({
message: `lnd-${currency} has no hold invoice support`,
code: errorCodes.NO_HOLD_INVOICE_SUPPORT,
}),
};

export { errorCodes };
Expand Down
8 changes: 7 additions & 1 deletion lib/swaps/SwapClient.ts
Original file line number Diff line number Diff line change
Expand Up @@ -23,6 +23,8 @@ enum ClientStatus {
Unlocked,
/** The client could not be initialized due to faulty configuration. */
Misconfigured,
/** The server is reachable but hold invoices are not supported. */
NoHoldInvoiceSupport,
}

type ChannelBalance = {
Expand Down Expand Up @@ -216,6 +218,7 @@ abstract class SwapClient extends EventEmitter {
case ClientStatus.Disconnected:
case ClientStatus.WaitingUnlock:
case ClientStatus.OutOfSync:
case ClientStatus.NoHoldInvoiceSupport:
// these statuses can only be set on an operational, initalized client
validStatusTransition = this.isOperational();
break;
Expand Down Expand Up @@ -359,7 +362,7 @@ abstract class SwapClient extends EventEmitter {
* Returns `true` if the client is enabled and configured properly.
*/
public isOperational(): boolean {
return !this.isDisabled() && !this.isMisconfigured() && !this.isNotInitialized();
return !this.isDisabled() && !this.isMisconfigured() && !this.isNotInitialized() && !this.hasNoInvoiceSupport();
}
public isDisconnected(): boolean {
return this.status === ClientStatus.Disconnected;
Expand All @@ -373,6 +376,9 @@ abstract class SwapClient extends EventEmitter {
public isOutOfSync(): boolean {
return this.status === ClientStatus.OutOfSync;
}
public hasNoInvoiceSupport(): boolean {
return this.status === ClientStatus.NoHoldInvoiceSupport;
}

/** Ends all connections, subscriptions, and timers for for this client. */
public close() {
Expand Down

0 comments on commit c4c411c

Please sign in to comment.