CSC/ECE 517 Spring 2024 - E2420. Reimplement student quizzes controller: Difference between revisions

From Expertiza_Wiki
Jump to navigation Jump to search
(Added in the wrong page, so deleting the changes)
Tag: Blanking
No edit summary
Line 1: Line 1:
==Expertiza==
Expertiza is an open-source project built using Ruby on Rails. It provides a platform for instructors and students to manage, submit, and evaluate assignments and projects. Instructors can create, edit, and grade assignments, while students can collaborate in teams, submit their work, and review peers' submissions. Expertiza supports submission across various document types, including URLs and wiki pages.


==Issues with previous Functionality==
* <b>RESTful Consistency:</b> The controller includes a mix of RESTful and non-RESTful actions. For instance, calculate_score and assign_quiz_to_student are not standard REST actions. These should either be integrated into the standard CRUD operations or properly justified as separate actions in line with RESTful practices.
* <b>HTTP Status Codes:</b> While some actions correctly return HTTP status codes (like: unprocessable_entity for validation errors), it's essential to ensure consistency across all actions. For example, the calculate_score action should explicitly return a 200 OK status upon success for clarity, even though it's the default.
* <b>Error Handling:</b> Some actions like destroy handle exceptions (ActiveRecord::RecordNotFound), but this consistent error handling approach is not applied across all actions where it might be relevant (e.g., show, update).
* <b>Parameter Handling:</b> The method questionnaire_params is well-structured for strong parameter handling, but there's inconsistency in how parameters are managed across actions. For example, response_map_params is defined but not used. Ensuring consistency and security in parameter handling is crucial.
* <b>Conditional Logic for Rendering:</b> There's a mix of rendering JSON directly in the actions and conditional logic for handling different outcomes (e.g., in assign_quiz_to_student). This could be streamlined for readability and maintainability.
==Design Goals==
This project builds on E2376, and the main goal is to get the endpoints of StudentQuizzesController running in reimplementation-backend repository. Detailed goals of the project are as follows:
* Preserve and enhance the functionality of the existing codebase, ensuring all features operate correctly and any identified issues are resolved.
* Eliminate redundant code by leveraging existing functionalities within the Expertiza system, adhering to the DRY (Don't Repeat Yourself) principle.
* Maintain the integrity of existing test cases and expand the test suite to include comprehensive tests for new and modified functionalities, ensuring thorough coverage and reliability. 
* Transition non-RESTful actions to conform to RESTful design principles, improving API intuitiveness and standardization.
* Improve error handling and response consistency across all endpoints, ensuring clear and informative feedback is provided for both successful operations and error conditions.
* Document all aspects of the implementation clearly, including inline code comments and external documentation, to facilitate ease of understanding and future development efforts.
* Implement automated testing within a continuous integration pipeline to run the full test suite on every commit, ensuring immediate feedback on the impact of changes and maintaining code quality.
==Reimplemented Methods==
Each section below covers methods of the student_quiizes_controller.rb model, how they were reimplemented, and why it was done that way.
==“calculate_score” method==
The reimplementation of the calculate_score method in the controller maintains its original functionality, focusing on retrieving and returning a score based on a given ResponseMap ID, or providing an error message if the ResponseMap is not found. The notable changes in the new version include the introduction of render_success and render_error helper methods, which serve to encapsulate the rendering of JSON responses, thereby enhancing code readability and maintainability. These modifications do not alter the method's core logic but provide a clearer, more consistent approach to handling successful outcomes and errors, ensuring a standardized response format across the controller. This approach reflects a modern Ruby coding practice, focusing on cleaner code without compromising the method's purpose or efficiency.
==“create_questionnaire” method==
Significant refinements were implemented to enhance the code's organization, readability, and error handling. Initially, the old method encapsulated the creation of a questionnaire, its questions, and associated answers within a single transaction block, directly interacting with the database models and handling exceptions in a generic manner. This approach, while functional, resulted in a more verbose method with nested iterations and direct creation calls within the transaction block.
The new create method introduces a more structured approach by segmenting the questionnaire creation and the addition of questions and answers into distinct operations. This separation is achieved through the create_questionnaire and create_questions_and_answers helper functions, which not only streamline the code but also improve clarity by breaking down the process into more manageable, focused steps. The use of these helper functions within the transaction ensures that the entire operation remains atomic, adhering to the principle that all parts of the questionnaire creation should either complete successfully or fail together, thus maintaining data integrity.
Furthermore, the new method employs a more sophisticated error handling strategy, explicitly rescuing StandardError and utilizing a render_error helper method to provide a consistent response format across different actions in the controller. This approach not only standardizes error responses but also enhances the method's robustness by clearly defining the scope of errors it can handle.
The shift to using helper methods like render_success and render_error for rendering responses aligns with modern Ruby practices, focusing on code modularity and maintainability. By encapsulating the success and error rendering logic, the new method offers a cleaner, more consistent interface for handling the various outcomes of the create operation, facilitating easier future modifications and improving the overall code quality.
==“assign_quiz_to_student” method==
In the reimplementation of the assign_quiz_to_student method, several changes were made.Firstly, the new version introduces helper methods find_resource_by_id for fetching the participant and questionnaire, and quiz_already_assigned? to check if the quiz has already been assigned to the student. These abstractions not only make the method more readable but also encapsulate specific functionalities, making the code more reusable and maintainable.
The condition checking for an existing assignment is now encapsulated within the quiz_already_assigned? method, simplifying the main method's logic flow and focusing it on the assignment process rather than validation checks.Another notable change is the introduction of build_response_map, a method presumably responsible for constructing a new ResponseMap instance. This further modularizes the code, separating the concerns of validation and object creation.
Error handling has been standardized using render_error and render_success helper methods, consistent with modern practices of handling HTTP responses. This not only makes the code cleaner but also ensures that the method's responses are consistent with other parts of the application.The use of return unless participant && questionnaire early in the method is a Ruby idiom that helps to avoid nested conditional statements, thereby enhancing the readability and flow of the method.
==“submit_answers” method==
In the reimplementation of the submit_answers method, several refinements were made to enhance code modularity, readability, and adherence to the DRY (Don't Repeat Yourself) principle, which the old version somewhat lacked, particularly in handling responses and scoring logic.The new method employs helper methods like find_response_map_for_current_user to fetch the relevant ResponseMap for the current user and process_answers to handle the logic of processing submitted answers and calculating the total score. This approach not only makes the code cleaner and more readable by breaking down the process into smaller, more manageable chunks but also improves maintainability by isolating specific functionalities.
In the original version, the logic for finding the ResponseMap, processing each answer, and calculating the total score was all embedded within the main submit_answers method, making it more cumbersome and less readable. This approach also violated the DRY principle, as similar patterns of fetching and processing could potentially be used in other parts of the application but would need to be rewritten.
The restructured method enhances error handling by utilizing render_error for consistent error messaging, similar to other methods in the controller, thereby standardizing response formats across different actions. This is a shift from the old method, where JSON error responses were constructed inline, leading to potential inconsistencies in error handling across the application.
By abstracting repetitive logic into helper methods, the new version adheres more closely to the DRY principle, reducing redundancy and the likelihood of errors during future modifications. The encapsulation of specific tasks into separate methods not only clarifies the main method's purpose—submitting answers and calculating scores—but also allows for easier testing and debugging of individual components.
Overall, the changes made in the new version of the submit_answers method reflect a thoughtful refactoring effort aimed at improving code quality, maintainability, and adherence to best practices in Ruby on Rails development

Revision as of 16:04, 24 March 2024

Expertiza

Expertiza is an open-source project built using Ruby on Rails. It provides a platform for instructors and students to manage, submit, and evaluate assignments and projects. Instructors can create, edit, and grade assignments, while students can collaborate in teams, submit their work, and review peers' submissions. Expertiza supports submission across various document types, including URLs and wiki pages.

Issues with previous Functionality

  • RESTful Consistency: The controller includes a mix of RESTful and non-RESTful actions. For instance, calculate_score and assign_quiz_to_student are not standard REST actions. These should either be integrated into the standard CRUD operations or properly justified as separate actions in line with RESTful practices.
  • HTTP Status Codes: While some actions correctly return HTTP status codes (like: unprocessable_entity for validation errors), it's essential to ensure consistency across all actions. For example, the calculate_score action should explicitly return a 200 OK status upon success for clarity, even though it's the default.
  • Error Handling: Some actions like destroy handle exceptions (ActiveRecord::RecordNotFound), but this consistent error handling approach is not applied across all actions where it might be relevant (e.g., show, update).
  • Parameter Handling: The method questionnaire_params is well-structured for strong parameter handling, but there's inconsistency in how parameters are managed across actions. For example, response_map_params is defined but not used. Ensuring consistency and security in parameter handling is crucial.
  • Conditional Logic for Rendering: There's a mix of rendering JSON directly in the actions and conditional logic for handling different outcomes (e.g., in assign_quiz_to_student). This could be streamlined for readability and maintainability.

Design Goals

This project builds on E2376, and the main goal is to get the endpoints of StudentQuizzesController running in reimplementation-backend repository. Detailed goals of the project are as follows:

  • Preserve and enhance the functionality of the existing codebase, ensuring all features operate correctly and any identified issues are resolved.
  • Eliminate redundant code by leveraging existing functionalities within the Expertiza system, adhering to the DRY (Don't Repeat Yourself) principle.
  • Maintain the integrity of existing test cases and expand the test suite to include comprehensive tests for new and modified functionalities, ensuring thorough coverage and reliability.
  • Transition non-RESTful actions to conform to RESTful design principles, improving API intuitiveness and standardization.
  • Improve error handling and response consistency across all endpoints, ensuring clear and informative feedback is provided for both successful operations and error conditions.
  • Document all aspects of the implementation clearly, including inline code comments and external documentation, to facilitate ease of understanding and future development efforts.
  • Implement automated testing within a continuous integration pipeline to run the full test suite on every commit, ensuring immediate feedback on the impact of changes and maintaining code quality.

Reimplemented Methods

Each section below covers methods of the student_quiizes_controller.rb model, how they were reimplemented, and why it was done that way.

“calculate_score” method

The reimplementation of the calculate_score method in the controller maintains its original functionality, focusing on retrieving and returning a score based on a given ResponseMap ID, or providing an error message if the ResponseMap is not found. The notable changes in the new version include the introduction of render_success and render_error helper methods, which serve to encapsulate the rendering of JSON responses, thereby enhancing code readability and maintainability. These modifications do not alter the method's core logic but provide a clearer, more consistent approach to handling successful outcomes and errors, ensuring a standardized response format across the controller. This approach reflects a modern Ruby coding practice, focusing on cleaner code without compromising the method's purpose or efficiency.

“create_questionnaire” method

Significant refinements were implemented to enhance the code's organization, readability, and error handling. Initially, the old method encapsulated the creation of a questionnaire, its questions, and associated answers within a single transaction block, directly interacting with the database models and handling exceptions in a generic manner. This approach, while functional, resulted in a more verbose method with nested iterations and direct creation calls within the transaction block.

The new create method introduces a more structured approach by segmenting the questionnaire creation and the addition of questions and answers into distinct operations. This separation is achieved through the create_questionnaire and create_questions_and_answers helper functions, which not only streamline the code but also improve clarity by breaking down the process into more manageable, focused steps. The use of these helper functions within the transaction ensures that the entire operation remains atomic, adhering to the principle that all parts of the questionnaire creation should either complete successfully or fail together, thus maintaining data integrity.

Furthermore, the new method employs a more sophisticated error handling strategy, explicitly rescuing StandardError and utilizing a render_error helper method to provide a consistent response format across different actions in the controller. This approach not only standardizes error responses but also enhances the method's robustness by clearly defining the scope of errors it can handle.

The shift to using helper methods like render_success and render_error for rendering responses aligns with modern Ruby practices, focusing on code modularity and maintainability. By encapsulating the success and error rendering logic, the new method offers a cleaner, more consistent interface for handling the various outcomes of the create operation, facilitating easier future modifications and improving the overall code quality.

“assign_quiz_to_student” method

In the reimplementation of the assign_quiz_to_student method, several changes were made.Firstly, the new version introduces helper methods find_resource_by_id for fetching the participant and questionnaire, and quiz_already_assigned? to check if the quiz has already been assigned to the student. These abstractions not only make the method more readable but also encapsulate specific functionalities, making the code more reusable and maintainable.

The condition checking for an existing assignment is now encapsulated within the quiz_already_assigned? method, simplifying the main method's logic flow and focusing it on the assignment process rather than validation checks.Another notable change is the introduction of build_response_map, a method presumably responsible for constructing a new ResponseMap instance. This further modularizes the code, separating the concerns of validation and object creation.

Error handling has been standardized using render_error and render_success helper methods, consistent with modern practices of handling HTTP responses. This not only makes the code cleaner but also ensures that the method's responses are consistent with other parts of the application.The use of return unless participant && questionnaire early in the method is a Ruby idiom that helps to avoid nested conditional statements, thereby enhancing the readability and flow of the method.

“submit_answers” method

In the reimplementation of the submit_answers method, several refinements were made to enhance code modularity, readability, and adherence to the DRY (Don't Repeat Yourself) principle, which the old version somewhat lacked, particularly in handling responses and scoring logic.The new method employs helper methods like find_response_map_for_current_user to fetch the relevant ResponseMap for the current user and process_answers to handle the logic of processing submitted answers and calculating the total score. This approach not only makes the code cleaner and more readable by breaking down the process into smaller, more manageable chunks but also improves maintainability by isolating specific functionalities.

In the original version, the logic for finding the ResponseMap, processing each answer, and calculating the total score was all embedded within the main submit_answers method, making it more cumbersome and less readable. This approach also violated the DRY principle, as similar patterns of fetching and processing could potentially be used in other parts of the application but would need to be rewritten.

The restructured method enhances error handling by utilizing render_error for consistent error messaging, similar to other methods in the controller, thereby standardizing response formats across different actions. This is a shift from the old method, where JSON error responses were constructed inline, leading to potential inconsistencies in error handling across the application.

By abstracting repetitive logic into helper methods, the new version adheres more closely to the DRY principle, reducing redundancy and the likelihood of errors during future modifications. The encapsulation of specific tasks into separate methods not only clarifies the main method's purpose—submitting answers and calculating scores—but also allows for easier testing and debugging of individual components.

Overall, the changes made in the new version of the submit_answers method reflect a thoughtful refactoring effort aimed at improving code quality, maintainability, and adherence to best practices in Ruby on Rails development