#include #include #include #include #include #include "ClearSilver.h" #include "sqlite3.h" #include "global.h" #include "custom.h" /* for date FORMAT strings */ #include "grade.h" /* for date FORMAT strings */ #include "manhat-lib/shared_util.h" #include "manhat-lib/shared_grade_book_menu.h" #include "manhat-lib/shared_file_util.h" #include "manhat-lib/shared_grade_book_util.h" #include "manhat-lib/shared_grade_book_db.h" #include "manhat-lib/shared_person_list.h" void read_parameters ( char *course, char *key, int *item_id) { char temp[MAX_KEY +1]; cs_get_required_parameter("crs", course, MAX_PATH); cs_get_required_parameter("id", key, MAX_KEY); cs_get_required_parameter("item_id", temp, MAX_KEY); *item_id = atoi(temp); } GRADE_LIST *get_input_grades(int number, int item_id) { #define MAX_TMP 40 char name[MAX_TMP]; char temp[MAX_TMP]; int i; GRADE_LIST *list =0; GRADE *ptr; char *comment; list = (GRADE_LIST*) malloc (sizeof(GRADE_LIST)); if(!list) cs_critical_error(ERR_MALLOC_FAILED, "grade_book_enter_grades"); list->head = 0; list->current = 0; for(i = 0; inext =0; ptr->item_id =item_id; strncpy(ptr->letter, "chg", MAX_GRADE_LEN +1); snprintf(name, MAX_TMP, "username_%d", i); cs_get_required_parameter(name, ptr->username, MAX_USERNAME); snprintf(name, MAX_TMP, "excuse_%d", i); cs_get_optional_parameter(name, temp, MAX_TMP-1); if(strlen(temp)) strncpy(ptr->excuse, "yes", MAX_BOOLEN_LEN +1); else strncpy(ptr->excuse, "no", MAX_BOOLEN_LEN +1); snprintf(name, MAX_TMP, "pending_%d", i); cs_get_optional_parameter(name, temp, MAX_TMP-1); if(strlen(temp)) strncpy(ptr->pending, "yes", MAX_BOOLEN_LEN +1); else strncpy(ptr->pending, "no", MAX_BOOLEN_LEN +1); if(!strcmp(ptr->pending, "no")) { if(strcmp(global_item_list->head->is_letter_grade, "no") == 0) { snprintf(name, MAX_TMP, "score_%d", i); cs_get_required_parameter(name, temp, MAX_POINT_LEN); ptr->score = atof(temp); ptr->letter_id = -1; } else { snprintf(name, MAX_TMP, "letter_%d", i); cs_get_required_parameter(name, temp, MAX_GRADE_LEN); ptr->letter_id = atoi(temp); ptr->score = -999999; } } else { ptr->letter_id = -1; ptr->score = -999999; } snprintf(name, MAX_TMP, "Query.comments_%d", i); comment = hdf_get_value(global_cgi->hdf, name, ""); if(strlen(comment)) ptr->comment = malloc_str(comment); else ptr->comment = malloc_str(" "); if(!list->head) list->head = ptr; else list->current->next = ptr; list->current = ptr; } return list; #undef MAX_TMP } int is_changed(GRADE *ptr) { int find = 0; if(!global_grade_list || !global_grade_list->head) return 1; for(global_grade_list->current = global_grade_list->head; global_grade_list->current; global_grade_list->current = global_grade_list->current->next) { if(!strcmp(ptr->username, global_grade_list->current->username)) { find = 1; if(ptr->score != global_grade_list->current->score || strcmp(ptr->excuse, global_grade_list->current->excuse) || strcmp(ptr->pending, global_grade_list->current->pending) || ptr->letter_id != global_grade_list->current->letter_id || strcmp(ptr->comment, global_grade_list->current->comment)) return 1; } } if(find == 0) return 1; return 0; } void update_input_list(GRADE_LIST *list, int *changes) { GRADE *ptr; int changed = 0; for(ptr = list->head; ptr; ptr = ptr->next) { changed = is_changed(ptr); if(!changed) strncpy(ptr->letter, "no", MAX_GRADE_LEN +1); else (*changes)++; } } void insert_grades_into_table(GRADE_LIST *list, CONFIG_STRUCT *conf) { GRADE *ptr; int ret =0; sqlite3 *db; char *stmt; time_t time_stamp = time(NULL); char path[MAX_PATH +1]; snprintf(path, MAX_PATH +1, "%s%s/%s", conf->course_path, GRADE_BOOK_DIR, GRADE_BOOK_DB); ret = sqlite3_open(path, &db); if(ret) cs_critical_error(ERR_GRADES_DB, "insert grades "); ret = sqlite3_exec(db, "Begin transaction insert_grades", 0, 0, 0); if(ret) { sqlite3_close(db); cs_critical_error(ERR_GRADES_DB, "begin insert grades function"); } for(ptr = list->head; ptr; ptr = ptr->next) { stmt = sqlite3_mprintf("insert into Grades values('%q', %d, %4.2f, '%q', '%q', '%q', %d, %d)", ptr->username, ptr->item_id, ptr->score, ptr->excuse, ptr->pending, ptr->comment ? ptr->comment:"", ptr->letter_id, time_stamp); if(stmt) { ret = sqlite3_exec(db, stmt, 0, 0, 0); if(ret) { sqlite3_exec(db, "rollback transaction insert_grades", 0, 0, 0); sqlite3_free(stmt); sqlite3_close(db); cs_critical_error(ERR_GRADES_DB, "insert grades failed"); } sqlite3_free(stmt); } } if(!strcmp(global_item_list->head->grade_entered,"no")) { stmt = sqlite3_mprintf("update Items set gradesEntered='yes' where itemId=%d", global_item_list->head->item_id); if(stmt) { ret = sqlite3_exec(db, stmt, 0, 0, 0); if(ret) { sqlite3_exec(db, "rollback transaction insert_grades", 0, 0, 0); sqlite3_free(stmt); sqlite3_close(db); cs_critical_error(ERR_GRADES_DB, "update items failed"); } sqlite3_free(stmt); } } sqlite3_exec(db, "commit transaction insert_grades", 0, 0, 0); sqlite3_exec(db, "end transaction insert_grades", 0, 0, 0); sqlite3_close(db); } void do_action(CONFIG_STRUCT *conf, int item_id, const char *course, const char *key, SESSION *user) { P_NODE *head; int number_students =0; GRADE_LIST *list = 0; int changes = 0; get_one_item(conf, item_id, GRADE_BOOK_DB); if(!global_item_list || !global_item_list->head) cs_critical_error(ERR_GRADES_DB, "There is no item in db"); number_students = hdf_get_int_value(global_cgi->hdf, "Query.number_students", 0); if(number_students >0) { list = get_input_grades(number_students, item_id); if(!strcmp(global_item_list->head->grade_entered, "yes")) { get_current_grade_list(conf, item_id, GRADE_BOOK_DB); /* shared_grade_book_db.c */ update_input_list(list, &changes); if(global_grade_list) free_grade_list(global_grade_list); } else changes = number_students; if(changes >0) insert_grades_into_table(list, conf); free_grade_list(list); printf("Location: %s?crs=%s&id=%s&item_id=%d&save=yes\n\n", "grade_book_enter_grades", course, key, item_id); } else { set_item_list_values(1, 0); /* shared_grade_book_util.c */ if(global_item_list->head && strcmp(global_item_list->head->is_letter_grade, "yes") ==0) { get_letter_grades(conf, item_id,GRADE_BOOK_DB); if(!global_letter_grades || !global_letter_grades->head) cs_critical_error(ERR_GRADES_DB, "grade_book_enter"); set_letter_grades_value(); if(global_letter_grades) free_letter_grade_list(global_letter_grades); } head = build_option_person_list (conf); /* shared_person_list.c */ set_person_list_values(head, user); /* shared_grade_book_util.c */ get_current_grade_list(conf, item_id, GRADE_BOOK_DB); /* shared_grade_book_db.c */ set_current_grade_list_values(); /* shared_grade_book_util.c */ cs_set_int_value("max_point_len", MAX_POINT_LEN); if(head) free_option_person_list(head); /* shared_person_list.c */ } if(global_item_list) free_item_list(global_item_list); /* shared_grade_book_util.c */ } int main () { char course[MAX_PATH +1]; char key[MAX_KEY +1]; int item_id; SESSION user; CONFIG_STRUCT conf; cs_cgi_init(); /* shared_cs_util.h */ read_parameters ( course, key, &item_id); read_configuration_file (course, &conf); validate_key (key, &user, &conf); if(user.group != FACULTY) cs_critical_error(ERR_REQUEST_DENIED, "grade_book"); do_action(&conf, item_id, course, key, &user); cs_cgi_display ("grade_book_enter_grades", 1); cs_cgi_destroy(); return 0; }