Merge pull request #1309 from pateljannat/issues-76

fix: misc batch issues
This commit is contained in:
Jannat Patel
2025-02-13 21:26:17 +05:30
committed by GitHub
13 changed files with 106 additions and 558 deletions

View File

@@ -78,7 +78,7 @@
<template #prefix>
<div v-if="column.key == 'member_name'">
<Avatar
class="flex items-center"
class="flex"
:image="row['member_image']"
:label="item"
size="sm"
@@ -240,6 +240,6 @@ const feedbackColumns = computed(() => {
<style>
.feedback-list > button > div {
align-items: start;
padding: 0.25rem 0;
padding: 0.15rem 0;
}
</style>

View File

@@ -78,7 +78,7 @@
:options="chartOptions"
:series="chartData"
type="bar"
height="200"
:height="chartData[0].data.length * 30 + 100"
/>
<div
class="flex items-center justify-center text-sm text-ink-gray-7 space-x-4"
@@ -357,7 +357,7 @@ const getChartData = () => {
})
Object.keys(student.assessments).forEach((assessment) => {
if (student.assessments[assessment].result === 'Passed') {
if (student.assessments[assessment].result === 'Pass') {
categories[assessment].value += 1
}
})

View File

@@ -67,13 +67,16 @@ const announcement = reactive({
})
const announcementResource = createResource({
url: 'lms.lms.api.make_announcement',
url: 'frappe.core.doctype.communication.email.make',
makeParams(values) {
return {
students: props.students,
recipients: props.students.join(', '),
cc: announcement.replyTo,
subject: announcement.subject,
content: announcement.announcement,
doctype: 'LMS Batch',
name: props.batch,
send_email: 1,
}
},
})

View File

@@ -32,25 +32,44 @@
{{ __('Assessment') }}
</span>
<span>
{{ __('Progress') }}
{{ __('Percentage/Status') }}
</span>
</div>
<div
<router-link
v-for="assessment in Object.keys(student.assessments)"
class="flex items-center text-ink-gray-7 font-medium"
:to="{
name:
student.assessments[assessment].type == 'LMS Assignment'
? 'AssignmentSubmission'
: '',
params:
student.assessments[assessment].type == 'LMS Assignment'
? {
assignmentID:
student.assessments[assessment].assessment,
submissionName:
student.assessments[assessment].submission,
}
: {},
}"
>
<span class="flex-1">
{{ assessment }}
</span>
<span v-if="isAssignment(student.assessments[assessment])">
<Badge :theme="getStatusTheme(student.assessments[assessment])">
{{ student.assessments[assessment] }}
<span v-if="isAssignment(student.assessments[assessment].status)">
<Badge
:theme="
getStatusTheme(student.assessments[assessment].status)
"
>
{{ student.assessments[assessment].status }}
</Badge>
</span>
<span v-else>
{{ student.assessments[assessment] }}
{{ student.assessments[assessment].status }}
</span>
</div>
</router-link>
</div>
<!-- Courses -->

View File

@@ -127,6 +127,11 @@ const batch = createResource({
batch: props.batchName,
},
auto: true,
onSuccess: (data) => {
if (!data) {
router.push({ name: 'Batches' })
}
},
})
const courses = createResource({

View File

@@ -951,62 +951,6 @@
"unique": 0,
"width": null
},
{
"allow_in_quick_entry": 0,
"allow_on_submit": 0,
"bold": 0,
"collapsible": 0,
"collapsible_depends_on": null,
"columns": 0,
"default": null,
"depends_on": null,
"description": null,
"docstatus": 0,
"doctype": "Custom Field",
"dt": "Web Form",
"fetch_from": null,
"fetch_if_empty": 0,
"fieldname": "payments_tab",
"fieldtype": "Tab Break",
"hidden": 0,
"hide_border": 0,
"hide_days": 0,
"hide_seconds": 0,
"ignore_user_permissions": 0,
"ignore_xss_filter": 0,
"in_global_search": 0,
"in_list_view": 0,
"in_preview": 0,
"in_standard_filter": 0,
"insert_after": "custom_css",
"is_system_generated": 1,
"is_virtual": 0,
"label": "Payments",
"length": 0,
"link_filters": null,
"mandatory_depends_on": null,
"modified": "2024-09-19 08:35:17.329032",
"module": null,
"name": "Web Form-payments_tab",
"no_copy": 0,
"non_negative": 0,
"options": null,
"permlevel": 0,
"precision": "",
"print_hide": 0,
"print_hide_if_no_value": 0,
"print_width": null,
"read_only": 0,
"read_only_depends_on": null,
"report_hide": 0,
"reqd": 0,
"search_index": 0,
"show_dashboard": 0,
"sort_options": 0,
"translatable": 0,
"unique": 0,
"width": null
},
{
"allow_in_quick_entry": 0,
"allow_on_submit": 0,
@@ -1119,230 +1063,6 @@
"unique": 0,
"width": null
},
{
"allow_in_quick_entry": 0,
"allow_on_submit": 0,
"bold": 0,
"collapsible": 0,
"collapsible_depends_on": null,
"columns": 0,
"default": null,
"depends_on": "accept_payment",
"description": null,
"docstatus": 0,
"doctype": "Custom Field",
"dt": "Web Form",
"fetch_from": null,
"fetch_if_empty": 0,
"fieldname": "payment_gateway",
"fieldtype": "Link",
"hidden": 0,
"hide_border": 0,
"hide_days": 0,
"hide_seconds": 0,
"ignore_user_permissions": 0,
"ignore_xss_filter": 0,
"in_global_search": 0,
"in_list_view": 0,
"in_preview": 0,
"in_standard_filter": 0,
"insert_after": "accept_payment",
"is_system_generated": 1,
"is_virtual": 0,
"label": "Payment Gateway",
"length": 0,
"link_filters": null,
"mandatory_depends_on": null,
"modified": "2024-09-19 08:35:17.408659",
"module": null,
"name": "Web Form-payment_gateway",
"no_copy": 0,
"non_negative": 0,
"options": "Payment Gateway",
"permlevel": 0,
"precision": "",
"print_hide": 0,
"print_hide_if_no_value": 0,
"print_width": null,
"read_only": 0,
"read_only_depends_on": null,
"report_hide": 0,
"reqd": 0,
"search_index": 0,
"show_dashboard": 0,
"sort_options": 0,
"translatable": 0,
"unique": 0,
"width": null
},
{
"allow_in_quick_entry": 0,
"allow_on_submit": 0,
"bold": 0,
"collapsible": 0,
"collapsible_depends_on": null,
"columns": 0,
"default": "Buy Now",
"depends_on": "accept_payment",
"description": null,
"docstatus": 0,
"doctype": "Custom Field",
"dt": "Web Form",
"fetch_from": null,
"fetch_if_empty": 0,
"fieldname": "payment_button_label",
"fieldtype": "Data",
"hidden": 0,
"hide_border": 0,
"hide_days": 0,
"hide_seconds": 0,
"ignore_user_permissions": 0,
"ignore_xss_filter": 0,
"in_global_search": 0,
"in_list_view": 0,
"in_preview": 0,
"in_standard_filter": 0,
"insert_after": "payment_gateway",
"is_system_generated": 1,
"is_virtual": 0,
"label": "Button Label",
"length": 0,
"link_filters": null,
"mandatory_depends_on": null,
"modified": "2024-09-19 08:35:17.439246",
"module": null,
"name": "Web Form-payment_button_label",
"no_copy": 0,
"non_negative": 0,
"options": null,
"permlevel": 0,
"precision": "",
"print_hide": 0,
"print_hide_if_no_value": 0,
"print_width": null,
"read_only": 0,
"read_only_depends_on": null,
"report_hide": 0,
"reqd": 0,
"search_index": 0,
"show_dashboard": 0,
"sort_options": 0,
"translatable": 0,
"unique": 0,
"width": null
},
{
"allow_in_quick_entry": 0,
"allow_on_submit": 0,
"bold": 0,
"collapsible": 0,
"collapsible_depends_on": null,
"columns": 0,
"default": null,
"depends_on": null,
"description": null,
"docstatus": 0,
"doctype": "Custom Field",
"dt": "Web Form",
"fetch_from": null,
"fetch_if_empty": 0,
"fieldname": "payments_cb",
"fieldtype": "Column Break",
"hidden": 0,
"hide_border": 0,
"hide_days": 0,
"hide_seconds": 0,
"ignore_user_permissions": 0,
"ignore_xss_filter": 0,
"in_global_search": 0,
"in_list_view": 0,
"in_preview": 0,
"in_standard_filter": 0,
"insert_after": "payment_button_help",
"is_system_generated": 1,
"is_virtual": 0,
"label": null,
"length": 0,
"link_filters": null,
"mandatory_depends_on": null,
"modified": "2024-09-19 08:35:17.491696",
"module": null,
"name": "Web Form-payments_cb",
"no_copy": 0,
"non_negative": 0,
"options": null,
"permlevel": 0,
"precision": "",
"print_hide": 0,
"print_hide_if_no_value": 0,
"print_width": null,
"read_only": 0,
"read_only_depends_on": null,
"report_hide": 0,
"reqd": 0,
"search_index": 0,
"show_dashboard": 0,
"sort_options": 0,
"translatable": 0,
"unique": 0,
"width": null
},
{
"allow_in_quick_entry": 0,
"allow_on_submit": 0,
"bold": 0,
"collapsible": 0,
"collapsible_depends_on": null,
"columns": 0,
"default": null,
"depends_on": "eval:doc.accept_payment && !doc.amount_based_on_field",
"description": null,
"docstatus": 0,
"doctype": "Custom Field",
"dt": "Web Form",
"fetch_from": null,
"fetch_if_empty": 0,
"fieldname": "amount",
"fieldtype": "Currency",
"hidden": 0,
"hide_border": 0,
"hide_days": 0,
"hide_seconds": 0,
"ignore_user_permissions": 0,
"ignore_xss_filter": 0,
"in_global_search": 0,
"in_list_view": 0,
"in_preview": 0,
"in_standard_filter": 0,
"insert_after": "amount_field",
"is_system_generated": 1,
"is_virtual": 0,
"label": "Amount",
"length": 0,
"link_filters": null,
"mandatory_depends_on": null,
"modified": "2024-09-19 08:35:17.569591",
"module": null,
"name": "Web Form-amount",
"no_copy": 0,
"non_negative": 0,
"options": null,
"permlevel": 0,
"precision": "",
"print_hide": 0,
"print_hide_if_no_value": 0,
"print_width": null,
"read_only": 0,
"read_only_depends_on": null,
"report_hide": 0,
"reqd": 0,
"search_index": 0,
"show_dashboard": 0,
"sort_options": 0,
"translatable": 0,
"unique": 0,
"width": null
},
{
"allow_in_quick_entry": 0,
"allow_on_submit": 0,
@@ -1399,174 +1119,6 @@
"unique": 0,
"width": null
},
{
"allow_in_quick_entry": 0,
"allow_on_submit": 0,
"bold": 0,
"collapsible": 0,
"collapsible_depends_on": null,
"columns": 0,
"default": null,
"depends_on": "accept_payment",
"description": null,
"docstatus": 0,
"doctype": "Custom Field",
"dt": "Web Form",
"fetch_from": null,
"fetch_if_empty": 0,
"fieldname": "payment_button_help",
"fieldtype": "Text",
"hidden": 0,
"hide_border": 0,
"hide_days": 0,
"hide_seconds": 0,
"ignore_user_permissions": 0,
"ignore_xss_filter": 0,
"in_global_search": 0,
"in_list_view": 0,
"in_preview": 0,
"in_standard_filter": 0,
"insert_after": "payment_button_label",
"is_system_generated": 1,
"is_virtual": 0,
"label": "Button Help",
"length": 0,
"link_filters": null,
"mandatory_depends_on": null,
"modified": "2024-09-19 08:35:17.466744",
"module": null,
"name": "Web Form-payment_button_help",
"no_copy": 0,
"non_negative": 0,
"options": null,
"permlevel": 0,
"precision": "",
"print_hide": 0,
"print_hide_if_no_value": 0,
"print_width": null,
"read_only": 0,
"read_only_depends_on": null,
"report_hide": 0,
"reqd": 0,
"search_index": 0,
"show_dashboard": 0,
"sort_options": 0,
"translatable": 0,
"unique": 0,
"width": null
},
{
"allow_in_quick_entry": 0,
"allow_on_submit": 0,
"bold": 0,
"collapsible": 0,
"collapsible_depends_on": null,
"columns": 0,
"default": "0",
"depends_on": "accept_payment",
"description": null,
"docstatus": 0,
"doctype": "Custom Field",
"dt": "Web Form",
"fetch_from": null,
"fetch_if_empty": 0,
"fieldname": "amount_based_on_field",
"fieldtype": "Check",
"hidden": 0,
"hide_border": 0,
"hide_days": 0,
"hide_seconds": 0,
"ignore_user_permissions": 0,
"ignore_xss_filter": 0,
"in_global_search": 0,
"in_list_view": 0,
"in_preview": 0,
"in_standard_filter": 0,
"insert_after": "payments_cb",
"is_system_generated": 1,
"is_virtual": 0,
"label": "Amount Based On Field",
"length": 0,
"link_filters": null,
"mandatory_depends_on": null,
"modified": "2024-09-19 08:35:17.517344",
"module": null,
"name": "Web Form-amount_based_on_field",
"no_copy": 0,
"non_negative": 0,
"options": null,
"permlevel": 0,
"precision": "",
"print_hide": 0,
"print_hide_if_no_value": 0,
"print_width": null,
"read_only": 0,
"read_only_depends_on": null,
"report_hide": 0,
"reqd": 0,
"search_index": 0,
"show_dashboard": 0,
"sort_options": 0,
"translatable": 0,
"unique": 0,
"width": null
},
{
"allow_in_quick_entry": 0,
"allow_on_submit": 0,
"bold": 0,
"collapsible": 0,
"collapsible_depends_on": null,
"columns": 0,
"default": null,
"depends_on": "eval:doc.accept_payment && doc.amount_based_on_field",
"description": null,
"docstatus": 0,
"doctype": "Custom Field",
"dt": "Web Form",
"fetch_from": null,
"fetch_if_empty": 0,
"fieldname": "amount_field",
"fieldtype": "Select",
"hidden": 0,
"hide_border": 0,
"hide_days": 0,
"hide_seconds": 0,
"ignore_user_permissions": 0,
"ignore_xss_filter": 0,
"in_global_search": 0,
"in_list_view": 0,
"in_preview": 0,
"in_standard_filter": 0,
"insert_after": "amount_based_on_field",
"is_system_generated": 1,
"is_virtual": 0,
"label": "Amount Field",
"length": 0,
"link_filters": null,
"mandatory_depends_on": null,
"modified": "2024-09-19 08:35:17.543136",
"module": null,
"name": "Web Form-amount_field",
"no_copy": 0,
"non_negative": 0,
"options": null,
"permlevel": 0,
"precision": "",
"print_hide": 0,
"print_hide_if_no_value": 0,
"print_width": null,
"read_only": 0,
"read_only_depends_on": null,
"report_hide": 0,
"reqd": 0,
"search_index": 0,
"show_dashboard": 0,
"sort_options": 0,
"translatable": 0,
"unique": 0,
"width": null
},
{
"allow_in_quick_entry": 0,
"allow_on_submit": 0,
@@ -1679,62 +1231,6 @@
"unique": 0,
"width": null
},
{
"allow_in_quick_entry": 0,
"allow_on_submit": 0,
"bold": 0,
"collapsible": 0,
"collapsible_depends_on": null,
"columns": 0,
"default": null,
"depends_on": "accept_payment",
"description": null,
"docstatus": 0,
"doctype": "Custom Field",
"dt": "Web Form",
"fetch_from": null,
"fetch_if_empty": 0,
"fieldname": "currency",
"fieldtype": "Link",
"hidden": 0,
"hide_border": 0,
"hide_days": 0,
"hide_seconds": 0,
"ignore_user_permissions": 0,
"ignore_xss_filter": 0,
"in_global_search": 0,
"in_list_view": 0,
"in_preview": 0,
"in_standard_filter": 0,
"insert_after": "amount",
"is_system_generated": 1,
"is_virtual": 0,
"label": "Currency",
"length": 0,
"link_filters": null,
"mandatory_depends_on": null,
"modified": "2024-09-19 08:35:17.595419",
"module": null,
"name": "Web Form-currency",
"no_copy": 0,
"non_negative": 0,
"options": "Currency",
"permlevel": 0,
"precision": "",
"print_hide": 0,
"print_hide_if_no_value": 0,
"print_width": null,
"read_only": 0,
"read_only_depends_on": null,
"report_hide": 0,
"reqd": 0,
"search_index": 0,
"show_dashboard": 0,
"sort_options": 0,
"translatable": 0,
"unique": 0,
"width": null
},
{
"allow_in_quick_entry": 0,
"allow_on_submit": 0,

View File

@@ -7,15 +7,10 @@ import zipfile
import os
import re
import shutil
import requests
import xml.etree.ElementTree as ET
from frappe.translate import get_all_translations
from frappe import _
from frappe.query_builder import DocType
from frappe.query_builder.functions import Count
from frappe.utils import (
time_diff,
now_datetime,
get_datetime,
cint,
flt,
@@ -24,10 +19,10 @@ from frappe.utils import (
format_date,
date_diff,
)
from typing import Optional
from lms.lms.utils import get_average_rating, get_lesson_count
from xml.dom.minidom import parseString
from lms.lms.doctype.course_lesson.course_lesson import save_progress
from frappe.core.doctype.communication.email import make
@frappe.whitelist()
@@ -845,7 +840,7 @@ def update_course_statistics():
@frappe.whitelist()
def get_announcements(batch):
return frappe.get_all(
communications = frappe.get_all(
"Communication",
filters={
"reference_doctype": "LMS Batch",
@@ -863,6 +858,13 @@ def get_announcements(batch):
order_by="communication_date desc",
)
for communication in communications:
communication.image = frappe.get_cached_value(
"User", communication.sender, "user_image"
)
return communications
@frappe.whitelist()
def delete_course(course):
@@ -1225,16 +1227,3 @@ def get_notifications(filters):
@frappe.whitelist(allow_guest=True)
def is_guest_allowed():
return frappe.get_cached_value("LMS Settings", None, "allow_guest_access")
@frappe.whitelist()
def make_announcement(students, cc, subject, content):
for student in students:
frappe.sendmail(
recipients=student,
cc=cc,
subject=subject,
message=content,
header=[subject, "green"],
retry=3,
)

View File

@@ -76,17 +76,19 @@ def send_confirmation_email(doc):
def send_mail(doc):
subject = _("Enrollment Confirmation for the Next Training Batch")
template = "batch_confirmation"
custom_template = frappe.db.get_single_value(
"LMS Settings", "batch_confirmation_template"
)
batch = frappe.db.get_value(
"LMS Batch",
doc.batch,
["name", "title", "start_date", "start_time", "medium"],
as_dict=1,
)
subject = _("Enrollment Confirmation for {0}").format(batch.title)
template = "batch_confirmation"
custom_template = frappe.db.get_single_value(
"LMS Settings", "batch_confirmation_template"
)
args = {
"title": batch.title,
"student_name": doc.member_name,
@@ -107,6 +109,6 @@ def send_mail(doc):
template=template if not custom_template else None,
content=content if custom_template else None,
args=args,
header=[subject, "green"],
header=[_(batch.title), "green"],
retry=3,
)

View File

@@ -1194,6 +1194,9 @@ def get_neighbour_lesson(course, chapter, lesson):
@frappe.whitelist(allow_guest=True)
def get_batch_details(batch):
if not frappe.db.get_value("LMS Batch", batch, "published") and has_student_role():
return
batch_details = frappe.db.get_value(
"LMS Batch",
batch,
@@ -1450,7 +1453,7 @@ def get_batch_students(batch):
)
detail.assessments[title] = assessment_info
if assessment_info.result == "Passed":
if assessment_info.result == "Pass":
assessments_completed += 1
detail.courses_completed = courses_completed
@@ -1493,20 +1496,26 @@ def has_submitted_assessment(assessment, assessment_type, member=None):
attempt = frappe.db.exists(doctype, filters)
if attempt:
attempt_details = frappe.db.get_value(doctype, filters, fields)
fields.append("name")
attempt_details = frappe.db.get_value(doctype, filters, fields, as_dict=1)
if assessment_type == "LMS Quiz":
result = "Failed"
passing_percentage = frappe.db.get_value(
"LMS Quiz", assessment, "passing_percentage"
)
if attempt_details >= passing_percentage:
result = "Passed"
if attempt_details.percentage >= passing_percentage:
result = "Pass"
else:
result = attempt_details
result = attempt_details.status
return frappe._dict(
{
"status": attempt_details,
"status": attempt_details.percentage
if assessment_type == "LMS Quiz"
else attempt_details.status,
"result": result,
"assessment": assessment,
"type": assessment_type,
"submission": attempt_details.name,
}
)
else:

View File

@@ -99,4 +99,5 @@ lms.patches.v2_0.update_quiz_submission_data
lms.patches.v2_0.convert_quiz_duration_to_minutes
lms.patches.v2_0.allow_guest_access #05-02-2025
lms.patches.v2_0.migrate_batch_student_data #10-02-2025
lms.patches.v2_0.delete_old_enrollment_doctypes
lms.patches.v2_0.delete_old_enrollment_doctypes
lms.patches.v2_0.delete_unused_custom_fields

View File

@@ -0,0 +1,24 @@
import frappe
def execute():
if "payments" not in frappe.get_installed_apps():
web_form_custom_fields = frappe.get_all(
"Custom Field", {"dt": "Web Form"}, ["name", "fieldname"]
)
unused_fields = [
"currency",
"amount_field",
"amount_based_on_field",
"payment_button_help",
"amount",
"payments_cb",
"payment_button_label",
"payment_gateway",
"payments_tab",
]
for field in web_form_custom_fields:
if field.fieldname in unused_fields:
frappe.delete_doc("Custom Field", field.name)

View File

@@ -6,12 +6,6 @@
{{ _("We are pleased to inform you that you have been enrolled in our upcoming batch. Congratulations!") }}
</p>
<br>
<p>
<b>
{{ title }}
</b>
</p>
<p>
<b>{{ _("Batch Start Date:") }}</b> {{ frappe.utils.format_date(start_date, "medium") }}
@@ -27,7 +21,7 @@
<br>
<p>
{{ _("Visit the following link to view your ") }}
<a href="/batches/{{ name }}">{{ _("Batch Details") }}</a>
<a href="/lms/batches/{{ name }}">{{ _("Batch Details") }}</a>
</p>
<p>
{{ _("If you have any questions or require assistance, feel free to contact us.") }}

View File

@@ -1,18 +1,24 @@
<div>
<p>{{ _('Hi') }} {{ billing_name }},</p>
<br>
<p>{{ _('We noticed that you started enrolling in the') }} {{ type }} {{ title }} {{ _('but didnt complete your payment') }}.</p>
<br>
<p>
{{ _("We have a limited number of seats, and they won't be available for long!")}}
</p>
<br>
<p>
{{ _("Dont miss this opportunity to enhance your skills. Click below to complete your enrollment") }}:
</p>
<br>
<p>
<a href="{{ link }}">👉 Complete Your Enrollment</a>
<a href="{{ link }}">👉 {{ _("Complete Your Enrollment") }}</a>
</p>
<br>
<p>
{{ _("If you have any questions or need assistance, feel free to reach out to our support team.") }}
</p>
<br>
<p>
{{ _("Looking forward to seeing you enrolled!") }}
</p>