From 0d8dc15c1392ea9c7ecc84690a7b6156bd9a0a47 Mon Sep 17 00:00:00 2001 From: Nicolas Burtey Date: Thu, 31 Aug 2023 14:48:12 +0100 Subject: [PATCH] chore: make app work offline --- .env | 1 + core/api/Makefile | 1 + core/api/src/app/bootstrap/index.ts | 13 ++++++++-- core/api/src/app/bootstrap/price-cache.ts | 29 +++++++++++++++++++++++ core/api/src/config/env.ts | 6 +++++ core/api/src/config/index.ts | 1 + core/api/src/servers/trigger.ts | 14 ++++++++--- core/api/src/services/price/index.ts | 2 +- 8 files changed, 61 insertions(+), 6 deletions(-) create mode 100644 core/api/src/app/bootstrap/price-cache.ts diff --git a/.env b/.env index d98d12a90f..5a94e907b7 100644 --- a/.env +++ b/.env @@ -109,6 +109,7 @@ export KRATOS_PG_CON="postgres://dbuser:secret@localhost:5433/default?sslmode=di export UNSECURE_DEFAULT_LOGIN_CODE="000000" export UNSECURE_IP_FROM_REQUEST_OBJECT=true +export UNSECURE_PRICE_CACHE=true export SVIX_SECRET="eyJhbGciOiJIUzI1NiIsInR5cCI6IkpXVCJ9.eyJpYXQiOjE2OTE2NzIwMTQsImV4cCI6MjAwNzAzMjAxNCwibmJmIjoxNjkxNjcyMDE0LCJpc3MiOiJzdml4LXNlcnZlciIsInN1YiI6Im9yZ18yM3JiOFlkR3FNVDBxSXpwZ0d3ZFhmSGlyTXUifQ.b9s0aWSisNdUNki4edabBEToLNSwjC9-AiJQr4J3y4E" export SVIX_ENDPOINT="http://localhost:8071" diff --git a/core/api/Makefile b/core/api/Makefile index 3eec2eef1f..7f0b186a6e 100644 --- a/core/api/Makefile +++ b/core/api/Makefile @@ -145,6 +145,7 @@ mine-block: lncli-1: docker exec -it $$(docker ps -q -f status=running -f name="lnd1-1") /bin/sh -c 'lncli -n regtest ${command}' +# to create an onchain address: make lncli-outside-1 command="newaddress p2wkh" # to pay an invoice: make lncli-outside-1 command="payinvoice lnbcrt1... --amt=100 -f" lncli-outside-1: docker exec -it $$(docker ps -q -f status=running -f name="lnd-outside-1-1") /bin/sh -c 'lncli -n regtest ${command}' diff --git a/core/api/src/app/bootstrap/index.ts b/core/api/src/app/bootstrap/index.ts index 199c48c4f9..889009fd3e 100644 --- a/core/api/src/app/bootstrap/index.ts +++ b/core/api/src/app/bootstrap/index.ts @@ -1,12 +1,20 @@ import { randomUUID } from "crypto" +import { seedPriceCache } from "./price-cache" + import { createAccountWithPhoneIdentifier } from "@/app/accounts" -import { ConfigError, getAdminAccounts, getDefaultAccountsConfig } from "@/config" +import { + ConfigError, + UNSECURE_PRICE_CACHE, + getAdminAccounts, + getDefaultAccountsConfig, +} from "@/config" import { CouldNotFindAccountFromKratosIdError, CouldNotFindError } from "@/domain/errors" import { WalletCurrency } from "@/domain/shared" +import { initialStaticAccountIds } from "@/services/ledger/facade" import { AccountsRepository, UsersRepository, @@ -14,7 +22,6 @@ import { } from "@/services/mongoose" import { Account } from "@/services/mongoose/schema" import { toObjectId } from "@/services/mongoose/utils" -import { initialStaticAccountIds } from "@/services/ledger/facade" export const randomUserId = () => randomUUID() as UserId @@ -85,5 +92,7 @@ export const bootstrap = async () => { if (wallet.currency !== WalletCurrency.Btc) { return new Error("Expected BTC-currency default wallet") } + + UNSECURE_PRICE_CACHE && (await seedPriceCache()) } } diff --git a/core/api/src/app/bootstrap/price-cache.ts b/core/api/src/app/bootstrap/price-cache.ts new file mode 100644 index 0000000000..a14e393782 --- /dev/null +++ b/core/api/src/app/bootstrap/price-cache.ts @@ -0,0 +1,29 @@ +import { UsdDisplayCurrency } from "@/domain/fiat" +import { LocalCacheService } from "@/services/cache" + +export const seedPriceCache = async () => { + const value: DisplayCurrencyPrices = { + USD: { + timestamp: new Date(), + currency: UsdDisplayCurrency, + price: 0.000124, + }, + EUR: { + timestamp: new Date(), + currency: UsdDisplayCurrency, + price: 0.000124, + }, + } + + await LocalCacheService().set({ + key: "price:current:sat", + value, + ttlSecs: (60 * 60 * 24 * 365) as Seconds, // 1y + }) + + await LocalCacheService().set({ + key: "price:current:usdcent", + value, + ttlSecs: (60 * 60 * 24 * 365) as Seconds, // 1y + }) +} diff --git a/core/api/src/config/env.ts b/core/api/src/config/env.ts index 40ce0fc189..4bdf3b544e 100644 --- a/core/api/src/config/env.ts +++ b/core/api/src/config/env.ts @@ -23,6 +23,11 @@ export const env = createEnv({ .or(z.string()) .pipe(z.coerce.boolean()) .default(false), + UNSECURE_PRICE_CACHE: z + .boolean() + .or(z.string()) + .pipe(z.coerce.boolean()) + .default(false), EXPORTER_PORT: z.number().or(z.string()).pipe(z.coerce.number()).default(3000), TRIGGER_PORT: z.number().or(z.string()).pipe(z.coerce.number()).default(8888), @@ -138,6 +143,7 @@ export const env = createEnv({ UNSECURE_DEFAULT_LOGIN_CODE: process.env.UNSECURE_DEFAULT_LOGIN_CODE, UNSECURE_IP_FROM_REQUEST_OBJECT: process.env.UNSECURE_IP_FROM_REQUEST_OBJECT, + UNSECURE_PRICE_CACHE: process.env.UNSECURE_PRICE_CACHE, EXPORTER_PORT: process.env.EXPORTER_PORT, TRIGGER_PORT: process.env.TRIGGER_PORT, diff --git a/core/api/src/config/index.ts b/core/api/src/config/index.ts index 0268d3a474..3de1308fa4 100644 --- a/core/api/src/config/index.ts +++ b/core/api/src/config/index.ts @@ -127,6 +127,7 @@ export const HELMREVISION = env.HELMREVISION export const LOGLEVEL = env.LOGLEVEL export const UNSECURE_DEFAULT_LOGIN_CODE = env.UNSECURE_DEFAULT_LOGIN_CODE export const UNSECURE_IP_FROM_REQUEST_OBJECT = env.UNSECURE_IP_FROM_REQUEST_OBJECT +export const UNSECURE_PRICE_CACHE = env.UNSECURE_PRICE_CACHE export const EXPORTER_PORT = env.EXPORTER_PORT export const TRIGGER_PORT = env.TRIGGER_PORT export const WEBSOCKET_PORT = env.WEBSOCKET_PORT diff --git a/core/api/src/servers/trigger.ts b/core/api/src/servers/trigger.ts index 54711b4eba..3fba3f9d7f 100644 --- a/core/api/src/servers/trigger.ts +++ b/core/api/src/servers/trigger.ts @@ -24,7 +24,13 @@ import { briaEventHandler } from "./event-handlers/bria" import healthzHandler from "./middlewares/healthz" -import { getSwapConfig, NETWORK, ONCHAIN_MIN_CONFIRMATIONS, TRIGGER_PORT } from "@/config" +import { + getSwapConfig, + NETWORK, + ONCHAIN_MIN_CONFIRMATIONS, + TRIGGER_PORT, + UNSECURE_PRICE_CACHE, +} from "@/config" import { Payments, @@ -36,13 +42,13 @@ import { uploadBackup } from "@/app/admin/backup" import { lnd1LoopConfig, lnd2LoopConfig } from "@/app/swap/get-active-loopd" import * as Wallets from "@/app/wallets" +import { DEFAULT_EXPIRATIONS } from "@/domain/bitcoin/lightning/invoice-expiration" import { TxDecoder } from "@/domain/bitcoin/onchain" import { CacheKeys } from "@/domain/cache" import { CouldNotFindWalletFromOnChainAddressError } from "@/domain/errors" -import { SwapTriggerError } from "@/domain/swap/errors" import { checkedToDisplayCurrency } from "@/domain/fiat" -import { DEFAULT_EXPIRATIONS } from "@/domain/bitcoin/lightning/invoice-expiration" import { ErrorLevel, paymentAmountFromNumber, WalletCurrency } from "@/domain/shared" +import { SwapTriggerError } from "@/domain/swap/errors" import { WalletInvoiceChecker } from "@/domain/wallet-invoices" import { BriaSubscriber } from "@/services/bria" @@ -57,6 +63,7 @@ import { setupMongoConnection } from "@/services/mongodb" import { WalletInvoicesRepository } from "@/services/mongoose" import { NotificationsService } from "@/services/notifications" import { recordExceptionInCurrentSpan, wrapAsyncToRunInSpan } from "@/services/tracing" +import { seedPriceCache } from "@/app/bootstrap/price-cache" const redisCache = RedisCacheService() const logger = baseLogger.child({ module: "trigger" }) @@ -512,6 +519,7 @@ const healthCheck = () => { // only execute if it is the main module if (require.main === module) { healthCheck() + UNSECURE_PRICE_CACHE && seedPriceCache() setupMongoConnection() .then(main) .catch((err) => logger.error(err)) diff --git a/core/api/src/services/price/index.ts b/core/api/src/services/price/index.ts index e1e6c902c0..dcc2888195 100644 --- a/core/api/src/services/price/index.ts +++ b/core/api/src/services/price/index.ts @@ -98,7 +98,7 @@ export const PriceService = (): IPriceService => { currency: displayCurrency, } } catch (err) { - baseLogger.error({ err }, "impossible to fetch most recent price") + baseLogger.warn({ err }, "impossible to fetch most recent price") return new UnknownPriceServiceError(err) } }