CSC/ECE 517 Fall 2023 - E2371. Reimplement quiz questionnaires controller: Difference between revisions

From Expertiza_Wiki
Jump to navigation Jump to search
No edit summary
 
(17 intermediate revisions by 3 users not shown)
Line 6: Line 6:




[http://expertiza.ncsu.edu/ Expertiza] is a prominent open-source project founded on the Ruby on Rails framework, serving as a collaborative effort between the faculty and students of NC State. This web application facilitates instructors in generating customized assignments, including both new and existing tasks. Additionally, instructors can establish a roster of topics for student enrollment. Within Expertiza, students have the ability to form teams for collaborative work on various projects and assignments. An integral aspect of the platform is the provision for students to conduct peer reviews of their peers' submissions.
[http://expertiza.ncsu.edu/ Expertiza] stands as a noteworthy open-source initiative, rooted in the robust Ruby on Rails framework, and is the product of a collaborative effort between faculty and students at NC State. This web application plays a pivotal role in aiding instructors in the creation of tailored assignments, encompassing both new and existing tasks. Furthermore, instructors can curate a diverse range of topics for student enrollment. Within the Expertiza ecosystem, students possess the capability to form collaborative teams for the seamless execution of various projects and assignments. A cornerstone of this platform is its provision for students to engage in peer reviews of their peers' submissions.


Distinguished by its support for a diverse array of document types, Expertiza enables submission of various formats such as URLs and wiki pages. Serving as an open-source learning management system developed using Ruby on Rails, Expertiza embodies an extensive suite of functionalities that empower students to submit and engage in peer review processes encompassing various learning objects like articles, codes, and websites. Instructors wield the capability to oversee and assess the submissions made by students through the platform. Expertiza is instrumental in facilitating instructors and teaching assistants in managing assignments for the courses they administer.
What sets Expertiza apart is its versatility in accommodating an array of document types, enabling submissions in diverse formats, including URLs and wiki pages. Positioned as an open-source learning management system, Expertiza harnesses the power of Ruby on Rails to provide an extensive suite of features that empower students to submit and actively participate in peer review processes across an array of learning objects, such as articles, code, and websites. Instructors find themselves equipped with the ability to oversee and assess student submissions efficiently through the platform. In essence, Expertiza plays an indispensable role in aiding instructors and teaching assistants in the efficient management of assignments for the courses they administer.


== '''Overview of the Controller''' ==
The QuizQuestionnairesController is a crucial component in the project, responsible for managing quiz questionnaires within the application. It extends the functionality provided by the base QuestionnairesController and incorporates the AuthorizationHelper module, making it central to handling user permissions and authorization checks. Its primary role is to determine whether users have the necessary privileges to perform various actions related to quiz questionnaires, such as creation, editing, viewing, and deletion, based on their roles and access rights.


== '''Overview of the Classes''' ==
In addition to its authorization responsibilities, the QuizQuestionnairesController plays a pivotal role in facilitating the creation and editing of quiz questionnaires. It defines methods for creating, updating, and deleting questionnaires, ensuring they adhere to specified guidelines and that edits are allowed under specific conditions. The controller also manages the intricacies of quiz data, from validating questions and managing answer choices to enforcing logic for different question types. This controller essentially acts as the backbone for handling all aspects of quiz-related actions, guaranteeing user permissions are respected and that quiz data is properly maintained throughout its lifecycle.


=== participants_controller.rb: ===
== '''Background of the Project''' ==
 
 
The reimplementation of the quiz questionnaire controller in Expertiza is an important project aimed at enhancing the functionality, clarity, and maintainability of this crucial component. The existing controller is in need of a comprehensive overhaul to better align with best coding practices and user requirements. Here's a background for this project:
 
Project Overview:
The project involves reimagining and improving the quiz questionnaire controller within the Expertiza platform. The current controller lacks clarity, has unclear functionality, and could benefit from enhanced performance. The primary objective is to implement CRUD operations (Create, Read, Update, Delete) for quiz questionnaires while ensuring that user permissions are adequately considered for these actions.
 
Key Tasks and Objectives:
 
CRUD Operations: The reimplementation will involve creating methods to handle the creation, editing, deletion, and viewing of quiz questionnaires. These methods should adhere to best coding practices and clearly indicate their functionality.
 
Code Refinement: Existing code should be refactored to ensure clean and concise implementation. Methods with the same names that perform different tasks should be renamed for clarity, and any unclear or redundant functionality should either be documented or removed. Performance bottlenecks, such as loops or methods that can be refactored for better efficiency, should be addressed.
 
Complexity Reduction: Any unused or unclear functionality should be removed from the controller. This step is essential in reducing the complexity of the codebase, making it more maintainable and understandable.
 
Testing: Comprehensive testing should be implemented for the quiz questionnaire controller. The tests should aim to cover at least 80% of the codebase, ensuring the reliability and correctness of the reimplementation. Tools like Rubocop and Code Climate should be used to identify and rectify code smells.
 
Benefits:
 
Improved User Experience: The reimplementation will result in a more user-friendly and intuitive interface for managing quiz questionnaires.
 
Enhanced Code Quality: The project will elevate the overall code quality, making it cleaner, more efficient, and easier to maintain.
 
Better Performance: Addressing performance issues will lead to faster and more responsive interactions with the system.
 
Reduced Complexity: The removal of unused or unclear functionality will simplify the controller, making it more accessible for developers and maintainers.
 
In summary, the reimplementation of the quiz questionnaire controller in Expertiza is a vital project that aims to revamp and optimize this component, ultimately providing a more effective and user-friendly experience for instructors, students, and developers.
 
== '''Implementation''' ==
 
=== quiz_questionnaire_controller.rb: ===
 
 
We have reimplemented the `Api::V1::QuizQuestionnairesController` in Ruby on Rails by making several key changes to improve code readability, maintainability, and error handling. Below are the main modifications made to the code:
 
1. Changed Function Names: The function names have been chosen to be more concise and descriptive. For example, the method originally named 'copy' is used to create a copy of a questionnaire, and this change makes the code more intuitive.
 
2. Improved Code Comments: Detailed comments have been added to each action method, explaining the purpose of the method and the expected parameters. This documentation is invaluable for both developers working on the code and anyone looking to understand how the API functions.
 
3. Improved Error Handling: The code has been enhanced to handle exceptions more specifically, such as catching `ActiveRecord::RecordNotFound` and `ActiveRecord::RecordInvalid` exceptions. This results in more informative error messages, which is beneficial for debugging and communication with clients.
 
4. Refactored Create Method: The `create` method has been refactored to improve clarity and robustness. It now first checks user privileges using the `check_privilege` method. If the user has the required permissions, it proceeds to create a new `QuizQuestionnaire` based on the provided parameters. This refactoring helps separate concerns and makes the code more organized.
 
5. Consistent Status Codes: The code now consistently uses HTTP status codes to indicate the result of API requests. For instance, it uses `status: :not_found` when a requested resource is not found, which aligns with common HTTP conventions. This consistency in status codes improves the predictability of API responses.
 
6. Consistent JSON Response Format: The JSON responses have been structured consistently to follow a standardized format. Keys like "model_object" and "participants" are used to make it easier for client applications to consume the API. This consistency simplifies the parsing of responses on the client side.
 
These changes enhance the overall quality of the code, making it more accessible for developers, improving the API's reliability, and providing a consistent and user-friendly experience for clients interacting with the API.
 
== Class Diagram of the Model ==
 
To understand how the model is made, lets look at the class diagram to understand how the model is represented in Database and what are the values it uses and the foreign keys quiz questionnaire has.


The ParticipantsController is responsible for managing participants in an application. Participants can be associated with either "Course" or "Assignment" models. It handles actions related to creating, updating, retrieving, and deleting participants. Inherit copies existing participants from a course down to its assignment while bequeath copies existing participants from an assignment up to its course. It has two private methods namely copy_participants_from_source_to_target which copies participants from source to target and participant_params.
[[File:Class_Diagram_Quiz_Questionnaire.png | 800px]]


=== assignment_participant.rb: ===
=== Screenshots ===


The assignment_participant.rb is a model class that has many associations including ‘assignment’. This association signifies that an AssignmentParticipant belongs to a specific assignment. The AssignmentParticipant class includes several attributes such as
1. Login
avg_vol_per_round, overall_avg_vol and handle that are vital for its functionality. There are many methods present which collectively facilitate various actions and operations related to managing participants in assignments, including reviewing, copying, importing, and handling file paths and deadlines. They include review_file_path, current_stage, stage_deadline, current_user_is_reviewer, reviews, dir_path, etc. There are also a couple of methods that use digital signatures such as assign_copyright and verify_digital_signature.


=== course_participant.rb: ===
[[File:Login.jpeg | 700px]]


The course_participant model has a class named CourseParticipant that inherits from a class called Participant. It is used to manage participants in courses, allowing for copying participants to assignments and importing new participants into a course. It consists of three methods namely copy, import and path. Copy creates a copy of a course participant for an assignment. Path method returns the path of the course participant while self.import method is used for importing course participants by taking row_hash, session, and id as parameters.


2. Create


== '''Background of the Project''' ==
[[File:Create.jpeg | 700px]]
 
 
3. Get/Show
 
[[File:Get.jpeg | 700px]]
 
 
4. Delete
 
[[File:Delete.jpeg | 700px]]
 
 
5. Update
 
[[File:Update.jpeg | 700px]]
 
 
6. Copy Questionnaire
 
[[File:Copy questionnaire.jpeg | 700px]]
 
 
 
== Testing ==
 
 
{| class="wikitable" style="margin-left:40px"
|-
! Test No. !! Description
|-
| 1 || Get Quiz Questionnaires
|-
| 2 || Create Quiz Questionnaire
|-
| 3 || Handle Invalid Quiz Questionnaire Creation Params
|-
| 4 || Handle No Permission to Create Quiz Questionnaire
|-
| 5 || Handle Assignment Not Requiring Quiz
|-
| 6 || Copy Quiz Questionnaire
|-
| 7 || Handle Copying Nonexistent Quiz Questionnaire
|-
| 8 || Retrieve Quiz Questionnaire
|-
| 9 || Handle Retrieving Nonexistent Quiz Questionnaire
|-
| 10 || Update Quiz Questionnaire
|-
| 11 || Handling Invalid Questionnaire Parameters during Update
|-
| 12 || Handling Lack of Permission during Questionnaire Update
|-
| 13 || Deleting a Quiz Questionnaire
|-
| 14 || Handling Non-Existent Quiz Questionnaire during Copy
|-
| 15 || Handling Deletion Permission
|-
|}
 
 
'''Test Environment:'''
 
1. Ruby on Rails environment.
 
2. RSpec for testing.
 
3. Factory Bot for test data creation.
 
4. Rswag for creating swagger api docs.
 
'''Objective:'''
 
Ensure that the new methods (copy, import, export, export_fields) in the CourseParticipant class are functioning correctly.
 
 
'''Test Cases:'''
 
 
'''Test Case 1: Get Quiz Questionnaires'''
 
''Assertion:''
 
Calling the endpoint to get quiz questionnaires should return a response with a status code of 200 and a JSON body containing an array of quiz questionnaires.
 
''Steps:''
 
1.Set up necessary data, including roles, an institution, a user, an assignment, and a participant.
 
2.Make a GET request to the /api/v1/quiz_questionnaires endpoint with the appropriate authorization header and content type.
 
3.Assert that the response status code is 200.
 
4.Assert that the response body contains an array with a size of 2, representing two quiz questionnaires.
 
''Explanation:''
 
This test case verifies that the API endpoint successfully retrieves quiz questionnaires and returns the expected response.
 
'''Test Case 2: Create Quiz Questionnaire'''
 
''Assertion:''
 
Making a POST request to create a quiz questionnaire with valid parameters should return a response with a status code of 201, and the response body should include the name of the created quiz questionnaire.
 
''Steps:''
 
1.Set up necessary data, including roles, an institution, a user, a team, and two quiz questionnaires.
 
2.Make a POST request to the /api/v1/quiz_questionnaires endpoint with valid parameters for creating a quiz questionnaire.
 
3.Assert that the response status code is 201.
 
4.Assert that the response body contains the name 'TestCreateQuizQ101'.
 
''Explanation:''
 
This test case ensures that the API endpoint can successfully create a quiz questionnaire with valid parameters.
 
'''Test Case 3: Handle Invalid Quiz Questionnaire Creation Params'''
 
''Assertion:''
 
Making a POST request to create a quiz questionnaire with invalid parameters should return a response with a status code of 422, indicating unprocessable entity due to invalid parameters.
 
''Steps:''
 
1.Set up necessary data, including roles, an institution, a user, and a team.
2.Make a POST request to the /api/v1/quiz_questionnaires endpoint with invalid parameters for creating a quiz questionnaire.
3.Assert that the response status code is 422.
 
''Explanation:''
 
This test case verifies that the API endpoint handles invalid parameters during quiz questionnaire creation and returns an appropriate response.
 
'''Test Case 4: Handle No Permission to Create Quiz Questionnaire'''
 
''Assertion:''
 
Making a POST request to create a quiz questionnaire without the required permission should return a response with a status code of 422, indicating unprocessable entity due to the lack of permission.
 
''Steps:''
 
1.Set up necessary data, including roles, an institution, a user, a team, and an assignment.
 
2.Make a POST request to the /api/v1/quiz_questionnaires endpoint with valid parameters but without the required permission.
 
3.Assert that the response status code is 422.
 
''Explanation:''
 
This test case ensures that the API endpoint checks for the required permission during quiz questionnaire creation and returns an appropriate response if permission is lacking.
 
'''Test Case 5: Handle Assignment Not Requiring Quiz'''
 
''Assertion:''
 
Making a POST request to create a quiz questionnaire for an assignment that does not require a quiz should return a response with a status code of 422, indicating unprocessable entity.
 
''Steps:''
 
1.Set up necessary data, including roles, an institution, a user, a team, and an assignment that does not require a quiz.
 
2.Make a POST request to the /api/v1/quiz_questionnaires endpoint with valid parameters for creating a quiz questionnaire.
 
3.Assert that the response status code is 422.
 
''Explanation:''
 
This test case ensures that the API endpoint correctly handles the creation of quiz questionnaires for assignments that do not require a quiz and returns an appropriate response.
 
'''Test Case 6: Copy Quiz Questionnaire'''
 
''Assertion:''
 
Making a POST request to copy a quiz questionnaire with a valid ID should return a response with a status code of 200, indicating successful copying.
 
''Steps:''
 
1.Set up necessary data, including roles, an institution, a user, and a quiz questionnaire to be copied.
 
2.Make a POST request to the /api/v1/quiz_questionnaires/copy/{id} endpoint with a valid ID for copying.
 
3.Assert that the response status code is 200.
 
''Explanation:''
 
This test case verifies that the API endpoint can successfully copy a quiz questionnaire with a valid ID.
 
'''Test Case 7: Handle Copying Nonexistent Quiz Questionnaire'''
 
''Assertion:''
 
Making a POST request to copy a nonexistent quiz questionnaire should return a response with a status code of 404, indicating not found.
 
''Steps:''
1.Set up necessary data, including roles, an institution, a user, and no quiz questionnaire with the specified ID.
 
2.Make a POST request to the /api/v1/quiz_questionnaires/copy/{id} endpoint with an invalid ID for copying.
 
3.Assert that the response status code is 404.
 
''Explanation:''
 
This test case ensures that the API endpoint handles the attempt to copy a nonexistent quiz questionnaire and returns an appropriate response.
 
'''Test Case 8: Retrieve Quiz Questionnaire'''
 
''Assertion:''
 
Making a GET request to retrieve details of a quiz questionnaire with a valid ID should return a response with a status code of 200, and the response body should contain the details of the quiz questionnaire.
 
''Steps:''
 
1.Set up necessary data, including roles, an institution, a user, and a quiz questionnaire.
 
2.Make a GET request to the /api/v1/quiz_questionnaires/{id} endpoint with a valid ID for retrieving details.
 
3.Assert that the response status code is 200.
 
4.Assert that the response body contains the details of the quiz questionnaire.
 
''Explanation:''
 
This test case verifies that the API endpoint can successfully retrieve details of a quiz questionnaire with a valid ID.
 
'''Test Case 9: Handle Retrieving Nonexistent Quiz Questionnaire'''
 
''Assertion:''
 
Making a GET request to retrieve details of a nonexistent quiz questionnaire should return a response with a status code of 404, indicating not found.
 
''Steps:''
 
1.Set up necessary data, including roles, an institution, a user, and no quiz questionnaire with the specified ID.
 
2.Make a GET request to the /api/v1/quiz_questionnaires/{id} endpoint with an invalid ID for retrieving details.
 
3.Assert that the response status code is 404.
 
''Explanation:''
 
This test case ensures that the API endpoint handles the attempt to retrieve details of a nonexistent quiz questionnaire and returns an appropriate response.
 
'''Test Case 10: Update Quiz Questionnaire'''
 
''Assertion:''
 
Making a PUT request to update a quiz questionnaire with valid parameters should return a response with a status code of 200, indicating successful updating.
 
''Steps:''
 
1.Set up necessary data, including roles, an institution, a user, and a quiz questionnaire.
 
2.Make a PUT request to the /api/v1/quiz_questionnaires/{id} endpoint with valid parameters for updating.
 
3.Assert that the response status code is 200.
 
''Explanation:''
 
This test case verifies that the API endpoint can successfully update a quiz questionnaire with valid parameters.
 
'''Test Case 11: Handling Invalid Questionnaire Parameters during Update'''
 
''Assertion:''
 
Return status code 422 if the questionnaire parameters are invalid during the update.
 
''Steps:''
 
1. Set up the necessary context and authorization token.
 
2. Prepare invalid questionnaire parameters with negative min_question_score, max_question_score greater than min_question_score, an invalid instructor_id, and a missing assignment_id.
 
3. Make a PUT request to update a quiz questionnaire with the provided invalid parameters.
 
4. Assert that the response status code is 422.
 
''Explanation:''
 
This test case ensures that the API returns a status code of 422 when attempting to update a quiz questionnaire with invalid parameters, such as negative min_question_score, max_question_score greater than min_question_score, an invalid instructor_id, and a missing assignment_id.
 
 
'''Test Case 12: Handling Lack of Permission during Questionnaire Update'''
 
''Assertion:''
 
Return status code 422 with an appropriate error message if the user lacks permission to update the quiz questionnaire.
 
''Steps:''
 
1. Set up the necessary context, including the authorization token.
 
2. Prepare valid questionnaire parameters for the update but with a user_id that lacks the required permission.
 
3. Make a PUT request to update a quiz questionnaire with the provided parameters and insufficient permissions.
 
4. Assert that the response status code is 422.
 
5. Verify that the error message indicates the requirement of permission to perform the update.
 
''Explanation:''
 
This test case ensures that the API returns a status code of 422 and a clear error message when attempting to update a quiz questionnaire without the necessary permission.
 
'''Test Case 13: Deleting a Quiz Questionnaire'''
 
''Assertion:''
 
The API endpoint should delete an existing quiz questionnaire.
 
''Steps:''
 
1. Make a DELETE request to the '/api/v1/quiz_questionnaires/{id}' endpoint with a valid quiz questionnaire ID.
 
2. Check if the response status code is 204.
 
3. Verify that the deleted quiz questionnaire no longer exists in the database.
 
''Explanation:''
 
This test case ensures that the API can successfully delete an existing quiz questionnaire.
 
'''Test Case 14: Handling Non-Existent Quiz Questionnaire during Copy'''
 
''Assertion:''
 
Return status code 404 with an appropriate error message if attempting to copy a quiz questionnaire with a non-existent ID.
 
''Steps:''
 
1. Set up the necessary context, including the authorization token.
 
2. Specify an ID that does not correspond to any quiz questionnaire in
the database.
 
3. Make a POST request to copy a quiz questionnaire with the provided non-existent ID.
 
4. Assert that the response status code is 404.
 
5. Verify that the error message indicates the non-existence of a quiz questionnaire with the given ID.
 
''Explanation:''
 
This test case ensures that the API responds appropriately when attempting to copy a quiz questionnaire that does not exist in the database.
 
'''Test Case 15: Handling Deletion Permission'''
 
''Assertion:''
 
Return status code 422 with an appropriate error message if a user lacks permission to delete the specified quiz questionnaire.
 
''Steps:''
 
1. Set up the necessary context, including the authorization token.
 
2. Specify a quiz questionnaire ID and provide user credentials that lack the permission to delete.
 
3. Make a DELETE request to delete the quiz questionnaire with the given ID.
 
4. Assert that the response status code is 422.


The Expertiza project involves the reimplementing of the participants_controller.rb and participants.rb files, along with their respective child classes. The previous iteration of the participant model and controller underwent reimplementations in prior semesters, resulting in tests that relied extensively on mocks and stubs due to missing components.
5. Verify that the error message indicates the requirement of proper permission to delete the quiz questionnaire.


The participants_controller.rb file encapsulates various methods and functionalities vital to managing participants within the system. This includes actions like adding, updating, and deleting participants, inheriting participants from courses to assignments, bequeathing participants from assignments to courses, changing participant handles, viewing copyright grants, and more. The controller makes use of helper functions, associations, and delegate methods to streamline participant operations.
''Explanation:''


Meanwhile, the course_participants.rb file extends the functionality of the base participant class, focusing on operations specific to course participants. This includes copying participants to assignments, importing course participants, and defining paths for course participants within the project.
This test case ensures that the API handles deletion attempts appropriately, returning a status code 422 when the user lacks the necessary permission to delete a quiz questionnaire.


The base participant.rb file defines the fundamental structure and behavior for all participants in the system, including shared associations, delegate methods, and validations. The file incorporates methods related to participant handling, user information retrieval, email functionalities, authorization, sorting, and export functionality.
== '''Program 4 Design Patterns Used''' ==


The project's primary objective revolves around enhancing the reliability and functionality of the participant-related components, thereby fortifying the overall system's capabilities and improving the testing process to ensure robustness and stability within the Expertiza platform.
=== Design Principles in QuizQuestionnairesController.rb: ===


The reimplementation must make sense; when reviewing the original model, we discovered that certain functions were unnecessary for the controller class and model in question and needed to be implemented in a different model. The majority of the adjustments were made to separate methods with a single capability pertinent to certain classes by deleting, combining, and replacing methods.To improve readability, notes are provided to every technique. The discussion of the reimplementations continues below with further details.
<u>Single Responsibility Principle (SRP)</u>


The QuizQuestionnairesController adheres to the Single Responsibility Principle (SRP) by ensuring that each of its actions is dedicated to a specific responsibility related to managing quiz questionnaires. The breakdown of responsibilities is as follows:


== '''Design Decisions''' ==
'''Index Action''': Retrieves a list of quiz questionnaires.


=== participants_controller.rb: ===
'''Show Action''': Retrieves details of a single quiz questionnaire.


'''Create Action''': Creates a new quiz questionnaire based on provided parameters.


We have reimplemented participants_controller.rb by making following changes:
'''Update Action''': Updates an existing quiz questionnaire.


''1) Changed function name:''
'''Destroy Action''': Deletes a quiz questionnaire.
The function name 'copy_participants_from_source_to_target' has been renamed to 'copy_participants' as original name was too long.


''2) Improved Code Comments:''
'''Copy Action''': Creates a copy of a quiz questionnaire.
The code has detailed comments for each action method, the purpose of the method and the expected parameters.
The parameters for each action method are explicitly defined in comments, making it clear which parameters are expected.


''3) Improved Error Handling:''
This adherence to the SRP enhances maintainability and readability, making it easier to understand and modify each action independently.
Exceptions are caught more specifically (e.g., StandardError) to provide better error messages.


''4) Refactored delete Method:''
<u>Dependency Inversion Principle (DIP)</u>
The destroy method has been refactored to use participant.delete(false) to avoid accidental deletion and provides better error handling.


''5) Consistent Status Codes:''
The Dependency Inversion Principle (DIP) is exemplified in the QuizQuestionnairesController through the use of ActiveRecord. Instead of directly depending on a specific database implementation, the controller relies on the ActiveRecord interface. This decouples the controller from the underlying database details, promoting flexibility and facilitating easier integration with different data storage solutions in the future.
The code uses consistent HTTP status codes for responses, for example, using status: :not_found for a resource not found.


''6) Consistent JSON Response Format:''
By embracing ActiveRecord as an abstraction layer, the controller adheres to the DIP, allowing for a more modular and extensible architecture. This design choice enables easier testing, as the controller's interactions with the database are abstracted through a well-defined interface.
The JSON responses are structured consistently, with keys like "model_object" and "participants," making it easier for clients to consume the API.


=== assignment_participant.rb: ===
=== Design Principles in ReviewQuestionnaire.rb: ===


This is the reimplemented AssignmentParticipant class. It is a subclass of the Participant class and includes additional functionalities and methods specific to participants assigned to an assignment in the system.
<u>Single Responsibility Principle (SRP):</u>


In the `assignment_participant.rb` class, several changes and improvements have been made to enhance the readability and maintainability of the code. Here are the specific modifications made:
To uphold the Single Responsibility Principle, we plan to extract the logic related to assessments retrieval—specifically in the get_assessments_for and  get_assessments_round_for methods—into a dedicated service or module. By doing so, we ensure that the ReviewQuestionnaire class maintains a single responsibility, focusing solely on the management of review questionnaires. This separation of concerns not only aligns with best practices but also contributes to clearer and more maintainable code.


<u>Factory Method Pattern:</u>


1. Removed certain comments and obsolete code for better readability and clarity.
We recognize the potential need to instantiate different types of questionnaires in the future while maintaining a common interface. To address this, we plan to implement the Factory Method Pattern. This pattern will allow us to encapsulate the instantiation logic, providing flexibility in creating various questionnaire types without altering the client code.


2. Introduced the safe navigation operator (`&.`) in several places to avoid nil errors, particularly in cases where object references may be nil.
=== Design Principles in MetaReviewQuestionnaire.rb: ===


3. Simplified certain methods, such as `reviewers` and `feedback`, for cleaner and more readable code.
<u>Single Responsibility Principle (SRP):</u>


4. Improved string formatting for directory paths and file paths to enhance readability.
In our ongoing efforts to enhance the maintainability and clarity of our codebase, we have identified the MetareviewQuestionnaire model as a candidate for refactoring. The model currently adheres well to the Single Responsibility Principle (SRP) by focusing on the management of metareview questionnaires. Each method within the model (post_initialization, symbol, get_assessments_for) appears to align with this singular responsibility.


5. Enhanced error handling in the `import` method to provide more informative error messages and handle exceptional cases more gracefully.
<u>Encapsulation:</u>


These changes aim to make the code more maintainable and concise while ensuring that the functionality and integrity of the `AssignmentParticipant` class remain intact.
To enhance encapsulation and follow best practices, we will encapsulate the class variable @print_name by providing an appropriate getter method. This step aims to hide the internal details of the class, promoting a cleaner and more maintainable code structure.


=== course_participant.rb: ===
<u>Factory Method Pattern:</u>


The following changes were reimplemented in the course_participant.rb
We recognize the potential need to instantiate different types of questionnaires in the future while maintaining a common interface. To address this, we plan to implement the Factory Method Pattern. This pattern will allow us to encapsulate the instantiation logic, providing flexibility in creating various questionnaire types without altering the client code.


In the CourseParticipant class, several changes and improvements have been made to enhance the readability and maintainability of the code. Here are the specific modifications made:
=== Design Principles in AssignmentQuestionnaire.rb: ===


1] The copy method has been simplified using the find_or_create_by method, which helps to find an existing record or create a new one if it doesn't exist.
<u>Single Responsibility Principle (SRP):</u>


2] In the import method, the find_or_create_by method has been used to both find or create a user and find or create a course participant. This helps to streamline the process and handle the cases where the records may or may not exist.
The AssignmentQuestionnaire model currently handles both ActiveRecord associations and custom query methods. To adhere more closely to the SRP, we plan to separate these concerns into distinct modules or classes. This separation will not only enhance the readability of our code but also contribute to a more modular and organized structure.


3] The path method has been refactored to use the safe navigation operator (&.) to avoid potential nil errors during the construction of the path. This ensures that the code is more robust and handles potential null references gracefully.
<u>Factory Method Pattern:</u>


These changes aim to make the code more concise and readable, without compromising the functionality or integrity of the CourseParticipant class.
In cases where there are varied ways to instantiate AssignmentQuestionnaire instances, we recognize the potential benefits of applying the Factory Method Pattern. This pattern allows us to define an interface for creating instances in a superclass while enabling subclasses to alter the types of objects created.




== Relevant Links ==
== Relevant Links ==


'''Github repository:''' https://github.com/krishna5701/reimplementation-back-end
'''Github repository:''' https://github.com/rajmadhu0406/reimplementation-back-end


'''Pull request:''' https://github.com/expertiza/reimplementation-back-end/pull/49
'''Pull request:''' https://github.com/expertiza/reimplementation-back-end/pull/48


'''Youtube video:''' https://youtu.be/tPK0-nbs-hI?si=MgWlrU1RWWTQfReO


== Team ==
== Team ==

Latest revision as of 07:12, 5 December 2023

This wiki page is for the description of changes made under E2371 OSS assignment for Fall 2023, CSC/ECE 517

Introduction

Expertiza stands as a noteworthy open-source initiative, rooted in the robust Ruby on Rails framework, and is the product of a collaborative effort between faculty and students at NC State. This web application plays a pivotal role in aiding instructors in the creation of tailored assignments, encompassing both new and existing tasks. Furthermore, instructors can curate a diverse range of topics for student enrollment. Within the Expertiza ecosystem, students possess the capability to form collaborative teams for the seamless execution of various projects and assignments. A cornerstone of this platform is its provision for students to engage in peer reviews of their peers' submissions.

What sets Expertiza apart is its versatility in accommodating an array of document types, enabling submissions in diverse formats, including URLs and wiki pages. Positioned as an open-source learning management system, Expertiza harnesses the power of Ruby on Rails to provide an extensive suite of features that empower students to submit and actively participate in peer review processes across an array of learning objects, such as articles, code, and websites. Instructors find themselves equipped with the ability to oversee and assess student submissions efficiently through the platform. In essence, Expertiza plays an indispensable role in aiding instructors and teaching assistants in the efficient management of assignments for the courses they administer.

Overview of the Controller

The QuizQuestionnairesController is a crucial component in the project, responsible for managing quiz questionnaires within the application. It extends the functionality provided by the base QuestionnairesController and incorporates the AuthorizationHelper module, making it central to handling user permissions and authorization checks. Its primary role is to determine whether users have the necessary privileges to perform various actions related to quiz questionnaires, such as creation, editing, viewing, and deletion, based on their roles and access rights.

In addition to its authorization responsibilities, the QuizQuestionnairesController plays a pivotal role in facilitating the creation and editing of quiz questionnaires. It defines methods for creating, updating, and deleting questionnaires, ensuring they adhere to specified guidelines and that edits are allowed under specific conditions. The controller also manages the intricacies of quiz data, from validating questions and managing answer choices to enforcing logic for different question types. This controller essentially acts as the backbone for handling all aspects of quiz-related actions, guaranteeing user permissions are respected and that quiz data is properly maintained throughout its lifecycle.

Background of the Project

The reimplementation of the quiz questionnaire controller in Expertiza is an important project aimed at enhancing the functionality, clarity, and maintainability of this crucial component. The existing controller is in need of a comprehensive overhaul to better align with best coding practices and user requirements. Here's a background for this project:

Project Overview: The project involves reimagining and improving the quiz questionnaire controller within the Expertiza platform. The current controller lacks clarity, has unclear functionality, and could benefit from enhanced performance. The primary objective is to implement CRUD operations (Create, Read, Update, Delete) for quiz questionnaires while ensuring that user permissions are adequately considered for these actions.

Key Tasks and Objectives:

CRUD Operations: The reimplementation will involve creating methods to handle the creation, editing, deletion, and viewing of quiz questionnaires. These methods should adhere to best coding practices and clearly indicate their functionality.

Code Refinement: Existing code should be refactored to ensure clean and concise implementation. Methods with the same names that perform different tasks should be renamed for clarity, and any unclear or redundant functionality should either be documented or removed. Performance bottlenecks, such as loops or methods that can be refactored for better efficiency, should be addressed.

Complexity Reduction: Any unused or unclear functionality should be removed from the controller. This step is essential in reducing the complexity of the codebase, making it more maintainable and understandable.

Testing: Comprehensive testing should be implemented for the quiz questionnaire controller. The tests should aim to cover at least 80% of the codebase, ensuring the reliability and correctness of the reimplementation. Tools like Rubocop and Code Climate should be used to identify and rectify code smells.

Benefits:

Improved User Experience: The reimplementation will result in a more user-friendly and intuitive interface for managing quiz questionnaires.

Enhanced Code Quality: The project will elevate the overall code quality, making it cleaner, more efficient, and easier to maintain.

Better Performance: Addressing performance issues will lead to faster and more responsive interactions with the system.

Reduced Complexity: The removal of unused or unclear functionality will simplify the controller, making it more accessible for developers and maintainers.

In summary, the reimplementation of the quiz questionnaire controller in Expertiza is a vital project that aims to revamp and optimize this component, ultimately providing a more effective and user-friendly experience for instructors, students, and developers.

Implementation

quiz_questionnaire_controller.rb:

We have reimplemented the `Api::V1::QuizQuestionnairesController` in Ruby on Rails by making several key changes to improve code readability, maintainability, and error handling. Below are the main modifications made to the code:

1. Changed Function Names: The function names have been chosen to be more concise and descriptive. For example, the method originally named 'copy' is used to create a copy of a questionnaire, and this change makes the code more intuitive.

2. Improved Code Comments: Detailed comments have been added to each action method, explaining the purpose of the method and the expected parameters. This documentation is invaluable for both developers working on the code and anyone looking to understand how the API functions.

3. Improved Error Handling: The code has been enhanced to handle exceptions more specifically, such as catching `ActiveRecord::RecordNotFound` and `ActiveRecord::RecordInvalid` exceptions. This results in more informative error messages, which is beneficial for debugging and communication with clients.

4. Refactored Create Method: The `create` method has been refactored to improve clarity and robustness. It now first checks user privileges using the `check_privilege` method. If the user has the required permissions, it proceeds to create a new `QuizQuestionnaire` based on the provided parameters. This refactoring helps separate concerns and makes the code more organized.

5. Consistent Status Codes: The code now consistently uses HTTP status codes to indicate the result of API requests. For instance, it uses `status: :not_found` when a requested resource is not found, which aligns with common HTTP conventions. This consistency in status codes improves the predictability of API responses.

6. Consistent JSON Response Format: The JSON responses have been structured consistently to follow a standardized format. Keys like "model_object" and "participants" are used to make it easier for client applications to consume the API. This consistency simplifies the parsing of responses on the client side.

These changes enhance the overall quality of the code, making it more accessible for developers, improving the API's reliability, and providing a consistent and user-friendly experience for clients interacting with the API.

Class Diagram of the Model

To understand how the model is made, lets look at the class diagram to understand how the model is represented in Database and what are the values it uses and the foreign keys quiz questionnaire has.

Screenshots

1. Login


2. Create


3. Get/Show


4. Delete


5. Update


6. Copy Questionnaire


Testing

Test No. Description
1 Get Quiz Questionnaires
2 Create Quiz Questionnaire
3 Handle Invalid Quiz Questionnaire Creation Params
4 Handle No Permission to Create Quiz Questionnaire
5 Handle Assignment Not Requiring Quiz
6 Copy Quiz Questionnaire
7 Handle Copying Nonexistent Quiz Questionnaire
8 Retrieve Quiz Questionnaire
9 Handle Retrieving Nonexistent Quiz Questionnaire
10 Update Quiz Questionnaire
11 Handling Invalid Questionnaire Parameters during Update
12 Handling Lack of Permission during Questionnaire Update
13 Deleting a Quiz Questionnaire
14 Handling Non-Existent Quiz Questionnaire during Copy
15 Handling Deletion Permission


Test Environment:

1. Ruby on Rails environment.

2. RSpec for testing.

3. Factory Bot for test data creation.

4. Rswag for creating swagger api docs.

Objective:

Ensure that the new methods (copy, import, export, export_fields) in the CourseParticipant class are functioning correctly.


Test Cases:


Test Case 1: Get Quiz Questionnaires

Assertion:

Calling the endpoint to get quiz questionnaires should return a response with a status code of 200 and a JSON body containing an array of quiz questionnaires.

Steps:

1.Set up necessary data, including roles, an institution, a user, an assignment, and a participant.

2.Make a GET request to the /api/v1/quiz_questionnaires endpoint with the appropriate authorization header and content type.

3.Assert that the response status code is 200.

4.Assert that the response body contains an array with a size of 2, representing two quiz questionnaires.

Explanation:

This test case verifies that the API endpoint successfully retrieves quiz questionnaires and returns the expected response.

Test Case 2: Create Quiz Questionnaire

Assertion:

Making a POST request to create a quiz questionnaire with valid parameters should return a response with a status code of 201, and the response body should include the name of the created quiz questionnaire.

Steps:

1.Set up necessary data, including roles, an institution, a user, a team, and two quiz questionnaires.

2.Make a POST request to the /api/v1/quiz_questionnaires endpoint with valid parameters for creating a quiz questionnaire.

3.Assert that the response status code is 201.

4.Assert that the response body contains the name 'TestCreateQuizQ101'.

Explanation:

This test case ensures that the API endpoint can successfully create a quiz questionnaire with valid parameters.

Test Case 3: Handle Invalid Quiz Questionnaire Creation Params

Assertion:

Making a POST request to create a quiz questionnaire with invalid parameters should return a response with a status code of 422, indicating unprocessable entity due to invalid parameters.

Steps:

1.Set up necessary data, including roles, an institution, a user, and a team. 2.Make a POST request to the /api/v1/quiz_questionnaires endpoint with invalid parameters for creating a quiz questionnaire. 3.Assert that the response status code is 422.

Explanation:

This test case verifies that the API endpoint handles invalid parameters during quiz questionnaire creation and returns an appropriate response.

Test Case 4: Handle No Permission to Create Quiz Questionnaire

Assertion:

Making a POST request to create a quiz questionnaire without the required permission should return a response with a status code of 422, indicating unprocessable entity due to the lack of permission.

Steps:

1.Set up necessary data, including roles, an institution, a user, a team, and an assignment.

2.Make a POST request to the /api/v1/quiz_questionnaires endpoint with valid parameters but without the required permission.

3.Assert that the response status code is 422.

Explanation:

This test case ensures that the API endpoint checks for the required permission during quiz questionnaire creation and returns an appropriate response if permission is lacking.

Test Case 5: Handle Assignment Not Requiring Quiz

Assertion:

Making a POST request to create a quiz questionnaire for an assignment that does not require a quiz should return a response with a status code of 422, indicating unprocessable entity.

Steps:

1.Set up necessary data, including roles, an institution, a user, a team, and an assignment that does not require a quiz.

2.Make a POST request to the /api/v1/quiz_questionnaires endpoint with valid parameters for creating a quiz questionnaire.

3.Assert that the response status code is 422.

Explanation:

This test case ensures that the API endpoint correctly handles the creation of quiz questionnaires for assignments that do not require a quiz and returns an appropriate response.

Test Case 6: Copy Quiz Questionnaire

Assertion:

Making a POST request to copy a quiz questionnaire with a valid ID should return a response with a status code of 200, indicating successful copying.

Steps:

1.Set up necessary data, including roles, an institution, a user, and a quiz questionnaire to be copied.

2.Make a POST request to the /api/v1/quiz_questionnaires/copy/{id} endpoint with a valid ID for copying.

3.Assert that the response status code is 200.

Explanation:

This test case verifies that the API endpoint can successfully copy a quiz questionnaire with a valid ID.

Test Case 7: Handle Copying Nonexistent Quiz Questionnaire

Assertion:

Making a POST request to copy a nonexistent quiz questionnaire should return a response with a status code of 404, indicating not found.

Steps: 1.Set up necessary data, including roles, an institution, a user, and no quiz questionnaire with the specified ID.

2.Make a POST request to the /api/v1/quiz_questionnaires/copy/{id} endpoint with an invalid ID for copying.

3.Assert that the response status code is 404.

Explanation:

This test case ensures that the API endpoint handles the attempt to copy a nonexistent quiz questionnaire and returns an appropriate response.

Test Case 8: Retrieve Quiz Questionnaire

Assertion:

Making a GET request to retrieve details of a quiz questionnaire with a valid ID should return a response with a status code of 200, and the response body should contain the details of the quiz questionnaire.

Steps:

1.Set up necessary data, including roles, an institution, a user, and a quiz questionnaire.

2.Make a GET request to the /api/v1/quiz_questionnaires/{id} endpoint with a valid ID for retrieving details.

3.Assert that the response status code is 200.

4.Assert that the response body contains the details of the quiz questionnaire.

Explanation:

This test case verifies that the API endpoint can successfully retrieve details of a quiz questionnaire with a valid ID.

Test Case 9: Handle Retrieving Nonexistent Quiz Questionnaire

Assertion:

Making a GET request to retrieve details of a nonexistent quiz questionnaire should return a response with a status code of 404, indicating not found.

Steps:

1.Set up necessary data, including roles, an institution, a user, and no quiz questionnaire with the specified ID.

2.Make a GET request to the /api/v1/quiz_questionnaires/{id} endpoint with an invalid ID for retrieving details.

3.Assert that the response status code is 404.

Explanation:

This test case ensures that the API endpoint handles the attempt to retrieve details of a nonexistent quiz questionnaire and returns an appropriate response.

Test Case 10: Update Quiz Questionnaire

Assertion:

Making a PUT request to update a quiz questionnaire with valid parameters should return a response with a status code of 200, indicating successful updating.

Steps:

1.Set up necessary data, including roles, an institution, a user, and a quiz questionnaire.

2.Make a PUT request to the /api/v1/quiz_questionnaires/{id} endpoint with valid parameters for updating.

3.Assert that the response status code is 200.

Explanation:

This test case verifies that the API endpoint can successfully update a quiz questionnaire with valid parameters.

Test Case 11: Handling Invalid Questionnaire Parameters during Update

Assertion:

Return status code 422 if the questionnaire parameters are invalid during the update.

Steps:

1. Set up the necessary context and authorization token.

2. Prepare invalid questionnaire parameters with negative min_question_score, max_question_score greater than min_question_score, an invalid instructor_id, and a missing assignment_id.

3. Make a PUT request to update a quiz questionnaire with the provided invalid parameters.

4. Assert that the response status code is 422.

Explanation:

This test case ensures that the API returns a status code of 422 when attempting to update a quiz questionnaire with invalid parameters, such as negative min_question_score, max_question_score greater than min_question_score, an invalid instructor_id, and a missing assignment_id.


Test Case 12: Handling Lack of Permission during Questionnaire Update

Assertion:

Return status code 422 with an appropriate error message if the user lacks permission to update the quiz questionnaire.

Steps:

1. Set up the necessary context, including the authorization token.

2. Prepare valid questionnaire parameters for the update but with a user_id that lacks the required permission.

3. Make a PUT request to update a quiz questionnaire with the provided parameters and insufficient permissions.

4. Assert that the response status code is 422.

5. Verify that the error message indicates the requirement of permission to perform the update.

Explanation:

This test case ensures that the API returns a status code of 422 and a clear error message when attempting to update a quiz questionnaire without the necessary permission.

Test Case 13: Deleting a Quiz Questionnaire

Assertion:

The API endpoint should delete an existing quiz questionnaire.

Steps:

1. Make a DELETE request to the '/api/v1/quiz_questionnaires/{id}' endpoint with a valid quiz questionnaire ID.

2. Check if the response status code is 204.

3. Verify that the deleted quiz questionnaire no longer exists in the database.

Explanation:

This test case ensures that the API can successfully delete an existing quiz questionnaire.

Test Case 14: Handling Non-Existent Quiz Questionnaire during Copy

Assertion:

Return status code 404 with an appropriate error message if attempting to copy a quiz questionnaire with a non-existent ID.

Steps:

1. Set up the necessary context, including the authorization token.

2. Specify an ID that does not correspond to any quiz questionnaire in the database.

3. Make a POST request to copy a quiz questionnaire with the provided non-existent ID.

4. Assert that the response status code is 404.

5. Verify that the error message indicates the non-existence of a quiz questionnaire with the given ID.

Explanation:

This test case ensures that the API responds appropriately when attempting to copy a quiz questionnaire that does not exist in the database.

Test Case 15: Handling Deletion Permission

Assertion:

Return status code 422 with an appropriate error message if a user lacks permission to delete the specified quiz questionnaire.

Steps:

1. Set up the necessary context, including the authorization token.

2. Specify a quiz questionnaire ID and provide user credentials that lack the permission to delete.

3. Make a DELETE request to delete the quiz questionnaire with the given ID.

4. Assert that the response status code is 422.

5. Verify that the error message indicates the requirement of proper permission to delete the quiz questionnaire.

Explanation:

This test case ensures that the API handles deletion attempts appropriately, returning a status code 422 when the user lacks the necessary permission to delete a quiz questionnaire.

Program 4 Design Patterns Used

Design Principles in QuizQuestionnairesController.rb:

Single Responsibility Principle (SRP)

The QuizQuestionnairesController adheres to the Single Responsibility Principle (SRP) by ensuring that each of its actions is dedicated to a specific responsibility related to managing quiz questionnaires. The breakdown of responsibilities is as follows:

Index Action: Retrieves a list of quiz questionnaires.

Show Action: Retrieves details of a single quiz questionnaire.

Create Action: Creates a new quiz questionnaire based on provided parameters.

Update Action: Updates an existing quiz questionnaire.

Destroy Action: Deletes a quiz questionnaire.

Copy Action: Creates a copy of a quiz questionnaire.

This adherence to the SRP enhances maintainability and readability, making it easier to understand and modify each action independently.

Dependency Inversion Principle (DIP)

The Dependency Inversion Principle (DIP) is exemplified in the QuizQuestionnairesController through the use of ActiveRecord. Instead of directly depending on a specific database implementation, the controller relies on the ActiveRecord interface. This decouples the controller from the underlying database details, promoting flexibility and facilitating easier integration with different data storage solutions in the future.

By embracing ActiveRecord as an abstraction layer, the controller adheres to the DIP, allowing for a more modular and extensible architecture. This design choice enables easier testing, as the controller's interactions with the database are abstracted through a well-defined interface.

Design Principles in ReviewQuestionnaire.rb:

Single Responsibility Principle (SRP):

To uphold the Single Responsibility Principle, we plan to extract the logic related to assessments retrieval—specifically in the get_assessments_for and get_assessments_round_for methods—into a dedicated service or module. By doing so, we ensure that the ReviewQuestionnaire class maintains a single responsibility, focusing solely on the management of review questionnaires. This separation of concerns not only aligns with best practices but also contributes to clearer and more maintainable code.

Factory Method Pattern:

We recognize the potential need to instantiate different types of questionnaires in the future while maintaining a common interface. To address this, we plan to implement the Factory Method Pattern. This pattern will allow us to encapsulate the instantiation logic, providing flexibility in creating various questionnaire types without altering the client code.

Design Principles in MetaReviewQuestionnaire.rb:

Single Responsibility Principle (SRP):

In our ongoing efforts to enhance the maintainability and clarity of our codebase, we have identified the MetareviewQuestionnaire model as a candidate for refactoring. The model currently adheres well to the Single Responsibility Principle (SRP) by focusing on the management of metareview questionnaires. Each method within the model (post_initialization, symbol, get_assessments_for) appears to align with this singular responsibility.

Encapsulation:

To enhance encapsulation and follow best practices, we will encapsulate the class variable @print_name by providing an appropriate getter method. This step aims to hide the internal details of the class, promoting a cleaner and more maintainable code structure.

Factory Method Pattern:

We recognize the potential need to instantiate different types of questionnaires in the future while maintaining a common interface. To address this, we plan to implement the Factory Method Pattern. This pattern will allow us to encapsulate the instantiation logic, providing flexibility in creating various questionnaire types without altering the client code.

Design Principles in AssignmentQuestionnaire.rb:

Single Responsibility Principle (SRP):

The AssignmentQuestionnaire model currently handles both ActiveRecord associations and custom query methods. To adhere more closely to the SRP, we plan to separate these concerns into distinct modules or classes. This separation will not only enhance the readability of our code but also contribute to a more modular and organized structure.

Factory Method Pattern:

In cases where there are varied ways to instantiate AssignmentQuestionnaire instances, we recognize the potential benefits of applying the Factory Method Pattern. This pattern allows us to define an interface for creating instances in a superclass while enabling subclasses to alter the types of objects created.


Relevant Links

Github repository: https://github.com/rajmadhu0406/reimplementation-back-end

Pull request: https://github.com/expertiza/reimplementation-back-end/pull/48

Youtube video: https://youtu.be/tPK0-nbs-hI?si=MgWlrU1RWWTQfReO

Team

Mentor

Muhammad Ali Qureshi

Student Team

1] Raj Madhu (rmadhu@ncsu.edu)

2] Jinil Shukla (jshukla@ncsu.edu)

3] Dhyey Shah (dshah22@ncsu.edu)