github.com/hyperledger/burrow@v0.34.5-0.20220512172541-77f09336001d/keys/key.go (about) 1 package keys 2 3 import ( 4 "encoding/json" 5 "fmt" 6 7 "github.com/hyperledger/burrow/crypto" 8 "github.com/tmthrgd/go-hex" 9 ) 10 11 type Key struct { 12 CurveType crypto.CurveType 13 Address crypto.Address 14 PublicKey crypto.PublicKey 15 PrivateKey crypto.PrivateKey 16 } 17 18 // json encodings - addresses should be hex encoded 19 type keyJSON struct { 20 CurveType string 21 Address string 22 PublicKey string 23 AddressHash string 24 PrivateKey privateKeyJSON 25 } 26 27 type privateKeyJSON struct { 28 Crypto string 29 Plain string `json:",omitempty"` 30 Salt []byte `json:",omitempty"` 31 Nonce []byte `json:",omitempty"` 32 CipherText []byte `json:",omitempty"` 33 } 34 35 func NewKey(typ crypto.CurveType) (*Key, error) { 36 privKey, err := crypto.GeneratePrivateKey(nil, typ) 37 if err != nil { 38 return nil, err 39 } 40 pubKey := privKey.GetPublicKey() 41 return &Key{ 42 CurveType: typ, 43 PublicKey: *pubKey, 44 Address: pubKey.GetAddress(), 45 PrivateKey: privKey, 46 }, nil 47 } 48 49 func NewKeyFromPub(curveType crypto.CurveType, PubKeyBytes []byte) (*Key, error) { 50 pubKey, err := crypto.PublicKeyFromBytes(PubKeyBytes, curveType) 51 if err != nil { 52 return nil, err 53 } 54 55 return &Key{ 56 CurveType: curveType, 57 PublicKey: *pubKey, 58 Address: pubKey.GetAddress(), 59 }, nil 60 } 61 62 func NewKeyFromPriv(curveType crypto.CurveType, PrivKeyBytes []byte) (*Key, error) { 63 privKey, err := crypto.PrivateKeyFromRawBytes(PrivKeyBytes, curveType) 64 65 if err != nil { 66 return nil, err 67 } 68 69 pubKey := privKey.GetPublicKey() 70 71 return &Key{ 72 CurveType: curveType, 73 Address: pubKey.GetAddress(), 74 PublicKey: *pubKey, 75 PrivateKey: privKey, 76 }, nil 77 } 78 79 func (k *Key) Pubkey() []byte { 80 return k.PublicKey.PublicKey 81 } 82 83 func (k *Key) MarshalJSON() (j []byte, err error) { 84 jStruct := keyJSON{ 85 CurveType: k.CurveType.String(), 86 Address: hex.EncodeUpperToString(k.Address[:]), 87 PublicKey: hex.EncodeUpperToString(k.Pubkey()), 88 AddressHash: k.PublicKey.AddressHashType(), 89 PrivateKey: privateKeyJSON{Crypto: CryptoNone, Plain: hex.EncodeUpperToString(k.PrivateKey.RawBytes())}, 90 } 91 j, err = json.Marshal(jStruct) 92 return j, err 93 } 94 95 func (k *Key) UnmarshalJSON(j []byte) (err error) { 96 keyJ := new(keyJSON) 97 err = json.Unmarshal(j, &keyJ) 98 if err != nil { 99 return err 100 } 101 if len(keyJ.PrivateKey.Plain) == 0 { 102 return fmt.Errorf("no private key") 103 } 104 curveType, err := crypto.CurveTypeFromString(keyJ.CurveType) 105 if err != nil { 106 curveType = crypto.CurveTypeEd25519 107 } 108 privKey, err := hex.DecodeString(keyJ.PrivateKey.Plain) 109 if err != nil { 110 return err 111 } 112 k2, err := NewKeyFromPriv(curveType, privKey) 113 if err != nil { 114 return err 115 } 116 117 k.Address = k2.Address 118 k.CurveType = curveType 119 k.PublicKey = *k2.PrivateKey.GetPublicKey() 120 k.PrivateKey = k2.PrivateKey 121 122 return nil 123 } 124 125 // returns the address if valid, nil otherwise 126 func isValidKeyJson(j []byte) []byte { 127 j1 := new(keyJSON) 128 e1 := json.Unmarshal(j, &j1) 129 if e1 == nil { 130 addr, _ := hex.DecodeString(j1.Address) 131 return addr 132 } 133 return nil 134 }