diff --git a/hiboo/sso/oidc.py b/hiboo/sso/oidc.py
index db3a93db0c6f9209d6bbcc6645fa4ded837e19f5..3d603a6de80f1f5f7c2bd7ee7928646573d74935 100644
--- a/hiboo/sso/oidc.py
+++ b/hiboo/sso/oidc.py
@@ -103,16 +103,14 @@ class OpenIDMixin(object):
     def exists_nonce(self, nonce, request):
         return bool(utils.redis.get("nonce:{}".format(nonce)))
 
-    def get_client(self, grant=None):
+    def get_jwt_config(self, grant=None):
         # In the case of AuthorizationCode, the current object is not the grant
         # but a grant extension, so the client is retrieved through the grant argument
-        return self.request.client if grant is None else grant.client
-
-    def get_jwt_config(self, grant=None):
-        return self.get_client().get_jwt_config()
+        client = self.request.client if grant is None else grant.client
+        return client.get_jwt_config()
 
     def generate_user_info(self, user, scope):
-        return self.get_client().generate_user_info(user, scope)
+        return Client.generate_user_info(user, scope)
 
 
 class Client(sqla_oauth2.OAuth2ClientMixin):
@@ -159,7 +157,8 @@ class Client(sqla_oauth2.OAuth2ClientMixin):
             'exp': 3600,
         }
 
-    def generate_user_info(self, user, scope):
+    @classmethod
+    def generate_user_info(cls, user, scope):
         """ User info generation function used by the oidc code mixin and the userinfo endpoint
         """
         return oidc.UserInfo(
@@ -211,5 +210,5 @@ def oidc_userinfo(service_uuid):
     client = Client.get_by_service(service_uuid) or flask.abort(404)
     token = client.validate_token(flask.request)
     profile = models.Profile.query.get(token["profile_uuid"])
-    return client.generate_user_info(profile, token["scope"])
+    return Client.generate_user_info(profile, token["scope"])
     
\ No newline at end of file