import os
from collections import defaultdict

from flask import render_template
from flask_login import login_required
from sqlalchemy import and_

from app import db
from app.decorators import operator_required
from app.models import Student, MonthNameList, Course, PaymentStatus, Payment, Teacher, Schedule
from app.users.operator import operator


@operator.route('/')
@login_required
@operator_required
def index():
    title = os.environ.get('APP_NAME')

    # get all students data on schedule, except if the student tuition payment is None, PENDING, REJECTED or WARNING_3
    students_courses_data = db.session.query(Schedule, Payment).join(Payment).filter(
        and_(Payment.status_of_payment is not None,
             Payment.status_of_payment != PaymentStatus.PENDING.name,
             Payment.status_of_payment != PaymentStatus.REJECTED.name,
             Payment.status_of_payment != PaymentStatus.WARNING_3.name))

    # get the amount of Teachers and Students
    total_students = Student.query.count()
    total_teachers = Teacher.query.count()

    month_name_list = []
    for data in MonthNameList:
        month_name_list.append(str(data))

    # make a query object for "Tahsin" and "Arabic Language" course
    tahsin = students_courses_data.join(Course).filter(Course.name == "Tahsin")
    arabic = students_courses_data.join(Course).filter(Course.name == "Bahasa Arab")

    # the total payment for the courses each month
    tahsin_course_data = []
    arabic_course_data = []
    for data in tahsin:
        for month_name in month_name_list:
            tahsin_course_data.append({str(month_name): data.Payment.created_at.strftime('%B').count(month_name)})
    for data in arabic:
        for month_name in month_name_list:
            arabic_course_data.append({str(month_name): data.Payment.created_at.strftime('%B').count(month_name)})

    # merge and sum the total value from the dictionary on the same month from the _courses_data result above
    total_tahsin_students_per_month = defaultdict(int)
    total_arabic_students_per_month = defaultdict(int)
    for d in tahsin_course_data:
        for key, value in d.items():
            total_tahsin_students_per_month[key] += value
    for d in arabic_course_data:
        for key, value in d.items():
            total_arabic_students_per_month[key] += value

    # store all of the month values on a list for each course
    tahsin_values = []
    arabic_values = []
    for key, value in total_tahsin_students_per_month.items():
        tahsin_values.append(value)
    for key, value in total_arabic_students_per_month.items():
        arabic_values.append(value)

    # make a dictionary to represent course name with the matching total student that do the payment for each month
    data_courses_each_month = [
        {
            'Tahsin': tahsin_values,
        },
        {
            'Bahasa Arab': arabic_values
        }
    ]

    return render_template('main/operator/operator-dashboard.html', title=title, total_teachers=total_teachers,
                           total_students=total_students, month_name_list=month_name_list,
                           data_courses_each_month=data_courses_each_month)

[((14, 1, 14, 20), 'app.users.operator.operator.route', 'operator.route', ({(14, 16, 14, 19): '"""/"""'}, {}), "('/')", False, 'from app.users.operator import operator\n'), ((18, 12, 18, 38), 'os.environ.get', 'os.environ.get', ({(18, 27, 18, 37): '"""APP_NAME"""'}, {}), "('APP_NAME')", False, 'import os\n'), ((28, 21, 28, 42), 'app.models.Student.query.count', 'Student.query.count', ({}, {}), '()', False, 'from app.models import Student, MonthNameList, Course, PaymentStatus, Payment, Teacher, Schedule\n'), ((29, 21, 29, 42), 'app.models.Teacher.query.count', 'Teacher.query.count', ({}, {}), '()', False, 'from app.models import Student, MonthNameList, Course, PaymentStatus, Payment, Teacher, Schedule\n'), ((50, 38, 50, 54), 'collections.defaultdict', 'defaultdict', ({(50, 50, 50, 53): 'int'}, {}), '(int)', False, 'from collections import defaultdict\n'), ((51, 38, 51, 54), 'collections.defaultdict', 'defaultdict', ({(51, 50, 51, 53): 'int'}, {}), '(int)', False, 'from collections import defaultdict\n'), ((77, 11, 79, 75), 'flask.render_template', 'render_template', (), '', False, 'from flask import render_template\n'), ((22, 8, 25, 71), 'sqlalchemy.and_', 'and_', ({(22, 13, 22, 50): 'Payment.status_of_payment is not None', (23, 13, 23, 68): 'Payment.status_of_payment != PaymentStatus.PENDING.name', (24, 13, 24, 69): 'Payment.status_of_payment != PaymentStatus.REJECTED.name', (25, 13, 25, 70): 'Payment.status_of_payment != PaymentStatus.WARNING_3.name'}, {}), '(Payment.status_of_payment is not None, Payment.status_of_payment !=\n    PaymentStatus.PENDING.name, Payment.status_of_payment != PaymentStatus.\n    REJECTED.name, Payment.status_of_payment != PaymentStatus.WARNING_3.name)', False, 'from sqlalchemy import and_\n'), ((21, 28, 21, 63), 'app.db.session.query', 'db.session.query', ({(21, 45, 21, 53): 'Schedule', (21, 55, 21, 62): 'Payment'}, {}), '(Schedule, Payment)', False, 'from app import db\n')]