smartcourseevaluation/smart_course_evaluation/reports/views.py

97 lines
3.8 KiB
Python

import pandas as pd
import matplotlib.pyplot as plt
import seaborn as sns
from django.shortcuts import render
from .forms import CSVUploadForm
import io
import base64
def get_plot_image():
buffer = io.BytesIO()
plt.savefig(buffer, format='png', bbox_inches='tight')
buffer.seek(0)
image_png = buffer.getvalue()
buffer.close()
return base64.b64encode(image_png).decode('utf-8')
def upload_csv(request):
charts = []
if request.method == "POST" and request.FILES.get("csv_file"):
form = CSVUploadForm(request.POST, request.FILES)
if form.is_valid():
csv_file = request.FILES["csv_file"]
df = pd.read_csv(csv_file)
df.columns = df.columns.str.strip() # Remove any spaces in headers
# Validate required columns
required_columns = ['Semester', 'Geschlecht', 'Fakultät', 'Wie hast du von diesem Kurs erfahren?']
missing = [col for col in required_columns if col not in df.columns]
if missing:
print('test')
return render(request, 'reports/upload.html', {
'form': form,
'error': f'Missing required columns: {", ".join(missing)}'
})
sns.set_theme(style="whitegrid")
# 1. Semester Distribution
semester_counts = df['Semester'].value_counts().sort_index()
plt.figure(figsize=(8, 4))
sns.lineplot(x=semester_counts.index, y=semester_counts.values, marker="o")
plt.title("Semester Distribution")
plt.xlabel("Semester")
plt.ylabel("Number of Students")
charts.append(get_plot_image())
plt.close()
# 2. Gender Distribution
gender_counts = df['Geschlecht'].value_counts()
plt.figure(figsize=(6, 4))
ax = sns.barplot(x=gender_counts.index, y=gender_counts.values, palette="pastel", hue=gender_counts.index, legend=False)
for i, v in enumerate(gender_counts.values):
ax.text(i, v + 0.2, str(v), color='black', ha='center', fontweight='bold')
plt.title("Gender Distribution")
plt.xlabel("Gender")
plt.ylabel("Number of Students")
charts.append(get_plot_image())
plt.close()
# 3. Faculty Distribution
df['Fakultät'] = df['Fakultät'].replace({
'B (Biotechnologie)': 'B',
'N (Informationstechnik)': 'N',
'M (Maschinenbau)': 'M',
'I (Informatik)': 'I',
'E (Elektrotechnik)': 'E',
})
faculty_counts = df['Fakultät'].value_counts()
plt.figure(figsize=(6, 4))
ax = sns.barplot(x=faculty_counts.index, y=faculty_counts.values, palette="muted", hue=faculty_counts.index, legend=False)
for i, v in enumerate(faculty_counts.values):
ax.text(i, v + 0.2, str(v), color='black', ha='center', fontweight='bold')
plt.title("Faculty Distribution")
plt.xlabel("Faculty")
plt.ylabel("Number of Students")
charts.append(get_plot_image())
plt.close()
print('test2')
# 4. Course Discovery (Pie Chart)
course_source_counts = df['Wie hast du von diesem Kurs erfahren?'].value_counts()
plt.figure(figsize=(6, 6))
plt.pie(course_source_counts, labels=course_source_counts.index, autopct='%1.1f%%', startangle=140)
plt.title("How Did Students Hear About the Course?")
charts.append(get_plot_image())
plt.close()
return render(request, 'reports/upload.html', {
'form': form,
'charts': charts
})
else:
form = CSVUploadForm()
return render(request, 'reports/upload.html', {'form': form})