def __init__(self): self.g_config = {} with open("../src/config/config.json") as j: self.g_config = json.load(j) wkh = WellKnownHandler(self.g_config["auth_server_url"], secure=False) self.__TOKEN_ENDPOINT = wkh.get(TYPE_OIDC, KEY_OIDC_TOKEN_ENDPOINT) #Generate ID Token _rsakey = RSA.generate(2048) _private_key = _rsakey.exportKey() _public_key = _rsakey.publickey().exportKey() file_out = open("private.pem", "wb") file_out.write(_private_key) file_out.close() file_out = open("public.pem", "wb") file_out.write(_public_key) file_out.close() _rsajwk = RSAKey(kid='RSA1', key=import_rsa_key(_private_key)) _payload = { "iss": self.g_config["client_id"], "sub": self.g_config["client_secret"], "aud": self.__TOKEN_ENDPOINT, "jti": datetime.datetime.today().strftime('%Y%m%d%s'), "exp": int(time.time())+3600 } _jws = JWS(_payload, alg="RS256") self.jwt = _jws.sign_compact(keys=[_rsajwk]) self.scopes = 'public_access' self.resourceName = "TestResourcePEP10" self.PEP_HOST = "http://localhost:5566" status, self.resourceID = self.createTestResource() print(self.jwt) print(self.resourceID)
def test_handle_authn_response_returns_id_token_for_verified_affiliation( self, signing_key_path, context, scope_value, affiliation): authn_req = AuthorizationRequest( scope='openid ' + scope_value, client_id='client1', redirect_uri='https://client.example.com', response_type='id_token') context.state[self.frontend.name] = { 'oidc_request': authn_req.to_urlencoded() } internal_response = InternalResponse( AuthenticationInformation(None, str(datetime.now()), 'https://idp.example.com')) internal_response.attributes['affiliation'] = [affiliation] internal_response.user_id = 'user1' resp = self.frontend.handle_authn_response(context, internal_response) auth_resp = AuthorizationResponse().from_urlencoded( urlparse(resp.message).fragment) id_token = IdToken().from_jwt( auth_resp['id_token'], key=[RSAKey(key=rsa_load(signing_key_path))]) assert id_token['iss'] == self.frontend.base_url assert id_token['aud'] == ['client1'] assert id_token['auth_time'] == internal_response.auth_info.timestamp
def test_pjwt_with_jwe_jwk(): keys = KEYS() keys.append(RSAKey(use="enc", key=rsa, kid="some-key-id")) jwe = JWE(alg="RSA-OAEP", enc="A256CBC-HS512") pj = PopJWT( "https://server.example.com", "https://client.example.org", sub="12345678", jwe=jwe, keys=keys, ) jwk = { "kty": "oct", "alg": "HS256", "k": "ZoRSOrFzN_FzUA5XKMYoVHyzff5oRJxl-IXRtztJ6uE", } pjwt = pj.pack_jwe(jwk=jwk, kid="some-key-id") s = pjwt.to_json() de_pjwt = PJWT().from_json(s) assert _eq(de_pjwt.keys(), ["iss", "aud", "exp", "cnf", "sub", "iat"]) assert list(de_pjwt["cnf"].keys()) == ["jwe"] _jwe = de_pjwt["cnf"]["jwe"] msg = jwe.decrypt(_jwe, keys.keys()) assert msg assert json.loads(msg.decode("utf8")) == jwk
def __create_jwt(self): if self.jks_path != None: _rsajwk = RSAKey(kid=self._kid, key=import_rsa_key_from_file(self.jks_path)) else: _rsajwk = RSAKey(kid=self._kid, key=import_rsa_key(self.__getRSAPrivateKey())) _payload = { "iss": self.client_id, "sub": self.client_id, "aud": self.__TOKEN_ENDPOINT, "jti": datetime.datetime.today().strftime('%Y%m%d%s'), "exp": int(time.time()) + 3600 } _jws = JWS(_payload, alg="RS256") return _jws.sign_compact(keys=[_rsajwk])
def rsa_init(spec): """ Initiates a :py:class:`oicmsg.oauth.keybundle.KeyBundle` instance containing newly minted RSA keys according to a spec. Example of specification:: {'name': 'myrsakey', 'path': 'keystore', 'size':2048, 'use': ['enc', 'sig'] } Using the spec above 2 RSA keys would be minted, one for encryption and one for signing. :param spec: :return: KeyBundle """ arg = {} for param in ["name", "path", "size"]: try: arg[param] = spec[param] except KeyError: pass kb = KeyBundle(keytype="RSA") for use in harmonize_usage(spec["use"]): _key = create_and_store_rsa_key_pair(use=use, **arg) kb.append(RSAKey(use=use, key=_key)) return kb
def setup(self): httpretty.enable() self.key = RSAKey(kid='testkey').load( os.path.join(FIXTURE_ROOT, 'testkey.pem')) def jwks(_request, _uri, headers): # noqa: E306 ks = KEYS() ks.add(self.key.serialize()) return 200, headers, ks.dump_jwks() httpretty.register_uri(httpretty.GET, oidc_rp_settings.PROVIDER_JWKS_ENDPOINT, status=200, body=jwks) httpretty.register_uri(httpretty.POST, oidc_rp_settings.PROVIDER_TOKEN_ENDPOINT, body=json.dumps({ 'id_token': self.generate_jws(), 'access_token': 'accesstoken', 'refresh_token': 'refreshtoken', }), content_type='text/json') httpretty.register_uri(httpretty.GET, oidc_rp_settings.PROVIDER_USERINFO_ENDPOINT, body=json.dumps({ 'sub': '1234', 'email': '*****@*****.**', }), content_type='text/json') yield httpretty.disable()
def _add_key_to_keyjar(self, pkey, owner=''): kb = keyio.KeyBundle() priv_key = RSA.importKey(pkey) key = RSAKey().load_key(priv_key) key.use = "sig" kb.append(key) self.keyjar.add_kb(owner, kb)
def get_jwt_keys(self) -> list[Key]: """ Takes a provider and returns the set of keys associated with it. Returns a list of keys. """ if self.jwt_alg == JWTAlgorithms.RS256: # if the user selected RS256 but didn't select a # CertificateKeyPair, we fall back to HS256 if not self.rsa_key: Event.new( EventAction.CONFIGURATION_ERROR, provider=self, message= "Provider was configured for RS256, but no key was selected.", ).save() self.jwt_alg = JWTAlgorithms.HS256 self.save() else: # Because the JWT Library uses python cryptodome, # we can't directly pass the RSAPublicKey # object, but have to load it ourselves key = import_rsa_key(self.rsa_key.key_data) keys = [RSAKey(key=key, kid=self.rsa_key.kid)] if not keys: raise Exception("You must add at least one RSA Key.") return keys if self.jwt_alg == JWTAlgorithms.HS256: return [SYMKey(key=self.client_secret, alg=self.jwt_alg)] raise Exception("Unsupported key algorithm.")
def test_pjwt_unpack_jwe(): keys = KEYS() keys.append(RSAKey(use="enc", key=rsa, kid="some-key-id")) pj = PopJWT("https://server.example.com", "https://client.example.org", sub="12345678") jwk = { "kty": "oct", "alg": "HS256", "k": "ZoRSOrFzN_FzUA5XKMYoVHyzff5oRJxl-IXRtztJ6uE", } jwe = JWE(json.dumps(jwk), alg="RSA-OAEP", enc="A256CBC-HS512") _jwe = jwe.encrypt(keys=keys.keys(), kid="some-key-id") pjwt = pj.pack_jwe(jwe=_jwe) s = pjwt.to_json() _jwt = PopJWT(jwe=jwe, keys=keys).unpack(s) assert _eq(_jwt.keys(), ["iss", "aud", "exp", "cnf", "sub", "iat"]) assert _eq(_jwt["cnf"].keys(), ["jwk", "jwe"]) assert _jwt["cnf"]["jwk"] == jwk
def test_pjwt_with_jwe_jwk(): keys = KEYS() keys.append(RSAKey(use="enc", key=rsa, kid="some-key-id")) jwe = JWE(alg="RSA-OAEP", enc="A256CBC-HS512") pj = PopJWT("https://server.example.com", "https://client.example.org", sub='12345678', jwe=jwe, keys=keys) jwk = { "kty": "oct", "alg": "HS256", "k": "ZoRSOrFzN_FzUA5XKMYoVHyzff5oRJxl-IXRtztJ6uE" } pjwt = pj.pack_jwe(jwk=jwk, kid='some-key-id') s = pjwt.to_json() de_pjwt = PJWT().from_json(s) assert _eq(de_pjwt.keys(), ['iss', 'aud', 'exp', 'cnf', 'sub', 'iat']) assert list(de_pjwt['cnf'].keys()) == ['jwe'] _jwe = de_pjwt['cnf']['jwe'] msg = jwe.decrypt(_jwe, keys.keys()) assert msg assert json.loads(msg.decode('utf8')) == jwk
def test_full_flow(self, account_linking_config, internal_response, context): ticket = "ticket" with responses.RequestsMock() as rsps: rsps.add( responses.GET, "%s/get_id" % account_linking_config["api_url"], status=404, body=ticket, content_type="text/html" ) result = self.account_linking.process(context, internal_response) assert isinstance(result, Redirect) assert result.message.startswith(account_linking_config["redirect_url"]) data = { "idp": internal_response.auth_info.issuer, "id": internal_response.user_id, "redirect_endpoint": self.account_linking.base_url + "/account_linking/handle_account_linking" } key = RSAKey(key=rsa_load(account_linking_config["sign_key"]), use="sig", alg="RS256") jws = JWS(json.dumps(data), alg=key.alg).sign_compact([key]) uuid = "uuid" with responses.RequestsMock() as rsps: # account is linked, 200 OK rsps.add( responses.GET, "%s/get_id?jwt=%s" % (account_linking_config["api_url"], jws), status=200, body=uuid, content_type="text/html", match_querystring=True ) internal_response = self.account_linking._handle_al_response(context) assert internal_response.user_id == uuid
def setUp(self): super().setUp() self.rsa_key_id = "1" # Generate RSA and save exports rsa_key = RSA.generate(2048) self.key = RSAKey(key=rsa_key, kid=self.rsa_key_id) self.public_key = rsa_key.publickey().export_key() self.xblock_attributes = { 'lti_version': 'lti_1p3', 'lti_1p3_launch_url': 'http://tool.example/launch', 'lti_1p3_oidc_url': 'http://tool.example/oidc', # We need to set the values below because they are not automatically # generated until the user selects `lti_version == 'lti_1p3'` on the # Studio configuration view. 'lti_1p3_tool_public_key': self.public_key, 'has_score': True, } self.xblock = make_xblock('lti_consumer', LtiConsumerXBlock, self.xblock_attributes) # Set dummy location so that UsageKey lookup is valid self.xblock.location = 'block-v1:course+test+2020+type@problem+block@test' # Creates an LTI configuration objects for testing self.lti_1p1_config = LtiConfiguration.objects.create( location=str(self.xblock.location), version=LtiConfiguration.LTI_1P1) self.lti_1p3_config = LtiConfiguration.objects.create( location=str(self.xblock.location), version=LtiConfiguration.LTI_1P3)
def test_jws(self): keys = [ SYMKey(key=TestMDQHandler.SYM_KEY_PHRASE, alg="HS256"), RSAKey(key=import_rsa_key_from_file( full_test_path("test_data/certs/rsa2048.pub"))), TestMDQHandler.EC_KEY ] # Test support for algorithms with supplied keys are working for alg in TestMDQHandler.SIGNING_ALGS_SUPPORTED: response = requests.get( TestMDQHandler.URL, params={MDQHandler.SIGNING_ALG_QUERY_PARAM: alg}, headers=TestMDQHandler.HEADERS) payload = JWS().verify_compact(response.text, keys) assert json.loads(payload) == TestMDQHandler.METADATA_FROM_FILE[ TestMDQHandler.CLIENT_ID] # Unsupported signing algorithm response = requests.get( TestMDQHandler.URL, params={MDQHandler.SIGNING_ALG_QUERY_PARAM: "PS256"}, headers=TestMDQHandler.HEADERS) assert response.status_code == 400 # Request signing with MDQ server without keys TestMDQHandler.MDQ = MDQHandler(TestMDQHandler.file_name, 36000) response = requests.get( TestMDQHandler.URL, params={MDQHandler.SIGNING_ALG_QUERY_PARAM: "PS256"}, headers=TestMDQHandler.HEADERS) assert response.status_code == 400
def setUpClass(cls): cls.g_config = {} with open("../src/config/config.json") as j: cls.g_config = json.load(j) wkh = WellKnownHandler(cls.g_config["auth_server_url"], secure=False) cls.__TOKEN_ENDPOINT = wkh.get(TYPE_OIDC, KEY_OIDC_TOKEN_ENDPOINT) _rsajwk = RSAKey(kid="RSA1", key=import_rsa_key_from_file("../src/private.pem")) _payload = { "iss": cls.g_config["client_id"], "sub": cls.g_config["client_id"], "aud": cls.__TOKEN_ENDPOINT, "user_name": "admin", "jti": datetime.datetime.today().strftime('%Y%m%d%s'), "exp": int(time.time()) + 3600, "isOperator": False } _jws = JWS(_payload, alg="RS256") cls.jwt = _jws.sign_compact(keys=[_rsajwk]) cls.scopes = 'protected_access' cls.PDP_HOST = "http://" + cls.g_config["host"] cls.PDP_PORT = cls.g_config["port"] cls.UID = cls.g_config["client_id"]
def test_existing_account_linking_with_known_known_uuid( self, account_linking_config, internal_response, context): uuid = "uuid" data = { "idp": internal_response.auth_info.issuer, "id": internal_response.subject_id, "redirect_endpoint": self.account_linking.base_url + "/account_linking/handle_account_linking" } key = RSAKey(key=rsa_load(account_linking_config["sign_key"]), use="sig", alg="RS256") jws = JWS(json.dumps(data), alg=key.alg).sign_compact([key]) responses.add(responses.GET, "%s/get_id?jwt=%s" % (account_linking_config["api_url"], jws), status=200, body=uuid, content_type="text/html", match_querystring=True) self.account_linking.process(context, internal_response) assert internal_response.subject_id == uuid
def __init__(self, config, callback_func): """ :type config: satosa.satosa_config.SATOSAConfig :type callback_func: (satosa.context.Context, satosa.internal_data.InternalResponse) -> satosa.response.Response :param config: The SATOSA proxy config :param callback_func: Callback function when the linking is done """ self.config = config self.callback_func = callback_func self.enabled = \ "ACCOUNT_LINKING" in config and ("enable" not in config.ACCOUNT_LINKING or config.ACCOUNT_LINKING["enable"]) if self.enabled: self.proxy_base = config.BASE self.al_rest_uri = config.ACCOUNT_LINKING["rest_uri"] self.al_redirect = config.ACCOUNT_LINKING["redirect"] self.endpoint = config.ACCOUNT_LINKING["endpoint"] self.verify_ssl = True if "verify_ssl" not in config.ACCOUNT_LINKING else \ config.ACCOUNT_LINKING["verify_ssl"] _bkey = rsa_load(config.ACCOUNT_LINKING["sign_key"]) self.sign_key = RSAKey().load_key(_bkey) self.sign_key.use = "sig" LOGGER.info("Account linking is active") else: LOGGER.info("Account linking is not active")
def test_pjwt_unpack_jwe(): keys = KEYS() keys.append(RSAKey(use="enc", key=rsa, kid="some-key-id")) pj = PopJWT("https://server.example.com", "https://client.example.org", sub='12345678') jwk = { "kty": "oct", "alg": "HS256", "k": "ZoRSOrFzN_FzUA5XKMYoVHyzff5oRJxl-IXRtztJ6uE" } jwe = JWE(json.dumps(jwk), alg="RSA-OAEP", enc="A256CBC-HS512") _jwe = jwe.encrypt(keys=keys.keys(), kid="some-key-id") pjwt = pj.pack_jwe(jwe=_jwe) s = pjwt.to_json() _jwt = PopJWT(jwe=jwe, keys=keys).unpack(s) assert _eq(_jwt.keys(), ['iss', 'aud', 'exp', 'cnf', 'sub', 'iat']) assert _eq(_jwt['cnf'].keys(), ['jwk', 'jwe']) assert _jwt['cnf']['jwk'] == jwk
def __call__(self): keyjar = self.conv.entity.keyjar self.conv.entity.original_keyjar = keyjar.copy() # invalidate the old key old_key_spec = self.op_args["old_key"] old_key = keyjar.keys_by_alg_and_usage('', old_key_spec['alg'], old_key_spec['use'])[0] old_key.inactive_since = time.time() # setup new key key_spec = self.op_args["new_key"] typ = key_spec["type"].upper() if typ == "RSA": kb = KeyBundle(keytype=typ, keyusage=key_spec["use"]) kb.append(RSAKey(use=key_spec["use"][0]).load_key( RSA.generate(key_spec["bits"]))) elif typ == "EC": kb = ec_init(key_spec) else: raise Unknown('keytype: {}'.format(typ)) # add new key to keyjar with list(kb.keys())[0].kid = self.op_args["new_kid"] keyjar.add_kb("", kb) # make jwks and update file keys = [] for kb in keyjar[""]: keys.extend( [k.to_dict() for k in list(kb.keys()) if not k.inactive_since]) jwks = dict(keys=keys) with open(self.op_args["jwks_path"], "w") as f: f.write(json.dumps(jwks))
def __init__(self, patch, config={}): Server.__init__(self) self.patch = patch self.session = None self.config = { 'issuer': 'https://example.com', } self.config.update(config) self.authz_codes = {} self.access_tokens = {} self.client = { 'test-client': { 'client_name': 'Test Client', 'client_secret': 'test-secret', 'post_logout_redirect_uris': [ 'http://localhost:5000/sign-out', ], 'redirect_uris': [ 'http://localhost:5000/oidc_callback', ], 'response_types': ['code'], } } self.access_token_lifetime = 3600 self.authorization_code_lifetime = 600 self.id_token_lifetime = 3600 self.registration_expires_in = 3600 self.host = '' self.userinfo_signed_response_alg = '' self.signing_key = RSAKey(key=rsa_load('signing_key.pem'), alg='RS256') self.urls = []
def init_oidc_provider(app): with app.app_context(): issuer = url_for('oidc_provider.index')[:-1] authentication_endpoint = url_for('oidc_provider.authentication_endpoint') jwks_uri = url_for('oidc_provider.jwks_uri') token_endpoint = url_for('oidc_provider.token_endpoint') userinfo_endpoint = url_for('oidc_provider.userinfo_endpoint') registration_endpoint = url_for('oidc_provider.registration_endpoint') end_session_endpoint = url_for('oidc_provider.end_session_endpoint') userinfo_ldap = LdapUserInfo() configuration_information = { 'issuer': issuer, 'authorization_endpoint': authentication_endpoint, 'jwks_uri': jwks_uri, 'token_endpoint': token_endpoint, 'userinfo_endpoint': userinfo_endpoint, 'registration_endpoint': registration_endpoint, 'end_session_endpoint': end_session_endpoint, 'scopes_supported': ['openid', 'profile'], 'response_types_supported': ['code', 'code id_token', 'code token', 'code id_token token'], # code and hybrid 'response_modes_supported': ['query', 'fragment'], 'grant_types_supported': ['authorization_code', 'implicit'], 'subject_types_supported': ['pairwise'], 'token_endpoint_auth_methods_supported': ['client_secret_basic'], 'claims_parameter_supported': True } signing_key = RSAKey(key=rsa_load('signing_key.pem'), alg='RS256') provider = Provider(signing_key, configuration_information, AuthorizationState(HashBasedSubjectIdentifierFactory(app.config['SUBJECT_ID_HASH_SALT'])), {}, userinfo_ldap) return provider
def test_cmp_rsa_ec(): _key1 = RSAKey() _key1.load_key(pem_cert2rsa(CERT)) _key2 = ECKey(**ECKEY) assert _key1 != _key2
def test_pop_jwe(): jwk = {"kty": "oct", "alg": "HS256", "k": "ZoRSOrFzN_FzUA5XKMYoVHyzff5oRJxl-IXRtztJ6uE"} encryption_keys = [RSAKey(use="enc", key=rsa, kid="some-key-id")] jwe = JWE(json.dumps(jwk), alg="RSA-OAEP", enc="A256CBC-HS512") _jwe = jwe.encrypt(keys=encryption_keys, kid="some-key-id") jwt = { "iss": "https://server.example.com", "aud": "https://client.example.org", "exp": 1361398824, "cnf": { "jwe": _jwe } } pjwt = PJWT(**jwt) s = pjwt.to_json() de_pjwt = PJWT().from_json(s) assert _eq(de_pjwt.keys(), ['iss', 'aud', 'exp', 'cnf']) assert list(de_pjwt['cnf'].keys()) == ['jwe'] _jwe = de_pjwt['cnf']['jwe'] msg = jwe.decrypt(_jwe, encryption_keys) assert msg assert json.loads(msg.decode('utf8')) == jwk
def key_setup(vault, **kwargs): """ :param vault: Where the keys are kept :return: 2-tuple: result of urlsplit and a dictionary with parameter name as key and url and value """ vault_path = proper_path(vault) if not os.path.exists(vault_path): os.makedirs(vault_path) kb = KeyBundle() for usage in ["sig", "enc"]: if usage in kwargs: if kwargs[usage] is None: continue _args = kwargs[usage] if _args["alg"].upper() == "RSA": try: _key = rsa_load('%s%s' % (vault_path, "pyoidc")) except Exception: devnull = open(os.devnull, 'w') with RedirectStdStreams(stdout=devnull, stderr=devnull): _key = create_and_store_rsa_key_pair(path=vault_path) k = RSAKey(key=_key, use=usage) k.add_kid() kb.append(k) return kb
def __init__(self, public_key=None, keyset_url=None): """ Instance message validator Import a public key from the tool by either using a keyset url or a combination of public key + key id. Keyset URL takes precedence because it makes key rotation easier to do. """ # Only store keyset URL to avoid blocking the class # instancing on an external url, which is only used # when validating a token. self.keyset_url = keyset_url self.public_key = None # Import from public key if public_key: try: new_key = RSAKey(use='sig') # Unescape key before importing it raw_key = codecs.decode(public_key, 'unicode_escape') # Import Key and save to internal state new_key.load_key(RSA.import_key(raw_key)) self.public_key = new_key except ValueError as err: raise exceptions.InvalidRsaKey() from err
def verify_JWT_token(self, token, key): try: header = str(token).split(".")[0] paddedHeader = header + '=' * (4 - len(header) % 4) decodedHeader = base64.b64decode(paddedHeader) #to remove byte-code decodedHeader_format = decodedHeader.decode('utf-8') decoded_str_header = json.loads(decodedHeader_format) payload = str(token).split(".")[1] paddedPayload = payload + '=' * (4 - len(payload) % 4) decoded = base64.b64decode(paddedPayload) #to remove byte-code decoded = decoded.decode('utf-8') decoded_str = json.loads(decoded) if self.getVerificationConfig() == True: if decoded_str_header['kid'] != "RSA1": verificator = JWT_Verification() result = verificator.verify_signature_JWT(token) else: #validate signature for rpt rsajwk = RSAKey( kid="RSA1", key=import_rsa_key_from_file("config/public.pem")) dict_rpt_values = JWS().verify_compact(token, keys=[rsajwk], sigalg="RS256") if dict_rpt_values == decoded_str: result = True else: result = False if result == False: self.logger.debug( "Verification of the signature for the JWT failed!") raise Exception else: self.logger.debug("Signature verification is correct!") user_value = None if decoded_str.get(key): user_value = decoded_str[key] elif decoded_str.get("pct_claims"): if decoded_str.get("pct_claims").get(key): user_value = decoded_str['pct_claims'][key] if isinstance(user_value, list) and len(user_value) != 0 and user_value[0]: user_value = user_value[0] if user_value is None: raise Exception return user_value except Exception as e: self.logger.debug( "Authenticated RPT Resource. No Valid JWT id token passed! " + str(e)) return None
def setUp(self): super().setUp() # Create custom LTI Block self.rsa_key_id = "1" rsa_key = RSA.generate(2048) self.key = RSAKey( key=rsa_key, kid=self.rsa_key_id ) self.public_key = rsa_key.publickey().export_key() self.xblock_attributes = { 'lti_version': 'lti_1p3', 'lti_1p3_launch_url': 'http://tool.example/launch', 'lti_1p3_oidc_url': 'http://tool.example/oidc', # Intentionally using the same key for tool key to # allow using signing methods and make testing easier. 'lti_1p3_tool_public_key': self.public_key, # LTI NRPS related attributes 'lti_1p3_enable_nrps': True } self.xblock = make_xblock('lti_consumer', LtiConsumerXBlock, self.xblock_attributes) # Set dummy location so that UsageKey lookup is valid self.xblock.location = 'block-v1:course+test+2020+type@problem+block@test' # Create configuration self.lti_config = LtiConfiguration.objects.create( location=str(self.xblock.location), version=LtiConfiguration.LTI_1P3, ) # Preload XBlock to avoid calls to modulestore self.lti_config.block = self.xblock # Patch internal method to avoid calls to modulestore patcher = patch( 'lti_consumer.models.LtiConfiguration.block', new_callable=PropertyMock, return_value=self.xblock ) self.addCleanup(patcher.stop) self._lti_block_patch = patcher.start() self.context_membership_endpoint = reverse( 'lti_consumer:lti-nrps-memberships-view-list', kwargs={ "lti_config_id": self.lti_config.id } ) batch_external_id_patcher = patch( 'lti_consumer.plugin.views.compat.batch_get_or_create_externalids', return_value=ExternalIDMapping() ) self._batch_external_id_patcher = batch_external_id_patcher.start()
def _get_oidc_mocks(self): private_key = RSA.generate(2048) generatedjwk = RSAKey(key=private_key.publickey()).serialize() kid = "somekey" private_pem = private_key.exportKey("PEM") token_data = { "iss": app.config["TESTOIDC_LOGIN_CONFIG"]["OIDC_SERVER"], "aud": app.config["TESTOIDC_LOGIN_CONFIG"]["CLIENT_ID"], "nbf": int(time.time()), "iat": int(time.time()), "exp": int(time.time() + 600), "sub": "cool.user", } token_headers = { "kid": kid, } id_token = jwt.encode(token_data, private_pem, "RS256", headers=token_headers) @urlmatch(netloc=r"fakeoidc", path="/token") def token_handler(_, request): if request.body.find("code=somecode") >= 0: content = {"access_token": "someaccesstoken", "id_token": id_token.decode("ascii")} return py_json.dumps(content) else: return {"status_code": 400, "content": '{"message": "Invalid code"}'} @urlmatch(netloc=r"fakeoidc", path="/user") def user_handler(_, __): content = { "sub": "cool.user", "preferred_username": "******", "email": "*****@*****.**", "email_verified": True, } return py_json.dumps(content) @urlmatch(netloc=r"fakeoidc", path="/jwks") def jwks_handler(_, __): jwk = generatedjwk.copy() jwk.update({"kid": kid}) content = {"keys": [jwk]} return py_json.dumps(content) @urlmatch(netloc=r"fakeoidc", path=".+openid.+") def discovery_handler(_, __): content = { "scopes_supported": ["profile"], "authorization_endpoint": "http://fakeoidc/authorize", "token_endpoint": "http://fakeoidc/token", "userinfo_endpoint": "http://fakeoidc/userinfo", "jwks_uri": "http://fakeoidc/jwks", } return py_json.dumps(content) return (discovery_handler, jwks_handler, token_handler, user_handler)
def setup(self): self.consent_db = ConsentDatasetDB("salt", 12) self.ticket_db = ConsentRequestDatasetDB("salt") self.max_month = 12 self.signing_key = RSAKey(key=RSA.generate(1024), alg='RS256') self.cm = ConsentManager(self.consent_db, self.ticket_db, [self.signing_key], 3600, self.max_month)
def test_extract_rsa_from_cert_2(): _ckey = pem_cert2rsa(CERT) _key = RSAKey() _key.load_key(_ckey) print(_key) assert _ckey.n == _key.get_key().n
def signing_key(): private_key = RSA.generate(2048) jwk = RSAKey(key=private_key.publickey()).serialize() return { "id": "somekey", "private_key": private_key.exportKey("PEM"), "jwk": jwk, }