This commit is contained in:
2026-07-24 18:28:45 +03:00
parent 249ae14a71
commit d634ef4644
5 changed files with 74 additions and 7 deletions

View File

@@ -119,6 +119,17 @@ export interface OrgBalancesResponse {
has_errors: boolean has_errors: boolean
} }
export interface OrgMnemonicResponse {
mnemonic: string
}
export interface OrgSecretKey {
chain: string
address: string
derivation_path: string
private_key: string
}
export function getOrganizationWallets(): Promise<OrgWallet[]> { export function getOrganizationWallets(): Promise<OrgWallet[]> {
return doB2bRequest('/v1/organizations/wallets', {}, true) return doB2bRequest('/v1/organizations/wallets', {}, true)
} }
@@ -126,3 +137,11 @@ export function getOrganizationWallets(): Promise<OrgWallet[]> {
export function getOrganizationBalances(): Promise<OrgBalancesResponse> { export function getOrganizationBalances(): Promise<OrgBalancesResponse> {
return doB2bRequest('/v1/organizations/wallets/balances', {}, true) return doB2bRequest('/v1/organizations/wallets/balances', {}, true)
} }
export function getOrganizationMnemonic(): Promise<OrgMnemonicResponse> {
return doB2bRequest('/v1/organizations/wallets/mnemonic', {}, true)
}
export function getOrganizationSecretKeys(): Promise<OrgSecretKey[]> {
return doB2bRequest('/v1/organizations/wallets/secret-keys', {}, true)
}

View File

@@ -1,6 +1,11 @@
export { useCreatePurchaseRequest } from './hooks/useCreatePurchaseRequest' export { useCreatePurchaseRequest } from './hooks/useCreatePurchaseRequest'
export { useMyPurchaseRequests } from './hooks/useMyPurchaseRequests' export { useMyPurchaseRequests } from './hooks/useMyPurchaseRequests'
export { getOrganizationWallets, getOrganizationBalances } from './api/b2bApi' export {
getOrganizationWallets,
getOrganizationBalances,
getOrganizationMnemonic,
getOrganizationSecretKeys,
} from './api/b2bApi'
export type { export type {
CreatePurchaseRequestBody, CreatePurchaseRequestBody,
B2bPurchaseRequest, B2bPurchaseRequest,
@@ -9,6 +14,8 @@ export type {
OrgAmountRaw, OrgAmountRaw,
OrgWalletBalance, OrgWalletBalance,
OrgBalancesResponse, OrgBalancesResponse,
OrgMnemonicResponse,
OrgSecretKey,
} from './api/b2bApi' } from './api/b2bApi'
export { export {
MIN_ORDER, MIN_ORDER,

View File

@@ -3,6 +3,8 @@ import { tokenStore, refreshAccessToken } from '@shared/api/tokenStore'
import { import {
getOrganizationWallets, getOrganizationWallets,
getOrganizationBalances, getOrganizationBalances,
getOrganizationMnemonic,
getOrganizationSecretKeys,
type OrgAmountRaw, type OrgAmountRaw,
type OrgWalletBalance, type OrgWalletBalance,
} from '@features/b2b' } from '@features/b2b'
@@ -242,6 +244,28 @@ export async function getOrgWalletAddresses(): Promise<WalletAddress[]> {
return result return result
} }
export async function getOrgMnemonic(): Promise<string> {
const res = await getOrganizationMnemonic()
return res.mnemonic
}
export interface SecretKey {
chain: string
address: string
derivationPath: string
privateKey: string
}
export async function getOrgSecretKeys(): Promise<SecretKey[]> {
const keys = await getOrganizationSecretKeys()
return (keys ?? []).map((k) => ({
chain: k.chain,
address: k.address,
derivationPath: k.derivation_path,
privateKey: k.private_key,
}))
}
export interface TokenInfo { export interface TokenInfo {
chain: string chain: string
symbol: string symbol: string

View File

@@ -1,3 +1,3 @@
export { useAllWalletBalances, usePrices, useSendWallet, useWalletAddresses, useWalletBalance, usePortfolio, useTokensList, useRelayQuote, useExecuteRelaySwap, useSignSwap, useTrxSwapQuote, useFetchTrxQuote, useExecuteTrxSwap, useJumperTokens, useJumperQuote, useFetchJumperQuote, useExecuteBridge, useCreateWallet, useRevealMnemonic } from './model/useWalletData' export { useAllWalletBalances, usePrices, useSendWallet, useWalletAddresses, useWalletBalance, usePortfolio, useTokensList, useRelayQuote, useExecuteRelaySwap, useSignSwap, useTrxSwapQuote, useFetchTrxQuote, useExecuteTrxSwap, useJumperTokens, useJumperQuote, useFetchJumperQuote, useExecuteBridge, useCreateWallet, useRevealMnemonic, useOrgSecretKeys } from './model/useWalletData'
export type { Chain, FormattedAmount, WalletBalanceData, PriceEntry, SendWalletPayload, SendWalletResponse, WalletAddress, PortfolioData, PortfolioChain, TokenInfo, RelayQuotePayload, RelayQuoteResponse, RelaySwapResponse, RelaySwapStep, TrxSwapQuotePayload, TrxSwapQuoteData, JumperToken, JumperTokensMap, JumperQuote, JumperQuotePayload, JumperQuoteToken, JumperFeeCost, BridgeExecutePayload, BridgeExecuteResult } from './api/walletApi' export type { Chain, FormattedAmount, WalletBalanceData, PriceEntry, SendWalletPayload, SendWalletResponse, WalletAddress, SecretKey, PortfolioData, PortfolioChain, TokenInfo, RelayQuotePayload, RelayQuoteResponse, RelaySwapResponse, RelaySwapStep, TrxSwapQuotePayload, TrxSwapQuoteData, JumperToken, JumperTokensMap, JumperQuote, JumperQuotePayload, JumperQuoteToken, JumperFeeCost, BridgeExecutePayload, BridgeExecuteResult } from './api/walletApi'
export { CHAINS } from './api/walletApi' export { CHAINS } from './api/walletApi'

View File

@@ -1,6 +1,6 @@
import { useQuery, useQueries, useMutation } from '@tanstack/react-query' import { useQuery, useQueries, useMutation } from '@tanstack/react-query'
import { useMe } from '@features/auth' import { useMe } from '@features/auth'
import { getWalletBalance, getPrices, sendWallet, getWalletAddresses, getPortfolio, getOrgPortfolio, getOrgWalletBalance, getOrgWalletAddresses, getTokensList, getRelayQuote, executeRelaySwap, signRawEvmTx, signSolTx, getTrxSwapQuote, executeTrxSwap, getJumperTokens, getJumperQuote, executeBridge, createWallet, revealMnemonic, CHAINS, type Chain, type SendWalletPayload, type RelayQuotePayload, type RelaySwapStep, type TrxSwapQuotePayload, type JumperQuotePayload, type BridgeExecutePayload } from '../api/walletApi' import { getWalletBalance, getPrices, sendWallet, getWalletAddresses, getPortfolio, getOrgPortfolio, getOrgWalletBalance, getOrgWalletAddresses, getOrgMnemonic, getOrgSecretKeys, getTokensList, getRelayQuote, executeRelaySwap, signRawEvmTx, signSolTx, getTrxSwapQuote, executeTrxSwap, getJumperTokens, getJumperQuote, executeBridge, createWallet, revealMnemonic, CHAINS, type Chain, type SendWalletPayload, type RelayQuotePayload, type RelaySwapStep, type TrxSwapQuotePayload, type JumperQuotePayload, type BridgeExecutePayload } from '../api/walletApi'
/** Legal-entity accounts read wallet data from b2b instead of cryptowallet. */ /** Legal-entity accounts read wallet data from b2b instead of cryptowallet. */
function useIsLegalAccount() { function useIsLegalAccount() {
@@ -109,13 +109,30 @@ export function useCreateWallet() {
// `enabled` gates the request so callers can require an explicit user action // `enabled` gates the request so callers can require an explicit user action
// (e.g. a "Показать" button) before the mnemonic is fetched. Defaults to true // (e.g. a "Показать" button) before the mnemonic is fetched. Defaults to true
// to preserve the standalone /seed-phrase page behavior. // to preserve the standalone /seed-phrase page behavior.
// Legal-entity accounts read the mnemonic from b2b (organization wallet) instead
// of the individual cryptowallet endpoint. Wait for `me` before firing so the
// account type is known and we don't hit the wrong backend.
export function useRevealMnemonic(enabled = true) { export function useRevealMnemonic(enabled = true) {
const { isLegal, ready } = useIsLegalAccount()
return useQuery({ return useQuery({
queryKey: ['wallet', 'mnemonic'], queryKey: ['wallet', 'mnemonic', isLegal ? 'org' : 'self'],
queryFn: revealMnemonic, queryFn: isLegal ? getOrgMnemonic : revealMnemonic,
staleTime: Infinity, staleTime: Infinity,
retry: false, retry: false,
enabled, enabled: enabled && ready,
})
}
// Organization private keys (legal-entity only) — sourced from b2b. Gated behind
// `enabled` because exposing private keys must require an explicit user action.
export function useOrgSecretKeys(enabled = false) {
const { isLegal, ready } = useIsLegalAccount()
return useQuery({
queryKey: ['wallet', 'secret-keys', 'org'],
queryFn: getOrgSecretKeys,
staleTime: Infinity,
retry: false,
enabled: enabled && ready && isLegal,
}) })
} }