Billeteras – Referencia del Go SDK
Descripción general
El módulo de billeteras en el Go SDK es responsable de:
- Representar una billetera de ULedger (
UL_Wallet) - Generar billeteras a partir de mnemonics, keys o JSON
- Persistir billeteras en disco (archivos
.ukey) - Reconstruir billeteras desde datos almacenados
- Gestionar la entropía BIP-39 y los mnemonics
Una billetera combina:
- Una dirección (derivada de la clave pública)
- Grupos de permisos (
AuthGroups) - Un par de claves criptográficas (
crypto.ULKey) usado para firmar transactions
Tipos principales
UL_Wallet
type UL_Wallet struct {
Address string `json:"address"`
Enabled bool `json:"enabled"`
Parent string `json:"parent"`
AuthGroups map[string]UL_AuthPermission `json:"authGroups"`
key crypto.ULKey `json:"-"`
}
Address– dirección de la billetera utilizada en la cadena y en las APIs.Enabled– indica si esta billetera está activa actualmente.Parent– dirección de la billetera padre (para jerarquías padre/hijo).AuthGroups– grupos de permisos lógicos.key– clave criptográfica en memoria (no serializada).
UL_AuthPermission
type UL_AuthPermission struct {
Create bool `json:"create"`
Read bool `json:"read"`
Update bool `json:"update"`
Delete bool `json:"delete"`
}
Define permisos CRUD para un nombre de grupo determinado (por ejemplo, "Wallet" o "wallet").
WalletData (estructura de persistencia)
type WalletData struct {
Address string `json:"address"`
Enabled bool `json:"enabled"`
Parent string `json:"parent"`
AuthGroups map[string]UL_AuthPermission `json:"authGroups"`
Mnemonic string `json:"mnemonic"`
KeyType crypto.KeyType `json:"keyType"`
PublicKeyHex string `json:"publicKeyHex"`
PrivateKeyHex string `json:"privateKeyHex"`
}
Esta es la estructura JSON utilizada al guardar/cargar billeteras (por ejemplo, desde archivos .ukey).
Constante de nombre de grupo de autenticación
const (
WALLET_GROUP_NAME = "wallet"
)
Un nombre de grupo predeterminado que puede usarse para permisos relacionados con billeteras.
Acceso a la key
(*UL_Wallet).GetKey
func (w *UL_Wallet) GetKey() crypto.ULKey
Devuelve el crypto.ULKey subyacente, que se utiliza para:
- Determinar el tipo de key (
GetType) - Obtener el hex de la clave pública/privada
- Firmar los compromisos de transactions
Esto es lo que usa la sesión de transaction cuando llama a wallet.GetKey().SignData(...).
Creación de billeteras
FromJson
func FromJson(data string, passphrase string) (*UL_Wallet, error)
Crea un UL_Wallet a partir de una cadena JSON que coincide con la estructura WalletData.
Qué hace:
-
Deserializa
dataenWalletData. -
Crea un
UL_Walletcon:Address,Parent,Enabled,AuthGroupsdel JSON.
-
Usa
KeyTypepara obtener uncrypto.ULKeyconcreto. -
Llama a:
GeneratePublicKeyFromHex(false, PublicKeyHex)GeneratePrivateKeyFromHex(PrivateKeyHex)
Si la reconstrucción de la key falla, se devuelve un error.
Usado en el CLI de transactions para cargar billeteras desde archivos (o JSON).
GetWalletFromHex
func GetWalletFromHex(
publicKeyHex, privateKeyHex string,
keyType crypto.KeyType,
) (UL_Wallet, error)
Crea una billetera directamente a partir del material de key proporcionado.
Pasos:
- Obtiene un
crypto.ULKeypara elkeyTypedado. - Llama a
GeneratePublicKeyFromHex(false, publicKeyHex). - Llama a
GeneratePrivateKeyFromHex(privateKeyHex). - Calcula la dirección como
ParseAddress(key.GetPublicKeyHex(false)). - Devuelve un
UL_Walletcon:Addressestablecido en la dirección derivadakeyestablecido en la key construida
Desde las pruebas:
-
Key válida → dirección no vacía
-
Se puede verificar que la clave privada va y viene correctamente:
if !strings.EqualFold(wallet.key.GetPrivateKeyHex(), privateKeyHex) {// discrepancia}
ParseAddress
func ParseAddress(publicKeyHex string) string
Deriva la dirección de la billetera a partir de la clave pública codificada en hex.
Algoritmo:
- Convierte el hex de la clave pública a minúsculas.
- Calcula
sha256sobre los bytes de la cadena en minúsculas. - Codifica el hash como hex.
Esta función determinista se usa tanto al generar nuevas billeteras como al reconstruir a partir de claves existentes.
GenerateFromMnemonic
func GenerateFromMnemonic(
mnemonic string,
passphrase string,
keyType crypto.KeyType,
) (UL_Wallet, error)
Crea una billetera a partir de un mnemonic BIP-39.
Flujo:
- Llama a
MnemonicToSeed(mnemonic, passphrase)para obtener una semilla. - Crea un
crypto.ULKeybasado enkeyType. - Llama a
GenerateKeyFromSeed(seed)en la key. - Deriva la dirección de la billetera mediante
ParseAddress(key.GetPublicKeyHex(false)). - Devuelve un
UL_Walletcon:Addressestablecidokeypoblado (otros campos comoEnabled,Parent,AuthGroupsse completan después)
GenerateNewWallet
func GenerateNewWallet(
passphrase string,
keyType crypto.KeyType,
parent string,
authGroups map[string]UL_AuthPermission,
entropy Entropy,
) (UL_Wallet, string, error)
Genera una nueva billetera + mnemonic.
Pasos:
-
Llama a
GenerateMnemonic(entropy)para obtener una frase BIP-39. -
Llama a
GenerateFromMnemonic(mnemonic, passphrase, keyType)para derivar una key. -
Establece:
wallet.Parent = parentwallet.Enabled = truewallet.AuthGroups = authGroups
-
Devuelve:
UL_Walletmnemonic(string)error
Esto es lo que el comando CLI de "Generar Billetera" envuelve en última instancia.
Guardar y cargar billeteras
(*UL_Wallet).SaveToFile
func (w *UL_Wallet) SaveToFile(
filePath string,
mnemonic string,
includePrivateKey bool,
) error
Persiste una billetera en un archivo .ukey.
Comportamiento:
-
Asegura que la ruta del archivo termine con
.ukey. -
Construye un
WalletDatacon:Address,Parent,EnabledKeyType,MnemonicPublicKeyHexAuthGroups
-
Incluye
PrivateKeyHexsolo siincludePrivateKey == true. -
Escribe el JSON en disco con permisos
0600.
Esto permite elegir entre:
- Archivos de billetera "completos" (incluyen la clave privada)
- Archivos de billetera "solo públicos" (sin clave privada, para distribución más segura)
LoadFromFile
func LoadFromFile(
filePath string,
passphrase string,
) (UL_Wallet, error)
Lee un archivo .ukey y reconstruye un UL_Wallet.
Orden de prioridad:
-
Mnemonic presente →
GenerateFromMnemonic(mnemonic, passphrase, KeyType) -
Si no, si clave privada presente:
GetHasherByType(KeyType)GetKeyByType(KeyType, hasher)GeneratePublicKeyFromHex(false, PublicKeyHex)GeneratePrivateKeyFromHex(PrivateKeyHex)
-
Si no (sin mnemonic, sin clave privada):
- Usa solo
KeyType+PublicKeyHex(estilo solo-lectura) - Sin clave privada en memoria
- Usa solo
Esto permite:
- Recuperar billeteras completas desde frases semilla
- Reconstruir billeteras desde pares de claves conocidos
- Cargar billeteras de solo lectura desde claves públicas
Utilidades de entropía y mnemonic
El segundo archivo mostrado es la capa auxiliar BIP-39 usada por GenerateNewWallet y GenerateFromMnemonic.
Tipo Entropy y constantes
type Entropy int
const (
Entropy128 Entropy = 128
Entropy160 Entropy = 160
Entropy192 Entropy = 192
Entropy224 Entropy = 224
Entropy256 Entropy = 256
// Default entropy size (256 bits = 24 words)
DefaultEntropy = Entropy256
)
- La entropía se expresa en bits y se corresponde con conteos de palabras:
- 128 → 12 palabras
- 160 → 15 palabras
- 192 → 18 palabras
- 224 → 21 palabras
- 256 → 24 palabras
MakeEntropy
func MakeEntropy(i int) Entropy
Convierte un entero (128, 160, 192, 224, 256) en la constante Entropy correspondiente, usando DefaultEntropy por defecto en cualquier otro caso.
GenerateMnemonic
func GenerateMnemonic(entropySize Entropy) (string, error)
Genera una frase mnemonic BIP-39.
- Tamaños de entropía válidos: múltiplos de 32 entre 128 y 256 bits.
- Internamente:
- Usa
crypto/randpara generar entropía. - Usa
bip39.NewMnemonic(entropy)para derivar la frase.
- Usa
Usado por GenerateNewWallet.
MnemonicToSeed
func MnemonicToSeed(
mnemonic string,
passphrase string,
) ([]byte, error)
Convierte un mnemonic BIP-39 + passphrase opcional en una semilla.
- Valida el mnemonic mediante
bip39.IsMnemonicValid. - Usa
bip39.NewSeed(mnemonic, passphrase).
Usado por GenerateFromMnemonic.
Helpers de validación e inspección
func ValidateMnemonic(mnemonic string) bool
func GetWordList() []string
func GetWordIndex(word string) (int, error)
func GetWordCount(mnemonic string) int
func GetEntropySize(mnemonic string) (Entropy, error)
ValidateMnemonic– verifica si una frase es BIP-39 válida.GetWordList– devuelve el diccionario BIP-39 subyacente.GetWordIndex– encuentra el índice de una palabra en esa lista.GetWordCount– número de palabras en una frase.GetEntropySize– deriva el tamaño de entropía según el conteo de palabras (12/15/18/21/24).
Ejemplo: creación programática de billetera (referencia)
Un breve ejemplo de uso de la API anterior:
package main
import (
"fmt"
"github.com/ULedgerInc/go-sdk/pkg/crypto"
"github.com/ULedgerInc/go-sdk/pkg/wallet"
)
func main() {
passphrase := "optional-passphrase"
auth := map[string]wallet.UL_AuthPermission{
"Wallet": {Create: true, Read: true, Update: true, Delete: false},
}
w, mnemonic, err := wallet.GenerateNewWallet(
passphrase,
crypto.KeyTypeSecp256k1,
"", // parent
auth, // auth groups
wallet.Entropy256, // 24 words
)
if err != nil {
panic(err)
}
fmt.Println("Address:", w.Address)
fmt.Println("Mnemonic:", mnemonic)
if err := w.SaveToFile("./wallets/my-wallet.ukey", mnemonic, true); err != nil {
panic(err)
}
}
Luego se puede cargar con `LoadFromFile` o parsear el JSON almacenado y usar `FromJson`.