Spaces:
Running
Running
File size: 7,646 Bytes
ef91894 |
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 116 117 118 119 120 121 122 123 124 125 126 127 128 129 130 131 132 133 134 135 136 137 138 139 140 141 142 143 144 145 146 147 148 149 150 151 152 153 154 155 156 157 158 159 160 161 162 163 164 165 166 167 168 169 170 171 172 173 174 |
import streamlit as st
import openai
import time
# Set your OpenAI API key from Hugging Face Secrets
openai.api_key = st.secrets["OPENAI_API_KEY"]
# Initialize OpenAI client
client = openai.OpenAI(api_key=openai.api_key)
# Function to generate exam questions using OpenAI API with retry logic
def generate_questions_with_retry(knowledge_material, question_type, cognitive_level, extra_instructions, case_based, num_choices=None, max_retries=3):
# Adjust the number of questions based on the type
if question_type == "Multiple Choice":
num_questions = 3
elif question_type == "Fill in the Blank":
num_questions = 10
elif question_type == "True/False":
num_questions = 5 # Generate 5 true/false questions
else: # Open-ended
num_questions = 3
# Base prompt
prompt = f"Generate {num_questions} {question_type.lower()} exam questions based on {cognitive_level.lower()} level from the following material: {knowledge_material}. {extra_instructions}"
# If case-based medical situation is selected, modify the prompt
if case_based:
prompt = f"Generate {num_questions} {question_type.lower()} exam questions based on {cognitive_level.lower()} level from the following medical material: {knowledge_material}. The questions should be based on case-based medical situations, such as patient scenarios. {extra_instructions}"
if question_type != "Fill in the Blank":
prompt += " Provide answers with short explanations."
# Add specific handling for Multiple Choice and True/False
if question_type == "Multiple Choice" and num_choices:
prompt += f" Each multiple choice question should have {num_choices} choices."
if question_type == "True/False":
prompt += " Provide short explanations for each question based on the given material, without stating True or False explicitly."
retries = 0
while retries < max_retries:
try:
response = client.chat.completions.create(
model="gpt-4o-mini",
messages=[
{"role": "system", "content": "You are a helpful assistant for generating exam questions."},
{"role": "user", "content": prompt}
]
)
return response.choices[0].message.content
except openai.error.APIConnectionError:
retries += 1
time.sleep(2) # Wait for 2 seconds before retrying
if retries == max_retries:
st.error("Failed to connect to OpenAI API after several attempts.")
return None
# Login page
if 'username' not in st.session_state:
# Show the login form if the username is not set
st.title("Login")
username_input = st.text_input("Enter your username:")
if st.button("Login"):
if username_input:
st.session_state['username'] = username_input
st.success(f"Welcome, {username_input}!")
else:
st.warning("Please enter a valid username.")
else:
# Main App after login
st.title(f"Welcome, {st.session_state['username']}! Generate your exam questions")
# Input field for knowledge material (text) with 3,000-word limit
knowledge_material = st.text_area("Enter knowledge material to generate exam questions:")
# Word count check
if len(knowledge_material.split()) > 3000:
st.warning("Please limit the knowledge material to 3,000 words or fewer.")
# File uploader for PDFs (limited to 5 MB)
uploaded_file = st.file_uploader("Upload a file (PDF)", type="pdf")
if uploaded_file is not None:
if uploaded_file.size > 5 * 1024 * 1024: # 5 MB limit
st.warning("File size exceeds 5 MB. Please upload a smaller file.")
else:
# Here you can add code to extract text from the PDF if needed
# For simplicity, we're focusing on the text input for now
st.success("File uploaded successfully! (Text extraction not implemented yet.)")
# Select question type
question_type = st.selectbox("Select question type:",
["Multiple Choice", "Fill in the Blank", "Open-ended", "True/False"])
# For multiple choice, let users select the number of choices
num_choices = None
if question_type == "Multiple Choice":
num_choices = st.selectbox("Select the number of choices for each question:", [3, 4, 5])
# Select cognitive level
cognitive_level = st.selectbox("Select cognitive level:",
["Recall", "Understanding", "Application", "Analysis", "Synthesis", "Evaluation"])
# Checkbox for Case-Based Medical Situations
case_based = st.checkbox("Generate case-based medical exam questions")
# Extra input field for additional instructions (placed below cognitive level)
extra_instructions = st.text_area("Enter additional instructions (e.g., how you want the questions to be phrased):")
# Generate questions button
if 'previous_questions' not in st.session_state:
st.session_state['previous_questions'] = []
if st.button("Generate Questions"):
if len(knowledge_material.split()) <= 3000:
# Generate questions with retry logic
questions = generate_questions_with_retry(
knowledge_material,
question_type,
cognitive_level,
extra_instructions,
case_based,
num_choices
)
if questions:
st.write("Generated Exam Questions:")
st.write(questions)
# Avoid showing repeated content in future requests
st.session_state['previous_questions'].append(questions)
# Option to download the questions as a text file
st.download_button(
label="Download Questions",
data=questions,
file_name='generated_questions.txt',
mime='text/plain'
)
else:
st.warning("Please reduce the word count to 3,000 or fewer.")
# Button to generate more questions based on the same material
if st.button("Generate More Questions"):
if len(knowledge_material.split()) <= 3000:
# Regenerate new questions, trying to avoid repeated content
questions = generate_questions_with_retry(
knowledge_material,
question_type,
cognitive_level,
extra_instructions,
case_based,
num_choices
)
# Check if the new set of questions is not the same as the previous set
if questions and questions not in st.session_state['previous_questions']:
st.write("Generated More Exam Questions:")
st.write(questions)
# Append the new questions to the session state
st.session_state['previous_questions'].append(questions)
# Option to download the new set of questions
st.download_button(
label="Download More Questions",
data=questions,
file_name='more_generated_questions.txt',
mime='text/plain'
)
else:
st.warning("New questions seem to overlap with the previous ones. Try adjusting the instructions.")
else:
st.warning("Please reduce the word count to 3,000 or fewer.")
|