seekia/internal/cryptography/nacl/nacl.go

100 lines
2.5 KiB
Go

// nacl provides functions to encrypt and decrypt data using Nacl
package nacl
// Public/Private keys are 32 bytes long
// Encrypted key is 80 bytes long
// When the keys need to be encoded as strings:
// Nacl public keys are encoded Base64
// Nacl private keys are encoded hex
import "seekia/internal/encoding"
import "golang.org/x/crypto/nacl/box"
import "crypto/rand"
import "errors"
func VerifyNaclPublicKeyString(inputKey string)bool{
_, err := ReadNaclPublicKeyString(inputKey)
if (err != nil){
return false
}
return true
}
func ReadNaclPublicKeyString(inputKey string)([32]byte, error){
decodedBytes, err := encoding.DecodeBase64StringToBytes(inputKey)
if (err != nil) {
return [32]byte{}, errors.New("ReadNaclPublicKeyString called with invalid key: " + inputKey)
}
if (len(decodedBytes) != 32){
return [32]byte{}, errors.New("ReadNaclPublicKeyString called with invalid key: " + inputKey)
}
publicKey := [32]byte(decodedBytes)
return publicKey, nil
}
func GetNewRandomPublicNaclKey()([32]byte, error){
var naclPublicKeyArray [32]byte
_, err := rand.Read(naclPublicKeyArray[:])
if (err != nil) { return [32]byte{}, err }
return naclPublicKeyArray, nil
}
func GetNewRandomPublicPrivateNaclKeys()([32]byte, [32]byte, error){
publicKeyArray, privateKeyArray, err := box.GenerateKey(rand.Reader)
if (err != nil) { return [32]byte{}, [32]byte{}, err }
return *publicKeyArray, *privateKeyArray, nil
}
//Outputs:
// -[80]byte: Nacl Encrypted Key
// -error
func EncryptKeyWithNacl(recipientPublicKey [32]byte, keyToEncrypt [32]byte)([80]byte, error){
encryptedKeyBytes, err := box.SealAnonymous(nil, keyToEncrypt[:], &recipientPublicKey, nil)
if (err != nil) { return [80]byte{}, err }
if (len(encryptedKeyBytes) != 80){
return [80]byte{}, errors.New("box.SealAnonymous returning invalid length encryptedKey.")
}
encryptedKeyArray := [80]byte(encryptedKeyBytes)
return encryptedKeyArray, nil
}
//Outputs:
// -bool: Able to decrypt
// -[32]byte: Decrypted key
// -error
func DecryptNaclEncryptedKey(encryptedKey [80]byte, recipientPublicKey [32]byte, recipientPrivateKey [32]byte)(bool, [32]byte, error) {
decryptedKey, success := box.OpenAnonymous(nil, encryptedKey[:], &recipientPublicKey, &recipientPrivateKey)
if (success == false) {
return false, [32]byte{}, nil
}
if (len(decryptedKey) != 32){
return false, [32]byte{}, errors.New("Invalid Nacl encrypted key length after decrypt.")
}
decryptedKeyArray := [32]byte(decryptedKey)
return true, decryptedKeyArray, nil
}