81 lines
2.0 KiB
Go
81 lines
2.0 KiB
Go
|
package crypto
|
||
|
|
||
|
import (
|
||
|
"crypto"
|
||
|
"crypto/rand"
|
||
|
"crypto/rsa"
|
||
|
"encoding/json"
|
||
|
)
|
||
|
|
||
|
// SigningMethodRSA implements the RSA family of SigningMethods.
|
||
|
type SigningMethodRSA struct {
|
||
|
Name string
|
||
|
Hash crypto.Hash
|
||
|
_ struct{}
|
||
|
}
|
||
|
|
||
|
// Specific instances of RSA SigningMethods.
|
||
|
var (
|
||
|
// SigningMethodRS256 implements RS256.
|
||
|
SigningMethodRS256 = &SigningMethodRSA{
|
||
|
Name: "RS256",
|
||
|
Hash: crypto.SHA256,
|
||
|
}
|
||
|
|
||
|
// SigningMethodRS384 implements RS384.
|
||
|
SigningMethodRS384 = &SigningMethodRSA{
|
||
|
Name: "RS384",
|
||
|
Hash: crypto.SHA384,
|
||
|
}
|
||
|
|
||
|
// SigningMethodRS512 implements RS512.
|
||
|
SigningMethodRS512 = &SigningMethodRSA{
|
||
|
Name: "RS512",
|
||
|
Hash: crypto.SHA512,
|
||
|
}
|
||
|
)
|
||
|
|
||
|
// Alg implements the SigningMethod interface.
|
||
|
func (m *SigningMethodRSA) Alg() string { return m.Name }
|
||
|
|
||
|
// Verify implements the Verify method from SigningMethod.
|
||
|
// For this signing method, must be an *rsa.PublicKey.
|
||
|
func (m *SigningMethodRSA) Verify(raw []byte, sig Signature, key interface{}) error {
|
||
|
rsaKey, ok := key.(*rsa.PublicKey)
|
||
|
if !ok {
|
||
|
return ErrInvalidKey
|
||
|
}
|
||
|
return rsa.VerifyPKCS1v15(rsaKey, m.Hash, m.sum(raw), sig)
|
||
|
}
|
||
|
|
||
|
// Sign implements the Sign method from SigningMethod.
|
||
|
// For this signing method, must be an *rsa.PrivateKey structure.
|
||
|
func (m *SigningMethodRSA) Sign(data []byte, key interface{}) (Signature, error) {
|
||
|
rsaKey, ok := key.(*rsa.PrivateKey)
|
||
|
if !ok {
|
||
|
return nil, ErrInvalidKey
|
||
|
}
|
||
|
sigBytes, err := rsa.SignPKCS1v15(rand.Reader, rsaKey, m.Hash, m.sum(data))
|
||
|
if err != nil {
|
||
|
return nil, err
|
||
|
}
|
||
|
return Signature(sigBytes), nil
|
||
|
}
|
||
|
|
||
|
func (m *SigningMethodRSA) sum(b []byte) []byte {
|
||
|
h := m.Hash.New()
|
||
|
h.Write(b)
|
||
|
return h.Sum(nil)
|
||
|
}
|
||
|
|
||
|
// Hasher implements the SigningMethod interface.
|
||
|
func (m *SigningMethodRSA) Hasher() crypto.Hash { return m.Hash }
|
||
|
|
||
|
// MarshalJSON implements json.Marshaler.
|
||
|
// See SigningMethodECDSA.MarshalJSON() for information.
|
||
|
func (m *SigningMethodRSA) MarshalJSON() ([]byte, error) {
|
||
|
return []byte(`"` + m.Alg() + `"`), nil
|
||
|
}
|
||
|
|
||
|
var _ json.Marshaler = (*SigningMethodRSA)(nil)
|