About XRPL
home

Wallet

주요 내용
지갑 생성, 기존 지갑 불러오기 및 balance, trustline, flag 조회
폴더명
Wallet

XRPL Ledger : xrpl.js - Wallet

스크립트 실행 명령어

$npx ts-node xrpl/Wallet/LoadWallet.ts $npx ts-node xrpl/Wallet/faucet.ts $npx ts-node xrpl/Wallet/WalletInfo.ts $npx ts-node xrpl/Wallet/createNewWallet.ts
Bash
복사

1. Wallet

Wallet은 XRPL 계정을 생성/로드/펀딩/조회하기 위한 도구(스크립트 모음)이다.
생성: 새 주소/시드 발급
펀딩(Devnet): Faucet으로 활성화(기본 리저브 충족)
조회: 잔액, 시퀀스, Flags, TrustLines 등

2. 왜 필요한가?

개발 초기 세팅: 테스트 계정 빠르게 준비
자동화: 반복 테스트에서 계정 생성/펀딩/조회 스크립트 표준화
디버깅: 실패 원인 분석 시 계정 상태 쉽게 확인

3. 시나리오: generatefaucetget-wallet-info

Step 1. 새 지갑 생성 (createNewWallet.ts)

주체: 개발자
행동: 새 시드/주소 생성
내용: 콘솔에 address/seed 출력
import dotenv from 'dotenv' import path from 'path' import { Wallet } from 'xrpl' // .env 파일 로드 (이 스크립트에서는 직접 사용하지 않지만, 프로젝트 전체 일관성을 위해 포함) dotenv.config({ path: path.join(__dirname, '..', '.env') }) export async function createNewWallet() { try { // 1. 새 지갑 생성 — 랜덤하게 키쌍, 주소, 시드가 생성됨 const newWallet = Wallet.generate() // 2. 콘솔 출력 — 생성된 지갑의 기본 정보 확인 가능 // ⚠️ 시드(seed)는 계정 권한 전체를 의미하므로 반드시 안전하게 보관 필요 console.log('새 지갑 생성 완료') console.log(`주소: ${newWallet.address}`) // r로 시작하는 XRPL 주소 console.log(`시드: ${newWallet.seed}`) // s로 시작하는 XRPL 시드 console.log(`공개키: ${newWallet.publicKey}`) // 33바이트 hex 형식 공개키 // 3. 함수 반환 — 다른 스크립트에서 불러 쓸 수 있도록 객체 형태로 반환 return { wallet: newWallet, address: newWallet.address, seed: newWallet.seed! } } catch (error) { // 예외 처리 — Wallet.generate() 자체는 거의 실패하지 않지만 런타임 예외 대비 console.error('❌ 새 지갑 생성 실패:', error) throw new Error(`새 지갑 생성 실패: ${error}`) } } // 모듈이 직접 실행된 경우에만 createNewWallet 실행 // (다른 곳에서 import할 경우에는 함수만 제공) if (require.main === module) { createNewWallet() }
TypeScript
복사

Step 2. Devnet 펀딩 (faucet.ts)

주체: 개발자
행동: Devnet Faucet으로 해당 시드 지갑 활성화
내용: 리저브/수수료 지불 가능한 최소 잔액 확보
import dotenv from "dotenv" import path from "path" import { Client, Wallet } from "xrpl" // .env 파일 로드 (시드값을 환경변수에서 불러오기 위함) dotenv.config({ path: path.join(__dirname, "..", ".env") }) export async function faucetAll() { // XRPL Devnet에 연결 (테스트용 네트워크) const client = new Client("wss://s.devnet.rippletest.net:51233") await client.connect() try { // 1. Admin 계정 활성화 if (process.env.ADMIN_SEED) { const adminWallet = Wallet.fromSeed(process.env.ADMIN_SEED.trim()) // faucet으로 지정된 지갑에 테스트 XRP 지급 (리저브 충족 및 트랜잭션 가능 상태로 만듦) await client.fundWallet(adminWallet) console.log(`✅ ADMIN (${adminWallet.address}) 계정 활성화 완료`) } else { console.warn("⚠️ ADMIN_SEED 환경변수 없음") } // 2. User 계정 활성화 if (process.env.USER_SEED) { const userWallet = Wallet.fromSeed(process.env.USER_SEED.trim()) await client.fundWallet(userWallet) console.log(`✅ USER (${userWallet.address}) 계정 활성화 완료`) } else { console.warn("⚠️ USER_SEED 환경변수 없음") } // 3. User2 계정 활성화 if (process.env.USER2_SEED) { const user2Wallet = Wallet.fromSeed(process.env.USER2_SEED.trim()) await client.fundWallet(user2Wallet) console.log(`✅ USER2 (${user2Wallet.address}) 계정 활성화 완료`) } else { console.warn("⚠️ USER2_SEED 환경변수 없음") } } catch (err) { // faucet 호출 실패 시 오류 출력 console.error("❌ 계정 활성화 중 오류:", err) } finally { // 항상 연결 종료 await client.disconnect() console.log("🔄 연결 종료") } } // 직접 실행된 경우에만 faucetAll 실행 if (require.main === module) { faucetAll() }
TypeScript
복사

Step 3. 지갑 정보 조회 (WalletInfo.ts)

주체: 누구나
행동: account_info, account_lines 등으로 상태 조회
내용: XRP 잔액, Sequence, Flags, TrustLines, RegularKey 등
import dotenv from "dotenv" import path from "path" import { Client, Wallet } from "xrpl" // .env 파일 로드 (시드값 불러오기 위함) dotenv.config({ path: path.join(__dirname, "..", ".env") }) export async function WalletInfo() { // XRPL Devnet 노드에 연결 const client = new Client("wss://s.devnet.rippletest.net:51233") await client.connect() try { // 환경변수에서 시드값 로드 const adminSeed = process.env.ADMIN_SEED const userSeed = process.env.USER_SEED const user2Seed = process.env.USER2_SEED if (!adminSeed || !userSeed || !user2Seed) { throw new Error("환경변수 ADMIN_SEED, USER_SEED, USER2_SEED 모두 필요") } // Seed로 Wallet 객체 생성 const adminWallet = Wallet.fromSeed(adminSeed.trim()) const userWallet = Wallet.fromSeed(userSeed.trim()) const user2Wallet = Wallet.fromSeed(user2Seed.trim()) // 1) 각 계정의 XRP 잔액 조회 const adminBalance = await client.getXrpBalance(adminWallet.address) const userBalance = await client.getXrpBalance(userWallet.address) const user2Balance = await client.getXrpBalance(user2Wallet.address) // 2) 각 계정의 Account Info 조회 (시퀀스, Flags, RegularKey 등) const adminInfo = await client.request({ command: "account_info", account: adminWallet.address }) const userInfo = await client.request({ command: "account_info", account: userWallet.address }) const user2Info = await client.request({ command: "account_info", account: user2Wallet.address }) // 3) 각 계정의 TrustLine 목록 조회 const adminLines = await client.request({ command: "account_lines", account: adminWallet.address }) const userLines = await client.request({ command: "account_lines", account: userWallet.address }) const user2Lines = await client.request({ command: "account_lines", account: user2Wallet.address }) // 결과 출력 console.log("📌 지갑 정보") console.log( `ADMIN: ${adminWallet.address} | Balance: ${adminBalance} XRP | Sequence: ${adminInfo.result.account_data.Sequence} | Flags: ${adminInfo.result.account_data.Flags} | RegularKey: ${adminInfo.result.account_data.RegularKey ?? "없음"}` ) console.log( `USER: ${userWallet.address} | Balance: ${userBalance} XRP | Sequence: ${userInfo.result.account_data.Sequence} | Flags: ${userInfo.result.account_data.Flags} | RegularKey: ${userInfo.result.account_data.RegularKey ?? "없음"}` ) console.log( `USER2: ${user2Wallet.address} | Balance: ${user2Balance} XRP | Sequence: ${user2Info.result.account_data.Sequence} | Flags: ${user2Info.result.account_data.Flags} | RegularKey: ${user2Info.result.account_data.RegularKey ?? "없음"}` ) console.log( `TrustLines - ADMIN: ${adminLines.result.lines.length}, USER: ${userLines.result.lines.length}, USER2: ${user2Lines.result.lines.length}` ) } catch (error) { // 오류 발생 시 로그 출력 console.error("❌ 지갑 정보 조회 실패:", error) } finally { // 연결 종료 await client.disconnect() console.log("🔄 연결 종료") } } // 직접 실행된 경우 WalletInfo 실행 if (require.main === module) { WalletInfo() }
TypeScript
복사