diff --git a/.env.example b/.env.example index 57a7290..c856c53 100644 --- a/.env.example +++ b/.env.example @@ -9,3 +9,4 @@ WEB_PORT=80 VITE_API_URL=http://localhost/api VITE_ESPLORA_BASE_URL=https://blockstream.info/liquidtestnet/api VITE_ESPLORA_EXPLORER_URL=https://blockstream.info/liquidtestnet +VITE_FAUCET_URL=https://liquidtestnet.com/faucet diff --git a/crates/indexer/configuration/base.yaml b/crates/indexer/configuration/base.yaml index a52f43b..f126e00 100644 --- a/crates/indexer/configuration/base.yaml +++ b/crates/indexer/configuration/base.yaml @@ -7,7 +7,7 @@ database: password: "password" database_name: "lending-indexer" esplora: - base_url: "https://blockstream.info/liquidtestnet/api" + base_url: "https://liquid.network/liquidtestnet/api" timeout: 10 indexer: interval: 10000 diff --git a/docker-compose.yml b/docker-compose.yml index b8d5c24..11b85fc 100644 --- a/docker-compose.yml +++ b/docker-compose.yml @@ -78,6 +78,7 @@ services: VITE_API_URL: ${VITE_API_URL} VITE_ESPLORA_BASE_URL: ${VITE_ESPLORA_BASE_URL} VITE_ESPLORA_EXPLORER_URL: ${VITE_ESPLORA_EXPLORER_URL} + VITE_FAUCET_URL: ${VITE_FAUCET_URL} restart: unless-stopped ports: - '${WEB_PORT}:80' diff --git a/web/.env.example b/web/.env.example index dcdb3ad..8ae4ff1 100644 --- a/web/.env.example +++ b/web/.env.example @@ -7,3 +7,6 @@ VITE_ESPLORA_BASE_URL=https://blockstream.info/liquidtestnet/api # Block explorer base URL for transaction links (optional; default: same as VITE_ESPLORA_BASE_URL) # Example: https://blockstream.info/liquidtestnet (no /api) for Blockstream Explorer VITE_ESPLORA_EXPLORER_URL=https://blockstream.info/liquidtestnet + +# Liquid testnet faucet (shown on seed entry screen; optional) +VITE_FAUCET_URL=https://liquidtestnet.com/faucet diff --git a/web/Dockerfile b/web/Dockerfile index 52a773c..da8d25c 100644 --- a/web/Dockerfile +++ b/web/Dockerfile @@ -30,9 +30,11 @@ WORKDIR /app/web ARG VITE_API_URL ARG VITE_ESPLORA_BASE_URL ARG VITE_ESPLORA_EXPLORER_URL +ARG VITE_FAUCET_URL ENV VITE_API_URL=$VITE_API_URL ENV VITE_ESPLORA_BASE_URL=$VITE_ESPLORA_BASE_URL ENV VITE_ESPLORA_EXPLORER_URL=$VITE_ESPLORA_EXPLORER_URL +ENV VITE_FAUCET_URL=$VITE_FAUCET_URL RUN npm run build FROM nginx:1.27-alpine AS runtime diff --git a/web/src/App.tsx b/web/src/App.tsx index 897a245..917c4ff 100644 --- a/web/src/App.tsx +++ b/web/src/App.tsx @@ -33,6 +33,8 @@ function Header({ onDisconnect: () => void showTabs: boolean }) { + const faucetUrl = import.meta.env.VITE_FAUCET_URL?.trim() + return (
@@ -95,6 +97,16 @@ function Header({ > Utility + {faucetUrl ? ( + + Faucet + + ) : null} b.toString(16).padStart(2, '0')).join('') +} + type Props = { seedHex: string | null setSeedHex: (hex: string) => void @@ -13,12 +23,43 @@ type Props = { export function SeedGate({ seedHex, setSeedHex, accountIndex, children }: Props) { const [inputValue, setInputValue] = useState('') const [error, setError] = useState(null) + const [displayedGeneratedSeed, setDisplayedGeneratedSeed] = useState(null) + const [copyFeedback, setCopyFeedback] = useState(false) + const faucetUrl = import.meta.env.VITE_FAUCET_URL?.trim() + + const handleRandomSeed = () => { + const hex = randomSeedHex() + setError(null) + setInputValue(hex) + setDisplayedGeneratedSeed(hex) + setCopyFeedback(false) + } + + const handleSeedInputChange = (value: string) => { + setInputValue(value) + const normalized = normalizeSeedInput(value) + setDisplayedGeneratedSeed((prev) => + prev !== null && normalized === prev ? prev : null + ) + setCopyFeedback(false) + } + + const handleCopyGeneratedSeed = async () => { + if (!displayedGeneratedSeed) return + try { + await navigator.clipboard.writeText(displayedGeneratedSeed) + setCopyFeedback(true) + window.setTimeout(() => setCopyFeedback(false), 2000) + } catch { + setCopyFeedback(false) + } + } const handleSubmit = (e: React.FormEvent) => { e.preventDefault() setError(null) try { - const trimmed = inputValue.trim().toLowerCase().replace(/^0x/, '') + const trimmed = normalizeSeedInput(inputValue) parseSeedHex(trimmed) setSeedHex(trimmed) } catch (err) { @@ -31,21 +72,61 @@ export function SeedGate({ seedHex, setSeedHex, accountIndex, children }: Props)

Demo signer: enter SEED_HEX (32 bytes, 64 hex chars)

-
- setInputValue(e.target.value)} - className="flex-1 min-w-0 font-mono" - /> - -
+
+
+ handleSeedInputChange(e.target.value)} + className="min-w-0 flex-1 font-mono" + /> + +
+ +
+ {displayedGeneratedSeed ? ( +
+

+ Generated seed (copy and keep private) +

+ + {displayedGeneratedSeed} + + +
+ ) : null} + {faucetUrl ? ( +

+ Need test coins?{' '} + + Open Liquid testnet faucet + +

+ ) : null} {error &&

{error}

}

- Only for testing. No real wallet yet. Seed is not persisted. + Only for testing. No real wallet yet. Seed is stored in your browser (localStorage) for this + demo.

diff --git a/web/src/pages/Dashboard/index.tsx b/web/src/pages/Dashboard/index.tsx index 8e110ad..ee54ad8 100644 --- a/web/src/pages/Dashboard/index.tsx +++ b/web/src/pages/Dashboard/index.tsx @@ -206,8 +206,8 @@ export function Dashboard({ return (
-
-
+
+
B @@ -216,39 +216,42 @@ export function Dashboard({ Your Borrows
-
-
-

LBTC Locked

- -
-
-

Active Deals

- -
-
-

Pending Deals

- +
+
+
+

LBTC Locked

+ +
+
+

Active Deals

+ +
+
+

Pending Deals

+ +
+ {statsError && ( -

+

{statsError}

)}
-
+
S @@ -257,25 +260,28 @@ export function Dashboard({ Your Supply
-
-
-

Active Offers

- -
-
-

Expecting Liquidation

- +
+
+
+

Active Offers

+ +
+
+

Expecting Liquidation

+ +
+ {statsError && ( -

+

{statsError}

)} diff --git a/web/src/vite-env.d.ts b/web/src/vite-env.d.ts index a8b0156..e2e9983 100644 --- a/web/src/vite-env.d.ts +++ b/web/src/vite-env.d.ts @@ -1,5 +1,9 @@ /// +interface ImportMetaEnv { + readonly VITE_FAUCET_URL?: string +} + declare module 'virtual:simplicity-sources' { export const sources: Record }