Ok, I found it in the grin-wallet src docs. But I’m having trouble translating the encrypt function to go.
original:
const encrypt = (str, nonce) => {
let key = Buffer.from(shared_secret, 'hex')
const cipher = crypto.createCipheriv(ALGO, key, nonce)
const enc = Buffer.concat([cipher.update(str, 'utf8'), cipher.final()])
const tag = cipher.getAuthTag()
return Buffer.concat([enc, tag]).toString('base64')
};
Any gophers here to show me what I’m missing here:
import (
"crypto/aes"
"crypto/cipher"
"crypto/rand"
"encoding/base64"
"encoding/hex"
"io"
)
func Encrypt(key, nonce, body []byte) (string, error) {
block, err := aes.NewCipher(key)
if err != nil {
return "", err
}
aesgcm, err := cipher.NewGCM(block)
if err != nil {
return "", err
}
cipherText := aesgcm.Seal(nil, nonce, body, nil)
return base64.StdEncoding.EncodeToString(cipherText), nil
}
Here’s how I computed my shared key:
import (
"encoding/json"
"fmt"
"os"
ecies "github.com/ecies/go"
log "github.com/sirupsen/logrus"
"github.com/ybbus/jsonrpc"
)
func InitSecureApi(conf GrinConfig) ([]byte, error) {
type Ok struct {
PublicKey string `json:"Ok"`
}
privateKey, err := ecies.GenerateKey()
if err != nil {
return []byte{}, fmt.Errorf("generate key pair failed: %s", err)
}
params := struct {
Public string `json:"ecdh_pubkey"`
}{
Public: privateKey.PublicKey.Hex(true),
}
rpcClient := jsonrpc.NewClient(conf.URL)
response, err := rpcClient.Call("init_secure_api", ¶ms)
if err != nil {
return []byte{}, fmt.Errorf("init_secure_api failed: %s", err)
}
var result Ok
err = response.GetObject(&result)
if err != nil {
return []byte{}, fmt.Errorf("get reponse object failed: %s", err)
}
log.Infof("received public key result: %s", result.PublicKey)
remotePublicKey, err := ecies.NewPublicKeyFromHex(result.PublicKey)
if err != nil {
return []byte{}, fmt.Errorf("failed remote public key %s", err)
}
sharedKey, err := privateKey.ECDH(remotePublicKey)
if err != nil {
return []byte{}, fmt.Errorf("failed ecdh %s", err)
}
return sharedKey, nil
}