From de398d189a2acf786622efbaa048516a2a610393 Mon Sep 17 00:00:00 2001 From: Tobias Kurze Date: Fri, 24 Jul 2020 16:45:18 +0200 Subject: [PATCH] tryd to fix a oid connect related bug, but there is still a BIG problem --- backend/__main__.py | 34 ++++++++++++++------ backend/api/auth_api.py | 16 ++++++--- backend/auth/oidc.py | 15 +++++++-- backend/config.py | Bin 4652 -> 4744 bytes backend/cron/cron_state_checker.py | 2 +- backend/tools/exception_decorator.py | 8 ++++- backend/tools/recorder_state_checker.py | 41 +++++++++++++++++------- 7 files changed, 86 insertions(+), 30 deletions(-) diff --git a/backend/__main__.py b/backend/__main__.py index 2997faa..7775e89 100644 --- a/backend/__main__.py +++ b/backend/__main__.py @@ -5,11 +5,12 @@ import logging import ssl import sys +import threading from jinja2.exceptions import TemplateNotFound from backend import app, db -from backend.cron import get_default_scheduler, add_default_jobs +from backend.cron import get_default_scheduler, add_default_jobs, async_permanent_cron_recorder_checker from backend.models import * from backend.models import room_model, recorder_model, RecorderCommand, Recorder from backend.recorder_adapters import get_defined_recorder_adapters @@ -17,13 +18,30 @@ from backend.tools.model_updater import update_recorder_models_database, create_ from backend.websocket.base import WebSocketBase +def _start_initial_recorder_state_update(run_in_thread=True): + if run_in_thread: + thread = threading.Thread(target=async_permanent_cron_recorder_checker.check_object_state, args=()) + thread.start() + else: + async_permanent_cron_recorder_checker.check_object_state() # initial check of all recorders + + + +def _create_and_start_default_scheduler(): + print("Starting Scheduler") + scheduler = get_default_scheduler() + add_default_jobs(scheduler) + scheduler.start() + return scheduler + + def main(): logging.basicConfig(level=logging.DEBUG, format='%(asctime)s - %(name)s - %(levelname)s - %(message)s') - #db.drop_all() - #db.create_all() + # db.drop_all() + # db.create_all() - #Recorder() + # Recorder() room_model.pre_fill_table() update_recorder_models_database(drop=False) create_default_recorders() @@ -44,16 +62,14 @@ def main(): except Exception as e: logging.critical(e) - print("Starting Scheduler") - scheduler = get_default_scheduler() - add_default_jobs(scheduler) - scheduler.start() + scheduler = _create_and_start_default_scheduler() + #_start_initial_recorder_state_update(run_in_thread=False) wsb = WebSocketBase() print("running websocket...(replaces normal app.run()") wsb.start_websocket(debug=True) # print("running web app...") - #app.run(debug=True, host="0.0.0.0", threaded=True) + # app.run(debug=True, host="0.0.0.0", threaded=True) wsb.send_test_msg() while True: diff --git a/backend/api/auth_api.py b/backend/api/auth_api.py index 2645de7..5cc4a05 100644 --- a/backend/api/auth_api.py +++ b/backend/api/auth_api.py @@ -7,6 +7,7 @@ Login through API does not start a new session, but instead returns JWT. """ import base64 import json +import logging from pprint import pprint import flask @@ -29,6 +30,8 @@ from backend.api import auth_api_bp, auth_api_providers_ns, auth_api_register_ns from backend.auth import AUTH_PROVIDERS, oidc_auth from backend.models.user_model import User, Group, BlacklistToken +logger = logging.getLogger("lrc.api.auth") + @auth_api_bp.route('/providers', methods=('GET',)) def get_auth_providers(): @@ -92,6 +95,7 @@ def login(): } return jsonify(token), 200 + # Endpoint for revoking the current users access token @auth_api_bp.route('/logout', methods=['GET', 'DELETE']) @jwt_required @@ -135,7 +139,7 @@ def create_or_retrieve_user_from_userinfo(userinfo): user = User.get_by_identifier(email) if user is not None: - app.logger.info("user found -> update user") + logger.info("user found -> update user") pprint(user.to_dict()) user.first_name = userinfo.get("given_name", "") user.last_name = userinfo.get("family_name", "") @@ -148,7 +152,7 @@ def create_or_retrieve_user_from_userinfo(userinfo): last_name=userinfo.get("family_name", ""), external_user=True, groups=user_groups) - app.logger.info("creating new user") + logger.info("creating new user") db.session.add(user) db.session.commit() @@ -159,8 +163,11 @@ def create_or_retrieve_user_from_userinfo(userinfo): @auth_api_bp.route('/oidc/', methods=['GET']) @oidc_auth.oidc_auth() def oidc(redirect_url=None): + logger.debug("oidc auth endpoint:") + return "fuck!" user = create_or_retrieve_user_from_userinfo(flask.session['userinfo']) if user is None: + logger.error("Could not authenticate: could not find or create user.") return "Could not authenticate: could not find or create user.", 401 if current_app.config.get("AUTH_RETURN_EXTERNAL_JWT", False): token = jwt.encode(flask.session['id_token'], current_app.config['SECRET_KEY']) @@ -169,13 +176,13 @@ def oidc(redirect_url=None): 'access_token': create_access_token(identity=user, fresh=True), 'refresh_token': create_refresh_token(identity=user) }) + logger.info("Token: {}".format(token)) if redirect_url is None: redirect_url = request.headers.get("Referer") if redirect_url is None: redirect_url = request.args.get('redirect_url') if redirect_url is None: redirect_url = "/" - app.logger.info("Token: {}".format(token)) response = make_response(redirect(redirect_url)) response.set_cookie('tokens', base64.b64encode(token.encode('utf-8'))) return response @@ -189,8 +196,7 @@ def refresh(): as we do not actually verify a password in this endpoint.""" jwt_identity = get_jwt_identity() user = User.get_by_identifier(jwt_identity) - app.logger.info("Refreshing token for " + str(user)) + logger.info("Refreshing token for " + str(user)) new_token = create_access_token(identity=user, fresh=False) ret = {'access_token': new_token} return jsonify(ret), 200 - diff --git a/backend/auth/oidc.py b/backend/auth/oidc.py index 943cf70..ca87038 100644 --- a/backend/auth/oidc.py +++ b/backend/auth/oidc.py @@ -15,7 +15,6 @@ from backend.models.user_model import User from . import auth_bp from .oidc_config import PROVIDER_NAME, OIDC_PROVIDERS - OIDCAuthentication.oidc_auth_orig = OIDCAuthentication.oidc_auth OIDCAuthentication.oidc_logout_orig = OIDCAuthentication.oidc_logout @@ -46,6 +45,7 @@ def create_or_retrieve_user_from_userinfo(userinfo): if user is not None: app.logger.info("user found") + app.logger.debug(f"user found: {email}") user.last_seen = datetime.utcnow() # TODO: update user! db.session.commit() @@ -54,21 +54,24 @@ def create_or_retrieve_user_from_userinfo(userinfo): user = User(email=email, first_name=userinfo.get("given_name", ""), last_name=userinfo.get("family_name", "")) - app.logger.info("creating new user") + app.logger.info(f"creating new user: {email}") db.session.add(user) db.session.commit() return user - @auth_bp.route('/oidc', methods=['GET']) @oidc_auth.oidc_auth() def oidc(): user_session = UserSession(flask.session) app.logger.info(user_session.userinfo) user = create_or_retrieve_user_from_userinfo(user_session.userinfo) + if user is None: + return '' login_user(user) + app.logger.info(f"logged in user: {str(user)}") + app.logger.debug(f"id token: {str(user_session.id_token)}") return jsonify(id_token=user_session.id_token, access_token=flask.session['access_token'], userinfo=user_session.userinfo) @@ -78,3 +81,9 @@ def oidc(): def oidc_logout(): oidc_auth.oidc_logout() return redirect('/') + + +@oidc_auth.error_view +def error(error=None, error_description=None): + app.logger.error(f"Something wwent wrong with OIDC auth – error: {error}, message: {error_description}") + return jsonify({'error': error, 'message': error_description}) diff --git a/backend/config.py b/backend/config.py index fe58a30646804f66fdf13167dc9d8b1d8ca94242..37999f49768eb6c3059fcbd2558b704f1f6faf23 100644 GIT binary patch literal 4744 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 WyUxpzi1O-UrMKGZFJ8B3dkAuXC^Yi` literal 4652 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 RecorderAdapte type = recorder_info.get("type") except KeyError: type = RecorderModel.get_by_id(recorder_info.get('recorder_model_id')).model_name - if "SMP" in type: - rec = SMP35x(recorder_info.get('ip'), recorder_info.get('password')) - else: - rec = Epiphan(recorder_info.get('ip'), recorder_info.get("username"), recorder_info.get("password")) - return rec + try: + if "SMP" in type: + rec = SMP35x(recorder_info.get('ip'), recorder_info.get('password')) + else: + rec = Epiphan(recorder_info.get('ip'), recorder_info.get("username"), recorder_info.get("password")) + return rec + except LrcException: + raise def check_stream_sanity(recorder_agent: Union[Recorder, dict], recorder_adapter: RecorderAdapter = None): - if recorder_adapter is None: - recorder_info = get_recorder_by_name(recorder_agent.get('name')) - recorder_adapter = get_recorder_adapter(recorder_info) - if not recorder_adapter.is_recording(): - return True, "not recording, so there is no stream!", recorder_agent.get('name') + try: + if recorder_adapter is None: + recorder_info = get_recorder_by_name(recorder_agent.get('name')) + recorder_adapter = get_recorder_adapter(recorder_info) + if not recorder_adapter.is_recording(): + return True, "not recording, so there is no stream!", recorder_agent.get('name') + except LrcException: + return False, "Could not determine if recorder is recording!", recorder_agent.get('name') if recorder_agent.get('archive_stream1') is None and recorder_agent.get( 'archive_stream2') is None: # fall back to default names and rtsp archive_stream_1_url = "rtsp://{}/{}".format(recorder_adapter.address, Config.DEFAULT_ARCHIVE_STREAM_1_NAME) @@ -186,7 +200,12 @@ def check_capture_agent_state(recorder_agent: Union[Recorder, dict]): return True, "Recorder is in offline / maintenance mode", recorder_agent.get('name') agent_state_error_msg = None logger.debug("Checking Agent {}".format(recorder_agent.get('name'))) - c = get_calender(recorder_agent.get('name')) + try: + c = get_calender(recorder_agent.get('name')) + except LrcException: + error_msg = "Could not get calender of recorder agent: {}!".format(recorder_agent.get('name')) + logger.fatal(error_msg) + return False, error_msg, recorder_agent.get('name') is_recording_in_calendar = len(list(c.timeline.now())) >= 1 if is_recording_in_calendar: logger.info("{} has entry in Calender and should therefore be recording... checking now!".format(