-
Notifications
You must be signed in to change notification settings - Fork 238
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Easier extending/replacing of key algorithms #42
Conversation
Codecov Report@@ Coverage Diff @@
## master #42 +/- ##
==========================================
+ Coverage 95.53% 95.57% +0.03%
==========================================
Files 7 7
Lines 538 542 +4
==========================================
+ Hits 514 518 +4
Misses 24 24
Continue to review full report at Codecov.
|
I'm curious what the use case for this is? Are you looking to define and use custom algorithms at run time, or is there another reason? |
Correct, using a custom ES256 implementation on a RaspberryPI. Also kind-of resolves #41 as it gets much easier to switch implementations. |
Code to switch an implementation (eg. customjose.py): from jose import jwk
class MyKeyImpl(jwk.Key):
# custom implementation here
def register():
jwk.ALGORITHMS.register_key("ES256", MyKeyImpl) Where you use jose: from jose import jwt
jwk.encode({}, "private key", algorithm="ES256") After: from customjose import register
from jose import jwt
register()
jwk.encode({}, "private key", algorithm="ES256") The runtime switch is dead simple and you don't have to change any code in your application. But the change also means that you can have multiple implementations of the Key classes and use |
@mpdavis any feedback? |
Hi, To check the utility of this patch, I wrote a cryptography backend for ES256/ES384/ES512 in a separate repo at zejn@f4a840a. There's still an unsettled way how to handle different backend crypto implementations. Currently used ecdsa is pure python and slow. There's a pull request for pyelliptic at #39, but it doesn't work with other than SHA256 - yann2192/pyelliptic#53 - and pyelliptic also does not support OpenSSL 1.1 - yann2192/pyelliptic#50. There's also an issue about supporting cryptography here - #41. I find this PR working, it touches very limited amount of code. Further rework would be welcome as it would allow to specify which key class to use if one does not want to use globally registered one. |
KEYS = {} | ||
|
||
def get_key(self, algorithm): | ||
from jose.jwk import HMACKey, RSAKey, ECKey |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I'm not a fan of this circular dependency. I would move this key registration/lookup logic to jwk.py
.
self.SUPPORTED.add(algorithm) | ||
return True | ||
else: | ||
return False |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Attempting to register an invalid key should raise a TypeError
@friedcell My apologies for taking so long to get back to you on this. I really appreciate the work. I only have a couple of comments on the PR, and I think overall it will be a good addition. |
Updated the code per request |
KEYS = {} | ||
|
||
def register_key(self, algorithm, key_class): | ||
from jose.jwk import Key |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
This still has a wonky dependency. Can you move it over as well?
Moved that too |
@mpdavis ping? |
LGTM |
Released in 1.4.0 |
Hey @friedcell, thanks for this PR! It made it really really easy for me to write PR #100. |
Changed some code to make jwk algorithm implementations easily extendable.
If you want to replace a certain key implementation you only do
jwk.ALGORITHMS.register_key("[algorithm name]", [key class])
and from that moment on the algorithm will use a different class to do everything.While doing it, made some stuff a bit more pythonic.