CSC/ECE 517 Fall 2024 - E2470. Reimplement grades controller: Difference between revisions

From Expertiza_Wiki
Jump to navigation Jump to search
No edit summary
No edit summary
Line 62: Line 62:
** Updates the total score and comments for a team submission based on the received data. It finds the specified assignment, modifies the grade, and makes an attempt to save those changes. Upon failure it will provide an error message.  
** Updates the total score and comments for a team submission based on the received data. It finds the specified assignment, modifies the grade, and makes an attempt to save those changes. Upon failure it will provide an error message.  


===Rationale for Changes===
{| class="wikitable"
{| class="wikitable"
|-
|-
! Change
! Change
! Rationale
! Rationale
! Relevant commit(s)
|-
|-
| Refactored '''`action_allowed?`''' into '''`action_allowed`''', and added new helper methods
| Refactored '''`action_allowed?`''' into '''`action_allowed`''', and added new helper methods
| The '''`grades#action_allowed?`''' method was not being called anywhere in the backend, which means this functionality is only presently used by the frontend. As such, '''`action_allowed?`''' needed to become a Rails API method and endpoint, meaning that it no longer returned a boolean (which is why it was renamed). Now it is a GET request to the appropriate route.
| The '''`grades#action_allowed?`''' method was not being called anywhere in the backend, which means this functionality is only presently used by the frontend. As such, '''`action_allowed?`''' needed to become a Rails API method and endpoint, meaning that it no longer returned a boolean (which is why it was renamed). Now it is a GET request to the appropriate route.
| [https://github.com/expertiza/reimplementation-back-end/commit/da9ec47222ba52f1ff675723a4d4fa051b4393e6 Commit Link]
|-
|-
|Added '''`participant_scores`''' model
|Added '''`participant_scores`''' model
|Added a participant scores model to belong to an assignment, '''`assignment_participant`''' and '''`question`'''. A participant score also holds a '''`score`''', '''`total_score`''' and '''`round`'''.
|Added a participant scores model to belong to an assignment, '''`assignment_participant`''' and '''`question`'''. A participant score also holds a '''`score`''', '''`total_score`''' and '''`round`'''.
| [https://github.com/expertiza/reimplementation-back-end/commit/f9c353fad8e62e556398b0ec6905348ae7c35d36 Commit Link]
|-
|-
|Changed return types of all controller methods to render JSON Strings
|Changed return types of all controller methods to render JSON Strings
|As Rails API methods the easiest and expected way to communicate with the new frontend is by rendering appropriate JSON response strings with HTTP status codes appended, this can allow the frontend to parse and handle returned data.
|As Rails API methods the easiest and expected way to communicate with the new frontend is by rendering appropriate JSON response strings with HTTP status codes appended, this can allow the frontend to parse and handle returned data.
| [https://github.com/expertiza/reimplementation-back-end/pull/123/commits/c9bcab14340991847f574abfa8b13e641d476a1d Commit Link 1] [https://github.com/expertiza/reimplementation-back-end/pull/123/commits/1dcb5a1d124c1319757e8cea7c02c6a6d19e7cf7 Commit Link 2]
|-
|-
|Added a new suite of API endpoint tests that are compatible with Rswag and tested our API endpoints thoroughly, additionally added factories for several projects in the system.
|Added a new suite of API endpoint tests that are compatible with Rswag and tested our API endpoints thoroughly, additionally added factories for several projects in the system.
|As with any software change in a large system, testing is extremely important, so we wrote comprehensive tests for our endpoints.  Additionally, since the grades_controller is dependent on many other models (mainly because there is no grades model).  These changes will help future projects by providing factory methods for various models that did not currently have them in the system which should make testing for other groups easier in the future.
|As with any software change in a large system, testing is extremely important, so we wrote comprehensive tests for our endpoints.  Additionally, since the grades_controller is dependent on many other models (mainly because there is no grades model).  These changes will help future projects by providing factory methods for various models that did not currently have them in the system which should make testing for other groups easier in the future.
|[https://github.com/expertiza/reimplementation-back-end/commit/c9bcab14340991847f574abfa8b13e641d476a1d Commit Link 1] [https://github.com/expertiza/reimplementation-back-end/commit/13e23163e84a5255547d218b316b86836473c1ff Commit Link 2] [https://github.com/expertiza/reimplementation-back-end/commit/0731245f40bab6376313672f39bf66e2f9d7d427 Commit Link 3] [https://github.com/expertiza/reimplementation-back-end/commit/e8d14390fbeedbc0748a695c121b787b53867727 Commit Link 4] [https://github.com/expertiza/reimplementation-back-end/commit/28e5212bec820b9e92b449d0b84edee77bbbdf79 Commit Link 5] [https://github.com/expertiza/reimplementation-back-end/commit/a82bf077613077eb89d5a6ce0c7adc903d93c674 Commit Link 6] [https://github.com/expertiza/reimplementation-back-end/commit/385ab059443b9599d0abb4474d01b830116cb06f Commit Link 7] [https://github.com/expertiza/reimplementation-back-end/commit/7e8c53109d09f7dc4ce5d8074f56cfbc64614ba1 Commit Link 8] [https://github.com/expertiza/reimplementation-back-end/commit/bf569bcb662a35f0a30b83d28c8650bddea902d5 Commit Link 9] [https://github.com/expertiza/reimplementation-back-end/commit/8ca62a8d55d4a4729a2eabda2ae3a2341ac4038c Commit Link 10]
|-
|-
|Refactored all the main API endpoint methods, added new helper methods, and removed redundant methods
|Refactored all the main API endpoint methods, added new helper methods, and removed redundant methods
|Many of the methods were redundant and unused in the front end (all the chart methods). We removed all of those methods and reimplemented the logic for the view methods, as previously they did grade calculation within the '''grades_controller''', something that does not follow the best programming practices. Instead, we have the calculated elsewhere and just have '''grades_controller''' displaying all the heat map information on the front end
|Many of the methods were redundant and unused in the front end (all the chart methods). We removed all of those methods and reimplemented the logic for the view methods, as previously they did grade calculation within the '''grades_controller''', something that does not follow the best programming practices. Instead, we have the calculated elsewhere and just have '''grades_controller''' displaying all the heat map information on the front end
|[https://github.com/expertiza/reimplementation-back-end/commit/911d861a634d69bf8056698249be70e85db186e9  Commit Link 1] [https://github.com/expertiza/reimplementation-back-end/commit/a374d3b5aa4d6dbc618dc2984633939f7c2dde7b Commit Link 2] [https://github.com/expertiza/reimplementation-back-end/commit/c524f1cfa36b74b7cfeceae68f6c81259f82c0ee Commit Link 3] [https://github.com/expertiza/reimplementation-back-end/commit/37866b6abeaea1da01dd52fb211e0cde5e6584c4 Commit Link 4] [https://github.com/expertiza/reimplementation-back-end/commit/911d861a634d69bf8056698249be70e85db186e9 Commit Link 5] [https://github.com/expertiza/reimplementation-back-end/commit/8323c30038f3bb05611b8ce2262e889194135f44 Commit Link 6]
|-
|-
|Overhauled method comment documentation replaced with correct comments that describe what the method does, and did a quick style pass to ensure code readability
|Overhauled method comment documentation replaced with correct comments that describe what the method does, and did a quick style pass to ensure code readability
|A lot of the comments within the '''grades_controller''' were not very good, some of which were outright incorrect or at the very least we're not correct to the current implementation of the controller at the time that we started it.  So updating all of the documentation to be accurate and reflect the current state of the controller after our changes was a necessity, trying to aim for a high understanding of what each method does without even needing to read the code for future work on the codebase.  Additionally, code readability was an issue in the old controller, primarily due to long or dense lines, we made an effort to limit these issues and promote clean, readable, and maintainable code.
|A lot of the comments within the '''grades_controller''' were not very good, some of which were outright incorrect or at the very least we're not correct to the current implementation of the controller at the time that we started it.  So updating all of the documentation to be accurate and reflect the current state of the controller after our changes was a necessity, trying to aim for a high understanding of what each method does without even needing to read the code for future work on the codebase.  Additionally, code readability was an issue in the old controller, primarily due to long or dense lines, we made an effort to limit these issues and promote clean, readable, and maintainable code.
|[https://github.com/expertiza/reimplementation-back-end/commit/182337179691819f9e16c985ceee4c20c3a5efcd Commit Link 1] [https://github.com/expertiza/reimplementation-back-end/commit/68272005c0a60e3a1476b2b69fec2372c915fd7a Commit Link 2] [https://github.com/expertiza/reimplementation-back-end/commit/9d305d96429509462058c772fed7cf9b069edc08 Commit Link 3] [https://github.com/expertiza/reimplementation-back-end/commit/141476315f950cdf6dd1ee777230c23313c4048e Commit Link 4]
|}
|}
===Code Snippet===
<pre>
# Determines if the current user is able to perform :action as specified by the path parameter
  # If the user has the role of TA or higher they are granted access to all operations beyond view_team
  # Uses a switch statement for easy maintainability if added functionality is ever needed for students or
  # additional roles, to add more functionality simply add additional switch cases in the same syntax with
  # case 'action' and then some boolean check determining if that is allowed or forbidden.
  # GET /api/v1/grades/:action/action_allowed
  def action_allowed
    permitted = case params[:action]
                when 'view_team'
                  view_team_allowed?
                else
                  user_ta_privileges?
                end
    render json: { allowed: permitted }, status: permitted ? :ok : :forbidden
  end
  # Provides the needed functionality of querying needed values from the backend db and returning them to build the
  # heat map in the frontend from the TA/staff view.  These values are set in the get_data_for_heat_map method
  # which takes the assignment id as a parameter.
  # GET /api/v1/grades/:id/view
  def view
    get_data_for_heat_map(params[:id])
    render json: { scores: @scores, assignment: @assignment, averages: @averages, avg_of_avg: @avg_of_avg,
                  review_score_count: @review_score_count }, status: :ok
  end
  # Provides all relevant data for the student perspective for the heat map page as well as the
  # needed information to showcase the questionnaires from the student view.  Additionally, handles the removal of user
  # identification in the reviews within the hide_reviewers_rom_student method.
  # GET /api/v1/grades/:id/view_team
  def view_team
    get_data_for_heat_map(params[:id])
    @scores[:participants] = hide_reviewers_from_student
    questionnaires = @assignment.questionnaires
    questions = retrieve_questions(questionnaires, @assignment.id)
    render json: {scores: @scores, assignment: @assignment, averages: @averages, avg_of_avg: @avg_of_avg,
                  review_score_count: @review_score_count, questions: questions }, status: :ok
  end
  # Sets information required for editing the grade information, this includes the participant, questions, scores, and
  # assignment
  # GET /api/v1/grades/:id/edit
  def edit
    begin
      participant = AssignmentParticipant.find(params[:id])
    rescue ActiveRecord::RecordNotFound
      render json: {message: "Assignment participant #{params[:id]} not found"}, status: :not_found
      return
    end
    assignment = participant.assignment
    questions = list_questions(assignment)
    scores = review_grades(assignment, questions)
    render json: {participant: participant, questions: questions, scores: scores, assignment: assignment}, status: :ok
  end
  # Provides functionality that handles informing the frontend which controller and action to direct to for instructor
  # review given the current state of the system.  The intended controller to handle the creation or editing of a review
  # is the response controller, however this method just determines if a new review must be made based on figuring out
  # whether or not an associated review_mapping exists from the participant already.  If one does they should go to
  # Response#edit and if one does not they should go to Response#new.  Only ever returns a status of ok.
  # GET /api/v1/grades/:id/instructor_review
  def instructor_review
    begin
      participant = AssignmentParticipant.find(params[:id])
    rescue ActiveRecord::RecordNotFound
      render json: { message: "Assignment participant #{params[:id]} not found" }, status: :not_found
      return
    end
   
    review_mapping = find_participant_review_mapping(participant)
    if review_mapping.new_record?
      render json: { controller: 'response', action: 'new', id: review_mapping.map_id,
                    return: 'instructor'}, status: :ok
    else
      review = Response.find_by(map_id: review_mapping.map_id)
      render json: { controller: 'response', action: 'edit', id: review.id, return: 'instructor'}, status: :ok
    end
  end
  # Update method for the grade associated with a team, allows an instructor to upgrade a team's grade with a grade
  # and a comment on their assignment for submission.  The team is then saved with this change in order to be accessed
  # elsewhere in the code for needed scoring evaluations.  If a failure occurs while saving the team then this will
  # return a bad_request response complete with a message and the global ERROR_INFO which can be set elsewhere for
  # further error handling mechanisms
  # PATCH /api/v1/grades/:participant_id/update/:grade_for_submission
  def update
    participant = AssignmentParticipant.find_by(id: params[:participant_id])
    team = participant.team
    team.grade_for_submission = params[:grade_for_submission]
    team.comment_for_submission = params[:comment_for_submission]
    begin
      team.save
    rescue StandardError => e
      render json: {message: "Error occurred while updating grade for team #{team.id}",
                    error: e.message }, status: :bad_request
      return
    end
    render json: { controller: 'grades', action: 'view_team', id: participant.id}, status: :ok
  end
</pre>


===Testing Details===
===Testing Details===

Revision as of 02:15, 30 October 2024

E2470. Reimplement grades controller

This page provides a description of the Expertiza based OSS project.



Link to Pull Request

Swagger Video Submission

About Expertiza

Expertiza is an open source project utilizing the Ruby on Rails framework. It is meant to serve as an environment for classes to host assignments, teams, and evaluations of submissions. It is designed to provide instructors the ability to create and modify assignments. Instructors have access to viewing all completed assignments and grades given as well. Additionally, it allows the instructor to provide topic lists that students can access to determine which projects they sign up for. Students are able to form teams for projects and assignments, and during each they can review both peers and other submissions from teams. Expertiza is designed to support submission types ranging from URLs to varying documents.

Introduction

The purpose of this project is to refactor grade_controller.rb, which is responsible for all grading functionality within Expertiza. Its main purpose is to enable instructors to view all grades for an assignment, and allow students to view their own grades. Our main focus is to streamline functionality, remove redundancies, and provide more clarity to this refactored class.

Problem Statement

The following tasks have been completed in this assignment:

  • Controller Refactoring:
    • Reimplement the existing grades_controller.rb to make it more modular, reusable, and compliant with the DRY (Don’t Repeat Yourself) principle.
    • Improve the readability and maintainability of the codebase, ensuring it is easily understandable for future developers.
    • Refactor code to eliminate unnecessary repetition and reduce complexity by adhering to SOLID design principles.
  • CRUD Operations:
    • Ensure that the required CRUD operations (Read, Update) are properly implemented and optimized.
    • Update methods to reflect best practices and consistent error handling mechanisms.

Previous Implementation

  • One of the first major concerns we noticed was the reliance on an excessive amount of helper classes. Helper classes were being defined and provided to the grades_controller, but no other class actually used them. It could be more consistent to keep that functionality stored within helper methods local to the class.
  • Functions such as view/view_my_scores/view_team would contain calculations and functionality beyond the purpose of the method, which should be delegated to private methods to preserve modularity.
  • The class contained obsolete variables in multiple methods which could be cleaned up.
  • Chart methodology is contained within the backend which can now be delegated to the front end, since the controller should only be responsible for grading functionality and returning appropriate data. Model data should be provided to the front end.
  • Penalty calculations are currently no longer relevant for the grading controller.
  • There are currently no render statements for appropriately providing data to the front end.

Our Implementation

Our Goals

  • Simplify the code structure in order to enhance readability by taking complex operations and unneeded local variable assignments into private helper methods within the grades_controller.
  • Enforce the intended functionality of the grades_controller by removing unneeded functionality and clutter, some of which is the responsibility of other controllers (i.e. calculating scores and penalties) or the frontend (i.e. rendering the bar chart information). The functionalities of the grades_controller are as follows:
    • Verify the user to ensure they are permitted to view the particular page they are looking for with the action_allowed controller method
    • Provide needed information for the grade heatmap from the instructor's POV, with no hidden information such as reviewers id’s or names
    • Provide needed information for the grade heatmap from the student's POV which obscures information such as the reviewer name/id
    • Update the student's grade and make comments on it from the instructor's POV
  • Cut down on repeated code to adhere to the DRY principle in order to improve maintainability and consistency within the code.
  • Update the return values of the grades_controller methods in order to provide needed information and HTTP response codes that consistently reflect state and errors, as well as provide the required information for frontend tasks such as making the heatmap itself.

Routes and Methods

  • GET /api/v1/grades/action_allowed – action_allowed
    • Checks if the current user is allowed to view scores or team information based on the queried action. Through helpers it focuses on checking if a student is viewing their own team’s scores, or if it’s an instructor trying to access grades. It renders a JSON response with status codes based on resulting output.
  • GET /api/v1/grades/view/:id – view
    • Prepares and provides data required for rendering a heat map for an instructor’s point of view. The helper method gathers all the relevant data before providing it in a JSON response with the scores, assignment details, average scores, and review score count.
  • GET /api/v1/grades/view_team/:id – view_team
    • Serves a similar function as the view statement, but focusing purely on the student’s perspective of their team. It provides data for rendering a heat map, but hides any sensitive information pertaining to grading, while also acquiring questions from the assignment. It renders a JSON response containing scores, assignment details, average scores, review score count, and questions.
  • GET /api/v1/grades/edit/:id – edit
    • Represents functionality for editing grade information, setting the scores for every question after listing the questions out. Renders a JSON response with details about the participant, questions, scores, and assignment.
  • GET /api/v1/grades/instructor_review/:id – instructor_review
    • Provides the instructor with a rendered JSON response on whether there’s a new record or preexisting instance of a review.
  • PATCH /api/v1/grades/update/:participant_id – update
    • Updates the total score and comments for a team submission based on the received data. It finds the specified assignment, modifies the grade, and makes an attempt to save those changes. Upon failure it will provide an error message.

Rationale for Changes

Change Rationale
Refactored `action_allowed?` into `action_allowed`, and added new helper methods The `grades#action_allowed?` method was not being called anywhere in the backend, which means this functionality is only presently used by the frontend. As such, `action_allowed?` needed to become a Rails API method and endpoint, meaning that it no longer returned a boolean (which is why it was renamed). Now it is a GET request to the appropriate route.
Added `participant_scores` model Added a participant scores model to belong to an assignment, `assignment_participant` and `question`. A participant score also holds a `score`, `total_score` and `round`.
Changed return types of all controller methods to render JSON Strings As Rails API methods the easiest and expected way to communicate with the new frontend is by rendering appropriate JSON response strings with HTTP status codes appended, this can allow the frontend to parse and handle returned data.
Added a new suite of API endpoint tests that are compatible with Rswag and tested our API endpoints thoroughly, additionally added factories for several projects in the system. As with any software change in a large system, testing is extremely important, so we wrote comprehensive tests for our endpoints. Additionally, since the grades_controller is dependent on many other models (mainly because there is no grades model). These changes will help future projects by providing factory methods for various models that did not currently have them in the system which should make testing for other groups easier in the future.
Refactored all the main API endpoint methods, added new helper methods, and removed redundant methods Many of the methods were redundant and unused in the front end (all the chart methods). We removed all of those methods and reimplemented the logic for the view methods, as previously they did grade calculation within the grades_controller, something that does not follow the best programming practices. Instead, we have the calculated elsewhere and just have grades_controller displaying all the heat map information on the front end
Overhauled method comment documentation replaced with correct comments that describe what the method does, and did a quick style pass to ensure code readability A lot of the comments within the grades_controller were not very good, some of which were outright incorrect or at the very least we're not correct to the current implementation of the controller at the time that we started it. So updating all of the documentation to be accurate and reflect the current state of the controller after our changes was a necessity, trying to aim for a high understanding of what each method does without even needing to read the code for future work on the codebase. Additionally, code readability was an issue in the old controller, primarily due to long or dense lines, we made an effort to limit these issues and promote clean, readable, and maintainable code.

Code Snippet

# Determines if the current user is able to perform :action as specified by the path parameter
  # If the user has the role of TA or higher they are granted access to all operations beyond view_team
  # Uses a switch statement for easy maintainability if added functionality is ever needed for students or
  # additional roles, to add more functionality simply add additional switch cases in the same syntax with
  # case 'action' and then some boolean check determining if that is allowed or forbidden.
  # GET /api/v1/grades/:action/action_allowed
  def action_allowed
    permitted = case params[:action]
                when 'view_team'
                  view_team_allowed?
                else
                  user_ta_privileges?
                end
    render json: { allowed: permitted }, status: permitted ? :ok : :forbidden
  end

  # Provides the needed functionality of querying needed values from the backend db and returning them to build the
  # heat map in the frontend from the TA/staff view.  These values are set in the get_data_for_heat_map method
  # which takes the assignment id as a parameter.
  # GET /api/v1/grades/:id/view
  def view
    get_data_for_heat_map(params[:id])
    render json: { scores: @scores, assignment: @assignment, averages: @averages, avg_of_avg: @avg_of_avg,
                   review_score_count: @review_score_count }, status: :ok
  end

  # Provides all relevant data for the student perspective for the heat map page as well as the
  # needed information to showcase the questionnaires from the student view.  Additionally, handles the removal of user
  # identification in the reviews within the hide_reviewers_rom_student method.
  # GET /api/v1/grades/:id/view_team
  def view_team
    get_data_for_heat_map(params[:id])
    @scores[:participants] = hide_reviewers_from_student
    questionnaires = @assignment.questionnaires
    questions = retrieve_questions(questionnaires, @assignment.id)
    render json: {scores: @scores, assignment: @assignment, averages: @averages, avg_of_avg: @avg_of_avg,
                  review_score_count: @review_score_count, questions: questions }, status: :ok
  end

  # Sets information required for editing the grade information, this includes the participant, questions, scores, and
  # assignment
  # GET /api/v1/grades/:id/edit
  def edit
    begin
      participant = AssignmentParticipant.find(params[:id])
    rescue ActiveRecord::RecordNotFound
      render json: {message: "Assignment participant #{params[:id]} not found"}, status: :not_found
      return
    end
    assignment = participant.assignment
    questions = list_questions(assignment)
    scores = review_grades(assignment, questions)
    render json: {participant: participant, questions: questions, scores: scores, assignment: assignment}, status: :ok
  end

  # Provides functionality that handles informing the frontend which controller and action to direct to for instructor
  # review given the current state of the system.  The intended controller to handle the creation or editing of a review
  # is the response controller, however this method just determines if a new review must be made based on figuring out
  # whether or not an associated review_mapping exists from the participant already.  If one does they should go to
  # Response#edit and if one does not they should go to Response#new.  Only ever returns a status of ok.
  # GET /api/v1/grades/:id/instructor_review
  def instructor_review
    begin
      participant = AssignmentParticipant.find(params[:id])
    rescue ActiveRecord::RecordNotFound
      render json: { message: "Assignment participant #{params[:id]} not found" }, status: :not_found
      return
    end
    
    review_mapping = find_participant_review_mapping(participant)
    if review_mapping.new_record?
      render json: { controller: 'response', action: 'new', id: review_mapping.map_id,
                     return: 'instructor'}, status: :ok
    else
      review = Response.find_by(map_id: review_mapping.map_id)
      render json: { controller: 'response', action: 'edit', id: review.id, return: 'instructor'}, status: :ok
    end
  end

  # Update method for the grade associated with a team, allows an instructor to upgrade a team's grade with a grade
  # and a comment on their assignment for submission.  The team is then saved with this change in order to be accessed
  # elsewhere in the code for needed scoring evaluations.  If a failure occurs while saving the team then this will
  # return a bad_request response complete with a message and the global ERROR_INFO which can be set elsewhere for
  # further error handling mechanisms
  # PATCH /api/v1/grades/:participant_id/update/:grade_for_submission
  def update
    participant = AssignmentParticipant.find_by(id: params[:participant_id])

    team = participant.team
    team.grade_for_submission = params[:grade_for_submission]
    team.comment_for_submission = params[:comment_for_submission]
    begin
      team.save
    rescue StandardError => e
      render json: {message: "Error occurred while updating grade for team #{team.id}",
                    error: e.message }, status: :bad_request
      return
    end
    render json: { controller: 'grades', action: 'view_team', id: participant.id}, status: :ok
  end

Testing Details

The test file can be located at:

spec/requests/api/v1/grades_controller_spec.rb
  • action_allowed
    • Passes in the view action and an assignment we wish to view. Determines if the user has the appropriate permissions to view it.
  • view
    • Passes in the id of the assignment and expects the scores, averages, avg_of_avg, review_score_count.
  • view_team
    • Pasess in the assignment id and expects the scores, averages, avg_of_avg, review_score_count.
  • edit
    • Passes in the id of the assignment and expects the participant's id, the same assignment's id, questions, and scores.
  • instructor_review
    • Passes in the id of a participant and expects controller, action, the same participant id, and the instructor.
  • update
    • Passes in a participant id and a body which contains grade_for_submission (integer) and comment_for_submission (string). Expects the same grade, comment, action, and participant's id.

Rswag UI An image showing the rswag ui of accepted test results.

Team

Mentor

  • Srusti, Chaitanya

Members

  • Eastin, Charlie
  • Hulse, Jeremy
  • Middleton, Maverick

Previous Iterations

  • Spring 2024
    • This iteration was not approved to be pulled into expertiza, but provided our team with additional insight on how to more appropriately refactor the grades controller.
  • Spring 2021
    • Added additional methodology for providing model data, along with a greater focus on helper classes.
  • Fall 2017
    • Refactored penalties, review systems, and utilized rspec testing.