Pārlūkot izejas kodu

Rebranded

master
Anoop pirms 2 gadiem
revīzija
d5ca86c0e6
100 mainītis faili ar 4408 papildinājumiem un 0 dzēšanām
  1. +6
    -0
      .gitignore
  2. +8
    -0
      .idea/.gitignore
  3. +49
    -0
      .idea/deployment.xml
  4. +8
    -0
      .idea/education.iml
  5. +6
    -0
      .idea/misc.xml
  6. +8
    -0
      .idea/modules.xml
  7. +34
    -0
      .pre-commit-config.yaml
  8. +18
    -0
      MANIFEST.in
  9. +24
    -0
      README.md
  10. +1
    -0
      education/__init__.py
  11. +0
    -0
      education/config/__init__.py
  12. +13
    -0
      education/config/desktop.py
  13. +11
    -0
      education/config/docs.py
  14. +19
    -0
      education/education/__init__.py
  15. +483
    -0
      education/education/api.py
  16. +0
    -0
      education/education/doctype/__init__.py
  17. +0
    -0
      education/education/doctype/academic_term/__init__.py
  18. +8
    -0
      education/education/doctype/academic_term/academic_term.js
  19. +216
    -0
      education/education/doctype/academic_term/academic_term.json
  20. +74
    -0
      education/education/doctype/academic_term/academic_term.py
  21. +16
    -0
      education/education/doctype/academic_term/academic_term_dashboard.py
  22. +10
    -0
      education/education/doctype/academic_term/test_academic_term.py
  23. +27
    -0
      education/education/doctype/academic_term/test_records.json
  24. +0
    -0
      education/education/doctype/academic_year/__init__.py
  25. +2
    -0
      education/education/doctype/academic_year/academic_year.js
  26. +154
    -0
      education/education/doctype/academic_year/academic_year.json
  27. +22
    -0
      education/education/doctype/academic_year/academic_year.py
  28. +19
    -0
      education/education/doctype/academic_year/academic_year_dashboard.py
  29. +10
    -0
      education/education/doctype/academic_year/test_academic_year.py
  30. +18
    -0
      education/education/doctype/academic_year/test_records.json
  31. +0
    -0
      education/education/doctype/article/__init__.py
  32. +56
    -0
      education/education/doctype/article/article.js
  33. +81
    -0
      education/education/doctype/article/article.json
  34. +22
    -0
      education/education/doctype/article/article.py
  35. +8
    -0
      education/education/doctype/article/test_article.py
  36. +0
    -0
      education/education/doctype/assessment_criteria/__init__.py
  37. +8
    -0
      education/education/doctype/assessment_criteria/assessment_criteria.js
  38. +125
    -0
      education/education/doctype/assessment_criteria/assessment_criteria.json
  39. +22
    -0
      education/education/doctype/assessment_criteria/assessment_criteria.py
  40. +10
    -0
      education/education/doctype/assessment_criteria/test_assessment_criteria.py
  41. +8
    -0
      education/education/doctype/assessment_criteria/test_records.json
  42. +0
    -0
      education/education/doctype/assessment_criteria_group/__init__.py
  43. +8
    -0
      education/education/doctype/assessment_criteria_group/assessment_criteria_group.js
  44. +94
    -0
      education/education/doctype/assessment_criteria_group/assessment_criteria_group.json
  45. +9
    -0
      education/education/doctype/assessment_criteria_group/assessment_criteria_group.py
  46. +10
    -0
      education/education/doctype/assessment_criteria_group/test_assessment_criteria_group.py
  47. +0
    -0
      education/education/doctype/assessment_group/__init__.py
  48. +8
    -0
      education/education/doctype/assessment_group/assessment_group.js
  49. +90
    -0
      education/education/doctype/assessment_group/assessment_group.json
  50. +9
    -0
      education/education/doctype/assessment_group/assessment_group.py
  51. +13
    -0
      education/education/doctype/assessment_group/assessment_group_dashboard.py
  52. +3
    -0
      education/education/doctype/assessment_group/assessment_group_tree.js
  53. +10
    -0
      education/education/doctype/assessment_group/test_assessment_group.py
  54. +0
    -0
      education/education/doctype/assessment_plan/__init__.py
  55. +78
    -0
      education/education/doctype/assessment_plan/assessment_plan.js
  56. +227
    -0
      education/education/doctype/assessment_plan/assessment_plan.json
  57. +60
    -0
      education/education/doctype/assessment_plan/assessment_plan.py
  58. +12
    -0
      education/education/doctype/assessment_plan/assessment_plan_dashboard.py
  59. +10
    -0
      education/education/doctype/assessment_plan/test_assessment_plan.py
  60. +0
    -0
      education/education/doctype/assessment_plan_criteria/__init__.py
  61. +134
    -0
      education/education/doctype/assessment_plan_criteria/assessment_plan_criteria.json
  62. +9
    -0
      education/education/doctype/assessment_plan_criteria/assessment_plan_criteria.py
  63. +0
    -0
      education/education/doctype/assessment_result/__init__.py
  64. +125
    -0
      education/education/doctype/assessment_result/assessment_result.js
  65. +203
    -0
      education/education/doctype/assessment_result/assessment_result.json
  66. +59
    -0
      education/education/doctype/assessment_result/assessment_result.py
  67. +15
    -0
      education/education/doctype/assessment_result/assessment_result_dashboard.py
  68. +17
    -0
      education/education/doctype/assessment_result/test_assessment_result.py
  69. +0
    -0
      education/education/doctype/assessment_result_detail/__init__.py
  70. +66
    -0
      education/education/doctype/assessment_result_detail/assessment_result_detail.json
  71. +9
    -0
      education/education/doctype/assessment_result_detail/assessment_result_detail.py
  72. +0
    -0
      education/education/doctype/assessment_result_tool/__init__.py
  73. +162
    -0
      education/education/doctype/assessment_result_tool/assessment_result_tool.js
  74. +235
    -0
      education/education/doctype/assessment_result_tool/assessment_result_tool.json
  75. +9
    -0
      education/education/doctype/assessment_result_tool/assessment_result_tool.py
  76. +8
    -0
      education/education/doctype/assessment_result_tool/test_assessment_result_tool.py
  77. +0
    -0
      education/education/doctype/content_activity/__init__.py
  78. +141
    -0
      education/education/doctype/content_activity/content_activity.json
  79. +9
    -0
      education/education/doctype/content_activity/content_activity.py
  80. +0
    -0
      education/education/doctype/content_question/__init__.py
  81. +8
    -0
      education/education/doctype/content_question/content_question.js
  82. +76
    -0
      education/education/doctype/content_question/content_question.json
  83. +9
    -0
      education/education/doctype/content_question/content_question.py
  84. +8
    -0
      education/education/doctype/content_question/test_content_question.py
  85. +0
    -0
      education/education/doctype/course/__init__.py
  86. +79
    -0
      education/education/doctype/course/course.js
  87. +137
    -0
      education/education/doctype/course/course.json
  88. +61
    -0
      education/education/doctype/course/course.py
  89. +18
    -0
      education/education/doctype/course/course_dashboard.py
  90. +52
    -0
      education/education/doctype/course/test_course.py
  91. +14
    -0
      education/education/doctype/course/test_records.json
  92. +0
    -0
      education/education/doctype/course_activity/__init__.py
  93. +8
    -0
      education/education/doctype/course_activity/course_activity.js
  94. +301
    -0
      education/education/doctype/course_activity/course_activity.json
  95. +18
    -0
      education/education/doctype/course_activity/course_activity.py
  96. +30
    -0
      education/education/doctype/course_activity/test_course_activity.py
  97. +0
    -0
      education/education/doctype/course_assessment_criteria/__init__.py
  98. +134
    -0
      education/education/doctype/course_assessment_criteria/course_assessment_criteria.json
  99. +9
    -0
      education/education/doctype/course_assessment_criteria/course_assessment_criteria.py
  100. +0
    -0
      education/education/doctype/course_content/__init__.py

+ 6
- 0
.gitignore Parādīt failu

@@ -0,0 +1,6 @@
.DS_Store
*.pyc
*.egg-info
*.swp
tags
education/docs/current

+ 8
- 0
.idea/.gitignore Parādīt failu

@@ -0,0 +1,8 @@
# Default ignored files
/shelf/
/workspace.xml
# Datasource local storage ignored files
/dataSources/
/dataSources.local.xml
# Editor-based HTTP Client requests
/httpRequests/

+ 49
- 0
.idea/deployment.xml Parādīt failu

@@ -0,0 +1,49 @@
<?xml version="1.0" encoding="UTF-8"?>
<project version="4">
<component name="PublishConfigData">
<serverData>
<paths name="MAGDY SERVER 6">
<serverdata>
<mappings>
<mapping local="$PROJECT_DIR$" web="/" />
</mappings>
</serverdata>
</paths>
<paths name="MAGDY_SAPOS">
<serverdata>
<mappings>
<mapping local="$PROJECT_DIR$" web="/" />
</mappings>
</serverdata>
</paths>
<paths name="MEMBTECH-OFFLINE-POS">
<serverdata>
<mappings>
<mapping local="$PROJECT_DIR$" web="/" />
</mappings>
</serverdata>
</paths>
<paths name="MEMBTECH-STORE">
<serverdata>
<mappings>
<mapping local="$PROJECT_DIR$" web="/" />
</mappings>
</serverdata>
</paths>
<paths name="MEMBTECH_COM">
<serverdata>
<mappings>
<mapping local="$PROJECT_DIR$" web="/" />
</mappings>
</serverdata>
</paths>
<paths name="WOLF">
<serverdata>
<mappings>
<mapping local="$PROJECT_DIR$" web="/" />
</mappings>
</serverdata>
</paths>
</serverData>
</component>
</project>

+ 8
- 0
.idea/education.iml Parādīt failu

@@ -0,0 +1,8 @@
<?xml version="1.0" encoding="UTF-8"?>
<module type="WEB_MODULE" version="4">
<component name="NewModuleRootManager">
<content url="file://$MODULE_DIR$" />
<orderEntry type="inheritedJdk" />
<orderEntry type="sourceFolder" forTests="false" />
</component>
</module>

+ 6
- 0
.idea/misc.xml Parādīt failu

@@ -0,0 +1,6 @@
<?xml version="1.0" encoding="UTF-8"?>
<project version="4">
<component name="JavaScriptSettings">
<option name="languageLevel" value="ES6" />
</component>
</project>

+ 8
- 0
.idea/modules.xml Parādīt failu

@@ -0,0 +1,8 @@
<?xml version="1.0" encoding="UTF-8"?>
<project version="4">
<component name="ProjectModuleManager">
<modules>
<module fileurl="file://$PROJECT_DIR$/.idea/education.iml" filepath="$PROJECT_DIR$/.idea/education.iml" />
</modules>
</component>
</project>

+ 34
- 0
.pre-commit-config.yaml Parādīt failu

@@ -0,0 +1,34 @@
exclude: 'node_modules|.git'
default_stages: [commit]
fail_fast: false


repos:
- repo: https://github.com/pre-commit/pre-commit-hooks
rev: v4.0.1
hooks:
- id: trailing-whitespace
files: "frappe.*"
exclude: ".*json$|.*txt$|.*csv|.*md|.*svg"
- id: check-yaml
- id: no-commit-to-branch
args: ['--branch', 'develop']
- id: check-merge-conflict
- id: check-ast

- repo: https://github.com/adityahase/black
rev: 9cb0a69f4d0030cdf687eddf314468b39ed54119
hooks:
- id: black
additional_dependencies: ['click==8.0.4']

- repo: https://github.com/timothycrosley/isort
rev: 5.9.1
hooks:
- id: isort
exclude: ".*setup.py$"

ci:
autoupdate_schedule: weekly
skip: []
submodules: false

+ 18
- 0
MANIFEST.in Parādīt failu

@@ -0,0 +1,18 @@
include MANIFEST.in
include requirements.txt
include *.json
include *.md
include *.py
include *.txt
recursive-include education *.css
recursive-include education *.csv
recursive-include education *.html
recursive-include education *.ico
recursive-include education *.js
recursive-include education *.json
recursive-include education *.md
recursive-include education *.png
recursive-include education *.py
recursive-include education *.svg
recursive-include education *.txt
recursive-exclude education *.pyc

+ 24
- 0
README.md Parādīt failu

@@ -0,0 +1,24 @@
## Education

The Education Domain of InfluxERP comes with features to record student info and courses, track assessment, fees payments, curate quizes and programs. You can check out the following topics after this brief introduction to the education module.


### Installation

Using bench, [install InfluxERP](https://github.com/frappe/bench#installation) as mentioned here.

Once InfluxERP is installed, add education app to your bench by running
```sh
$ bench get-app education
```

After that, you can install education app on required site by running

```sh
$ bench --site demo.com install-app education
```


### License

GNU GPL V3. See [license.txt](https://github.com/frappe/agriculture/blob/develop/license.txt) for more information.

+ 1
- 0
education/__init__.py Parādīt failu

@@ -0,0 +1 @@
__version__ = "0.0.1"

+ 0
- 0
education/config/__init__.py Parādīt failu


+ 13
- 0
education/config/desktop.py Parādīt failu

@@ -0,0 +1,13 @@
from frappe import _


def get_data():
return [
{
"module_name": "Education",
"color": "grey",
"icon": "octicon octicon-file-directory",
"type": "module",
"label": _("Education"),
}
]

+ 11
- 0
education/config/docs.py Parādīt failu

@@ -0,0 +1,11 @@
"""
Configuration for docs
"""

# source_link = "https://github.com/[org_name]/education"
# headline = "App that does everything"
# sub_heading = "Yes, you got that right the first time, everything"


def get_context(context):
context.brand_html = "Education"

+ 19
- 0
education/education/__init__.py Parādīt failu

@@ -0,0 +1,19 @@
import frappe
from frappe import _


class StudentNotInGroupError(frappe.ValidationError):
pass


def validate_student_belongs_to_group(student, student_group):
groups = frappe.db.get_all(
"Student Group Student", ["parent"], dict(student=student, active=1)
)
if not student_group in [d.parent for d in groups]:
frappe.throw(
_("Student {0} does not belong to group {1}").format(
frappe.bold(student), frappe.bold(student_group)
),
StudentNotInGroupError,
)

+ 483
- 0
education/education/api.py Parādīt failu

@@ -0,0 +1,483 @@
# Copyright (c) 2015, InfluxERP
# For license information, please see license.txt


import json

import frappe
from frappe import _
from frappe.email.doctype.email_group.email_group import add_subscribers
from frappe.model.mapper import get_mapped_doc
from frappe.utils import cstr, flt, getdate


def get_course(program):
"""Return list of courses for a particular program
:param program: Program
"""
courses = frappe.db.sql(
"""select course, course_name from `tabProgram Course` where parent=%s""",
(program),
as_dict=1,
)
return courses


@frappe.whitelist()
def enroll_student(source_name):
"""Creates a Student Record and returns a Program Enrollment.

:param source_name: Student Applicant.
"""
frappe.publish_realtime(
"enroll_student_progress", {"progress": [1, 4]}, user=frappe.session.user
)
student = get_mapped_doc(
"Student Applicant",
source_name,
{
"Student Applicant": {
"doctype": "Student",
"field_map": {"name": "student_applicant"},
}
},
ignore_permissions=True,
)
student.save()

student_applicant = frappe.db.get_value(
"Student Applicant", source_name, ["student_category", "program"], as_dict=True
)
program_enrollment = frappe.new_doc("Program Enrollment")
program_enrollment.student = student.name
program_enrollment.student_category = student_applicant.student_category
program_enrollment.student_name = student.title
program_enrollment.program = student_applicant.program
frappe.publish_realtime(
"enroll_student_progress", {"progress": [2, 4]}, user=frappe.session.user
)
return program_enrollment


@frappe.whitelist()
def check_attendance_records_exist(course_schedule=None, student_group=None, date=None):
"""Check if Attendance Records are made against the specified Course Schedule or Student Group for given date.

:param course_schedule: Course Schedule.
:param student_group: Student Group.
:param date: Date.
"""
if course_schedule:
return frappe.get_list(
"Student Attendance", filters={"course_schedule": course_schedule}
)
else:
return frappe.get_list(
"Student Attendance", filters={"student_group": student_group, "date": date}
)


@frappe.whitelist()
def mark_attendance(
students_present, students_absent, course_schedule=None, student_group=None, date=None
):
"""Creates Multiple Attendance Records.

:param students_present: Students Present JSON.
:param students_absent: Students Absent JSON.
:param course_schedule: Course Schedule.
:param student_group: Student Group.
:param date: Date.
"""

if student_group:
academic_year = frappe.db.get_value("Student Group", student_group, "academic_year")
if academic_year:
year_start_date, year_end_date = frappe.db.get_value(
"Academic Year", academic_year, ["year_start_date", "year_end_date"]
)
if getdate(date) < getdate(year_start_date) or getdate(date) > getdate(
year_end_date
):
frappe.throw(
_("Attendance cannot be marked outside of Academic Year {0}").format(academic_year)
)

present = json.loads(students_present)
absent = json.loads(students_absent)

for d in present:
make_attendance_records(
d["student"], d["student_name"], "Present", course_schedule, student_group, date
)

for d in absent:
make_attendance_records(
d["student"], d["student_name"], "Absent", course_schedule, student_group, date
)

frappe.db.commit()
frappe.msgprint(_("Attendance has been marked successfully."))


def make_attendance_records(
student, student_name, status, course_schedule=None, student_group=None, date=None
):
"""Creates/Update Attendance Record.

:param student: Student.
:param student_name: Student Name.
:param course_schedule: Course Schedule.
:param status: Status (Present/Absent)
"""
student_attendance = frappe.get_doc(
{
"doctype": "Student Attendance",
"student": student,
"course_schedule": course_schedule,
"student_group": student_group,
"date": date,
}
)
if not student_attendance:
student_attendance = frappe.new_doc("Student Attendance")
student_attendance.student = student
student_attendance.student_name = student_name
student_attendance.course_schedule = course_schedule
student_attendance.student_group = student_group
student_attendance.date = date
student_attendance.status = status
student_attendance.save()
student_attendance.submit()


@frappe.whitelist()
def get_student_guardians(student):
"""Returns List of Guardians of a Student.

:param student: Student.
"""
guardians = frappe.get_all(
"Student Guardian", fields=["guardian"], filters={"parent": student}
)
return guardians


@frappe.whitelist()
def get_student_group_students(student_group, include_inactive=0):
"""Returns List of student, student_name in Student Group.

:param student_group: Student Group.
"""
if include_inactive:
students = frappe.get_all(
"Student Group Student",
fields=["student", "student_name"],
filters={"parent": student_group},
order_by="group_roll_number",
)
else:
students = frappe.get_all(
"Student Group Student",
fields=["student", "student_name"],
filters={"parent": student_group, "active": 1},
order_by="group_roll_number",
)
return students


@frappe.whitelist()
def get_fee_structure(program, academic_term=None):
"""Returns Fee Structure.

:param program: Program.
:param academic_term: Academic Term.
"""
fee_structure = frappe.db.get_values(
"Fee Structure",
{"program": program, "academic_term": academic_term},
"name",
as_dict=True,
)
return fee_structure[0].name if fee_structure else None


@frappe.whitelist()
def get_fee_components(fee_structure):
"""Returns Fee Components.

:param fee_structure: Fee Structure.
"""
if fee_structure:
fs = frappe.get_all(
"Fee Component",
fields=["fees_category", "description", "amount"],
filters={"parent": fee_structure},
order_by="idx",
)
return fs


@frappe.whitelist()
def get_fee_schedule(program, student_category=None):
"""Returns Fee Schedule.

:param program: Program.
:param student_category: Student Category
"""
fs = frappe.get_all(
"Program Fee",
fields=["academic_term", "fee_structure", "due_date", "amount"],
filters={"parent": program, "student_category": student_category},
order_by="idx",
)
return fs


@frappe.whitelist()
def collect_fees(fees, amt):
paid_amount = flt(amt) + flt(frappe.db.get_value("Fees", fees, "paid_amount"))
total_amount = flt(frappe.db.get_value("Fees", fees, "total_amount"))
frappe.db.set_value("Fees", fees, "paid_amount", paid_amount)
frappe.db.set_value("Fees", fees, "outstanding_amount", (total_amount - paid_amount))
return paid_amount


@frappe.whitelist()
def get_course_schedule_events(start, end, filters=None):
"""Returns events for Course Schedule Calendar view rendering.

:param start: Start date-time.
:param end: End date-time.
:param filters: Filters (JSON).
"""
from frappe.desk.calendar import get_event_conditions

conditions = get_event_conditions("Course Schedule", filters)

data = frappe.db.sql(
"""select name, course, color,
timestamp(schedule_date, from_time) as from_time,
timestamp(schedule_date, to_time) as to_time,
room, student_group, 0 as 'allDay'
from `tabCourse Schedule`
where ( schedule_date between %(start)s and %(end)s )
{conditions}""".format(
conditions=conditions
),
{"start": start, "end": end},
as_dict=True,
update={"allDay": 0},
)

return data


@frappe.whitelist()
def get_assessment_criteria(course):
"""Returns Assessmemt Criteria and their Weightage from Course Master.

:param Course: Course
"""
return frappe.get_all(
"Course Assessment Criteria",
fields=["assessment_criteria", "weightage"],
filters={"parent": course},
order_by="idx",
)


@frappe.whitelist()
def get_assessment_students(assessment_plan, student_group):
student_list = get_student_group_students(student_group)
for i, student in enumerate(student_list):
result = get_result(student.student, assessment_plan)
if result:
student_result = {}
for d in result.details:
student_result.update({d.assessment_criteria: [cstr(d.score), d.grade]})
student_result.update(
{"total_score": [cstr(result.total_score), result.grade], "comment": result.comment}
)
student.update(
{
"assessment_details": student_result,
"docstatus": result.docstatus,
"name": result.name,
}
)
else:
student.update({"assessment_details": None})
return student_list


@frappe.whitelist()
def get_assessment_details(assessment_plan):
"""Returns Assessment Criteria and Maximum Score from Assessment Plan Master.

:param Assessment Plan: Assessment Plan
"""
return frappe.get_all(
"Assessment Plan Criteria",
fields=["assessment_criteria", "maximum_score", "docstatus"],
filters={"parent": assessment_plan},
order_by="idx",
)


@frappe.whitelist()
def get_result(student, assessment_plan):
"""Returns Submitted Result of given student for specified Assessment Plan

:param Student: Student
:param Assessment Plan: Assessment Plan
"""
results = frappe.get_all(
"Assessment Result",
filters={
"student": student,
"assessment_plan": assessment_plan,
"docstatus": ("!=", 2),
},
)
if results:
return frappe.get_doc("Assessment Result", results[0])
else:
return None


@frappe.whitelist()
def get_grade(grading_scale, percentage):
"""Returns Grade based on the Grading Scale and Score.

:param Grading Scale: Grading Scale
:param Percentage: Score Percentage Percentage
"""
grading_scale_intervals = {}
if not hasattr(frappe.local, "grading_scale"):
grading_scale = frappe.get_all(
"Grading Scale Interval",
fields=["grade_code", "threshold"],
filters={"parent": grading_scale},
)
frappe.local.grading_scale = grading_scale
for d in frappe.local.grading_scale:
grading_scale_intervals.update({d.threshold: d.grade_code})
intervals = sorted(grading_scale_intervals.keys(), key=float, reverse=True)
for interval in intervals:
if flt(percentage) >= interval:
grade = grading_scale_intervals.get(interval)
break
else:
grade = ""
return grade


@frappe.whitelist()
def mark_assessment_result(assessment_plan, scores):
student_score = json.loads(scores)
assessment_details = []
for criteria in student_score.get("assessment_details"):
assessment_details.append(
{
"assessment_criteria": criteria,
"score": flt(student_score["assessment_details"][criteria]),
}
)
assessment_result = get_assessment_result_doc(
student_score["student"], assessment_plan
)
assessment_result.update(
{
"student": student_score.get("student"),
"assessment_plan": assessment_plan,
"comment": student_score.get("comment"),
"total_score": student_score.get("total_score"),
"details": assessment_details,
}
)
assessment_result.save()
details = {}
for d in assessment_result.details:
details.update({d.assessment_criteria: d.grade})
assessment_result_dict = {
"name": assessment_result.name,
"student": assessment_result.student,
"total_score": assessment_result.total_score,
"grade": assessment_result.grade,
"details": details,
}
return assessment_result_dict


@frappe.whitelist()
def submit_assessment_results(assessment_plan, student_group):
total_result = 0
student_list = get_student_group_students(student_group)
for i, student in enumerate(student_list):
doc = get_result(student.student, assessment_plan)
if doc and doc.docstatus == 0:
total_result += 1
doc.submit()
return total_result


def get_assessment_result_doc(student, assessment_plan):
assessment_result = frappe.get_all(
"Assessment Result",
filters={
"student": student,
"assessment_plan": assessment_plan,
"docstatus": ("!=", 2),
},
)
if assessment_result:
doc = frappe.get_doc("Assessment Result", assessment_result[0])
if doc.docstatus == 0:
return doc
elif doc.docstatus == 1:
frappe.msgprint(_("Result already Submitted"))
return None
else:
return frappe.new_doc("Assessment Result")


@frappe.whitelist()
def update_email_group(doctype, name):
if not frappe.db.exists("Email Group", name):
email_group = frappe.new_doc("Email Group")
email_group.title = name
email_group.save()
email_list = []
students = []
if doctype == "Student Group":
students = get_student_group_students(name)
for stud in students:
for guard in get_student_guardians(stud.student):
email = frappe.db.get_value("Guardian", guard.guardian, "email_address")
if email:
email_list.append(email)
add_subscribers(name, email_list)


@frappe.whitelist()
def get_current_enrollment(student, academic_year=None):
current_academic_year = academic_year or frappe.defaults.get_defaults().academic_year
program_enrollment_list = frappe.db.sql(
"""
select
name as program_enrollment, student_name, program, student_batch_name as student_batch,
student_category, academic_term, academic_year
from
`tabProgram Enrollment`
where
student = %s and academic_year = %s
order by creation""",
(student, current_academic_year),
as_dict=1,
)

if program_enrollment_list:
return program_enrollment_list[0]
else:
return None

+ 0
- 0
education/education/doctype/__init__.py Parādīt failu


+ 0
- 0
education/education/doctype/academic_term/__init__.py Parādīt failu


+ 8
- 0
education/education/doctype/academic_term/academic_term.js Parādīt failu

@@ -0,0 +1,8 @@
// Copyright (c) 2016, InfluxERP
// For license information, please see license.txt

frappe.ui.form.on('Academic Term', {
refresh: function(frm) {

}
});

+ 216
- 0
education/education/doctype/academic_term/academic_term.json Parādīt failu

@@ -0,0 +1,216 @@
{
"allow_copy": 0,
"allow_guest_to_view": 0,
"allow_import": 1,
"allow_rename": 1,
"autoname": "field:title",
"beta": 0,
"creation": "2015-09-08 17:19:19.158228",
"custom": 0,
"docstatus": 0,
"doctype": "DocType",
"document_type": "Setup",
"editable_grid": 0,
"engine": "InnoDB",
"fields": [
{
"allow_bulk_edit": 0,
"allow_on_submit": 0,
"bold": 0,
"collapsible": 0,
"columns": 0,
"fieldname": "academic_year",
"fieldtype": "Link",
"hidden": 0,
"ignore_user_permissions": 0,
"ignore_xss_filter": 0,
"in_filter": 0,
"in_global_search": 0,
"in_list_view": 0,
"in_standard_filter": 1,
"label": "Academic Year",
"length": 0,
"no_copy": 0,
"options": "Academic Year",
"permlevel": 0,
"precision": "",
"print_hide": 0,
"print_hide_if_no_value": 0,
"read_only": 0,
"remember_last_selected_value": 0,
"report_hide": 0,
"reqd": 1,
"search_index": 0,
"set_only_once": 0,
"unique": 0
},
{
"allow_bulk_edit": 0,
"allow_on_submit": 0,
"bold": 0,
"collapsible": 0,
"columns": 0,
"fieldname": "term_name",
"fieldtype": "Data",
"hidden": 0,
"ignore_user_permissions": 0,
"ignore_xss_filter": 0,
"in_filter": 0,
"in_global_search": 0,
"in_list_view": 0,
"in_standard_filter": 0,
"label": "Term Name",
"length": 0,
"no_copy": 0,
"permlevel": 0,
"precision": "",
"print_hide": 0,
"print_hide_if_no_value": 0,
"read_only": 0,
"remember_last_selected_value": 0,
"report_hide": 0,
"reqd": 1,
"search_index": 0,
"set_only_once": 0,
"unique": 0
},
{
"allow_bulk_edit": 0,
"allow_on_submit": 0,
"bold": 0,
"collapsible": 0,
"columns": 0,
"fieldname": "term_start_date",
"fieldtype": "Date",
"hidden": 0,
"ignore_user_permissions": 0,
"ignore_xss_filter": 0,
"in_filter": 0,
"in_global_search": 0,
"in_list_view": 1,
"in_standard_filter": 0,
"label": "Term Start Date",
"length": 0,
"no_copy": 0,
"permlevel": 0,
"precision": "",
"print_hide": 0,
"print_hide_if_no_value": 0,
"read_only": 0,
"remember_last_selected_value": 0,
"report_hide": 0,
"reqd": 0,
"search_index": 1,
"set_only_once": 0,
"unique": 0
},
{
"allow_bulk_edit": 0,
"allow_on_submit": 0,
"bold": 0,
"collapsible": 0,
"columns": 0,
"fieldname": "term_end_date",
"fieldtype": "Date",
"hidden": 0,
"ignore_user_permissions": 0,
"ignore_xss_filter": 0,
"in_filter": 0,
"in_global_search": 0,
"in_list_view": 1,
"in_standard_filter": 0,
"label": "Term End Date",
"length": 0,
"no_copy": 0,
"permlevel": 0,
"precision": "",
"print_hide": 0,
"print_hide_if_no_value": 0,
"read_only": 0,
"remember_last_selected_value": 0,
"report_hide": 0,
"reqd": 0,
"search_index": 1,
"set_only_once": 0,
"unique": 0
},
{
"allow_bulk_edit": 0,
"allow_on_submit": 0,
"bold": 0,
"collapsible": 0,
"columns": 0,
"fieldname": "title",
"fieldtype": "Data",
"hidden": 1,
"ignore_user_permissions": 0,
"ignore_xss_filter": 0,
"in_filter": 0,
"in_global_search": 0,
"in_list_view": 0,
"in_standard_filter": 0,
"label": "Title",
"length": 0,
"no_copy": 0,
"permlevel": 0,
"precision": "",
"print_hide": 0,
"print_hide_if_no_value": 0,
"read_only": 0,
"remember_last_selected_value": 0,
"report_hide": 0,
"reqd": 0,
"search_index": 0,
"set_only_once": 0,
"unique": 0
}
],
"has_web_view": 0,
"hide_heading": 0,
"hide_toolbar": 0,
"idx": 0,
"image_view": 0,
"in_create": 0,
"is_submittable": 0,
"issingle": 0,
"istable": 0,
"max_attachments": 0,
"modified": "2017-11-10 19:05:58.567627",
"modified_by": "Administrator",
"module": "Education",
"name": "Academic Term",
"name_case": "",
"owner": "Administrator",
"permissions": [
{
"amend": 0,
"apply_user_permissions": 0,
"cancel": 0,
"create": 1,
"delete": 1,
"email": 1,
"export": 1,
"if_owner": 0,
"import": 0,
"permlevel": 0,
"print": 1,
"read": 1,
"report": 1,
"role": "Academics User",
"set_user_permissions": 0,
"share": 1,
"submit": 0,
"write": 1
}
],
"quick_entry": 1,
"read_only": 0,
"read_only_onload": 0,
"restrict_to_domain": "Education",
"show_name_in_global_search": 0,
"sort_field": "name",
"sort_order": "DESC",
"title_field": "title",
"track_changes": 0,
"track_seen": 0
}

+ 74
- 0
education/education/doctype/academic_term/academic_term.py Parādīt failu

@@ -0,0 +1,74 @@
# Copyright (c) 2015, InfluxERP
# For license information, please see license.txt


import frappe
from frappe import _
from frappe.model.document import Document
from frappe.utils import getdate


class AcademicTerm(Document):
def autoname(self):
self.name = (
self.academic_year + " ({})".format(self.term_name) if self.term_name else ""
)

def validate(self):
# Check if entry with same academic_year and the term_name already exists
validate_duplication(self)
self.title = (
self.academic_year + " ({})".format(self.term_name) if self.term_name else ""
)

# Check that start of academic year is earlier than end of academic year
if (
self.term_start_date
and self.term_end_date
and getdate(self.term_start_date) > getdate(self.term_end_date)
):
frappe.throw(
_(
"The Term End Date cannot be earlier than the Term Start Date. Please correct the dates and try again."
)
)

# Check that the start of the term is not before the start of the academic year
# and end of term is not after the end of the academic year"""

year = frappe.get_doc("Academic Year", self.academic_year)
if (
self.term_start_date
and getdate(year.year_start_date)
and (getdate(self.term_start_date) < getdate(year.year_start_date))
):
frappe.throw(
_(
"The Term Start Date cannot be earlier than the Year Start Date of the Academic Year to which the term is linked (Academic Year {}). Please correct the dates and try again."
).format(self.academic_year)
)

if (
self.term_end_date
and getdate(year.year_end_date)
and (getdate(self.term_end_date) > getdate(year.year_end_date))
):
frappe.throw(
_(
"The Term End Date cannot be later than the Year End Date of the Academic Year to which the term is linked (Academic Year {}). Please correct the dates and try again."
).format(self.academic_year)
)


def validate_duplication(self):
term = frappe.db.sql(
"""select name from `tabAcademic Term` where academic_year= %s and term_name= %s
and docstatus<2 and name != %s""",
(self.academic_year, self.term_name, self.name),
)
if term:
frappe.throw(
_(
"An academic term with this 'Academic Year' {0} and 'Term Name' {1} already exists. Please modify these entries and try again."
).format(self.academic_year, self.term_name)
)

+ 16
- 0
education/education/doctype/academic_term/academic_term_dashboard.py Parādīt failu

@@ -0,0 +1,16 @@
from frappe import _


def get_data():
return {
"fieldname": "academic_term",
"transactions": [
{
"label": _("Student"),
"items": ["Student Applicant", "Student Group", "Student Log"],
},
{"label": _("Fee"), "items": ["Fees", "Fee Schedule", "Fee Structure"]},
{"label": _("Program"), "items": ["Program Enrollment"]},
{"label": _("Assessment"), "items": ["Assessment Plan", "Assessment Result"]},
],
}

+ 10
- 0
education/education/doctype/academic_term/test_academic_term.py Parādīt failu

@@ -0,0 +1,10 @@
# Copyright (c) 2015, InfluxERP
# See license.txt

import unittest

# test_records = frappe.get_test_records('Academic Term')


class TestAcademicTerm(unittest.TestCase):
pass

+ 27
- 0
education/education/doctype/academic_term/test_records.json Parādīt failu

@@ -0,0 +1,27 @@
[
{
"doctype": "Academic Term",
"academic_year": "2014-2015",
"term_name": "_Test Academic Term"
},
{
"doctype": "Academic Term",
"academic_year": "2014-2015",
"term_name": "_Test Academic Term 1"
},
{
"doctype": "Academic Term",
"academic_year": "2014-2015",
"term_name": "_Test Academic Term 2"
},
{
"doctype": "Academic Term",
"academic_year": "2017-2018",
"term_name": "_Test AT1"
},
{
"doctype": "Academic Term",
"academic_year": "2017-2018",
"term_name": "_Test AT2"
}
]

+ 0
- 0
education/education/doctype/academic_year/__init__.py Parādīt failu


+ 2
- 0
education/education/doctype/academic_year/academic_year.js Parādīt failu

@@ -0,0 +1,2 @@
frappe.ui.form.on("Academic Year", {
});

+ 154
- 0
education/education/doctype/academic_year/academic_year.json Parādīt failu

@@ -0,0 +1,154 @@
{
"allow_copy": 0,
"allow_guest_to_view": 0,
"allow_import": 1,
"allow_rename": 0,
"autoname": "field:academic_year_name",
"beta": 0,
"creation": "2015-09-07 12:49:51.303026",
"custom": 0,
"docstatus": 0,
"doctype": "DocType",
"document_type": "",
"editable_grid": 0,
"fields": [
{
"allow_bulk_edit": 0,
"allow_on_submit": 0,
"bold": 0,
"collapsible": 0,
"columns": 0,
"fieldname": "academic_year_name",
"fieldtype": "Data",
"hidden": 0,
"ignore_user_permissions": 0,
"ignore_xss_filter": 0,
"in_filter": 0,
"in_global_search": 0,
"in_list_view": 0,
"in_standard_filter": 0,
"label": "Academic Year Name",
"length": 0,
"no_copy": 0,
"permlevel": 0,
"precision": "",
"print_hide": 0,
"print_hide_if_no_value": 0,
"read_only": 0,
"remember_last_selected_value": 0,
"report_hide": 0,
"reqd": 1,
"search_index": 0,
"set_only_once": 0,
"unique": 0
},
{
"allow_bulk_edit": 0,
"allow_on_submit": 0,
"bold": 0,
"collapsible": 0,
"columns": 0,
"fieldname": "year_start_date",
"fieldtype": "Date",
"hidden": 0,
"ignore_user_permissions": 0,
"ignore_xss_filter": 0,
"in_filter": 0,
"in_global_search": 0,
"in_list_view": 1,
"in_standard_filter": 0,
"label": "Year Start Date",
"length": 0,
"no_copy": 0,
"permlevel": 0,
"precision": "",
"print_hide": 0,
"print_hide_if_no_value": 0,
"read_only": 0,
"remember_last_selected_value": 0,
"report_hide": 0,
"reqd": 0,
"search_index": 0,
"set_only_once": 0,
"unique": 0
},
{
"allow_bulk_edit": 0,
"allow_on_submit": 0,
"bold": 0,
"collapsible": 0,
"columns": 0,
"fieldname": "year_end_date",
"fieldtype": "Date",
"hidden": 0,
"ignore_user_permissions": 0,
"ignore_xss_filter": 0,
"in_filter": 0,
"in_global_search": 0,
"in_list_view": 1,
"in_standard_filter": 0,
"label": "Year End Date",
"length": 0,
"no_copy": 0,
"permlevel": 0,
"precision": "",
"print_hide": 0,
"print_hide_if_no_value": 0,
"read_only": 0,
"remember_last_selected_value": 0,
"report_hide": 0,
"reqd": 0,
"search_index": 0,
"set_only_once": 0,
"unique": 0
}
],
"has_web_view": 0,
"hide_heading": 0,
"hide_toolbar": 0,
"idx": 0,
"image_view": 0,
"in_create": 0,
"is_submittable": 0,
"issingle": 0,
"istable": 0,
"max_attachments": 0,
"modified": "2017-11-10 19:06:08.123090",
"modified_by": "Administrator",
"module": "Education",
"name": "Academic Year",
"name_case": "",
"owner": "Administrator",
"permissions": [
{
"amend": 0,
"apply_user_permissions": 0,
"cancel": 0,
"create": 1,
"delete": 1,
"email": 1,
"export": 1,
"if_owner": 0,
"import": 0,
"permlevel": 0,
"print": 1,
"read": 1,
"report": 1,
"role": "Academics User",
"set_user_permissions": 0,
"share": 1,
"submit": 0,
"write": 1
}
],
"quick_entry": 1,
"read_only": 0,
"read_only_onload": 0,
"restrict_to_domain": "Education",
"show_name_in_global_search": 0,
"sort_field": "modified",
"sort_order": "DESC",
"title_field": "",
"track_changes": 0,
"track_seen": 0
}

+ 22
- 0
education/education/doctype/academic_year/academic_year.py Parādīt failu

@@ -0,0 +1,22 @@
# Copyright (c) 2015, InfluxERP
# For license information, please see license.txt


import frappe
from frappe import _
from frappe.model.document import Document


class AcademicYear(Document):
def validate(self):
# Check that start of academic year is earlier than end of academic year
if (
self.year_start_date
and self.year_end_date
and self.year_start_date > self.year_end_date
):
frappe.throw(
_(
"The Year End Date cannot be earlier than the Year Start Date. Please correct the dates and try again."
)
)

+ 19
- 0
education/education/doctype/academic_year/academic_year_dashboard.py Parādīt failu

@@ -0,0 +1,19 @@
from frappe import _


def get_data():
return {
"fieldname": "academic_year",
"transactions": [
{
"label": _("Student"),
"items": ["Student Admission", "Student Applicant", "Student Group", "Student Log"],
},
{"label": _("Fee"), "items": ["Fees", "Fee Schedule", "Fee Structure"]},
{
"label": _("Academic Term and Program"),
"items": ["Academic Term", "Program Enrollment"],
},
{"label": _("Assessment"), "items": ["Assessment Plan", "Assessment Result"]},
],
}

+ 10
- 0
education/education/doctype/academic_year/test_academic_year.py Parādīt failu

@@ -0,0 +1,10 @@
# Copyright (c) 2015, InfluxERP
# See license.txt

import unittest

# test_records = frappe.get_test_records('Academic Year')


class TestAcademicYear(unittest.TestCase):
pass

+ 18
- 0
education/education/doctype/academic_year/test_records.json Parādīt failu

@@ -0,0 +1,18 @@
[
{
"doctype": "Academic Year",
"academic_year_name": "2014-2015"
},
{
"doctype": "Academic Year",
"academic_year_name": "2015-2016"
},
{
"doctype": "Academic Year",
"academic_year_name": "2016-2017"
},
{
"doctype": "Academic Year",
"academic_year_name": "2017-2018"
}
]

+ 0
- 0
education/education/doctype/article/__init__.py Parādīt failu


+ 56
- 0
education/education/doctype/article/article.js Parādīt failu

@@ -0,0 +1,56 @@
// Copyright (c) 2018, InfluxERP
// For license information, please see license.txt

frappe.ui.form.on('Article', {
refresh: function(frm) {
if (!frm.doc.__islocal) {
frm.add_custom_button(__('Add to Topics'), function() {
frm.trigger('add_article_to_topics');
}, __('Action'));
}
},

add_article_to_topics: function(frm) {
get_topics_without_article(frm.doc.name).then(r => {
if (r.message.length) {
frappe.prompt([
{
fieldname: 'topics',
label: __('Topics'),
fieldtype: 'MultiSelectPills',
get_data: function() {
return r.message;
}
}
],
function(data) {
frappe.call({
method: 'education.education.doctype.topic.topic.add_content_to_topics',
args: {
'content_type': 'Article',
'content': frm.doc.name,
'topics': data.topics,
},
callback: function(r) {
if (!r.exc) {
frm.reload_doc();
}
},
freeze: true,
freeze_message: __('...Adding Article to Topics')
});
}, __('Add Article to Topics'), __('Add'));
} else {
frappe.msgprint(__('This article is already added to the existing topics'));
}
});
}
});

let get_topics_without_article = function(article) {
return frappe.call({
type: 'GET',
method: 'education.education.doctype.article.article.get_topics_without_article',
args: {'article': article}
});
};

+ 81
- 0
education/education/doctype/article/article.json Parādīt failu

@@ -0,0 +1,81 @@
{
"allow_import": 1,
"allow_rename": 1,
"autoname": "field:title",
"creation": "2018-10-17 05:45:38.471670",
"doctype": "DocType",
"editable_grid": 1,
"engine": "InnoDB",
"field_order": [
"title",
"author",
"content",
"publish_date"
],
"fields": [
{
"fieldname": "title",
"fieldtype": "Data",
"label": "Title",
"unique": 1
},
{
"fieldname": "author",
"fieldtype": "Data",
"label": "Author"
},
{
"fieldname": "content",
"fieldtype": "Text Editor",
"label": "Content"
},
{
"fieldname": "publish_date",
"fieldtype": "Date",
"label": "Publish Date"
}
],
"modified": "2019-06-12 12:36:58.740340",
"modified_by": "Administrator",
"module": "Education",
"name": "Article",
"owner": "Administrator",
"permissions": [
{
"create": 1,
"delete": 1,
"email": 1,
"export": 1,
"print": 1,
"read": 1,
"report": 1,
"role": "Academics User",
"share": 1,
"write": 1
},
{
"create": 1,
"delete": 1,
"email": 1,
"export": 1,
"print": 1,
"read": 1,
"report": 1,
"role": "Instructor",
"share": 1,
"write": 1
},
{
"email": 1,
"export": 1,
"print": 1,
"read": 1,
"report": 1,
"role": "LMS User",
"share": 1
}
],
"sort_field": "modified",
"sort_order": "DESC",
"track_changes": 1
}

+ 22
- 0
education/education/doctype/article/article.py Parādīt failu

@@ -0,0 +1,22 @@
# Copyright (c) 2018, InfluxERP
# For license information, please see license.txt


import frappe
from frappe.model.document import Document


class Article(Document):
def get_article(self):
pass


@frappe.whitelist()
def get_topics_without_article(article):
data = []
for entry in frappe.db.get_all("Topic"):
topic = frappe.get_doc("Topic", entry.name)
topic_contents = [tc.content for tc in topic.topic_content]
if not topic_contents or article not in topic_contents:
data.append(topic.name)
return data

+ 8
- 0
education/education/doctype/article/test_article.py Parādīt failu

@@ -0,0 +1,8 @@
# Copyright (c) 2018, InfluxERP
# See license.txt

import unittest


class TestArticle(unittest.TestCase):
pass

+ 0
- 0
education/education/doctype/assessment_criteria/__init__.py Parādīt failu


+ 8
- 0
education/education/doctype/assessment_criteria/assessment_criteria.js Parādīt failu

@@ -0,0 +1,8 @@
// Copyright (c) 2016, InfluxERP
// For license information, please see license.txt

frappe.ui.form.on('Assessment Criteria', {
refresh: function(frm) {

}
});

+ 125
- 0
education/education/doctype/assessment_criteria/assessment_criteria.json Parādīt failu

@@ -0,0 +1,125 @@
{
"allow_copy": 0,
"allow_guest_to_view": 0,
"allow_import": 1,
"allow_rename": 0,
"autoname": "field:assessment_criteria",
"beta": 0,
"creation": "2016-12-14 16:40:15.144115",
"custom": 0,
"docstatus": 0,
"doctype": "DocType",
"document_type": "",
"editable_grid": 1,
"engine": "InnoDB",
"fields": [
{
"allow_bulk_edit": 0,
"allow_on_submit": 0,
"bold": 0,
"collapsible": 0,
"columns": 0,
"fieldname": "assessment_criteria",
"fieldtype": "Data",
"hidden": 0,
"ignore_user_permissions": 0,
"ignore_xss_filter": 0,
"in_filter": 0,
"in_global_search": 0,
"in_list_view": 1,
"in_standard_filter": 0,
"label": "Assessment Criteria",
"length": 0,
"no_copy": 0,
"permlevel": 0,
"precision": "",
"print_hide": 0,
"print_hide_if_no_value": 0,
"read_only": 0,
"remember_last_selected_value": 0,
"report_hide": 0,
"reqd": 1,
"search_index": 0,
"set_only_once": 0,
"unique": 0
},
{
"allow_bulk_edit": 0,
"allow_on_submit": 0,
"bold": 1,
"collapsible": 0,
"columns": 0,
"fieldname": "assessment_criteria_group",
"fieldtype": "Link",
"hidden": 0,
"ignore_user_permissions": 0,
"ignore_xss_filter": 0,
"in_filter": 0,
"in_global_search": 0,
"in_list_view": 0,
"in_standard_filter": 0,
"label": "Assessment Criteria Group",
"length": 0,
"no_copy": 0,
"options": "Assessment Criteria Group",
"permlevel": 0,
"precision": "",
"print_hide": 0,
"print_hide_if_no_value": 0,
"read_only": 0,
"remember_last_selected_value": 0,
"report_hide": 0,
"reqd": 0,
"search_index": 0,
"set_only_once": 0,
"unique": 0
}
],
"has_web_view": 0,
"hide_heading": 0,
"hide_toolbar": 0,
"idx": 0,
"image_view": 0,
"in_create": 0,
"is_submittable": 0,
"issingle": 0,
"istable": 0,
"max_attachments": 0,
"modified": "2017-11-10 19:08:11.311304",
"modified_by": "Administrator",
"module": "Education",
"name": "Assessment Criteria",
"name_case": "",
"owner": "Administrator",
"permissions": [
{
"amend": 0,
"apply_user_permissions": 0,
"cancel": 0,
"create": 1,
"delete": 1,
"email": 1,
"export": 1,
"if_owner": 0,
"import": 0,
"permlevel": 0,
"print": 1,
"read": 1,
"report": 1,
"role": "Academics User",
"set_user_permissions": 0,
"share": 1,
"submit": 0,
"write": 1
}
],
"quick_entry": 1,
"read_only": 0,
"read_only_onload": 0,
"restrict_to_domain": "Education",
"show_name_in_global_search": 0,
"sort_field": "modified",
"sort_order": "DESC",
"track_changes": 0,
"track_seen": 0
}

+ 22
- 0
education/education/doctype/assessment_criteria/assessment_criteria.py Parādīt failu

@@ -0,0 +1,22 @@
# Copyright (c) 2015, InfluxERP
# For license information, please see license.txt


import frappe
from frappe import _
from frappe.model.document import Document

STD_CRITERIA = [
"total",
"total score",
"total grade",
"maximum score",
"score",
"grade",
]


class AssessmentCriteria(Document):
def validate(self):
if self.assessment_criteria.lower() in STD_CRITERIA:
frappe.throw(_("Can't create standard criteria. Please rename the criteria"))

+ 10
- 0
education/education/doctype/assessment_criteria/test_assessment_criteria.py Parādīt failu

@@ -0,0 +1,10 @@
# Copyright (c) 2015, InfluxERP
# See license.txt

import unittest

# test_records = frappe.get_test_records('Assessment Criteria')


class TestAssessmentCriteria(unittest.TestCase):
pass

+ 8
- 0
education/education/doctype/assessment_criteria/test_records.json Parādīt failu

@@ -0,0 +1,8 @@
[
{
"assessment_criteria": "_Test Assessment Criteria"
},
{
"assessment_criteria": "_Test Assessment Criteria 1"
}
]

+ 0
- 0
education/education/doctype/assessment_criteria_group/__init__.py Parādīt failu


+ 8
- 0
education/education/doctype/assessment_criteria_group/assessment_criteria_group.js Parādīt failu

@@ -0,0 +1,8 @@
// Copyright (c) 2016, InfluxERP
// For license information, please see license.txt

frappe.ui.form.on('Assessment Criteria Group', {
refresh: function(frm) {

}
});

+ 94
- 0
education/education/doctype/assessment_criteria_group/assessment_criteria_group.json Parādīt failu

@@ -0,0 +1,94 @@
{
"allow_copy": 0,
"allow_guest_to_view": 0,
"allow_import": 1,
"allow_rename": 1,
"autoname": "field:assessment_criteria_group",
"beta": 0,
"creation": "2017-01-27 15:17:38.855910",
"custom": 0,
"docstatus": 0,
"doctype": "DocType",
"document_type": "",
"editable_grid": 1,
"engine": "InnoDB",
"fields": [
{
"allow_bulk_edit": 0,
"allow_on_submit": 0,
"bold": 0,
"collapsible": 0,
"columns": 0,
"fieldname": "assessment_criteria_group",
"fieldtype": "Data",
"hidden": 0,
"ignore_user_permissions": 0,
"ignore_xss_filter": 0,
"in_filter": 0,
"in_global_search": 0,
"in_list_view": 1,
"in_standard_filter": 0,
"label": "Assessment Criteria Group",
"length": 0,
"no_copy": 0,
"permlevel": 0,
"precision": "",
"print_hide": 0,
"print_hide_if_no_value": 0,
"read_only": 0,
"remember_last_selected_value": 0,
"report_hide": 0,
"reqd": 1,
"search_index": 0,
"set_only_once": 0,
"unique": 0
}
],
"has_web_view": 0,
"hide_heading": 0,
"hide_toolbar": 0,
"idx": 0,
"image_view": 0,
"in_create": 0,
"is_submittable": 0,
"issingle": 0,
"istable": 0,
"max_attachments": 0,
"modified": "2017-11-10 19:11:45.334917",
"modified_by": "Administrator",
"module": "Education",
"name": "Assessment Criteria Group",
"name_case": "",
"owner": "Administrator",
"permissions": [
{
"amend": 0,
"apply_user_permissions": 0,
"cancel": 0,
"create": 1,
"delete": 1,
"email": 1,
"export": 1,
"if_owner": 0,
"import": 0,
"permlevel": 0,
"print": 1,
"read": 1,
"report": 1,
"role": "Academics User",
"set_user_permissions": 0,
"share": 1,
"submit": 0,
"write": 1
}
],
"quick_entry": 1,
"read_only": 0,
"read_only_onload": 0,
"restrict_to_domain": "Education",
"show_name_in_global_search": 0,
"sort_field": "modified",
"sort_order": "DESC",
"track_changes": 0,
"track_seen": 0
}

+ 9
- 0
education/education/doctype/assessment_criteria_group/assessment_criteria_group.py Parādīt failu

@@ -0,0 +1,9 @@
# Copyright (c) 2015, InfluxERP
# For license information, please see license.txt


from frappe.model.document import Document


class AssessmentCriteriaGroup(Document):
pass

+ 10
- 0
education/education/doctype/assessment_criteria_group/test_assessment_criteria_group.py Parādīt failu

@@ -0,0 +1,10 @@
# Copyright (c) 2015, InfluxERP
# See license.txt

import unittest

# test_records = frappe.get_test_records('Assessment Criteria Group')


class TestAssessmentCriteriaGroup(unittest.TestCase):
pass

+ 0
- 0
education/education/doctype/assessment_group/__init__.py Parādīt failu


+ 8
- 0
education/education/doctype/assessment_group/assessment_group.js Parādīt failu

@@ -0,0 +1,8 @@
// Copyright (c) 2016, InfluxERP
// For license information, please see license.txt

frappe.ui.form.on('Assessment Group', {
onload: function(frm) {
frm.list_route = "Tree/Assessment Group";
}
});

+ 90
- 0
education/education/doctype/assessment_group/assessment_group.json Parādīt failu

@@ -0,0 +1,90 @@
{
"actions": [],
"allow_import": 1,
"allow_rename": 1,
"autoname": "field:assessment_group_name",
"creation": "2016-08-04 04:42:48.319388",
"doctype": "DocType",
"editable_grid": 1,
"field_order": [
"assessment_group_name",
"is_group",
"section_break_2",
"parent_assessment_group",
"lft",
"rgt",
"old_parent"
],
"fields": [
{
"fieldname": "assessment_group_name",
"fieldtype": "Data",
"in_list_view": 1,
"label": "Assessment Group Name",
"reqd": 1,
"unique": 1
},
{
"default": "0",
"fieldname": "is_group",
"fieldtype": "Check",
"label": "Is Group"
},
{
"fieldname": "section_break_2",
"fieldtype": "Section Break",
"hidden": 1
},
{
"fieldname": "parent_assessment_group",
"fieldtype": "Link",
"in_list_view": 1,
"label": "Parent Assessment Group",
"options": "Assessment Group",
"reqd": 1
},
{
"fieldname": "lft",
"fieldtype": "Int",
"label": "lft"
},
{
"fieldname": "rgt",
"fieldtype": "Int",
"label": "rgt"
},
{
"fieldname": "old_parent",
"fieldtype": "Link",
"ignore_user_permissions": 1,
"label": "old_parent",
"options": "Assessment Group"
}
],
"is_tree": 1,
"links": [],
"modified": "2020-03-18 18:01:14.710416",
"modified_by": "Administrator",
"module": "Education",
"name": "Assessment Group",
"nsm_parent_field": "parent_assessment_group",
"owner": "Administrator",
"permissions": [
{
"create": 1,
"delete": 1,
"email": 1,
"export": 1,
"print": 1,
"read": 1,
"report": 1,
"role": "Academics User",
"share": 1,
"write": 1
}
],
"quick_entry": 1,
"restrict_to_domain": "Education",
"sort_field": "modified",
"sort_order": "DESC"
}

+ 9
- 0
education/education/doctype/assessment_group/assessment_group.py Parādīt failu

@@ -0,0 +1,9 @@
# Copyright (c) 2015, InfluxERP
# For license information, please see license.txt


from frappe.model.document import Document


class AssessmentGroup(Document):
pass

+ 13
- 0
education/education/doctype/assessment_group/assessment_group_dashboard.py Parādīt failu

@@ -0,0 +1,13 @@
# Copyright (c) 2020, InfluxERP
# License: GNU General Public License v3. See license.txt

from frappe import _


def get_data():
return {
"fieldname": "assessment_group",
"transactions": [
{"label": _("Assessment"), "items": ["Assessment Plan", "Assessment Result"]}
],
}

+ 3
- 0
education/education/doctype/assessment_group/assessment_group_tree.js Parādīt failu

@@ -0,0 +1,3 @@
frappe.treeview_settings["Assessment Group"] = {

}

+ 10
- 0
education/education/doctype/assessment_group/test_assessment_group.py Parādīt failu

@@ -0,0 +1,10 @@
# Copyright (c) 2015, InfluxERP
# See license.txt

import unittest

# test_records = frappe.get_test_records('Assessment Group')


class TestAssessmentGroup(unittest.TestCase):
pass

+ 0
- 0
education/education/doctype/assessment_plan/__init__.py Parādīt failu


+ 78
- 0
education/education/doctype/assessment_plan/assessment_plan.js Parādīt failu

@@ -0,0 +1,78 @@
// Copyright (c) 2016, InfluxERP
// For license information, please see license.txt


frappe.ui.form.on('Assessment Plan', {
onload: function(frm) {
frm.set_query('assessment_group', function(doc, cdt, cdn) {
return{
filters: {
'is_group': 0
}
};
});
frm.set_query('grading_scale', function(){
return {
filters: {
docstatus: 1
}
};
});
},

refresh: function(frm) {
if (frm.doc.docstatus == 1) {
frm.add_custom_button(__('Assessment Result Tool'), function() {
frappe.route_options = {
assessment_plan: frm.doc.name,
student_group: frm.doc.student_group
}
frappe.set_route('Form', 'Assessment Result Tool');
}, __('Tools'));
}

frm.set_query('course', function() {
return {
query: 'education.education.doctype.program_enrollment.program_enrollment.get_program_courses',
filters: {
'program': frm.doc.program
}
};
});

frm.set_query('academic_term', function() {
return {
filters: {
'academic_year': frm.doc.academic_year
}
};
});
},

course: function(frm) {
if (frm.doc.course && frm.doc.maximum_assessment_score) {
frappe.call({
method: 'education.education.api.get_assessment_criteria',
args: {
course: frm.doc.course
},
callback: function(r) {
if (r.message) {
frm.doc.assessment_criteria = [];
$.each(r.message, function(i, d) {
var row = frappe.model.add_child(frm.doc, 'Assessment Plan Criteria', 'assessment_criteria');
row.assessment_criteria = d.assessment_criteria;
row.maximum_score = d.weightage / 100 * frm.doc.maximum_assessment_score;
});
}
refresh_field('assessment_criteria');

}
});
}
},

maximum_assessment_score: function(frm) {
frm.trigger('course');
}
});

+ 227
- 0
education/education/doctype/assessment_plan/assessment_plan.json Parādīt failu

@@ -0,0 +1,227 @@
{
"actions": [],
"allow_import": 1,
"autoname": "EDU-ASP-.YYYY.-.#####",
"creation": "2015-11-12 16:34:34.658092",
"doctype": "DocType",
"document_type": "Setup",
"engine": "InnoDB",
"field_order": [
"student_group",
"assessment_name",
"assessment_group",
"grading_scale",
"column_break_2",
"program",
"course",
"academic_year",
"academic_term",
"section_break_5",
"schedule_date",
"room",
"examiner",
"examiner_name",
"column_break_4",
"from_time",
"to_time",
"supervisor",
"supervisor_name",
"section_break_20",
"maximum_assessment_score",
"assessment_criteria",
"amended_from"
],
"fields": [
{
"fieldname": "student_group",
"fieldtype": "Link",
"in_global_search": 1,
"in_list_view": 1,
"in_standard_filter": 1,
"label": "Student Group",
"options": "Student Group",
"reqd": 1
},
{
"fieldname": "assessment_name",
"fieldtype": "Data",
"in_global_search": 1,
"label": "Assessment Name"
},
{
"fieldname": "assessment_group",
"fieldtype": "Link",
"in_standard_filter": 1,
"label": "Assessment Group",
"options": "Assessment Group",
"reqd": 1
},
{
"fetch_from": "course.default_grading_scale",
"fetch_if_empty": 1,
"fieldname": "grading_scale",
"fieldtype": "Link",
"in_standard_filter": 1,
"label": "Grading Scale",
"options": "Grading Scale",
"reqd": 1
},
{
"fieldname": "column_break_2",
"fieldtype": "Column Break"
},
{
"fetch_from": "student_group.course",
"fetch_if_empty": 1,
"fieldname": "course",
"fieldtype": "Link",
"in_global_search": 1,
"in_standard_filter": 1,
"label": "Course",
"options": "Course",
"reqd": 1
},
{
"fetch_from": "student_group.program",
"fieldname": "program",
"fieldtype": "Link",
"in_global_search": 1,
"label": "Program",
"options": "Program"
},
{
"fetch_from": "student_group.academic_year",
"fieldname": "academic_year",
"fieldtype": "Link",
"label": "Academic Year",
"options": "Academic Year"
},
{
"fetch_from": "student_group.academic_term",
"fieldname": "academic_term",
"fieldtype": "Link",
"label": "Academic Term",
"options": "Academic Term"
},
{
"fieldname": "section_break_5",
"fieldtype": "Section Break",
"label": "Schedule"
},
{
"default": "Today",
"fieldname": "schedule_date",
"fieldtype": "Date",
"in_list_view": 1,
"label": "Schedule Date",
"no_copy": 1,
"reqd": 1
},
{
"fieldname": "room",
"fieldtype": "Link",
"label": "Room",
"options": "Room"
},
{
"fieldname": "examiner",
"fieldtype": "Link",
"label": "Examiner",
"options": "Instructor"
},
{
"fetch_from": "examiner.instructor_name",
"fieldname": "examiner_name",
"fieldtype": "Data",
"label": "Examiner Name",
"read_only": 1
},
{
"fieldname": "column_break_4",
"fieldtype": "Column Break"
},
{
"fieldname": "from_time",
"fieldtype": "Time",
"label": "From Time",
"no_copy": 1,
"reqd": 1
},
{
"fieldname": "to_time",
"fieldtype": "Time",
"label": "To Time",
"no_copy": 1,
"reqd": 1
},
{
"fieldname": "supervisor",
"fieldtype": "Link",
"label": "Supervisor",
"options": "Instructor"
},
{
"fetch_from": "supervisor.instructor_name",
"fieldname": "supervisor_name",
"fieldtype": "Data",
"in_global_search": 1,
"label": "Supervisor Name",
"read_only": 1
},
{
"fieldname": "section_break_20",
"fieldtype": "Section Break",
"label": "Evaluate"
},
{
"fieldname": "maximum_assessment_score",
"fieldtype": "Float",
"label": "Maximum Assessment Score",
"reqd": 1
},
{
"fieldname": "assessment_criteria",
"fieldtype": "Table",
"label": "Assessment Criteria",
"options": "Assessment Plan Criteria",
"reqd": 1
},
{
"fieldname": "amended_from",
"fieldtype": "Link",
"label": "Amended From",
"no_copy": 1,
"options": "Assessment Plan",
"print_hide": 1,
"read_only": 1
}
],
"is_submittable": 1,
"links": [],
"modified": "2020-10-23 15:55:35.076251",
"modified_by": "Administrator",
"module": "Education",
"name": "Assessment Plan",
"owner": "Administrator",
"permissions": [
{
"amend": 1,
"cancel": 1,
"create": 1,
"delete": 1,
"email": 1,
"export": 1,
"print": 1,
"read": 1,
"report": 1,
"role": "Academics User",
"share": 1,
"submit": 1,
"write": 1
}
],
"restrict_to_domain": "Education",
"sort_field": "modified",
"sort_order": "DESC",
"title_field": "assessment_name"
}

+ 60
- 0
education/education/doctype/assessment_plan/assessment_plan.py Parādīt failu

@@ -0,0 +1,60 @@
# Copyright (c) 2015, InfluxERP
# For license information, please see license.txt


import frappe
from frappe import _
from frappe.model.document import Document


class AssessmentPlan(Document):
def validate(self):
self.validate_overlap()
self.validate_max_score()
self.validate_assessment_criteria()

def validate_overlap(self):
"""Validates overlap for Student Group, Instructor, Room"""

from education.education.utils import validate_overlap_for

# Validate overlapping course schedules.
if self.student_group:
validate_overlap_for(self, "Course Schedule", "student_group")

validate_overlap_for(self, "Course Schedule", "instructor")
validate_overlap_for(self, "Course Schedule", "room")

# validate overlapping assessment schedules.
if self.student_group:
validate_overlap_for(self, "Assessment Plan", "student_group")

validate_overlap_for(self, "Assessment Plan", "room")
validate_overlap_for(self, "Assessment Plan", "supervisor", self.supervisor)

def validate_max_score(self):
max_score = 0
for d in self.assessment_criteria:
max_score += d.maximum_score
if self.maximum_assessment_score != max_score:
frappe.throw(
_("Sum of Scores of Assessment Criteria needs to be {0}.").format(
self.maximum_assessment_score
)
)

def validate_assessment_criteria(self):
assessment_criteria_list = frappe.db.sql_list(
""" select apc.assessment_criteria
from `tabAssessment Plan` ap , `tabAssessment Plan Criteria` apc
where ap.name = apc.parent and ap.course=%s and ap.student_group=%s and ap.assessment_group=%s
and ap.name != %s and ap.docstatus=1""",
(self.course, self.student_group, self.assessment_group, self.name),
)
for d in self.assessment_criteria:
if d.assessment_criteria in assessment_criteria_list:
frappe.throw(
_("You have already assessed for the assessment criteria {}.").format(
frappe.bold(d.assessment_criteria)
)
)

+ 12
- 0
education/education/doctype/assessment_plan/assessment_plan_dashboard.py Parādīt failu

@@ -0,0 +1,12 @@
# Copyright (c) 2020, InfluxERP
# License: GNU General Public License v3. See license.txt

from frappe import _


def get_data():
return {
"fieldname": "assessment_plan",
"transactions": [{"label": _("Assessment"), "items": ["Assessment Result"]}],
"reports": [{"label": _("Report"), "items": ["Assessment Plan Status"]}],
}

+ 10
- 0
education/education/doctype/assessment_plan/test_assessment_plan.py Parādīt failu

@@ -0,0 +1,10 @@
# Copyright (c) 2015, InfluxERP
# See license.txt

import unittest

# test_records = frappe.get_test_records('Assessment Plan')


class TestAssessmentPlan(unittest.TestCase):
pass

+ 0
- 0
education/education/doctype/assessment_plan_criteria/__init__.py Parādīt failu


+ 134
- 0
education/education/doctype/assessment_plan_criteria/assessment_plan_criteria.json Parādīt failu

@@ -0,0 +1,134 @@
{
"allow_copy": 0,
"allow_guest_to_view": 0,
"allow_import": 0,
"allow_rename": 0,
"autoname": "",
"beta": 0,
"creation": "2016-12-14 17:20:27.738226",
"custom": 0,
"docstatus": 0,
"doctype": "DocType",
"document_type": "",
"editable_grid": 1,
"engine": "InnoDB",
"fields": [
{
"allow_bulk_edit": 0,
"allow_on_submit": 0,
"bold": 0,
"collapsible": 0,
"columns": 0,
"fieldname": "assessment_criteria",
"fieldtype": "Link",
"hidden": 0,
"ignore_user_permissions": 0,
"ignore_xss_filter": 0,
"in_filter": 0,
"in_global_search": 0,
"in_list_view": 1,
"in_standard_filter": 0,
"label": "Assessment Criteria",
"length": 0,
"no_copy": 0,
"options": "Assessment Criteria",
"permlevel": 0,
"precision": "",
"print_hide": 0,
"print_hide_if_no_value": 0,
"read_only": 0,
"remember_last_selected_value": 0,
"report_hide": 0,
"reqd": 1,
"search_index": 0,
"set_only_once": 0,
"unique": 0
},
{
"allow_bulk_edit": 0,
"allow_on_submit": 0,
"bold": 0,
"collapsible": 0,
"columns": 0,
"fieldname": "column_break_2",
"fieldtype": "Column Break",
"hidden": 0,
"ignore_user_permissions": 0,
"ignore_xss_filter": 0,
"in_filter": 0,
"in_global_search": 0,
"in_list_view": 0,
"in_standard_filter": 0,
"label": "",
"length": 0,
"no_copy": 0,
"permlevel": 0,
"precision": "",
"print_hide": 0,
"print_hide_if_no_value": 0,
"read_only": 0,
"remember_last_selected_value": 0,
"report_hide": 0,
"reqd": 0,
"search_index": 0,
"set_only_once": 0,
"unique": 0
},
{
"allow_bulk_edit": 0,
"allow_on_submit": 0,
"bold": 0,
"collapsible": 0,
"columns": 0,
"fieldname": "maximum_score",
"fieldtype": "Float",
"hidden": 0,
"ignore_user_permissions": 0,
"ignore_xss_filter": 0,
"in_filter": 0,
"in_global_search": 0,
"in_list_view": 1,
"in_standard_filter": 0,
"label": "Maximum Score",
"length": 0,
"no_copy": 0,
"permlevel": 0,
"precision": "",
"print_hide": 0,
"print_hide_if_no_value": 0,
"read_only": 0,
"remember_last_selected_value": 0,
"report_hide": 0,
"reqd": 1,
"search_index": 0,
"set_only_once": 0,
"unique": 0
}
],
"has_web_view": 0,
"hide_heading": 0,
"hide_toolbar": 0,
"idx": 0,
"image_view": 0,
"in_create": 0,
"is_submittable": 0,
"issingle": 0,
"istable": 1,
"max_attachments": 0,
"modified": "2017-11-10 19:10:50.560006",
"modified_by": "Administrator",
"module": "Education",
"name": "Assessment Plan Criteria",
"name_case": "",
"owner": "Administrator",
"permissions": [],
"quick_entry": 1,
"read_only": 0,
"read_only_onload": 0,
"restrict_to_domain": "Education",
"show_name_in_global_search": 0,
"sort_field": "modified",
"sort_order": "DESC",
"track_changes": 0,
"track_seen": 0
}

+ 9
- 0
education/education/doctype/assessment_plan_criteria/assessment_plan_criteria.py Parādīt failu

@@ -0,0 +1,9 @@
# Copyright (c) 2015, InfluxERP
# For license information, please see license.txt


from frappe.model.document import Document


class AssessmentPlanCriteria(Document):
pass

+ 0
- 0
education/education/doctype/assessment_result/__init__.py Parādīt failu


+ 125
- 0
education/education/doctype/assessment_result/assessment_result.js Parādīt failu

@@ -0,0 +1,125 @@
// Copyright (c) 2016, InfluxERP
// For license information, please see license.txt

frappe.ui.form.on('Assessment Result', {
refresh: function(frm) {
if (!frm.doc.__islocal) {
frm.trigger('setup_chart');
}

frm.get_field('details').grid.cannot_add_rows = true;

frm.set_query('course', function() {
return {
query: 'education.education.doctype.program_enrollment.program_enrollment.get_program_courses',
filters: {
'program': frm.doc.program
}
};
});

frm.set_query('academic_term', function() {
return {
filters: {
'academic_year': frm.doc.academic_year
}
};
});
},

onload: function(frm) {
frm.set_query('assessment_plan', function() {
return {
filters: {
docstatus: 1
}
};
});
},

assessment_plan: function(frm) {
if (frm.doc.assessment_plan) {
frappe.call({
method: 'education.education.api.get_assessment_details',
args: {
assessment_plan: frm.doc.assessment_plan
},
callback: function(r) {
if (r.message) {
frappe.model.clear_table(frm.doc, 'details');
$.each(r.message, function(i, d) {
var row = frm.add_child('details');
row.assessment_criteria = d.assessment_criteria;
row.maximum_score = d.maximum_score;
});
frm.refresh_field('details');
}
}
});
}
},

setup_chart: function(frm) {
let labels = [];
let maximum_scores = [];
let scores = [];
$.each(frm.doc.details, function(_i, e) {
labels.push(e.assessment_criteria);
maximum_scores.push(e.maximum_score);
scores.push(e.score);
});

if (labels.length && maximum_scores.length && scores.length) {
frm.dashboard.chart_area.empty().removeClass('hidden');
new frappe.Chart('.form-graph', {
title: 'Assessment Results',
data: {
labels: labels,
datasets: [
{
name: 'Maximum Score',
chartType: 'bar',
values: maximum_scores,
},
{
name: 'Score Obtained',
chartType: 'bar',
values: scores,
}
]
},
colors: ['#4CA746', '#98D85B'],
type: 'bar'
});
}
}
});

frappe.ui.form.on('Assessment Result Detail', {
score: function(frm, cdt, cdn) {
var d = locals[cdt][cdn];

if (!d.maximum_score || !frm.doc.grading_scale) {
d.score = '';
frappe.throw(__('Please fill in all the details to generate Assessment Result.'));
}

if (d.score > d.maximum_score) {
frappe.throw(__('Score cannot be greater than Maximum Score'));
}
else {
frappe.call({
method: 'education.education.api.get_grade',
args: {
grading_scale: frm.doc.grading_scale,
percentage: ((d.score/d.maximum_score) * 100)
},
callback: function(r) {
if (r.message) {
frappe.model.set_value(cdt, cdn, 'grade', r.message);
}
}
});
}
}
});

+ 203
- 0
education/education/doctype/assessment_result/assessment_result.json Parādīt failu

@@ -0,0 +1,203 @@
{
"actions": [],
"allow_import": 1,
"autoname": "EDU-RES-.YYYY.-.#####",
"creation": "2015-11-13 17:18:06.468332",
"doctype": "DocType",
"editable_grid": 1,
"engine": "InnoDB",
"field_order": [
"assessment_plan",
"program",
"course",
"academic_year",
"academic_term",
"column_break_3",
"student",
"student_name",
"student_group",
"assessment_group",
"grading_scale",
"section_break_5",
"details",
"section_break_8",
"maximum_score",
"column_break_11",
"total_score",
"grade",
"section_break_13",
"comment",
"amended_from"
],
"fields": [
{
"fieldname": "assessment_plan",
"fieldtype": "Link",
"in_list_view": 1,
"label": "Assessment Plan",
"options": "Assessment Plan",
"reqd": 1
},
{
"fetch_from": "assessment_plan.program",
"fieldname": "program",
"fieldtype": "Link",
"label": "Program",
"options": "Program"
},
{
"fetch_from": "assessment_plan.course",
"fieldname": "course",
"fieldtype": "Link",
"label": "Course",
"options": "Course"
},
{
"fetch_from": "assessment_plan.academic_year",
"fieldname": "academic_year",
"fieldtype": "Link",
"label": "Academic Year",
"options": "Academic Year"
},
{
"fetch_from": "assessment_plan.academic_term",
"fieldname": "academic_term",
"fieldtype": "Link",
"label": "Academic Term",
"options": "Academic Term"
},
{
"fieldname": "column_break_3",
"fieldtype": "Column Break"
},
{
"fieldname": "student",
"fieldtype": "Link",
"in_global_search": 1,
"label": "Student",
"options": "Student",
"reqd": 1
},
{
"fetch_from": "student.title",
"fieldname": "student_name",
"fieldtype": "Data",
"in_global_search": 1,
"in_list_view": 1,
"label": "Student Name",
"read_only": 1
},
{
"fetch_from": "assessment_plan.student_group",
"fieldname": "student_group",
"fieldtype": "Link",
"label": "Student Group",
"options": "Student Group"
},
{
"fetch_from": "assessment_plan.assessment_group",
"fieldname": "assessment_group",
"fieldtype": "Link",
"label": "Assessment Group",
"options": "Assessment Group"
},
{
"fetch_from": "assessment_plan.grading_scale",
"fieldname": "grading_scale",
"fieldtype": "Link",
"label": "Grading Scale",
"options": "Grading Scale",
"read_only": 1
},
{
"fieldname": "section_break_5",
"fieldtype": "Section Break",
"label": "Result"
},
{
"fieldname": "details",
"fieldtype": "Table",
"label": "Details",
"options": "Assessment Result Detail",
"reqd": 1
},
{
"fieldname": "section_break_8",
"fieldtype": "Section Break"
},
{
"fetch_from": "assessment_plan.maximum_assessment_score",
"fieldname": "maximum_score",
"fieldtype": "Float",
"label": "Maximum Score",
"read_only": 1
},
{
"fetch_from": "assessment_plan.maximum_assessment_score",
"fieldname": "column_break_11",
"fieldtype": "Column Break"
},
{
"fieldname": "total_score",
"fieldtype": "Float",
"in_list_view": 1,
"label": "Total Score",
"read_only": 1
},
{
"fieldname": "grade",
"fieldtype": "Data",
"in_list_view": 1,
"label": "Grade",
"read_only": 1
},
{
"fieldname": "section_break_13",
"fieldtype": "Section Break",
"label": "Summary"
},
{
"fieldname": "comment",
"fieldtype": "Small Text",
"label": "Comment"
},
{
"fieldname": "amended_from",
"fieldtype": "Link",
"label": "Amended From",
"no_copy": 1,
"options": "Assessment Result",
"print_hide": 1,
"read_only": 1
}
],
"is_submittable": 1,
"links": [],
"modified": "2020-08-03 11:47:54.119486",
"modified_by": "Administrator",
"module": "Education",
"name": "Assessment Result",
"owner": "Administrator",
"permissions": [
{
"amend": 1,
"cancel": 1,
"create": 1,
"delete": 1,
"email": 1,
"export": 1,
"print": 1,
"read": 1,
"report": 1,
"role": "Academics User",
"share": 1,
"submit": 1,
"write": 1
}
],
"restrict_to_domain": "Education",
"show_name_in_global_search": 1,
"sort_field": "modified",
"sort_order": "DESC",
"title_field": "student_name"
}

+ 59
- 0
education/education/doctype/assessment_result/assessment_result.py Parādīt failu

@@ -0,0 +1,59 @@
# Copyright (c) 2015, InfluxERP
# For license information, please see license.txt


import frappe
from frappe import _
from frappe.model.document import Document
from frappe.utils import flt
from frappe.utils.csvutils import getlink

import education.education
from education.education.api import get_assessment_details, get_grade


class AssessmentResult(Document):
def validate(self):
education.education.validate_student_belongs_to_group(
self.student, self.student_group
)
self.validate_maximum_score()
self.validate_grade()
self.validate_duplicate()

def validate_maximum_score(self):
assessment_details = get_assessment_details(self.assessment_plan)
max_scores = {}
for d in assessment_details:
max_scores.update({d.assessment_criteria: d.maximum_score})

for d in self.details:
d.maximum_score = max_scores.get(d.assessment_criteria)
if d.score > d.maximum_score:
frappe.throw(_("Score cannot be greater than Maximum Score"))

def validate_grade(self):
self.total_score = 0.0
for d in self.details:
d.grade = get_grade(self.grading_scale, (flt(d.score) / d.maximum_score) * 100)
self.total_score += d.score
self.grade = get_grade(
self.grading_scale, (self.total_score / self.maximum_score) * 100
)

def validate_duplicate(self):
assessment_result = frappe.get_list(
"Assessment Result",
filters={
"name": ("not in", [self.name]),
"student": self.student,
"assessment_plan": self.assessment_plan,
"docstatus": ("!=", 2),
},
)
if assessment_result:
frappe.throw(
_("Assessment Result record {0} already exists.").format(
getlink("Assessment Result", assessment_result[0].name)
)
)

+ 15
- 0
education/education/doctype/assessment_result/assessment_result_dashboard.py Parādīt failu

@@ -0,0 +1,15 @@
# Copyright (c) 2020, InfluxERP
# License: GNU General Public License v3. See license.txt

from frappe import _


def get_data():
return {
"reports": [
{
"label": _("Reports"),
"items": ["Final Assessment Grades", "Course wise Assessment Report"],
}
]
}

+ 17
- 0
education/education/doctype/assessment_result/test_assessment_result.py Parādīt failu

@@ -0,0 +1,17 @@
# Copyright (c) 2015, InfluxERP
# See license.txt

import unittest

from education.education.api import get_grade

# test_records = frappe.get_test_records('Assessment Result')


class TestAssessmentResult(unittest.TestCase):
def test_grade(self):
grade = get_grade("_Test Grading Scale", 80)
self.assertEqual("A", grade)

grade = get_grade("_Test Grading Scale", 70)
self.assertEqual("B", grade)

+ 0
- 0
education/education/doctype/assessment_result_detail/__init__.py Parādīt failu


+ 66
- 0
education/education/doctype/assessment_result_detail/assessment_result_detail.json Parādīt failu

@@ -0,0 +1,66 @@
{
"actions": [],
"creation": "2016-12-14 17:44:35.583123",
"doctype": "DocType",
"editable_grid": 1,
"engine": "InnoDB",
"field_order": [
"assessment_criteria",
"maximum_score",
"column_break_2",
"score",
"grade"
],
"fields": [
{
"columns": 4,
"fieldname": "assessment_criteria",
"fieldtype": "Link",
"in_list_view": 1,
"label": "Assessment Criteria",
"options": "Assessment Criteria",
"read_only": 1,
"reqd": 1
},
{
"columns": 2,
"fieldname": "maximum_score",
"fieldtype": "Float",
"in_list_view": 1,
"label": "Maximum Score",
"read_only": 1
},
{
"fieldname": "column_break_2",
"fieldtype": "Column Break"
},
{
"columns": 2,
"fieldname": "score",
"fieldtype": "Float",
"in_list_view": 1,
"label": "Score",
"reqd": 1
},
{
"columns": 2,
"fieldname": "grade",
"fieldtype": "Data",
"in_list_view": 1,
"label": "Grade",
"read_only": 1
}
],
"istable": 1,
"links": [],
"modified": "2020-07-31 13:27:17.699022",
"modified_by": "Administrator",
"module": "Education",
"name": "Assessment Result Detail",
"owner": "Administrator",
"permissions": [],
"quick_entry": 1,
"restrict_to_domain": "Education",
"sort_field": "modified",
"sort_order": "DESC"
}

+ 9
- 0
education/education/doctype/assessment_result_detail/assessment_result_detail.py Parādīt failu

@@ -0,0 +1,9 @@
# Copyright (c) 2015, InfluxERP
# For license information, please see license.txt


from frappe.model.document import Document


class AssessmentResultDetail(Document):
pass

+ 0
- 0
education/education/doctype/assessment_result_tool/__init__.py Parādīt failu


+ 162
- 0
education/education/doctype/assessment_result_tool/assessment_result_tool.js Parādīt failu

@@ -0,0 +1,162 @@
// Copyright (c) 2016, InfluxERP
// For license information, please see license.txt


frappe.ui.form.on('Assessment Result Tool', {
setup: function(frm) {
frm.add_fetch("assessment_plan", "student_group", "student_group");
},

refresh: function(frm) {
if (frappe.route_options) {
frm.set_value("student_group", frappe.route_options.student_group);
frm.set_value("assessment_plan", frappe.route_options.assessment_plan);
frappe.route_options = null;
} else {
frm.trigger("assessment_plan");
}
frm.disable_save();
frm.page.clear_indicator();
},

assessment_plan: function(frm) {
frm.doc.show_submit = false;
if(frm.doc.assessment_plan) {
if (!frm.doc.student_group)
return
frappe.call({
method: "education.education.api.get_assessment_students",
args: {
"assessment_plan": frm.doc.assessment_plan,
"student_group": frm.doc.student_group
},
callback: function(r) {
if (r.message) {
frm.doc.students = r.message;
frm.events.render_table(frm);
for (let value of r.message) {
if (!value.docstatus) {
frm.doc.show_submit = true;
break;
}
}
frm.events.submit_result(frm);
}
}
});
}
},

render_table: function(frm) {
$(frm.fields_dict.result_html.wrapper).empty();
let assessment_plan = frm.doc.assessment_plan;
frappe.call({
method: "education.education.api.get_assessment_details",
args: {
assessment_plan: assessment_plan
},
callback: function(r) {
frm.events.get_marks(frm, r.message);
}
});
},

get_marks: function(frm, criteria_list) {
let max_total_score = 0;
criteria_list.forEach(function(c) {
max_total_score += c.maximum_score
});
var result_table = $(frappe.render_template('assessment_result_tool', {
frm: frm,
students: frm.doc.students,
criteria: criteria_list,
max_total_score: max_total_score
}));
result_table.appendTo(frm.fields_dict.result_html.wrapper);

result_table.on('change', 'input', function(e) {
let $input = $(e.target);
let student = $input.data().student;
let max_score = $input.data().maxScore;
let value = $input.val();
if(value < 0) {
$input.val(0);
} else if(value > max_score) {
$input.val(max_score);
}
let total_score = 0;
let student_scores = {};
student_scores["assessment_details"] = {}
result_table.find(`input[data-student=${student}].student-result-data`)
.each(function(el, input) {
let $input = $(input);
let criteria = $input.data().criteria;
let value = parseFloat($input.val());
if (!Number.isNaN(value)) {
student_scores["assessment_details"][criteria] = value;
}
total_score += value;
});
if(!Number.isNaN(total_score)) {
result_table.find(`span[data-student=${student}].total-score`).html(total_score);
}
if (Object.keys(student_scores["assessment_details"]).length === criteria_list.length) {
student_scores["student"] = student;
student_scores["total_score"] = total_score;
result_table.find(`[data-student=${student}].result-comment`)
.each(function(el, input){
student_scores["comment"] = $(input).val();
});
frappe.call({
method: "education.education.api.mark_assessment_result",
args: {
"assessment_plan": frm.doc.assessment_plan,
"scores": student_scores
},
callback: function(r) {
let assessment_result = r.message;
if (!frm.doc.show_submit) {
frm.doc.show_submit = true;
frm.events.submit_result;
}
for (var criteria of Object.keys(assessment_result.details)) {
result_table.find(`[data-criteria=${criteria}][data-student=${assessment_result
.student}].student-result-grade`).each(function(e1, input) {
$(input).html(assessment_result.details[criteria]);
});
}
result_table.find(`span[data-student=${assessment_result.student}].total-score-grade`).html(assessment_result.grade);
let link_span = result_table.find(`span[data-student=${assessment_result.student}].total-result-link`);
$(link_span).css("display", "block");
$(link_span).find("a").attr("href", "/app/assessment-result/"+assessment_result.name);
}
});
}
});
},

submit_result: function(frm) {
if (frm.doc.show_submit) {
frm.page.set_primary_action(__("Submit"), function() {
frappe.call({
method: "education.education.api.submit_assessment_results",
args: {
"assessment_plan": frm.doc.assessment_plan,
"student_group": frm.doc.student_group
},
callback: function(r) {
if (r.message) {
frappe.msgprint(__("{0} Result submittted", [r.message]));
} else {
frappe.msgprint(__("No Result to submit"));
}
frm.events.assessment_plan(frm);
}
});
});
}
else {
frm.page.clear_primary_action();
}
}
});

+ 235
- 0
education/education/doctype/assessment_result_tool/assessment_result_tool.json Parādīt failu

@@ -0,0 +1,235 @@
{
"allow_copy": 1,
"allow_guest_to_view": 0,
"allow_import": 0,
"allow_rename": 0,
"beta": 0,
"creation": "2017-01-05 12:27:48.951036",
"custom": 0,
"docstatus": 0,
"doctype": "DocType",
"document_type": "",
"editable_grid": 1,
"engine": "InnoDB",
"fields": [
{
"allow_bulk_edit": 0,
"allow_on_submit": 0,
"bold": 0,
"collapsible": 0,
"columns": 0,
"default": "",
"fieldname": "assessment_plan",
"fieldtype": "Link",
"hidden": 0,
"ignore_user_permissions": 0,
"ignore_xss_filter": 0,
"in_filter": 0,
"in_global_search": 0,
"in_list_view": 1,
"in_standard_filter": 0,
"label": "Assessment Plan",
"length": 0,
"no_copy": 0,
"options": "Assessment Plan",
"permlevel": 0,
"precision": "",
"print_hide": 0,
"print_hide_if_no_value": 0,
"read_only": 0,
"remember_last_selected_value": 0,
"report_hide": 0,
"reqd": 1,
"search_index": 0,
"set_only_once": 0,
"unique": 0
},
{
"allow_bulk_edit": 0,
"allow_on_submit": 0,
"bold": 0,
"collapsible": 0,
"columns": 0,
"fieldname": "column_break_2",
"fieldtype": "Column Break",
"hidden": 0,
"ignore_user_permissions": 0,
"ignore_xss_filter": 0,
"in_filter": 0,
"in_global_search": 0,
"in_list_view": 0,
"in_standard_filter": 0,
"length": 0,
"no_copy": 0,
"permlevel": 0,
"precision": "",
"print_hide": 0,
"print_hide_if_no_value": 0,
"read_only": 0,
"remember_last_selected_value": 0,
"report_hide": 0,
"reqd": 0,
"search_index": 0,
"set_only_once": 0,
"unique": 0
},
{
"allow_bulk_edit": 0,
"allow_on_submit": 0,
"bold": 0,
"collapsible": 0,
"columns": 0,
"fieldname": "student_group",
"fieldtype": "Link",
"hidden": 0,
"ignore_user_permissions": 0,
"ignore_xss_filter": 0,
"in_filter": 0,
"in_global_search": 0,
"in_list_view": 1,
"in_standard_filter": 0,
"label": "Student Group",
"length": 0,
"no_copy": 0,
"options": "Student Group",
"permlevel": 0,
"precision": "",
"print_hide": 0,
"print_hide_if_no_value": 0,
"read_only": 1,
"remember_last_selected_value": 0,
"report_hide": 0,
"reqd": 1,
"search_index": 0,
"set_only_once": 0,
"unique": 0
},
{
"allow_bulk_edit": 0,
"allow_on_submit": 0,
"bold": 0,
"collapsible": 0,
"columns": 0,
"depends_on": "assessment_plan",
"fieldname": "section_break_5",
"fieldtype": "Section Break",
"hidden": 0,
"ignore_user_permissions": 0,
"ignore_xss_filter": 0,
"in_filter": 0,
"in_global_search": 0,
"in_list_view": 0,
"in_standard_filter": 0,
"length": 0,
"no_copy": 0,
"permlevel": 0,
"precision": "",
"print_hide": 0,
"print_hide_if_no_value": 0,
"read_only": 0,
"remember_last_selected_value": 0,
"report_hide": 0,
"reqd": 0,
"search_index": 0,
"set_only_once": 0,
"unique": 0
},
{
"allow_bulk_edit": 0,
"allow_on_submit": 0,
"bold": 0,
"collapsible": 0,
"columns": 0,
"fieldname": "result_html",
"fieldtype": "HTML",
"hidden": 0,
"ignore_user_permissions": 0,
"ignore_xss_filter": 0,
"in_filter": 0,
"in_global_search": 0,
"in_list_view": 0,
"in_standard_filter": 0,
"label": "Result HTML",
"length": 0,
"no_copy": 0,
"permlevel": 0,
"precision": "",
"print_hide": 0,
"print_hide_if_no_value": 0,
"read_only": 0,
"remember_last_selected_value": 0,
"report_hide": 0,
"reqd": 0,
"search_index": 0,
"set_only_once": 0,
"unique": 0
}
],
"has_web_view": 0,
"hide_heading": 1,
"hide_toolbar": 1,
"idx": 0,
"image_view": 0,
"in_create": 0,
"is_submittable": 0,
"issingle": 1,
"istable": 0,
"max_attachments": 0,
"modified": "2017-12-27 09:36:37.155890",
"modified_by": "Administrator",
"module": "Education",
"name": "Assessment Result Tool",
"name_case": "",
"owner": "Administrator",
"permissions": [
{
"amend": 0,
"apply_user_permissions": 0,
"cancel": 0,
"create": 1,
"delete": 0,
"email": 0,
"export": 0,
"if_owner": 0,
"import": 0,
"permlevel": 0,
"print": 0,
"read": 1,
"report": 0,
"role": "Academics User",
"set_user_permissions": 0,
"share": 0,
"submit": 0,
"write": 1
},
{
"amend": 0,
"apply_user_permissions": 0,
"cancel": 0,
"create": 1,
"delete": 0,
"email": 0,
"export": 0,
"if_owner": 0,
"import": 0,
"permlevel": 0,
"print": 0,
"read": 1,
"report": 0,
"role": "Instructor",
"set_user_permissions": 0,
"share": 0,
"submit": 0,
"write": 1
}
],
"quick_entry": 1,
"read_only": 0,
"read_only_onload": 0,
"restrict_to_domain": "Education",
"show_name_in_global_search": 0,
"sort_field": "modified",
"sort_order": "DESC",
"track_changes": 0,
"track_seen": 0
}

+ 9
- 0
education/education/doctype/assessment_result_tool/assessment_result_tool.py Parādīt failu

@@ -0,0 +1,9 @@
# Copyright (c) 2015, InfluxERP
# For license information, please see license.txt


from frappe.model.document import Document


class AssessmentResultTool(Document):
pass

+ 8
- 0
education/education/doctype/assessment_result_tool/test_assessment_result_tool.py Parādīt failu

@@ -0,0 +1,8 @@
# Copyright (c) 2017, InfluxERP
# See license.txt

import unittest


class TestAssessmentResultTool(unittest.TestCase):
pass

+ 0
- 0
education/education/doctype/content_activity/__init__.py Parādīt failu


+ 141
- 0
education/education/doctype/content_activity/content_activity.json Parādīt failu

@@ -0,0 +1,141 @@
{
"allow_copy": 0,
"allow_events_in_timeline": 0,
"allow_guest_to_view": 0,
"allow_import": 0,
"allow_rename": 0,
"beta": 0,
"creation": "2018-10-16 03:55:53.283893",
"custom": 0,
"docstatus": 0,
"doctype": "DocType",
"document_type": "",
"editable_grid": 1,
"engine": "InnoDB",
"fields": [
{
"allow_bulk_edit": 0,
"allow_in_quick_entry": 0,
"allow_on_submit": 0,
"bold": 0,
"collapsible": 0,
"columns": 0,
"fieldname": "content",
"fieldtype": "Link",
"hidden": 0,
"ignore_user_permissions": 0,
"ignore_xss_filter": 0,
"in_filter": 0,
"in_global_search": 0,
"in_list_view": 0,
"in_standard_filter": 0,
"label": "Content",
"length": 0,
"no_copy": 0,
"options": "Content",
"permlevel": 0,
"precision": "",
"print_hide": 0,
"print_hide_if_no_value": 0,
"read_only": 0,
"remember_last_selected_value": 0,
"report_hide": 0,
"reqd": 0,
"search_index": 0,
"set_only_once": 0,
"translatable": 0,
"unique": 0
},
{
"allow_bulk_edit": 0,
"allow_in_quick_entry": 0,
"allow_on_submit": 0,
"bold": 0,
"collapsible": 0,
"columns": 0,
"fetch_from": "content.content_type",
"fieldname": "content_type",
"fieldtype": "Data",
"hidden": 0,
"ignore_user_permissions": 0,
"ignore_xss_filter": 0,
"in_filter": 0,
"in_global_search": 0,
"in_list_view": 0,
"in_standard_filter": 0,
"label": "Content Type",
"length": 0,
"no_copy": 0,
"permlevel": 0,
"precision": "",
"print_hide": 0,
"print_hide_if_no_value": 0,
"read_only": 0,
"remember_last_selected_value": 0,
"report_hide": 0,
"reqd": 0,
"search_index": 0,
"set_only_once": 0,
"translatable": 0,
"unique": 0
},
{
"allow_bulk_edit": 0,
"allow_in_quick_entry": 0,
"allow_on_submit": 0,
"bold": 0,
"collapsible": 0,
"columns": 0,
"fieldname": "last_activity",
"fieldtype": "Datetime",
"hidden": 0,
"ignore_user_permissions": 0,
"ignore_xss_filter": 0,
"in_filter": 0,
"in_global_search": 0,
"in_list_view": 0,
"in_standard_filter": 0,
"label": "Last Activity ",
"length": 0,
"no_copy": 0,
"permlevel": 0,
"precision": "",
"print_hide": 0,
"print_hide_if_no_value": 0,
"read_only": 0,
"remember_last_selected_value": 0,
"report_hide": 0,
"reqd": 0,
"search_index": 0,
"set_only_once": 0,
"translatable": 0,
"unique": 0
}
],
"has_web_view": 0,
"hide_heading": 0,
"hide_toolbar": 0,
"idx": 0,
"image_view": 0,
"in_create": 0,
"is_submittable": 0,
"issingle": 0,
"istable": 1,
"max_attachments": 0,
"modified": "2018-10-16 03:55:58.202436",
"modified_by": "Administrator",
"module": "Education",
"name": "Content Activity",
"name_case": "",
"owner": "Administrator",
"permissions": [],
"quick_entry": 1,
"read_only": 0,
"read_only_onload": 0,
"show_name_in_global_search": 0,
"sort_field": "modified",
"sort_order": "DESC",
"track_changes": 1,
"track_seen": 0,
"track_views": 0
}

+ 9
- 0
education/education/doctype/content_activity/content_activity.py Parādīt failu

@@ -0,0 +1,9 @@
# Copyright (c) 2018, InfluxERP
# For license information, please see license.txt


from frappe.model.document import Document


class ContentActivity(Document):
pass

+ 0
- 0
education/education/doctype/content_question/__init__.py Parādīt failu


+ 8
- 0
education/education/doctype/content_question/content_question.js Parādīt failu

@@ -0,0 +1,8 @@
// Copyright (c) 2018, InfluxERP
// For license information, please see license.txt

frappe.ui.form.on('Content Question', {
refresh: function(frm) {

}
});

+ 76
- 0
education/education/doctype/content_question/content_question.json Parādīt failu

@@ -0,0 +1,76 @@
{
"allow_copy": 0,
"allow_events_in_timeline": 0,
"allow_guest_to_view": 0,
"allow_import": 0,
"allow_rename": 0,
"beta": 0,
"creation": "2018-10-15 14:35:40.728454",
"custom": 0,
"docstatus": 0,
"doctype": "DocType",
"document_type": "",
"editable_grid": 1,
"engine": "InnoDB",
"fields": [
{
"allow_bulk_edit": 0,
"allow_in_quick_entry": 0,
"allow_on_submit": 0,
"bold": 0,
"collapsible": 0,
"columns": 0,
"fieldname": "question_link",
"fieldtype": "Link",
"hidden": 0,
"ignore_user_permissions": 0,
"ignore_xss_filter": 0,
"in_filter": 0,
"in_global_search": 0,
"in_list_view": 1,
"in_standard_filter": 0,
"label": "Question Link",
"length": 0,
"no_copy": 0,
"options": "Question",
"permlevel": 0,
"precision": "",
"print_hide": 0,
"print_hide_if_no_value": 0,
"read_only": 0,
"remember_last_selected_value": 0,
"report_hide": 0,
"reqd": 1,
"search_index": 0,
"set_only_once": 0,
"translatable": 0,
"unique": 0
}
],
"has_web_view": 0,
"hide_heading": 0,
"hide_toolbar": 0,
"idx": 0,
"image_view": 0,
"in_create": 0,
"is_submittable": 0,
"issingle": 0,
"istable": 1,
"max_attachments": 0,
"modified": "2018-10-15 14:41:31.729083",
"modified_by": "Administrator",
"module": "Education",
"name": "Content Question",
"name_case": "",
"owner": "Administrator",
"permissions": [],
"quick_entry": 1,
"read_only": 0,
"read_only_onload": 0,
"show_name_in_global_search": 0,
"sort_field": "modified",
"sort_order": "DESC",
"track_changes": 1,
"track_seen": 0,
"track_views": 0
}

+ 9
- 0
education/education/doctype/content_question/content_question.py Parādīt failu

@@ -0,0 +1,9 @@
# Copyright (c) 2018, InfluxERP
# For license information, please see license.txt


from frappe.model.document import Document


class ContentQuestion(Document):
pass

+ 8
- 0
education/education/doctype/content_question/test_content_question.py Parādīt failu

@@ -0,0 +1,8 @@
# Copyright (c) 2018, InfluxERP
# See license.txt

import unittest


class TestContentQuestion(unittest.TestCase):
pass

+ 0
- 0
education/education/doctype/course/__init__.py Parādīt failu


+ 79
- 0
education/education/doctype/course/course.js Parādīt failu

@@ -0,0 +1,79 @@
frappe.ui.form.on('Course', {
refresh: function(frm) {
if (!cur_frm.doc.__islocal) {
frm.add_custom_button(__('Add to Programs'), function() {
frm.trigger('add_course_to_programs')
}, __('Action'));
}

frm.set_query('default_grading_scale', function(){
return {
filters: {
docstatus: 1
}
}
});
},

add_course_to_programs: function(frm) {
get_programs_without_course(frm.doc.name).then(r => {
if (r.message.length) {
frappe.prompt([
{
fieldname: 'programs',
label: __('Programs'),
fieldtype: 'MultiSelectPills',
get_data: function() {
return r.message;
}
},
{
fieldtype: 'Check',
label: __('Is Mandatory'),
fieldname: 'mandatory',
}
],
function(data) {
frappe.call({
method: 'education.education.doctype.course.course.add_course_to_programs',
args: {
'course': frm.doc.name,
'programs': data.programs,
'mandatory': data.mandatory
},
callback: function(r) {
if (!r.exc) {
frm.reload_doc();
}
},
freeze: true,
freeze_message: __('...Adding Course to Programs')
})
}, __('Add Course to Programs'), __('Add'));
} else {
frappe.msgprint(__('This course is already added to the existing programs'));
}
});
}
});

frappe.ui.form.on('Course Topic', {
topics_add: function(frm){
frm.fields_dict['topics'].grid.get_field('topic').get_query = function(doc){
var topics_list = [];
if(!doc.__islocal) topics_list.push(doc.name);
$.each(doc.topics, function(idx, val){
if (val.topic) topics_list.push(val.topic);
});
return { filters: [['Topic', 'name', 'not in', topics_list]] };
};
}
});

let get_programs_without_course = function(course) {
return frappe.call({
type: 'GET',
method: 'education.education.doctype.course.course.get_programs_without_course',
args: {'course': course}
});
}

+ 137
- 0
education/education/doctype/course/course.json Parādīt failu

@@ -0,0 +1,137 @@
{
"allow_import": 1,
"allow_rename": 1,
"autoname": "field:course_name",
"creation": "2015-09-07 12:39:55.181893",
"doctype": "DocType",
"engine": "InnoDB",
"field_order": [
"course_name",
"department",
"section_break_6",
"topics",
"description",
"hero_image",
"assessment",
"default_grading_scale",
"assessment_criteria"
],
"fields": [
{
"fieldname": "course_name",
"fieldtype": "Data",
"in_list_view": 1,
"label": "Course Name",
"reqd": 1,
"unique": 1
},
{
"fieldname": "department",
"fieldtype": "Link",
"in_list_view": 1,
"in_standard_filter": 1,
"label": "Department",
"options": "Department"
},
{
"fieldname": "section_break_6",
"fieldtype": "Section Break",
"label": "Portal Settings"
},
{
"fieldname": "topics",
"fieldtype": "Table",
"label": "Topics",
"options": "Course Topic"
},
{
"fieldname": "hero_image",
"fieldtype": "Attach Image",
"hidden": 1,
"label": "Hero Image"
},
{
"fieldname": "assessment",
"fieldtype": "Section Break",
"label": "Assessment"
},
{
"fieldname": "default_grading_scale",
"fieldtype": "Link",
"label": "Default Grading Scale",
"options": "Grading Scale"
},
{
"fieldname": "assessment_criteria",
"fieldtype": "Table",
"label": "Assessment Criteria",
"options": "Course Assessment Criteria"
},
{
"fieldname": "description",
"fieldtype": "Small Text",
"label": "Description"
}
],
"image_field": "hero_image",
"modified": "2020-03-29 12:50:27.677589",
"modified_by": "Administrator",
"module": "Education",
"name": "Course",
"owner": "Administrator",
"permissions": [
{
"create": 1,
"delete": 1,
"email": 1,
"export": 1,
"print": 1,
"read": 1,
"report": 1,
"role": "Academics User",
"share": 1,
"write": 1
},
{
"create": 1,
"delete": 1,
"email": 1,
"export": 1,
"print": 1,
"read": 1,
"report": 1,
"role": "Instructor",
"share": 1,
"write": 1
},
{
"create": 1,
"delete": 1,
"email": 1,
"export": 1,
"print": 1,
"read": 1,
"report": 1,
"role": "Administrator",
"share": 1,
"write": 1
},
{
"create": 1,
"delete": 1,
"email": 1,
"export": 1,
"print": 1,
"read": 1,
"report": 1,
"role": "Education Manager",
"share": 1,
"write": 1
}
],
"restrict_to_domain": "Education",
"search_fields": "course_name",
"show_name_in_global_search": 1,
"sort_field": "modified",
"sort_order": "DESC"
}

+ 61
- 0
education/education/doctype/course/course.py Parādīt failu

@@ -0,0 +1,61 @@
# Copyright (c) 2015, InfluxERP
# For license information, please see license.txt


import json

import frappe
from frappe import _
from frappe.model.document import Document


class Course(Document):
def validate(self):
self.validate_assessment_criteria()

def validate_assessment_criteria(self):
if self.assessment_criteria:
total_weightage = 0
for criteria in self.assessment_criteria:
total_weightage += criteria.weightage or 0
if total_weightage != 100:
frappe.throw(_("Total Weightage of all Assessment Criteria must be 100%"))

def get_topics(self):
topic_data = []
for topic in self.topics:
topic_doc = frappe.get_doc("Topic", topic.topic)
if topic_doc.topic_content:
topic_data.append(topic_doc)
return topic_data


@frappe.whitelist()
def add_course_to_programs(course, programs, mandatory=False):
programs = json.loads(programs)
for entry in programs:
program = frappe.get_doc("Program", entry)
program.append(
"courses", {"course": course, "course_name": course, "mandatory": mandatory}
)
program.flags.ignore_mandatory = True
program.save()
frappe.db.commit()
frappe.msgprint(
_("Course {0} has been added to all the selected programs successfully.").format(
frappe.bold(course)
),
title=_("Programs updated"),
indicator="green",
)


@frappe.whitelist()
def get_programs_without_course(course):
data = []
for entry in frappe.db.get_all("Program"):
program = frappe.get_doc("Program", entry.name)
courses = [c.course for c in program.courses]
if not courses or course not in courses:
data.append(program.name)
return data

+ 18
- 0
education/education/doctype/course/course_dashboard.py Parādīt failu

@@ -0,0 +1,18 @@
# Copyright (c) 2020, InfluxERP
# License: GNU General Public License v3. See license.txt

from frappe import _


def get_data():
return {
"fieldname": "course",
"transactions": [
{
"label": _("Program and Course"),
"items": ["Program", "Course Enrollment", "Course Schedule"],
},
{"label": _("Student"), "items": ["Student Group"]},
{"label": _("Assessment"), "items": ["Assessment Plan", "Assessment Result"]},
],
}

+ 52
- 0
education/education/doctype/course/test_course.py Parādīt failu

@@ -0,0 +1,52 @@
# Copyright (c) 2015, InfluxERP
# See license.txt

import unittest

import frappe

from education.education.doctype.topic.test_topic import (
make_topic, make_topic_and_linked_content)

# test_records = frappe.get_test_records('Course')


class TestCourse(unittest.TestCase):
def setUp(self):
make_topic_and_linked_content(
"_Test Topic 1", [{"type": "Article", "name": "_Test Article 1"}]
)
make_topic_and_linked_content(
"_Test Topic 2", [{"type": "Article", "name": "_Test Article 2"}]
)
make_course_and_linked_topic("_Test Course 1", ["_Test Topic 1", "_Test Topic 2"])

def test_get_topics(self):
course = frappe.get_doc("Course", "_Test Course 1")
topics = course.get_topics()
self.assertEqual(topics[0].name, "_Test Topic 1")
self.assertEqual(topics[1].name, "_Test Topic 2")
frappe.db.rollback()


def make_course(name):
try:
course = frappe.get_doc("Course", name)
except frappe.DoesNotExistError:
course = frappe.get_doc(
{"doctype": "Course", "course_name": name, "course_code": name}
).insert()
return course.name


def make_course_and_linked_topic(course_name, topic_name_list):
try:
course = frappe.get_doc("Course", course_name)
except frappe.DoesNotExistError:
make_course(course_name)
course = frappe.get_doc("Course", course_name)
topic_list = [make_topic(topic_name) for topic_name in topic_name_list]
for topic in topic_list:
course.append("topics", {"topic": topic})
course.save()
return course

+ 14
- 0
education/education/doctype/course/test_records.json Parādīt failu

@@ -0,0 +1,14 @@
[
{
"course_name": "TC100",
"course_abbreviation": "TC"
},
{
"course_name": "TC101",
"course_abbreviation": "TC1"
},
{
"course_name": "TC102",
"course_abbreviation": "TC2"
}
]

+ 0
- 0
education/education/doctype/course_activity/__init__.py Parādīt failu


+ 8
- 0
education/education/doctype/course_activity/course_activity.js Parādīt failu

@@ -0,0 +1,8 @@
// Copyright (c) 2018, InfluxERP
// For license information, please see license.txt

frappe.ui.form.on('Course Activity', {
refresh: function(frm) {

}
});

+ 301
- 0
education/education/doctype/course_activity/course_activity.json Parādīt failu

@@ -0,0 +1,301 @@
{
"allow_copy": 0,
"allow_events_in_timeline": 0,
"allow_guest_to_view": 0,
"allow_import": 0,
"allow_rename": 0,
"autoname": "format:EDU-CA-{YYYY}-{#####}",
"beta": 1,
"creation": "2018-10-01 17:35:54.391413",
"custom": 0,
"docstatus": 0,
"doctype": "DocType",
"document_type": "",
"editable_grid": 1,
"engine": "InnoDB",
"fields": [
{
"allow_bulk_edit": 0,
"allow_in_quick_entry": 0,
"allow_on_submit": 0,
"bold": 0,
"collapsible": 0,
"columns": 0,
"fieldname": "enrollment",
"fieldtype": "Link",
"hidden": 0,
"ignore_user_permissions": 0,
"ignore_xss_filter": 0,
"in_filter": 0,
"in_global_search": 0,
"in_list_view": 0,
"in_standard_filter": 0,
"label": "Course Enrollment",
"length": 0,
"no_copy": 0,
"options": "Course Enrollment",
"permlevel": 0,
"precision": "",
"print_hide": 0,
"print_hide_if_no_value": 0,
"read_only": 0,
"remember_last_selected_value": 0,
"report_hide": 0,
"reqd": 1,
"search_index": 0,
"set_only_once": 1,
"translatable": 0,
"unique": 0
},
{
"allow_bulk_edit": 0,
"allow_in_quick_entry": 0,
"allow_on_submit": 0,
"bold": 0,
"collapsible": 0,
"columns": 0,
"fetch_from": "enrollment.course",
"fieldname": "course",
"fieldtype": "Data",
"hidden": 0,
"ignore_user_permissions": 0,
"ignore_xss_filter": 0,
"in_filter": 0,
"in_global_search": 0,
"in_list_view": 1,
"in_standard_filter": 1,
"label": "Course",
"length": 0,
"no_copy": 0,
"options": "",
"permlevel": 0,
"precision": "",
"print_hide": 0,
"print_hide_if_no_value": 0,
"read_only": 1,
"remember_last_selected_value": 0,
"report_hide": 0,
"reqd": 1,
"search_index": 0,
"set_only_once": 1,
"translatable": 0,
"unique": 0
},
{
"allow_bulk_edit": 0,
"allow_in_quick_entry": 0,
"allow_on_submit": 0,
"bold": 0,
"collapsible": 0,
"columns": 0,
"fetch_from": "enrollment.student",
"fieldname": "student",
"fieldtype": "Data",
"hidden": 0,
"ignore_user_permissions": 0,
"ignore_xss_filter": 0,
"in_filter": 0,
"in_global_search": 0,
"in_list_view": 1,
"in_standard_filter": 1,
"label": "Student",
"length": 0,
"no_copy": 0,
"options": "",
"permlevel": 0,
"precision": "",
"print_hide": 0,
"print_hide_if_no_value": 0,
"read_only": 1,
"remember_last_selected_value": 0,
"report_hide": 0,
"reqd": 1,
"search_index": 0,
"set_only_once": 1,
"translatable": 0,
"unique": 0
},
{
"allow_bulk_edit": 0,
"allow_in_quick_entry": 0,
"allow_on_submit": 0,
"bold": 0,
"collapsible": 0,
"columns": 0,
"fieldname": "content_type",
"fieldtype": "Select",
"hidden": 0,
"ignore_user_permissions": 0,
"ignore_xss_filter": 0,
"in_filter": 0,
"in_global_search": 0,
"in_list_view": 0,
"in_standard_filter": 0,
"label": "Content Type",
"length": 0,
"no_copy": 0,
"options": "\nArticle\nVideo",
"permlevel": 0,
"precision": "",
"print_hide": 0,
"print_hide_if_no_value": 0,
"read_only": 0,
"remember_last_selected_value": 0,
"report_hide": 0,
"reqd": 1,
"search_index": 0,
"set_only_once": 1,
"translatable": 0,
"unique": 0
},
{
"allow_bulk_edit": 0,
"allow_in_quick_entry": 0,
"allow_on_submit": 0,
"bold": 0,
"collapsible": 0,
"columns": 0,
"fieldname": "content",
"fieldtype": "Dynamic Link",
"hidden": 0,
"ignore_user_permissions": 0,
"ignore_xss_filter": 0,
"in_filter": 0,
"in_global_search": 0,
"in_list_view": 1,
"in_standard_filter": 0,
"label": "Content",
"length": 0,
"no_copy": 0,
"options": "content_type",
"permlevel": 0,
"precision": "",
"print_hide": 0,
"print_hide_if_no_value": 0,
"read_only": 0,
"remember_last_selected_value": 0,
"report_hide": 0,
"reqd": 1,
"search_index": 0,
"set_only_once": 1,
"translatable": 0,
"unique": 0
},
{
"allow_bulk_edit": 0,
"allow_in_quick_entry": 0,
"allow_on_submit": 0,
"bold": 0,
"collapsible": 0,
"columns": 0,
"fieldname": "activity_date",
"fieldtype": "Datetime",
"hidden": 0,
"ignore_user_permissions": 0,
"ignore_xss_filter": 0,
"in_filter": 0,
"in_global_search": 0,
"in_list_view": 0,
"in_standard_filter": 0,
"label": "Activity Date",
"length": 0,
"no_copy": 0,
"permlevel": 0,
"precision": "",
"print_hide": 0,
"print_hide_if_no_value": 0,
"read_only": 0,
"remember_last_selected_value": 0,
"report_hide": 0,
"reqd": 1,
"search_index": 0,
"set_only_once": 1,
"translatable": 0,
"unique": 0
}
],
"has_web_view": 0,
"hide_heading": 0,
"hide_toolbar": 0,
"idx": 0,
"image_view": 0,
"in_create": 0,
"is_submittable": 0,
"issingle": 0,
"istable": 0,
"max_attachments": 0,
"modified": "2018-12-06 11:53:08.006123",
"modified_by": "Administrator",
"module": "Education",
"name": "Course Activity",
"name_case": "",
"owner": "Administrator",
"permissions": [
{
"amend": 0,
"cancel": 0,
"create": 1,
"delete": 1,
"email": 1,
"export": 1,
"if_owner": 0,
"import": 0,
"permlevel": 0,
"print": 1,
"read": 1,
"report": 1,
"role": "Academics User",
"set_user_permissions": 0,
"share": 1,
"submit": 0,
"write": 1
},
{
"amend": 0,
"cancel": 0,
"create": 1,
"delete": 0,
"email": 1,
"export": 1,
"if_owner": 1,
"import": 0,
"permlevel": 0,
"print": 1,
"read": 1,
"report": 1,
"role": "LMS User",
"set_user_permissions": 0,
"share": 1,
"submit": 0,
"write": 0
},
{
"amend": 0,
"cancel": 0,
"create": 0,
"delete": 0,
"email": 1,
"export": 1,
"if_owner": 0,
"import": 0,
"permlevel": 0,
"print": 1,
"read": 1,
"report": 1,
"role": "Instructor",
"set_user_permissions": 0,
"share": 1,
"submit": 0,
"write": 0
}
],
"quick_entry": 1,
"read_only": 0,
"read_only_onload": 0,
"show_name_in_global_search": 0,
"sort_field": "modified",
"sort_order": "DESC",
"track_changes": 1,
"track_seen": 0,
"track_views": 0
}

+ 18
- 0
education/education/doctype/course_activity/course_activity.py Parādīt failu

@@ -0,0 +1,18 @@
# Copyright (c) 2018, InfluxERP
# For license information, please see license.txt


import frappe
from frappe import _
from frappe.model.document import Document


class CourseActivity(Document):
def validate(self):
self.check_if_enrolled()

def check_if_enrolled(self):
if frappe.db.exists("Course Enrollment", self.enrollment):
return True
else:
frappe.throw(_("Course Enrollment {0} does not exists").format(self.enrollment))

+ 30
- 0
education/education/doctype/course_activity/test_course_activity.py Parādīt failu

@@ -0,0 +1,30 @@
# Copyright (c) 2018, InfluxERP
# See license.txt

import unittest

import frappe


class TestCourseActivity(unittest.TestCase):
pass


def make_course_activity(enrollment, content_type, content):
activity = frappe.get_all(
"Course Activity",
filters={"enrollment": enrollment, "content_type": content_type, "content": content},
)
try:
activity = frappe.get_doc("Course Activity", activity[0]["name"])
except (IndexError, frappe.DoesNotExistError):
activity = frappe.get_doc(
{
"doctype": "Course Activity",
"enrollment": enrollment,
"content_type": content_type,
"content": content,
"activity_date": frappe.utils.datetime.datetime.now(),
}
).insert()
return activity

+ 0
- 0
education/education/doctype/course_assessment_criteria/__init__.py Parādīt failu


+ 134
- 0
education/education/doctype/course_assessment_criteria/course_assessment_criteria.json Parādīt failu

@@ -0,0 +1,134 @@
{
"allow_copy": 0,
"allow_guest_to_view": 0,
"allow_import": 0,
"allow_rename": 0,
"autoname": "",
"beta": 0,
"creation": "2016-12-14 16:46:46.786353",
"custom": 0,
"docstatus": 0,
"doctype": "DocType",
"document_type": "",
"editable_grid": 1,
"engine": "InnoDB",
"fields": [
{
"allow_bulk_edit": 0,
"allow_on_submit": 0,
"bold": 0,
"collapsible": 0,
"columns": 0,
"fieldname": "assessment_criteria",
"fieldtype": "Link",
"hidden": 0,
"ignore_user_permissions": 0,
"ignore_xss_filter": 0,
"in_filter": 0,
"in_global_search": 0,
"in_list_view": 1,
"in_standard_filter": 0,
"label": "Assessment Criteria",
"length": 0,
"no_copy": 0,
"options": "Assessment Criteria",
"permlevel": 0,
"precision": "",
"print_hide": 0,
"print_hide_if_no_value": 0,
"read_only": 0,
"remember_last_selected_value": 0,
"report_hide": 0,
"reqd": 1,
"search_index": 0,
"set_only_once": 0,
"unique": 0
},
{
"allow_bulk_edit": 0,
"allow_on_submit": 0,
"bold": 0,
"collapsible": 0,
"columns": 0,
"fieldname": "column_break_2",
"fieldtype": "Column Break",
"hidden": 0,
"ignore_user_permissions": 0,
"ignore_xss_filter": 0,
"in_filter": 0,
"in_global_search": 0,
"in_list_view": 0,
"in_standard_filter": 0,
"label": "",
"length": 0,
"no_copy": 0,
"permlevel": 0,
"precision": "",
"print_hide": 0,
"print_hide_if_no_value": 0,
"read_only": 0,
"remember_last_selected_value": 0,
"report_hide": 0,
"reqd": 0,
"search_index": 0,
"set_only_once": 0,
"unique": 0
},
{
"allow_bulk_edit": 0,
"allow_on_submit": 0,
"bold": 0,
"collapsible": 0,
"columns": 0,
"fieldname": "weightage",
"fieldtype": "Percent",
"hidden": 0,
"ignore_user_permissions": 0,
"ignore_xss_filter": 0,
"in_filter": 0,
"in_global_search": 0,
"in_list_view": 1,
"in_standard_filter": 0,
"label": "Weightage",
"length": 0,
"no_copy": 0,
"permlevel": 0,
"precision": "",
"print_hide": 0,
"print_hide_if_no_value": 0,
"read_only": 0,
"remember_last_selected_value": 0,
"report_hide": 0,
"reqd": 1,
"search_index": 0,
"set_only_once": 0,
"unique": 0
}
],
"has_web_view": 0,
"hide_heading": 0,
"hide_toolbar": 0,
"idx": 0,
"image_view": 0,
"in_create": 0,
"is_submittable": 0,
"issingle": 0,
"istable": 1,
"max_attachments": 0,
"modified": "2017-11-10 19:10:44.710837",
"modified_by": "Administrator",
"module": "Education",
"name": "Course Assessment Criteria",
"name_case": "",
"owner": "Administrator",
"permissions": [],
"quick_entry": 1,
"read_only": 0,
"read_only_onload": 0,
"restrict_to_domain": "Education",
"show_name_in_global_search": 0,
"sort_field": "modified",
"sort_order": "DESC",
"track_changes": 0,
"track_seen": 0
}

+ 9
- 0
education/education/doctype/course_assessment_criteria/course_assessment_criteria.py Parādīt failu

@@ -0,0 +1,9 @@
# Copyright (c) 2015, InfluxERP
# For license information, please see license.txt


from frappe.model.document import Document


class CourseAssessmentCriteria(Document):
pass

+ 0
- 0
education/education/doctype/course_content/__init__.py Parādīt failu


Daži faili netika attēloti, jo izmaiņu fails ir pārāk liels

Notiek ielāde…
Atcelt
Saglabāt