From dc37f30a1273c1d3b7949b1d64e60d37da3b9fd4 Mon Sep 17 00:00:00 2001
From: John Estabrook <jestabro@vyos.io>
Date: Sun, 23 Oct 2022 11:08:19 -0500
Subject: graphql: T4574: set token expiration time in claims

---
 src/services/api/graphql/graphql/auth_token_mutation.py | 7 ++++++-
 src/services/api/graphql/libs/token_auth.py             | 4 ++--
 src/services/vyos-http-api-server                       | 1 +
 3 files changed, 9 insertions(+), 3 deletions(-)

diff --git a/src/services/api/graphql/graphql/auth_token_mutation.py b/src/services/api/graphql/graphql/auth_token_mutation.py
index 33779d4f0..21ac40094 100644
--- a/src/services/api/graphql/graphql/auth_token_mutation.py
+++ b/src/services/api/graphql/graphql/auth_token_mutation.py
@@ -14,6 +14,7 @@
 # along with this library.  If not, see <http://www.gnu.org/licenses/>.
 
 import jwt
+import datetime
 from typing import Any, Dict
 from ariadne import ObjectType, UnionType
 from graphql import GraphQLResolveInfo
@@ -30,7 +31,11 @@ def auth_token_resolver(obj: Any, info: GraphQLResolveInfo, data: Dict):
     passwd = data['password']
 
     secret = state.settings['secret']
-    res = generate_token(user, passwd, secret)
+    exp_interval = int(state.settings['app'].state.vyos_token_exp)
+    expiration = (datetime.datetime.now(tz=datetime.timezone.utc) +
+                  datetime.timedelta(seconds=exp_interval))
+
+    res = generate_token(user, passwd, secret, expiration)
     if res:
         data['result'] = res
         return {
diff --git a/src/services/api/graphql/libs/token_auth.py b/src/services/api/graphql/libs/token_auth.py
index 2d63a1cc7..fafb0f5af 100644
--- a/src/services/api/graphql/libs/token_auth.py
+++ b/src/services/api/graphql/libs/token_auth.py
@@ -14,7 +14,7 @@ def init_secret():
     secret = token_hex(16)
     state.settings['secret'] = secret
 
-def generate_token(user: str, passwd: str, secret: str) -> dict:
+def generate_token(user: str, passwd: str, secret: str, exp: int) -> dict:
     if user is None or passwd is None:
         return {}
     if _check_passwd_pam(user, passwd):
@@ -25,7 +25,7 @@ def generate_token(user: str, passwd: str, secret: str) -> dict:
             app.state.vyos_token_users = {}
             users = app.state.vyos_token_users
         user_id = uuid.uuid1().hex
-        payload_data = {'iss': user, 'sub': user_id}
+        payload_data = {'iss': user, 'sub': user_id, 'exp': exp}
         secret = state.settings.get('secret')
         if secret is None:
             return {
diff --git a/src/services/vyos-http-api-server b/src/services/vyos-http-api-server
index 840041b73..4af27b949 100755
--- a/src/services/vyos-http-api-server
+++ b/src/services/vyos-http-api-server
@@ -698,6 +698,7 @@ if __name__ == '__main__':
                 app.state.vyos_introspection = False
             # default value is merged in conf_mode http-api.py, if not set
             app.state.vyos_auth_type = server_config['graphql']['authentication']['type']
+            app.state.vyos_token_exp = server_config['graphql']['authentication']['expiration']
     else:
         app.state.vyos_graphql = False
 
-- 
cgit v1.2.3