@@ -166,8 +166,7 @@ from cwt import COSE, COSEKey, Recipient
166166mac_key = COSEKey.generate_symmetric_key(alg = " HS512" , kid = " 01" )
167167
168168# The sender side:
169- r = Recipient.from_jwk({" alg" : " direct" })
170- r.apply(mac_key)
169+ r = Recipient.new(unprotected = {" alg" : " direct" , " kid" : mac_key.kid})
171170
172171sender = COSE .new()
173172encoded = sender.encode_and_mac(b " Hello world!" , mac_key, recipients = [r])
@@ -188,18 +187,17 @@ shared_material = token_bytes(32)
188187shared_key = COSEKey.from_symmetric_key(shared_material, kid = " 01" )
189188
190189# The sender side:
191- r = Recipient.from_jwk(
192- {
193- " kty" : " oct" ,
190+ r = Recipient.new(
191+ unprotected = {
194192 " alg" : " direct+HKDF-SHA-256" ,
195193 " salt" : " aabbccddeeffgghh" ,
196194 },
197195)
198- mac_key = r.apply (shared_key, context = {" alg" : " HS256" })
196+ mac_key = r.encode (shared_key.to_bytes() , context = {" alg" : " HS256" })
199197sender = COSE .new(alg_auto_inclusion = True )
200198encoded = sender.encode_and_mac(
201199 b " Hello world!" ,
202- key = mac_key,
200+ mac_key,
203201 recipients = [r],
204202)
205203
@@ -215,31 +213,25 @@ The AES key wrap algorithm can be used to wrap a MAC key as follows:
215213``` py
216214from cwt import COSE , COSEKey, Recipient
217215
218- # The sender side:
219- mac_key = COSEKey.generate_symmetric_key(alg = " HS512" )
220- r = Recipient.from_jwk(
216+ enc_key = COSEKey.from_jwk(
221217 {
222218 " kty" : " oct" ,
223- " alg" : " A128KW" ,
224219 " kid" : " 01" ,
220+ " alg" : " A128KW" ,
225221 " k" : " hJtXIZ2uSN5kbQfbtTNWbg" , # A shared wrapping key
226- },
227- )
228- r.apply(mac_key)
222+ }
223+ );
224+
225+ # The sender side:
226+ mac_key = COSEKey.generate_symmetric_key(alg = " HS512" )
227+ r = Recipient.new(unprotected = {" alg" : " A128KW" }, sender_key = enc_key)
228+ r.encode(mac_key.to_bytes())
229229sender = COSE .new(alg_auto_inclusion = True )
230- encoded = sender.encode_and_mac(b " Hello world!" , key = mac_key, recipients = [r])
230+ encoded = sender.encode_and_mac(b " Hello world!" , mac_key, recipients = [r])
231231
232232# The recipient side:
233233recipient = COSE .new()
234- shared_key = COSEKey.from_jwk(
235- {
236- " kty" : " oct" ,
237- " alg" : " A128KW" ,
238- " kid" : " 01" ,
239- " k" : " hJtXIZ2uSN5kbQfbtTNWbg" ,
240- },
241- )
242- assert b " Hello world!" == recipient.decode(encoded, shared_key)
234+ assert b " Hello world!" == recipient.decode(encoded, enc_key)
243235```
244236
245237#### Direct Key Agreement for MAC
@@ -263,20 +255,10 @@ pub_key = COSEKey.from_jwk(
263255 " y" : " HlLtdXARY_f55A3fnzQbPcm6hgr34Mp8p-nuzQCE0Zw" ,
264256 }
265257)
266- r = Recipient.from_jwk(
267- {
268- " kty" : " EC" ,
269- " alg" : " ECDH-ES+HKDF-256" ,
270- " crv" : " P-256" ,
271- },
272- )
273- mac_key = r.apply(recipient_key = pub_key, context = {" alg" : " HS256" })
258+ r = Recipient.new({" alg" : " ECDH-ES+HKDF-256" }, recipient_key = pub_key)
259+ mac_key = r.encode(context = {" alg" : " HS256" })
274260sender = COSE .new(alg_auto_inclusion = True )
275- encoded = sender.encode_and_mac(
276- b " Hello world!" ,
277- key = mac_key,
278- recipients = [r],
279- )
261+ encoded = sender.encode_and_mac(b " Hello world!" , mac_key, recipients = [r])
280262
281263# The recipient side:
282264# The following key is the private key of the above pub_key.
@@ -304,41 +286,39 @@ assert b"Hello world!" == recipient.decode(encoded, priv_key, context={"alg": "H
304286``` py
305287from cwt import COSE , COSEKey, Recipient
306288
289+ mac_key = COSEKey.generate_symmetric_key(alg = " HS256" )
290+
307291# The sender side:
308- r = Recipient.from_jwk(
309- {
310- " kty" : " OKP" ,
311- " alg" : " ECDH-ES+HKDF-256" ,
312- " crv" : " X25519" ,
313- },
314- )
315292pub_key = COSEKey.from_jwk(
316293 {
317- " kty" : " OKP " ,
318- " alg" : " ECDH-ES+HKDF-256 " ,
294+ " kty" : " EC " ,
295+ " alg" : " ECDH-ES+A128KW " ,
319296 " kid" : " 01" ,
320- " crv" : " X25519" ,
321- " x" : " y3wJq3uXPHeoCO4FubvTc7VcBuqpvUrSvU6ZMbHDTCI" ,
297+ " crv" : " P-256" ,
298+ " x" : " Ze2loSV3wrroKUN_4zhwGhCqo3Xhu1td4QjeQ5wIVR0" ,
299+ " y" : " HlLtdXARY_f55A3fnzQbPcm6hgr34Mp8p-nuzQCE0Zw" ,
322300 }
323301)
324- mac_key = r.apply(recipient_key = pub_key, context = {" alg" : " HS256" })
302+ r = Recipient.new(unprotected = {" alg" : " ECDH-ES+A128KW" }, recipient_key = pub_key)
303+ r.encode(mac_key.to_bytes(), context = {" alg" : " HS256" })
325304sender = COSE .new(alg_auto_inclusion = True )
326305encoded = sender.encode_and_mac(
327306 b " Hello world!" ,
328- key = mac_key,
307+ mac_key,
329308 recipients = [r],
330309)
331310
332311# The recipient side:
333312recipient = COSE .new()
334313priv_key = COSEKey.from_jwk(
335314 {
336- " kty" : " OKP " ,
337- " alg" : " ECDH-ES+HKDF-256 " ,
315+ " kty" : " EC " ,
316+ " alg" : " ECDH-ES+A128KW " ,
338317 " kid" : " 01" ,
339- " crv" : " X25519" ,
340- " x" : " y3wJq3uXPHeoCO4FubvTc7VcBuqpvUrSvU6ZMbHDTCI" ,
341- " d" : " vsJ1oX5NNi0IGdwGldiac75r-Utmq3Jq4LGv48Q_Qc4" ,
318+ " crv" : " P-256" ,
319+ " x" : " Ze2loSV3wrroKUN_4zhwGhCqo3Xhu1td4QjeQ5wIVR0" ,
320+ " y" : " HlLtdXARY_f55A3fnzQbPcm6hgr34Mp8p-nuzQCE0Zw" ,
321+ " d" : " r_kHyZ-a06rmxM3yESK84r1otSg-aQcVStkRhA-iCM8" ,
342322 }
343323)
344324assert b " Hello world!" == recipient.decode(encoded, priv_key, context = {" alg" : " HS256" })
@@ -435,8 +415,8 @@ enc_key = COSEKey.generate_symmetric_key(alg="ChaCha20/Poly1305", kid="01")
435415
436416# The sender side:
437417nonce = enc_key.generate_nonce()
438- r = Recipient.from_jwk( {" alg" : " direct" })
439- r.apply( enc_key)
418+ r = Recipient.new( unprotected = {" alg" : " direct" , " kid " : enc_key.kid })
419+ # r = Recipient.new(unprotected={1: -6, 4: enc_key.kid}) # is also acceptable
440420
441421sender = COSE .new()
442422encoded = sender.encode_and_encrypt(
@@ -461,14 +441,13 @@ shared_material = token_bytes(32)
461441shared_key = COSEKey.from_symmetric_key(shared_material, kid = " 01" )
462442
463443# The sender side:
464- r = Recipient.from_jwk(
465- {
466- " kty" : " oct" ,
444+ r = Recipient.new(
445+ unprotected = {
467446 " alg" : " direct+HKDF-SHA-256" ,
468447 " salt" : " aabbccddeeffgghh" ,
469448 },
470449)
471- enc_key = r.apply (shared_key, context = {" alg" : " A256GCM" })
450+ enc_key = r.encode (shared_key.to_bytes() , context = {" alg" : " A256GCM" })
472451sender = COSE .new(alg_auto_inclusion = True )
473452encoded = sender.encode_and_encrypt(
474453 b " Hello world!" ,
@@ -492,15 +471,19 @@ from cwt import COSE, COSEKey, Recipient
492471enc_key = COSEKey.generate_symmetric_key(alg = " ChaCha20/Poly1305" )
493472
494473# The sender side:
495- r = Recipient .from_jwk(
474+ wrapping_key = COSEKey .from_jwk(
496475 {
497476 " kty" : " oct" ,
498477 " alg" : " A128KW" ,
499478 " kid" : " 01" ,
500479 " k" : " hJtXIZ2uSN5kbQfbtTNWbg" , # A shared wrapping key
501- },
480+ }
481+ )
482+ r = Recipient.new(
483+ unprotected = {" alg" : " A128KW" },
484+ sender_key = wrapping_key,
502485)
503- r.apply (enc_key)
486+ r.encode (enc_key.to_bytes() )
504487sender = COSE .new(alg_auto_inclusion = True )
505488encoded = sender.encode_and_encrypt(b " Hello world!" , key = enc_key, recipients = [r])
506489
@@ -528,13 +511,6 @@ agreement methods (``ECDH-ES+HKDF-256`` with various curves).
528511from cwt import COSE , COSEKey, Recipient
529512
530513# The sender side:
531- r = Recipient.from_jwk(
532- {
533- " kty" : " EC" ,
534- " alg" : " ECDH-ES+HKDF-256" ,
535- " crv" : " P-256" ,
536- },
537- )
538514pub_key = COSEKey.from_jwk(
539515 {
540516 " kty" : " EC" ,
@@ -544,7 +520,8 @@ pub_key = COSEKey.from_jwk(
544520 " y" : " HlLtdXARY_f55A3fnzQbPcm6hgr34Mp8p-nuzQCE0Zw" ,
545521 }
546522)
547- enc_key = r.apply(recipient_key = pub_key, context = {" alg" : " A128GCM" })
523+ r = Recipient.new(unprotected = {" alg" : " ECDH-ES+HKDF-256" }, recipient_key = pub_key)
524+ enc_key = r.encode(context = {" alg" : " A128GCM" })
548525sender = COSE .new(alg_auto_inclusion = True )
549526encoded = sender.encode_and_encrypt(
550527 b " Hello world!" ,
@@ -574,43 +551,51 @@ assert b"Hello world!" == recipient.decode(encoded, priv_key, context={"alg": "A
574551from cwt import COSE , COSEKey, Recipient
575552
576553# The sender side:
577- r = Recipient.from_jwk(
554+ enc_key = COSEKey.generate_symmetric_key(alg = " A128GCM" )
555+ nonce = enc_key.generate_nonce()
556+ r_pub_key = COSEKey.from_jwk(
578557 {
579- " kty" : " OKP" ,
580- " alg" : " ECDH-ES+HKDF-256" ,
581- " crv" : " X25519" ,
582- },
558+ " kty" : " EC" ,
559+ " crv" : " P-256" ,
560+ " kid" : " meriadoc.brandybuck@buckland.example" ,
561+ " x" : " Ze2loSV3wrroKUN_4zhwGhCqo3Xhu1td4QjeQ5wIVR0" ,
562+ " y" : " HlLtdXARY_f55A3fnzQbPcm6hgr34Mp8p-nuzQCE0Zw" ,
563+ }
583564)
584- pub_key = COSEKey.from_jwk(
565+ s_priv_key = COSEKey.from_jwk(
585566 {
586- " kty" : " OKP" ,
587- " alg" : " ECDH-ES+HKDF-256" ,
588- " kid" : " 01" ,
589- " crv" : " X25519" ,
590- " x" : " y3wJq3uXPHeoCO4FubvTc7VcBuqpvUrSvU6ZMbHDTCI" ,
567+ " kty" : " EC" ,
568+ " crv" : " P-256" ,
569+ " alg" : " ECDH-SS+A128KW" ,
570+ " x" : " 7cvYCcdU22WCwW1tZXR8iuzJLWGcd46xfxO1XJs-SPU" ,
571+ " y" : " DzhJXgz9RI6TseNmwEfLoNVns8UmvONsPzQDop2dKoo" ,
572+ " d" : " Uqr4fay_qYQykwcNCB2efj_NFaQRRQ-6fHZm763jt5w" ,
591573 }
592574)
593- enc_key = r.apply(recipient_key = pub_key, context = {" alg" : " A128GCM" })
575+ r = Recipient.new(unprotected = {" alg" : " ECDH-SS+A128KW" }, sender_key = s_priv_key, recipient_key = r_pub_key)
576+ r.encode(enc_key.to_bytes(), context = {" alg" : " A128GCM" })
594577sender = COSE .new(alg_auto_inclusion = True )
595578encoded = sender.encode_and_encrypt(
596579 b " Hello world!" ,
597580 key = enc_key,
581+ nonce = nonce,
598582 recipients = [r],
599583)
600584
601585# The recipient side:
602586recipient = COSE .new()
603- priv_key = COSEKey.from_jwk(
587+ r_priv_key = COSEKey.from_jwk(
604588 {
605- " kty" : " OKP" ,
606- " alg" : " ECDH-ES+HKDF-256" ,
607- " kid" : " 01" ,
608- " crv" : " X25519" ,
609- " x" : " y3wJq3uXPHeoCO4FubvTc7VcBuqpvUrSvU6ZMbHDTCI" ,
610- " d" : " vsJ1oX5NNi0IGdwGldiac75r-Utmq3Jq4LGv48Q_Qc4" ,
589+ " kty" : " EC" ,
590+ " crv" : " P-256" ,
591+ " alg" : " ECDH-SS+A128KW" ,
592+ " kid" : " meriadoc.brandybuck@buckland.example" ,
593+ " x" : " Ze2loSV3wrroKUN_4zhwGhCqo3Xhu1td4QjeQ5wIVR0" ,
594+ " y" : " HlLtdXARY_f55A3fnzQbPcm6hgr34Mp8p-nuzQCE0Zw" ,
595+ " d" : " r_kHyZ-a06rmxM3yESK84r1otSg-aQcVStkRhA-iCM8" ,
611596 }
612597)
613- assert b " Hello world!" == recipient.decode(encoded, priv_key , context = {" alg" : " A128GCM" })
598+ assert b " Hello world!" == recipient.decode(encoded, r_priv_key , context = {" alg" : " A128GCM" })
614599```
615600
616601#### COSE-HPKE (Encrypt)
@@ -645,8 +630,9 @@ r = Recipient.new(
645630 3 : 0x 0001 , # aead: AES-128-GCM
646631 },
647632 },
633+ recipient_key = rpk,
648634)
649- r.encode(enc_key.to_bytes(), recipient_key = rpk )
635+ r.encode(enc_key.to_bytes())
650636sender = COSE .new()
651637encoded = sender.encode_and_encrypt(
652638 b " This is the content." ,
0 commit comments