From 77e2c04ec0d95d1dbf45948a7193890a0e0a32e7 Mon Sep 17 00:00:00 2001 From: Russell Ballestrini Date: Wed, 22 Oct 2025 20:04:20 -0400 Subject: [PATCH] Use selected model for activity AI operations Pass the selected model parameter through the entire activity workflow to ensure all AI operations (categorization, translation, feedback generation, and grading) use the user's chosen model instead of defaulting to the system default. Falls back to default when no model is selected. --- app.py | 87 ++++++++++++++++++++++++++++++++++++++++------------------ 1 file changed, 60 insertions(+), 27 deletions(-) diff --git a/app.py b/app.py index 0925fdb..2b78963 100644 --- a/app.py +++ b/app.py @@ -638,7 +638,7 @@ def handle_message(data): activity_state = ActivityState.query.filter_by(room_id=room.id).first() if activity_state: - gevent.spawn(handle_activity_response, room_name, message, username) + gevent.spawn(handle_activity_response, room_name, message, username, model) return if model != "None": @@ -1569,7 +1569,7 @@ def get_activity_content(file_path): def loop_through_steps_until_question( - activity_content, activity_state, room_name, username + activity_content, activity_state, room_name, username, model=None ): room = get_room(room_name) @@ -1600,7 +1600,7 @@ def loop_through_steps_until_question( # Emit the current step content blocks if "content_blocks" in step: content = "\n\n".join(step["content_blocks"]) - translated_content = translate_text(content, user_language) + translated_content = translate_text(content, user_language, model) new_message = Message( username="System", content=translated_content, room_id=room.id ) @@ -1622,7 +1622,7 @@ def loop_through_steps_until_question( if "question" in step: question_content = step["question"] translated_question_content = translate_text( - question_content, user_language + question_content, user_language, model ) new_message = Message( username="System (Question)", @@ -1663,7 +1663,7 @@ def loop_through_steps_until_question( # Activity completed # Display activity info before completing - display_activity_info(room_name, username) + display_activity_info(room_name, username, model) db.session.delete(activity_state) db.session.commit() @@ -1702,7 +1702,7 @@ def start_activity(room_name, s3_file_path, username): # Loop through steps until a question is found or the end is reached loop_through_steps_until_question( - activity_content, activity_state, room_name, username + activity_content, activity_state, room_name, username, model ) # Emit activity status update @@ -1807,7 +1807,7 @@ def execute_processing_script(metadata, script): return local_env["script_result"] -def handle_activity_response(room_name, user_response, username): +def handle_activity_response(room_name, user_response, username, model=None): with app.app_context(): room = get_room(room_name) activity_state = ActivityState.query.filter_by(room_id=room.id).first() @@ -1854,6 +1854,7 @@ def handle_activity_response(room_name, user_response, username): user_response, step["buckets"], step.get("tokens_for_ai", ""), + model, ) # Initialize transition to None @@ -2161,7 +2162,7 @@ def handle_activity_response(room_name, user_response, username): if "content_blocks" in transition: transition_content = "\n\n".join(transition["content_blocks"]) translated_transition_content = translate_text( - transition_content, user_language + transition_content, user_language, model ) new_message = Message( username="System", @@ -2201,6 +2202,7 @@ def handle_activity_response(room_name, user_response, username): json.dumps(activity_state.dict_metadata), # Pass full metadata json.dumps(new_metadata), feedback_tokens_for_ai, # Pass legacy tokens to be combined + model, ) feedback_messages.extend(multi_feedback_messages) elif feedback_tokens_for_ai: @@ -2224,6 +2226,7 @@ def handle_activity_response(room_name, user_response, username): username, json.dumps(feedback_metadata), json.dumps(new_metadata), + model, ) if feedback and feedback.strip(): feedback_messages.append( @@ -2310,7 +2313,7 @@ def handle_activity_response(room_name, user_response, username): # Loop through steps until a question is found or the end is reached loop_through_steps_until_question( - activity_content, activity_state, room_name, username + activity_content, activity_state, room_name, username, model ) else: # the user response is any bucket other than correct. @@ -2322,7 +2325,7 @@ def handle_activity_response(room_name, user_response, username): # Emit the question again question_content = step["question"] translated_question_content = translate_text( - question_content, user_language + question_content, user_language, model ) new_message = Message( username="System (Question)", @@ -2361,7 +2364,7 @@ def handle_activity_response(room_name, user_response, username): else: # Handle steps without a question loop_through_steps_until_question( - activity_content, activity_state, room_name, username + activity_content, activity_state, room_name, username, model ) except Exception as e: @@ -2379,7 +2382,7 @@ def handle_activity_response(room_name, user_response, username): ) -def display_activity_info(room_name, username): +def display_activity_info(room_name, username, model=None): with app.app_context(): room = get_room(room_name) activity_state = ActivityState.query.filter_by(room_id=room.id).first() @@ -2433,7 +2436,7 @@ def display_activity_info(room_name, username): ) # Generate the grading using the AI - grading_message = generate_grading(chat_history, rubric) + grading_message = generate_grading(chat_history, rubric, model) # Store and emit the activity info info_message = f"Activity Info:\nCurrent Section: {activity_state.section_id}\nCurrent Step: {activity_state.step_id}\nAttempts: {activity_state.attempts}\n\n{grading_message}" @@ -2467,8 +2470,12 @@ def display_activity_info(room_name, username): print(f"Exception: {e}") -def generate_grading(chat_history, rubric): - openai_client, model_name = get_openai_client_and_model() +def generate_grading(chat_history, rubric, model=None): + # Use provided model or fall back to default + if model and model != "None": + openai_client, model_name = get_openai_client_and_model(model) + else: + openai_client, model_name = get_openai_client_and_model() messages = [ { "role": "system", @@ -2515,8 +2522,12 @@ def get_next_step(activity_content, current_section_id, current_step_id): # Categorize the user's response. -def categorize_response(question, response, buckets, tokens_for_ai): - openai_client, model_name = get_openai_client_and_model() +def categorize_response(question, response, buckets, tokens_for_ai, model=None): + # Use provided model or fall back to default + if model and model != "None": + openai_client, model_name = get_openai_client_and_model(model) + else: + openai_client, model_name = get_openai_client_and_model() bucket_list = ", ".join([str(bucket) for bucket in buckets]) # Check if tokens_for_ai already includes format instructions (ANALYSIS/BUCKET format) if "ANALYSIS:" in tokens_for_ai and "BUCKET:" in tokens_for_ai: @@ -2592,8 +2603,13 @@ def generate_ai_feedback( username, json_metadata, json_new_metadata, + model=None, ): - openai_client, model_name = get_openai_client_and_model() + # Use provided model or fall back to default + if model and model != "None": + openai_client, model_name = get_openai_client_and_model(model) + else: + openai_client, model_name = get_openai_client_and_model() messages = [ { "role": "system", @@ -2625,6 +2641,7 @@ def provide_feedback( username, json_metadata, json_new_metadata, + model=None, ): feedback = "" if "ai_feedback" in transition: @@ -2637,6 +2654,7 @@ def provide_feedback( username, json_metadata, json_new_metadata, + model, ) feedback += f"\n\n{ai_feedback}" @@ -2654,6 +2672,7 @@ def provide_feedback_prompts( json_metadata, json_new_metadata, legacy_tokens_for_ai="", + model=None, ): """Generate feedback from multiple prompts""" feedback_messages = [] @@ -2675,22 +2694,31 @@ def provide_feedback_prompts( prompt_metadata = { k: v for k, v in full_metadata.items() if k in filter_keys } - + # Check skip condition if specified skip_condition = prompt.get("skip_condition") if skip_condition: should_skip = False values = list(prompt_metadata.values()) - + if skip_condition == "all_null": - should_skip = all(value is None or value == "" or value == "None" for value in values) + should_skip = all( + value is None or value == "" or value == "None" + for value in values + ) elif skip_condition == "all_false": - should_skip = all(value is False or value == "False" for value in values) + should_skip = all( + value is False or value == "False" for value in values + ) elif skip_condition == "all_true": - should_skip = all(value is True or value == "True" for value in values) - + should_skip = all( + value is True or value == "True" for value in values + ) + if should_skip: - print(f"DEBUG: Skipping prompt '{prompt_name}' - skip_condition '{skip_condition}' met") + print( + f"DEBUG: Skipping prompt '{prompt_name}' - skip_condition '{skip_condition}' met" + ) continue # Special debug for Ship Status and Game Over @@ -2752,6 +2780,7 @@ def provide_feedback_prompts( username, json.dumps(prompt_metadata), # Use filtered metadata for this prompt json_new_metadata, + model, ) # Only add feedback if it has content @@ -2763,14 +2792,18 @@ def provide_feedback_prompts( return feedback_messages -def translate_text(text, target_language): +def translate_text(text, target_language, model=None): # Guard clause for default language target_language = target_language.lower().split() if "english" in target_language: return text - openai_client, model_name = get_openai_client_and_model() + # Use provided model or fall back to default + if model and model != "None": + openai_client, model_name = get_openai_client_and_model(model) + else: + openai_client, model_name = get_openai_client_and_model() messages = [ { "role": "system",