CSC/ECE 517 Fall 2016/E1643. Refactor Suggestion controller
E1643. Refactor and Test Suggestion Controller
This page gives a detail of the OSS project of refactoring and testing the suggestion controller of Expertiza.
Introduction
Expertiza is a Ruby on Rails based open source project. The main motive of this project is to make learning more effective through peer review. This website is a result of combined effort of both students and faculty at NC State, and is used not just by this university but also in many other universities. The website allows students to form teams and work on various projects listed by the instructor and also suggest new topics that seem interesting, though they can opt not to work on them. It also makes it easy for the instructor to add a new topic to an assignment/project, create a new project and add students to it. The time spent by TAs and instructor is greatly reduced. The key feature is peer review, where the students can review the work of others and provide feedback. This helps in improving the existing work and also provides a new way to learn. There isn’t any restriction on the format of submission as it accepts any form of submission varying from URL to wiki pages, which isn’t a common feature in other websites.
Motivation
This provides a great opportunity for the students to learn through collaboration. It provides a chance to contribute to an open source project. One would take back experience of working on Rails, and testing environments like RSpec. Being one of the primary user of Expertiza, students would enhance the functionalities according to their experiences using it and can view their changes implemented real-time.
Problem Statement
Our files to be modified are: app/views/mailer/suggested_topic_approved_message.html.erb, suggestion_controller_spec.rb
The current folder of suggestion_controller.rb provides a chance to suggest a new topic to work on for a project. There is also an option for the student to not work on it. One can also submit the suggestion anonymously. Once a student submits the topic, the instructor can check that in the view suggestions tab, and can either approve or reject. Once the instructor approves, the student gets a mail regarding the approval. This mail is sent only if the student doesn’t submit the topic anonymously. In the process of assigning the given suggestion as a project topic to the student, it automatically gets assigned to the whole team if the student is part of a team.
Our problem statement includes:
1. Modifying the code in accordance to rails 4 syntax
2. Send email code which was duplicated needs to be replaced by a single method
3. Fix and test the working of email functionality (an email is sent to the student who suggested the topic once the instructor approves, unless he/she sends it anonymously)
4. Write integration tests for each method in suggestion_controller.rb (including some edge cases)
Setup
Before starting off with working on the Expertiza project, we need to fork the existing code from expertiza/master branch. We are provided with 3 methods of setting up Expertiza: Docker, setting it up locally and using Expertiza image. We are describing the first two methods (the ones we used) below.
Docker
The Docker has been setup on a Windows PC and steps are given below
Start Docker on Windows docker run --expose 3000 -p 3000:3000 -v //c//Users//Srikar//Expertiza://c//Users//Srikar//Expertiza -it winbobob/expertiza-fall2016 /etc/init.d/mysql start mysql -uroot -p show databases; quit git clone https://github.com/srikarpotta/expertiza.git cd expertiza cp config/database.yml.example config/database.yml cp config/secrets.yml.example config/secrets.yml bundle install rake db:migrate sudo apt-get install npm npm install -g bower sudo rm /usr/bin/node sudo ln –s /usr/bin/nodejs /usr/bin/node bower install --allow-root thin start
On a Local Machine
We have used MacOS, so the following steps are in regard to MacOS. The following steps will help you setup Expertiza project in your local machine. The steps are comprehensive amalgamation of steps mentioned in Development Setup, the documentprovided and also few steps that were missed in both. The order we followed:
#Fork the git repository mentioned above #Clone the repository to your local machine Install [http://brew.sh/ Homebrew] #Install RBENV brew update brew install rbenv brew install ruby-build #Install dependencies brew install aspell gcc47 libxml2 libxslt graphviz #Install gems export JAVA_HOME=/etc/alternatives/java_sdk bundle install #Change yml files #Go to expertiza/config and rename secrets.yml.example to secrets.yml #Go to expertiza/config and rename database.yml.example to database.yml #Edit database.yml to include the root password for your local MySQL in the “password” field #Install mysql (https://gist.github.com/nrollr/a8d156206fa1e53c6cd6) #Log into MySql as root (mysql is generally present in /usr/local/mysql/bin/) mysql -uroot -p #Create expertiza user create user expertiza@localhost; #Create the databases create database pg_development; create database pg_test; #Set privileges for expertiza user grant all on pg_development.to expertiza@localhost; grant all on pg_test.to expertiza@localhost; #Install javascript libraries sudo apt-get install npm sudo npm install bower bower install #Download the expertiza scrubbed library (https://drive.google.com/file/d/0B2vDvVjH76uEMDJhNjZVOUFTWmM/view) #Load this sql file into pg_development database created using the method mentioned here. #Run bundle exec rake db:migrate #Run bundle exec rake db:test:prepare #Run rails s #Open browser and test localhost:3000 #Login credentials Username - instructor6 Password - password
Our Implementation
There weren't any test cases before and also the email functionality wasn't working. We have fixed the email functionality and also refactored parts of the code. As per our knowledge we couldn't find any code in accordance to Ruby 2 syntax.
Refactoring
Testing
We were tasked with writing integration test cases for suggestion_controller. We came up with 6 end-to-end test cases to test “integration” of suggestion controller with other models, controllers and views. The test script can be found here.
Prerequisite
All the scenarios uses the following:
- Instructor6
- Student2064
- Assignment 1
Scenario 1
Instructor6 logs in and visits assignment 1 to check suggested topics (currently empty)
scenario "allow instructor to log in and view suggestions (suggestions should be empty) for Assignment 1" do user = User.find_by_name('instructor6') stub_current_user(user, user.role.name, user.role) visit '/suggestion/list?id=1&type=Assignment' expect(page).to have_content "Suggested topics for Assignment 1" expect(page).to have_no_content "Computer Vision" end
Scenario 2
Student2064 logs in -> Visits on Assignment 1 -> Clicks on new suggestion -> Submits new topic called “Computer Vision” -> Checks submission is successful -> Adds comment -> Submits comment -> Checks successful submission of comment -> Tries submitting blank comment -> Checks unsuccessful submission of blank comment -> Tries editing suggestion title and suggestion description -> Checks edit is successful -> Logs out successfully
# Create new suggestion (Computer Vision) fill_in 'suggestion_title', with: 'Computer Vision' fill_in 'suggestion_description', with: 'This is a Computer Vision suggestion' select "N", :from => "suggestion_signup_preference" click_button 'Submit' expect(page).to have_content "Thank you for your suggestion!" expect(page).to have_content "Suggested topics for Assignment 1" expect(page).to have_content "Computer Vision" expect(page).to have_content "Initiated" # View the suggestion find_link('View').click expect(page).to have_content "View Suggested topic Computer Vision" # Add comment fill_in 'suggestion_comment_comments', with: 'Student2064 commenting on Computer Vision' click_button 'Submit comment' expect(page).to have_content "Your comment has been successfully added." expect(page).to have_content "Student2064 commenting on Computer Vision" # Try adding blank comment click_button 'Submit comment' expect(page).to have_content "There was an error adding your comment." # Edit title and description find_link('Edit').click expect(page).to have_content "Edit Suggested topic Computer Vision" fill_in 'suggestion_title', with: 'Computer Vision 2' fill_in 'suggestion_description', with: 'This is a Computer Vision suggestion 2' select "Y", :from => "suggestion_signup_preference" click_button 'Submit' expect(page).to have_content "Suggested topics for Assignment 1" expect(page).to have_content "Computer Vision 2"
Other scenarios that were tested are given below
Scenario 3
Student2064 logs in and suggests a topic (Computer Vision) under Assignment 1 -> Instructor6 logs in and checks on Assignment 1 -> Checks that “Computer Vision” is submitted by student2064 -> Checks comment by student2064 -> Instructor6 approves the suggestion -> Student2064 logs in -> Visits Assignment 1 -> Checks suggestion “Computer Vision” is accepted
Scenario 4
Student2064 logs in and suggests a topic (Computer Vision) under Assignment 1 -> Instructor6 logs in and checks on Assignment 1 -> Checks that “Computer Vision” is submitted by student2064 -> Checks comment by student2064 -> Instructor6 rejects the suggestion -> Student2064 logs in -> Visits Assignment 1 -> Checks suggestion “Computer Vision” is rejected
Scenario 5
Student2064 logs in and suggests a topic (Computer Vision) under Assignment 1 ->Instructor6 logs in and checks on Assignment 1 -> Checks that “Computer Vision” is submitted by student2064 -> Checks comment by student2064 -> Instructor votes for the suggestion -> Student2064 logs in -> Visits Assignment 1 -> Checks Instructor6 has voted for the suggestion
Scenario 6
Student2064 logs in and visits Assignment 1 -> Suggests “Computer Vision” -> Select “No” for suggestion signup preference -> Submits suggestion -> Instructor6 logs in and visits Assignment 1 suggestions -> Approves suggestion “Computer Vision” -> Checks suggestion approved successfully
Why these scenarios?
The scenarios are carefully designed to fulfil the following criteria: Test the integration of core functionalities of suggestion controller Have maximum code coverage Not to repeat scenarios developed by another contributor in topic_suggestion_spec.rb
Conclusions
What we learnt
- How to read existing codebases
- Understand other people’s code before contributing
- Refactor existing code without breaking existing functionalities
- Write integration test cases
What’s next?
“Program testing can be a very effective way to show the presence of bugs, but is hopelessly inadequate for showing their absence.” - Edsger Dijkstra
Thus, the best way to uncover bugs lurking in our code is to come up with more scenarios and implement them. We have tested the most business critical scenarios and few edge cases were covered by creators of topic_suggestion_spec.rb. They only show the absence of bugs in the routes we are following to reach from point A to point B. However, many such scenarios exists which are not yet covered. We hope to extend our work further in future to cover many such scenarios.