I am developing a method that will make a signature based in the type of private key that is passed as argument. To do that, I'm passing a *crypto.PrivateKey variable as argument. But the problem comes when I want to do a type assertion to use the argument.
func Sign(text string, privKey *crypto.PrivateKey) string{
if _, ok := (*privKey).(rsa.PrivateKey) //This is ok
if _, ok := (privKey).(*rsa.PrivateKey) //This is not ok 2
I guess I can do the first thing because if I use "*", the compiler think that it is an interface. But I don't know why I can't do the second thing, when it should be correct.
By the way, I need to use a variable of type *rsa.PrivateKey, I can do this this way:
privRsa, _ := (*privKey).(rsa.PrivateKey)
var priv *rsa.PrivateKey
priv = &privRsa
What I can not understand is why I can't directly convert the *crypto.PrivateKey into *rsa.PrivateKey, or if it exist a way to do that. I thing doing it the way I'm doing it right now would allocate new space in memory that I shouldn't if I want it to be efficient
CodePudding user response:
crypto.PrivateKey
is an interface. *crypto.PrivateKey
is a pointer to an interface. You can use type-assertion on an interface to get the underlying value:
func Sign(text string, privKey crypto.PrivateKey) string{
if _, ok := privKey.(rsa.PrivateKey)
...
}
...
var pkey rsa.PrivateKey
Sign(text,pkey)
Here, the private key value in the interface is a copy of the rsa.PrivateKey
.
If you pass the address of pkey
, then, then the interface would have a pointer to the private key:
func Sign(text string, privKey crypto.PrivateKey) string{
if _, ok := privKey.(*rsa.PrivateKey)
...
}
...
var pkey rsa.PrivateKey
Sign(text,&pkey)