Class: JOSE::JWK
- Inherits:
-
Struct
- Object
- Struct
- JOSE::JWK
- Defined in:
- lib/jose/jwk.rb
Overview
JWK stands for JSON Web Key which is defined in RFC 7517.
Defined Under Namespace
Modules: KTY, OpenSSHKey, PEM Classes: KTY_EC, KTY_OKP_Ed25519, KTY_OKP_Ed25519ph, KTY_OKP_Ed448, KTY_OKP_Ed448ph, KTY_OKP_X25519, KTY_OKP_X448, KTY_RSA, KTY_oct, PKeyProxy, Set
Instance Attribute Summary collapse
-
#fields ⇒ Object
Returns the value of attribute fields.
-
#keys ⇒ Object
Returns the value of attribute keys.
-
#kty ⇒ Object
Returns the value of attribute kty.
Class Method Summary collapse
-
.block_decrypt(jwk, encrypted) ⇒ [String, JOSE::JWE]
Decrypts the
encrypted
binary or map using thejwk
. -
.block_encrypt(jwk, plain_text, jwe = nil) ⇒ JOSE::EncryptedMap
Encrypts the
plain_text
using thejwk
and algorithms specified by thejwe
. -
.block_encryptor(jwk) ⇒ JOSE::Map+
Returns a block encryptor map for the key type.
-
.box_decrypt(jwk, encrypted, public_jwk = nil) ⇒ [String, JOSE::JWE]
Key Agreement decryption of the
encrypted
binary or map usingmy_private_jwk
. -
.box_encrypt(plain_text, box_keys, jwe = nil) ⇒ JOSE::EncryptedMap, [JOSE::EncryptedMap, JOSE::JWK]
Key Agreement encryption of
plain_text
by generating an ephemeral private key based onother_public_jwk
curve. -
.derive_key(jwk, *args) ⇒ String
Derives a key (typically just returns a binary representation of the key).
-
.from(object, modules = nil, key = nil) ⇒ JOSE::JWK+
Converts a binary or map into a
JOSE.JWK
. -
.from_binary(object, modules = nil, key = nil) ⇒ JOSE::JWK+
Converts a binary into a JOSE::JWK.
-
.from_file(file, modules = nil, key = nil) ⇒ JOSE::JWK
Reads file and calls JWK.from_binary to convert into a JOSE::JWK.
-
.from_key(object, modules = {}) ⇒ JOSE::JWK
Converts Ruby records for EC and RSA keys into a JOSE::JWK.
-
.from_map(object, modules = nil, key = nil) ⇒ JOSE::JWK+
Converts a map into a JOSE::JWK.
-
.from_oct(object, modules = {}) ⇒ JOSE::JWK
Converts an arbitrary binary into a JOSE::JWK with
"kty"
of"oct"
. -
.from_oct_file(file, modules = {}) ⇒ JOSE::JWK
Reads file and calls JOSE::JWK.from_oct to convert into a JOSE::JWK.
-
.from_okp(object, modules = {}) ⇒ JOSE::JWK
Converts an octet key pair into a JOSE::JWK with
"kty"
of"OKP"
. -
.from_openssh_key(object, modules = {}) ⇒ JOSE::JWK
Converts an openssh key into a JOSE::JWK with
"kty"
of"OKP"
. -
.from_openssh_key_file(file, modules = {}) ⇒ JOSE::JWK
Reads file and calls JOSE::JWK.from_openssh_key to convert into a JOSE::JWK.
-
.from_pem(object, modules = nil, password = nil) ⇒ JOSE::JWK
Converts a PEM (Privacy Enhanced Email) binary into a JOSE::JWK.
-
.from_pem_file(file, modules = nil, password = nil) ⇒ JOSE::JWK
Reads file and calls JOSE::JWK.from_pem to convert into a JOSE::JWK.
- .generate_key(params) ⇒ JOSE::JWK
-
.merge(left, right) ⇒ JOSE::JWK
Merges map on right into map on left.
-
.shared_secret(your_jwk, my_jwk) ⇒ String
Computes the shared secret between two keys.
-
.sign(plain_text, jws, jwk = nil, header = nil) ⇒ JOSE::SignedMap
Signs the
plain_text
using thejwk
and the default signer algorithmjws
for the key type. -
.signer(jwk) ⇒ JOSE::Map
Returns a signer map for the key type.
-
.thumbprint(digest_type, jwk = nil) ⇒ String
Returns the unique thumbprint for a JOSE::JWK using the
digest_type
. -
.to_binary(jwk, key = nil, jwe = nil) ⇒ String, ...
Converts a JOSE::JWK into a binary.
-
.to_file(jwk, file, key = nil, jwe = nil) ⇒ Fixnum
Calls JOSE::JWK.to_binary on a JOSE::JWK and then writes the binary to
file
. -
.to_key(jwk) ⇒ OpenSSL::PKey, Object
Converts a JOSE::JWK into the raw key format.
-
.to_map(jwk, key = nil, jwe = nil) ⇒ JOSE::Map+
Converts a JOSE::JWK into a map.
-
.to_oct(jwk) ⇒ String+
Converts a JOSE::JWK into a raw binary octet.
-
.to_oct_file(jwk, file) ⇒ Fixnum
Calls JOSE::JWK.to_oct on a JOSE::JWK and then writes the binary to
file
. -
.to_okp(jwk) ⇒ Object+
Converts a JOSE::JWK into an octet key pair.
-
.to_openssh_key(jwk) ⇒ Object+
Converts a JOSE::JWK into an OpenSSH key binary.
-
.to_openssh_key_file(jwk, file) ⇒ Fixnum
Calls JOSE::JWK.to_openssh_key on a JOSE::JWK and then writes the binary to
file
. -
.to_pem(jwk, password = nil) ⇒ String+
Converts a JOSE::JWK into a PEM (Privacy Enhanced Email) binary.
-
.to_pem_file(jwk, file, password = nil) ⇒ Fixnum
Calls JOSE::JWK.to_pem on a JOSE::JWK and then writes the binary to
file
. - .to_public(jwk) ⇒ JOSE::JWK+
-
.to_public_file(jwk, file) ⇒ Fixnum
Calls JOSE::JWK.to_binary on a JOSE::JWK and then writes the binary to
file
. -
.to_public_key(jwk) ⇒ OpenSSL::PKey, ...
Calls JOSE::JWK.to_public and then JOSE::JWK.to_key on a JOSE::JWK.
-
.to_public_map(jwk) ⇒ JOSE::Map+
Calls JOSE::JWK.to_public and then JOSE::JWK.to_map on a JOSE::JWK.
-
.to_thumbprint_map(jwk) ⇒ JOSE::Map+
Converts a JOSE::JWK into a map that can be used by JOSE::JWK.thumbprint.
-
.verifier(jwk) ⇒ Array<String>
Returns a verifier algorithm list for the key type.
-
.verify(signed, jwk) ⇒ [Boolean, String, JOSE::JWS]
Verifies the
signed
using thejwk
. -
.verify_strict(signed, allow, jwk) ⇒ [Boolean, String, JOSE::JWS]
Verifies the
signed
using thejwk
and whitelists the"alg"
usingallow
.
Instance Method Summary collapse
-
#block_decrypt(encrypted) ⇒ [String, JOSE::JWE]
Decrypts the
encrypted
binary or map using thejwk
. -
#block_encrypt(plain_text, jwe = nil) ⇒ JOSE::EncryptedMap
Encrypts the
plain_text
using thejwk
and algorithms specified by thejwe
. -
#block_encryptor ⇒ JOSE::Map
Returns a block encryptor map for the key type.
-
#box_decrypt(encrypted, public_jwk = nil) ⇒ [String, JOSE::JWE]
Key Agreement decryption of the
encrypted
binary or map usingmy_private_jwk
. -
#box_encrypt(plain_text, jwk_secret = nil, jwe = nil) ⇒ JOSE::EncryptedMap, [JOSE::EncryptedMap, JOSE::JWK]
Key Agreement encryption of
plain_text
by generating an ephemeral private key based onother_public_jwk
curve. -
#derive_key(*args) ⇒ String
Derives a key (typically just returns a binary representation of the key).
-
#generate_key ⇒ JOSE::JWK
Generates a new key based on the current one.
-
#merge(object) ⇒ JOSE::JWK
Merges object into current map.
-
#shared_secret(other_jwk) ⇒ String
Computes the shared secret between two keys.
-
#sign(plain_text, jws = nil, header = nil) ⇒ JOSE::SignedMap
Signs the
plain_text
using thejwk
and the default signer algorithmjws
for the key type. -
#signer ⇒ JOSE::Map
Returns a signer map for the key type.
-
#thumbprint(digest_type = nil) ⇒ String
Returns the unique thumbprint for a JOSE::JWK using the
digest_type
. -
#to_binary(key = nil, jwe = nil) ⇒ String, JOSE::EncryptedBinary
Converts a JOSE::JWK into a binary.
-
#to_file(file, key = nil, jwe = nil) ⇒ Fixnum
Calls JOSE::JWK.to_binary on a JOSE::JWK and then writes the binary to
file
. -
#to_key ⇒ OpenSSL::PKey, Object
Converts a JOSE::JWK into the raw key format.
-
#to_map(key = nil, jwe = nil) ⇒ JOSE::Map
Converts a JOSE::JWK into a map.
-
#to_oct ⇒ String
Converts a JOSE::JWK into a raw binary octet.
-
#to_oct_file(file) ⇒ Fixnum
Calls JOSE::JWK#to_oct on a JOSE::JWK and then writes the binary to
file
. -
#to_okp ⇒ String
Converts a JOSE::JWK into an octet key pair.
-
#to_openssh_key ⇒ Object
Converts a JOSE::JWK into an OpenSSH key binary.
-
#to_openssh_key_file(file) ⇒ Fixnum
Calls JOSE::JWK#to_openssh_key on a JOSE::JWK and then writes the binary to
file
. -
#to_pem(password = nil) ⇒ String
Converts a JOSE::JWK into a PEM (Privacy Enhanced Email) binary.
-
#to_pem_file(file, password = nil) ⇒ Fixnum
Calls JOSE::JWK#to_pem on a JOSE::JWK and then writes the binary to
file
. - #to_public ⇒ JOSE::JWK
-
#to_public_file(file) ⇒ Fixnum
Calls JOSE::JWK.to_public on a JOSE::JWK and then writes the binary to
file
. -
#to_public_key ⇒ OpenSSL::PKey, Object
Calls JOSE::JWK#to_public and then JOSE::JWK#to_key on a JOSE::JWK.
-
#to_public_map ⇒ JOSE::Map
Calls JOSE::JWK#to_public and then JOSE::JWK#to_map on a JOSE::JWK.
-
#to_thumbprint_map ⇒ JOSE::Map
Converts a JOSE::JWK into a map that can be used by JOSE::JWK.thumbprint.
-
#verifier ⇒ Array<String>
Returns a verifier algorithm list for the key type.
-
#verify(signed) ⇒ [Boolean, String, JOSE::JWS]
Verifies the
signed
using thejwk
. -
#verify_strict(signed, allow) ⇒ [Boolean, String, JOSE::JWS]
Verifies the
signed
using thejwk
and whitelists the"alg"
usingallow
.
Instance Attribute Details
#fields ⇒ Object
Returns the value of attribute fields
3 4 5 |
# File 'lib/jose/jwk.rb', line 3 def fields @fields end |
#keys ⇒ Object
Returns the value of attribute keys
3 4 5 |
# File 'lib/jose/jwk.rb', line 3 def keys @keys end |
#kty ⇒ Object
Returns the value of attribute kty
3 4 5 |
# File 'lib/jose/jwk.rb', line 3 def kty @kty end |
Class Method Details
.block_decrypt(jwk, encrypted) ⇒ [String, JOSE::JWE]
Decrypts the encrypted
binary or map using the jwk
.
599 600 601 602 603 604 605 606 607 608 609 610 |
# File 'lib/jose/jwk.rb', line 599 def self.block_decrypt(jwk, encrypted) if jwk.is_a?(Array) public_jwk, secret_jwk = from(jwk) if secret_jwk.nil? secret_jwk = public_jwk public_jwk = nil end return box_decrypt(secret_jwk, encrypted, public_jwk) else return from(jwk).block_decrypt(encrypted) end end |
.block_encrypt(jwk, plain_text, jwe = nil) ⇒ JOSE::EncryptedMap
Encrypts the plain_text
using the jwk
and algorithms specified by the jwe
.
628 629 630 631 632 633 634 |
# File 'lib/jose/jwk.rb', line 628 def self.block_encrypt(jwk, plain_text, jwe = nil) if jwk.is_a?(Array) return box_encrypt(plain_text, from(jwk), jwe) else return from(jwk).block_encrypt(plain_text, jwe) end end |
.block_encryptor(jwk) ⇒ JOSE::Map+
Returns a block encryptor map for the key type.
651 652 653 654 655 656 657 |
# File 'lib/jose/jwk.rb', line 651 def self.block_encryptor(jwk) if jwk.is_a?(Array) return from(jwk).map { |obj| obj.block_encryptor } else return from(jwk).block_encryptor end end |
.box_decrypt(jwk, encrypted, public_jwk = nil) ⇒ [String, JOSE::JWE]
Key Agreement decryption of the encrypted
binary or map using my_private_jwk
.
674 675 676 |
# File 'lib/jose/jwk.rb', line 674 def self.box_decrypt(jwk, encrypted, public_jwk = nil) return from(jwk).box_decrypt(encrypted, public_jwk) end |
.box_encrypt(plain_text, box_keys, jwe = nil) ⇒ JOSE::EncryptedMap, [JOSE::EncryptedMap, JOSE::JWK]
Key Agreement encryption of plain_text
by generating an ephemeral private key based on other_public_jwk
curve.
If no private key has been specified in box_keys
, it generates an ephemeral private key based on other public key curve.
703 704 705 706 |
# File 'lib/jose/jwk.rb', line 703 def self.box_encrypt(plain_text, box_keys, jwe = nil) jwk_public, jwk_secret = from(box_keys) return jwk_public.box_encrypt(plain_text, jwk_secret, jwe) end |
.derive_key(jwk, *args) ⇒ String
Derives a key (typically just returns a binary representation of the key).
756 757 758 |
# File 'lib/jose/jwk.rb', line 756 def self.derive_key(jwk, *args) return from(jwk).derive_key(*args) end |
.from(object, modules = nil, key = nil) ⇒ JOSE::JWK+
Converts a binary or map into a JOSE.JWK
.
JOSE::JWK.from({"k" => "", "kty" => "oct"})
# => #<struct JOSE::JWK keys=nil, kty=#<struct JOSE::JWK::KTY_oct oct="">, fields=JOSE::Map[]>
JOSE::JWK.from("{\"k\":\"\",\"kty\":\"oct\"}")
# => #<struct JOSE::JWK keys=nil, kty=#<struct JOSE::JWK::KTY_oct oct="">, fields=JOSE::Map[]>
The "kty"
field may be overridden with a custom module that implements the JOSE::JWK::KTY behaviours.
For example:
JOSE::JWK.from({ "kty" => "custom" }, { kty: MyCustomKey })
# => #<struct JOSE::JWK keys=nil, kty=#<MyCustomKey:0x007f8c5419ff68>, fields=JOSE::Map[]>
If a key
has been specified, it will decrypt an encrypted binary or map into a JOSE::JWK using the specified key
.
JOSE::JWK.from("eyJhbGciOiJQQkVTMi1IUzI1NitBMTI4S1ciLCJjdHkiOiJqd2sranNvbiIsImVuYyI6IkExMjhHQ00iLCJwMmMiOjQwOTYsInAycyI6Im5OQ1ZNQUktNTU5UVFtbWRFcnBsZFEifQ.Ucye69ii4dxd1ykNFlJyBVeA6xeNu4aV.2pZ4nBoxBjmdrneS.boqwdFZVNAFHk1M5P6kPYgBUgGwW32QuKzHuFA.wL9Hy6dcE_DPkUW9s5iwKA", "password")
# => [#<struct JOSE::JWK keys=nil, kty=#<struct JOSE::JWK::KTY_oct oct="secret">, fields=JOSE::Map[]>,
# #<struct JOSE::JWE
# alg=
# #<struct JOSE::JWE::ALG_PBES2
# hmac=OpenSSL::Digest::SHA256,
# bits=128,
# salt="PBES2-HS256+A128KW\x00\x9C\xD0\x950\x02>\xE7\x9FPBi\x9D\x12\xBAeu",
# iter=4096>,
# enc=#<struct JOSE::JWE::ENC_AES_GCM cipher_name="aes-128-gcm", bits=128, cek_len=16, iv_len=12>,
# zip=nil,
# fields=JOSE::Map["cty" => "jwk+json"]>]
43 44 45 46 47 48 49 50 51 52 53 54 55 56 |
# File 'lib/jose/jwk.rb', line 43 def self.from(object, modules = nil, key = nil) case object when JOSE::Map, Hash return from_map(object, modules, key) when String return from_binary(object, modules, key) when JOSE::JWK return object when Array return object.map { |obj| from(obj, modules, key) } else raise ArgumentError, "'object' must be a Hash, String, JOSE::JWK, or Array" end end |
.from_binary(object, modules = nil, key = nil) ⇒ JOSE::JWK+
Converts a binary into a JOSE::JWK.
64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 |
# File 'lib/jose/jwk.rb', line 64 def self.from_binary(object, modules = nil, key = nil) if (modules.is_a?(String) or modules.is_a?(JOSE::JWK)) and key.nil? key = modules modules = {} end modules ||= {} case object when String if key plain_text, jwe = JOSE::JWE.block_decrypt(key, object) return from_binary(plain_text, modules), jwe else return from_map(JOSE.decode(object), modules) end when Array return object.map { |obj| from_binary(obj, modules, key) } else raise ArgumentError, "'object' must be a String or Array" end end |
.from_file(file, modules = nil, key = nil) ⇒ JOSE::JWK
Reads file and calls from_binary to convert into a JOSE::JWK.
91 92 93 |
# File 'lib/jose/jwk.rb', line 91 def self.from_file(file, modules = nil, key = nil) return from_binary(File.binread(file), modules, key) end |
.from_key(object, modules = {}) ⇒ JOSE::JWK
Converts Ruby records for EC and RSA keys into a JOSE::JWK.
100 101 102 103 |
# File 'lib/jose/jwk.rb', line 100 def self.from_key(object, modules = {}) kty = modules[:kty] || JOSE::JWK::KTY return JOSE::JWK.new(nil, *kty.from_key(object)) end |
.from_map(object, modules = nil, key = nil) ⇒ JOSE::JWK+
Converts a map into a JOSE::JWK.
111 112 113 114 115 116 117 118 119 120 121 122 123 124 125 126 127 128 129 130 |
# File 'lib/jose/jwk.rb', line 111 def self.from_map(object, modules = nil, key = nil) if (modules.is_a?(String) or modules.is_a?(JOSE::JWK)) and key.nil? key = modules modules = {} end modules ||= {} case object when JOSE::Map, Hash if key plain_text, jwe = JOSE::JWE.block_decrypt(key, object) return from_binary(plain_text, modules), jwe else return from_fields(JOSE::JWK.new(nil, nil, JOSE::Map.new(object)), modules) end when Array return object.map { |obj| from_map(obj, modules, key) } else raise ArgumentError, "'object' must be a JOSE::Map, Hash, or Array" end end |
.from_oct(object, modules = {}) ⇒ JOSE::JWK
Converts an arbitrary binary into a JOSE::JWK with "kty"
of "oct"
.
137 138 139 140 |
# File 'lib/jose/jwk.rb', line 137 def self.from_oct(object, modules = {}) kty = modules[:kty] || JOSE::JWK::KTY_oct return JOSE::JWK.new(nil, *kty.from_oct(object)) end |
.from_oct_file(file, modules = {}) ⇒ JOSE::JWK
Reads file and calls JOSE::JWK.from_oct to convert into a JOSE::JWK.
147 148 149 |
# File 'lib/jose/jwk.rb', line 147 def self.from_oct_file(file, modules = {}) return from_oct(File.binread(file), modules) end |
.from_okp(object, modules = {}) ⇒ JOSE::JWK
Converts an octet key pair into a JOSE::JWK with "kty"
of "OKP"
.
156 157 158 159 160 161 162 163 164 165 166 167 168 169 170 171 172 173 174 175 |
# File 'lib/jose/jwk.rb', line 156 def self.from_okp(object, modules = {}) raise ArgumentError, "object must be an Array of length 2" if not object.is_a?(Array) or object.length != 2 kty = modules[:kty] || case object[0] when :Ed25519 JOSE::JWK::KTY_OKP_Ed25519 when :Ed25519ph JOSE::JWK::KTY_OKP_Ed25519ph when :Ed448 JOSE::JWK::KTY_OKP_Ed448 when :Ed448ph JOSE::JWK::KTY_OKP_Ed448ph when :X25519 JOSE::JWK::KTY_OKP_X25519 when :X448 JOSE::JWK::KTY_OKP_X448 else raise ArgumentError, "unrecognized :okp object" end return JOSE::JWK.new(nil, *kty.from_okp(object)) end |
.from_openssh_key(object, modules = {}) ⇒ JOSE::JWK
Converts an openssh key into a JOSE::JWK with "kty"
of "OKP"
.
182 183 184 185 186 187 188 189 190 191 192 193 194 195 196 197 198 199 200 201 202 203 204 205 206 207 208 209 210 211 |
# File 'lib/jose/jwk.rb', line 182 def self.from_openssh_key(object, modules = {}) raise ArgumentError, "object must be a String or Array" if not object.is_a?(String) and not object.is_a?(Array) keys = object if object.is_a?(String) keys = JOSE::JWK::OpenSSHKey.from_binary(object) end ((pk_type, pk), key), = keys[0] sk_type, sk_pk, = key if pk_type and pk and key and sk_type and sk_pk and pk_type == sk_type and pk == sk_pk kty = modules[:kty] || case pk_type when 'ssh-ed25519' JOSE::JWK::KTY_OKP_Ed25519 when 'ssh-ed25519ph' JOSE::JWK::KTY_OKP_Ed25519ph when 'ssh-ed448' JOSE::JWK::KTY_OKP_Ed448 when 'ssh-ed448ph' JOSE::JWK::KTY_OKP_Ed448ph when 'ssh-x25519' JOSE::JWK::KTY_OKP_X25519 when 'ssh-x448' JOSE::JWK::KTY_OKP_X448 else raise ArgumentError, "unrecognized openssh key type: #{pk_type.inspect}" end return JOSE::JWK.new(nil, *kty.from_openssh_key(key)) else raise ArgumentError, "unrecognized openssh key format" end end |
.from_openssh_key_file(file, modules = {}) ⇒ JOSE::JWK
Reads file and calls JOSE::JWK.from_openssh_key to convert into a JOSE::JWK.
218 219 220 |
# File 'lib/jose/jwk.rb', line 218 def self.from_openssh_key_file(file, modules = {}) return from_openssh_key(File.binread(file), modules) end |
.from_pem(object, modules = nil, password = nil) ⇒ JOSE::JWK
230 231 232 233 234 235 236 237 238 |
# File 'lib/jose/jwk.rb', line 230 def self.from_pem(object, modules = nil, password = nil) if modules.is_a?(String) and password.nil? password = modules modules = {} end modules ||= {} kty = modules[:kty] || JOSE::JWK::PEM return JOSE::JWK.new(nil, *kty.from_binary(object, password)) end |
.from_pem_file(file, modules = nil, password = nil) ⇒ JOSE::JWK
Reads file and calls JOSE::JWK.from_pem to convert into a JOSE::JWK.
246 247 248 |
# File 'lib/jose/jwk.rb', line 246 def self.from_pem_file(file, modules = nil, password = nil) return from_pem(File.binread(file), modules, password) end |
.generate_key(params) ⇒ JOSE::JWK
Generates a new JOSE::JWK based on another JOSE::JWK or from initialization params provided.
Passing another JOSE::JWK results in different behavior depending on the "kty"
:
"EC"
- uses the same named curve to generate a new key"oct"
- uses the byte size to generate a new key"OKP"
- uses the named curve to generate a new key"RSA"
- uses the same modulus and exponent sizes to generate a new key
The following initialization params may also be used:
[:ec, "P-256" | "P-384" | "P-521"]
- generates an"EC"
key using the"P-256"
,"P-384"
, or"P-521"
curves[:oct, bytes]
- generates an"oct"
key made of a randombytes
number of bytes[:okp, :Ed25519 | :Ed25519ph | :Ed448 | :Ed448ph | :X25519 | :X448]
- generates an"OKP"
key using the specified curve[:rsa, modulus_size] | [:rsa, modulus_size, exponent_size]
- generates an"RSA"
key using themodulus_size
andexponent_size
786 787 788 789 790 791 792 793 794 795 796 797 798 799 800 801 802 803 804 805 806 807 808 809 810 811 812 813 814 815 816 817 818 819 820 821 822 |
# File 'lib/jose/jwk.rb', line 786 def self.generate_key(params) if params.is_a?(Array) and (params.length == 2 or params.length == 3) case params[0] when :ec return JOSE::JWK.new(nil, *JOSE::JWK::KTY_EC.generate_key(params)) when :oct return JOSE::JWK.new(nil, *JOSE::JWK::KTY_oct.generate_key(params)) when :okp case params[1] when :Ed25519 return JOSE::JWK.new(nil, *JOSE::JWK::KTY_OKP_Ed25519.generate_key(params)) when :Ed25519ph return JOSE::JWK.new(nil, *JOSE::JWK::KTY_OKP_Ed25519ph.generate_key(params)) when :Ed448 return JOSE::JWK.new(nil, *JOSE::JWK::KTY_OKP_Ed448.generate_key(params)) when :Ed448ph return JOSE::JWK.new(nil, *JOSE::JWK::KTY_OKP_Ed448ph.generate_key(params)) when :X25519 return JOSE::JWK.new(nil, *JOSE::JWK::KTY_OKP_X25519.generate_key(params)) when :X448 return JOSE::JWK.new(nil, *JOSE::JWK::KTY_OKP_X448.generate_key(params)) else raise ArgumentError, "invalid :okp key generation params" end when :rsa return JOSE::JWK.new(nil, *JOSE::JWK::KTY_RSA.generate_key(params)) else raise ArgumentError, "invalid key generation params" end elsif params.is_a?(JOSE::JWK) return params.generate_key elsif params.respond_to?(:generate_key) return JOSE::JWK.new(nil, *params.generate_key(JOSE::Map[])) else raise ArgumentError, "invalid key generation params" end end |
.merge(left, right) ⇒ JOSE::JWK
Merges map on right into map on left.
835 836 837 |
# File 'lib/jose/jwk.rb', line 835 def self.merge(left, right) return from(left).merge(right) end |
.shared_secret(your_jwk, my_jwk) ⇒ String
Computes the shared secret between two keys.
Currently only works for "EC"
keys and "OKP"
keys with "crv"
set to "X25519"
or "X448"
.
863 864 865 |
# File 'lib/jose/jwk.rb', line 863 def self.shared_secret(your_jwk, my_jwk) return from(your_jwk).shared_secret(from(my_jwk)) end |
.sign(plain_text, jws, jwk = nil, header = nil) ⇒ JOSE::SignedMap
Signs the plain_text
using the jwk
and the default signer algorithm jws
for the key type.
888 889 890 891 892 893 894 |
# File 'lib/jose/jwk.rb', line 888 def self.sign(plain_text, jws, jwk = nil, header = nil) if jwk.nil? jwk = jws jws = nil end return from(jwk).sign(plain_text, jws, header) end |
.signer(jwk) ⇒ JOSE::Map
Returns a signer map for the key type.
912 913 914 |
# File 'lib/jose/jwk.rb', line 912 def self.signer(jwk) return from(jwk).signer end |
.thumbprint(digest_type, jwk = nil) ⇒ String
Returns the unique thumbprint for a JOSE::JWK using the digest_type
.
# let's define two different keys that will have the same thumbprint
jwk1 = JOSE::JWK.from_oct("secret")
jwk2 = JOSE::JWK.from({ "use" => "sig", "k" => "c2VjcmV0", "kty" => "oct" })
JOSE::JWK.thumbprint(jwk1)
# => "DWBh0SEIAPYh1x5uvot4z3AhaikHkxNJa3Ada2fT-Cg"
JOSE::JWK.thumbprint(jwk2)
# => "DWBh0SEIAPYh1x5uvot4z3AhaikHkxNJa3Ada2fT-Cg"
JOSE::JWK.thumbprint('MD5', jwk1)
# => "Kldz8k5PQm7y1E3aNBlMiA"
JOSE::JWK.thumbprint('MD5', jwk2)
# => "Kldz8k5PQm7y1E3aNBlMiA"
943 944 945 946 947 948 949 |
# File 'lib/jose/jwk.rb', line 943 def self.thumbprint(digest_type, jwk = nil) if jwk.nil? jwk = digest_type digest_type = nil end return from(jwk).thumbprint(digest_type) end |
.to_binary(jwk, key = nil, jwe = nil) ⇒ String, ...
Converts a JOSE::JWK into a binary.
258 259 260 261 262 263 264 |
# File 'lib/jose/jwk.rb', line 258 def self.to_binary(jwk, key = nil, jwe = nil) if jwk.is_a?(Array) return jwk.map { |obj| from(obj).to_binary(key, jwe) } else return from(jwk).to_binary(key, jwe) end end |
.to_file(jwk, file, key = nil, jwe = nil) ⇒ Fixnum
Calls JOSE::JWK.to_binary on a JOSE::JWK and then writes the binary to file
.
289 290 291 |
# File 'lib/jose/jwk.rb', line 289 def self.to_file(jwk, file, key = nil, jwe = nil) return from(jwk).to_file(file, key, jwe) end |
.to_key(jwk) ⇒ OpenSSL::PKey, Object
Converts a JOSE::JWK into the raw key format.
307 308 309 |
# File 'lib/jose/jwk.rb', line 307 def self.to_key(jwk) return from(jwk).to_key end |
.to_map(jwk, key = nil, jwe = nil) ⇒ JOSE::Map+
Converts a JOSE::JWK into a map.
324 325 326 327 328 329 330 |
# File 'lib/jose/jwk.rb', line 324 def self.to_map(jwk, key = nil, jwe = nil) if jwk.is_a?(Array) return from(jwk).map { |obj| obj.to_map(key, jwe) } else return from(jwk).to_map(key, jwe) end end |
.to_oct(jwk) ⇒ String+
Converts a JOSE::JWK into a raw binary octet.
352 353 354 355 356 357 358 |
# File 'lib/jose/jwk.rb', line 352 def self.to_oct(jwk) if jwk.is_a?(Array) return from(jwk).map { |obj| obj.to_oct } else return from(jwk).to_oct end end |
.to_oct_file(jwk, file) ⇒ Fixnum
Calls JOSE::JWK.to_oct on a JOSE::JWK and then writes the binary to file
.
372 373 374 |
# File 'lib/jose/jwk.rb', line 372 def self.to_oct_file(jwk, file) return from(jwk).to_file(file) end |
.to_okp(jwk) ⇒ Object+
Converts a JOSE::JWK into an octet key pair.
388 389 390 391 392 393 394 |
# File 'lib/jose/jwk.rb', line 388 def self.to_okp(jwk) if jwk.is_a?(Array) return from(jwk).map { |obj| obj.to_okp } else return from(jwk).to_okp end end |
.to_openssh_key(jwk) ⇒ Object+
Converts a JOSE::JWK into an OpenSSH key binary.
407 408 409 410 411 412 413 |
# File 'lib/jose/jwk.rb', line 407 def self.to_openssh_key(jwk) if jwk.is_a?(Array) return from(jwk).map { |obj| obj.to_openssh_key } else return from(jwk).to_openssh_key end end |
.to_openssh_key_file(jwk, file) ⇒ Fixnum
Calls JOSE::JWK.to_openssh_key on a JOSE::JWK and then writes the binary to file
.
427 428 429 |
# File 'lib/jose/jwk.rb', line 427 def self.to_openssh_key_file(jwk, file) return from(jwk).to_file(file) end |
.to_pem(jwk, password = nil) ⇒ String+
Converts a JOSE::JWK into a PEM (Privacy Enhanced Email) binary.
444 445 446 447 448 449 450 |
# File 'lib/jose/jwk.rb', line 444 def self.to_pem(jwk, password = nil) if jwk.is_a?(Array) return from(jwk).map { |obj| obj.to_pem(password) } else return from(jwk).to_pem(password) end end |
.to_pem_file(jwk, file, password = nil) ⇒ Fixnum
Calls JOSE::JWK.to_pem on a JOSE::JWK and then writes the binary to file
.
466 467 468 |
# File 'lib/jose/jwk.rb', line 466 def self.to_pem_file(jwk, file, password = nil) return from(jwk).to_file(file, password) end |
.to_public(jwk) ⇒ JOSE::JWK+
Converts a private JOSE::JWK into a public JOSE::JWK.
jwk_rsa = JOSE::JWK.generate_key([:rsa, 256]).to_map
# => JOSE::Map[
# "dq" => "Iv_BghpjRyv8hk4AgsX_3w",
# "e" => "AQAB",
# "d" => "imiCh2gK77pDAa_NuQbHN1hZdLY0eTl8tp4WLfe1uQ0",
# "p" => "-eKE_wk7O5JWw_1fw-rciw",
# "qi" => "MqCwIoTTCkYmGQHsOM7IuA",
# "n" => "vj2WbxlGF1yU9SoQJMqKw6c2asTks_cVuXEAO3x_yOU",
# "kty" => "RSA",
# "q" => "wuVog_0-60w7_56y8wZuTw",
# "dp" => "lU_9GEdz1UzD-6hSqMaVsQ"]
JOSE::JWK.to_public(jwk_rsa).to_map
# => JOSE::Map[
# "e" => "AQAB",
# "n" => "vj2WbxlGF1yU9SoQJMqKw6c2asTks_cVuXEAO3x_yOU",
# "kty" => "RSA"]
501 502 503 504 505 506 507 |
# File 'lib/jose/jwk.rb', line 501 def self.to_public(jwk) if jwk.is_a?(Array) return from(jwk).map { |obj| obj.to_public } else return from(jwk).to_public end end |
.to_public_file(jwk, file) ⇒ Fixnum
Calls JOSE::JWK.to_binary on a JOSE::JWK and then writes the binary to file
.
522 523 524 |
# File 'lib/jose/jwk.rb', line 522 def self.to_public_file(jwk, file) return from(jwk).to_public_file(file) end |
.to_public_key(jwk) ⇒ OpenSSL::PKey, ...
Calls JOSE::JWK.to_public and then JOSE::JWK.to_key on a JOSE::JWK.
538 539 540 541 542 543 544 |
# File 'lib/jose/jwk.rb', line 538 def self.to_public_key(jwk) if jwk.is_a?(Array) return from(jwk).map { |obj| obj.to_public_key } else return from(jwk).to_public_key end end |
.to_public_map(jwk) ⇒ JOSE::Map+
Calls JOSE::JWK.to_public and then JOSE::JWK.to_map on a JOSE::JWK.
557 558 559 560 561 562 563 |
# File 'lib/jose/jwk.rb', line 557 def self.to_public_map(jwk) if jwk.is_a?(Array) return from(jwk).map { |obj| obj.to_public_map } else return from(jwk).to_public_map end end |
.to_thumbprint_map(jwk) ⇒ JOSE::Map+
Converts a JOSE::JWK into a map that can be used by JOSE::JWK.thumbprint.
576 577 578 579 580 581 582 |
# File 'lib/jose/jwk.rb', line 576 def self.to_thumbprint_map(jwk) if jwk.is_a?(Array) return from(jwk).map { |obj| obj.to_thumbprint_map } else return from(jwk).to_thumbprint_map end end |
.verifier(jwk) ⇒ Array<String>
Returns a verifier algorithm list for the key type.
967 968 969 970 971 972 973 |
# File 'lib/jose/jwk.rb', line 967 def self.verifier(jwk) if jwk.is_a?(Array) return from(jwk).map { |obj| obj.verifier } else return from(jwk).verifier end end |
.verify(signed, jwk) ⇒ [Boolean, String, JOSE::JWS]
Verifies the signed
using the jwk
.
988 989 990 |
# File 'lib/jose/jwk.rb', line 988 def self.verify(signed, jwk) return from(jwk).verify(signed) end |
.verify_strict(signed, allow, jwk) ⇒ [Boolean, String, JOSE::JWS]
Verifies the signed
using the jwk
and whitelists the "alg"
using allow
.
1008 1009 1010 |
# File 'lib/jose/jwk.rb', line 1008 def self.verify_strict(signed, allow, jwk) return from(jwk).verify_strict(signed, allow) end |
Instance Method Details
#block_decrypt(encrypted) ⇒ [String, JOSE::JWE]
Decrypts the encrypted
binary or map using the jwk
.
617 618 619 |
# File 'lib/jose/jwk.rb', line 617 def block_decrypt(encrypted) return JOSE::JWE.block_decrypt(self, encrypted) end |
#block_encrypt(plain_text, jwe = nil) ⇒ JOSE::EncryptedMap
Encrypts the plain_text
using the jwk
and algorithms specified by the jwe
.
642 643 644 645 |
# File 'lib/jose/jwk.rb', line 642 def block_encrypt(plain_text, jwe = nil) jwe ||= block_encryptor return JOSE::JWE.block_encrypt(self, plain_text, jwe) end |
#block_encryptor ⇒ JOSE::Map
Returns a block encryptor map for the key type.
662 663 664 |
# File 'lib/jose/jwk.rb', line 662 def block_encryptor return kty.block_encryptor(fields) end |
#box_decrypt(encrypted, public_jwk = nil) ⇒ [String, JOSE::JWE]
Key Agreement decryption of the encrypted
binary or map using my_private_jwk
.
685 686 687 688 689 690 691 |
# File 'lib/jose/jwk.rb', line 685 def box_decrypt(encrypted, public_jwk = nil) if public_jwk return JOSE::JWE.block_decrypt([public_jwk, self], encrypted) else return JOSE::JWE.block_decrypt(self, encrypted) end end |
#box_encrypt(plain_text, jwk_secret = nil, jwe = nil) ⇒ JOSE::EncryptedMap, [JOSE::EncryptedMap, JOSE::JWK]
Key Agreement encryption of plain_text
by generating an ephemeral private key based on other_public_jwk
curve.
If no private key has been specified in my_private_key
, it generates an ephemeral private key based on other public key curve.
718 719 720 721 722 723 724 725 726 727 728 729 730 731 732 733 734 735 736 737 738 739 740 741 742 743 744 745 746 747 748 749 |
# File 'lib/jose/jwk.rb', line 718 def box_encrypt(plain_text, jwk_secret = nil, jwe = nil) epk_secret = nil jwk_public = self if jwk_secret.nil? epk_secret = jwk_secret = jwk_public.generate_key end if not jwk_secret.is_a?(JOSE::JWK) jwk_secret = JOSE::JWK.from(jwk_secret) end if jwe.nil? jwe = jwk_public.block_encryptor end if jwe.is_a?(Hash) jwe = JOSE::Map.new(jwe) end if jwe.is_a?(JOSE::Map) if jwe['apu'].nil? jwe = jwe.put('apu', jwk_secret.fields['kid'] || jwk_secret.thumbprint) end if jwe['apv'].nil? jwe = jwe.put('apv', jwk_public.fields['kid'] || jwk_public.thumbprint) end if jwe['epk'].nil? jwe = jwe.put('epk', jwk_secret.to_public_map) end end if epk_secret return JOSE::JWE.block_encrypt([jwk_public, jwk_secret], plain_text, jwe), epk_secret else return JOSE::JWE.block_encrypt([jwk_public, jwk_secret], plain_text, jwe) end end |
#derive_key(*args) ⇒ String
Derives a key (typically just returns a binary representation of the key).
764 765 766 |
# File 'lib/jose/jwk.rb', line 764 def derive_key(*args) return kty.derive_key(*args) end |
#generate_key ⇒ JOSE::JWK
Generates a new key based on the current one.
827 828 829 |
# File 'lib/jose/jwk.rb', line 827 def generate_key return JOSE::JWK.new(nil, *kty.generate_key(fields)) end |
#merge(object) ⇒ JOSE::JWK
Merges object into current map.
842 843 844 845 846 847 848 849 850 851 852 853 854 |
# File 'lib/jose/jwk.rb', line 842 def merge(object) object = case object when JOSE::Map, Hash object when String JOSE.decode(object) when JOSE::JWK object.to_map else raise ArgumentError, "'object' must be a Hash, String, or JOSE::JWK" end return JOSE::JWK.from_map(self.to_map.merge(object)) end |
#shared_secret(other_jwk) ⇒ String
Computes the shared secret between two keys.
Currently only works for "EC"
keys and "OKP"
keys with "crv"
set to "X25519"
or "X448"
.
873 874 875 876 877 878 |
# File 'lib/jose/jwk.rb', line 873 def shared_secret(other_jwk) other_jwk = from(other_jwk) if not other_jwk.is_a?(JOSE::JWK) raise ArgumentError, "key types must match" if other_jwk.kty.class != kty.class raise ArgumentError, "key type does not support shared secret computations" if not kty.respond_to?(:derive_key) return kty.derive_key(other_jwk) end |
#sign(plain_text, jws = nil, header = nil) ⇒ JOSE::SignedMap
Signs the plain_text
using the jwk
and the default signer algorithm jws
for the key type.
903 904 905 906 |
# File 'lib/jose/jwk.rb', line 903 def sign(plain_text, jws = nil, header = nil) jws ||= signer return JOSE::JWS.sign(self, plain_text, jws, header) end |
#signer ⇒ JOSE::Map
Returns a signer map for the key type.
919 920 921 |
# File 'lib/jose/jwk.rb', line 919 def signer return kty.signer(fields) end |
#thumbprint(digest_type = nil) ⇒ String
Returns the unique thumbprint for a JOSE::JWK using the digest_type
.
957 958 959 960 961 |
# File 'lib/jose/jwk.rb', line 957 def thumbprint(digest_type = nil) digest_type ||= 'SHA256' thumbprint_binary = JOSE.encode(to_thumbprint_map) return JOSE.urlsafe_encode64(OpenSSL::Digest.new(digest_type).digest(thumbprint_binary)) end |
#to_binary(key = nil, jwe = nil) ⇒ String, JOSE::EncryptedBinary
Converts a JOSE::JWK into a binary.
271 272 273 274 275 276 277 278 279 280 |
# File 'lib/jose/jwk.rb', line 271 def to_binary(key = nil, jwe = nil) if not key.nil? jwe ||= kty.key_encryptor(fields, key) end if key and jwe return to_map(key, jwe).compact else return JOSE.encode(to_map) end end |
#to_file(file, key = nil, jwe = nil) ⇒ Fixnum
Calls JOSE::JWK.to_binary on a JOSE::JWK and then writes the binary to file
.
299 300 301 |
# File 'lib/jose/jwk.rb', line 299 def to_file(file, key = nil, jwe = nil) return File.binwrite(file, to_binary(key, jwe)) end |
#to_key ⇒ OpenSSL::PKey, Object
Converts a JOSE::JWK into the raw key format.
314 315 316 |
# File 'lib/jose/jwk.rb', line 314 def to_key return kty.to_key end |
#to_map(key = nil, jwe = nil) ⇒ JOSE::Map
Converts a JOSE::JWK into a map.
337 338 339 340 341 342 343 344 345 346 |
# File 'lib/jose/jwk.rb', line 337 def to_map(key = nil, jwe = nil) if not key.nil? jwe ||= kty.key_encryptor(fields, key) end if key and jwe return JOSE::JWE.block_encrypt(key, to_binary, jwe) else return kty.to_map(fields) end end |
#to_oct ⇒ String
Converts a JOSE::JWK into a raw binary octet.
363 364 365 |
# File 'lib/jose/jwk.rb', line 363 def to_oct return kty.to_oct end |
#to_oct_file(file) ⇒ Fixnum
Calls JOSE::JWK#to_oct on a JOSE::JWK and then writes the binary to file
.
380 381 382 |
# File 'lib/jose/jwk.rb', line 380 def to_oct_file(file) return File.binwrite(file, to_oct) end |
#to_okp ⇒ String
Converts a JOSE::JWK into an octet key pair.
399 400 401 |
# File 'lib/jose/jwk.rb', line 399 def to_okp return kty.to_okp end |
#to_openssh_key ⇒ Object
Converts a JOSE::JWK into an OpenSSH key binary.
418 419 420 |
# File 'lib/jose/jwk.rb', line 418 def to_openssh_key return kty.to_openssh_key(fields) end |
#to_openssh_key_file(file) ⇒ Fixnum
Calls JOSE::JWK#to_openssh_key on a JOSE::JWK and then writes the binary to file
.
435 436 437 |
# File 'lib/jose/jwk.rb', line 435 def to_openssh_key_file(file) return File.binwrite(file, to_openssh_key) end |
#to_pem(password = nil) ⇒ String
Converts a JOSE::JWK into a PEM (Privacy Enhanced Email) binary.
456 457 458 |
# File 'lib/jose/jwk.rb', line 456 def to_pem(password = nil) return kty.to_pem(password) end |
#to_pem_file(file, password = nil) ⇒ Fixnum
Calls JOSE::JWK#to_pem on a JOSE::JWK and then writes the binary to file
.
475 476 477 |
# File 'lib/jose/jwk.rb', line 475 def to_pem_file(file, password = nil) return File.binwrite(file, to_pem(password)) end |
#to_public ⇒ JOSE::JWK
513 514 515 |
# File 'lib/jose/jwk.rb', line 513 def to_public return JOSE::JWK.from_map(to_public_map) end |
#to_public_file(file) ⇒ Fixnum
Calls JOSE::JWK.to_public on a JOSE::JWK and then writes the binary to file
.
530 531 532 |
# File 'lib/jose/jwk.rb', line 530 def to_public_file(file) return File.binwrite(file, to_public.to_binary) end |
#to_public_key ⇒ OpenSSL::PKey, Object
Calls JOSE::JWK#to_public and then JOSE::JWK#to_key on a JOSE::JWK.
549 550 551 |
# File 'lib/jose/jwk.rb', line 549 def to_public_key return to_public.to_key end |
#to_public_map ⇒ JOSE::Map
Calls JOSE::JWK#to_public and then JOSE::JWK#to_map on a JOSE::JWK.
568 569 570 |
# File 'lib/jose/jwk.rb', line 568 def to_public_map return kty.to_public_map(fields) end |
#to_thumbprint_map ⇒ JOSE::Map
Converts a JOSE::JWK into a map that can be used by JOSE::JWK.thumbprint.
587 588 589 |
# File 'lib/jose/jwk.rb', line 587 def to_thumbprint_map return kty.to_thumbprint_map(fields) end |
#verifier ⇒ Array<String>
Returns a verifier algorithm list for the key type.
978 979 980 |
# File 'lib/jose/jwk.rb', line 978 def verifier return kty.verifier(fields) end |
#verify(signed) ⇒ [Boolean, String, JOSE::JWS]
Verifies the signed
using the jwk
.
997 998 999 |
# File 'lib/jose/jwk.rb', line 997 def verify(signed) return JOSE::JWS.verify(self, signed) end |
#verify_strict(signed, allow) ⇒ [Boolean, String, JOSE::JWS]
Verifies the signed
using the jwk
and whitelists the "alg"
using allow
.
1018 1019 1020 |
# File 'lib/jose/jwk.rb', line 1018 def verify_strict(signed, allow) return JOSE::JWS.verify_strict(self, allow, signed) end |