<?xml version="1.0"?>
<feed xmlns="http://www.w3.org/2005/Atom" xml:lang="en">
	<id>https://wiki.expertiza.ncsu.edu/api.php?action=feedcontributions&amp;feedformat=atom&amp;user=Vdatla</id>
	<title>Expertiza_Wiki - User contributions [en]</title>
	<link rel="self" type="application/atom+xml" href="https://wiki.expertiza.ncsu.edu/api.php?action=feedcontributions&amp;feedformat=atom&amp;user=Vdatla"/>
	<link rel="alternate" type="text/html" href="https://wiki.expertiza.ncsu.edu/index.php?title=Special:Contributions/Vdatla"/>
	<updated>2026-05-16T09:55:16Z</updated>
	<subtitle>User contributions</subtitle>
	<generator>MediaWiki 1.41.0</generator>
	<entry>
		<id>https://wiki.expertiza.ncsu.edu/index.php?title=CSC/ECE_517_Fall_2016/E1690_Improvements_to_password_recovery_and_repeated_login_failures&amp;diff=106083</id>
		<title>CSC/ECE 517 Fall 2016/E1690 Improvements to password recovery and repeated login failures</title>
		<link rel="alternate" type="text/html" href="https://wiki.expertiza.ncsu.edu/index.php?title=CSC/ECE_517_Fall_2016/E1690_Improvements_to_password_recovery_and_repeated_login_failures&amp;diff=106083"/>
		<updated>2016-12-02T20:38:42Z</updated>

		<summary type="html">&lt;p&gt;Vdatla: /* Password Reset */&lt;/p&gt;
&lt;hr /&gt;
&lt;div&gt;==E1690 Improvements to password recovery and repeated login failures==&lt;br /&gt;
&lt;br /&gt;
This wiki page is for the description of changes made under E1690 FinalProject for Fall 2016, CSC/ECE 517.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
__TOC__&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
===Background===&lt;br /&gt;
&lt;br /&gt;
Expertiza is an Open Source web application developed on Ruby On Rails platform. It is a platform which allows students to access assignments posted by the course instructor. Expertiza also allows students to select assignment topics, form teams and submit their work. It also allows them to review other students' submissions and improve their work based on the feedback provided. The instructor can look at the feedback provided by students and rate the student based on feedback provided for others work.&lt;br /&gt;
It helps organize and upload assignments and reducing the manual review process and helps students provide a peer feedback and also learn from reviewed work. Teams can be chosen by the student or can be assigned automatically based on a priority list inputted alongside each topic available for the assignment.&lt;br /&gt;
&lt;br /&gt;
===Project Description===&lt;br /&gt;
&lt;br /&gt;
Our final project consists of two cases of the password recovery process. Use case 1, Currently, when a user forgets his/her password and wants to reset the password, Expertiza system randomly generates a new password and sends the password as plain text in a email. It is normally considered as a bad practice to send passwords as paint text. We are replacing this practice by sending a reset password link that expires after a certain amount of time. Use case 2 deals with when a user enters wrong credentials. Currently, the login page simply shows an error. Irrespective of the number of times that a user enters wrong login credentials, the system produces a general error message. We are going to be replacing this system by using the alternative 2, using a captcha to verify that the user is indeed a human and not a bot trying to run a brute force attack on the system. This will add the needed layer of security and should serve as a great solution. Below are more details of our implementation. &lt;br /&gt;
&lt;br /&gt;
===Files Created/Modified===&lt;br /&gt;
As a part of the project the files mentioned below were the ones, created/modified as needed.&lt;br /&gt;
* auth_controller.rb&lt;br /&gt;
* password_retrieval_controller.rb &lt;br /&gt;
* password_reset.rb (model)&lt;br /&gt;
* reset_password.html.erb (view)&lt;br /&gt;
&lt;br /&gt;
===Implementation===&lt;br /&gt;
We have implemented the new password recovery system by sending a reset password link to the user's email. This link will be comprised of a generated path to a newly created view for resetting the password with a uniquely randomly generated token. This parameter will be a string attribute of a new model reset_password. This link will expire after a given amount of time. Using logic to compare the createdAt timestamp as well as the current time, the application would decide if the token is expired or not.&lt;br /&gt;
&lt;br /&gt;
We are also implementing a backoff system that will require the user to complete a smart captcha after 3 failed attempts. This smart captcha will be generated through Recaptcha gem and the user will then be redirected to the login page after successfully changing the password. This will ensure that the system is not vulnerable to Brute Force attacks as well as bots.&lt;br /&gt;
&lt;br /&gt;
==Password Reset==&lt;br /&gt;
&lt;br /&gt;
===Model Schema===&lt;br /&gt;
Model: password_reset.rb&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
Attributes&lt;br /&gt;
*-id(autogenerated) -integer&lt;br /&gt;
*-unique_tokenhash -String&lt;br /&gt;
*-createdAt (autogenerated) -timestamp&lt;br /&gt;
*-user_email -string&lt;br /&gt;
&lt;br /&gt;
'''Model Details'''&lt;br /&gt;
&lt;br /&gt;
When the user clicks on reset password, it will redirect to a view that has an input to enter the email address of the user. Reset password button will generate a random token (Long string) which will be hashed and saved in the database of the model reset_password. An expiration date will be generated and saved along with the user_id by looking up the user table using email id. The unhashed Token value will be appended on the url emailed to the user for the password reset page.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
www.expertiza.com/password_edit/check_reset_url?token=ZB71yObR-Tdssg-@#%&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
On clicking the url, the link will take you to password_retrieval_controller that will direct you to a reset page. Before redirecting , the controller checks the parameters in the link (username and token) and makes sure that token username pair exists and not expired. Token from the params will be hashed again and checked with the DB. This prevents an attacker who has read access to the database from making a token for some other user, reading the value that was sent in the email, then sending the same value himself. Once the controller completes all the necessary checks, it will redirect to a reset password page for that specific user (based on the user_id / username) &lt;br /&gt;
&lt;br /&gt;
Each Email Address can have only one active token saved in the database. Every time a new token is generated, it will replace the existing one which ensures that only one reset link is available. Also, this will make sure that DB content of password_reset can never exceed the number of users registered in the application. This eliminates the need to clear out expired Tokens.&lt;br /&gt;
&lt;br /&gt;
[[File:Capture password reset.JPG]]&lt;br /&gt;
&lt;br /&gt;
==Captcha==&lt;br /&gt;
&lt;br /&gt;
The project will be using ReCAPTCHA gem. ReCAPTCHA is a free service from Google that helps protect websites from spam and abuse. A “CAPTCHA” is a test to tell humans and robot apart. This kind of service is important for websites or web applications with lots of user generated content. The test is easy for a human to solve, but hard for bots and other malicious software to figure out.&lt;br /&gt;
&lt;br /&gt;
After 3 failed Login attempts, a captcha would appear to make sure that a bot or a malicious software is not trying to attempt login using brute force.&lt;br /&gt;
&lt;br /&gt;
[[File:Captcha.png]]&lt;br /&gt;
&lt;br /&gt;
==== Gem File ====&lt;br /&gt;
Adding this line to the Gem file allows us to have access to the recaptcha gem.&lt;br /&gt;
&lt;br /&gt;
&amp;lt;pre&amp;gt;gem &amp;quot;recaptcha&amp;quot;, require: &amp;quot;recaptcha/rails&amp;quot;&amp;lt;/pre&amp;gt;&lt;br /&gt;
&lt;br /&gt;
==== Backoff System ====&lt;br /&gt;
In Auth Controller we added the following code. The variable @@attempts acts as a counter to track the amount of invalid login attempts a user makes. By utilizing the existing login code we were able to place the increment code. Once the attempts variable is greater than or equal to 3 we then force the user to use the recaptcha question in addition to their correct logic credentials. Once the new requirements to login are satisfied the user is redirected to the password retrieval, otherwise they are redirected to the root screen with the captcha question. &lt;br /&gt;
&amp;lt;pre&amp;gt;&lt;br /&gt;
  @@attemps = 0&lt;br /&gt;
&lt;br /&gt;
  def login&lt;br /&gt;
  if request.get?&lt;br /&gt;
  AuthController.clear_session(session)&lt;br /&gt;
  else&lt;br /&gt;
  user = User.find_by_login(params[:login][:name])&lt;br /&gt;
  if user and user.valid_password?(params[:login][:password])&lt;br /&gt;
  after_login(user)&lt;br /&gt;
  else&lt;br /&gt;
&lt;br /&gt;
  @@attemps = @@attemps + 1&lt;br /&gt;
  logger.warn &amp;quot;Failed login attempt.&amp;quot;&lt;br /&gt;
  flash[:error] = &amp;quot;Your username or password is incorrect.&amp;quot;&lt;br /&gt;
  if @@attemps &amp;gt;= 3 ##User entered invalid login credentials at least 3 times&lt;br /&gt;
  if verify_recaptcha(model: @user)&lt;br /&gt;
  @@attemps = 0&lt;br /&gt;
  redirect_to controller: 'password_retrieval', action: 'forgotten'&lt;br /&gt;
  end&lt;br /&gt;
&lt;br /&gt;
  else&lt;br /&gt;
  redirect_to root_path&lt;br /&gt;
&lt;br /&gt;
  end&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
  end&lt;br /&gt;
  end&lt;br /&gt;
  end # def login&lt;br /&gt;
&lt;br /&gt;
&amp;lt;/pre&amp;gt;&lt;br /&gt;
&lt;br /&gt;
==Testing==&lt;br /&gt;
&lt;br /&gt;
To run the Rspecs test cases:&lt;br /&gt;
 rspec path_to_expertiza/spec/controllers/password_retrieval_controller_spec.rb &lt;br /&gt;
&lt;br /&gt;
To test from UI:&lt;br /&gt;
 i) Enter the wrong password on login page three consecutive times, you will shown with Google Captcha for the fourth attempt.&lt;br /&gt;
 ii) On entering the password, wrong the fourth time you will be redirected to &amp;quot;forgot password&amp;quot; page.&lt;br /&gt;
     It can also be reached by clicking &amp;quot;forgot password&amp;quot; page on login page.&lt;br /&gt;
 iii) Enter the email Id, for which new password has to be set. On clicking &amp;quot;Request password&amp;quot; you will get a mail with password reset link. &lt;br /&gt;
 iv) Clicking on the password reset link, you will be redirected to password reset page where you can set your new password. &lt;br /&gt;
&lt;br /&gt;
Here is a short [http://recordit.co/pXq9jM9xhr video] demonstrating the same.&lt;/div&gt;</summary>
		<author><name>Vdatla</name></author>
	</entry>
	<entry>
		<id>https://wiki.expertiza.ncsu.edu/index.php?title=CSC/ECE_517_Fall_2016&amp;diff=106082</id>
		<title>CSC/ECE 517 Fall 2016</title>
		<link rel="alternate" type="text/html" href="https://wiki.expertiza.ncsu.edu/index.php?title=CSC/ECE_517_Fall_2016&amp;diff=106082"/>
		<updated>2016-12-02T20:37:20Z</updated>

		<summary type="html">&lt;p&gt;Vdatla: /* Final Project Design Document */&lt;/p&gt;
&lt;hr /&gt;
&lt;div&gt;[http://www.example.com link title]==Calibration Assignment Submissions==&lt;br /&gt;
*[[Calibration Assignment Submission (Firebrick JS)]]&lt;br /&gt;
*[[Calibration Assignment Submission (Active Job)]]&lt;br /&gt;
==Writing Assignments 2==&lt;br /&gt;
*[[CSC/ECE 517 Fall 2016/E1666. Test team functionality]]&lt;br /&gt;
*[[CSC/ECE 517 Fall 2016/E1643. Refactor Suggestion controller]]&lt;br /&gt;
*[[CSC/ECE 517 Fall 2016/E1631. Refactoring Bidding Interface]]&lt;br /&gt;
*[[CSC/ECE 517 Fall 2016/E1674.Refactor leaderboard.rb and write unit tests]]&lt;br /&gt;
*[[CSC/ECE 517 Fall 2016/E1671. Unit Tests for participants.rb Hierarchy]]&lt;br /&gt;
*[[CSC/ECE 517 Fall 2016/E1668.Test e-mailing functionality]]&lt;br /&gt;
*[[CSC/ECE 517 Fall 2016/E1658. Refractor lottery_controller.rb and write integration tests]]&lt;br /&gt;
*[[CSC/ECE 517 Fall 2016/E1660. Review requirements and thresholds]]&lt;br /&gt;
*[[CSC/ECE 517 Fall 2016/E1650. Sort instructor views alphabetically by default]]&lt;br /&gt;
*[[CSC/ECE 517 Fall 2016/E1644. Refactor and test Teams Controller]]&lt;br /&gt;
*[[CSC/ECE 517 Fall 2016/E1645. Refactoring Tree Display Controller]]&lt;br /&gt;
*[[CSC/ECE 517 Fall 2016/E1659. Refactor on_the_fly_calc.rb]]&lt;br /&gt;
*[[CSC/ECE 517 Fall 2016/E1657. Introduce a Student View for instructors]]&lt;br /&gt;
*[[CSC/ECE 517 Fall 2016/E1653. Fix and improve rubric criteria]]&lt;br /&gt;
*[[CSC/ECE 517 Fall 2016/E1642. Refactor review_response_map.rb]]&lt;br /&gt;
*[[CSC/ECE 517 Fall 2016/E1633. Refactor different question types from quiz feature]]&lt;br /&gt;
*[[CSC/ECE_517_Fall_2016/E1664:_Feature_Test_Assignment_Creation]]&lt;br /&gt;
*[[CSC/ECE 517 Fall 2016/E1666. Test team functionality]]&lt;br /&gt;
*[[CSC/ECE_517_Fall_2016/E1654. Improve_date-picker_and_deadlines]]&lt;br /&gt;
*[[CSC/ECE_517_Fall_2016/E1652 Fix teammate advertisements and requests to join a team ]]&lt;br /&gt;
*[[CSC/ECE_517_Fall_2016/E1662. UI issues/fixes]]&lt;br /&gt;
*[[CSC/ECE_517_Fall_2016/E1673. Refactor question_type.rb]]&lt;br /&gt;
*[[CSC/ECE_517_Fall_2016/E1675. Timestamp for student file &amp;amp; hyperlink submissions]]&lt;br /&gt;
*[[CSC/ECE_517_Fall_2016/E1640. Refactor response.rb and response_helper.rb]]&lt;br /&gt;
*[[CSC/ECE 517 Fall 2016/E1634. Refactor and write unit test of due_date.rb and deadline_helper.rb]]&lt;br /&gt;
*[[CSC/ECE_517_Fall_2016/M1654._Improve_network_security_features]]&lt;br /&gt;
*[[CSC/ECE_517_Fall_2016/E1670._Unit_tests_for_answers.rb]]&lt;br /&gt;
*[[CSC/ECE_517_Fall_2016/E1641. Refactor review_mapping_controller.rb]]&lt;br /&gt;
*[[CSC/ECE_517_Fall_2016/M1652_Implement_ImageMap_Support_Servo]]&lt;br /&gt;
*[[CSC/ECE_517_Fall_2016/E1648/Add_past_due_assignment]]&lt;br /&gt;
*[[CSC/ECE 517 Fall 2016/E1656. Improve imports]]&lt;br /&gt;
*[[CSC/ECE_517_Fall_2016/M1653_Implement_HTML_form_validation]]&lt;br /&gt;
*[[CSC/ECE_517_Fall_2016/E1635._Refactor_join_team_requests_controller.rb_and_invitation_controller.rb]]&lt;br /&gt;
*[[CSC/ECE 517 Fall 2016/E1665. Test staggered-deadline functionality]]&lt;br /&gt;
&lt;br /&gt;
==Final Project Design Document==&lt;br /&gt;
*[[CSC/ECE 517 Fall 2016 E1696  Improve Self-Review]]&lt;br /&gt;
*[[CSC/ECE 517 Fall 2016 E1676  Role-based reviewing]]&lt;br /&gt;
*[[CSC/ECE 517 Fall 2016/E1680. Improve survey functionality]]&lt;br /&gt;
*[[CSC/ECE 517 Fall 2016/E1693. Drag-and-drop interface for creating rubrics]]&lt;br /&gt;
*[[CSC/ECE 517 Fall 2016/E1701. Accelerate RSpec testing]]&lt;br /&gt;
*[[CSC/ECE 517 Fall 2016 E1679 Let experts as well as students do reviews]]&lt;br /&gt;
*[[CSC/ECE 517 Fall 2016/E1705. Tracking the time students look at the others' submissions]]&lt;br /&gt;
*[[CSC/ECE 517 Fall 2016/E1688. Send feedback to support + tree display improvement]]&lt;br /&gt;
*[[CSC/ECE 517 Fall 2016 E1707: Top trading cycles to exclude previous teammates]]&lt;br /&gt;
*[[CSC/ECE 517 Fall 2016 E1678: Review configuration options]]&lt;br /&gt;
*[[CSC/ECE 517 Fall 2016 E1682: Improve score calculation]]&lt;br /&gt;
*[[CSC/ECE 517 Fall 2016 E1684: Feature Test for Assignment Submission]]&lt;br /&gt;
*[[CSC/ECE 517 Fall 2016 E1689: Anonymous Chat Between Author and Reviewer]]&lt;br /&gt;
*[[CSC/ECE 517 Fall 2016 E1703: Logging for Expertiza]]&lt;br /&gt;
*[[CSC/ECE 517 Fall 2016 E1708: Improvements to staggered-deadline assignments]]&lt;br /&gt;
*[[CSC/ECE 517 Fall 2016 E1685: UI changes for review and score reports]]&lt;br /&gt;
*[[CSC/ECE 517 Fall 2016/ M1653 Implement HTML form validation]]&lt;br /&gt;
*[[CSC/ECE 517 Fall 2016/ E1700 Integrate Google doc editor/viewer]]&lt;br /&gt;
*[[CSC/ECE_517_Fall_2016/M1652_ImageMap_Support_Servo]]&lt;br /&gt;
*[[CSC/ECE 517 Fall 2016 E1687 Instructor account creation over the web]]&lt;br /&gt;
*[[CSC/ECE_517_Fall_2016/E1690_Improvements_to_password_recovery_and_repeated_login_failures | CSC/ECE 517 Fall 2016/E1690 Improvements to password recovery and repeated login failures]]&lt;/div&gt;</summary>
		<author><name>Vdatla</name></author>
	</entry>
	<entry>
		<id>https://wiki.expertiza.ncsu.edu/index.php?title=CSC/ECE_517_Fall_2016&amp;diff=106081</id>
		<title>CSC/ECE 517 Fall 2016</title>
		<link rel="alternate" type="text/html" href="https://wiki.expertiza.ncsu.edu/index.php?title=CSC/ECE_517_Fall_2016&amp;diff=106081"/>
		<updated>2016-12-02T20:35:24Z</updated>

		<summary type="html">&lt;p&gt;Vdatla: &lt;/p&gt;
&lt;hr /&gt;
&lt;div&gt;[http://www.example.com link title]==Calibration Assignment Submissions==&lt;br /&gt;
*[[Calibration Assignment Submission (Firebrick JS)]]&lt;br /&gt;
*[[Calibration Assignment Submission (Active Job)]]&lt;br /&gt;
==Writing Assignments 2==&lt;br /&gt;
*[[CSC/ECE 517 Fall 2016/E1666. Test team functionality]]&lt;br /&gt;
*[[CSC/ECE 517 Fall 2016/E1643. Refactor Suggestion controller]]&lt;br /&gt;
*[[CSC/ECE 517 Fall 2016/E1631. Refactoring Bidding Interface]]&lt;br /&gt;
*[[CSC/ECE 517 Fall 2016/E1674.Refactor leaderboard.rb and write unit tests]]&lt;br /&gt;
*[[CSC/ECE 517 Fall 2016/E1671. Unit Tests for participants.rb Hierarchy]]&lt;br /&gt;
*[[CSC/ECE 517 Fall 2016/E1668.Test e-mailing functionality]]&lt;br /&gt;
*[[CSC/ECE 517 Fall 2016/E1658. Refractor lottery_controller.rb and write integration tests]]&lt;br /&gt;
*[[CSC/ECE 517 Fall 2016/E1660. Review requirements and thresholds]]&lt;br /&gt;
*[[CSC/ECE 517 Fall 2016/E1650. Sort instructor views alphabetically by default]]&lt;br /&gt;
*[[CSC/ECE 517 Fall 2016/E1644. Refactor and test Teams Controller]]&lt;br /&gt;
*[[CSC/ECE 517 Fall 2016/E1645. Refactoring Tree Display Controller]]&lt;br /&gt;
*[[CSC/ECE 517 Fall 2016/E1659. Refactor on_the_fly_calc.rb]]&lt;br /&gt;
*[[CSC/ECE 517 Fall 2016/E1657. Introduce a Student View for instructors]]&lt;br /&gt;
*[[CSC/ECE 517 Fall 2016/E1653. Fix and improve rubric criteria]]&lt;br /&gt;
*[[CSC/ECE 517 Fall 2016/E1642. Refactor review_response_map.rb]]&lt;br /&gt;
*[[CSC/ECE 517 Fall 2016/E1633. Refactor different question types from quiz feature]]&lt;br /&gt;
*[[CSC/ECE_517_Fall_2016/E1664:_Feature_Test_Assignment_Creation]]&lt;br /&gt;
*[[CSC/ECE 517 Fall 2016/E1666. Test team functionality]]&lt;br /&gt;
*[[CSC/ECE_517_Fall_2016/E1654. Improve_date-picker_and_deadlines]]&lt;br /&gt;
*[[CSC/ECE_517_Fall_2016/E1652 Fix teammate advertisements and requests to join a team ]]&lt;br /&gt;
*[[CSC/ECE_517_Fall_2016/E1662. UI issues/fixes]]&lt;br /&gt;
*[[CSC/ECE_517_Fall_2016/E1673. Refactor question_type.rb]]&lt;br /&gt;
*[[CSC/ECE_517_Fall_2016/E1675. Timestamp for student file &amp;amp; hyperlink submissions]]&lt;br /&gt;
*[[CSC/ECE_517_Fall_2016/E1640. Refactor response.rb and response_helper.rb]]&lt;br /&gt;
*[[CSC/ECE 517 Fall 2016/E1634. Refactor and write unit test of due_date.rb and deadline_helper.rb]]&lt;br /&gt;
*[[CSC/ECE_517_Fall_2016/M1654._Improve_network_security_features]]&lt;br /&gt;
*[[CSC/ECE_517_Fall_2016/E1670._Unit_tests_for_answers.rb]]&lt;br /&gt;
*[[CSC/ECE_517_Fall_2016/E1641. Refactor review_mapping_controller.rb]]&lt;br /&gt;
*[[CSC/ECE_517_Fall_2016/M1652_Implement_ImageMap_Support_Servo]]&lt;br /&gt;
*[[CSC/ECE_517_Fall_2016/E1648/Add_past_due_assignment]]&lt;br /&gt;
*[[CSC/ECE 517 Fall 2016/E1656. Improve imports]]&lt;br /&gt;
*[[CSC/ECE_517_Fall_2016/M1653_Implement_HTML_form_validation]]&lt;br /&gt;
*[[CSC/ECE_517_Fall_2016/E1635._Refactor_join_team_requests_controller.rb_and_invitation_controller.rb]]&lt;br /&gt;
*[[CSC/ECE 517 Fall 2016/E1665. Test staggered-deadline functionality]]&lt;br /&gt;
&lt;br /&gt;
==Final Project Design Document==&lt;br /&gt;
*[[CSC/ECE 517 Fall 2016 E1696  Improve Self-Review]]&lt;br /&gt;
*[[CSC/ECE 517 Fall 2016 E1676  Role-based reviewing]]&lt;br /&gt;
*[[CSC/ECE 517 Fall 2016/E1680. Improve survey functionality]]&lt;br /&gt;
*[[CSC/ECE 517 Fall 2016/E1693. Drag-and-drop interface for creating rubrics]]&lt;br /&gt;
*[[CSC/ECE 517 Fall 2016/E1701. Accelerate RSpec testing]]&lt;br /&gt;
*[[CSC/ECE 517 Fall 2016 E1679 Let experts as well as students do reviews]]&lt;br /&gt;
*[[CSC/ECE 517 Fall 2016/E1705. Tracking the time students look at the others' submissions]]&lt;br /&gt;
*[[CSC/ECE 517 Fall 2016/E1688. Send feedback to support + tree display improvement]]&lt;br /&gt;
*[[CSC/ECE 517 Fall 2016 E1707: Top trading cycles to exclude previous teammates]]&lt;br /&gt;
*[[CSC/ECE 517 Fall 2016 E1678: Review configuration options]]&lt;br /&gt;
*[[CSC/ECE 517 Fall 2016 E1682: Improve score calculation]]&lt;br /&gt;
*[[CSC/ECE 517 Fall 2016 E1684: Feature Test for Assignment Submission]]&lt;br /&gt;
*[[CSC/ECE 517 Fall 2016 E1689: Anonymous Chat Between Author and Reviewer]]&lt;br /&gt;
*[[CSC/ECE 517 Fall 2016 E1703: Logging for Expertiza]]&lt;br /&gt;
*[[CSC/ECE 517 Fall 2016 E1708: Improvements to staggered-deadline assignments]]&lt;br /&gt;
*[[CSC/ECE 517 Fall 2016 E1685: UI changes for review and score reports]]&lt;br /&gt;
*[[CSC/ECE 517 Fall 2016/ M1653 Implement HTML form validation]]&lt;br /&gt;
*[[CSC/ECE 517 Fall 2016/ E1700 Integrate Google doc editor/viewer]]&lt;br /&gt;
*[[CSC/ECE_517_Fall_2016/M1652_ImageMap_Support_Servo]]&lt;br /&gt;
*[[CSC/ECE 517 Fall 2016 E1687 Instructor account creation over the web]]&lt;br /&gt;
*[[CSC/ECE_517_Fall_2016/E1690_Improvements_to_password_recovery_and_repeated_login_failures]]&lt;/div&gt;</summary>
		<author><name>Vdatla</name></author>
	</entry>
	<entry>
		<id>https://wiki.expertiza.ncsu.edu/index.php?title=CSC/ECE_517_Fall_2016/E1690_Improvements_to_password_recovery_and_repeated_login_failures&amp;diff=106080</id>
		<title>CSC/ECE 517 Fall 2016/E1690 Improvements to password recovery and repeated login failures</title>
		<link rel="alternate" type="text/html" href="https://wiki.expertiza.ncsu.edu/index.php?title=CSC/ECE_517_Fall_2016/E1690_Improvements_to_password_recovery_and_repeated_login_failures&amp;diff=106080"/>
		<updated>2016-12-02T20:25:07Z</updated>

		<summary type="html">&lt;p&gt;Vdatla: /* Testing */&lt;/p&gt;
&lt;hr /&gt;
&lt;div&gt;==E1690 Improvements to password recovery and repeated login failures==&lt;br /&gt;
&lt;br /&gt;
This wiki page is for the description of changes made under E1690 FinalProject for Fall 2016, CSC/ECE 517.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
__TOC__&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
===Background===&lt;br /&gt;
&lt;br /&gt;
Expertiza is an Open Source web application developed on Ruby On Rails platform. It is a platform which allows students to access assignments posted by the course instructor. Expertiza also allows students to select assignment topics, form teams and submit their work. It also allows them to review other students' submissions and improve their work based on the feedback provided. The instructor can look at the feedback provided by students and rate the student based on feedback provided for others work.&lt;br /&gt;
It helps organize and upload assignments and reducing the manual review process and helps students provide a peer feedback and also learn from reviewed work. Teams can be chosen by the student or can be assigned automatically based on a priority list inputted alongside each topic available for the assignment.&lt;br /&gt;
&lt;br /&gt;
===Project Description===&lt;br /&gt;
&lt;br /&gt;
Our final project consists of two cases of the password recovery process. Use case 1, Currently, when a user forgets his/her password and wants to reset the password, Expertiza system randomly generates a new password and sends the password as plain text in a email. It is normally considered as a bad practice to send passwords as paint text. We are replacing this practice by sending a reset password link that expires after a certain amount of time. Use case 2 deals with when a user enters wrong credentials. Currently, the login page simply shows an error. Irrespective of the number of times that a user enters wrong login credentials, the system produces a general error message. We are going to be replacing this system by using the alternative 2, using a captcha to verify that the user is indeed a human and not a bot trying to run a brute force attack on the system. This will add the needed layer of security and should serve as a great solution. Below are more details of our implementation. &lt;br /&gt;
&lt;br /&gt;
===Files Created/Modified===&lt;br /&gt;
As a part of the project the files mentioned below were the ones, created/modified as needed.&lt;br /&gt;
* auth_controller.rb&lt;br /&gt;
* password_retrieval_controller.rb &lt;br /&gt;
* password_reset.rb (model)&lt;br /&gt;
* reset_password.html.erb (view)&lt;br /&gt;
&lt;br /&gt;
===Implementation===&lt;br /&gt;
We have implemented the new password recovery system by sending a reset password link to the user's email. This link will be comprised of a generated path to a newly created view for resetting the password with a uniquely randomly generated token. This parameter will be a string attribute of a new model reset_password. This link will expire after a given amount of time. Using logic to compare the createdAt timestamp as well as the current time, the application would decide if the token is expired or not.&lt;br /&gt;
&lt;br /&gt;
We are also implementing a backoff system that will require the user to complete a smart captcha after 3 failed attempts. This smart captcha will be generated through Recaptcha gem and the user will then be redirected to the login page after successfully changing the password. This will ensure that the system is not vulnerable to Brute Force attacks as well as bots.&lt;br /&gt;
&lt;br /&gt;
==Password Reset==&lt;br /&gt;
&lt;br /&gt;
===Model Schema===&lt;br /&gt;
Model: reset_password&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
Attributes&lt;br /&gt;
*-id(autogenerated) -integer&lt;br /&gt;
*-unique_tokenhash -String&lt;br /&gt;
*-createdAt (autogenerated) -timestamp&lt;br /&gt;
*-user_email -string&lt;br /&gt;
&lt;br /&gt;
'''Model Details'''&lt;br /&gt;
&lt;br /&gt;
When the user clicks on reset password, it will redirect to a view that has an input to enter the email address of the user. Reset password button will generate a random token (Long string) which will be hashed and saved in the database of the model reset_password. An expiration date will be generated and saved along with the user_id by looking up the user table using email id. The unhashed Token value will be appended on the url emailed to the user for the password reset page.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
www.expertiza.com/password_edit/check_reset_url?token=ZB71yObR-Tdssg-@#%&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
On clicking the url, the link will take you to password_retrieval_controller that will direct you to a reset page. Before redirecting , the controller checks the parameters in the link (username and token) and makes sure that token username pair exists and not expired. Token from the params will be hashed again and checked with the DB. This prevents an attacker who has read access to the database from making a token for some other user, reading the value that was sent in the email, then sending the same value himself. Once the controller completes all the necessary checks, it will redirect to a reset password page for that specific user (based on the user_id / username) &lt;br /&gt;
&lt;br /&gt;
Each Email Address can have only one active token saved in the database. Every time a new token is generated, it will replace the existing one which ensures that only one reset link is available. Also, this will make sure that DB content of password_reset can never exceed the number of users registered in the application. This eliminates the need to clear out expired Tokens.&lt;br /&gt;
&lt;br /&gt;
[[File:Capture password reset.JPG]]&lt;br /&gt;
&lt;br /&gt;
==Captcha==&lt;br /&gt;
&lt;br /&gt;
The project will be using ReCAPTCHA gem. ReCAPTCHA is a free service from Google that helps protect websites from spam and abuse. A “CAPTCHA” is a test to tell humans and robot apart. This kind of service is important for websites or web applications with lots of user generated content. The test is easy for a human to solve, but hard for bots and other malicious software to figure out.&lt;br /&gt;
&lt;br /&gt;
After 3 failed Login attempts, a captcha would appear to make sure that a bot or a malicious software is not trying to attempt login using brute force.&lt;br /&gt;
&lt;br /&gt;
[[File:Captcha.png]]&lt;br /&gt;
&lt;br /&gt;
==== Gem File ====&lt;br /&gt;
Adding this line to the Gem file allows us to have access to the recaptcha gem.&lt;br /&gt;
&lt;br /&gt;
&amp;lt;pre&amp;gt;gem &amp;quot;recaptcha&amp;quot;, require: &amp;quot;recaptcha/rails&amp;quot;&amp;lt;/pre&amp;gt;&lt;br /&gt;
&lt;br /&gt;
==== Backoff System ====&lt;br /&gt;
In Auth Controller we added the following code. The variable @@attempts acts as a counter to track the amount of invalid login attempts a user makes. By utilizing the existing login code we were able to place the increment code. Once the attempts variable is greater than or equal to 3 we then force the user to use the recaptcha question in addition to their correct logic credentials. Once the new requirements to login are satisfied the user is redirected to the password retrieval, otherwise they are redirected to the root screen with the captcha question. &lt;br /&gt;
&amp;lt;pre&amp;gt;&lt;br /&gt;
  @@attemps = 0&lt;br /&gt;
&lt;br /&gt;
  def login&lt;br /&gt;
  if request.get?&lt;br /&gt;
  AuthController.clear_session(session)&lt;br /&gt;
  else&lt;br /&gt;
  user = User.find_by_login(params[:login][:name])&lt;br /&gt;
  if user and user.valid_password?(params[:login][:password])&lt;br /&gt;
  after_login(user)&lt;br /&gt;
  else&lt;br /&gt;
&lt;br /&gt;
  @@attemps = @@attemps + 1&lt;br /&gt;
  logger.warn &amp;quot;Failed login attempt.&amp;quot;&lt;br /&gt;
  flash[:error] = &amp;quot;Your username or password is incorrect.&amp;quot;&lt;br /&gt;
  if @@attemps &amp;gt;= 3 ##User entered invalid login credentials at least 3 times&lt;br /&gt;
  if verify_recaptcha(model: @user)&lt;br /&gt;
  @@attemps = 0&lt;br /&gt;
  redirect_to controller: 'password_retrieval', action: 'forgotten'&lt;br /&gt;
  end&lt;br /&gt;
&lt;br /&gt;
  else&lt;br /&gt;
  redirect_to root_path&lt;br /&gt;
&lt;br /&gt;
  end&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
  end&lt;br /&gt;
  end&lt;br /&gt;
  end # def login&lt;br /&gt;
&lt;br /&gt;
&amp;lt;/pre&amp;gt;&lt;br /&gt;
&lt;br /&gt;
==Testing==&lt;br /&gt;
&lt;br /&gt;
To run the Rspecs test cases:&lt;br /&gt;
 rspec path_to_expertiza/spec/controllers/password_retrieval_controller_spec.rb &lt;br /&gt;
&lt;br /&gt;
To test from UI:&lt;br /&gt;
 i) Enter the wrong password on login page three consecutive times, you will shown with Google Captcha for the fourth attempt.&lt;br /&gt;
 ii) On entering the password, wrong the fourth time you will be redirected to &amp;quot;forgot password&amp;quot; page.&lt;br /&gt;
     It can also be reached by clicking &amp;quot;forgot password&amp;quot; page on login page.&lt;br /&gt;
 iii) Enter the email Id, for which new password has to be set. On clicking &amp;quot;Request password&amp;quot; you will get a mail with password reset link. &lt;br /&gt;
 iv) Clicking on the password reset link, you will be redirected to password reset page where you can set your new password. &lt;br /&gt;
&lt;br /&gt;
Here is a short [http://recordit.co/pXq9jM9xhr video] demonstrating the same.&lt;/div&gt;</summary>
		<author><name>Vdatla</name></author>
	</entry>
	<entry>
		<id>https://wiki.expertiza.ncsu.edu/index.php?title=CSC/ECE_517_Fall_2016/E1690_Improvements_to_password_recovery_and_repeated_login_failures&amp;diff=106079</id>
		<title>CSC/ECE 517 Fall 2016/E1690 Improvements to password recovery and repeated login failures</title>
		<link rel="alternate" type="text/html" href="https://wiki.expertiza.ncsu.edu/index.php?title=CSC/ECE_517_Fall_2016/E1690_Improvements_to_password_recovery_and_repeated_login_failures&amp;diff=106079"/>
		<updated>2016-12-02T20:15:24Z</updated>

		<summary type="html">&lt;p&gt;Vdatla: &lt;/p&gt;
&lt;hr /&gt;
&lt;div&gt;==E1690 Improvements to password recovery and repeated login failures==&lt;br /&gt;
&lt;br /&gt;
This wiki page is for the description of changes made under E1690 FinalProject for Fall 2016, CSC/ECE 517.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
__TOC__&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
===Background===&lt;br /&gt;
&lt;br /&gt;
Expertiza is an Open Source web application developed on Ruby On Rails platform. It is a platform which allows students to access assignments posted by the course instructor. Expertiza also allows students to select assignment topics, form teams and submit their work. It also allows them to review other students' submissions and improve their work based on the feedback provided. The instructor can look at the feedback provided by students and rate the student based on feedback provided for others work.&lt;br /&gt;
It helps organize and upload assignments and reducing the manual review process and helps students provide a peer feedback and also learn from reviewed work. Teams can be chosen by the student or can be assigned automatically based on a priority list inputted alongside each topic available for the assignment.&lt;br /&gt;
&lt;br /&gt;
===Project Description===&lt;br /&gt;
&lt;br /&gt;
Our final project consists of two cases of the password recovery process. Use case 1, Currently, when a user forgets his/her password and wants to reset the password, Expertiza system randomly generates a new password and sends the password as plain text in a email. It is normally considered as a bad practice to send passwords as paint text. We are replacing this practice by sending a reset password link that expires after a certain amount of time. Use case 2 deals with when a user enters wrong credentials. Currently, the login page simply shows an error. Irrespective of the number of times that a user enters wrong login credentials, the system produces a general error message. We are going to be replacing this system by using the alternative 2, using a captcha to verify that the user is indeed a human and not a bot trying to run a brute force attack on the system. This will add the needed layer of security and should serve as a great solution. Below are more details of our implementation. &lt;br /&gt;
&lt;br /&gt;
===Files Created/Modified===&lt;br /&gt;
As a part of the project the files mentioned below were the ones, created/modified as needed.&lt;br /&gt;
* auth_controller.rb&lt;br /&gt;
* password_retrieval_controller.rb &lt;br /&gt;
* password_reset.rb (model)&lt;br /&gt;
* reset_password.html.erb (view)&lt;br /&gt;
&lt;br /&gt;
===Implementation===&lt;br /&gt;
We have implemented the new password recovery system by sending a reset password link to the user's email. This link will be comprised of a generated path to a newly created view for resetting the password with a uniquely randomly generated token. This parameter will be a string attribute of a new model reset_password. This link will expire after a given amount of time. Using logic to compare the createdAt timestamp as well as the current time, the application would decide if the token is expired or not.&lt;br /&gt;
&lt;br /&gt;
We are also implementing a backoff system that will require the user to complete a smart captcha after 3 failed attempts. This smart captcha will be generated through Recaptcha gem and the user will then be redirected to the login page after successfully changing the password. This will ensure that the system is not vulnerable to Brute Force attacks as well as bots.&lt;br /&gt;
&lt;br /&gt;
==Password Reset==&lt;br /&gt;
&lt;br /&gt;
===Model Schema===&lt;br /&gt;
Model: reset_password&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
Attributes&lt;br /&gt;
*-id(autogenerated) -integer&lt;br /&gt;
*-unique_tokenhash -String&lt;br /&gt;
*-createdAt (autogenerated) -timestamp&lt;br /&gt;
*-user_email -string&lt;br /&gt;
&lt;br /&gt;
'''Model Details'''&lt;br /&gt;
&lt;br /&gt;
When the user clicks on reset password, it will redirect to a view that has an input to enter the email address of the user. Reset password button will generate a random token (Long string) which will be hashed and saved in the database of the model reset_password. An expiration date will be generated and saved along with the user_id by looking up the user table using email id. The unhashed Token value will be appended on the url emailed to the user for the password reset page.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
www.expertiza.com/password_edit/check_reset_url?token=ZB71yObR-Tdssg-@#%&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
On clicking the url, the link will take you to password_retrieval_controller that will direct you to a reset page. Before redirecting , the controller checks the parameters in the link (username and token) and makes sure that token username pair exists and not expired. Token from the params will be hashed again and checked with the DB. This prevents an attacker who has read access to the database from making a token for some other user, reading the value that was sent in the email, then sending the same value himself. Once the controller completes all the necessary checks, it will redirect to a reset password page for that specific user (based on the user_id / username) &lt;br /&gt;
&lt;br /&gt;
Each Email Address can have only one active token saved in the database. Every time a new token is generated, it will replace the existing one which ensures that only one reset link is available. Also, this will make sure that DB content of password_reset can never exceed the number of users registered in the application. This eliminates the need to clear out expired Tokens.&lt;br /&gt;
&lt;br /&gt;
[[File:Capture password reset.JPG]]&lt;br /&gt;
&lt;br /&gt;
==Captcha==&lt;br /&gt;
&lt;br /&gt;
The project will be using ReCAPTCHA gem. ReCAPTCHA is a free service from Google that helps protect websites from spam and abuse. A “CAPTCHA” is a test to tell humans and robot apart. This kind of service is important for websites or web applications with lots of user generated content. The test is easy for a human to solve, but hard for bots and other malicious software to figure out.&lt;br /&gt;
&lt;br /&gt;
After 3 failed Login attempts, a captcha would appear to make sure that a bot or a malicious software is not trying to attempt login using brute force.&lt;br /&gt;
&lt;br /&gt;
[[File:Captcha.png]]&lt;br /&gt;
&lt;br /&gt;
==== Gem File ====&lt;br /&gt;
Adding this line to the Gem file allows us to have access to the recaptcha gem.&lt;br /&gt;
&lt;br /&gt;
&amp;lt;pre&amp;gt;gem &amp;quot;recaptcha&amp;quot;, require: &amp;quot;recaptcha/rails&amp;quot;&amp;lt;/pre&amp;gt;&lt;br /&gt;
&lt;br /&gt;
==== Backoff System ====&lt;br /&gt;
In Auth Controller we added the following code. The variable @@attempts acts as a counter to track the amount of invalid login attempts a user makes. By utilizing the existing login code we were able to place the increment code. Once the attempts variable is greater than or equal to 3 we then force the user to use the recaptcha question in addition to their correct logic credentials. Once the new requirements to login are satisfied the user is redirected to the password retrieval, otherwise they are redirected to the root screen with the captcha question. &lt;br /&gt;
&amp;lt;pre&amp;gt;&lt;br /&gt;
  @@attemps = 0&lt;br /&gt;
&lt;br /&gt;
  def login&lt;br /&gt;
  if request.get?&lt;br /&gt;
  AuthController.clear_session(session)&lt;br /&gt;
  else&lt;br /&gt;
  user = User.find_by_login(params[:login][:name])&lt;br /&gt;
  if user and user.valid_password?(params[:login][:password])&lt;br /&gt;
  after_login(user)&lt;br /&gt;
  else&lt;br /&gt;
&lt;br /&gt;
  @@attemps = @@attemps + 1&lt;br /&gt;
  logger.warn &amp;quot;Failed login attempt.&amp;quot;&lt;br /&gt;
  flash[:error] = &amp;quot;Your username or password is incorrect.&amp;quot;&lt;br /&gt;
  if @@attemps &amp;gt;= 3 ##User entered invalid login credentials at least 3 times&lt;br /&gt;
  if verify_recaptcha(model: @user)&lt;br /&gt;
  @@attemps = 0&lt;br /&gt;
  redirect_to controller: 'password_retrieval', action: 'forgotten'&lt;br /&gt;
  end&lt;br /&gt;
&lt;br /&gt;
  else&lt;br /&gt;
  redirect_to root_path&lt;br /&gt;
&lt;br /&gt;
  end&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
  end&lt;br /&gt;
  end&lt;br /&gt;
  end # def login&lt;br /&gt;
&lt;br /&gt;
&amp;lt;/pre&amp;gt;&lt;br /&gt;
&lt;br /&gt;
==Testing==&lt;br /&gt;
&lt;br /&gt;
To run the Rspecs test cases:&lt;br /&gt;
 rspec path_to_expertiza/spec/controllers/password_retrieval_controller_spec.rb &lt;br /&gt;
&lt;br /&gt;
To test from UI:&lt;br /&gt;
 i) Enter the wrong password on login page three consecutive times, you will shown with Google Captcha for the fourth attempt.&lt;br /&gt;
 ii) On entering the password, wrong the fourth time you will be redirected to &amp;quot;forgot password&amp;quot; page. It can also be reached by clicking &amp;quot;forgot password&amp;quot; page on login page.&lt;br /&gt;
 iii) Enter the email Id, for which new password has to be set. On clicking &amp;quot;Request password&amp;quot; you will get a mail with password reset link. &lt;br /&gt;
 iv) Clicking on the password reset link, you will be redirected to password reset page where you can set your new password. &lt;br /&gt;
&lt;br /&gt;
Here is a short [http://recordit.co/pXq9jM9xhr video] demonstrating the same.&lt;/div&gt;</summary>
		<author><name>Vdatla</name></author>
	</entry>
	<entry>
		<id>https://wiki.expertiza.ncsu.edu/index.php?title=CSC/ECE_517_Fall_2016/E1690_Improvements_to_password_recovery_and_repeated_login_failures&amp;diff=106078</id>
		<title>CSC/ECE 517 Fall 2016/E1690 Improvements to password recovery and repeated login failures</title>
		<link rel="alternate" type="text/html" href="https://wiki.expertiza.ncsu.edu/index.php?title=CSC/ECE_517_Fall_2016/E1690_Improvements_to_password_recovery_and_repeated_login_failures&amp;diff=106078"/>
		<updated>2016-12-02T20:14:28Z</updated>

		<summary type="html">&lt;p&gt;Vdatla: &lt;/p&gt;
&lt;hr /&gt;
&lt;div&gt;==E1690 Improvements to password recovery and repeated login failures==&lt;br /&gt;
&lt;br /&gt;
This wiki page is for the description of changes made under E1690 FinalProject for Fall 2016, CSC/ECE 517.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
__TOC__&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
===Background===&lt;br /&gt;
&lt;br /&gt;
Expertiza is an Open Source web application developed on Ruby On Rails platform. It is a platform which allows students to access assignments posted by the course instructor. Expertiza also allows students to select assignment topics, form teams and submit their work. It also allows them to review other students' submissions and improve their work based on the feedback provided. The instructor can look at the feedback provided by students and rate the student based on feedback provided for others work.&lt;br /&gt;
It helps organize and upload assignments and reducing the manual review process and helps students provide a peer feedback and also learn from reviewed work. Teams can be chosen by the student or can be assigned automatically based on a priority list inputted alongside each topic available for the assignment.&lt;br /&gt;
&lt;br /&gt;
===Project Description===&lt;br /&gt;
&lt;br /&gt;
Our final project consists of two cases of the password recovery process. Use case 1, Currently, when a user forgets his/her password and wants to reset the password, Expertiza system randomly generates a new password and sends the password as plain text in a email. It is normally considered as a bad practice to send passwords as paint text. We are replacing this practice by sending a reset password link that expires after a certain amount of time. Use case 2 deals with when a user enters wrong credentials. Currently, the login page simply shows an error. Irrespective of the number of times that a user enters wrong login credentials, the system produces a general error message. We are going to be replacing this system by using the alternative 2, using a captcha to verify that the user is indeed a human and not a bot trying to run a brute force attack on the system. This will add the needed layer of security and should serve as a great solution. Below are more details of our implementation. &lt;br /&gt;
&lt;br /&gt;
===Files Created/Modified===&lt;br /&gt;
As a part of the project the files mentioned below were the ones, created/modified as needed.&lt;br /&gt;
* auth_controller.rb&lt;br /&gt;
* password_retrieval_controller.rb &lt;br /&gt;
* password_reset.rb (model)&lt;br /&gt;
* reset_password.html.erb (view)&lt;br /&gt;
&lt;br /&gt;
===Implementation===&lt;br /&gt;
We have implemented the new password recovery system by sending a reset password link to the user's email. This link will be comprised of a generated path to a newly created view for resetting the password with a uniquely randomly generated token. This parameter will be a string attribute of a new model reset_password. This link will expire after a given amount of time. Using logic to compare the createdAt timestamp as well as the current time, the pplication would decide if the token is expired or not.&lt;br /&gt;
&lt;br /&gt;
We are also implementing a backoff system that will require the user to complete a smart captcha after 3 failed attempts. This smart captcha will be generated through Recaptcha gem and the user will then be redirected to the login page after successfully changing the password. This will ensure that the system is not vulnerable to Brute Force attacks as well as bots.&lt;br /&gt;
&lt;br /&gt;
==Password Reset==&lt;br /&gt;
&lt;br /&gt;
===Model Schema===&lt;br /&gt;
Model: reset_password&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
Attributes&lt;br /&gt;
*-id(autogenerated) -integer&lt;br /&gt;
*-unique_tokenhash -String&lt;br /&gt;
*-createdAt (autogenerated) -timestamp&lt;br /&gt;
*-user_email -string&lt;br /&gt;
&lt;br /&gt;
'''Model Details'''&lt;br /&gt;
&lt;br /&gt;
When the user clicks on reset password, it will redirect to a view that has an input to enter the email address of the user. Reset password button will generate a random token (Long string) which will be hashed and saved in the database of the model reset_password. An expiration date will be generated and saved along with the user_id by looking up the user table using email id. The unhashed Token value will be appended on the url emailed to the user for the password reset page.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
www.expertiza.com/password_edit/check_reset_url?token=ZB71yObR-Tdssg-@#%&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
On clicking the url, the link will take you to password_retrieval_controller that will direct you to a reset page. Before redirecting , the controller checks the parameters in the link (username and token) and makes sure that token username pair exists and not expired. Token from the params will be hashed again and checked with the DB. This prevents an attacker who has read access to the database from making a token for some other user, reading the value that was sent in the email, then sending the same value himself. Once the controller completes all the necessary checks, it will redirect to a reset password page for that specific user (based on the user_id / username) &lt;br /&gt;
&lt;br /&gt;
Each Email Address can have only one active token saved in the database. Every time a new token is generated, it will replace the existing one which ensures that only one reset link is available. Also, this will make sure that DB content of password_reset can never exceed the number of users registered in the application. This eliminates the need to clear out expired Tokens.&lt;br /&gt;
&lt;br /&gt;
[[File:Capture password reset.JPG]]&lt;br /&gt;
&lt;br /&gt;
==Captcha==&lt;br /&gt;
&lt;br /&gt;
The project will be using ReCAPTCHA gem. ReCAPTCHA is a free service from Google that helps protect websites from spam and abuse. A “CAPTCHA” is a test to tell humans and robot apart. This kind of service is important for websites or web applications with lots of user generated content. The test is easy for a human to solve, but hard for bots and other malicious software to figure out.&lt;br /&gt;
&lt;br /&gt;
After 3 failed Login attempts, a captcha would appear to make sure that a bot or a malicious software is not trying to attempt login using brute force.&lt;br /&gt;
&lt;br /&gt;
[[File:Captcha.png]]&lt;br /&gt;
&lt;br /&gt;
==== Gem File ====&lt;br /&gt;
Adding this line to the Gem file allows us to have access to the recaptcha gem.&lt;br /&gt;
&lt;br /&gt;
&amp;lt;pre&amp;gt;gem &amp;quot;recaptcha&amp;quot;, require: &amp;quot;recaptcha/rails&amp;quot;&amp;lt;/pre&amp;gt;&lt;br /&gt;
&lt;br /&gt;
==== Backoff System ====&lt;br /&gt;
In Auth Controller we added the following code. The variable @@attempts acts as a counter to track the amount of invalid login attempts a user makes. By utilizing the existing login code we were able to place the increment code. Once the attempts variable is greater than or equal to 3 we then force the user to use the recaptcha question in addition to their correct logic credentials. Once the new requirements to login are satisfied the user is redirected to the password retrieval, otherwise they are redirected to the root screen with the captcha question. &lt;br /&gt;
&amp;lt;pre&amp;gt;&lt;br /&gt;
  @@attemps = 0&lt;br /&gt;
&lt;br /&gt;
  def login&lt;br /&gt;
  if request.get?&lt;br /&gt;
  AuthController.clear_session(session)&lt;br /&gt;
  else&lt;br /&gt;
  user = User.find_by_login(params[:login][:name])&lt;br /&gt;
  if user and user.valid_password?(params[:login][:password])&lt;br /&gt;
  after_login(user)&lt;br /&gt;
  else&lt;br /&gt;
&lt;br /&gt;
  @@attemps = @@attemps + 1&lt;br /&gt;
  logger.warn &amp;quot;Failed login attempt.&amp;quot;&lt;br /&gt;
  flash[:error] = &amp;quot;Your username or password is incorrect.&amp;quot;&lt;br /&gt;
  if @@attemps &amp;gt;= 3 ##User entered invalid login credentials at least 3 times&lt;br /&gt;
  if verify_recaptcha(model: @user)&lt;br /&gt;
  @@attemps = 0&lt;br /&gt;
  redirect_to controller: 'password_retrieval', action: 'forgotten'&lt;br /&gt;
  end&lt;br /&gt;
&lt;br /&gt;
  else&lt;br /&gt;
  redirect_to root_path&lt;br /&gt;
&lt;br /&gt;
  end&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
  end&lt;br /&gt;
  end&lt;br /&gt;
  end # def login&lt;br /&gt;
&lt;br /&gt;
&amp;lt;/pre&amp;gt;&lt;br /&gt;
&lt;br /&gt;
==Testing==&lt;br /&gt;
&lt;br /&gt;
To run the Rspecs test cases:&lt;br /&gt;
 rspec path_to_expertiza/spec/controllers/password_retrieval_controller_spec.rb &lt;br /&gt;
&lt;br /&gt;
To test from UI:&lt;br /&gt;
 i) Enter the wrong password on login page three consecutive times, you will shown with Google Captcha for the fourth attempt.&lt;br /&gt;
 ii) On entering the password, wrong the fourth time you will be redirected to &amp;quot;forgot password&amp;quot; page. It can also be reached by clicking &amp;quot;forgot password&amp;quot; page on login page.&lt;br /&gt;
 iii) Enter the email Id, for which new password has to be set. On clicking &amp;quot;Request password&amp;quot; you will get a mail with password reset link. &lt;br /&gt;
 iv) Clicking on the password reset link, you will be redirected to password reset page where you can set your new password. &lt;br /&gt;
&lt;br /&gt;
Here is a short [http://recordit.co/pXq9jM9xhr video] demonstrating the same.&lt;/div&gt;</summary>
		<author><name>Vdatla</name></author>
	</entry>
	<entry>
		<id>https://wiki.expertiza.ncsu.edu/index.php?title=CSC/ECE_517_Fall_2016/E1690_Improvements_to_password_recovery_and_repeated_login_failures&amp;diff=106077</id>
		<title>CSC/ECE 517 Fall 2016/E1690 Improvements to password recovery and repeated login failures</title>
		<link rel="alternate" type="text/html" href="https://wiki.expertiza.ncsu.edu/index.php?title=CSC/ECE_517_Fall_2016/E1690_Improvements_to_password_recovery_and_repeated_login_failures&amp;diff=106077"/>
		<updated>2016-12-02T20:11:00Z</updated>

		<summary type="html">&lt;p&gt;Vdatla: &lt;/p&gt;
&lt;hr /&gt;
&lt;div&gt;==E1690 Improvements to password recovery and repeated login failures==&lt;br /&gt;
&lt;br /&gt;
This wiki page is for the description of changes made under E1690 FinalProject for Fall 2016, CSC/ECE 517.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
__TOC__&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
===Background===&lt;br /&gt;
&lt;br /&gt;
Expertiza is an Open Source web application developed on Ruby On Rails platform. It is a platform which allows students to access assignments posted by the course instructor. Expertiza also allows students to select assignment topics, form teams and submit their work. It also allows them to review other students' submissions and improve their work based on the feedback provided. The instructor can look at the feedback provided by students and rate the student based on feedback provided for others work.&lt;br /&gt;
It helps organize and upload assignments and reducing the manual review process and helps students provide a peer feedback and also learn from reviewed work. Teams can be chosen by the student or can be assigned automatically based on a priority list inputted alongside each topic available for the assignment.&lt;br /&gt;
&lt;br /&gt;
===Project Description===&lt;br /&gt;
&lt;br /&gt;
Our final project consists of two cases of the password recovery process. Use case 1, Currently, when a user forgets his/her password and wants to reset the password, Expertiza system randomly generates a new password and sends the password as plain text in a email. It is normally considered as a bad practice to send passwords as paint text. We are replacing this practice by sending a reset password link that expires after a certain amount of time. Use case 2 deals with when a user enters wrong credentials. Currently, the login page simply shows an error. Irrespective of the number of times that a user enters wrong login credentials, the system produces a general error message. We are going to be replacing this system by using the alternative 2, using a captcha to verify that the user is indeed a human and not a bot trying to run a brute force attack on the system. This will add the needed layer of security and should serve as a great solution. Below are more details of our planned implementation. &lt;br /&gt;
&lt;br /&gt;
===Files Created/Modified===&lt;br /&gt;
As a part of the project the files mentioned below were the ones, created/modified as needed.&lt;br /&gt;
* auth_controller.rb&lt;br /&gt;
* password_retrieval_controller.rb &lt;br /&gt;
* password_reset.rb (model)&lt;br /&gt;
* reset_password.html.erb (view)&lt;br /&gt;
&lt;br /&gt;
===Implementation===&lt;br /&gt;
We are going to implement the new password recovery system by sending a reset password link to the users email. This link will be comprised of a generated path to a newly created view for resetting the password with a uniquely randomly generated parameter. This parameter will be a string attribute of a new model we are creating called reset_password. This link will expire after a given amount of time. Using logic to compare the createdAt timestamp as well as the current time, we would be able to program the idea of an expired link. &lt;br /&gt;
&lt;br /&gt;
We are also implementing a backoff system that will require the user to complete a smart captcha after 3 failed attempts. This smart captcha will be generated through Recaptcha gem and the user will then be redirected to the login page after successfully changing the password. This will ensure that the system is not vulnerable to Brute Force attacks as well as bots.&lt;br /&gt;
&lt;br /&gt;
==Password Reset==&lt;br /&gt;
&lt;br /&gt;
===Model Schema===&lt;br /&gt;
Model: reset_password&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
Attributes&lt;br /&gt;
*-id(autogenerated) -integer&lt;br /&gt;
*-unique_tokenhash -String&lt;br /&gt;
*-createdAt (autogenerated) -timestamp&lt;br /&gt;
*-user_email -string&lt;br /&gt;
&lt;br /&gt;
'''Model Details'''&lt;br /&gt;
&lt;br /&gt;
When the user clicks on reset password, it will redirect to a view that has an input to enter the email address of the user. Reset password button will generate a random token (Long string) which will be hashed and saved in the database of the model reset_password. An expiration date will be generated and saved along with the user_id by looking up the user table using email id. The unhashed Token value will be appended on the url emailed to the user for the password reset page.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
www.expertiza.com/password_edit/check_reset_url?token=ZB71yObR-Tdssg-@#%&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
On clicking the url, the link will take you to password_retrieval_controller that will direct you to a reset page. Before redirecting , the controller checks the parameters in the link (username and token) and makes sure that token username pair exists and not expired. Token from the params will be hashed again and checked with the DB. This prevents an attacker who has read access to the database from making a token for some other user, reading the value that was sent in the email, then sending the same value himself. Once the controller completes all the necessary checks, it will redirect to a reset password page for that specific user (based on the user_id / username) &lt;br /&gt;
&lt;br /&gt;
Each Email Address can have only one active token saved in the database. Every time a new token is generated, it will replace the existing one which ensures that only one reset link is available. Also, this will make sure that DB content of password_reset can never exceed the number of users registered in the application. This eliminates the need to clear out expired Tokens.&lt;br /&gt;
&lt;br /&gt;
[[File:Capture password reset.JPG]]&lt;br /&gt;
&lt;br /&gt;
==Captcha==&lt;br /&gt;
&lt;br /&gt;
The project will be using ReCAPTCHA gem. ReCAPTCHA is a free service from Google that helps protect websites from spam and abuse. A “CAPTCHA” is a test to tell humans and robot apart. This kind of service is important for websites or web applications with lots of user generated content. The test is easy for a human to solve, but hard for bots and other malicious software to figure out.&lt;br /&gt;
&lt;br /&gt;
After 3 failed Login attempts, a captcha would appear to make sure that a bot or a malicious software is not trying to attempt login using brute force.&lt;br /&gt;
&lt;br /&gt;
[[File:Captcha.png]]&lt;br /&gt;
&lt;br /&gt;
==== Gem File ====&lt;br /&gt;
Adding this line to the Gem file allows us to have access to the recaptcha gem.&lt;br /&gt;
&lt;br /&gt;
&amp;lt;pre&amp;gt;gem &amp;quot;recaptcha&amp;quot;, require: &amp;quot;recaptcha/rails&amp;quot;&amp;lt;/pre&amp;gt;&lt;br /&gt;
&lt;br /&gt;
==== Backoff System ====&lt;br /&gt;
In Auth Controller we added the following code. The variable @@attempts acts as a counter to track the amount of invalid login attempts a user makes. By utilizing the existing login code we were able to place the increment code. Once the attempts variable is greater than or equal to 3 we then force the user to use the recaptcha question in addition to their correct logic credentials. Once the new requirements to login are satisfied the user is redirected to the password retrieval, otherwise they are redirected to the root screen with the captcha question. &lt;br /&gt;
&amp;lt;pre&amp;gt;&lt;br /&gt;
  @@attemps = 0&lt;br /&gt;
&lt;br /&gt;
  def login&lt;br /&gt;
  if request.get?&lt;br /&gt;
  AuthController.clear_session(session)&lt;br /&gt;
  else&lt;br /&gt;
  user = User.find_by_login(params[:login][:name])&lt;br /&gt;
  if user and user.valid_password?(params[:login][:password])&lt;br /&gt;
  after_login(user)&lt;br /&gt;
  else&lt;br /&gt;
&lt;br /&gt;
  @@attemps = @@attemps + 1&lt;br /&gt;
  logger.warn &amp;quot;Failed login attempt.&amp;quot;&lt;br /&gt;
  flash[:error] = &amp;quot;Your username or password is incorrect.&amp;quot;&lt;br /&gt;
  if @@attemps &amp;gt;= 3 ##User entered invalid login credentials at least 3 times&lt;br /&gt;
  if verify_recaptcha(model: @user)&lt;br /&gt;
  @@attemps = 0&lt;br /&gt;
  redirect_to controller: 'password_retrieval', action: 'forgotten'&lt;br /&gt;
  end&lt;br /&gt;
&lt;br /&gt;
  else&lt;br /&gt;
  redirect_to root_path&lt;br /&gt;
&lt;br /&gt;
  end&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
  end&lt;br /&gt;
  end&lt;br /&gt;
  end # def login&lt;br /&gt;
&lt;br /&gt;
&amp;lt;/pre&amp;gt;&lt;br /&gt;
&lt;br /&gt;
==Testing==&lt;br /&gt;
&lt;br /&gt;
To run the Rspecs test cases:&lt;br /&gt;
 rspec path_to_expertiza/spec/controllers/password_retrieval_controller_spec.rb &lt;br /&gt;
&lt;br /&gt;
To test from UI:&lt;br /&gt;
 i) Enter the wrong password on login page three consecutive times, you will shown with Google Captcha for the fourth attempt.&lt;br /&gt;
 ii) On entering the password, wrong the fourth time you will be redirected to &amp;quot;forgot password&amp;quot; page. It can also be reached by clicking &amp;quot;forgot password&amp;quot; page on login page.&lt;br /&gt;
 iii) Enter the email Id, for which new password has to be set. On clicking &amp;quot;Request password&amp;quot; you will get a mail with password reset link. &lt;br /&gt;
 iv) Clicking on the password reset link, you will be redirected to password reset page where you can set your new password. &lt;br /&gt;
&lt;br /&gt;
Here is a short [http://recordit.co/pXq9jM9xhr video] demonstrating the same.&lt;/div&gt;</summary>
		<author><name>Vdatla</name></author>
	</entry>
	<entry>
		<id>https://wiki.expertiza.ncsu.edu/index.php?title=CSC/ECE_517_Fall_2016/E1690_Improvements_to_password_recovery_and_repeated_login_failures&amp;diff=106076</id>
		<title>CSC/ECE 517 Fall 2016/E1690 Improvements to password recovery and repeated login failures</title>
		<link rel="alternate" type="text/html" href="https://wiki.expertiza.ncsu.edu/index.php?title=CSC/ECE_517_Fall_2016/E1690_Improvements_to_password_recovery_and_repeated_login_failures&amp;diff=106076"/>
		<updated>2016-12-02T20:04:58Z</updated>

		<summary type="html">&lt;p&gt;Vdatla: /* E1690 Improvements to password recovery and repeated login failures */&lt;/p&gt;
&lt;hr /&gt;
&lt;div&gt;==E1690 Improvements to password recovery and repeated login failures==&lt;br /&gt;
&lt;br /&gt;
This wiki page is for the description of changes made under E1690 FinalProject for Fall 2016, CSC/ECE 517.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
__TOC__&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
===Background===&lt;br /&gt;
&lt;br /&gt;
Expertiza is an Open Source web application developed on Ruby On Rails platform. It is a platform which allows students to access assignments posted by the course instructor. Expertiza also allows students to select assignment topics, form teams and submit their work. It also allows them to review other students' submissions and improve their work based on the feedback provided. The instructor can look at the feedback provided by students and rate the student based on feedback provided for others work.&lt;br /&gt;
It helps organize and upload assignments and reducing the manual review process and helps students provide a peer feedback and also learn from reviewed work. Teams can be chosen by the student or can be assigned automatically based on a priority list inputted alongside each topic available for the assignment.&lt;br /&gt;
&lt;br /&gt;
===Project Description===&lt;br /&gt;
&lt;br /&gt;
Our final project consists of two cases of the password recovery process. Use case 1, Currently, when a user forgets his/her password and wants to reset the password, Expertiza system randomly generates a new password and sends the password as plain text in a email. It is normally considered as a bad practice to send passwords as paint text. We are replacing this practice by sending a reset password link that expires after a certain amount of time.  Use case 2 deals with when a user enters wrong credentials. Currently, the login page simply shows an error. Irrespective of the number of times that a user enters wrong login credentials, the system produces a general error message.  We are going to be replacing this system by using the alternative 2, using a captcha to verify that the user is indeed a human and not a bot trying to run a brute force attack on the system.  This will add the needed layer of security and should serve as a great solution.  Below are more details of our planned implementation.  &lt;br /&gt;
&lt;br /&gt;
===Files Created/Modified===&lt;br /&gt;
As a part of the project the files mentioned below were the ones, created/modified as needed.&lt;br /&gt;
* auth_controller.rb&lt;br /&gt;
* password_retrieval_controller.rb &lt;br /&gt;
* password_reset.rb  (model)&lt;br /&gt;
* reset_password.html.erb  (view)&lt;br /&gt;
&lt;br /&gt;
===Implementation===&lt;br /&gt;
We are going to implement the new password recovery system by sending a reset password link to the users email. This link will be comprised of a generated path to a newly created view for resetting the password with a uniquely randomly generated parameter.  This parameter will be a string attribute of a new model we are creating called reset_password.  This link will expire after a given amount of time. Using logic to compare the createdAt timestamp as well as the current time, we would be able to program the idea of an expired link.  &lt;br /&gt;
&lt;br /&gt;
We are also implementing a backoff system that will require the user to complete a smart captcha after 3 failed attempts.  This smart captcha will be generated through Recaptcha gem and the user will then be redirected to the login page after successfully changing the password.  This will ensure that the system is not vulnerable to Brute Force attacks as well as bots.&lt;br /&gt;
&lt;br /&gt;
==Password Reset==&lt;br /&gt;
&lt;br /&gt;
===Model Schema===&lt;br /&gt;
Model: reset_password&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
Attributes&lt;br /&gt;
*-id(autogenerated)   -integer&lt;br /&gt;
*-unique_tokenhash       -String&lt;br /&gt;
*-createdAt    (autogenerated) -timestamp&lt;br /&gt;
*-user_id -integer (Foreign key to user table)&lt;br /&gt;
&lt;br /&gt;
'''Model Details'''&lt;br /&gt;
&lt;br /&gt;
When the user clicks on reset password, it will redirect to a view that has an input to enter the email address of the user. Reset password button will generate a random token (Long string) which will be hashed and saved in the database of the model reset_password. An expiration date will be generated and saved along with the user_id by looking up the user table using email id. The unhashed Token value will be appended on the url emailed to the user for the password reset page.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
www.expertiza.com/resetPass?username=random&amp;amp;token=ZB71yObR-Tdssg-@#%&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
On clicking the url, the link will take you to a controller that will direct you to a reset page. Before redirecting , the controller checks the parameters in the link (username and token) and makes sure that token username pair exists and not expired. Token from the params will be hashed again and checked with the db. This prevents an attacker who has read access to the database from making a token for some other user, reading the value that was sent in the email, then sending the same value himself. Once the controller completes all the necessary checks, it will redirect to a reset password page for that specific user (based on the user_id / username) &lt;br /&gt;
&lt;br /&gt;
[[File:Capture password reset.JPG]]&lt;br /&gt;
&lt;br /&gt;
==Captcha==&lt;br /&gt;
&lt;br /&gt;
The project will be using ReCAPTCHA gem. ReCAPTCHA is a free service from Google that helps protect websites from spam and abuse. A “CAPTCHA” is a test to tell humans and robot apart. This kind of service is important for websites or web applications with lots of user generated content. The test is easy for a human to solve, but hard for bots and other malicious software to figure out.&lt;br /&gt;
&lt;br /&gt;
After 3 failed Login attempts, a captcha would appear to make sure that a bot or a malicious software is not trying to attempt login using brute force.&lt;br /&gt;
&lt;br /&gt;
[[File:Captcha.png]]&lt;br /&gt;
&lt;br /&gt;
==== Gem File ====&lt;br /&gt;
Adding this line to the Gem file allows us to have access to the recaptcha gem.&lt;br /&gt;
&lt;br /&gt;
&amp;lt;pre&amp;gt;gem &amp;quot;recaptcha&amp;quot;, require: &amp;quot;recaptcha/rails&amp;quot;&amp;lt;/pre&amp;gt;&lt;br /&gt;
&lt;br /&gt;
==== Backoff System ====&lt;br /&gt;
In Auth Controller we added the following code.  The variable @@attempts acts as a counter to track the amount of invalid login attempts a user makes.  By utilizing the existing login code we were able to place the increment code.  Once the attempts variable is greater than or equal to 3 we then force the user to use the recaptcha question in addition to their correct logic credentials.  Once the new requirements to login are satisfied the user is redirected to the password retrieval, otherwise they are redirected to the root screen with the captcha question.  &lt;br /&gt;
&amp;lt;pre&amp;gt;&lt;br /&gt;
  @@attemps = 0&lt;br /&gt;
&lt;br /&gt;
  def login&lt;br /&gt;
    if request.get?&lt;br /&gt;
      AuthController.clear_session(session)&lt;br /&gt;
    else&lt;br /&gt;
      user = User.find_by_login(params[:login][:name])&lt;br /&gt;
      if user and user.valid_password?(params[:login][:password])&lt;br /&gt;
        after_login(user)&lt;br /&gt;
      else&lt;br /&gt;
&lt;br /&gt;
        @@attemps = @@attemps + 1&lt;br /&gt;
        logger.warn &amp;quot;Failed login attempt.&amp;quot;&lt;br /&gt;
        flash[:error] = &amp;quot;Your username or password is incorrect.&amp;quot;&lt;br /&gt;
        if @@attemps &amp;gt;= 3                                                         ##User entered invalid login credentials at least 3 times&lt;br /&gt;
            if verify_recaptcha(model: @user)&lt;br /&gt;
              @@attemps = 0&lt;br /&gt;
              redirect_to controller: 'password_retrieval', action: 'forgotten'&lt;br /&gt;
            end&lt;br /&gt;
&lt;br /&gt;
        else&lt;br /&gt;
          redirect_to root_path&lt;br /&gt;
&lt;br /&gt;
        end&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
      end&lt;br /&gt;
    end&lt;br /&gt;
  end # def login&lt;br /&gt;
&lt;br /&gt;
&amp;lt;/pre&amp;gt;&lt;br /&gt;
&lt;br /&gt;
==Testing==&lt;br /&gt;
&lt;br /&gt;
To run the Rspecs test cases:&lt;br /&gt;
 rspec path_to_expertiza/spec/controllers/password_retrieval_controller_spec.rb &lt;br /&gt;
&lt;br /&gt;
To test from UI:&lt;br /&gt;
 i)  Enter the wrong password on login page three consecutive times, you will shown with Google Captcha for the fourth attempt.&lt;br /&gt;
 ii) On entering the password, wrong the fourth time you will be redirected to &amp;quot;forgot password&amp;quot; page. It can also be reached by clicking &amp;quot;forgot password&amp;quot; page on login page.&lt;br /&gt;
 iii) Enter the email Id, for which new password has to be set. On clicking &amp;quot;Request password&amp;quot; you will get a mail with password reset link. &lt;br /&gt;
 iv) Clicking on the password reset link, you will be redirected to password reset page where you can set your new password. &lt;br /&gt;
&lt;br /&gt;
Here is a short [http://recordit.co/pXq9jM9xhr video] demonstrating the same.&lt;/div&gt;</summary>
		<author><name>Vdatla</name></author>
	</entry>
	<entry>
		<id>https://wiki.expertiza.ncsu.edu/index.php?title=CSC/ECE_517_Fall_2016/E1690_Improvements_to_password_recovery_and_repeated_login_failures&amp;diff=106075</id>
		<title>CSC/ECE 517 Fall 2016/E1690 Improvements to password recovery and repeated login failures</title>
		<link rel="alternate" type="text/html" href="https://wiki.expertiza.ncsu.edu/index.php?title=CSC/ECE_517_Fall_2016/E1690_Improvements_to_password_recovery_and_repeated_login_failures&amp;diff=106075"/>
		<updated>2016-12-02T19:58:04Z</updated>

		<summary type="html">&lt;p&gt;Vdatla: &lt;/p&gt;
&lt;hr /&gt;
&lt;div&gt;==E1690 Improvements to password recovery and repeated login failures==&lt;br /&gt;
&lt;br /&gt;
This wiki page is for the description of changes made under E1690 FinalProject for Fall 2016, CSC/ECE 517.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
__TOC__&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
===Background===&lt;br /&gt;
&lt;br /&gt;
Expertiza is an Open Source web application developed on Ruby On Rails platform. It is a platform which allows students to access assignments posted by the course instructor. Expertiza also allows students to select assignment topics, form teams and submit their work. It also allows them to review other students' submissions and improve their work based on the feedback provided. The instructor can look at the feedback provided by students and rate the student based on feedback provided for others work.&lt;br /&gt;
It helps organize and upload assignments and reducing the manual review process and helps students provide a peer feedback and also learn from reviewed work. Teams can be chosen by the student or can be assigned automatically based on a priority list inputted alongside each topic available for the assignment.&lt;br /&gt;
&lt;br /&gt;
===Project Description===&lt;br /&gt;
&lt;br /&gt;
Our final project consists of two cases of the password recovery process. Use case 1, Currently, when a user forgets his/her password and wants to reset the password, Expertiza system randomly generates a new password and sends the password as plain text in a email. It is normally considered as a bad practice to send passwords as paint text. We are replacing this practice by sending a reset password link that expires after a certain amount of time.  Use case 2 deals with when a user enters wrong credentials. Currently, the login page simply shows an error. Irrespective of the number of times that a user enters wrong login credentials, the system produces a general error message.  We are going to be replacing this system by using the alternative 2, using a captcha to verify that the user is indeed a human and not a bot trying to run a brute force attack on the system.  This will add the needed layer of security and should serve as a great solution.  Below are more details of our planned implementation.  &lt;br /&gt;
&lt;br /&gt;
===Files Created/Modified===&lt;br /&gt;
As a part of the project the files mentioned below were the ones, created/modified as needed.&lt;br /&gt;
* auth_controller.rb&lt;br /&gt;
* reset_password.rb (model)&lt;br /&gt;
* reset_password.html.erb (vie)&lt;br /&gt;
&lt;br /&gt;
===Implementation===&lt;br /&gt;
We are going to implement the new password recovery system by sending a reset password link to the users email. This link will be comprised of a generated path to a newly created view for resetting the password with a uniquely randomly generated parameter.  This parameter will be a string attribute of a new model we are creating called reset_password.  This link will expire after a given amount of time. Using logic to compare the createdAt timestamp as well as the current time, we would be able to program the idea of an expired link.  &lt;br /&gt;
&lt;br /&gt;
We are also implementing a backoff system that will require the user to complete a smart captcha after 3 failed attempts.  This smart captcha will be generated through Recaptcha gem and the user will then be redirected to the login page after successfully changing the password.  This will ensure that the system is not vulnerable to Brute Force attacks as well as bots.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
==Password Reset==&lt;br /&gt;
&lt;br /&gt;
===Model Schema===&lt;br /&gt;
Model: reset_password&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
Attributes&lt;br /&gt;
*-id(autogenerated)   -integer&lt;br /&gt;
*-unique_tokenhash       -String&lt;br /&gt;
*-createdAt    (autogenerated) -timestamp&lt;br /&gt;
*-user_id -integer (Foreign key to user table)&lt;br /&gt;
&lt;br /&gt;
'''Model Details'''&lt;br /&gt;
&lt;br /&gt;
When the user clicks on reset password, it will redirect to a view that has an input to enter the email address of the user. Reset password button will generate a random token (Long string) which will be hashed and saved in the database of the model reset_password. An expiration date will be generated and saved along with the user_id by looking up the user table using email id. The unhashed Token value will be appended on the url emailed to the user for the password reset page.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
www.expertiza.com/resetPass?username=random&amp;amp;token=ZB71yObR-Tdssg-@#%&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
On clicking the url, the link will take you to a controller that will direct you to a reset page. Before redirecting , the controller checks the parameters in the link (username and token) and makes sure that token username pair exists and not expired. Token from the params will be hashed again and checked with the db. This prevents an attacker who has read access to the database from making a token for some other user, reading the value that was sent in the email, then sending the same value himself. Once the controller completes all the necessary checks, it will redirect to a reset password page for that specific user (based on the user_id / username) &lt;br /&gt;
&lt;br /&gt;
[[File:Capture password reset.JPG]]&lt;br /&gt;
&lt;br /&gt;
==Captcha==&lt;br /&gt;
&lt;br /&gt;
The project will be using ReCAPTCHA gem. ReCAPTCHA is a free service from Google that helps protect websites from spam and abuse. A “CAPTCHA” is a test to tell humans and robot apart. This kind of service is important for websites or web applications with lots of user generated content. The test is easy for a human to solve, but hard for bots and other malicious software to figure out.&lt;br /&gt;
&lt;br /&gt;
After 3 failed Login attempts, a captcha would appear to make sure that a bot or a malicious software is not trying to attempt login using brute force.&lt;br /&gt;
&lt;br /&gt;
[[File:Captcha.png]]&lt;br /&gt;
&lt;br /&gt;
==== Gem File ====&lt;br /&gt;
Adding this line to the Gem file allows us to have access to the recaptcha gem.&lt;br /&gt;
&lt;br /&gt;
&amp;lt;pre&amp;gt;gem &amp;quot;recaptcha&amp;quot;, require: &amp;quot;recaptcha/rails&amp;quot;&amp;lt;/pre&amp;gt;&lt;br /&gt;
&lt;br /&gt;
==== Backoff System ====&lt;br /&gt;
In Auth Controller we added the following code.  The variable @@attempts acts as a counter to track the amount of invalid login attempts a user makes.  By utilizing the existing login code we were able to place the increment code.  Once the attempts variable is greater than or equal to 3 we then force the user to use the recaptcha question in addition to their correct logic credentials.  Once the new requirements to login are satisfied the user is redirected to the password retrieval, otherwise they are redirected to the root screen with the captcha question.  &lt;br /&gt;
&amp;lt;pre&amp;gt;&lt;br /&gt;
  @@attemps = 0&lt;br /&gt;
&lt;br /&gt;
  def login&lt;br /&gt;
    if request.get?&lt;br /&gt;
      AuthController.clear_session(session)&lt;br /&gt;
    else&lt;br /&gt;
      user = User.find_by_login(params[:login][:name])&lt;br /&gt;
      if user and user.valid_password?(params[:login][:password])&lt;br /&gt;
        after_login(user)&lt;br /&gt;
      else&lt;br /&gt;
&lt;br /&gt;
        @@attemps = @@attemps + 1&lt;br /&gt;
        logger.warn &amp;quot;Failed login attempt.&amp;quot;&lt;br /&gt;
        flash[:error] = &amp;quot;Your username or password is incorrect.&amp;quot;&lt;br /&gt;
        if @@attemps &amp;gt;= 3                                                         ##User entered invalid login credentials at least 3 times&lt;br /&gt;
            if verify_recaptcha(model: @user)&lt;br /&gt;
              @@attemps = 0&lt;br /&gt;
              redirect_to controller: 'password_retrieval', action: 'forgotten'&lt;br /&gt;
            end&lt;br /&gt;
&lt;br /&gt;
        else&lt;br /&gt;
          redirect_to root_path&lt;br /&gt;
&lt;br /&gt;
        end&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
      end&lt;br /&gt;
    end&lt;br /&gt;
  end # def login&lt;br /&gt;
&lt;br /&gt;
&amp;lt;/pre&amp;gt;&lt;br /&gt;
&lt;br /&gt;
==Testing==&lt;br /&gt;
&lt;br /&gt;
To run the Rspecs test cases:&lt;br /&gt;
 rspec path_to_expertiza/spec/controllers/password_retrieval_controller_spec.rb &lt;br /&gt;
&lt;br /&gt;
To test from UI:&lt;br /&gt;
 i)  Enter the wrong password on login page three consecutive times, you will shown with Google Captcha for the fourth attempt.&lt;br /&gt;
 ii) On entering the password, wrong the fourth time you will be redirected to &amp;quot;forgot password&amp;quot; page. It can also be reached by clicking &amp;quot;forgot password&amp;quot; page on login page.&lt;br /&gt;
 iii) Enter the email Id, for which new password has to be set. On clicking &amp;quot;Request password&amp;quot; you will get a mail with password reset link. &lt;br /&gt;
 iv) Clicking on the password reset link, you will be redirected to password reset page where you can set your new password. &lt;br /&gt;
&lt;br /&gt;
Here is a short [http://recordit.co/pXq9jM9xhr video] demonstrating the same.&lt;/div&gt;</summary>
		<author><name>Vdatla</name></author>
	</entry>
	<entry>
		<id>https://wiki.expertiza.ncsu.edu/index.php?title=CSC/ECE_517_Fall_2016/E1690_Improvements_to_password_recovery_and_repeated_login_failures&amp;diff=106074</id>
		<title>CSC/ECE 517 Fall 2016/E1690 Improvements to password recovery and repeated login failures</title>
		<link rel="alternate" type="text/html" href="https://wiki.expertiza.ncsu.edu/index.php?title=CSC/ECE_517_Fall_2016/E1690_Improvements_to_password_recovery_and_repeated_login_failures&amp;diff=106074"/>
		<updated>2016-12-02T19:49:08Z</updated>

		<summary type="html">&lt;p&gt;Vdatla: /* Backoff System */&lt;/p&gt;
&lt;hr /&gt;
&lt;div&gt;==E1690 Improvements to password recovery and repeated login failures==&lt;br /&gt;
&lt;br /&gt;
This wiki page is for the description of changes made under E1690 FinalProject for Fall 2016, CSC/ECE 517.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
__TOC__&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
===Background===&lt;br /&gt;
&lt;br /&gt;
Expertiza is an Open Source web application developed on Ruby On Rails platform. It is a platform which allows students to access assignments posted by the course instructor. Expertiza also allows students to select assignment topics, form teams and submit their work. It also allows them to review other students' submissions and improve their work based on the feedback provided. The instructor can look at the feedback provided by students and rate the student based on feedback provided for others work.&lt;br /&gt;
It helps organize and upload assignments and reducing the manual review process and helps students provide a peer feedback and also learn from reviewed work. Teams can be chosen by the student or can be assigned automatically based on a priority list inputted alongside each topic available for the assignment.&lt;br /&gt;
&lt;br /&gt;
===Project Description===&lt;br /&gt;
&lt;br /&gt;
Our final project consists of two cases of the password recovery process. Use case 1, Currently, when a user forgets his/her password and wants to reset the password, Expertiza system randomly generates a new password and sends the password as plain text in a email. It is normally considered as a bad practice to send passwords as paint text. We are replacing this practice by sending a reset password link that expires after a certain amount of time.  Use case 2 deals with when a user enters wrong credentials. Currently, the login page simply shows an error. Irrespective of the number of times that a user enters wrong login credentials, the system produces a general error message.  We are going to be replacing this system by using the alternative 2, using a captcha to verify that the user is indeed a human and not a bot trying to run a brute force attack on the system.  This will add the needed layer of security and should serve as a great solution.  Below are more details of our planned implementation.  &lt;br /&gt;
&lt;br /&gt;
===Files Created/Modified===&lt;br /&gt;
As a part of the project the files mentioned below were the ones, created/modified as needed.&lt;br /&gt;
* auth_controller.rb&lt;br /&gt;
* reset_password.rb (model)&lt;br /&gt;
* reset_password.html.erb (vie)&lt;br /&gt;
&lt;br /&gt;
===Implementation===&lt;br /&gt;
We are going to implement the new password recovery system by sending a reset password link to the users email. This link will be comprised of a generated path to a newly created view for resetting the password with a uniquely randomly generated parameter.  This parameter will be a string attribute of a new model we are creating called reset_password.  This link will expire after a given amount of time. Using logic to compare the createdAt timestamp as well as the current time, we would be able to program the idea of an expired link.  &lt;br /&gt;
&lt;br /&gt;
We are also implementing a backoff system that will require the user to complete a smart captcha after 3 failed attempts.  This smart captcha will be generated through Recaptcha gem and the user will then be redirected to the login page after successfully changing the password.  This will ensure that the system is not vulnerable to Brute Force attacks as well as bots.&lt;br /&gt;
==== Gem File ====&lt;br /&gt;
Adding this line to the Gem file allows us to have access to the recaptcha gem.&lt;br /&gt;
&lt;br /&gt;
&amp;lt;pre&amp;gt;gem &amp;quot;recaptcha&amp;quot;, require: &amp;quot;recaptcha/rails&amp;quot;&amp;lt;/pre&amp;gt;&lt;br /&gt;
&lt;br /&gt;
==== Backoff System ====&lt;br /&gt;
In Auth Controller we added the following code.  The variable @@attempts acts as a counter to track the amount of invalid login attempts a user makes.  By utilizing the existing login code we were able to place the increment code.  Once the attempts variable is greater than or equal to 3 we then force the user to use the recaptcha question in addition to their correct logic credentials.  Once the new requirements to login are satisfied the user is redirected to the password retrieval, otherwise they are redirected to the root screen with the captcha question.  &lt;br /&gt;
&amp;lt;pre&amp;gt;&lt;br /&gt;
  @@attemps = 0&lt;br /&gt;
&lt;br /&gt;
  def login&lt;br /&gt;
    if request.get?&lt;br /&gt;
      AuthController.clear_session(session)&lt;br /&gt;
    else&lt;br /&gt;
      user = User.find_by_login(params[:login][:name])&lt;br /&gt;
      if user and user.valid_password?(params[:login][:password])&lt;br /&gt;
        after_login(user)&lt;br /&gt;
      else&lt;br /&gt;
&lt;br /&gt;
        @@attemps = @@attemps + 1&lt;br /&gt;
        logger.warn &amp;quot;Failed login attempt.&amp;quot;&lt;br /&gt;
        flash[:error] = &amp;quot;Your username or password is incorrect.&amp;quot;&lt;br /&gt;
        if @@attemps &amp;gt;= 3                                                         ##User entered invalid login credentials at least 3 times&lt;br /&gt;
            if verify_recaptcha(model: @user)&lt;br /&gt;
              @@attemps = 0&lt;br /&gt;
              redirect_to controller: 'password_retrieval', action: 'forgotten'&lt;br /&gt;
            end&lt;br /&gt;
&lt;br /&gt;
        else&lt;br /&gt;
          redirect_to root_path&lt;br /&gt;
&lt;br /&gt;
        end&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
      end&lt;br /&gt;
    end&lt;br /&gt;
  end # def login&lt;br /&gt;
&lt;br /&gt;
&amp;lt;/pre&amp;gt;&lt;br /&gt;
&lt;br /&gt;
==Password Reset==&lt;br /&gt;
&lt;br /&gt;
===Model Schema===&lt;br /&gt;
Model: reset_password&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
Attributes&lt;br /&gt;
*-id(autogenerated)   -integer&lt;br /&gt;
*-unique_tokenhash       -String&lt;br /&gt;
*-createdAt    (autogenerated) -timestamp&lt;br /&gt;
*-user_id -integer (Foreign key to user table)&lt;br /&gt;
&lt;br /&gt;
'''Model Details'''&lt;br /&gt;
&lt;br /&gt;
When the user clicks on reset password, it will redirect to a view that has an input to enter the email address of the user. Reset password button will generate a random token (Long string) which will be hashed and saved in the database of the model reset_password. An expiration date will be generated and saved along with the user_id by looking up the user table using email id. The unhashed Token value will be appended on the url emailed to the user for the password reset page.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
www.expertiza.com/resetPass?username=random&amp;amp;token=ZB71yObR-Tdssg-@#%&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
On clicking the url, the link will take you to a controller that will direct you to a reset page. Before redirecting , the controller checks the parameters in the link (username and token) and makes sure that token username pair exists and not expired. Token from the params will be hashed again and checked with the db. This prevents an attacker who has read access to the database from making a token for some other user, reading the value that was sent in the email, then sending the same value himself. Once the controller completes all the necessary checks, it will redirect to a reset password page for that specific user (based on the user_id / username) &lt;br /&gt;
&lt;br /&gt;
[[File:Capture password reset.JPG]]&lt;br /&gt;
&lt;br /&gt;
==Captcha==&lt;br /&gt;
&lt;br /&gt;
The project will be using ReCAPTCHA gem. ReCAPTCHA is a free service from Google that helps protect websites from spam and abuse. A “CAPTCHA” is a test to tell humans and robot apart. This kind of service is important for websites or web applications with lots of user generated content. The test is easy for a human to solve, but hard for bots and other malicious software to figure out.&lt;br /&gt;
&lt;br /&gt;
After 3 failed Login attempts, a captcha would appear to make sure that a bot or a malicious software is not trying to attempt login using brute force.&lt;br /&gt;
&lt;br /&gt;
[[File:Captcha.png]]&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
==Testing==&lt;br /&gt;
&lt;br /&gt;
To run the Rspecs test cases:&lt;br /&gt;
 rspec path_to_expertiza/spec/controllers/password_retrieval_controller_spec.rb &lt;br /&gt;
&lt;br /&gt;
To test from UI:&lt;br /&gt;
 i)  Enter the wrong password on login page three consecutive times, you will shown with Google Captcha for the fourth attempt.&lt;br /&gt;
 ii) On entering the password, wrong the fourth time you will be redirected to &amp;quot;forgot password&amp;quot; page. It can also be reached by clicking &amp;quot;forgot password&amp;quot; page on login page.&lt;br /&gt;
 iii) Enter the email Id, for which new password has to be set. On clicking &amp;quot;Request password&amp;quot; you will get a mail with password reset link. &lt;br /&gt;
 iv) Clicking on the password reset link, you will be redirected to password reset page where you can set your new password. &lt;br /&gt;
&lt;br /&gt;
Here is a short [http://recordit.co/pXq9jM9xhr video] demonstrating the same.&lt;/div&gt;</summary>
		<author><name>Vdatla</name></author>
	</entry>
	<entry>
		<id>https://wiki.expertiza.ncsu.edu/index.php?title=CSC/ECE_517_Fall_2016/E1690_Improvements_to_password_recovery_and_repeated_login_failures&amp;diff=105772</id>
		<title>CSC/ECE 517 Fall 2016/E1690 Improvements to password recovery and repeated login failures</title>
		<link rel="alternate" type="text/html" href="https://wiki.expertiza.ncsu.edu/index.php?title=CSC/ECE_517_Fall_2016/E1690_Improvements_to_password_recovery_and_repeated_login_failures&amp;diff=105772"/>
		<updated>2016-11-15T01:02:51Z</updated>

		<summary type="html">&lt;p&gt;Vdatla: &lt;/p&gt;
&lt;hr /&gt;
&lt;div&gt;==E1690 Improvements to password recovery and repeated login failures==&lt;br /&gt;
&lt;br /&gt;
This wiki page is for the description of changes made under E1690 FinalProject for Fall 2016, CSC/ECE 517.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
__TOC__&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
===Background===&lt;br /&gt;
&lt;br /&gt;
Expertiza is an Open Source web application developed on Ruby On Rails platform. It is a platform which allows students to access assignments posted by the course instructor. Expertiza also allows students to select assignment topics, form teams and submit their work. It also allows them to review other students' submissions and improve their work based on the feedback provided. The instructor can look at the feedback provided by students and rate the student based on feedback provided for others work.&lt;br /&gt;
It helps organize and upload assignments and reducing the manual review process and helps students provide a peer feedback and also learn from reviewed work. Teams can be chosen by the student or can be assigned automatically based on a priority list inputted alongside each topic available for the assignment.&lt;br /&gt;
&lt;br /&gt;
===Project Description===&lt;br /&gt;
&lt;br /&gt;
Our final project consists of two cases of the password recovery process. Use case 1, Currently, when a user forgets his/her password and wants to reset the password, Expertiza system randomly generates a new password and sends the password as plain text in a email. It is normally considered as a bad practice to send passwords as paint text. We are replacing this practice by sending a reset password link that expires after a certain amount of time.  Use case 2 deals with when a user enters wrong credentials. Currently, the login page simply shows an error. Irrespective of the number of times that a user enters wrong login credentials, the system produces a general error message.  We are going to be replacing this system by using the alternative 2, using a captcha to verify that the user is indeed a human and not a bot trying to run a brute force attack on the system.  This will add the needed layer of security and should serve as a great solution.  Below are more details of our planned implementation.  &lt;br /&gt;
&lt;br /&gt;
===Files Created/Modified===&lt;br /&gt;
As a part of the project the files mentioned below were the ones, created/modified as needed.&lt;br /&gt;
* auth_controller.rb&lt;br /&gt;
* reset_password.rb (model)&lt;br /&gt;
* reset_password.html.erb (vie)&lt;br /&gt;
&lt;br /&gt;
===Implementation===&lt;br /&gt;
We are going to implement the new password recovery system by sending a reset password link to the users email. This link will be comprised of a generated path to a newly created view for resetting the password with a uniquely randomly generated parameter.  This parameter will be a string attribute of a new model we are creating called reset_password.  This link will expire after a given amount of time. Using logic to compare the createdAt timestamp as well as the current time, we would be able to program the idea of an expired link.  &lt;br /&gt;
&lt;br /&gt;
We are also implementing a backoff system that will require the user to complete a smart captcha after 3 failed attempts.  This smart captcha will be generated through Recaptcha gem and the user will then be redirected to the login page after successfully changing the password.  This will ensure that the system is not vulnerable to Brute Force attacks as well as bots. &lt;br /&gt;
&lt;br /&gt;
==Password Reset==&lt;br /&gt;
&lt;br /&gt;
===Model Schema===&lt;br /&gt;
Model: reset_password&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
Attributes&lt;br /&gt;
*-id(autogenerated)   -integer&lt;br /&gt;
*-unique_tokenhash       -String&lt;br /&gt;
*-createdAt    (autogenerated) -timestamp&lt;br /&gt;
*-user_id -integer (Foreign key to user table)&lt;br /&gt;
&lt;br /&gt;
'''Model Details'''&lt;br /&gt;
&lt;br /&gt;
When the user clicks on reset password, it will redirect to a view that has an input to enter the email address of the user. Reset password button will generate a random token (Long string) which will be hashed and saved in the database of the model reset_password. An expiration date will be generated and saved along with the user_id by looking up the user table using email id. The unhashed Token value will be appended on the url emailed to the user for the password reset page.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
www.expertiza.com/resetPass?username=random&amp;amp;token=ZB71yObR-Tdssg-@#%&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
On clicking the url, the link will take you to a controller that will direct you to a reset page. Before redirecting , the controller checks the parameters in the link (username and token) and makes sure that token username pair exists and not expired. Token from the params will be hashed again and checked with the db. This prevents an attacker who has read access to the database from making a token for some other user, reading the value that was sent in the email, then sending the same value himself. Once the controller completes all the necessary checks, it will redirect to a reset password page for that specific user (based on the user_id / username) &lt;br /&gt;
&lt;br /&gt;
[[File:Capture password reset.JPG]]&lt;br /&gt;
&lt;br /&gt;
==Captcha==&lt;br /&gt;
&lt;br /&gt;
The project will be using ReCAPTCHA gem. ReCAPTCHA is a free service from Google that helps protect websites from spam and abuse. A “CAPTCHA” is a test to tell humans and robot apart. This kind of service is important for websites or web applications with lots of user generated content. The test is easy for a human to solve, but hard for bots and other malicious software to figure out.&lt;br /&gt;
&lt;br /&gt;
After 3 failed Login attempts, a captcha would appear to make sure that a bot or a malicious software is not trying to attempt login using brute force.&lt;br /&gt;
&lt;br /&gt;
[[File:Captcha.png]]&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
==Test Cases==&lt;br /&gt;
&lt;br /&gt;
Following methods and functionalities will be tested using rspec&lt;br /&gt;
&lt;br /&gt;
* Check if Hash is being generated as per required.&lt;br /&gt;
* Check if targeted user_id and user_mail are extracted from db&lt;br /&gt;
* Check if the link generated is of desired format&lt;br /&gt;
* Check if mail functionality is called.&lt;br /&gt;
* Check if token and user_name are extracted from the url&lt;br /&gt;
* Check if successful reset password changes record in DB&lt;br /&gt;
* Check status triggered by reCAPTCHA Gem&lt;/div&gt;</summary>
		<author><name>Vdatla</name></author>
	</entry>
	<entry>
		<id>https://wiki.expertiza.ncsu.edu/index.php?title=CSC/ECE_517_Fall_2016/E1690_Improvements_to_password_recovery_and_repeated_login_failures&amp;diff=105769</id>
		<title>CSC/ECE 517 Fall 2016/E1690 Improvements to password recovery and repeated login failures</title>
		<link rel="alternate" type="text/html" href="https://wiki.expertiza.ncsu.edu/index.php?title=CSC/ECE_517_Fall_2016/E1690_Improvements_to_password_recovery_and_repeated_login_failures&amp;diff=105769"/>
		<updated>2016-11-15T01:00:41Z</updated>

		<summary type="html">&lt;p&gt;Vdatla: &lt;/p&gt;
&lt;hr /&gt;
&lt;div&gt;==E1690 Improvements to password recovery and repeated login failures==&lt;br /&gt;
&lt;br /&gt;
This wiki page is for the description of changes made under E1690 FinalProject for Fall 2016, CSC/ECE 517.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
__TOC__&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
===Background===&lt;br /&gt;
&lt;br /&gt;
Expertiza is an Open Source web application developed on Ruby On Rails platform. It is a platform which allows students to access assignments posted by the course instructor. Expertiza also allows students to select assignment topics, form teams and submit their work. It also allows them to review other students' submissions and improve their work based on the feedback provided. The instructor can look at the feedback provided by students and rate the student based on feedback provided for others work.&lt;br /&gt;
It helps organize and upload assignments and reducing the manual review process and helps students provide a peer feedback and also learn from reviewed work. Teams can be chosen by the student or can be assigned automatically based on a priority list inputted alongside each topic available for the assignment.&lt;br /&gt;
&lt;br /&gt;
===Project Description===&lt;br /&gt;
&lt;br /&gt;
Our final project consists of two cases of the password recovery process. Use case 1, Currently, when a user forgets his/her password and wants to reset the password, Expertiza system randomly generates a new password and sends the password as plain text in a email. It is normally considered as a bad practice to send passwords as paint text. We are replacing this practice by sending a reset password link that expires after a certain amount of time.  Use case 2 deals with when a user enters wrong credentials. Currently, the login page simply shows an error. Irrespective of the number of times that a user enters wrong login credentials, the system produces a general error message.  We are going to be replacing this system by using the alternative 2, using a captcha to verify that the user is indeed a human and not a bot trying to run a brute force attack on the system.  This will add the needed layer of security and should serve as a great solution.  Below are more details of our planned implementation.  &lt;br /&gt;
&lt;br /&gt;
===Files Created/Modified===&lt;br /&gt;
As a part of the project the files mentioned below were the ones, created/modified as needed.&lt;br /&gt;
* auth_controller.rb&lt;br /&gt;
* reset_password.rb (model)&lt;br /&gt;
* reset_password.html.erb (vie)&lt;br /&gt;
&lt;br /&gt;
===Implementation===&lt;br /&gt;
We are going to implement the new password recovery system by sending a reset password link to the users email. This link will be comprised of a generated path to a newly created view for resetting the password with a uniquely randomly generated parameter.  This parameter will be a string attribute of a new model we are creating called reset_password.  This link will expire after a given amount of time. Using logic to compare the createdAt timestamp as well as the current time, we would be able to program the idea of an expired link.  &lt;br /&gt;
&lt;br /&gt;
We are also implementing a backoff system that will require the user to complete a smart captcha after 3 failed attempts.  This smart captcha will be generated through Recaptcha gem and the user will then be redirected to the login page after successfully changing the password.  This will ensure that the system is not vulnerable to Brute Force attacks as well as bots. &lt;br /&gt;
&lt;br /&gt;
===Model Schema===&lt;br /&gt;
Model: reset_password&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
Attributes&lt;br /&gt;
*-id(autogenerated)   -integer&lt;br /&gt;
*-unique_tokenhash       -String&lt;br /&gt;
*-createdAt    (autogenerated) -timestamp&lt;br /&gt;
*-user_id -integer (Foreign key to user table)&lt;br /&gt;
&lt;br /&gt;
'''Model Details'''&lt;br /&gt;
&lt;br /&gt;
When the user clicks on reset password, it will redirect to a view that has an input to enter the email address of the user. Reset password button will generate a random token (Long string) which will be hashed and saved in the database of the model reset_password. An expiration date will be generated and saved along with the user_id by looking up the user table using email id. The unhashed Token value will be appended on the url emailed to the user for the password reset page.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
www.expertiza.com/resetPass?username=random&amp;amp;token=ZB71yObR-Tdssg-@#%&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
On clicking the url, the link will take you to a controller that will direct you to a reset page. Before redirecting , the controller checks the parameters in the link (username and token) and makes sure that token username pair exists and not expired. Token from the params will be hashed again and checked with the db. This prevents an attacker who has read access to the database from making a token for some other user, reading the value that was sent in the email, then sending the same value himself. Once the controller completes all the necessary checks, it will redirect to a reset password page for that specific user (based on the user_id / username) &lt;br /&gt;
&lt;br /&gt;
[[File:Capture password reset.JPG]]&lt;br /&gt;
&lt;br /&gt;
===Captcha===&lt;br /&gt;
&lt;br /&gt;
The project will be using ReCAPTCHA gem. ReCAPTCHA is a free service from Google that helps protect websites from spam and abuse. A “CAPTCHA” is a test to tell humans and robot apart. This kind of service is important for websites or web applications with lots of user generated content. The test is easy for a human to solve, but hard for bots and other malicious software to figure out.&lt;br /&gt;
&lt;br /&gt;
After 3 failed Login attempts, a captcha would appear to make sure that a bot or a malicious software is not trying to attempt login using brute force.&lt;br /&gt;
&lt;br /&gt;
[[File:Captcha.png]]&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
===Test Cases===&lt;br /&gt;
&lt;br /&gt;
Following methods and functionalities will be tested using rspec&lt;br /&gt;
&lt;br /&gt;
* Check if Hash is being generated as per required.&lt;br /&gt;
* Check if targeted user_id and user_mail are extracted from db&lt;br /&gt;
* Check if the link generated is of desired format&lt;br /&gt;
* Check if mail functionality is called.&lt;br /&gt;
* Check if token and user_name are extracted from the url&lt;br /&gt;
* Check if successful reset password changes record in DB&lt;br /&gt;
* Check status triggered by reCAPTCHA Gem&lt;/div&gt;</summary>
		<author><name>Vdatla</name></author>
	</entry>
	<entry>
		<id>https://wiki.expertiza.ncsu.edu/index.php?title=CSC/ECE_517_Fall_2016/E1690_Improvements_to_password_recovery_and_repeated_login_failures&amp;diff=105766</id>
		<title>CSC/ECE 517 Fall 2016/E1690 Improvements to password recovery and repeated login failures</title>
		<link rel="alternate" type="text/html" href="https://wiki.expertiza.ncsu.edu/index.php?title=CSC/ECE_517_Fall_2016/E1690_Improvements_to_password_recovery_and_repeated_login_failures&amp;diff=105766"/>
		<updated>2016-11-15T00:59:25Z</updated>

		<summary type="html">&lt;p&gt;Vdatla: &lt;/p&gt;
&lt;hr /&gt;
&lt;div&gt;==E1690 Improvements to password recovery and repeated login failures==&lt;br /&gt;
&lt;br /&gt;
This wiki page is for the description of changes made under E1690 FinalProject for Fall 2016, CSC/ECE 517.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
__TOC__&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
===Background===&lt;br /&gt;
&lt;br /&gt;
Expertiza is an Open Source web application developed on Ruby On Rails platform. It is a platform which allows students to access assignments posted by the course instructor. Expertiza also allows students to select assignment topics, form teams and submit their work. It also allows them to review other students' submissions and improve their work based on the feedback provided. The instructor can look at the feedback provided by students and rate the student based on feedback provided for others work.&lt;br /&gt;
It helps organize and upload assignments and reducing the manual review process and helps students provide a peer feedback and also learn from reviewed work. Teams can be chosen by the student or can be assigned automatically based on a priority list inputted alongside each topic available for the assignment.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
===Project Description===&lt;br /&gt;
&lt;br /&gt;
Our final project consists of two cases of the password recovery process. Use case 1, Currently, when a user forgets his/her password and wants to reset the password, Expertiza system randomly generates a new password and sends the password as plain text in a email. It is normally considered as a bad practice to send passwords as paint text. We are replacing this practice by sending a reset password link that expires after a certain amount of time.  Use case 2 deals with when a user enters wrong credentials. Currently, the login page simply shows an error. Irrespective of the number of times that a user enters wrong login credentials, the system produces a general error message.  We are going to be replacing this system by using the alternative 2, using a captcha to verify that the user is indeed a human and not a bot trying to run a brute force attack on the system.  This will add the needed layer of security and should serve as a great solution.  Below are more details of our planned implementation.  &lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
===Files Created/Modified===&lt;br /&gt;
As a part of the project the files mentioned below were the ones, created/modified as needed.&lt;br /&gt;
* auth_controller.rb&lt;br /&gt;
* reset_password.rb (model)&lt;br /&gt;
* reset_password.html.erb (vie)&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
===Implementation===&lt;br /&gt;
We are going to implement the new password recovery system by sending a reset password link to the users email. This link will be comprised of a generated path to a newly created view for resetting the password with a uniquely randomly generated parameter.  This parameter will be a string attribute of a new model we are creating called reset_password.  This link will expire after a given amount of time. Using logic to compare the createdAt timestamp as well as the current time, we would be able to program the idea of an expired link.  &lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
We are also implementing a backoff system that will require the user to complete a smart captcha after 3 failed attempts.  This smart captcha will be generated through Recaptcha gem and the user will then be redirected to the login page after successfully changing the password.  This will ensure that the system is not vulnerable to Brute Force attacks as well as bots. &lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
===Model Schema===&lt;br /&gt;
Model: reset_password&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
Attributes&lt;br /&gt;
*-id(autogenerated)   -integer&lt;br /&gt;
*-unique_tokenhash       -String&lt;br /&gt;
*-createdAt    (autogenerated) -timestamp&lt;br /&gt;
*-user_id -integer (Foreign key to user table)&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
'''Model Details'''&lt;br /&gt;
&lt;br /&gt;
When the user clicks on reset password, it will redirect to a view that has an input to enter the email address of the user. Reset password button will generate a random token (Long string) which will be hashed and saved in the database of the model reset_password. An expiration date will be generated and saved along with the user_id by looking up the user table using email id. The unhashed Token value will be appended on the url emailed to the user for the password reset page.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
www.expertiza.com/resetPass?username=random&amp;amp;token=ZB71yObR-Tdssg-@#%&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
On clicking the url, the link will take you to a controller that will direct you to a reset page. Before redirecting , the controller checks the parameters in the link (username and token) and makes sure that token username pair exists and not expired. Token from the params will be hashed again and checked with the db. This prevents an attacker who has read access to the database from making a token for some other user, reading the value that was sent in the email, then sending the same value himself. Once the controller completes all the necessary checks, it will redirect to a reset password page for that specific user (based on the user_id / username) &lt;br /&gt;
&lt;br /&gt;
[[File:Capture password reset.JPG]]&lt;br /&gt;
&lt;br /&gt;
===Captcha===&lt;br /&gt;
&lt;br /&gt;
The project will be using ReCAPTCHA gem. ReCAPTCHA is a free service from Google that helps protect websites from spam and abuse. A “CAPTCHA” is a test to tell humans and robot apart. This kind of service is important for websites or web applications with lots of user generated content. The test is easy for a human to solve, but hard for bots and other malicious software to figure out.&lt;br /&gt;
&lt;br /&gt;
After 3 failed Login attempts, a captcha would appear to make sure that a bot or a malicious software is not trying to attempt login using brute force.&lt;br /&gt;
&lt;br /&gt;
[[File:Captcha.png]]&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
===Test Cases===&lt;br /&gt;
&lt;br /&gt;
Following methods and functionalities will be tested using rspec&lt;br /&gt;
&lt;br /&gt;
* Check if Hash is being generated as per required.&lt;br /&gt;
* Check if targeted user_id and user_mail are extracted from db&lt;br /&gt;
* Check if the link generated is of desired format&lt;br /&gt;
* Check if mail functionality is called.&lt;br /&gt;
* Check if token and user_name are extracted from the url&lt;br /&gt;
* Check if successful reset password changes record in DB&lt;br /&gt;
* Check status triggered by reCAPTCHA Gem&lt;/div&gt;</summary>
		<author><name>Vdatla</name></author>
	</entry>
	<entry>
		<id>https://wiki.expertiza.ncsu.edu/index.php?title=CSC/ECE_517_Fall_2016/E1690_Improvements_to_password_recovery_and_repeated_login_failures&amp;diff=105765</id>
		<title>CSC/ECE 517 Fall 2016/E1690 Improvements to password recovery and repeated login failures</title>
		<link rel="alternate" type="text/html" href="https://wiki.expertiza.ncsu.edu/index.php?title=CSC/ECE_517_Fall_2016/E1690_Improvements_to_password_recovery_and_repeated_login_failures&amp;diff=105765"/>
		<updated>2016-11-15T00:58:09Z</updated>

		<summary type="html">&lt;p&gt;Vdatla: &lt;/p&gt;
&lt;hr /&gt;
&lt;div&gt;==E1690 Improvements to password recovery and repeated login failures==&lt;br /&gt;
&lt;br /&gt;
This wiki page is for the description of changes made under E1690 FinalProject for Fall 2016, CSC/ECE 517.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
__TOC__&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
===Background===&lt;br /&gt;
&lt;br /&gt;
Expertiza is an Open Source web application developed on Ruby On Rails platform. It is a platform which allows students to access assignments posted by the course instructor. Expertiza also allows students to select assignment topics, form teams and submit their work. It also allows them to review other students' submissions and improve their work based on the feedback provided. The instructor can look at the feedback provided by students and rate the student based on feedback provided for others work.&lt;br /&gt;
It helps organize and upload assignments and reducing the manual review process and helps students provide a peer feedback and also learn from reviewed work. Teams can be chosen by the student or can be assigned automatically based on a priority list inputted alongside each topic available for the assignment.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
===Project Description===&lt;br /&gt;
&lt;br /&gt;
Our final project consists of two cases of the password recovery process. Use case 1, Currently, when a user forgets his/her password and wants to reset the password, Expertiza system randomly generates a new password and sends the password as plain text in a email. It is normally considered as a bad practice to send passwords as paint text. We are replacing this practice by sending a reset password link that expires after a certain amount of time.  Use case 2 deals with when a user enters wrong credentials. Currently, the login page simply shows an error. Irrespective of the number of times that a user enters wrong login credentials, the system produces a general error message.  We are going to be replacing this system by using the alternative 2, using a captcha to verify that the user is indeed a human and not a bot trying to run a brute force attack on the system.  This will add the needed layer of security and should serve as a great solution.  Below are more details of our planned implementation.  &lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
===Files Created/Modified===&lt;br /&gt;
As a part of the project the files mentioned below were the ones, created/modified as needed.&lt;br /&gt;
* auth_controller.rb&lt;br /&gt;
* reset_password.rb (model)&lt;br /&gt;
* reset_password.html.erb (vie)&lt;br /&gt;
&lt;br /&gt;
===Implementation===&lt;br /&gt;
We are going to implement the new password recovery system by sending a reset password link to the users email. This link will be comprised of a generated path to a newly created view for resetting the password with a uniquely randomly generated parameter.  This parameter will be a string attribute of a new model we are creating called reset_password.  This link will expire after a given amount of time. Using logic to compare the createdAt timestamp as well as the current time, we would be able to program the idea of an expired link.  &lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
We are also implementing a backoff system that will require the user to complete a smart captcha after 3 failed attempts.  This smart captcha will be generated through Recaptcha gem and the user will then be redirected to the login page after successfully changing the password.  This will ensure that the system is not vulnerable to Brute Force attacks as well as bots. &lt;br /&gt;
&lt;br /&gt;
===Model Schema===&lt;br /&gt;
Model: reset_password&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
Attributes&lt;br /&gt;
-id(autogenerated)   -integer&lt;br /&gt;
-unique_tokenhash       -String&lt;br /&gt;
-createdAt    (autogenerated) -timestamp&lt;br /&gt;
-user_id -integer (Foreign key to user table)&lt;br /&gt;
&lt;br /&gt;
'''Model Details'''&lt;br /&gt;
When the user clicks on reset password, it will redirect to a view that has an input to enter the email address of the user. Reset password button will generate a random token (Long string) which will be hashed and saved in the database of the model reset_password. An expiration date will be generated and saved along with the user_id by looking up the user table using email id. The unhashed Token value will be appended on the url emailed to the user for the password reset page.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
www.expertiza.com/resetPass?username=random&amp;amp;token=ZB71yObR-Tdssg-@#%&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
On clicking the url, the link will take you to a controller that will direct you to a reset page. Before redirecting , the controller checks the parameters in the link (username and token) and makes sure that token username pair exists and not expired. Token from the params will be hashed again and checked with the db. This prevents an attacker who has read access to the database from making a token for some other user, reading the value that was sent in the email, then sending the same value himself. Once the controller completes all the necessary checks, it will redirect to a reset password page for that specific user (based on the user_id / username) &lt;br /&gt;
&lt;br /&gt;
[[File:Capture password reset.JPG]]&lt;br /&gt;
&lt;br /&gt;
===Captcha===&lt;br /&gt;
&lt;br /&gt;
The project will be using ReCAPTCHA gem. ReCAPTCHA is a free service from Google that helps protect websites from spam and abuse. A “CAPTCHA” is a test to tell humans and robot apart. This kind of service is important for websites or web applications with lots of user generated content. The test is easy for a human to solve, but hard for bots and other malicious software to figure out.&lt;br /&gt;
&lt;br /&gt;
After 3 failed Login attempts, a captcha would appear to make sure that a bot or a malicious software is not trying to attempt login using brute force.&lt;br /&gt;
&lt;br /&gt;
[[File:Captcha.png]]&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
===Test Cases===&lt;br /&gt;
&lt;br /&gt;
Following methods and functionalities will be tested using rspec&lt;br /&gt;
&lt;br /&gt;
* Check if Hash is being generated as per required.&lt;br /&gt;
* Check if targeted user_id and user_mail are extracted from db&lt;br /&gt;
* Check if the link generated is of desired format&lt;br /&gt;
* Check if mail functionality is called.&lt;br /&gt;
* Check if token and user_name are extracted from the url&lt;br /&gt;
* Check if successful reset password changes record in DB&lt;br /&gt;
* Check status triggered by reCAPTCHA Gem&lt;/div&gt;</summary>
		<author><name>Vdatla</name></author>
	</entry>
	<entry>
		<id>https://wiki.expertiza.ncsu.edu/index.php?title=CSC/ECE_517_Fall_2016/E1690_Improvements_to_password_recovery_and_repeated_login_failures&amp;diff=105764</id>
		<title>CSC/ECE 517 Fall 2016/E1690 Improvements to password recovery and repeated login failures</title>
		<link rel="alternate" type="text/html" href="https://wiki.expertiza.ncsu.edu/index.php?title=CSC/ECE_517_Fall_2016/E1690_Improvements_to_password_recovery_and_repeated_login_failures&amp;diff=105764"/>
		<updated>2016-11-15T00:56:45Z</updated>

		<summary type="html">&lt;p&gt;Vdatla: &lt;/p&gt;
&lt;hr /&gt;
&lt;div&gt;==E1690 Improvements to password recovery and repeated login failures==&lt;br /&gt;
&lt;br /&gt;
This wiki page is for the description of changes made under E1690 FinalProject for Fall 2016, CSC/ECE 517.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
__TOC__&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
===Background===&lt;br /&gt;
&lt;br /&gt;
Expertiza is an Open Source web application developed on Ruby On Rails platform. It is a platform which allows students to access assignments posted by the course instructor. Expertiza also allows students to select assignment topics, form teams and submit their work. It also allows them to review other students' submissions and improve their work based on the feedback provided. The instructor can look at the feedback provided by students and rate the student based on feedback provided for others work.&lt;br /&gt;
It helps organize and upload assignments and reducing the manual review process and helps students provide a peer feedback and also learn from reviewed work. Teams can be chosen by the student or can be assigned automatically based on a priority list inputted alongside each topic available for the assignment.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
===Project Description===&lt;br /&gt;
&lt;br /&gt;
Our final project consists of two cases of the password recovery process. Use case 1, Currently, when a user forgets his/her password and wants to reset the password, Expertiza system randomly generates a new password and sends the password as plain text in a email. It is normally considered as a bad practice to send passwords as paint text. We are replacing this practice by sending a reset password link that expires after a certain amount of time.  Use case 2 deals with when a user enters wrong credentials. Currently, the login page simply shows an error. Irrespective of the number of times that a user enters wrong login credentials, the system produces a general error message.  We are going to be replacing this system by using the alternative 2, using a captcha to verify that the user is indeed a human and not a bot trying to run a brute force attack on the system.  This will add the needed layer of security and should serve as a great solution.  Below are more details of our planned implementation.  &lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
===Files Created/Modified===&lt;br /&gt;
As a part of the project the files mentioned below were the ones, created/modified as needed.&lt;br /&gt;
1. auth_controller.rb&lt;br /&gt;
2. reset_password.rb (model)&lt;br /&gt;
3. reset_password.html.erb (vie)&lt;br /&gt;
&lt;br /&gt;
===Implementation===&lt;br /&gt;
We are going to implement the new password recovery system by sending a reset password link to the users email. This link will be comprised of a generated path to a newly created view for resetting the password with a uniquely randomly generated parameter.  This parameter will be a string attribute of a new model we are creating called reset_password.  This link will expire after a given amount of time. Using logic to compare the createdAt timestamp as well as the current time, we would be able to program the idea of an expired link.  &lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
We are also implementing a backoff system that will require the user to complete a smart captcha after 3 failed attempts.  This smart captcha will be generated through Recaptcha gem and the user will then be redirected to the login page after successfully changing the password.  This will ensure that the system is not vulnerable to Brute Force attacks as well as bots. &lt;br /&gt;
&lt;br /&gt;
===Model Schema===&lt;br /&gt;
Model: reset_password&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
Attributes&lt;br /&gt;
-id(autogenerated)   -integer&lt;br /&gt;
-unique_tokenhash       -String&lt;br /&gt;
-createdAt    (autogenerated) -timestamp&lt;br /&gt;
-user_id -integer (Foreign key to user table)&lt;br /&gt;
&lt;br /&gt;
'''Model Details'''&lt;br /&gt;
When the user clicks on reset password, it will redirect to a view that has an input to enter the email address of the user. Reset password button will generate a random token (Long string) which will be hashed and saved in the database of the model reset_password. An expiration date will be generated and saved along with the user_id by looking up the user table using email id. The unhashed Token value will be appended on the url emailed to the user for the password reset page.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
www.expertiza.com/resetPass?username=random&amp;amp;token=ZB71yObR-Tdssg-@#%&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
On clicking the url, the link will take you to a controller that will direct you to a reset page. Before redirecting , the controller checks the parameters in the link (username and token) and makes sure that token username pair exists and not expired. Token from the params will be hashed again and checked with the db. This prevents an attacker who has read access to the database from making a token for some other user, reading the value that was sent in the email, then sending the same value himself. Once the controller completes all the necessary checks, it will redirect to a reset password page for that specific user (based on the user_id / username) &lt;br /&gt;
&lt;br /&gt;
[[File:Capture password reset.JPG]]&lt;br /&gt;
&lt;br /&gt;
===Captcha===&lt;br /&gt;
&lt;br /&gt;
The project will be using ReCAPTCHA gem. ReCAPTCHA is a free service from Google that helps protect websites from spam and abuse. A “CAPTCHA” is a test to tell humans and robot apart. This kind of service is important for websites or web applications with lots of user generated content. The test is easy for a human to solve, but hard for bots and other malicious software to figure out.&lt;br /&gt;
&lt;br /&gt;
After 3 failed Login attempts, a captcha would appear to make sure that a bot or a malicious software is not trying to attempt login using brute force.&lt;br /&gt;
&lt;br /&gt;
[[File:Captcha.png]]&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
===Test Cases===&lt;br /&gt;
&lt;br /&gt;
Following methods and functionalities will be tested using rspec&lt;br /&gt;
&lt;br /&gt;
1. Check if Hash is being generated as per required.&lt;br /&gt;
2. Check if targeted user_id and user_mail are extracted from db&lt;br /&gt;
3. Check if the link generated is of desired format&lt;br /&gt;
4. Check if mail functionality is called.&lt;br /&gt;
5. Check if token and user_name are extracted from the url&lt;br /&gt;
6. Check if successful reset password changes record in DB&lt;br /&gt;
7. Check status triggered by reCAPTCHA Gem&lt;/div&gt;</summary>
		<author><name>Vdatla</name></author>
	</entry>
	<entry>
		<id>https://wiki.expertiza.ncsu.edu/index.php?title=CSC/ECE_517_Fall_2016/E1690_Improvements_to_password_recovery_and_repeated_login_failures&amp;diff=105763</id>
		<title>CSC/ECE 517 Fall 2016/E1690 Improvements to password recovery and repeated login failures</title>
		<link rel="alternate" type="text/html" href="https://wiki.expertiza.ncsu.edu/index.php?title=CSC/ECE_517_Fall_2016/E1690_Improvements_to_password_recovery_and_repeated_login_failures&amp;diff=105763"/>
		<updated>2016-11-15T00:56:02Z</updated>

		<summary type="html">&lt;p&gt;Vdatla: &lt;/p&gt;
&lt;hr /&gt;
&lt;div&gt;==E1690 Improvements to password recovery and repeated login failures==&lt;br /&gt;
&lt;br /&gt;
This wiki page is for the description of changes made under E1690 FinalProject for Fall 2016, CSC/ECE 517.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
__TOC__&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
===Background===&lt;br /&gt;
&lt;br /&gt;
Expertiza is an Open Source web application developed on Ruby On Rails platform. It is a platform which allows students to access assignments posted by the course instructor. Expertiza also allows students to select assignment topics, form teams and submit their work. It also allows them to review other students' submissions and improve their work based on the feedback provided. The instructor can look at the feedback provided by students and rate the student based on feedback provided for others work.&lt;br /&gt;
It helps organize and upload assignments and reducing the manual review process and helps students provide a peer feedback and also learn from reviewed work. Teams can be chosen by the student or can be assigned automatically based on a priority list inputted alongside each topic available for the assignment.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
===Project Description===&lt;br /&gt;
&lt;br /&gt;
Our final project consists of two cases of the password recovery process. Use case 1, Currently, when a user forgets his/her password and wants to reset the password, Expertiza system randomly generates a new password and sends the password as plain text in a email. It is normally considered as a bad practice to send passwords as paint text. We are replacing this practice by sending a reset password link that expires after a certain amount of time.  Use case 2 deals with when a user enters wrong credentials. Currently, the login page simply shows an error. Irrespective of the number of times that a user enters wrong login credentials, the system produces a general error message.  We are going to be replacing this system by using the alternative 2, using a captcha to verify that the user is indeed a human and not a bot trying to run a brute force attack on the system.  This will add the needed layer of security and should serve as a great solution.  Below are more details of our planned implementation.  &lt;br /&gt;
&lt;br /&gt;
===Files Created/Modified===&lt;br /&gt;
As a part of the project the files mentioned below were the ones, created/modified as needed.&lt;br /&gt;
auth_controller.rb&lt;br /&gt;
reset_password.rb (model)&lt;br /&gt;
reset_password.html.erb (vie)&lt;br /&gt;
&lt;br /&gt;
===Implementation===&lt;br /&gt;
We are going to implement the new password recovery system by sending a reset password link to the users email. This link will be comprised of a generated path to a newly created view for resetting the password with a uniquely randomly generated parameter.  This parameter will be a string attribute of a new model we are creating called reset_password.  This link will expire after a given amount of time. Using logic to compare the createdAt timestamp as well as the current time, we would be able to program the idea of an expired link.  &lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
We are also implementing a backoff system that will require the user to complete a smart captcha after 3 failed attempts.  This smart captcha will be generated through Recaptcha gem and the user will then be redirected to the login page after successfully changing the password.  This will ensure that the system is not vulnerable to Brute Force attacks as well as bots. &lt;br /&gt;
&lt;br /&gt;
===Model Schema===&lt;br /&gt;
Model: reset_password&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
Attributes&lt;br /&gt;
-id(autogenerated)   -integer&lt;br /&gt;
-unique_tokenhash       -String&lt;br /&gt;
-createdAt    (autogenerated) -timestamp&lt;br /&gt;
-user_id -integer (Foreign key to user table)&lt;br /&gt;
&lt;br /&gt;
'''Model Details'''&lt;br /&gt;
When the user clicks on reset password, it will redirect to a view that has an input to enter the email address of the user. Reset password button will generate a random token (Long string) which will be hashed and saved in the database of the model reset_password. An expiration date will be generated and saved along with the user_id by looking up the user table using email id. The unhashed Token value will be appended on the url emailed to the user for the password reset page.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
www.expertiza.com/resetPass?username=random&amp;amp;token=ZB71yObR-Tdssg-@#%&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
On clicking the url, the link will take you to a controller that will direct you to a reset page. Before redirecting , the controller checks the parameters in the link (username and token) and makes sure that token username pair exists and not expired. Token from the params will be hashed again and checked with the db. This prevents an attacker who has read access to the database from making a token for some other user, reading the value that was sent in the email, then sending the same value himself. Once the controller completes all the necessary checks, it will redirect to a reset password page for that specific user (based on the user_id / username) &lt;br /&gt;
&lt;br /&gt;
[[File:Capture password reset.JPG]]&lt;br /&gt;
&lt;br /&gt;
===Captcha===&lt;br /&gt;
&lt;br /&gt;
The project will be using ReCAPTCHA gem. ReCAPTCHA is a free service from Google that helps protect websites from spam and abuse. A “CAPTCHA” is a test to tell humans and robot apart. This kind of service is important for websites or web applications with lots of user generated content. The test is easy for a human to solve, but hard for bots and other malicious software to figure out.&lt;br /&gt;
&lt;br /&gt;
After 3 failed Login attempts, a captcha would appear to make sure that a bot or a malicious software is not trying to attempt login using brute force.&lt;br /&gt;
&lt;br /&gt;
[[File:Captcha.png]]&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
===Test Cases===&lt;br /&gt;
&lt;br /&gt;
Following methods and functionalities will be tested using rspec&lt;br /&gt;
&lt;br /&gt;
1. Check if Hash is being generated as per required.&lt;br /&gt;
2. Check if targeted user_id and user_mail are extracted from db&lt;br /&gt;
3. Check if the link generated is of desired format&lt;br /&gt;
4. Check if mail functionality is called.&lt;br /&gt;
5. Check if token and user_name are extracted from the url&lt;br /&gt;
6. Check if successful reset password changes record in DB&lt;br /&gt;
7. Check status triggered by reCAPTCHA Gem&lt;/div&gt;</summary>
		<author><name>Vdatla</name></author>
	</entry>
	<entry>
		<id>https://wiki.expertiza.ncsu.edu/index.php?title=File:Captcha.png&amp;diff=105750</id>
		<title>File:Captcha.png</title>
		<link rel="alternate" type="text/html" href="https://wiki.expertiza.ncsu.edu/index.php?title=File:Captcha.png&amp;diff=105750"/>
		<updated>2016-11-15T00:33:38Z</updated>

		<summary type="html">&lt;p&gt;Vdatla: &lt;/p&gt;
&lt;hr /&gt;
&lt;div&gt;&lt;/div&gt;</summary>
		<author><name>Vdatla</name></author>
	</entry>
	<entry>
		<id>https://wiki.expertiza.ncsu.edu/index.php?title=CSC/ECE_517_Fall_2016/E1690_Improvements_to_password_recovery_and_repeated_login_failures&amp;diff=105747</id>
		<title>CSC/ECE 517 Fall 2016/E1690 Improvements to password recovery and repeated login failures</title>
		<link rel="alternate" type="text/html" href="https://wiki.expertiza.ncsu.edu/index.php?title=CSC/ECE_517_Fall_2016/E1690_Improvements_to_password_recovery_and_repeated_login_failures&amp;diff=105747"/>
		<updated>2016-11-15T00:31:50Z</updated>

		<summary type="html">&lt;p&gt;Vdatla: &lt;/p&gt;
&lt;hr /&gt;
&lt;div&gt;==E1690 Improvements to password recovery and repeated login failures==&lt;br /&gt;
&lt;br /&gt;
This wiki page is for the description of changes made under E1690 FinalProject for Fall 2016, CSC/ECE 517.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
__TOC__&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
===Background===&lt;br /&gt;
&lt;br /&gt;
Expertiza is an Open Source web application developed on Ruby On Rails platform. It is a platform which allows students to access assignments posted by the course instructor. Expertiza also allows students to select assignment topics, form teams and submit their work. It also allows them to review other students' submissions and improve their work based on the feedback provided. The instructor can look at the feedback provided by students and rate the student based on feedback provided for others work.&lt;br /&gt;
It helps organize and upload assignments and reducing the manual review process and helps students provide a peer feedback and also learn from reviewed work. Teams can be chosen by the student or can be assigned automatically based on a priority list inputted alongside each topic available for the assignment.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
===Project Description===&lt;br /&gt;
&lt;br /&gt;
Our final project consists of two cases of the password recovery process. Use case 1, Currently, when a user forgets his/her password and wants to reset the password, Expertiza system randomly generates a new password and sends the password as plain text in a email. It is normally considered as a bad practice to send passwords as paint text. We are replacing this practice by sending a reset password link that expires after a certain amount of time.  Use case 2 deals with when a user enters wrong credentials. Currently, the login page simply shows an error. Irrespective of the number of times that a user enters wrong login credentials, the system produces a general error message.  We are going to be replacing this system by using the alternative 2, using a captcha to verify that the user is indeed a human and not a bot trying to run a brute force attack on the system.  This will add the needed layer of security and should serve as a great solution.  Below are more details of our planned implementation.  &lt;br /&gt;
&lt;br /&gt;
===Files Created/Modified===&lt;br /&gt;
As a part of the project the files mentioned below were the ones, created/modified as needed.&lt;br /&gt;
auth_controller.rb&lt;br /&gt;
reset_password.rb (model)&lt;br /&gt;
reset_password.html.erb (vie)&lt;br /&gt;
&lt;br /&gt;
===Implementation===&lt;br /&gt;
We are going to implement the new password recovery system by sending a reset password link to the users email. This link will be comprised of a generated path to a newly created view for resetting the password with a uniquely randomly generated parameter.  This parameter will be a string attribute of a new model we are creating called reset_password.  This link will expire after a given amount of time. Using logic to compare the createdAt timestamp as well as the current time, we would be able to program the idea of an expired link.  &lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
We are also implementing a backoff system that will require the user to complete a smart captcha after 3 failed attempts.  This smart captcha will be generated through Recaptcha gem and the user will then be redirected to the login page after successfully changing the password.  This will ensure that the system is not vulnerable to Brute Force attacks as well as bots. &lt;br /&gt;
&lt;br /&gt;
===Model Schema===&lt;br /&gt;
Model: reset_password&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
Attributes&lt;br /&gt;
-id(autogenerated)   -integer&lt;br /&gt;
-unique_tokenhash       -String&lt;br /&gt;
-createdAt    (autogenerated) -timestamp&lt;br /&gt;
-user_id -integer (Foreign key to user table)&lt;br /&gt;
&lt;br /&gt;
'''Model Details'''&lt;br /&gt;
When the user clicks on reset password, it will redirect to a view that has an input to enter the email address of the user. Reset password button will generate a random token (Long string) which will be hashed and saved in the database of the model reset_password. An expiration date will be generated and saved along with the user_id by looking up the user table using email id. The unhashed Token value will be appended on the url emailed to the user for the password reset page.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
www.expertiza.com/resetPass?username=random&amp;amp;token=ZB71yObR-Tdssg-@#%&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
On clicking the url, the link will take you to a controller that will direct you to a reset page. Before redirecting , the controller checks the parameters in the link (username and token) and makes sure that token username pair exists and not expired. Token from the params will be hashed again and checked with the db. This prevents an attacker who has read access to the database from making a token for some other user, reading the value that was sent in the email, then sending the same value himself. Once the controller completes all the necessary checks, it will redirect to a reset password page for that specific user (based on the user_id / username) &lt;br /&gt;
&lt;br /&gt;
[[File:Capture password reset.JPG]]&lt;br /&gt;
&lt;br /&gt;
===Captcha===&lt;br /&gt;
&lt;br /&gt;
The project will be using ReCAPTCHA gem. ReCAPTCHA is a free service from Google that helps protect websites from spam and abuse. A “CAPTCHA” is a test to tell humans and robot apart. This kind of service is important for websites or web applications with lots of user generated content. The test is easy for a human to solve, but hard for bots and other malicious software to figure out.&lt;br /&gt;
&lt;br /&gt;
After 3 failed Login attempts, a captcha would appear to make sure that a bot or a malicious software is not trying to attempt login using brute force.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
===References===&lt;br /&gt;
1. [https://en.wikipedia.org/wiki/RSpec wikipedia.org/wiki/RSpec] &amp;lt;br&amp;gt;&lt;br /&gt;
2. [http://rspec.info/ rspec.info/ ] &amp;lt;br&amp;gt;&lt;br /&gt;
3. [https://semaphoreci.com/community/tutorials/getting-started-with-rspec semaphoreci.com/community/tutorials/getting-started-with-rspec] &amp;lt;br&amp;gt;&lt;br /&gt;
4. [https://github.com/rspec/rspec github.com/rspec/rspec] &amp;lt;br&amp;gt;&lt;br /&gt;
5. [http://wiki.expertiza.ncsu.edu/index.php/Main_Page#Expertiza Expertiza Wiki ]&amp;lt;br&amp;gt;&lt;br /&gt;
6. [https://github.com/expertiza/expertiza Expertiza Github ]&amp;lt;br&amp;gt;&lt;br /&gt;
7. [http://expertiza.ncsu.edu Expertiza] &amp;lt;br&amp;gt;&lt;br /&gt;
8. [http://research.csc.ncsu.edu/efg/expertiza/papers Research Papers on Expertiza] &amp;lt;br&amp;gt;&lt;/div&gt;</summary>
		<author><name>Vdatla</name></author>
	</entry>
	<entry>
		<id>https://wiki.expertiza.ncsu.edu/index.php?title=File:Capture_password_reset.JPG&amp;diff=105746</id>
		<title>File:Capture password reset.JPG</title>
		<link rel="alternate" type="text/html" href="https://wiki.expertiza.ncsu.edu/index.php?title=File:Capture_password_reset.JPG&amp;diff=105746"/>
		<updated>2016-11-15T00:30:29Z</updated>

		<summary type="html">&lt;p&gt;Vdatla: &lt;/p&gt;
&lt;hr /&gt;
&lt;div&gt;&lt;/div&gt;</summary>
		<author><name>Vdatla</name></author>
	</entry>
	<entry>
		<id>https://wiki.expertiza.ncsu.edu/index.php?title=CSC/ECE_517_Fall_2016/E1690_Improvements_to_password_recovery_and_repeated_login_failures&amp;diff=105745</id>
		<title>CSC/ECE 517 Fall 2016/E1690 Improvements to password recovery and repeated login failures</title>
		<link rel="alternate" type="text/html" href="https://wiki.expertiza.ncsu.edu/index.php?title=CSC/ECE_517_Fall_2016/E1690_Improvements_to_password_recovery_and_repeated_login_failures&amp;diff=105745"/>
		<updated>2016-11-15T00:29:03Z</updated>

		<summary type="html">&lt;p&gt;Vdatla: Created page with &amp;quot;==E1690 Improvements to password recovery and repeated login failures==  This wiki page is for the description of changes made under E1690 FinalProject for Fall 2016, CSC/ECE 517...&amp;quot;&lt;/p&gt;
&lt;hr /&gt;
&lt;div&gt;==E1690 Improvements to password recovery and repeated login failures==&lt;br /&gt;
&lt;br /&gt;
This wiki page is for the description of changes made under E1690 FinalProject for Fall 2016, CSC/ECE 517.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
__TOC__&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
===Background===&lt;br /&gt;
&lt;br /&gt;
Expertiza is an Open Source web application developed on Ruby On Rails platform. It is a platform which allows students to access assignments posted by the course instructor. Expertiza also allows students to select assignment topics, form teams and submit their work. It also allows them to review other students' submissions and improve their work based on the feedback provided. The instructor can look at the feedback provided by students and rate the student based on feedback provided for others work.&lt;br /&gt;
It helps organize and upload assignments and reducing the manual review process and helps students provide a peer feedback and also learn from reviewed work. Teams can be chosen by the student or can be assigned automatically based on a priority list inputted alongside each topic available for the assignment.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
===Project Description===&lt;br /&gt;
&lt;br /&gt;
Our final project consists of two cases of the password recovery process. Use case 1, Currently, when a user forgets his/her password and wants to reset the password, Expertiza system randomly generates a new password and sends the password as plain text in a email. It is normally considered as a bad practice to send passwords as paint text. We are replacing this practice by sending a reset password link that expires after a certain amount of time.  Use case 2 deals with when a user enters wrong credentials. Currently, the login page simply shows an error. Irrespective of the number of times that a user enters wrong login credentials, the system produces a general error message.  We are going to be replacing this system by using the alternative 2, using a captcha to verify that the user is indeed a human and not a bot trying to run a brute force attack on the system.  This will add the needed layer of security and should serve as a great solution.  Below are more details of our planned implementation.  &lt;br /&gt;
&lt;br /&gt;
===Files Created/Modified===&lt;br /&gt;
As a part of the project the files mentioned below were the ones, created/modified as needed.&lt;br /&gt;
auth_controller.rb&lt;br /&gt;
reset_password.rb (model)&lt;br /&gt;
reset_password.html.erb (vie)&lt;br /&gt;
&lt;br /&gt;
===Implementation===&lt;br /&gt;
We are going to implement the new password recovery system by sending a reset password link to the users email. This link will be comprised of a generated path to a newly created view for resetting the password with a uniquely randomly generated parameter.  This parameter will be a string attribute of a new model we are creating called reset_password.  This link will expire after a given amount of time. Using logic to compare the createdAt timestamp as well as the current time, we would be able to program the idea of an expired link.  &lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
We are also implementing a backoff system that will require the user to complete a smart captcha after 3 failed attempts.  This smart captcha will be generated through Recaptcha gem and the user will then be redirected to the login page after successfully changing the password.  This will ensure that the system is not vulnerable to Brute Force attacks as well as bots. &lt;br /&gt;
&lt;br /&gt;
===Model Schema===&lt;br /&gt;
Model: reset_password&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
Attributes&lt;br /&gt;
-id(autogenerated)   -integer&lt;br /&gt;
-unique_tokenhash       -String&lt;br /&gt;
-createdAt    (autogenerated) -timestamp&lt;br /&gt;
-user_id -integer (Foreign key to user table)&lt;br /&gt;
&lt;br /&gt;
'''Model Details'''&lt;br /&gt;
When the user clicks on reset password, it will redirect to a view that has an input to enter the email address of the user. Reset password button will generate a random token (Long string) which will be hashed and saved in the database of the model reset_password. An expiration date will be generated and saved along with the user_id by looking up the user table using email id. The unhashed Token value will be appended on the url emailed to the user for the password reset page.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
www.expertiza.com/resetPass?username=random&amp;amp;token=ZB71yObR-Tdssg-@#%&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
On clicking the url, the link will take you to a controller that will direct you to a reset page. Before redirecting , the controller checks the parameters in the link (username and token) and makes sure that token username pair exists and not expired. Token from the params will be hashed again and checked with the db. This prevents an attacker who has read access to the database from making a token for some other user, reading the value that was sent in the email, then sending the same value himself. Once the controller completes all the necessary checks, it will redirect to a reset password page for that specific user (based on the user_id / username) &lt;br /&gt;
&lt;br /&gt;
[[File:Example.jpg]]&lt;br /&gt;
&lt;br /&gt;
===References===&lt;br /&gt;
1. [https://en.wikipedia.org/wiki/RSpec wikipedia.org/wiki/RSpec] &amp;lt;br&amp;gt;&lt;br /&gt;
2. [http://rspec.info/ rspec.info/ ] &amp;lt;br&amp;gt;&lt;br /&gt;
3. [https://semaphoreci.com/community/tutorials/getting-started-with-rspec semaphoreci.com/community/tutorials/getting-started-with-rspec] &amp;lt;br&amp;gt;&lt;br /&gt;
4. [https://github.com/rspec/rspec github.com/rspec/rspec] &amp;lt;br&amp;gt;&lt;br /&gt;
5. [http://wiki.expertiza.ncsu.edu/index.php/Main_Page#Expertiza Expertiza Wiki ]&amp;lt;br&amp;gt;&lt;br /&gt;
6. [https://github.com/expertiza/expertiza Expertiza Github ]&amp;lt;br&amp;gt;&lt;br /&gt;
7. [http://expertiza.ncsu.edu Expertiza] &amp;lt;br&amp;gt;&lt;br /&gt;
8. [http://research.csc.ncsu.edu/efg/expertiza/papers Research Papers on Expertiza] &amp;lt;br&amp;gt;&lt;/div&gt;</summary>
		<author><name>Vdatla</name></author>
	</entry>
	<entry>
		<id>https://wiki.expertiza.ncsu.edu/index.php?title=CSC/ECE_517_Fall_2016/E1670._Unit_tests_for_answers.rb&amp;diff=104045</id>
		<title>CSC/ECE 517 Fall 2016/E1670. Unit tests for answers.rb</title>
		<link rel="alternate" type="text/html" href="https://wiki.expertiza.ncsu.edu/index.php?title=CSC/ECE_517_Fall_2016/E1670._Unit_tests_for_answers.rb&amp;diff=104045"/>
		<updated>2016-10-30T15:48:17Z</updated>

		<summary type="html">&lt;p&gt;Vdatla: &lt;/p&gt;
&lt;hr /&gt;
&lt;div&gt;==E1670 . Unit tests for answers.rb==&lt;br /&gt;
&lt;br /&gt;
This wiki page is for the description of changes made under E1670 OSS assignment for Fall 2016, CSC/ECE 517.&lt;br /&gt;
&lt;br /&gt;
===NOTE to reviewers===&lt;br /&gt;
Mocks and factories are used in the unit tests so they can't be tested by UI.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
__TOC__&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
===Background===&lt;br /&gt;
&lt;br /&gt;
Expertiza is an Open Source web application developed on Ruby On Rails platform. It is a platform which allows students to access assignments posted by the course instructor. Expertiza also allows students to select assignment topics, form teams and submit their work. It also allows them to review other students' submissions and improve their work based on the feedback provided. The instructor can look at the feedback provided by students and rate the student based on feedback provided for others work.&lt;br /&gt;
It helps organize and upload assignments and reducing the manual review process and helps students provide a peer feedback and also learn from reviewed work. Teams can be chosen by the student or can be assigned automatically based on a priority list inputted alongside each topic available for the assignment.&lt;br /&gt;
&lt;br /&gt;
===Project Description===&lt;br /&gt;
&lt;br /&gt;
In Expertiza, each questionnaire contains many questions, those question may have different types (e.g. checkbox, criterion, etc). When a user fills in a rubric, the responses for each question will become an answer record. The responses of rubrics are stored in answers table in DB. The answer.rb is the model for the answers table in the Database. The Answer.rb model does not have any test cases corresponding to it and the aim of the project is to write fast, effective and flexible unit test cases that offer maximum code coverage.&lt;br /&gt;
&lt;br /&gt;
===Files Created/Modified===&lt;br /&gt;
As a part of the project the files mentioned below were the ones, created/modified as needed.&lt;br /&gt;
*answer_spec.rb (path /spec/models/answer_spec.rb)&lt;br /&gt;
*factories.rb   (path /spec/factory/)&lt;br /&gt;
&lt;br /&gt;
===RSpec===&lt;br /&gt;
====RSpec Introduction====&lt;br /&gt;
RSpec is a testing framework for Ruby for behavior-driven development (BDD) licensed under MIT. It is inspired by JBehave and contains fully integrated JMock based framework which has a very rich and powerful DSL (domain-specific language) which resembles a natural language specification.&lt;br /&gt;
Composed of multiple libraries structured to work together, RSpec provides encapsulated testing via the describe block to specify the behavior of the class and the context for the unit test case.&lt;br /&gt;
&lt;br /&gt;
==== Why RSpec? ====&lt;br /&gt;
RSpec is easy to learn and implement and can be used with other testing tools like Cucumber and Minitest independently. It is extremely powerful for testing states with complicated setup and also helps in tearing down complex code to access the objects required for testing&lt;br /&gt;
RSpec semantics encourage agile thinking and practice and it structures the tests in a more intuitive way.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
===Functions in answers.rb===&lt;br /&gt;
Listed below are the functionalities and the Rspec unit tests corresponding to the function names along with a list of scenarios tested.&lt;br /&gt;
&lt;br /&gt;
'''Function Name : Compute_scores'''&lt;br /&gt;
&lt;br /&gt;
Compute_scores is a function in model answer.rb which gives the average, maximum and minimum scores obtained in a series a responses/assessments. It has two input parameters: List of assessments and questions. The function iterates over each assessment to get the total score of that assessment. If the response or review is invalid, that assessment won’t be considered in the calculation of the score average. After iterating over all assessments, Max score, and Min scores are calculated along with the average score based on the number of valid assessments. Their scores are returned by the function.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
'''Rspec Unit Test : Compute_scores'''&lt;br /&gt;
&lt;br /&gt;
Following scenarios are tested:&lt;br /&gt;
&lt;br /&gt;
* To return scores as nil if the input list of assessments is nil. This is to make sure no Null Pointer exceptions are thrown by the code&lt;br /&gt;
*To return a particular score when a single valid assessment is given as an input.&lt;br /&gt;
*To return a particular score when multiple valid assessments are given as an input. This is to test the looping functionality of the method.&lt;br /&gt;
*To return a particular score when invalid assessments are given as an input. The validity and total scores are returned by a mock and not by the actual functions. This is to make the test cases less rigid so that failure of dependent functions do not disrupt the functionality of interface level tests.&lt;br /&gt;
*To return a particular score when invalid flag is nil. Invalid flag can either be 0,1 or nil. Nil situation is tested to prevent NullPointer Exceptions&lt;br /&gt;
*To check if the method get_total_score is called with the right parameters.&lt;br /&gt;
&lt;br /&gt;
This unit test uses a stub and returns a mock value.&lt;br /&gt;
&amp;lt;pre&amp;gt;&lt;br /&gt;
Answer.stub(:get_total_score)&lt;br /&gt;
&amp;lt;/pre&amp;gt;&lt;br /&gt;
This is to eliminate tight coupling between compute_scores and get_total_scores. Failure in get_total_scores wouldn't break the compute_scores test cases.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
'''Function Name : Get_total_scores'''&lt;br /&gt;
&lt;br /&gt;
This function is called by the Compute_scores method of the answer.rb model to compute the total score of an assessment. The input consists of assessment for which the total score is being calculated and the list of questions being evaluated in the assessment. The method uses questionnaire id from the questions and response id to obtain a score view questionnaire data. This score view is a read-only record. The questionnaire data mainly consists of q1_max_question_score, sum_of_weights and weighted_score. Before calculating the score, the function performs two crucial tasks. &lt;br /&gt;
*Checks if the answer for a scored question is nil. If it is nil or unanswered, the question will be ignored and not counted towards the score of this response.&lt;br /&gt;
* Calls the submission_valid function by passing the response record to set the @invalid flag based on the validity of the response.&lt;br /&gt;
The total score is calculated using the below formula&lt;br /&gt;
&lt;br /&gt;
&amp;lt;pre&amp;gt;&lt;br /&gt;
(weighted_score / (sum_of_weights * max_question_score)) * 100&lt;br /&gt;
&amp;lt;/pre&amp;gt;&lt;br /&gt;
&lt;br /&gt;
Any edge cases would return -1 indicating no score&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
'''Rspec Unit Test : Get_total_scores'''&lt;br /&gt;
&lt;br /&gt;
Following scenarios are tested:&lt;br /&gt;
&lt;br /&gt;
*To return an anticipated total score of a single response without any edge cases. Since this function will be called only on one response at a time, there is no need to test for multiple responses at the same time.&lt;br /&gt;
*To return an anticipated total score of a response where nil answer is for a scored question. This is to check if its weight gets removed from the sum_of_weights.&lt;br /&gt;
*To return -1 when the sum of weights becomes 0. This can happen when all the scored questions are unanswered. Return value of -1 is checked at the calling function to ensure if a score is returned or not.&lt;br /&gt;
*To return -1 when weighted_score of questionnaireData is nil&lt;br /&gt;
* To check if submission_valid is called. This method is called to set invalid flag to indicate whether the response entered is valid or not. The validity criteria is explained in the submission_valid? Function.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
This unit test uses two stubs and returns mock results&lt;br /&gt;
&amp;lt;pre&amp;gt;&lt;br /&gt;
ScoreView.stub(:find_by_sql)&lt;br /&gt;
&amp;lt;/pre&amp;gt;&lt;br /&gt;
&amp;lt;pre&amp;gt;&lt;br /&gt;
Answer.stub(:where)&lt;br /&gt;
&amp;lt;/pre&amp;gt;&lt;br /&gt;
This is to reduce the outcome of the test to depend on DB calls. For example, in case the connection to DB fails, this unit test would still pass making it less rigid.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
'''Function Name : submission_valid?'''&lt;br /&gt;
&lt;br /&gt;
This purpose of this function is to verify the validity of a review based on a deadline.  This function obtains a list of AssignmentDueDate objects  in descending order which is then compared against the current time to determine which deadlines are valid and which ones are not. The flag variable is used to represent whether or not a deadline was available in the previous iteration of the loop. If the flag is set to TRUE and the deadline is less than the current date, then latest_review_phase_start_time is set to this deadline. A list of ResubmissionTime objects is also retrieved from the controller. These objects are then compared against the then latest_review_phase_start_time variable to determine a response. &lt;br /&gt;
&lt;br /&gt;
Observations: The current implementation of the function is bugged. It retrieves a list of sorted AssignmentDueDate objects and proceeds to check if this list is empty. However, instead of exiting if the function if the list is empty, it carries on execution and raises an exception on hitting the for loop. &lt;br /&gt;
&lt;br /&gt;
*Checks if a review is valid or not by comparing its date with a list of deadlines.&lt;br /&gt;
*Returns 1 or 0 depending on validity&lt;br /&gt;
*Current implementation is bugged. Throws an exception if no AssignmentDueDate objects are passed, returns nil if any objects are passed.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
'''Rspec Unit Test : submission_valid?'''&lt;br /&gt;
&lt;br /&gt;
Following scenarios are tested:&lt;br /&gt;
&lt;br /&gt;
*Passing valid AssignmentDueDate objects&lt;br /&gt;
*Not passing any AssignmentDueDate objects&lt;br /&gt;
&lt;br /&gt;
When valid AssignmentDueDate objects are passed, stubs are used to create fake AssignmentDueDate Objects and ResubmissionTime objects. These objects are then populated with valid deadline dates and deadline_type values. These values are then supplied when requested by the submission_valid? Function rather than actually calling the function.  The current implementation of this test case expects the program to throw an error when it reaches the for loop. Once this bug is fixed, this test case may be re-written to test a more legitimate test case.&lt;br /&gt;
&lt;br /&gt;
In case an empty list of AssignmentDueDate objects is passed back to the submission_valid?() method. This would cause the function to return nil. When this function is fixed, the following test case may be re-written to test for a more legitimate test-case.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
This unit test uses two stubs and returns mock results&lt;br /&gt;
&amp;lt;pre&amp;gt;&lt;br /&gt;
AssignmentDueDate.stub_chain(:where, :order)&lt;br /&gt;
&amp;lt;/pre&amp;gt;&lt;br /&gt;
The above stub returns two AssignmentDueDate objects whenever the where() and order() method are chained on AssignmentDueDate.&lt;br /&gt;
&amp;lt;pre&amp;gt;&lt;br /&gt;
ResubmissionTime.stub_chain(:where, :order)&lt;br /&gt;
&amp;lt;/pre&amp;gt;&lt;br /&gt;
The above stub returns two ResubmissionTime objects whenever the where() and order() method are chained on ResubmissionTime.&lt;br /&gt;
&amp;lt;pre&amp;gt;&lt;br /&gt;
AssignmentDueDate.stub_chain(:where, :order)&lt;br /&gt;
&amp;lt;/pre&amp;gt;&lt;br /&gt;
This stub is used in the second test case to return nil objects.&lt;br /&gt;
&lt;br /&gt;
the stub_chain method can be used to create stubs where chained methods are expected.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
'''Function Name : answers_by_question, answers_by_question_for_reviewee,answers_by_question_for_reviewee_in_round'''&lt;br /&gt;
&lt;br /&gt;
These three functions are sql queries that hit the DB to get an output record after a series of selections and joins. SQL queries that hit DB often do not have a high priority when it comes to testing, so the project does not aggressively test these functions. However, these functions are tested to make sure the queries are able to find the right column names and tables successfully. Any change in the table schema would be detected in these test cases. The functionality of these queries are not tested but instead the existence of an output is tested. This ensures that answer.rb is able to make a successful db connection and is sync with the latest db schema. Since the function actually hits the DB, mocks can no longer be used, instead active records were created and saved in test db using FactoryGirl gem from the factories.rb. These records are cleared after every test case.&lt;br /&gt;
&lt;br /&gt;
Following factories were used to create records in the table&lt;br /&gt;
*question&lt;br /&gt;
*response_record&lt;br /&gt;
*response_map&lt;br /&gt;
*answer&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
'''Rspec Unit Test : answers_by_question, answers_by_question_for_reviewee,answers_by_question_for_reviewee_in_round'''&lt;br /&gt;
&lt;br /&gt;
The factories are created such a way that the query would return an output and the tests will pass if the query returns a non nil record. The functionality of these functions would be tested by the integration tests of the controller&lt;br /&gt;
&lt;br /&gt;
&amp;lt;pre&amp;gt;&lt;br /&gt;
describe &amp;quot;#test sql queries in answer.rb&amp;quot; do&lt;br /&gt;
&lt;br /&gt;
    it &amp;quot;returns answer by question record from db which is not empty&amp;quot; do&lt;br /&gt;
      assignment_id = 1&lt;br /&gt;
      q_id = 1&lt;br /&gt;
      expect(Answer.answers_by_question(assignment_id,q_id)).not_to be_empty&lt;br /&gt;
    end&lt;br /&gt;
&lt;br /&gt;
    it &amp;quot;returns answers by question for reviewee from the db which is not empty&amp;quot; do&lt;br /&gt;
      assignment_id = 1&lt;br /&gt;
      reviewee_id = 1&lt;br /&gt;
      q_id = 1	&lt;br /&gt;
      expect(Answer.answers_by_question_for_reviewee(assignment_id,reviewee_id,q_id)).not_to be_empty&lt;br /&gt;
    end&lt;br /&gt;
&lt;br /&gt;
    it &amp;quot;returns answers by question for reviewee in round from db which is not empty&amp;quot; do&lt;br /&gt;
      assignment_id = 1&lt;br /&gt;
      reviewee_id = 1&lt;br /&gt;
      q_id = 1&lt;br /&gt;
      round = 1&lt;br /&gt;
      expect(Answer.answers_by_question_for_reviewee_in_round(assignment_id,reviewee_id,q_id,round)).not_to be_empty&lt;br /&gt;
    end&lt;br /&gt;
  end&lt;br /&gt;
&amp;lt;/pre&amp;gt;&lt;br /&gt;
&lt;br /&gt;
'''Validation and Dependency  Rspec Test'''&lt;br /&gt;
&lt;br /&gt;
Apart from testing functions, the models are also tested for validations and external dependencies. Model answer.rb does not have any validations but does have a dependency on question.rb. Answer belongs_to question and this was tested using a simple dependency rspec test.&lt;br /&gt;
&amp;lt;pre&amp;gt;&lt;br /&gt;
it { should belong_to(:question) }&lt;br /&gt;
&amp;lt;/pre&amp;gt;&lt;br /&gt;
&lt;br /&gt;
===Running Rspec===&lt;br /&gt;
*To run the test suite for a particular file only( answer_spec.rb):&lt;br /&gt;
&amp;lt;pre&amp;gt;&lt;br /&gt;
root@ubuntu:~/expertiza$ rspec spec/models/answer_spec.rb&lt;br /&gt;
&amp;lt;/pre&amp;gt;&lt;br /&gt;
*To run the entire suite of test cases:&lt;br /&gt;
&amp;lt;pre&amp;gt;&lt;br /&gt;
root@ubuntu:~/expertiza$ rspec spec&lt;br /&gt;
&amp;lt;/pre&amp;gt;&lt;br /&gt;
&lt;br /&gt;
===Rspec Test Results===&lt;br /&gt;
&lt;br /&gt;
&amp;lt;pre&amp;gt;&lt;br /&gt;
1 deprecation warning total&lt;br /&gt;
&lt;br /&gt;
Finished in 12.39 seconds (files took 11.25 seconds to load)&lt;br /&gt;
17 examples, 0 failures&lt;br /&gt;
&lt;br /&gt;
Randomized with seed 37447&lt;br /&gt;
&lt;br /&gt;
Coverage report generated for RSpec to /home/root/expertiza/coverage. 998 / 3919 LOC (25.47%) covered.&lt;br /&gt;
[Coveralls] Outside the CI environment, not sending data.&lt;br /&gt;
&amp;lt;/pre&amp;gt;&lt;br /&gt;
&lt;br /&gt;
===References===&lt;br /&gt;
1. [https://en.wikipedia.org/wiki/RSpec wikipedia.org/wiki/RSpec] &amp;lt;br&amp;gt;&lt;br /&gt;
2. [http://rspec.info/ rspec.info/ ] &amp;lt;br&amp;gt;&lt;br /&gt;
3. [https://semaphoreci.com/community/tutorials/getting-started-with-rspec semaphoreci.com/community/tutorials/getting-started-with-rspec] &amp;lt;br&amp;gt;&lt;br /&gt;
4. [https://github.com/rspec/rspec github.com/rspec/rspec] &amp;lt;br&amp;gt;&lt;br /&gt;
5. [http://wiki.expertiza.ncsu.edu/index.php/Main_Page#Expertiza Expertiza Wiki ]&amp;lt;br&amp;gt;&lt;br /&gt;
6. [https://github.com/expertiza/expertiza Expertiza Github ]&amp;lt;br&amp;gt;&lt;br /&gt;
7. [http://expertiza.ncsu.edu Expertiza] &amp;lt;br&amp;gt;&lt;br /&gt;
8. [http://research.csc.ncsu.edu/efg/expertiza/papers Research Papers on Expertiza] &amp;lt;br&amp;gt;&lt;/div&gt;</summary>
		<author><name>Vdatla</name></author>
	</entry>
	<entry>
		<id>https://wiki.expertiza.ncsu.edu/index.php?title=CSC/ECE_517_Fall_2016/E1670._Unit_tests_for_answers.rb&amp;diff=103696</id>
		<title>CSC/ECE 517 Fall 2016/E1670. Unit tests for answers.rb</title>
		<link rel="alternate" type="text/html" href="https://wiki.expertiza.ncsu.edu/index.php?title=CSC/ECE_517_Fall_2016/E1670._Unit_tests_for_answers.rb&amp;diff=103696"/>
		<updated>2016-10-29T02:39:31Z</updated>

		<summary type="html">&lt;p&gt;Vdatla: /* Files Created/Modified */&lt;/p&gt;
&lt;hr /&gt;
&lt;div&gt;==E1670 . Unit tests for answers.rb==&lt;br /&gt;
&lt;br /&gt;
This wiki page is for the description of changes made under E1670 OSS assignment for Fall 2016, CSC/ECE 517.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
__TOC__&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
===Background===&lt;br /&gt;
&lt;br /&gt;
Expertiza is an Open Source web application developed on Ruby On Rails platform. It is a platform which allows students to take assignments posted by the course instructors. Expertiza allows students to select assignment topics, form teams and submit their work. It also allows them to review other students' submissions and improve their work based on this feedback.&lt;br /&gt;
&lt;br /&gt;
===Project Description===&lt;br /&gt;
&lt;br /&gt;
In Expertiza, each questionnaire contains many questions, those question may have different types (e.g. checkbox, criterion, etc). When a user fills in a rubric, the responses for each question will become an answer record. The responses of rubrics are stored in answers table in DB. The answer.rb is the model for the answers table in DB. Answer.rb model does not have any test cases and the aim of the project is to write fast, effective and flexible unit test cases that offer maximum code coverage.&lt;br /&gt;
&lt;br /&gt;
===Files Created/Modified===&lt;br /&gt;
*answer_spec.rb (path /spec/models/answer_spec.rb)&lt;br /&gt;
*factories.rb   (path /spec/factory/)&lt;br /&gt;
&lt;br /&gt;
===RSpec===&lt;br /&gt;
====RSpec Introduction====&lt;br /&gt;
RSpec is a testing framework for Ruby for behavior-driven development (BDD) licensed under MIT. It is inspired by JBehave and contains fully integrated JMock based framework which has a very rich and powerful DSL (domain-specific language) which resembles a natural language specification.&lt;br /&gt;
Composed of multiple libraries structured to work together, RSpec provides encapsulated testing via the describe block to specify the behavior of the class and the context for the unit test case.&lt;br /&gt;
&lt;br /&gt;
==== Why RSpec? ====&lt;br /&gt;
RSpec is easy to learn and implement and can be used with other testing tools like Cucumber and Minitest independently. It is extremely powerful for testing states with complicated setup and also helps in tearing down complex code to access the objects required for testing&lt;br /&gt;
RSpec semantics encourage agile thinking and practice and it structures the tests in a more intuitive way.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
===Functions in answers.rb===&lt;br /&gt;
&lt;br /&gt;
'''Function Name : Compute_scores'''&lt;br /&gt;
&lt;br /&gt;
Compute_scores is a function in model answer.rb which gives the average, maximum and minimum scores obtained in a series a responses/assessments. It has two input parameters: List of assessments and questions. The function iterates over each assessment to get the total score of that assessment. If the response or review is invalid, that assessment won’t be considered in the calculation of the score average. After iterating over all assessments, Max score, and Min scores are calculated along with the average score based on the number of valid assessments. Their scores are returned by the function.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
'''Rspec Unit Test : Compute_scores'''&lt;br /&gt;
&lt;br /&gt;
Following scenarios are tested:&lt;br /&gt;
&lt;br /&gt;
* To return scores as nil if the input list of assessments is nil. This is to make sure no Null Pointer exceptions are thrown by the code&lt;br /&gt;
*To return a particular score when a single valid assessment is given as an input.&lt;br /&gt;
*To return a particular score when multiple valid assessments are given as an input. This is to test the looping functionality of the method.&lt;br /&gt;
*To return a particular score when invalid assessments are given as an input. The validity and total scores are returned by a mock and not by the actual functions. This is to make the test cases less rigid so that failure of dependent functions do not disrupt the functionality of interface level tests.&lt;br /&gt;
*To return a particular score when invalid flag is nil. Invalid flag can either be 0,1 or nil. Nil situation is tested to prevent NullPointer Exceptions&lt;br /&gt;
*To check if the method get_total_score is called with the right parameters.&lt;br /&gt;
&lt;br /&gt;
This unit test uses a stub and returns a mock value.&lt;br /&gt;
&amp;lt;pre&amp;gt;&lt;br /&gt;
Answer.stub(:get_total_score)&lt;br /&gt;
&amp;lt;/pre&amp;gt;&lt;br /&gt;
This is to eliminate tight coupling between compute_scores and get_total_scores. Failure in get_total_scores wouldn't break the compute_scores test cases.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
'''Function Name : Get_total_scores'''&lt;br /&gt;
&lt;br /&gt;
This function is called by the Compute_scores method of the answer.rb model to compute the total score of an assessment. The input consists of assessment for which the total score is being calculated and the list of questions being evaluated in the assessment. The method uses questionnaire id from the questions and response id to obtain a score view questionnaire data. This score view is a read-only record. The questionnaire data mainly consists of q1_max_question_score, sum_of_weights and weighted_score. Before calculating the score, the function performs two crucial tasks. &lt;br /&gt;
*Checks if the answer for a scored question is nil. If it is nil or unanswered, the question will be ignored and not counted towards the score of this response.&lt;br /&gt;
* Calls the submission_valid function by passing the response record to set the @invalid flag based on the validity of the response.&lt;br /&gt;
The total score is calculated using the below formula&lt;br /&gt;
&lt;br /&gt;
&amp;lt;pre&amp;gt;&lt;br /&gt;
(weighted_score / (sum_of_weights * max_question_score)) * 100&lt;br /&gt;
&amp;lt;/pre&amp;gt;&lt;br /&gt;
&lt;br /&gt;
Any edge cases would return -1 indicating no score&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
'''Rspec Unit Test : Get_total_scores'''&lt;br /&gt;
&lt;br /&gt;
Following scenarios are tested:&lt;br /&gt;
&lt;br /&gt;
*To return an anticipated total score of a single response without any edge cases. Since this function will be called only on one response at a time, there is no need to test for multiple responses at the same time.&lt;br /&gt;
*To return an anticipated total score of a response where nil answer is for a scored question. This is to check if its weight gets removed from the sum_of_weights.&lt;br /&gt;
*To return -1 when the sum of weights becomes 0. This can happen when all the scored questions are unanswered. Return value of -1 is checked at the calling function to ensure if a score is returned or not.&lt;br /&gt;
*To return -1 when weighted_score of questionnaireData is nil&lt;br /&gt;
* To check if submission_valid is called. This method is called to set invalid flag to indicate whether the response entered is valid or not. The validity criteria is explained in the submission_valid? Function.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
This unit test uses two stubs and returns mock results&lt;br /&gt;
&amp;lt;pre&amp;gt;&lt;br /&gt;
ScoreView.stub(:find_by_sql)&lt;br /&gt;
&amp;lt;/pre&amp;gt;&lt;br /&gt;
&amp;lt;pre&amp;gt;&lt;br /&gt;
Answer.stub(:where)&lt;br /&gt;
&amp;lt;/pre&amp;gt;&lt;br /&gt;
This is to reduce the outcome of the test to depend on DB calls. For example, in case the connection to DB fails, this unit test would still pass making it less rigid.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
'''Function Name : submission_valid?'''&lt;br /&gt;
&lt;br /&gt;
This purpose of this function is to verify the validity of a review based on a deadline.  This function obtains a list of AssignmentDueDate objects  in descending order which is then compared against the current time to determine which deadlines are valid and which ones are not. The flag variable is used to represent whether or not a deadline was available in the previous iteration of the loop. If the flag is set to TRUE and the deadline is less than the current date, then latest_review_phase_start_time is set to this deadline. A list of ResubmissionTime objects is also retrieved from the controller. These objects are then compared against the then latest_review_phase_start_time variable to determine a response. &lt;br /&gt;
&lt;br /&gt;
Observations: The current implementation of the function is bugged. It retrieves a list of sorted AssignmentDueDate objects and proceeds to check if this list is empty. However, instead of exiting if the function if the list is empty, it carries on execution and raises an exception on hitting the for loop. &lt;br /&gt;
&lt;br /&gt;
*Checks if a review is valid or not by comparing its date with a list of deadlines.&lt;br /&gt;
*Returns 1 or 0 depending on validity&lt;br /&gt;
*Current implementation is bugged. Throws an exception if no AssignmentDueDate objects are passed, returns nil if any objects are passed.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
'''Rspec Unit Test : submission_valid?'''&lt;br /&gt;
&lt;br /&gt;
Following scenarios are tested:&lt;br /&gt;
&lt;br /&gt;
*Passing valid AssignmentDueDate objects&lt;br /&gt;
*Not passing any AssignmentDueDate objects&lt;br /&gt;
&lt;br /&gt;
When valid AssignmentDueDate objects are passed, stubs are used to create fake AssignmentDueDate Objects and ResubmissionTime objects. These objects are then populated with valid deadline dates and deadline_type values. These values are then supplied when requested by the submission_valid? Function rather than actually calling the function.  The current implementation of this test case expects the program to throw an error when it reaches the for loop. Once this bug is fixed, this test case may be re-written to test a more legitimate test case.&lt;br /&gt;
&lt;br /&gt;
In case an empty list of AssignmentDueDate objects is passed back to the submission_valid?() method. This would cause the function to return nil. When this function is fixed, the following test case may be re-written to test for a more legitimate test-case.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
This unit test uses two stubs and returns mock results&lt;br /&gt;
&amp;lt;pre&amp;gt;&lt;br /&gt;
AssignmentDueDate.stub_chain(:where, :order)&lt;br /&gt;
&amp;lt;/pre&amp;gt;&lt;br /&gt;
The above stub returns two AssignmentDueDate objects whenever the where() and order() method are chained on AssignmentDueDate.&lt;br /&gt;
&amp;lt;pre&amp;gt;&lt;br /&gt;
ResubmissionTime.stub_chain(:where, :order)&lt;br /&gt;
&amp;lt;/pre&amp;gt;&lt;br /&gt;
The above stub returns two ResubmissionTime objects whenever the where() and order() method are chained on ResubmissionTime.&lt;br /&gt;
&amp;lt;pre&amp;gt;&lt;br /&gt;
AssignmentDueDate.stub_chain(:where, :order)&lt;br /&gt;
&amp;lt;/pre&amp;gt;&lt;br /&gt;
This stub is used in the second test case to return nil objects.&lt;br /&gt;
&lt;br /&gt;
the stub_chain method can be used to create stubs where chained methods are expected.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
'''Function Name : answers_by_question, answers_by_question_for_reviewee,answers_by_question_for_reviewee_in_round'''&lt;br /&gt;
&lt;br /&gt;
These three functions are sql queries that hit the DB to get an output record after a series of selections and joins. SQL queries that hit DB often do not have a high priority when it comes to testing, so the project does not aggressively test these functions. However, these functions are tested to make sure the queries are able to find the right column names and tables successfully. Any change in the table schema would be detected in these test cases. The functionality of these queries are not tested but instead the existence of an output is tested. This ensures that answer.rb is able to make a successful db connection and is sync with the latest db schema. Since the function actually hits the DB, mocks can no longer be used, instead active records were created and saved in test db using FactoryGirl gem from the factories.rb. These records are cleared after every test case.&lt;br /&gt;
&lt;br /&gt;
Following factories were used to create records in the table&lt;br /&gt;
*question&lt;br /&gt;
*response_record&lt;br /&gt;
*response_map&lt;br /&gt;
*answer&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
'''Rspec Unit Test : answers_by_question, answers_by_question_for_reviewee,answers_by_question_for_reviewee_in_round'''&lt;br /&gt;
&lt;br /&gt;
The factories are created such a way that the query would return an output and the tests will pass if the query returns a non nil record. The functionality of these functions would be tested by the integration tests of the controller&lt;br /&gt;
&lt;br /&gt;
&amp;lt;pre&amp;gt;&lt;br /&gt;
describe &amp;quot;#test sql queries in answer.rb&amp;quot; do&lt;br /&gt;
&lt;br /&gt;
    it &amp;quot;returns answer by question record from db which is not empty&amp;quot; do&lt;br /&gt;
      assignment_id = 1&lt;br /&gt;
      q_id = 1&lt;br /&gt;
      expect(Answer.answers_by_question(assignment_id,q_id)).not_to be_empty&lt;br /&gt;
    end&lt;br /&gt;
&lt;br /&gt;
    it &amp;quot;returns answers by question for reviewee from the db which is not empty&amp;quot; do&lt;br /&gt;
      assignment_id = 1&lt;br /&gt;
      reviewee_id = 1&lt;br /&gt;
      q_id = 1	&lt;br /&gt;
      expect(Answer.answers_by_question_for_reviewee(assignment_id,reviewee_id,q_id)).not_to be_empty&lt;br /&gt;
    end&lt;br /&gt;
&lt;br /&gt;
    it &amp;quot;returns answers by question for reviewee in round from db which is not empty&amp;quot; do&lt;br /&gt;
      assignment_id = 1&lt;br /&gt;
      reviewee_id = 1&lt;br /&gt;
      q_id = 1&lt;br /&gt;
      round = 1&lt;br /&gt;
      expect(Answer.answers_by_question_for_reviewee_in_round(assignment_id,reviewee_id,q_id,round)).not_to be_empty&lt;br /&gt;
    end&lt;br /&gt;
  end&lt;br /&gt;
&amp;lt;/pre&amp;gt;&lt;br /&gt;
&lt;br /&gt;
'''Validation and Dependency  Rspec Test'''&lt;br /&gt;
&lt;br /&gt;
Apart from testing functions, the models are also tested for validations and external dependencies. Model answer.rb does not have any validations but does have a dependency on question.rb. Answer belongs_to question and this was tested using a simple dependency rspec test.&lt;br /&gt;
&amp;lt;pre&amp;gt;&lt;br /&gt;
it { should belong_to(:question) }&lt;br /&gt;
&amp;lt;/pre&amp;gt;&lt;br /&gt;
===Running Rspec===&lt;br /&gt;
*To run the test suite for a particular file only( answer_spec.rb):&lt;br /&gt;
&amp;lt;pre&amp;gt;&lt;br /&gt;
root@ubuntu:~/expertiza$ rspec spec/models/answer_spec.rb&lt;br /&gt;
&amp;lt;/pre&amp;gt;&lt;br /&gt;
*To run the entire suite of test cases:&lt;br /&gt;
&amp;lt;pre&amp;gt;&lt;br /&gt;
root@ubuntu:~/expertiza$ rspec spec&lt;br /&gt;
&amp;lt;/pre&amp;gt;&lt;br /&gt;
&lt;br /&gt;
===Rspec Test Results===&lt;br /&gt;
&lt;br /&gt;
&amp;lt;pre&amp;gt;&lt;br /&gt;
1 deprecation warning total&lt;br /&gt;
&lt;br /&gt;
Finished in 12.39 seconds (files took 11.25 seconds to load)&lt;br /&gt;
17 examples, 0 failures&lt;br /&gt;
&lt;br /&gt;
Randomized with seed 37447&lt;br /&gt;
&lt;br /&gt;
Coverage report generated for RSpec to /home/root/expertiza/coverage. 998 / 3919 LOC (25.47%) covered.&lt;br /&gt;
[Coveralls] Outside the CI environment, not sending data.&lt;br /&gt;
&amp;lt;/pre&amp;gt;&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
===References===&lt;br /&gt;
1. [https://en.wikipedia.org/wiki/RSpec wikipedia.org/wiki/RSpec] &amp;lt;br&amp;gt;&lt;br /&gt;
2. [http://rspec.info/ rspec.info/ ] &amp;lt;br&amp;gt;&lt;br /&gt;
3. [https://semaphoreci.com/community/tutorials/getting-started-with-rspec semaphoreci.com/community/tutorials/getting-started-with-rspec] &amp;lt;br&amp;gt;&lt;br /&gt;
4. [https://github.com/rspec/rspec github.com/rspec/rspec] &amp;lt;br&amp;gt;&lt;/div&gt;</summary>
		<author><name>Vdatla</name></author>
	</entry>
	<entry>
		<id>https://wiki.expertiza.ncsu.edu/index.php?title=CSC/ECE_517_Fall_2016/E1670._Unit_tests_for_answers.rb&amp;diff=103440</id>
		<title>CSC/ECE 517 Fall 2016/E1670. Unit tests for answers.rb</title>
		<link rel="alternate" type="text/html" href="https://wiki.expertiza.ncsu.edu/index.php?title=CSC/ECE_517_Fall_2016/E1670._Unit_tests_for_answers.rb&amp;diff=103440"/>
		<updated>2016-10-29T00:33:23Z</updated>

		<summary type="html">&lt;p&gt;Vdatla: &lt;/p&gt;
&lt;hr /&gt;
&lt;div&gt;==E1670 . Unit tests for answers.rb==&lt;br /&gt;
&lt;br /&gt;
This wiki page is for the description of changes made under E1670 OSS assignment for Fall 2016, CSC/ECE 517.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
__TOC__&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
===Background===&lt;br /&gt;
&lt;br /&gt;
Expertiza is an Open Source web application developed on Ruby On Rails platform. It is a platform which allows students to take assignments posted by the course instructors. Expertiza allows students to select assignment topics, form teams and submit their work. It also allows them to review other students' submissions and improve their work based on this feedback.&lt;br /&gt;
&lt;br /&gt;
===Project Description===&lt;br /&gt;
&lt;br /&gt;
In Expertiza, each questionnaire contains many questions, those question may have different types (e.g. checkbox, criterion, etc). When a user fills in a rubric, the responses for each question will become an answer record. The responses of rubrics are stored in answers table in DB. The answer.rb is the model for the answers table in DB. Answer.rb model does not have any test cases and the aim of the project is to write fast, effective and flexible unit test cases that offer maximum code coverage.&lt;br /&gt;
&lt;br /&gt;
===Files Created/Modified===&lt;br /&gt;
*answer_spec.rb&lt;br /&gt;
*factories.rb&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
===RSpec===&lt;br /&gt;
====RSpec Introduction====&lt;br /&gt;
RSpec is a testing framework for Ruby for behavior-driven development (BDD) licensed under MIT. It is inspired by JBehave and contains fully integrated JMock based framework which has a very rich and powerful DSL (domain-specific language) which resembles a natural language specification.&lt;br /&gt;
Composed of multiple libraries structured to work together, RSpec provides encapsulated testing via the describe block to specify the behavior of the class and the context for the unit test case.&lt;br /&gt;
&lt;br /&gt;
==== Why RSpec? ====&lt;br /&gt;
RSpec is easy to learn and implement and can be used with other testing tools like Cucumber and Minitest independently. It is extremely powerful for testing states with complicated setup and also helps in tearing down complex code to access the objects required for testing&lt;br /&gt;
RSpec semantics encourage agile thinking and practice and it structures the tests in a more intuitive way.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
===Functions in answers.rb===&lt;br /&gt;
&lt;br /&gt;
'''Function Name : Compute_scores'''&lt;br /&gt;
&lt;br /&gt;
Compute_scores is a function in model answer.rb which gives the average, maximum and minimum scores obtained in a series a responses/assessments. It has two input parameters: List of assessments and questions. The function iterates over each assessment to get the total score of that assessment. If the response or review is invalid, that assessment won’t be considered in the calculation of the score average. After iterating over all assessments, Max score, and Min scores are calculated along with the average score based on the number of valid assessments. Their scores are returned by the function.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
'''Rspec Unit Test : Compute_scores'''&lt;br /&gt;
&lt;br /&gt;
Following scenarios are tested:&lt;br /&gt;
&lt;br /&gt;
* To return scores as nil if the input list of assessments is nil. This is to make sure no Null Pointer exceptions are thrown by the code&lt;br /&gt;
*To return a particular score when a single valid assessment is given as an input.&lt;br /&gt;
*To return a particular score when multiple valid assessments are given as an input. This is to test the looping functionality of the method.&lt;br /&gt;
*To return a particular score when invalid assessments are given as an input. The validity and total scores are returned by a mock and not by the actual functions. This is to make the test cases less rigid so that failure of dependent functions do not disrupt the functionality of interface level tests.&lt;br /&gt;
*To return a particular score when invalid flag is nil. Invalid flag can either be 0,1 or nil. Nil situation is tested to prevent NullPointer Exceptions&lt;br /&gt;
*To check if the method get_total_score is called with the right parameters.&lt;br /&gt;
&lt;br /&gt;
This unit test uses a stub and returns a mock value.&lt;br /&gt;
&amp;lt;pre&amp;gt;&lt;br /&gt;
Answer.stub(:get_total_score)&lt;br /&gt;
&amp;lt;/pre&amp;gt;&lt;br /&gt;
This is to eliminate tight coupling between compute_scores and get_total_scores. Failure in get_total_scores wouldn't break the compute_scores test cases.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
'''Function Name : Get_total_scores'''&lt;br /&gt;
&lt;br /&gt;
This function is called by the Compute_scores method of the answer.rb model to compute the total score of an assessment. The input consists of assessment for which the total score is being calculated and the list of questions being evaluated in the assessment. The method uses questionnaire id from the questions and response id to obtain a score view questionnaire data. This score view is a read-only record. The questionnaire data mainly consists of q1_max_question_score, sum_of_weights and weighted_score. Before calculating the score, the function performs two crucial tasks. &lt;br /&gt;
*Checks if the answer for a scored question is nil. If it is nil or unanswered, the question will be ignored and not counted towards the score of this response.&lt;br /&gt;
* Calls the submission_valid function by passing the response record to set the @invalid flag based on the validity of the response.&lt;br /&gt;
The total score is calculated using the below formula&lt;br /&gt;
&lt;br /&gt;
&amp;lt;pre&amp;gt;&lt;br /&gt;
(weighted_score / (sum_of_weights * max_question_score)) * 100&lt;br /&gt;
&amp;lt;/pre&amp;gt;&lt;br /&gt;
&lt;br /&gt;
Any edge cases would return -1 indicating no score&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
'''Rspec Unit Test : Get_total_scores'''&lt;br /&gt;
&lt;br /&gt;
Following scenarios are tested:&lt;br /&gt;
&lt;br /&gt;
*To return an anticipated total score of a single response without any edge cases. Since this function will be called only on one response at a time, there is no need to test for multiple responses at the same time.&lt;br /&gt;
*To return an anticipated total score of a response where nil answer is for a scored question. This is to check if its weight gets removed from the sum_of_weights.&lt;br /&gt;
*To return -1 when the sum of weights becomes 0. This can happen when all the scored questions are unanswered. Return value of -1 is checked at the calling function to ensure if a score is returned or not.&lt;br /&gt;
*To return -1 when weighted_score of questionnaireData is nil&lt;br /&gt;
* To check if submission_valid is called. This method is called to set invalid flag to indicate whether the response entered is valid or not. The validity criteria is explained in the submission_valid? Function.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
This unit test uses two stubs and returns mock results&lt;br /&gt;
&amp;lt;pre&amp;gt;&lt;br /&gt;
ScoreView.stub(:find_by_sql)&lt;br /&gt;
&amp;lt;/pre&amp;gt;&lt;br /&gt;
&amp;lt;pre&amp;gt;&lt;br /&gt;
Answer.stub(:where)&lt;br /&gt;
&amp;lt;/pre&amp;gt;&lt;br /&gt;
This is to reduce the outcome of the test to depend on DB calls. For example, in case the connection to DB fails, this unit test would still pass making it less rigid.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
'''Function Name : submission_valid?'''&lt;br /&gt;
&lt;br /&gt;
This purpose of this function is to verify the validity of a review based on a deadline.  This function obtains a list of AssignmentDueDate objects  in descending order which is then compared against the current time to determine which deadlines are valid and which ones are not. The flag variable is used to represent whether or not a deadline was available in the previous iteration of the loop. If the flag is set to TRUE and the deadline is less than the current date, then latest_review_phase_start_time is set to this deadline. A list of ResubmissionTime objects is also retrieved from the controller. These objects are then compared against the then latest_review_phase_start_time variable to determine a response. &lt;br /&gt;
&lt;br /&gt;
Observations: The current implementation of the function is bugged. It retrieves a list of sorted AssignmentDueDate objects and proceeds to check if this list is empty. However, instead of exiting if the function if the list is empty, it carries on execution and raises an exception on hitting the for loop. &lt;br /&gt;
&lt;br /&gt;
*Checks if a review is valid or not by comparing its date with a list of deadlines.&lt;br /&gt;
*Returns 1 or 0 depending on validity&lt;br /&gt;
*Current implementation is bugged. Throws an exception if no AssignmentDueDate objects are passed, returns nil if any objects are passed.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
'''Rspec Unit Test : submission_valid?'''&lt;br /&gt;
&lt;br /&gt;
Following scenarios are tested:&lt;br /&gt;
&lt;br /&gt;
*Passing valid AssignmentDueDate objects&lt;br /&gt;
*Not passing any AssignmentDueDate objects&lt;br /&gt;
&lt;br /&gt;
When valid AssignmentDueDate objects are passed, stubs are used to create fake AssignmentDueDate Objects and ResubmissionTime objects. These objects are then populated with valid deadline dates and deadline_type values. These values are then supplied when requested by the submission_valid? Function rather than actually calling the function.  The current implementation of this test case expects the program to throw an error when it reaches the for loop. Once this bug is fixed, this test case may be re-written to test a more legitimate test case.&lt;br /&gt;
&lt;br /&gt;
In case an empty list of AssignmentDueDate objects is passed back to the submission_valid?() method. This would cause the function to return nil. When this function is fixed, the following test case may be re-written to test for a more legitimate test-case.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
This unit test uses two stubs and returns mock results&lt;br /&gt;
&amp;lt;pre&amp;gt;&lt;br /&gt;
AssignmentDueDate.stub_chain(:where, :order)&lt;br /&gt;
&amp;lt;/pre&amp;gt;&lt;br /&gt;
The above stub returns two AssignmentDueDate objects whenever the where() and order() method are chained on AssignmentDueDate.&lt;br /&gt;
&amp;lt;pre&amp;gt;&lt;br /&gt;
ResubmissionTime.stub_chain(:where, :order)&lt;br /&gt;
&amp;lt;/pre&amp;gt;&lt;br /&gt;
The above stub returns two ResubmissionTime objects whenever the where() and order() method are chained on ResubmissionTime.&lt;br /&gt;
&amp;lt;pre&amp;gt;&lt;br /&gt;
AssignmentDueDate.stub_chain(:where, :order)&lt;br /&gt;
&amp;lt;/pre&amp;gt;&lt;br /&gt;
This stub is used in the second test case to return nil objects.&lt;br /&gt;
&lt;br /&gt;
the stub_chain method can be used to create stubs where chained methods are expected.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
'''Function Name : answers_by_question, answers_by_question_for_reviewee,answers_by_question_for_reviewee_in_round'''&lt;br /&gt;
&lt;br /&gt;
These three functions are sql queries that hit the DB to get an output record after a series of selections and joins. SQL queries that hit DB often do not have a high priority when it comes to testing, so the project does not aggressively test these functions. However, these functions are tested to make sure the queries are able to find the right column names and tables successfully. Any change in the table schema would be detected in these test cases. The functionality of these queries are not tested but instead the existence of an output is tested. This ensures that answer.rb is able to make a successful db connection and is sync with the latest db schema. Since the function actually hits the DB, mocks can no longer be used, instead active records were created and saved in test db using FactoryGirl gem from the factories.rb. These records are cleared after every test case.&lt;br /&gt;
&lt;br /&gt;
Following factories were used to create records in the table&lt;br /&gt;
*question&lt;br /&gt;
*response_record&lt;br /&gt;
*response_map&lt;br /&gt;
*answer&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
'''Rspec Unit Test : answers_by_question, answers_by_question_for_reviewee,answers_by_question_for_reviewee_in_round'''&lt;br /&gt;
&lt;br /&gt;
The factories are created such a way that the query would return an output and the tests will pass if the query returns a non nil record. The functionality of these functions would be tested by the integration tests of the controller&lt;br /&gt;
&lt;br /&gt;
&amp;lt;pre&amp;gt;&lt;br /&gt;
describe &amp;quot;#test sql queries in answer.rb&amp;quot; do&lt;br /&gt;
&lt;br /&gt;
    it &amp;quot;returns answer by question record from db which is not empty&amp;quot; do&lt;br /&gt;
      assignment_id = 1&lt;br /&gt;
      q_id = 1&lt;br /&gt;
      expect(Answer.answers_by_question(assignment_id,q_id)).not_to be_empty&lt;br /&gt;
    end&lt;br /&gt;
&lt;br /&gt;
    it &amp;quot;returns answers by question for reviewee from the db which is not empty&amp;quot; do&lt;br /&gt;
      assignment_id = 1&lt;br /&gt;
      reviewee_id = 1&lt;br /&gt;
      q_id = 1	&lt;br /&gt;
      expect(Answer.answers_by_question_for_reviewee(assignment_id,reviewee_id,q_id)).not_to be_empty&lt;br /&gt;
    end&lt;br /&gt;
&lt;br /&gt;
    it &amp;quot;returns answers by question for reviewee in round from db which is not empty&amp;quot; do&lt;br /&gt;
      assignment_id = 1&lt;br /&gt;
      reviewee_id = 1&lt;br /&gt;
      q_id = 1&lt;br /&gt;
      round = 1&lt;br /&gt;
      expect(Answer.answers_by_question_for_reviewee_in_round(assignment_id,reviewee_id,q_id,round)).not_to be_empty&lt;br /&gt;
    end&lt;br /&gt;
  end&lt;br /&gt;
&amp;lt;/pre&amp;gt;&lt;br /&gt;
&lt;br /&gt;
'''Validation and Dependency  Rspec Test'''&lt;br /&gt;
&lt;br /&gt;
Apart from testing functions, the models are also tested for validations and external dependencies. Model answer.rb does not have any validations but does have a dependency on question.rb. Answer belongs_to question and this was tested using a simple dependency rspec test.&lt;br /&gt;
&amp;lt;pre&amp;gt;&lt;br /&gt;
it { should belong_to(:question) }&lt;br /&gt;
&amp;lt;/pre&amp;gt;&lt;br /&gt;
===Running Rspec===&lt;br /&gt;
*To run the test suite for a particular file only( answer_spec.rb):&lt;br /&gt;
&amp;lt;pre&amp;gt;&lt;br /&gt;
root@ubuntu:~/expertiza$ rspec spec/models/answer_spec.rb&lt;br /&gt;
&amp;lt;/pre&amp;gt;&lt;br /&gt;
*To run the entire suite of test cases:&lt;br /&gt;
&amp;lt;pre&amp;gt;&lt;br /&gt;
root@ubuntu:~/expertiza$ rspec spec&lt;br /&gt;
&amp;lt;/pre&amp;gt;&lt;br /&gt;
&lt;br /&gt;
===Rspec Test Results===&lt;br /&gt;
&lt;br /&gt;
&amp;lt;pre&amp;gt;&lt;br /&gt;
1 deprecation warning total&lt;br /&gt;
&lt;br /&gt;
Finished in 12.39 seconds (files took 11.25 seconds to load)&lt;br /&gt;
17 examples, 0 failures&lt;br /&gt;
&lt;br /&gt;
Randomized with seed 37447&lt;br /&gt;
&lt;br /&gt;
Coverage report generated for RSpec to /home/root/expertiza/coverage. 998 / 3919 LOC (25.47%) covered.&lt;br /&gt;
[Coveralls] Outside the CI environment, not sending data.&lt;br /&gt;
&amp;lt;/pre&amp;gt;&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
===References===&lt;br /&gt;
1. [https://en.wikipedia.org/wiki/RSpec wikipedia.org/wiki/RSpec] &amp;lt;br&amp;gt;&lt;br /&gt;
2. [http://rspec.info/ rspec.info/ ] &amp;lt;br&amp;gt;&lt;br /&gt;
3. [https://semaphoreci.com/community/tutorials/getting-started-with-rspec semaphoreci.com/community/tutorials/getting-started-with-rspec] &amp;lt;br&amp;gt;&lt;br /&gt;
4. [https://github.com/rspec/rspec github.com/rspec/rspec] &amp;lt;br&amp;gt;&lt;/div&gt;</summary>
		<author><name>Vdatla</name></author>
	</entry>
	<entry>
		<id>https://wiki.expertiza.ncsu.edu/index.php?title=CSC/ECE_517_Fall_2016/E1670._Unit_tests_for_answers.rb&amp;diff=103424</id>
		<title>CSC/ECE 517 Fall 2016/E1670. Unit tests for answers.rb</title>
		<link rel="alternate" type="text/html" href="https://wiki.expertiza.ncsu.edu/index.php?title=CSC/ECE_517_Fall_2016/E1670._Unit_tests_for_answers.rb&amp;diff=103424"/>
		<updated>2016-10-29T00:23:53Z</updated>

		<summary type="html">&lt;p&gt;Vdatla: &lt;/p&gt;
&lt;hr /&gt;
&lt;div&gt;==E1670 . Unit tests for answers.rb==&lt;br /&gt;
&lt;br /&gt;
This wiki page is for the description of changes made under E1670 OSS assignment for Fall 2016, CSC/ECE 517.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
__TOC__&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
===Background===&lt;br /&gt;
&lt;br /&gt;
Expertiza is an Open Source web application developed on Ruby On Rails platform. It is a platform which allows students to take assignments posted by the course instructors. Expertiza allows students to select assignment topics, form teams and submit their work. It also allows them to review other students' submissions and improve their work based on this feedback.&lt;br /&gt;
&lt;br /&gt;
===Project Description===&lt;br /&gt;
&lt;br /&gt;
In Expertiza, each questionnaire contains many questions, those question may have different types (e.g. checkbox, criterion, etc). When a user fills in a rubric, the responses for each question will become an answer record. The responses of rubrics are stored in answers table in DB. The answer.rb is the model for the answers table in DB. Answer.rb model does not have any test cases and the aim of the project is to write fast, effective and flexible unit test cases that offer maximum code coverage.&lt;br /&gt;
&lt;br /&gt;
===Files Created/Modified===&lt;br /&gt;
*answer_spec.rb&lt;br /&gt;
*factories.rb&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
===RSpec===&lt;br /&gt;
====RSpec Introduction====&lt;br /&gt;
RSpec is a testing framework for Ruby for behavior-driven development (BDD) licensed under MIT. It is inspired by JBehave and contains fully integrated JMock based framework which has a very rich and powerful DSL (domain-specific language) which resembles a natural language specification.&lt;br /&gt;
Composed of multiple libraries structured to work together, RSpec provides encapsulated testing via the describe block to specify the behavior of the class and the context for the unit test case.&lt;br /&gt;
&lt;br /&gt;
==== Why RSpec? ====&lt;br /&gt;
RSpec is easy to learn and implement and can be used with other testing tools like Cucumber and Minitest independently. It is extremely powerful for testing states with complicated setup and also helps in tearing down complex code to access the objects required for testing&lt;br /&gt;
RSpec semantics encourage agile thinking and practice and it structures the tests in a more intuitive way.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
===Functions in answers.rb===&lt;br /&gt;
&lt;br /&gt;
'''Function Name : Compute_scores'''&lt;br /&gt;
&lt;br /&gt;
Compute_scores is a function in model answer.rb which gives the average, maximum and minimum scores obtained in a series a responses/assessments. It has two input parameters: List of assessments and questions. The function iterates over each assessment to get the total score of that assessment. If the response or review is invalid, that assessment won’t be considered in the calculation of the score average. After iterating over all assessments, Max score, and Min scores are calculated along with the average score based on the number of valid assessments. Their scores are returned by the function.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
'''Rspec Unit Test : Compute_scores'''&lt;br /&gt;
&lt;br /&gt;
Following scenarios are tested:&lt;br /&gt;
&lt;br /&gt;
* To return scores as nil if the input list of assessments is nil. This is to make sure no Null Pointer exceptions are thrown by the code&lt;br /&gt;
*To return a particular score when a single valid assessment is given as an input.&lt;br /&gt;
*To return a particular score when multiple valid assessments are given as an input. This is to test the looping functionality of the method.&lt;br /&gt;
*To return a particular score when invalid assessments are given as an input. The validity and total scores are returned by a mock and not by the actual functions. This is to make the test cases less rigid so that failure of dependent functions do not disrupt the functionality of interface level tests.&lt;br /&gt;
*To return a particular score when invalid flag is nil. Invalid flag can either be 0,1 or nil. Nil situation is tested to prevent NullPointer Exceptions&lt;br /&gt;
*To check if the method get_total_score is called with the right parameters.&lt;br /&gt;
&lt;br /&gt;
This unit test uses a stub and returns a mock value.&lt;br /&gt;
&amp;lt;pre&amp;gt;&lt;br /&gt;
Answer.stub(:get_total_score)&lt;br /&gt;
&amp;lt;/pre&amp;gt;&lt;br /&gt;
This is to eliminate tight coupling between compute_scores and get_total_scores. Failure in get_total_scores wouldn't break the compute_scores test cases.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
'''Function Name : Get_total_scores'''&lt;br /&gt;
&lt;br /&gt;
This function is called by the Compute_scores method of the answer.rb model to compute the total score of an assessment. The input consists of assessment for which the total score is being calculated and the list of questions being evaluated in the assessment. The method uses questionnaire id from the questions and response id to obtain a score view questionnaire data. This score view is a read-only record. The questionnaire data mainly consists of q1_max_question_score, sum_of_weights and weighted_score. Before calculating the score, the function performs two crucial tasks. &lt;br /&gt;
*Checks if the answer for a scored question is nil. If it is nil or unanswered, the question will be ignored and not counted towards the score of this response.&lt;br /&gt;
* Calls the submission_valid function by passing the response record to set the @invalid flag based on the validity of the response.&lt;br /&gt;
The total score is calculated using the below formula&lt;br /&gt;
&lt;br /&gt;
&amp;lt;pre&amp;gt;&lt;br /&gt;
(weighted_score / (sum_of_weights * max_question_score)) * 100&lt;br /&gt;
&amp;lt;/pre&amp;gt;&lt;br /&gt;
&lt;br /&gt;
Any edge cases would return -1 indicating no score&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
'''Rspec Unit Test : Get_total_scores'''&lt;br /&gt;
&lt;br /&gt;
Following scenarios are tested:&lt;br /&gt;
&lt;br /&gt;
*To return an anticipated total score of a single response without any edge cases. Since this function will be called only on one response at a time, there is no need to test for multiple responses at the same time.&lt;br /&gt;
*To return an anticipated total score of a response where nil answer is for a scored question. This is to check if its weight gets removed from the sum_of_weights.&lt;br /&gt;
*To return -1 when the sum of weights becomes 0. This can happen when all the scored questions are unanswered. Return value of -1 is checked at the calling function to ensure if a score is returned or not.&lt;br /&gt;
*To return -1 when weighted_score of questionnaireData is nil&lt;br /&gt;
* To check if submission_valid is called. This method is called to set invalid flag to indicate whether the response entered is valid or not. The validity criteria is explained in the submission_valid? Function.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
This unit test uses two stubs and returns mock results&lt;br /&gt;
&amp;lt;pre&amp;gt;&lt;br /&gt;
ScoreView.stub(:find_by_sql)&lt;br /&gt;
&amp;lt;/pre&amp;gt;&lt;br /&gt;
&amp;lt;pre&amp;gt;&lt;br /&gt;
Answer.stub(:where)&lt;br /&gt;
&amp;lt;/pre&amp;gt;&lt;br /&gt;
This is to reduce the outcome of the test to depend on DB calls. For example, in case the connection to DB fails, this unit test would still pass making it less rigid.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
'''Function Name : submission_valid?'''&lt;br /&gt;
&lt;br /&gt;
This purpose of this function is to verify the validity of a review based on a deadline.  This function obtains a list of AssignmentDueDate objects  in descending order which is then compared against the current time to determine which deadlines are valid and which ones are not. The flag variable is used to represent whether or not a deadline was available in the previous iteration of the loop. If the flag is set to TRUE and the deadline is less than the current date, then latest_review_phase_start_time is set to this deadline. A list of ResubmissionTime objects is also retrieved from the controller. These objects are then compared against the then latest_review_phase_start_time variable to determine a response. &lt;br /&gt;
&lt;br /&gt;
Observations: The current implementation of the function is bugged. It retrieves a list of sorted AssignmentDueDate objects and proceeds to check if this list is empty. However, instead of exiting if the function if the list is empty, it carries on execution and raises an exception on hitting the for loop. &lt;br /&gt;
&lt;br /&gt;
*Checks if a review is valid or not by comparing its date with a list of deadlines.&lt;br /&gt;
*Returns 1 or 0 depending on validity&lt;br /&gt;
*Current implementation is bugged. Throws an exception if no AssignmentDueDate objects are passed, returns nil if any objects are passed.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
'''Rspec Unit Test : submission_valid?'''&lt;br /&gt;
&lt;br /&gt;
Following scenarios are tested:&lt;br /&gt;
&lt;br /&gt;
*Passing valid AssignmentDueDate objects&lt;br /&gt;
*Not passing any AssignmentDueDate objects&lt;br /&gt;
&lt;br /&gt;
When valid AssignmentDueDate objects are passed, stubs are used to create fake AssignmentDueDate Objects and ResubmissionTime objects. These objects are then populated with valid deadline dates and deadline_type values. These values are then supplied when requested by the submission_valid? Function rather than actually calling the function.  The current implementation of this test case expects the program to throw an error when it reaches the for loop. Once this bug is fixed, this test case may be re-written to test a more legitimate test case.&lt;br /&gt;
&lt;br /&gt;
In case an empty list of AssignmentDueDate objects is passed back to the submission_valid?() method. This would cause the function to return nil. When this function is fixed, the following test case may be re-written to test for a more legitimate test-case.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
This unit test uses two stubs and returns mock results&lt;br /&gt;
&amp;lt;pre&amp;gt;&lt;br /&gt;
AssignmentDueDate.stub_chain(:where, :order)&lt;br /&gt;
&amp;lt;/pre&amp;gt;&lt;br /&gt;
The above stub returns two AssignmentDueDate objects whenever the where() and order() method are chained on AssignmentDueDate.&lt;br /&gt;
&amp;lt;pre&amp;gt;&lt;br /&gt;
ResubmissionTime.stub_chain(:where, :order)&lt;br /&gt;
&amp;lt;/pre&amp;gt;&lt;br /&gt;
The above stub returns two ResubmissionTime objects whenever the where() and order() method are chained on ResubmissionTime.&lt;br /&gt;
&amp;lt;pre&amp;gt;&lt;br /&gt;
AssignmentDueDate.stub_chain(:where, :order)&lt;br /&gt;
&amp;lt;/pre&amp;gt;&lt;br /&gt;
This stub is used in the second test case to return nil objects.&lt;br /&gt;
&lt;br /&gt;
the stub_chain method can be used to create stubs where chained methods are expected.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
'''Function Name : answers_by_question, answers_by_question_for_reviewee,answers_by_question_for_reviewee_in_round'''&lt;br /&gt;
&lt;br /&gt;
These three functions are sql queries that hit the DB to get a output record after a series of selections and joins. SQL queries that hit DB often do not have a high priority when it comes to testing, so the project does not aggressively test these functions. However, these functions are tested to make sure the queries are able to find the right column names and tables successfully. Any change in the table schema would be detected in these test cases. The functionality of these queries are not tested but instead existence of an output is tested. This ensures that answer.rb is able to make a successful db connection and is sync with the latest db schema. Since the function actually hits the DB, mocks can no longer be used, instead active records were created and saved in test db using FactoryGirl gem from the factories.rb. These records are cleared after every test case.&lt;br /&gt;
&lt;br /&gt;
Following factories were used to create records in the table&lt;br /&gt;
*question&lt;br /&gt;
*response_record&lt;br /&gt;
*response_map&lt;br /&gt;
*answer&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
'''Rspec Unit Test : answers_by_question, answers_by_question_for_reviewee,answers_by_question_for_reviewee_in_round'''&lt;br /&gt;
&lt;br /&gt;
The factories are created such a way that the query would return an output and the tests will pass if the query returns a non nil record. The functionality of these functions would be tested by the integration tests of the controller&lt;br /&gt;
&lt;br /&gt;
&amp;lt;pre&amp;gt;&lt;br /&gt;
describe &amp;quot;#test sql queries in answer.rb&amp;quot; do&lt;br /&gt;
&lt;br /&gt;
    it &amp;quot;returns answer by question record from db which is not empty&amp;quot; do&lt;br /&gt;
      assignment_id = 1&lt;br /&gt;
      q_id = 1&lt;br /&gt;
      expect(Answer.answers_by_question(assignment_id,q_id)).not_to be_empty&lt;br /&gt;
    end&lt;br /&gt;
&lt;br /&gt;
    it &amp;quot;returns answers by question for reviewee from the db which is not empty&amp;quot; do&lt;br /&gt;
      assignment_id = 1&lt;br /&gt;
      reviewee_id = 1&lt;br /&gt;
      q_id = 1	&lt;br /&gt;
      expect(Answer.answers_by_question_for_reviewee(assignment_id,reviewee_id,q_id)).not_to be_empty&lt;br /&gt;
    end&lt;br /&gt;
&lt;br /&gt;
    it &amp;quot;returns answers by question for reviewee in round from db which is not empty&amp;quot; do&lt;br /&gt;
      assignment_id = 1&lt;br /&gt;
      reviewee_id = 1&lt;br /&gt;
      q_id = 1&lt;br /&gt;
      round = 1&lt;br /&gt;
      expect(Answer.answers_by_question_for_reviewee_in_round(assignment_id,reviewee_id,q_id,round)).not_to be_empty&lt;br /&gt;
    end&lt;br /&gt;
  end&lt;br /&gt;
&amp;lt;/pre&amp;gt;&lt;br /&gt;
&lt;br /&gt;
'''Validation and Dependency  Rspec Test'''&lt;br /&gt;
&lt;br /&gt;
Apart from testing functions, the models are also tested for validations and external dependencies. Model answer.rb does not have any validations but does have a dependency on question.rb. Answer belongs_to question and this was tested using a simple dependency rspec test.&lt;br /&gt;
&amp;lt;pre&amp;gt;&lt;br /&gt;
it { should belong_to(:question) }&lt;br /&gt;
&amp;lt;/pre&amp;gt;&lt;br /&gt;
===Running Rspec===&lt;br /&gt;
*To run the test suite for a particular file only( answer_spec.rb):&lt;br /&gt;
&amp;lt;pre&amp;gt;&lt;br /&gt;
root@ubuntu:~/expertiza$ rspec spec/models/answer_spec.rb&lt;br /&gt;
&amp;lt;/pre&amp;gt;&lt;br /&gt;
*To run the entire suite of test cases:&lt;br /&gt;
&amp;lt;pre&amp;gt;&lt;br /&gt;
root@ubuntu:~/expertiza$ rspec spec&lt;br /&gt;
&amp;lt;/pre&amp;gt;&lt;br /&gt;
&lt;br /&gt;
===Rspec Test Results===&lt;br /&gt;
&lt;br /&gt;
&amp;lt;pre&amp;gt;&lt;br /&gt;
1 deprecation warning total&lt;br /&gt;
&lt;br /&gt;
Finished in 12.39 seconds (files took 11.25 seconds to load)&lt;br /&gt;
17 examples, 0 failures&lt;br /&gt;
&lt;br /&gt;
Randomized with seed 37447&lt;br /&gt;
&lt;br /&gt;
Coverage report generated for RSpec to /home/root/expertiza/coverage. 998 / 3919 LOC (25.47%) covered.&lt;br /&gt;
[Coveralls] Outside the CI environment, not sending data.&lt;br /&gt;
&amp;lt;/pre&amp;gt;&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
===References===&lt;br /&gt;
1. [https://en.wikipedia.org/wiki/RSpec wikipedia.org/wiki/RSpec] &amp;lt;br&amp;gt;&lt;br /&gt;
2. [http://rspec.info/ rspec.info/ ] &amp;lt;br&amp;gt;&lt;br /&gt;
3. [https://semaphoreci.com/community/tutorials/getting-started-with-rspec semaphoreci.com/community/tutorials/getting-started-with-rspec] &amp;lt;br&amp;gt;&lt;br /&gt;
4. [https://github.com/rspec/rspec github.com/rspec/rspec] &amp;lt;br&amp;gt;&lt;/div&gt;</summary>
		<author><name>Vdatla</name></author>
	</entry>
	<entry>
		<id>https://wiki.expertiza.ncsu.edu/index.php?title=CSC/ECE_517_Fall_2016/E1670._Unit_tests_for_answers.rb&amp;diff=103413</id>
		<title>CSC/ECE 517 Fall 2016/E1670. Unit tests for answers.rb</title>
		<link rel="alternate" type="text/html" href="https://wiki.expertiza.ncsu.edu/index.php?title=CSC/ECE_517_Fall_2016/E1670._Unit_tests_for_answers.rb&amp;diff=103413"/>
		<updated>2016-10-29T00:20:24Z</updated>

		<summary type="html">&lt;p&gt;Vdatla: &lt;/p&gt;
&lt;hr /&gt;
&lt;div&gt;==E1670 . Unit tests for answers.rb==&lt;br /&gt;
&lt;br /&gt;
This wiki page is for the description of changes made under E1670 OSS assignment for Fall 2016, CSC/ECE 517.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
__TOC__&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
===Background===&lt;br /&gt;
&lt;br /&gt;
Expertiza is an Open Source web application developed on Ruby On Rails platform. It is a platform which allows students to take assignments posted by the course instructors. Expertiza allows students to select assignment topics, form teams and submit their work. It also allows them to review other students' submissions and improve their work based on this feedback.&lt;br /&gt;
&lt;br /&gt;
===Project Description===&lt;br /&gt;
&lt;br /&gt;
In Expertiza, each questionnaire contains many questions, those question may have different types (e.g. checkbox, criterion, etc). When a user fills in a rubric, the responses for each question will become an answer record. The responses of rubrics are stored in answers table in DB. The answer.rb is the model for the answers table in DB. Answer.rb model does not have any test cases and the aim of the project is to write fast, effective and flexible unit test cases that offer maximum code coverage.&lt;br /&gt;
&lt;br /&gt;
===Files Created/Modified===&lt;br /&gt;
*answer_spec.rb&lt;br /&gt;
*factories.rb&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
===RSpec===&lt;br /&gt;
====RSpec Introduction====&lt;br /&gt;
RSpec is a testing framework for Ruby for behavior-driven development (BDD) licensed under MIT. It is inspired by JBehave and contains fully integrated JMock based framework which has a very rich and powerful DSL (domain-specific language) which resembles a natural language specification.&lt;br /&gt;
Composed of multiple libraries structured to work together, RSpec provides encapsulated testing via the describe block to specify the behavior of the class and the context for the unit test case.&lt;br /&gt;
&lt;br /&gt;
==== Why RSpec? ====&lt;br /&gt;
RSpec is easy to learn and implement and can be used with other testing tools like Cucumber and Minitest independently. It is extremely powerful for testing states with complicated setup and also helps in tearing down complex code to access the objects required for testing&lt;br /&gt;
RSpec semantics encourage agile thinking and practice and it structures the tests in a more intuitive way.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
===Functions in answers.rb===&lt;br /&gt;
&lt;br /&gt;
'''Function Name : Compute_scores'''&lt;br /&gt;
&lt;br /&gt;
Compute_scores is a function in model answer.rb which gives the average, maximum and minimum scores obtained in a series a responses/assessments. It has two input parameters: List of assessments and questions. The function iterates over each assessment to get the total score of that assessment. If the response or review is invalid, that assessment won’t be considered in the calculation of the score average. After iterating over all assessments, Max score, and Min scores are calculated along with the average score based on the number of valid assessments. Their scores are returned by the function.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
'''Rspec Unit Test : Compute_scores'''&lt;br /&gt;
&lt;br /&gt;
Following scenarios are tested:&lt;br /&gt;
&lt;br /&gt;
* To return scores as nil if the input list of assessments is nil. This is to make sure no Null Pointer exceptions are thrown by the code&lt;br /&gt;
*To return a particular score when a single valid assessment is given as an input.&lt;br /&gt;
*To return a particular score when multiple valid assessments are given as an input. This is to test the looping functionality of the method.&lt;br /&gt;
*To return a particular score when invalid assessments are given as an input. The validity and total scores are returned by a mock and not by the actual functions. This is to make the test cases less rigid so that failure of dependent functions do not disrupt the functionality of interface level tests.&lt;br /&gt;
*To return a particular score when invalid flag is nil. Invalid flag can either be 0,1 or nil. Nil situation is tested to prevent NullPointer Exceptions&lt;br /&gt;
*To check if the method get_total_score is called with the right parameters.&lt;br /&gt;
&lt;br /&gt;
This unit test uses a stub and returns a mock value.&lt;br /&gt;
&amp;lt;pre&amp;gt;&lt;br /&gt;
Answer.stub(:get_total_score)&lt;br /&gt;
&amp;lt;/pre&amp;gt;&lt;br /&gt;
This is to eliminate tight coupling between compute_scores and get_total_scores. Failure in get_total_scores wouldn't break the compute_scores test cases.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
'''Function Name : Get_total_scores'''&lt;br /&gt;
&lt;br /&gt;
This function is called by the Compute_scores method of the answer.rb model to compute the total score of an assessment. The input consists of assessment for which the total score is being calculated and the list of questions being evaluated in the assessment. The method uses questionnaire id from the questions and response id to obtain a score view questionnaire data. This score view is a read-only record. The questionnaire data mainly consists of q1_max_question_score, sum_of_weights and weighted_score. Before calculating the score, the function performs two crucial tasks. &lt;br /&gt;
*Checks if the answer for a scored question is nil. If it is nil or unanswered, the question will be ignored and not counted towards the score of this response.&lt;br /&gt;
* Calls the submission_valid function by passing the response record to set the @invalid flag based on the validity of the response.&lt;br /&gt;
The total score is calculated using the below formula&lt;br /&gt;
&lt;br /&gt;
&amp;lt;pre&amp;gt;&lt;br /&gt;
(weighted_score / (sum_of_weights * max_question_score)) * 100&lt;br /&gt;
&amp;lt;/pre&amp;gt;&lt;br /&gt;
&lt;br /&gt;
Any edge cases would return -1 indicating no score&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
'''Rspec Unit Test : Get_total_scores'''&lt;br /&gt;
&lt;br /&gt;
Following scenarios are tested:&lt;br /&gt;
&lt;br /&gt;
*To return an anticipated total score of a single response without any edge cases. Since this function will be called only on one response at a time, there is no need to test for multiple responses at the same time.&lt;br /&gt;
*To return an anticipated total score of a response where nil answer is for a scored question. This is to check if its weight gets removed from the sum_of_weights.&lt;br /&gt;
*To return -1 when the sum of weights becomes 0. This can happen when all the scored questions are unanswered. Return value of -1 is checked at the calling function to ensure if a score is returned or not.&lt;br /&gt;
*To return -1 when weighted_score of questionnaireData is nil&lt;br /&gt;
* To check if submission_valid is called. This method is called to set invalid flag to indicate whether the response entered is valid or not. The validity criteria is explained in the submission_valid? Function.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
This unit test uses two stubs and returns mock results&lt;br /&gt;
&amp;lt;pre&amp;gt;&lt;br /&gt;
ScoreView.stub(:find_by_sql)&lt;br /&gt;
&amp;lt;/pre&amp;gt;&lt;br /&gt;
&amp;lt;pre&amp;gt;&lt;br /&gt;
Answer.stub(:where)&lt;br /&gt;
&amp;lt;/pre&amp;gt;&lt;br /&gt;
This is to reduce the outcome of the test to depend on DB calls. For example, in case the connection to DB fails, this unit test would still pass making it less rigid.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
'''Function Name : submission_valid?'''&lt;br /&gt;
&lt;br /&gt;
This purpose of this function is to verify the validity of a review based on a deadline.  This function obtains a list of AssignmentDueDate objects  in descending order which is then compared against the current time to determine which deadlines are valid and which ones are not. The flag variable is used to represent whether or not a deadline was available in the previous iteration of the loop. If the flag is set to TRUE and the deadline is less than the current date, then latest_review_phase_start_time is set to this deadline. A list of ResubmissionTime objects is also retrieved from the controller. These objects are then compared against the then latest_review_phase_start_time variable to determine a response. &lt;br /&gt;
&lt;br /&gt;
Observations: The current implementation of the function is bugged. It retrieves a list of sorted AssignmentDueDate objects and proceeds to check if this list is empty. However, instead of exiting if the function if the list is empty, it carries on execution and raises an exception on hitting the for loop. &lt;br /&gt;
&lt;br /&gt;
*Checks if a review is valid or not by comparing its date with a list of deadlines.&lt;br /&gt;
*Returns 1 or 0 depending on validity&lt;br /&gt;
*Current implementation is bugged. Throws an exception if no AssignmentDueDate objects are passed, returns nil if any objects are passed.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
'''Rspec Unit Test : submission_valid?'''&lt;br /&gt;
&lt;br /&gt;
Following scenarios are tested:&lt;br /&gt;
&lt;br /&gt;
*Passing valid AssignmentDueDate objects&lt;br /&gt;
*Not passing any AssignmentDueDate objects&lt;br /&gt;
&lt;br /&gt;
When valid AssignmentDueDate objects are passed, stubs are used to create fake AssignmentDueDate Objects and ResubmissionTime objects. These objects are then populated with valid deadline dates and deadline_type values. These values are then supplied when requested by the submission_valid? Function rather than actually calling the function.  The current implementation of this test case expects the program to throw an error when it reaches the for loop. Once this bug is fixed, this test case may be re-written to test a more legitimate test case.&lt;br /&gt;
&lt;br /&gt;
In case an empty list of AssignmentDueDate objects is passed back to the submission_valid?() method. This would cause the function to return nil. When this function is fixed, the following test case may be re-written to test for a more legitimate test-case.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
This unit test uses two stubs and returns mock results&lt;br /&gt;
&amp;lt;pre&amp;gt;&lt;br /&gt;
AssignmentDueDate.stub_chain(:where, :order)&lt;br /&gt;
&amp;lt;/pre&amp;gt;&lt;br /&gt;
The above stub returns two AssignmentDueDate objects whenever the where() and order() method are chained on AssignmentDueDate.&lt;br /&gt;
&amp;lt;pre&amp;gt;&lt;br /&gt;
ResubmissionTime.stub_chain(:where, :order)&lt;br /&gt;
&amp;lt;/pre&amp;gt;&lt;br /&gt;
The above stub returns two ResubmissionTime objects whenever the where() and order() method are chained on ResubmissionTime.&lt;br /&gt;
&amp;lt;pre&amp;gt;&lt;br /&gt;
AssignmentDueDate.stub_chain(:where, :order)&lt;br /&gt;
&amp;lt;/pre&amp;gt;&lt;br /&gt;
This stub is used in the second test case to return nil objects.&lt;br /&gt;
&lt;br /&gt;
the stub_chain method can be used to create stubs where chained methods are expected.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
'''Function Name : answers_by_question, answers_by_question_for_reviewee,answers_by_question_for_reviewee_in_round'''&lt;br /&gt;
&lt;br /&gt;
These three functions are sql queries that hit the DB to get a output record after a series of selections and joins. SQL queries that hit DB often do not have a high priority when it comes to testing, so the project does not aggressively test these functions. However, these functions are tested to make sure the queries are able to find the right column names and tables successfully. Any change in the table schema would be detected in these test cases. The functionality of these queries are not tested but instead existence of an output is tested. This ensures that answer.rb is able to make a successful db connection and is sync with the latest db schema. Since the function actually hits the DB, mocks can no longer be used, instead active records were created and saved in test db using FactoryGirl gem from the factories.rb. These records are cleared after every test case.&lt;br /&gt;
&lt;br /&gt;
Following factories were used to create records in the table&lt;br /&gt;
*question&lt;br /&gt;
*response_record&lt;br /&gt;
*response_map&lt;br /&gt;
*answer&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
'''Rspec Unit Test : answers_by_question, answers_by_question_for_reviewee,answers_by_question_for_reviewee_in_round'''&lt;br /&gt;
&lt;br /&gt;
The factories are created such a way that the query would return an output and the tests will pass if the query returns a non nil record. The functionality of these functions would be tested by the integration tests of the controller&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
'''Validation and Dependency  Rspec Test'''&lt;br /&gt;
&lt;br /&gt;
Apart from testing functions, the models are also tested for validations and external dependencies. Model answer.rb does not have any validations but does have a dependency on question.rb. Answer belongs_to question and this was tested using a simple dependency rspec test.&lt;br /&gt;
&amp;lt;pre&amp;gt;&lt;br /&gt;
it { should belong_to(:question) }&lt;br /&gt;
&amp;lt;/pre&amp;gt;&lt;br /&gt;
===Running Rspec===&lt;br /&gt;
*To run the test suite for a particular file only( answer_spec.rb):&lt;br /&gt;
&amp;lt;pre&amp;gt;&lt;br /&gt;
root@ubuntu:~/expertiza$ rspec spec/models/answer_spec.rb&lt;br /&gt;
&amp;lt;/pre&amp;gt;&lt;br /&gt;
*To run the entire suite of test cases:&lt;br /&gt;
&amp;lt;pre&amp;gt;&lt;br /&gt;
root@ubuntu:~/expertiza$ rspec spec&lt;br /&gt;
&amp;lt;/pre&amp;gt;&lt;br /&gt;
&lt;br /&gt;
===Rspec Test Results===&lt;br /&gt;
&lt;br /&gt;
&amp;lt;pre&amp;gt;&lt;br /&gt;
1 deprecation warning total&lt;br /&gt;
&lt;br /&gt;
Finished in 12.39 seconds (files took 11.25 seconds to load)&lt;br /&gt;
17 examples, 0 failures&lt;br /&gt;
&lt;br /&gt;
Randomized with seed 37447&lt;br /&gt;
&lt;br /&gt;
Coverage report generated for RSpec to /home/root/expertiza/coverage. 998 / 3919 LOC (25.47%) covered.&lt;br /&gt;
[Coveralls] Outside the CI environment, not sending data.&lt;br /&gt;
&amp;lt;/pre&amp;gt;&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
===References===&lt;br /&gt;
1. [https://en.wikipedia.org/wiki/RSpec wikipedia.org/wiki/RSpec] &amp;lt;br&amp;gt;&lt;br /&gt;
2. [http://rspec.info/ rspec.info/ ] &amp;lt;br&amp;gt;&lt;br /&gt;
3. [https://semaphoreci.com/community/tutorials/getting-started-with-rspec semaphoreci.com/community/tutorials/getting-started-with-rspec] &amp;lt;br&amp;gt;&lt;br /&gt;
4. [https://github.com/rspec/rspec github.com/rspec/rspec] &amp;lt;br&amp;gt;&lt;/div&gt;</summary>
		<author><name>Vdatla</name></author>
	</entry>
	<entry>
		<id>https://wiki.expertiza.ncsu.edu/index.php?title=CSC/ECE_517_Fall_2016/E1670._Unit_tests_for_answers.rb&amp;diff=103411</id>
		<title>CSC/ECE 517 Fall 2016/E1670. Unit tests for answers.rb</title>
		<link rel="alternate" type="text/html" href="https://wiki.expertiza.ncsu.edu/index.php?title=CSC/ECE_517_Fall_2016/E1670._Unit_tests_for_answers.rb&amp;diff=103411"/>
		<updated>2016-10-29T00:19:48Z</updated>

		<summary type="html">&lt;p&gt;Vdatla: &lt;/p&gt;
&lt;hr /&gt;
&lt;div&gt;==E1670 . Unit tests for answers.rb==&lt;br /&gt;
&lt;br /&gt;
This wiki page is for the description of changes made under E1670 OSS assignment for Fall 2016, CSC/ECE 517.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
__TOC__&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
===Background===&lt;br /&gt;
&lt;br /&gt;
Expertiza is an Open Source web application developed on Ruby On Rails platform. It is a platform which allows students to take assignments posted by the course instructors. Expertiza allows students to select assignment topics, form teams and submit their work. It also allows them to review other students' submissions and improve their work based on this feedback.&lt;br /&gt;
&lt;br /&gt;
===Project Description===&lt;br /&gt;
&lt;br /&gt;
In Expertiza, each questionnaire contains many questions, those question may have different types (e.g. checkbox, criterion, etc). When a user fills in a rubric, the responses for each question will become an answer record. The responses of rubrics are stored in answers table in DB. The answer.rb is the model for the answers table in DB. Answer.rb model does not have any test cases and the aim of the project is to write fast, effective and flexible unit test cases that offer maximum code coverage.&lt;br /&gt;
&lt;br /&gt;
===Files Created/Modified===&lt;br /&gt;
*answer_spec.rb&lt;br /&gt;
*factories.rb&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
===RSpec===&lt;br /&gt;
====RSpec Introduction====&lt;br /&gt;
RSpec is a testing framework for Ruby for behavior-driven development (BDD) licensed under MIT. It is inspired by JBehave and contains fully integrated JMock based framework which has a very rich and powerful DSL (domain-specific language) which resembles a natural language specification.&lt;br /&gt;
Composed of multiple libraries structured to work together, RSpec provides encapsulated testing via the describe block to specify the behavior of the class and the context for the unit test case.&lt;br /&gt;
&lt;br /&gt;
==== Why RSpec? ====&lt;br /&gt;
RSpec is easy to learn and implement and can be used with other testing tools like Cucumber and Minitest independently. It is extremely powerful for testing states with complicated setup and also helps in tearing down complex code to access the objects required for testing&lt;br /&gt;
RSpec semantics encourage agile thinking and practice and it structures the tests in a more intuitive way.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
===Functions in answers.rb===&lt;br /&gt;
&lt;br /&gt;
'''Function Name : Compute_scores'''&lt;br /&gt;
&lt;br /&gt;
Compute_scores is a function in model answer.rb which gives the average, maximum and minimum scores obtained in a series a responses/assessments. It has two input parameters: List of assessments and questions. The function iterates over each assessment to get the total score of that assessment. If the response or review is invalid, that assessment won’t be considered in the calculation of the score average. After iterating over all assessments, Max score, and Min scores are calculated along with the average score based on the number of valid assessments. Their scores are returned by the function.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
'''Rspec Unit Test : Compute_scores'''&lt;br /&gt;
&lt;br /&gt;
Following scenarios are tested:&lt;br /&gt;
&lt;br /&gt;
* To return scores as nil if the input list of assessments is nil. This is to make sure no Null Pointer exceptions are thrown by the code&lt;br /&gt;
*To return a particular score when a single valid assessment is given as an input.&lt;br /&gt;
*To return a particular score when multiple valid assessments are given as an input. This is to test the looping functionality of the method.&lt;br /&gt;
*To return a particular score when invalid assessments are given as an input. The validity and total scores are returned by a mock and not by the actual functions. This is to make the test cases less rigid so that failure of dependent functions do not disrupt the functionality of interface level tests.&lt;br /&gt;
*To return a particular score when invalid flag is nil. Invalid flag can either be 0,1 or nil. Nil situation is tested to prevent NullPointer Exceptions&lt;br /&gt;
*To check if the method get_total_score is called with the right parameters.&lt;br /&gt;
&lt;br /&gt;
This unit test uses a stub and returns a mock value.&lt;br /&gt;
&amp;lt;pre&amp;gt;&lt;br /&gt;
Answer.stub(:get_total_score)&lt;br /&gt;
&amp;lt;/pre&amp;gt;&lt;br /&gt;
This is to eliminate tight coupling between compute_scores and get_total_scores. Failure in get_total_scores wouldn't break the compute_scores test cases.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
'''Function Name : Get_total_scores'''&lt;br /&gt;
&lt;br /&gt;
This function is called by the Compute_scores method of the answer.rb model to compute the total score of an assessment. The input consists of assessment for which the total score is being calculated and the list of questions being evaluated in the assessment. The method uses questionnaire id from the questions and response id to obtain a score view questionnaire data. This score view is a read-only record. The questionnaire data mainly consists of q1_max_question_score, sum_of_weights and weighted_score. Before calculating the score, the function performs two crucial tasks. &lt;br /&gt;
*Checks if the answer for a scored question is nil. If it is nil or unanswered, the question will be ignored and not counted towards the score of this response.&lt;br /&gt;
* Calls the submission_valid function by passing the response record to set the @invalid flag based on the validity of the response.&lt;br /&gt;
The total score is calculated using the below formula&lt;br /&gt;
&lt;br /&gt;
&amp;lt;pre&amp;gt;&lt;br /&gt;
(weighted_score / (sum_of_weights * max_question_score)) * 100&lt;br /&gt;
&amp;lt;/pre&amp;gt;&lt;br /&gt;
&lt;br /&gt;
Any edge cases would return -1 indicating no score&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
'''Rspec Unit Test : Get_total_scores'''&lt;br /&gt;
&lt;br /&gt;
Following scenarios are tested:&lt;br /&gt;
&lt;br /&gt;
*To return an anticipated total score of a single response without any edge cases. Since this function will be called only on one response at a time, there is no need to test for multiple responses at the same time.&lt;br /&gt;
*To return an anticipated total score of a response where nil answer is for a scored question. This is to check if its weight gets removed from the sum_of_weights.&lt;br /&gt;
*To return -1 when the sum of weights becomes 0. This can happen when all the scored questions are unanswered. Return value of -1 is checked at the calling function to ensure if a score is returned or not.&lt;br /&gt;
*To return -1 when weighted_score of questionnaireData is nil&lt;br /&gt;
* To check if submission_valid is called. This method is called to set invalid flag to indicate whether the response entered is valid or not. The validity criteria is explained in the submission_valid? Function.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
This unit test uses two stubs and returns mock results&lt;br /&gt;
&amp;lt;pre&amp;gt;&lt;br /&gt;
ScoreView.stub(:find_by_sql)&lt;br /&gt;
&amp;lt;/pre&amp;gt;&lt;br /&gt;
&amp;lt;pre&amp;gt;&lt;br /&gt;
Answer.stub(:where)&lt;br /&gt;
&amp;lt;/pre&amp;gt;&lt;br /&gt;
This is to reduce the outcome of the test to depend on DB calls. For example, in case the connection to DB fails, this unit test would still pass making it less rigid.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
'''Function Name : submission_valid?'''&lt;br /&gt;
&lt;br /&gt;
This purpose of this function is to verify the validity of a review based on a deadline.  This function obtains a list of AssignmentDueDate objects  in descending order which is then compared against the current time to determine which deadlines are valid and which ones are not. The flag variable is used to represent whether or not a deadline was available in the previous iteration of the loop. If the flag is set to TRUE and the deadline is less than the current date, then latest_review_phase_start_time is set to this deadline. A list of ResubmissionTime objects is also retrieved from the controller. These objects are then compared against the then latest_review_phase_start_time variable to determine a response. &lt;br /&gt;
&lt;br /&gt;
Observations: The current implementation of the function is bugged. It retrieves a list of sorted AssignmentDueDate objects and proceeds to check if this list is empty. However, instead of exiting if the function if the list is empty, it carries on execution and raises an exception on hitting the for loop. &lt;br /&gt;
&lt;br /&gt;
*Checks if a review is valid or not by comparing its date with a list of deadlines.&lt;br /&gt;
*Returns 1 or 0 depending on validity&lt;br /&gt;
*Current implementation is bugged. Throws an exception if no AssignmentDueDate objects are passed, returns nil if any objects are passed.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
'''Rspec Unit Test : submission_valid?'''&lt;br /&gt;
&lt;br /&gt;
Following scenarios are tested:&lt;br /&gt;
&lt;br /&gt;
*Passing valid AssignmentDueDate objects&lt;br /&gt;
*Not passing any AssignmentDueDate objects&lt;br /&gt;
&lt;br /&gt;
When valid AssignmentDueDate objects are passed, stubs are used to create fake AssignmentDueDate Objects and ResubmissionTime objects. These objects are then populated with valid deadline dates and deadline_type values. These values are then supplied when requested by the submission_valid? Function rather than actually calling the function.  The current implementation of this test case expects the program to throw an error when it reaches the for loop. Once this bug is fixed, this test case may be re-written to test a more legitimate test case.&lt;br /&gt;
&lt;br /&gt;
In case an empty list of AssignmentDueDate objects is passed back to the submission_valid?() method. This would cause the function to return nil. When this function is fixed, the following test case may be re-written to test for a more legitimate test-case.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
This unit test uses two stubs and returns mock results&lt;br /&gt;
&amp;lt;pre&amp;gt;&lt;br /&gt;
AssignmentDueDate.stub_chain(:where, :order)&lt;br /&gt;
&amp;lt;/pre&amp;gt;&lt;br /&gt;
The above stub returns two AssignmentDueDate objects whenever the where() and order() method are chained on AssignmentDueDate.&lt;br /&gt;
&amp;lt;pre&amp;gt;&lt;br /&gt;
ResubmissionTime.stub_chain(:where, :order)&lt;br /&gt;
&amp;lt;/pre&amp;gt;&lt;br /&gt;
The above stub returns two ResubmissionTime objects whenever the where() and order() method are chained on ResubmissionTime.&lt;br /&gt;
&amp;lt;pre&amp;gt;&lt;br /&gt;
AssignmentDueDate.stub_chain(:where, :order)&lt;br /&gt;
&amp;lt;/pre&amp;gt;&lt;br /&gt;
This stub is used in the second test case to return nil objects.&lt;br /&gt;
&lt;br /&gt;
the stub_chain method can be used to create stubs where chained methods are expected.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
'''Function Name : answers_by_question, answers_by_question_for_reviewee,answers_by_question_for_reviewee_in_round'''&lt;br /&gt;
&lt;br /&gt;
These three functions are sql queries that hit the DB to get a output record after a series of selections and joins. SQL queries that hit DB often do not have a high priority when it comes to testing, so the project does not aggressively test these functions. However, these functions are tested to make sure the queries are able to find the right column names and tables successfully. Any change in the table schema would be detected in these test cases. The functionality of these queries are not tested but instead existence of an output is tested. This ensures that answer.rb is able to make a successful db connection and is sync with the latest db schema. Since the function actually hits the DB, mocks can no longer be used, instead active records were created and saved in test db using FactoryGirl gem from the factories.rb. These records are cleared after every test case.&lt;br /&gt;
&lt;br /&gt;
Following factories were used to create records in the table&lt;br /&gt;
*question&lt;br /&gt;
*response_record&lt;br /&gt;
*response_map&lt;br /&gt;
*answer&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
'''Rspec Unit Test : answers_by_question, answers_by_question_for_reviewee,answers_by_question_for_reviewee_in_round'''&lt;br /&gt;
&lt;br /&gt;
The factories are created such a way that the query would return an output and the tests will pass if the query returns a non nil record. The functionality of these functions would be tested by the integration tests of the controller&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
'''Validation and Dependency  Rspec Test'''&lt;br /&gt;
&lt;br /&gt;
Apart from testing functions, the models are also tested for validations and external dependencies. Model answer.rb does not have any validations but does have a dependency on question.rb. Answer belongs_to question and this was tested using a simple dependency rspec test.&lt;br /&gt;
&amp;lt;pre&amp;gt;&lt;br /&gt;
it { should belong_to(:question) }&lt;br /&gt;
&amp;lt;/pre&amp;gt;&lt;br /&gt;
===Running Rspec===&lt;br /&gt;
*To run the test suite for a particular file only( answer_spec.rb):&lt;br /&gt;
&amp;lt;pre&amp;gt;&lt;br /&gt;
root@ubuntu:~/expertiza$ rspec spec/models/answer_spec.rb&lt;br /&gt;
&amp;lt;/pre&amp;gt;&lt;br /&gt;
*To run the entire suite of test cases:&lt;br /&gt;
&amp;lt;pre&amp;gt;&lt;br /&gt;
root@ubuntu:~/expertiza$ rspec spec&lt;br /&gt;
&amp;lt;/pre&amp;gt;&lt;br /&gt;
&lt;br /&gt;
===Rspec Test Results===&lt;br /&gt;
&lt;br /&gt;
&amp;lt;pre&amp;gt;&lt;br /&gt;
1 deprecation warning total&lt;br /&gt;
&lt;br /&gt;
Finished in 12.39 seconds (files took 11.25 seconds to load)&lt;br /&gt;
17 examples, 0 failures&lt;br /&gt;
&lt;br /&gt;
Randomized with seed 37447&lt;br /&gt;
&lt;br /&gt;
Coverage report generated for RSpec to /home/root/expertiza/coverage. 998 / 3919 LOC (25.47%) covered.&lt;br /&gt;
[Coveralls] Outside the CI environment, not sending data.&lt;br /&gt;
&amp;lt;/pre&amp;gt;&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
===References===&lt;br /&gt;
1. [https://en.wikipedia.org/wiki/RSpec wikipedia.org/wiki/RSpec] &amp;lt;br&amp;gt;&lt;br /&gt;
2. [http://rspec.info/] &amp;lt;br&amp;gt;&lt;br /&gt;
3. [https://semaphoreci.com/community/tutorials/getting-started-with-rspec] &amp;lt;br&amp;gt;&lt;br /&gt;
4. [https://github.com/rspec/rspec] &amp;lt;br&amp;gt;&lt;/div&gt;</summary>
		<author><name>Vdatla</name></author>
	</entry>
	<entry>
		<id>https://wiki.expertiza.ncsu.edu/index.php?title=CSC/ECE_517_Fall_2016/E1670._Unit_tests_for_answers.rb&amp;diff=103408</id>
		<title>CSC/ECE 517 Fall 2016/E1670. Unit tests for answers.rb</title>
		<link rel="alternate" type="text/html" href="https://wiki.expertiza.ncsu.edu/index.php?title=CSC/ECE_517_Fall_2016/E1670._Unit_tests_for_answers.rb&amp;diff=103408"/>
		<updated>2016-10-29T00:18:51Z</updated>

		<summary type="html">&lt;p&gt;Vdatla: &lt;/p&gt;
&lt;hr /&gt;
&lt;div&gt;==E1670 . Unit tests for answers.rb==&lt;br /&gt;
&lt;br /&gt;
This wiki page is for the description of changes made under E1670 OSS assignment for Fall 2016, CSC/ECE 517.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
__TOC__&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
===Background===&lt;br /&gt;
&lt;br /&gt;
Expertiza is an Open Source web application developed on Ruby On Rails platform. It is a platform which allows students to take assignments posted by the course instructors. Expertiza allows students to select assignment topics, form teams and submit their work. It also allows them to review other students' submissions and improve their work based on this feedback.&lt;br /&gt;
&lt;br /&gt;
===Project Description===&lt;br /&gt;
&lt;br /&gt;
In Expertiza, each questionnaire contains many questions, those question may have different types (e.g. checkbox, criterion, etc). When a user fills in a rubric, the responses for each question will become an answer record. The responses of rubrics are stored in answers table in DB. The answer.rb is the model for the answers table in DB. Answer.rb model does not have any test cases and the aim of the project is to write fast, effective and flexible unit test cases that offer maximum code coverage.&lt;br /&gt;
&lt;br /&gt;
===Files Created/Modified===&lt;br /&gt;
*answer_spec.rb&lt;br /&gt;
*factories.rb&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
===RSpec===&lt;br /&gt;
====RSpec Introduction====&lt;br /&gt;
RSpec is a testing framework for Ruby for behavior-driven development (BDD) licensed under MIT. It is inspired by JBehave and contains fully integrated JMock based framework which has a very rich and powerful DSL (domain-specific language) which resembles a natural language specification.&lt;br /&gt;
Composed of multiple libraries structured to work together, RSpec provides encapsulated testing via the describe block to specify the behavior of the class and the context for the unit test case.&lt;br /&gt;
&lt;br /&gt;
==== Why RSpec? ====&lt;br /&gt;
RSpec is easy to learn and implement and can be used with other testing tools like Cucumber and Minitest independently. It is extremely powerful for testing states with complicated setup and also helps in tearing down complex code to access the objects required for testing&lt;br /&gt;
RSpec semantics encourage agile thinking and practice and it structures the tests in a more intuitive way.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
===Functions in answers.rb===&lt;br /&gt;
&lt;br /&gt;
'''Function Name : Compute_scores'''&lt;br /&gt;
&lt;br /&gt;
Compute_scores is a function in model answer.rb which gives the average, maximum and minimum scores obtained in a series a responses/assessments. It has two input parameters: List of assessments and questions. The function iterates over each assessment to get the total score of that assessment. If the response or review is invalid, that assessment won’t be considered in the calculation of the score average. After iterating over all assessments, Max score, and Min scores are calculated along with the average score based on the number of valid assessments. Their scores are returned by the function.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
'''Rspec Unit Test : Compute_scores'''&lt;br /&gt;
&lt;br /&gt;
Following scenarios are tested:&lt;br /&gt;
&lt;br /&gt;
* To return scores as nil if the input list of assessments is nil. This is to make sure no Null Pointer exceptions are thrown by the code&lt;br /&gt;
*To return a particular score when a single valid assessment is given as an input.&lt;br /&gt;
*To return a particular score when multiple valid assessments are given as an input. This is to test the looping functionality of the method.&lt;br /&gt;
*To return a particular score when invalid assessments are given as an input. The validity and total scores are returned by a mock and not by the actual functions. This is to make the test cases less rigid so that failure of dependent functions do not disrupt the functionality of interface level tests.&lt;br /&gt;
*To return a particular score when invalid flag is nil. Invalid flag can either be 0,1 or nil. Nil situation is tested to prevent NullPointer Exceptions&lt;br /&gt;
*To check if the method get_total_score is called with the right parameters.&lt;br /&gt;
&lt;br /&gt;
This unit test uses a stub and returns a mock value.&lt;br /&gt;
&amp;lt;pre&amp;gt;&lt;br /&gt;
Answer.stub(:get_total_score)&lt;br /&gt;
&amp;lt;/pre&amp;gt;&lt;br /&gt;
This is to eliminate tight coupling between compute_scores and get_total_scores. Failure in get_total_scores wouldn't break the compute_scores test cases.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
'''Function Name : Get_total_scores'''&lt;br /&gt;
&lt;br /&gt;
This function is called by the Compute_scores method of the answer.rb model to compute the total score of an assessment. The input consists of assessment for which the total score is being calculated and the list of questions being evaluated in the assessment. The method uses questionnaire id from the questions and response id to obtain a score view questionnaire data. This score view is a read-only record. The questionnaire data mainly consists of q1_max_question_score, sum_of_weights and weighted_score. Before calculating the score, the function performs two crucial tasks. &lt;br /&gt;
*Checks if the answer for a scored question is nil. If it is nil or unanswered, the question will be ignored and not counted towards the score of this response.&lt;br /&gt;
* Calls the submission_valid function by passing the response record to set the @invalid flag based on the validity of the response.&lt;br /&gt;
The total score is calculated using the below formula&lt;br /&gt;
&lt;br /&gt;
&amp;lt;pre&amp;gt;&lt;br /&gt;
(weighted_score / (sum_of_weights * max_question_score)) * 100&lt;br /&gt;
&amp;lt;/pre&amp;gt;&lt;br /&gt;
&lt;br /&gt;
Any edge cases would return -1 indicating no score&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
'''Rspec Unit Test : Get_total_scores'''&lt;br /&gt;
&lt;br /&gt;
Following scenarios are tested:&lt;br /&gt;
&lt;br /&gt;
*To return an anticipated total score of a single response without any edge cases. Since this function will be called only on one response at a time, there is no need to test for multiple responses at the same time.&lt;br /&gt;
*To return an anticipated total score of a response where nil answer is for a scored question. This is to check if its weight gets removed from the sum_of_weights.&lt;br /&gt;
*To return -1 when the sum of weights becomes 0. This can happen when all the scored questions are unanswered. Return value of -1 is checked at the calling function to ensure if a score is returned or not.&lt;br /&gt;
*To return -1 when weighted_score of questionnaireData is nil&lt;br /&gt;
* To check if submission_valid is called. This method is called to set invalid flag to indicate whether the response entered is valid or not. The validity criteria is explained in the submission_valid? Function.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
This unit test uses two stubs and returns mock results&lt;br /&gt;
&amp;lt;pre&amp;gt;&lt;br /&gt;
ScoreView.stub(:find_by_sql)&lt;br /&gt;
&amp;lt;/pre&amp;gt;&lt;br /&gt;
&amp;lt;pre&amp;gt;&lt;br /&gt;
Answer.stub(:where)&lt;br /&gt;
&amp;lt;/pre&amp;gt;&lt;br /&gt;
This is to reduce the outcome of the test to depend on DB calls. For example, in case the connection to DB fails, this unit test would still pass making it less rigid.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
'''Function Name : submission_valid?'''&lt;br /&gt;
&lt;br /&gt;
This purpose of this function is to verify the validity of a review based on a deadline.  This function obtains a list of AssignmentDueDate objects  in descending order which is then compared against the current time to determine which deadlines are valid and which ones are not. The flag variable is used to represent whether or not a deadline was available in the previous iteration of the loop. If the flag is set to TRUE and the deadline is less than the current date, then latest_review_phase_start_time is set to this deadline. A list of ResubmissionTime objects is also retrieved from the controller. These objects are then compared against the then latest_review_phase_start_time variable to determine a response. &lt;br /&gt;
&lt;br /&gt;
Observations: The current implementation of the function is bugged. It retrieves a list of sorted AssignmentDueDate objects and proceeds to check if this list is empty. However, instead of exiting if the function if the list is empty, it carries on execution and raises an exception on hitting the for loop. &lt;br /&gt;
&lt;br /&gt;
*Checks if a review is valid or not by comparing its date with a list of deadlines.&lt;br /&gt;
*Returns 1 or 0 depending on validity&lt;br /&gt;
*Current implementation is bugged. Throws an exception if no AssignmentDueDate objects are passed, returns nil if any objects are passed.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
'''Rspec Unit Test : submission_valid?'''&lt;br /&gt;
&lt;br /&gt;
Following scenarios are tested:&lt;br /&gt;
&lt;br /&gt;
*Passing valid AssignmentDueDate objects&lt;br /&gt;
*Not passing any AssignmentDueDate objects&lt;br /&gt;
&lt;br /&gt;
When valid AssignmentDueDate objects are passed, stubs are used to create fake AssignmentDueDate Objects and ResubmissionTime objects. These objects are then populated with valid deadline dates and deadline_type values. These values are then supplied when requested by the submission_valid? Function rather than actually calling the function.  The current implementation of this test case expects the program to throw an error when it reaches the for loop. Once this bug is fixed, this test case may be re-written to test a more legitimate test case.&lt;br /&gt;
&lt;br /&gt;
In case an empty list of AssignmentDueDate objects is passed back to the submission_valid?() method. This would cause the function to return nil. When this function is fixed, the following test case may be re-written to test for a more legitimate test-case.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
This unit test uses two stubs and returns mock results&lt;br /&gt;
&amp;lt;pre&amp;gt;&lt;br /&gt;
AssignmentDueDate.stub_chain(:where, :order)&lt;br /&gt;
&amp;lt;/pre&amp;gt;&lt;br /&gt;
The above stub returns two AssignmentDueDate objects whenever the where() and order() method are chained on AssignmentDueDate.&lt;br /&gt;
&amp;lt;pre&amp;gt;&lt;br /&gt;
ResubmissionTime.stub_chain(:where, :order)&lt;br /&gt;
&amp;lt;/pre&amp;gt;&lt;br /&gt;
The above stub returns two ResubmissionTime objects whenever the where() and order() method are chained on ResubmissionTime.&lt;br /&gt;
&amp;lt;pre&amp;gt;&lt;br /&gt;
AssignmentDueDate.stub_chain(:where, :order)&lt;br /&gt;
&amp;lt;/pre&amp;gt;&lt;br /&gt;
This stub is used in the second test case to return nil objects.&lt;br /&gt;
&lt;br /&gt;
the stub_chain method can be used to create stubs where chained methods are expected.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
'''Function Name : answers_by_question, answers_by_question_for_reviewee,answers_by_question_for_reviewee_in_round'''&lt;br /&gt;
&lt;br /&gt;
These three functions are sql queries that hit the DB to get a output record after a series of selections and joins. SQL queries that hit DB often do not have a high priority when it comes to testing, so the project does not aggressively test these functions. However, these functions are tested to make sure the queries are able to find the right column names and tables successfully. Any change in the table schema would be detected in these test cases. The functionality of these queries are not tested but instead existence of an output is tested. This ensures that answer.rb is able to make a successful db connection and is sync with the latest db schema. Since the function actually hits the DB, mocks can no longer be used, instead active records were created and saved in test db using FactoryGirl gem from the factories.rb. These records are cleared after every test case.&lt;br /&gt;
&lt;br /&gt;
Following factories were used to create records in the table&lt;br /&gt;
*question&lt;br /&gt;
*response_record&lt;br /&gt;
*response_map&lt;br /&gt;
*answer&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
'''Rspec Unit Test : answers_by_question, answers_by_question_for_reviewee,answers_by_question_for_reviewee_in_round'''&lt;br /&gt;
&lt;br /&gt;
The factories are created such a way that the query would return an output and the tests will pass if the query returns a non nil record. The functionality of these functions would be tested by the integration tests of the controller&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
'''Validation and Dependency  Rspec Test'''&lt;br /&gt;
&lt;br /&gt;
Apart from testing functions, the models are also tested for validations and external dependencies. Model answer.rb does not have any validations but does have a dependency on question.rb. Answer belongs_to question and this was tested using a simple dependency rspec test.&lt;br /&gt;
&amp;lt;pre&amp;gt;&lt;br /&gt;
it { should belong_to(:question) }&lt;br /&gt;
&amp;lt;/pre&amp;gt;&lt;br /&gt;
===Running Rspec===&lt;br /&gt;
*To run the test suite for a particular file only( answer_spec.rb):&lt;br /&gt;
&amp;lt;pre&amp;gt;&lt;br /&gt;
root@ubuntu:~/expertiza$ rspec spec/models/answer_spec.rb&lt;br /&gt;
&amp;lt;/pre&amp;gt;&lt;br /&gt;
*To run the entire suite of test cases:&lt;br /&gt;
&amp;lt;pre&amp;gt;&lt;br /&gt;
root@ubuntu:~/expertiza$ rspec spec&lt;br /&gt;
&amp;lt;/pre&amp;gt;&lt;br /&gt;
&lt;br /&gt;
===Rspec Test Results===&lt;br /&gt;
&lt;br /&gt;
&amp;lt;pre&amp;gt;&lt;br /&gt;
1 deprecation warning total&lt;br /&gt;
&lt;br /&gt;
Finished in 12.39 seconds (files took 11.25 seconds to load)&lt;br /&gt;
17 examples, 0 failures&lt;br /&gt;
&lt;br /&gt;
Randomized with seed 37447&lt;br /&gt;
&lt;br /&gt;
Coverage report generated for RSpec to /home/root/expertiza/coverage. 998 / 3919 LOC (25.47%) covered.&lt;br /&gt;
[Coveralls] Outside the CI environment, not sending data.&lt;br /&gt;
&amp;lt;/pre&amp;gt;&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
===References===&lt;br /&gt;
1. [https://en.wikipedia.org/wiki/RSpec] &amp;lt;br&amp;gt;&lt;br /&gt;
2. [http://rspec.info/] &amp;lt;br&amp;gt;&lt;br /&gt;
3. [https://semaphoreci.com/community/tutorials/getting-started-with-rspec] &amp;lt;br&amp;gt;&lt;br /&gt;
4. [https://github.com/rspec/rspec] &amp;lt;br&amp;gt;&lt;/div&gt;</summary>
		<author><name>Vdatla</name></author>
	</entry>
	<entry>
		<id>https://wiki.expertiza.ncsu.edu/index.php?title=CSC/ECE_517_Fall_2016/E1670._Unit_tests_for_answers.rb&amp;diff=103406</id>
		<title>CSC/ECE 517 Fall 2016/E1670. Unit tests for answers.rb</title>
		<link rel="alternate" type="text/html" href="https://wiki.expertiza.ncsu.edu/index.php?title=CSC/ECE_517_Fall_2016/E1670._Unit_tests_for_answers.rb&amp;diff=103406"/>
		<updated>2016-10-29T00:15:27Z</updated>

		<summary type="html">&lt;p&gt;Vdatla: &lt;/p&gt;
&lt;hr /&gt;
&lt;div&gt;==E1670 . Unit tests for answers.rb==&lt;br /&gt;
&lt;br /&gt;
This wiki page is for the description of changes made under E1670 OSS assignment for Fall 2016, CSC/ECE 517.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
__TOC__&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
===Background===&lt;br /&gt;
&lt;br /&gt;
Expertiza is an Open Source web application developed on Ruby On Rails platform. It is a platform which allows students to take assignments posted by the course instructors. Expertiza allows students to select assignment topics, form teams and submit their work. It also allows them to review other students' submissions and improve their work based on this feedback.&lt;br /&gt;
&lt;br /&gt;
===Project Description===&lt;br /&gt;
&lt;br /&gt;
In Expertiza, each questionnaire contains many questions, those question may have different types (e.g. checkbox, criterion, etc). When a user fills in a rubric, the responses for each question will become an answer record. The responses of rubrics are stored in answers table in DB. The answer.rb is the model for the answers table in DB. Answer.rb model does not have any test cases and the aim of the project is to write fast, effective and flexible unit test cases that offer maximum code coverage.&lt;br /&gt;
&lt;br /&gt;
===Files Created/Modified===&lt;br /&gt;
*answer_spec.rb&lt;br /&gt;
*factories.rb&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
===RSpec===&lt;br /&gt;
====RSpec Introduction====&lt;br /&gt;
RSpec is a testing framework for Ruby for behavior-driven development (BDD) licensed under MIT. It is inspired by JBehave and contains fully integrated JMock based framework which has a very rich and powerful DSL (domain-specific language) which resembles a natural language specification.&lt;br /&gt;
Composed of multiple libraries structured to work together, RSpec provides encapsulated testing via the describe block to specify the behavior of the class and the context for the unit test case.&lt;br /&gt;
&lt;br /&gt;
==== Why RSpec? ====&lt;br /&gt;
RSpec is easy to learn and implement and can be used with other testing tools like Cucumber and Minitest independently. It is extremely powerful for testing states with complicated setup and also helps in tearing down complex code to access the objects required for testing&lt;br /&gt;
RSpec semantics encourage agile thinking and practice and it structures the tests in a more intuitive way.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
===Functions in answers.rb===&lt;br /&gt;
&lt;br /&gt;
'''Function Name : Compute_scores'''&lt;br /&gt;
&lt;br /&gt;
Compute_scores is a function in model answer.rb which gives the average, maximum and minimum scores obtained in a series a responses/assessments. It has two input parameters: List of assessments and questions. The function iterates over each assessment to get the total score of that assessment. If the response or review is invalid, that assessment won’t be considered in the calculation of the score average. After iterating over all assessments, Max score, and Min scores are calculated along with the average score based on the number of valid assessments. Their scores are returned by the function.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
'''Rspec Unit Test : Compute_scores'''&lt;br /&gt;
&lt;br /&gt;
Following scenarios are tested:&lt;br /&gt;
&lt;br /&gt;
* To return scores as nil if the input list of assessments is nil. This is to make sure no Null Pointer exceptions are thrown by the code&lt;br /&gt;
*To return a particular score when a single valid assessment is given as an input.&lt;br /&gt;
*To return a particular score when multiple valid assessments are given as an input. This is to test the looping functionality of the method.&lt;br /&gt;
*To return a particular score when invalid assessments are given as an input. The validity and total scores are returned by a mock and not by the actual functions. This is to make the test cases less rigid so that failure of dependent functions do not disrupt the functionality of interface level tests.&lt;br /&gt;
*To return a particular score when invalid flag is nil. Invalid flag can either be 0,1 or nil. Nil situation is tested to prevent NullPointer Exceptions&lt;br /&gt;
*To check if the method get_total_score is called with the right parameters.&lt;br /&gt;
&lt;br /&gt;
This unit test uses a stub and returns a mock value.&lt;br /&gt;
&amp;lt;pre&amp;gt;&lt;br /&gt;
Answer.stub(:get_total_score)&lt;br /&gt;
&amp;lt;/pre&amp;gt;&lt;br /&gt;
This is to eliminate tight coupling between compute_scores and get_total_scores. Failure in get_total_scores wouldn't break the compute_scores test cases.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
'''Function Name : Get_total_scores'''&lt;br /&gt;
&lt;br /&gt;
This function is called by the Compute_scores method of the answer.rb model to compute the total score of an assessment. The input consists of assessment for which the total score is being calculated and the list of questions being evaluated in the assessment. The method uses questionnaire id from the questions and response id to obtain a score view questionnaire data. This score view is a read-only record. The questionnaire data mainly consists of q1_max_question_score, sum_of_weights and weighted_score. Before calculating the score, the function performs two crucial tasks. &lt;br /&gt;
*Checks if the answer for a scored question is nil. If it is nil or unanswered, the question will be ignored and not counted towards the score of this response.&lt;br /&gt;
* Calls the submission_valid function by passing the response record to set the @invalid flag based on the validity of the response.&lt;br /&gt;
The total score is calculated using the below formula&lt;br /&gt;
&lt;br /&gt;
&amp;lt;pre&amp;gt;&lt;br /&gt;
(weighted_score / (sum_of_weights * max_question_score)) * 100&lt;br /&gt;
&amp;lt;/pre&amp;gt;&lt;br /&gt;
&lt;br /&gt;
Any edge cases would return -1 indicating no score&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
'''Rspec Unit Test : Get_total_scores'''&lt;br /&gt;
&lt;br /&gt;
Following scenarios are tested:&lt;br /&gt;
&lt;br /&gt;
*To return an anticipated total score of a single response without any edge cases. Since this function will be called only on one response at a time, there is no need to test for multiple responses at the same time.&lt;br /&gt;
*To return an anticipated total score of a response where nil answer is for a scored question. This is to check if its weight gets removed from the sum_of_weights.&lt;br /&gt;
*To return -1 when the sum of weights becomes 0. This can happen when all the scored questions are unanswered. Return value of -1 is checked at the calling function to ensure if a score is returned or not.&lt;br /&gt;
*To return -1 when weighted_score of questionnaireData is nil&lt;br /&gt;
* To check if submission_valid is called. This method is called to set invalid flag to indicate whether the response entered is valid or not. The validity criteria is explained in the submission_valid? Function.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
This unit test uses two stubs and returns mock results&lt;br /&gt;
&amp;lt;pre&amp;gt;&lt;br /&gt;
ScoreView.stub(:find_by_sql)&lt;br /&gt;
&amp;lt;/pre&amp;gt;&lt;br /&gt;
&amp;lt;pre&amp;gt;&lt;br /&gt;
Answer.stub(:where)&lt;br /&gt;
&amp;lt;/pre&amp;gt;&lt;br /&gt;
This is to reduce the outcome of the test to depend on DB calls. For example, in case the connection to DB fails, this unit test would still pass making it less rigid.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
'''Function Name : submission_valid?'''&lt;br /&gt;
&lt;br /&gt;
This purpose of this function is to verify the validity of a review based on a deadline.  This function obtains a list of AssignmentDueDate objects  in descending order which is then compared against the current time to determine which deadlines are valid and which ones are not. The flag variable is used to represent whether or not a deadline was available in the previous iteration of the loop. If the flag is set to TRUE and the deadline is less than the current date, then latest_review_phase_start_time is set to this deadline. A list of ResubmissionTime objects is also retrieved from the controller. These objects are then compared against the then latest_review_phase_start_time variable to determine a response. &lt;br /&gt;
&lt;br /&gt;
Observations: The current implementation of the function is bugged. It retrieves a list of sorted AssignmentDueDate objects and proceeds to check if this list is empty. However, instead of exiting if the function if the list is empty, it carries on execution and raises an exception on hitting the for loop. &lt;br /&gt;
&lt;br /&gt;
*Checks if a review is valid or not by comparing its date with a list of deadlines.&lt;br /&gt;
*Returns 1 or 0 depending on validity&lt;br /&gt;
*Current implementation is bugged. Throws an exception if no AssignmentDueDate objects are passed, returns nil if any objects are passed.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
'''Rspec Unit Test : submission_valid?'''&lt;br /&gt;
&lt;br /&gt;
Following scenarios are tested:&lt;br /&gt;
&lt;br /&gt;
*Passing valid AssignmentDueDate objects&lt;br /&gt;
*Not passing any AssignmentDueDate objects&lt;br /&gt;
&lt;br /&gt;
When valid AssignmentDueDate objects are passed, stubs are used to create fake AssignmentDueDate Objects and ResubmissionTime objects. These objects are then populated with valid deadline dates and deadline_type values. These values are then supplied when requested by the submission_valid? Function rather than actually calling the function.  The current implementation of this test case expects the program to throw an error when it reaches the for loop. Once this bug is fixed, this test case may be re-written to test a more legitimate test case.&lt;br /&gt;
&lt;br /&gt;
In case an empty list of AssignmentDueDate objects is passed back to the submission_valid?() method. This would cause the function to return nil. When this function is fixed, the following test case may be re-written to test for a more legitimate test-case.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
This unit test uses two stubs and returns mock results&lt;br /&gt;
&amp;lt;pre&amp;gt;&lt;br /&gt;
AssignmentDueDate.stub_chain(:where, :order)&lt;br /&gt;
&amp;lt;/pre&amp;gt;&lt;br /&gt;
The above stub returns two AssignmentDueDate objects whenever the where() and order() method are chained on AssignmentDueDate.&lt;br /&gt;
&amp;lt;pre&amp;gt;&lt;br /&gt;
ResubmissionTime.stub_chain(:where, :order)&lt;br /&gt;
&amp;lt;/pre&amp;gt;&lt;br /&gt;
The above stub returns two ResubmissionTime objects whenever the where() and order() method are chained on ResubmissionTime.&lt;br /&gt;
&amp;lt;pre&amp;gt;&lt;br /&gt;
AssignmentDueDate.stub_chain(:where, :order)&lt;br /&gt;
&amp;lt;/pre&amp;gt;&lt;br /&gt;
This stub is used in the second test case to return nil objects.&lt;br /&gt;
&lt;br /&gt;
the stub_chain method can be used to create stubs where chained methods are expected.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
'''Function Name : answers_by_question, answers_by_question_for_reviewee,answers_by_question_for_reviewee_in_round'''&lt;br /&gt;
&lt;br /&gt;
These three functions are sql queries that hit the DB to get a output record after a series of selections and joins. SQL queries that hit DB often do not have a high priority when it comes to testing, so the project does not aggressively test these functions. However, these functions are tested to make sure the queries are able to find the right column names and tables successfully. Any change in the table schema would be detected in these test cases. The functionality of these queries are not tested but instead existence of an output is tested. This ensures that answer.rb is able to make a successful db connection and is sync with the latest db schema. Since the function actually hits the DB, mocks can no longer be used, instead active records were created and saved in test db using FactoryGirl gem from the factories.rb. These records are cleared after every test case.&lt;br /&gt;
&lt;br /&gt;
Following factories were used to create records in the table&lt;br /&gt;
*question&lt;br /&gt;
*response_record&lt;br /&gt;
*response_map&lt;br /&gt;
*answer&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
'''Rspec Unit Test : answers_by_question, answers_by_question_for_reviewee,answers_by_question_for_reviewee_in_round'''&lt;br /&gt;
&lt;br /&gt;
The factories are created such a way that the query would return an output and the tests will pass if the query returns a non nil record. The functionality of these functions would be tested by the integration tests of the controller&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
'''Validation and Dependency  Rspec Test'''&lt;br /&gt;
&lt;br /&gt;
Apart from testing functions, the models are also tested for validations and external dependencies. Model answer.rb does not have any validations but does have a dependency on question.rb. Answer belongs_to question and this was tested using a simple dependency rspec test.&lt;br /&gt;
&amp;lt;pre&amp;gt;&lt;br /&gt;
it { should belong_to(:question) }&lt;br /&gt;
&amp;lt;/pre&amp;gt;&lt;br /&gt;
&lt;br /&gt;
===Rspec Test Results===&lt;br /&gt;
&lt;br /&gt;
&amp;lt;pre&amp;gt;&lt;br /&gt;
1 deprecation warning total&lt;br /&gt;
&lt;br /&gt;
Finished in 12.39 seconds (files took 11.25 seconds to load)&lt;br /&gt;
17 examples, 0 failures&lt;br /&gt;
&lt;br /&gt;
Randomized with seed 37447&lt;br /&gt;
&lt;br /&gt;
Coverage report generated for RSpec to /home/root/expertiza/coverage. 998 / 3919 LOC (25.47%) covered.&lt;br /&gt;
[Coveralls] Outside the CI environment, not sending data.&lt;br /&gt;
&amp;lt;/pre&amp;gt;&lt;/div&gt;</summary>
		<author><name>Vdatla</name></author>
	</entry>
	<entry>
		<id>https://wiki.expertiza.ncsu.edu/index.php?title=CSC/ECE_517_Fall_2016/E1670._Unit_tests_for_answers.rb&amp;diff=103403</id>
		<title>CSC/ECE 517 Fall 2016/E1670. Unit tests for answers.rb</title>
		<link rel="alternate" type="text/html" href="https://wiki.expertiza.ncsu.edu/index.php?title=CSC/ECE_517_Fall_2016/E1670._Unit_tests_for_answers.rb&amp;diff=103403"/>
		<updated>2016-10-29T00:14:56Z</updated>

		<summary type="html">&lt;p&gt;Vdatla: &lt;/p&gt;
&lt;hr /&gt;
&lt;div&gt;==E1670 . Unit tests for answers.rb==&lt;br /&gt;
&lt;br /&gt;
This wiki page is for the description of changes made under E1670 OSS assignment for Fall 2016, CSC/ECE 517.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
__TOC__&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
===Background===&lt;br /&gt;
&lt;br /&gt;
Expertiza is an Open Source web application developed on Ruby On Rails platform. It is a platform which allows students to take assignments posted by the course instructors. Expertiza allows students to select assignment topics, form teams and submit their work. It also allows them to review other students' submissions and improve their work based on this feedback.&lt;br /&gt;
&lt;br /&gt;
===Project Description===&lt;br /&gt;
&lt;br /&gt;
In Expertiza, each questionnaire contains many questions, those question may have different types (e.g. checkbox, criterion, etc). When a user fills in a rubric, the responses for each question will become an answer record. The responses of rubrics are stored in answers table in DB. The answer.rb is the model for the answers table in DB. Answer.rb model does not have any test cases and the aim of the project is to write fast, effective and flexible unit test cases that offer maximum code coverage.&lt;br /&gt;
&lt;br /&gt;
===Files Created/Modified===&lt;br /&gt;
*answer_spec.rb&lt;br /&gt;
*factories.rb&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
===RSpec===&lt;br /&gt;
====RSpec Introduction====&lt;br /&gt;
RSpec is a testing framework for Ruby for behavior-driven development (BDD) licensed under MIT. It is inspired by JBehave and contains fully integrated JMock based framework which has a very rich and powerful DSL (domain-specific language) which resembles a natural language specification.&lt;br /&gt;
Composed of multiple libraries structured to work together, RSpec provides encapsulated testing via the describe block to specify the behavior of the class and the context for the unit test case.&lt;br /&gt;
&lt;br /&gt;
==== Why RSpec? ====&lt;br /&gt;
RSpec is easy to learn and implement and can be used with other testing tools like Cucumber and Minitest independently. It is extremely powerful for testing states with complicated setup and also helps in tearing down complex code to access the objects required for testing&lt;br /&gt;
RSpec semantics encourage agile thinking and practice and it structures the tests in a more intuitive way.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
===Functions in answers.rb===&lt;br /&gt;
&lt;br /&gt;
'''Function Name : Compute_scores'''&lt;br /&gt;
&lt;br /&gt;
Compute_scores is a function in model answer.rb which gives the average, maximum and minimum scores obtained in a series a responses/assessments. It has two input parameters: List of assessments and questions. The function iterates over each assessment to get the total score of that assessment. If the response or review is invalid, that assessment won’t be considered in the calculation of the score average. After iterating over all assessments, Max score, and Min scores are calculated along with the average score based on the number of valid assessments. Their scores are returned by the function.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
'''Rspec Unit Test : Compute_scores'''&lt;br /&gt;
&lt;br /&gt;
Following scenarios are tested:&lt;br /&gt;
&lt;br /&gt;
* To return scores as nil if the input list of assessments is nil. This is to make sure no Null Pointer exceptions are thrown by the code&lt;br /&gt;
*To return a particular score when a single valid assessment is given as an input.&lt;br /&gt;
*To return a particular score when multiple valid assessments are given as an input. This is to test the looping functionality of the method.&lt;br /&gt;
*To return a particular score when invalid assessments are given as an input. The validity and total scores are returned by a mock and not by the actual functions. This is to make the test cases less rigid so that failure of dependent functions do not disrupt the functionality of interface level tests.&lt;br /&gt;
*To return a particular score when invalid flag is nil. Invalid flag can either be 0,1 or nil. Nil situation is tested to prevent NullPointer Exceptions&lt;br /&gt;
*To check if the method get_total_score is called with the right parameters.&lt;br /&gt;
&lt;br /&gt;
This unit test uses a stub and returns a mock value.&lt;br /&gt;
&amp;lt;pre&amp;gt;&lt;br /&gt;
Answer.stub(:get_total_score)&lt;br /&gt;
&amp;lt;/pre&amp;gt;&lt;br /&gt;
This is to eliminate tight coupling between compute_scores and get_total_scores. Failure in get_total_scores wouldn't break the compute_scores test cases.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
'''Function Name : Get_total_scores'''&lt;br /&gt;
&lt;br /&gt;
This function is called by the Compute_scores method of the answer.rb model to compute the total score of an assessment. The input consists of assessment for which the total score is being calculated and the list of questions being evaluated in the assessment. The method uses questionnaire id from the questions and response id to obtain a score view questionnaire data. This score view is a read-only record. The questionnaire data mainly consists of q1_max_question_score, sum_of_weights and weighted_score. Before calculating the score, the function performs two crucial tasks. &lt;br /&gt;
*Checks if the answer for a scored question is nil. If it is nil or unanswered, the question will be ignored and not counted towards the score of this response.&lt;br /&gt;
* Calls the submission_valid function by passing the response record to set the @invalid flag based on the validity of the response.&lt;br /&gt;
The total score is calculated using the below formula&lt;br /&gt;
&lt;br /&gt;
&amp;lt;pre&amp;gt;&lt;br /&gt;
(weighted_score / (sum_of_weights * max_question_score)) * 100&lt;br /&gt;
&amp;lt;/pre&amp;gt;&lt;br /&gt;
&lt;br /&gt;
Any edge cases would return -1 indicating no score&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
'''Rspec Unit Test : Get_total_scores'''&lt;br /&gt;
&lt;br /&gt;
Following scenarios are tested:&lt;br /&gt;
&lt;br /&gt;
*To return an anticipated total score of a single response without any edge cases. Since this function will be called only on one response at a time, there is no need to test for multiple responses at the same time.&lt;br /&gt;
*To return an anticipated total score of a response where nil answer is for a scored question. This is to check if its weight gets removed from the sum_of_weights.&lt;br /&gt;
*To return -1 when the sum of weights becomes 0. This can happen when all the scored questions are unanswered. Return value of -1 is checked at the calling function to ensure if a score is returned or not.&lt;br /&gt;
*To return -1 when weighted_score of questionnaireData is nil&lt;br /&gt;
* To check if submission_valid is called. This method is called to set invalid flag to indicate whether the response entered is valid or not. The validity criteria is explained in the submission_valid? Function.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
This unit test uses two stubs and returns mock results&lt;br /&gt;
&amp;lt;pre&amp;gt;&lt;br /&gt;
ScoreView.stub(:find_by_sql)&lt;br /&gt;
&amp;lt;/pre&amp;gt;&lt;br /&gt;
&amp;lt;pre&amp;gt;&lt;br /&gt;
Answer.stub(:where)&lt;br /&gt;
&amp;lt;/pre&amp;gt;&lt;br /&gt;
This is to reduce the outcome of the test to depend on DB calls. For example, in case the connection to DB fails, this unit test would still pass making it less rigid.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
'''Function Name : submission_valid?'''&lt;br /&gt;
&lt;br /&gt;
This purpose of this function is to verify the validity of a review based on a deadline.  This function obtains a list of AssignmentDueDate objects  in descending order which is then compared against the current time to determine which deadlines are valid and which ones are not. The flag variable is used to represent whether or not a deadline was available in the previous iteration of the loop. If the flag is set to TRUE and the deadline is less than the current date, then latest_review_phase_start_time is set to this deadline. A list of ResubmissionTime objects is also retrieved from the controller. These objects are then compared against the then latest_review_phase_start_time variable to determine a response. &lt;br /&gt;
&lt;br /&gt;
Observations: The current implementation of the function is bugged. It retrieves a list of sorted AssignmentDueDate objects and proceeds to check if this list is empty. However, instead of exiting if the function if the list is empty, it carries on execution and raises an exception on hitting the for loop. &lt;br /&gt;
&lt;br /&gt;
*Checks if a review is valid or not by comparing its date with a list of deadlines.&lt;br /&gt;
*Returns 1 or 0 depending on validity&lt;br /&gt;
*Current implementation is bugged. Throws an exception if no AssignmentDueDate objects are passed, returns nil if any objects are passed.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
'''Rspec Unit Test : submission_valid?'''&lt;br /&gt;
&lt;br /&gt;
Following scenarios are tested:&lt;br /&gt;
&lt;br /&gt;
*Passing valid AssignmentDueDate objects&lt;br /&gt;
*Not passing any AssignmentDueDate objects&lt;br /&gt;
&lt;br /&gt;
When valid AssignmentDueDate objects are passed, stubs are used to create fake AssignmentDueDate Objects and ResubmissionTime objects. These objects are then populated with valid deadline dates and deadline_type values. These values are then supplied when requested by the submission_valid? Function rather than actually calling the function.  The current implementation of this test case expects the program to throw an error when it reaches the for loop. Once this bug is fixed, this test case may be re-written to test a more legitimate test case.&lt;br /&gt;
&lt;br /&gt;
In case an empty list of AssignmentDueDate objects is passed back to the submission_valid?() method. This would cause the function to return nil. When this function is fixed, the following test case may be re-written to test for a more legitimate test-case.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
This unit test uses two stubs and returns mock results&lt;br /&gt;
&amp;lt;pre&amp;gt;&lt;br /&gt;
AssignmentDueDate.stub_chain(:where, :order)&lt;br /&gt;
&amp;lt;/pre&amp;gt;&lt;br /&gt;
The above stub returns two AssignmentDueDate objects whenever the where() and order() method are chained on AssignmentDueDate.&lt;br /&gt;
&amp;lt;pre&amp;gt;&lt;br /&gt;
ResubmissionTime.stub_chain(:where, :order)&lt;br /&gt;
&amp;lt;/pre&amp;gt;&lt;br /&gt;
The above stub returns two ResubmissionTime objects whenever the where() and order() method are chained on ResubmissionTime.&lt;br /&gt;
&amp;lt;pre&amp;gt;&lt;br /&gt;
AssignmentDueDate.stub_chain(:where, :order)&lt;br /&gt;
&amp;lt;/pre&amp;gt;&lt;br /&gt;
This stub is used in the second test case to return nil objects.&lt;br /&gt;
&lt;br /&gt;
the stub_chain method can be used to create stubs where chained methods are expected.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
'''Function Name : answers_by_question, answers_by_question_for_reviewee,answers_by_question_for_reviewee_in_round'''&lt;br /&gt;
&lt;br /&gt;
These three functions are sql queries that hit the DB to get a output record after a series of selections and joins. SQL queries that hit DB often do not have a high priority when it comes to testing, so the project does not aggressively test these functions. However, these functions are tested to make sure the queries are able to find the right column names and tables successfully. Any change in the table schema would be detected in these test cases. The functionality of these queries are not tested but instead existence of an output is tested. This ensures that answer.rb is able to make a successful db connection and is sync with the latest db schema. Since the function actually hits the DB, mocks can no longer be used, instead active records were created and saved in test db using FactoryGirl gem from the factories.rb. These records are cleared after every test case.&lt;br /&gt;
&lt;br /&gt;
Following factories were used to create records in the table&lt;br /&gt;
*question&lt;br /&gt;
*response_record&lt;br /&gt;
*response_map&lt;br /&gt;
*answer&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
'''Rspec Unit Test : answers_by_question, answers_by_question_for_reviewee,answers_by_question_for_reviewee_in_round'''&lt;br /&gt;
&lt;br /&gt;
The factories are created such a way that the query would return an output and the tests will pass if the query returns a non nil record. The functionality of these functions would be tested by the integration tests of the controller&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
'''Validation and Dependency  Rspec Test'''&lt;br /&gt;
&lt;br /&gt;
Apart from testing functions, the models are also tested for validations and external dependencies. Model answer.rb does not have any validations but does have a dependency on question.rb. Answer belongs_to question and this was tested using a simple dependency rspec test.&lt;br /&gt;
&amp;lt;pre&amp;gt;&lt;br /&gt;
it { should belong_to(:question) }&lt;br /&gt;
&amp;lt;/pre&amp;gt;&lt;br /&gt;
&lt;br /&gt;
===Rspec Test Results===&lt;br /&gt;
&lt;br /&gt;
&amp;lt;pre&amp;gt;&lt;br /&gt;
1 deprecation warning total&lt;br /&gt;
&lt;br /&gt;
Finished in 12.39 seconds (files took 11.25 seconds to load)&lt;br /&gt;
17 examples, 0 failures&lt;br /&gt;
&lt;br /&gt;
Randomized with seed 37447&lt;br /&gt;
&lt;br /&gt;
Coverage report generated for RSpec to /home/root/expertiza/coverage. 998 / 3919 LOC (25.47%) covered.&lt;br /&gt;
[Coveralls] Outside the CI environment, not sending data.&lt;br /&gt;
root@ubuntu:~/expertiza$ &lt;br /&gt;
&amp;lt;/pre&amp;gt;&lt;/div&gt;</summary>
		<author><name>Vdatla</name></author>
	</entry>
	<entry>
		<id>https://wiki.expertiza.ncsu.edu/index.php?title=CSC/ECE_517_Fall_2016&amp;diff=103394</id>
		<title>CSC/ECE 517 Fall 2016</title>
		<link rel="alternate" type="text/html" href="https://wiki.expertiza.ncsu.edu/index.php?title=CSC/ECE_517_Fall_2016&amp;diff=103394"/>
		<updated>2016-10-29T00:12:15Z</updated>

		<summary type="html">&lt;p&gt;Vdatla: /* Writing Assignments 2 */&lt;/p&gt;
&lt;hr /&gt;
&lt;div&gt;[http://www.example.com link title]==Calibration Assignment Submissions==&lt;br /&gt;
*[[Calibration Assignment Submission (Firebrick JS)]]&lt;br /&gt;
*[[Calibration Assignment Submission (Active Job)]]&lt;br /&gt;
==Writing Assignments 2==&lt;br /&gt;
*[[CSC/ECE 517 Fall 2016/E1666. Test team functionality]]&lt;br /&gt;
*[[CSC/ECE 517 Fall 2016/E1643. Refactor Suggestion controller]]&lt;br /&gt;
*[[CSC/ECE 517 Fall 2016/E1631. Refactoring Bidding Interface]]&lt;br /&gt;
*[[CSC/ECE 517 Fall 2016/E1674.Refactor leaderboard.rb and write unit tests]]&lt;br /&gt;
*[[CSC/ECE 517 Fall 2016/E1671. Unit Tests for participants.rb Hierarchy]]&lt;br /&gt;
*[[CSC/ECE 517 Fall 2016/E1668.Test e-mailing functionality]]&lt;br /&gt;
*[[CSC/ECE 517 Fall 2016/E1658. Refractor lottery_controller.rb and write integration tests]]&lt;br /&gt;
*[[CSC/ECE 517 Fall 2016/E1660. Review requirements and thresholds]]&lt;br /&gt;
*[[CSC/ECE 517 Fall 2016/E1650. Sort instructor views alphabetically by default]]&lt;br /&gt;
*[[CSC/ECE 517 Fall 2016/E1644. Refactor and test Teams Controller]]&lt;br /&gt;
*[[CSC/ECE 517 Fall 2016/E1659. Refactor on_the_fly_calc.rb]]&lt;br /&gt;
*[[CSC/ECE 517 Fall 2016/E1657. Introduce a Student View for instructors]]&lt;br /&gt;
*[[CSC/ECE 517 Fall 2016/E1653. Fix and improve rubric criteria]]&lt;br /&gt;
*[[CSC/ECE 517 Fall 2016/E1642. Refactor review_response_map.rb]]&lt;br /&gt;
*[[CSC/ECE_517_Fall_2016/E1664:_Feature_Test_Assignment_Creation]]&lt;br /&gt;
*[[CSC/ECE 517 Fall 2016/E1666. Test team functionality]]&lt;br /&gt;
*[[CSC/ECE_517_Fall_2016/E1654. Improve_date-picker_and_deadlines]]&lt;br /&gt;
*[[CSC/ECE_517_Fall_2016/E1652 Fix teammate advertisements and requests to join a team ]]&lt;br /&gt;
*[[CSC/ECE_517_Fall_2016/E1662. UI issues/fixes]]&lt;br /&gt;
*[[CSC/ECE_517_Fall_2016/E1673. Refactor question_type.rb]]&lt;br /&gt;
*[[CSC/ECE_517_Fall_2016/E1675. Timestamp for student file &amp;amp; hyperlink submissions]]&lt;br /&gt;
*[[CSC/ECE_517_Fall_2016/E1640. Refactor response.rb and response_helper.rb]]&lt;br /&gt;
*[[CSC/ECE 517 Fall 2016/E1634. Refactor and write unit test of due_date.rb and deadline_helper.rb]]&lt;br /&gt;
*[[CSC/ECE_517_Fall_2016/M1654._Improve_network_security_features]]&lt;br /&gt;
*[[CSC/ECE_517_Fall_2016/E1670._Unit_tests_for_answers.rb]]&lt;/div&gt;</summary>
		<author><name>Vdatla</name></author>
	</entry>
	<entry>
		<id>https://wiki.expertiza.ncsu.edu/index.php?title=E1670&amp;diff=103388</id>
		<title>E1670</title>
		<link rel="alternate" type="text/html" href="https://wiki.expertiza.ncsu.edu/index.php?title=E1670&amp;diff=103388"/>
		<updated>2016-10-29T00:08:27Z</updated>

		<summary type="html">&lt;p&gt;Vdatla: moved E1670 to CSC/ECE 517 Fall 2016/E1670. Unit tests for answers.rb&lt;/p&gt;
&lt;hr /&gt;
&lt;div&gt;#REDIRECT [[CSC/ECE 517 Fall 2016/E1670. Unit tests for answers.rb]]&lt;/div&gt;</summary>
		<author><name>Vdatla</name></author>
	</entry>
	<entry>
		<id>https://wiki.expertiza.ncsu.edu/index.php?title=CSC/ECE_517_Fall_2016/E1670._Unit_tests_for_answers.rb&amp;diff=103387</id>
		<title>CSC/ECE 517 Fall 2016/E1670. Unit tests for answers.rb</title>
		<link rel="alternate" type="text/html" href="https://wiki.expertiza.ncsu.edu/index.php?title=CSC/ECE_517_Fall_2016/E1670._Unit_tests_for_answers.rb&amp;diff=103387"/>
		<updated>2016-10-29T00:08:27Z</updated>

		<summary type="html">&lt;p&gt;Vdatla: moved E1670 to CSC/ECE 517 Fall 2016/E1670. Unit tests for answers.rb&lt;/p&gt;
&lt;hr /&gt;
&lt;div&gt;==E1670 . Unit tests for answers.rb==&lt;br /&gt;
&lt;br /&gt;
This wiki page is for the description of changes made under E1670 OSS assignment for Fall 2016, CSC/ECE 517.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
__TOC__&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
===Background===&lt;br /&gt;
&lt;br /&gt;
Expertiza is an Open Source web application developed on Ruby On Rails platform. It is a platform which allows students to take assignments posted by the course instructors. Expertiza allows students to select assignment topics, form teams and submit their work. It also allows them to review other students' submissions and improve their work based on this feedback.&lt;br /&gt;
&lt;br /&gt;
===Project Description===&lt;br /&gt;
&lt;br /&gt;
In Expertiza, each questionnaire contains many questions, those question may have different types (e.g. checkbox, criterion, etc). When a user fills in a rubric, the responses for each question will become an answer record. The responses of rubrics are stored in answers table in DB. The answer.rb is the model for the answers table in DB. Answer.rb model does not have any test cases and the aim of the project is to write fast, effective and flexible unit test cases that offer maximum code coverage.&lt;br /&gt;
&lt;br /&gt;
===Files Created/Modified===&lt;br /&gt;
*answer_spec.rb&lt;br /&gt;
*factories.rb&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
===RSpec===&lt;br /&gt;
====RSpec Introduction====&lt;br /&gt;
RSpec is a testing framework for Ruby for behavior-driven development (BDD) licensed under MIT. It is inspired by JBehave and contains fully integrated JMock based framework which has a very rich and powerful DSL (domain-specific language) which resembles a natural language specification.&lt;br /&gt;
Composed of multiple libraries structured to work together, RSpec provides encapsulated testing via the describe block to specify the behavior of the class and the context for the unit test case.&lt;br /&gt;
&lt;br /&gt;
==== Why RSpec? ====&lt;br /&gt;
RSpec is easy to learn and implement and can be used with other testing tools like Cucumber and Minitest independently. It is extremely powerful for testing states with complicated setup and also helps in tearing down complex code to access the objects required for testing&lt;br /&gt;
RSpec semantics encourage agile thinking and practice and it structures the tests in a more intuitive way.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
===Functions in answers.rb===&lt;br /&gt;
&lt;br /&gt;
'''Function Name : Compute_scores'''&lt;br /&gt;
&lt;br /&gt;
Compute_scores is a function in model answer.rb which gives the average, maximum and minimum scores obtained in a series a responses/assessments. It has two input parameters: List of assessments and questions. The function iterates over each assessment to get the total score of that assessment. If the response or review is invalid, that assessment won’t be considered in the calculation of the score average. After iterating over all assessments, Max score, and Min scores are calculated along with the average score based on the number of valid assessments. Their scores are returned by the function.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
'''Rspec Unit Test : Compute_scores'''&lt;br /&gt;
&lt;br /&gt;
Following scenarios are tested:&lt;br /&gt;
&lt;br /&gt;
* To return scores as nil if the input list of assessments is nil. This is to make sure no Null Pointer exceptions are thrown by the code&lt;br /&gt;
*To return a particular score when a single valid assessment is given as an input.&lt;br /&gt;
*To return a particular score when multiple valid assessments are given as an input. This is to test the looping functionality of the method.&lt;br /&gt;
*To return a particular score when invalid assessments are given as an input. The validity and total scores are returned by a mock and not by the actual functions. This is to make the test cases less rigid so that failure of dependent functions do not disrupt the functionality of interface level tests.&lt;br /&gt;
*To return a particular score when invalid flag is nil. Invalid flag can either be 0,1 or nil. Nil situation is tested to prevent NullPointer Exceptions&lt;br /&gt;
*To check if the method get_total_score is called with the right parameters.&lt;br /&gt;
&lt;br /&gt;
This unit test uses a stub and returns a mock value.&lt;br /&gt;
&amp;lt;pre&amp;gt;&lt;br /&gt;
Answer.stub(:get_total_score)&lt;br /&gt;
&amp;lt;/pre&amp;gt;&lt;br /&gt;
This is to eliminate tight coupling between compute_scores and get_total_scores. Failure in get_total_scores wouldn't break the compute_scores test cases.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
'''Function Name : Get_total_scores'''&lt;br /&gt;
&lt;br /&gt;
This function is called by the Compute_scores method of the answer.rb model to compute the total score of an assessment. The input consists of assessment for which the total score is being calculated and the list of questions being evaluated in the assessment. The method uses questionnaire id from the questions and response id to obtain a score view questionnaire data. This score view is a read-only record. The questionnaire data mainly consists of q1_max_question_score, sum_of_weights and weighted_score. Before calculating the score, the function performs two crucial tasks. &lt;br /&gt;
*Checks if the answer for a scored question is nil. If it is nil or unanswered, the question will be ignored and not counted towards the score of this response.&lt;br /&gt;
* Calls the submission_valid function by passing the response record to set the @invalid flag based on the validity of the response.&lt;br /&gt;
The total score is calculated using the below formula&lt;br /&gt;
&lt;br /&gt;
&amp;lt;pre&amp;gt;&lt;br /&gt;
(weighted_score / (sum_of_weights * max_question_score)) * 100&lt;br /&gt;
&amp;lt;/pre&amp;gt;&lt;br /&gt;
&lt;br /&gt;
Any edge cases would return -1 indicating no score&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
'''Rspec Unit Test : Get_total_scores'''&lt;br /&gt;
&lt;br /&gt;
Following scenarios are tested:&lt;br /&gt;
&lt;br /&gt;
*To return an anticipated total score of a single response without any edge cases. Since this function will be called only on one response at a time, there is no need to test for multiple responses at the same time.&lt;br /&gt;
*To return an anticipated total score of a response where nil answer is for a scored question. This is to check if its weight gets removed from the sum_of_weights.&lt;br /&gt;
*To return -1 when the sum of weights becomes 0. This can happen when all the scored questions are unanswered. Return value of -1 is checked at the calling function to ensure if a score is returned or not.&lt;br /&gt;
*To return -1 when weighted_score of questionnaireData is nil&lt;br /&gt;
* To check if submission_valid is called. This method is called to set invalid flag to indicate whether the response entered is valid or not. The validity criteria is explained in the submission_valid? Function.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
This unit test uses two stubs and returns mock results&lt;br /&gt;
&amp;lt;pre&amp;gt;&lt;br /&gt;
ScoreView.stub(:find_by_sql)&lt;br /&gt;
&amp;lt;/pre&amp;gt;&lt;br /&gt;
&amp;lt;pre&amp;gt;&lt;br /&gt;
Answer.stub(:where)&lt;br /&gt;
&amp;lt;/pre&amp;gt;&lt;br /&gt;
This is to reduce the outcome of the test to depend on DB calls. For example, in case the connection to DB fails, this unit test would still pass making it less rigid.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
'''Function Name : submission_valid?'''&lt;br /&gt;
&lt;br /&gt;
This purpose of this function is to verify the validity of a review based on a deadline.  This function obtains a list of AssignmentDueDate objects  in descending order which is then compared against the current time to determine which deadlines are valid and which ones are not. The flag variable is used to represent whether or not a deadline was available in the previous iteration of the loop. If the flag is set to TRUE and the deadline is less than the current date, then latest_review_phase_start_time is set to this deadline. A list of ResubmissionTime objects is also retrieved from the controller. These objects are then compared against the then latest_review_phase_start_time variable to determine a response. &lt;br /&gt;
&lt;br /&gt;
Observations: The current implementation of the function is bugged. It retrieves a list of sorted AssignmentDueDate objects and proceeds to check if this list is empty. However, instead of exiting if the function if the list is empty, it carries on execution and raises an exception on hitting the for loop. &lt;br /&gt;
&lt;br /&gt;
*Checks if a review is valid or not by comparing its date with a list of deadlines.&lt;br /&gt;
*Returns 1 or 0 depending on validity&lt;br /&gt;
*Current implementation is bugged. Throws an exception if no AssignmentDueDate objects are passed, returns nil if any objects are passed.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
'''Rspec Unit Test : submission_valid?'''&lt;br /&gt;
&lt;br /&gt;
Following scenarios are tested:&lt;br /&gt;
&lt;br /&gt;
*Passing valid AssignmentDueDate objects&lt;br /&gt;
*Not passing any AssignmentDueDate objects&lt;br /&gt;
&lt;br /&gt;
When valid AssignmentDueDate objects are passed, stubs are used to create fake AssignmentDueDate Objects and ResubmissionTime objects. These objects are then populated with valid deadline dates and deadline_type values. These values are then supplied when requested by the submission_valid? Function rather than actually calling the function.  The current implementation of this test case expects the program to throw an error when it reaches the for loop. Once this bug is fixed, this test case may be re-written to test a more legitimate test case.&lt;br /&gt;
&lt;br /&gt;
In case an empty list of AssignmentDueDate objects is passed back to the submission_valid?() method. This would cause the function to return nil. When this function is fixed, the following test case may be re-written to test for a more legitimate test-case.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
This unit test uses two stubs and returns mock results&lt;br /&gt;
&amp;lt;pre&amp;gt;&lt;br /&gt;
AssignmentDueDate.stub_chain(:where, :order)&lt;br /&gt;
&amp;lt;/pre&amp;gt;&lt;br /&gt;
The above stub returns two AssignmentDueDate objects whenever the where() and order() method are chained on AssignmentDueDate.&lt;br /&gt;
&amp;lt;pre&amp;gt;&lt;br /&gt;
ResubmissionTime.stub_chain(:where, :order)&lt;br /&gt;
&amp;lt;/pre&amp;gt;&lt;br /&gt;
The above stub returns two ResubmissionTime objects whenever the where() and order() method are chained on ResubmissionTime.&lt;br /&gt;
&amp;lt;pre&amp;gt;&lt;br /&gt;
AssignmentDueDate.stub_chain(:where, :order)&lt;br /&gt;
&amp;lt;/pre&amp;gt;&lt;br /&gt;
This stub is used in the second test case to return nil objects.&lt;br /&gt;
&lt;br /&gt;
the stub_chain method can be used to create stubs where chained methods are expected.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
'''Function Name : answers_by_question, answers_by_question_for_reviewee,answers_by_question_for_reviewee_in_round'''&lt;br /&gt;
&lt;br /&gt;
These three functions are sql queries that hit the DB to get a output record after a series of selections and joins. SQL queries that hit DB often do not have a high priority when it comes to testing, so the project does not aggressively test these functions. However, these functions are tested to make sure the queries are able to find the right column names and tables successfully. Any change in the table schema would be detected in these test cases. The functionality of these queries are not tested but instead existence of an output is tested. This ensures that answer.rb is able to make a successful db connection and is sync with the latest db schema. Since the function actually hits the DB, mocks can no longer be used, instead active records were created and saved in test db using FactoryGirl gem from the factories.rb. These records are cleared after every test case.&lt;br /&gt;
&lt;br /&gt;
Following factories were used to create records in the table&lt;br /&gt;
*question&lt;br /&gt;
*response_record&lt;br /&gt;
*response_map&lt;br /&gt;
*answer&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
'''Rspec Unit Test : answers_by_question, answers_by_question_for_reviewee,answers_by_question_for_reviewee_in_round'''&lt;br /&gt;
&lt;br /&gt;
The factories are created such a way that the query would return an output and the tests will pass if the query returns a non nil record. The functionality of these functions would be tested by the integration tests of the controller&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
'''Validation and Dependency  Rspec Test'''&lt;br /&gt;
&lt;br /&gt;
Apart from testing functions, the models are also tested for validations and external dependencies. Model answer.rb does not have any validations but does have a dependency on question.rb. Answer belongs_to question and this was tested using a simple dependency rspec test.&lt;br /&gt;
&amp;lt;pre&amp;gt;&lt;br /&gt;
it { should belong_to(:question) }&lt;br /&gt;
&amp;lt;/pre&amp;gt;&lt;/div&gt;</summary>
		<author><name>Vdatla</name></author>
	</entry>
	<entry>
		<id>https://wiki.expertiza.ncsu.edu/index.php?title=CSC/ECE_517_Fall_2016/E1670._Unit_tests_for_answers.rb&amp;diff=102711</id>
		<title>CSC/ECE 517 Fall 2016/E1670. Unit tests for answers.rb</title>
		<link rel="alternate" type="text/html" href="https://wiki.expertiza.ncsu.edu/index.php?title=CSC/ECE_517_Fall_2016/E1670._Unit_tests_for_answers.rb&amp;diff=102711"/>
		<updated>2016-10-28T06:32:36Z</updated>

		<summary type="html">&lt;p&gt;Vdatla: &lt;/p&gt;
&lt;hr /&gt;
&lt;div&gt;==E1670 . Unit tests for answers.rb==&lt;br /&gt;
&lt;br /&gt;
This wiki page is for the description of changes made under E1670 OSS assignment for Fall 2016, CSC/ECE 517.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
__TOC__&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
===Background===&lt;br /&gt;
&lt;br /&gt;
Expertiza is an Open Source web application developed on Ruby On Rails platform. It is a platform which allows students to take assignments posted by the course instructors. Expertiza allows students to select assignment topics, form teams and submit their work. It also allows them to review other students' submissions and improve their work based on this feedback.&lt;br /&gt;
&lt;br /&gt;
===Project Description===&lt;br /&gt;
&lt;br /&gt;
In Expertiza, each questionnaire contains many questions, those question may have different types (e.g. checkbox, criterion, etc). When a user fills in a rubric, the responses for each question will become an answer record. The responses of rubrics are stored in answers table in DB. The answer.rb is the model for the answers table in DB. Answer.rb model does not have any test cases and the aim of the project is to write fast, effective and flexible unit test cases that offer maximum code coverage.&lt;br /&gt;
&lt;br /&gt;
===Files Created/Modified===&lt;br /&gt;
*answer_spec.rb&lt;br /&gt;
*factories.rb&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
===RSpec===&lt;br /&gt;
====RSpec Introduction====&lt;br /&gt;
RSpec is a testing framework for Ruby for behavior-driven development (BDD) licensed under MIT. It is inspired by JBehave and contains fully integrated JMock based framework which has a very rich and powerful DSL (domain-specific language) which resembles a natural language specification.&lt;br /&gt;
Composed of multiple libraries structured to work together, RSpec provides encapsulated testing via the describe block to specify the behavior of the class and the context for the unit test case.&lt;br /&gt;
&lt;br /&gt;
==== Why RSpec? ====&lt;br /&gt;
RSpec is easy to learn and implement and can be used with other testing tools like Cucumber and Minitest independently. It is extremely powerful for testing states with complicated setup and also helps in tearing down complex code to access the objects required for testing&lt;br /&gt;
RSpec semantics encourage agile thinking and practice and it structures the tests in a more intuitive way.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
===Functions in answers.rb===&lt;br /&gt;
&lt;br /&gt;
'''Function Name : Compute_scores'''&lt;br /&gt;
&lt;br /&gt;
Compute_scores is a function in model answer.rb which gives the average, maximum and minimum scores obtained in a series a responses/assessments. It has two input parameters: List of assessments and questions. The function iterates over each assessment to get the total score of that assessment. If the response or review is invalid, that assessment won’t be considered in the calculation of the score average. After iterating over all assessments, Max score, and Min scores are calculated along with the average score based on the number of valid assessments. Their scores are returned by the function.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
'''Rspec Unit Test : Compute_scores'''&lt;br /&gt;
&lt;br /&gt;
Following scenarios are tested:&lt;br /&gt;
&lt;br /&gt;
* To return scores as nil if the input list of assessments is nil. This is to make sure no Null Pointer exceptions are thrown by the code&lt;br /&gt;
*To return a particular score when a single valid assessment is given as an input.&lt;br /&gt;
*To return a particular score when multiple valid assessments are given as an input. This is to test the looping functionality of the method.&lt;br /&gt;
*To return a particular score when invalid assessments are given as an input. The validity and total scores are returned by a mock and not by the actual functions. This is to make the test cases less rigid so that failure of dependent functions do not disrupt the functionality of interface level tests.&lt;br /&gt;
*To return a particular score when invalid flag is nil. Invalid flag can either be 0,1 or nil. Nil situation is tested to prevent NullPointer Exceptions&lt;br /&gt;
*To check if the method get_total_score is called with the right parameters.&lt;br /&gt;
&lt;br /&gt;
This unit test uses a stub and returns a mock value.&lt;br /&gt;
&amp;lt;pre&amp;gt;&lt;br /&gt;
Answer.stub(:get_total_score)&lt;br /&gt;
&amp;lt;/pre&amp;gt;&lt;br /&gt;
This is to eliminate tight coupling between compute_scores and get_total_scores. Failure in get_total_scores wouldn't break the compute_scores test cases.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
'''Function Name : Get_total_scores'''&lt;br /&gt;
&lt;br /&gt;
This function is called by the Compute_scores method of the answer.rb model to compute the total score of an assessment. The input consists of assessment for which the total score is being calculated and the list of questions being evaluated in the assessment. The method uses questionnaire id from the questions and response id to obtain a score view questionnaire data. This score view is a read-only record. The questionnaire data mainly consists of q1_max_question_score, sum_of_weights and weighted_score. Before calculating the score, the function performs two crucial tasks. &lt;br /&gt;
*Checks if the answer for a scored question is nil. If it is nil or unanswered, the question will be ignored and not counted towards the score of this response.&lt;br /&gt;
* Calls the submission_valid function by passing the response record to set the @invalid flag based on the validity of the response.&lt;br /&gt;
The total score is calculated using the below formula&lt;br /&gt;
&lt;br /&gt;
&amp;lt;pre&amp;gt;&lt;br /&gt;
(weighted_score / (sum_of_weights * max_question_score)) * 100&lt;br /&gt;
&amp;lt;/pre&amp;gt;&lt;br /&gt;
&lt;br /&gt;
Any edge cases would return -1 indicating no score&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
'''Rspec Unit Test : Get_total_scores'''&lt;br /&gt;
&lt;br /&gt;
Following scenarios are tested:&lt;br /&gt;
&lt;br /&gt;
*To return an anticipated total score of a single response without any edge cases. Since this function will be called only on one response at a time, there is no need to test for multiple responses at the same time.&lt;br /&gt;
*To return an anticipated total score of a response where nil answer is for a scored question. This is to check if its weight gets removed from the sum_of_weights.&lt;br /&gt;
*To return -1 when the sum of weights becomes 0. This can happen when all the scored questions are unanswered. Return value of -1 is checked at the calling function to ensure if a score is returned or not.&lt;br /&gt;
*To return -1 when weighted_score of questionnaireData is nil&lt;br /&gt;
* To check if submission_valid is called. This method is called to set invalid flag to indicate whether the response entered is valid or not. The validity criteria is explained in the submission_valid? Function.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
This unit test uses two stubs and returns mock results&lt;br /&gt;
&amp;lt;pre&amp;gt;&lt;br /&gt;
ScoreView.stub(:find_by_sql)&lt;br /&gt;
&amp;lt;/pre&amp;gt;&lt;br /&gt;
&amp;lt;pre&amp;gt;&lt;br /&gt;
Answer.stub(:where)&lt;br /&gt;
&amp;lt;/pre&amp;gt;&lt;br /&gt;
This is to reduce the outcome of the test to depend on DB calls. For example, in case the connection to DB fails, this unit test would still pass making it less rigid.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
'''Function Name : submission_valid?'''&lt;br /&gt;
&lt;br /&gt;
This purpose of this function is to verify the validity of a review based on a deadline.  This function obtains a list of AssignmentDueDate objects  in descending order which is then compared against the current time to determine which deadlines are valid and which ones are not. The flag variable is used to represent whether or not a deadline was available in the previous iteration of the loop. If the flag is set to TRUE and the deadline is less than the current date, then latest_review_phase_start_time is set to this deadline. A list of ResubmissionTime objects is also retrieved from the controller. These objects are then compared against the then latest_review_phase_start_time variable to determine a response. &lt;br /&gt;
&lt;br /&gt;
Observations: The current implementation of the function is bugged. It retrieves a list of sorted AssignmentDueDate objects and proceeds to check if this list is empty. However, instead of exiting if the function if the list is empty, it carries on execution and raises an exception on hitting the for loop. &lt;br /&gt;
&lt;br /&gt;
*Checks if a review is valid or not by comparing its date with a list of deadlines.&lt;br /&gt;
*Returns 1 or 0 depending on validity&lt;br /&gt;
*Current implementation is bugged. Throws an exception if no AssignmentDueDate objects are passed, returns nil if any objects are passed.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
'''Rspec Unit Test : submission_valid?'''&lt;br /&gt;
&lt;br /&gt;
Following scenarios are tested:&lt;br /&gt;
&lt;br /&gt;
*Passing valid AssignmentDueDate objects&lt;br /&gt;
*Not passing any AssignmentDueDate objects&lt;br /&gt;
&lt;br /&gt;
When valid AssignmentDueDate objects are passed, stubs are used to create fake AssignmentDueDate Objects and ResubmissionTime objects. These objects are then populated with valid deadline dates and deadline_type values. These values are then supplied when requested by the submission_valid? Function rather than actually calling the function.  The current implementation of this test case expects the program to throw an error when it reaches the for loop. Once this bug is fixed, this test case may be re-written to test a more legitimate test case.&lt;br /&gt;
&lt;br /&gt;
In case an empty list of AssignmentDueDate objects is passed back to the submission_valid?() method. This would cause the function to return nil. When this function is fixed, the following test case may be re-written to test for a more legitimate test-case.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
This unit test uses two stubs and returns mock results&lt;br /&gt;
&amp;lt;pre&amp;gt;&lt;br /&gt;
AssignmentDueDate.stub_chain(:where, :order)&lt;br /&gt;
&amp;lt;/pre&amp;gt;&lt;br /&gt;
The above stub returns two AssignmentDueDate objects whenever the where() and order() method are chained on AssignmentDueDate.&lt;br /&gt;
&amp;lt;pre&amp;gt;&lt;br /&gt;
ResubmissionTime.stub_chain(:where, :order)&lt;br /&gt;
&amp;lt;/pre&amp;gt;&lt;br /&gt;
The above stub returns two ResubmissionTime objects whenever the where() and order() method are chained on ResubmissionTime.&lt;br /&gt;
&amp;lt;pre&amp;gt;&lt;br /&gt;
AssignmentDueDate.stub_chain(:where, :order)&lt;br /&gt;
&amp;lt;/pre&amp;gt;&lt;br /&gt;
This stub is used in the second test case to return nil objects.&lt;br /&gt;
&lt;br /&gt;
the stub_chain method can be used to create stubs where chained methods are expected.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
'''Function Name : answers_by_question, answers_by_question_for_reviewee,answers_by_question_for_reviewee_in_round'''&lt;br /&gt;
&lt;br /&gt;
These three functions are sql queries that hit the DB to get a output record after a series of selections and joins. SQL queries that hit DB often do not have a high priority when it comes to testing, so the project does not aggressively test these functions. However, these functions are tested to make sure the queries are able to find the right column names and tables successfully. Any change in the table schema would be detected in these test cases. The functionality of these queries are not tested but instead existence of an output is tested. This ensures that answer.rb is able to make a successful db connection and is sync with the latest db schema. Since the function actually hits the DB, mocks can no longer be used, instead active records were created and saved in test db using FactoryGirl gem from the factories.rb. These records are cleared after every test case.&lt;br /&gt;
&lt;br /&gt;
Following factories were used to create records in the table&lt;br /&gt;
*question&lt;br /&gt;
*response_record&lt;br /&gt;
*response_map&lt;br /&gt;
*answer&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
'''Rspec Unit Test : answers_by_question, answers_by_question_for_reviewee,answers_by_question_for_reviewee_in_round'''&lt;br /&gt;
&lt;br /&gt;
The factories are created such a way that the query would return an output and the tests will pass if the query returns a non nil record. The functionality of these functions would be tested by the integration tests of the controller&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
'''Validation and Dependency  Rspec Test'''&lt;br /&gt;
&lt;br /&gt;
Apart from testing functions, the models are also tested for validations and external dependencies. Model answer.rb does not have any validations but does have a dependency on question.rb. Answer belongs_to question and this was tested using a simple dependency rspec test.&lt;br /&gt;
&amp;lt;pre&amp;gt;&lt;br /&gt;
it { should belong_to(:question) }&lt;br /&gt;
&amp;lt;/pre&amp;gt;&lt;/div&gt;</summary>
		<author><name>Vdatla</name></author>
	</entry>
	<entry>
		<id>https://wiki.expertiza.ncsu.edu/index.php?title=CSC/ECE_517_Fall_2016/E1670._Unit_tests_for_answers.rb&amp;diff=102710</id>
		<title>CSC/ECE 517 Fall 2016/E1670. Unit tests for answers.rb</title>
		<link rel="alternate" type="text/html" href="https://wiki.expertiza.ncsu.edu/index.php?title=CSC/ECE_517_Fall_2016/E1670._Unit_tests_for_answers.rb&amp;diff=102710"/>
		<updated>2016-10-28T06:17:36Z</updated>

		<summary type="html">&lt;p&gt;Vdatla: &lt;/p&gt;
&lt;hr /&gt;
&lt;div&gt;==E1670 . Unit tests for answers.rb==&lt;br /&gt;
&lt;br /&gt;
This wiki page is for the description of changes made under E1670 OSS assignment for Fall 2016, CSC/ECE 517.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
__TOC__&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
===Background===&lt;br /&gt;
&lt;br /&gt;
Expertiza is an Open Source web application developed on Ruby On Rails platform. It is a platform which allows students to take assignments posted by the course instructors. Expertiza allows students to select assignment topics, form teams and submit their work. It also allows them to review other students' submissions and improve their work based on this feedback.&lt;br /&gt;
&lt;br /&gt;
===Project Description===&lt;br /&gt;
&lt;br /&gt;
In Expertiza, each questionnaire contains many questions, those question may have different types (e.g. checkbox, criterion, etc). When a user fills in a rubric, the responses for each question will become an answer record. The responses of rubrics are stored in answers table in DB. The answer.rb is the model for the answers table in DB. Answer.rb model does not have any test cases and the aim of the project is to write fast, effective and flexible unit test cases that offer maximum code coverage.&lt;br /&gt;
&lt;br /&gt;
===Files Created/Modified===&lt;br /&gt;
*answer_spec.rb&lt;br /&gt;
*factories.rb&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
===RSpec===&lt;br /&gt;
====RSpec Introduction====&lt;br /&gt;
RSpec is a testing framework for Ruby for behavior-driven development (BDD) licensed under MIT. It is inspired by JBehave and contains fully integrated JMock based framework which has a very rich and powerful DSL (domain-specific language) which resembles a natural language specification.&lt;br /&gt;
Composed of multiple libraries structured to work together, RSpec provides encapsulated testing via the describe block to specify the behavior of the class and the context for the unit test case.&lt;br /&gt;
&lt;br /&gt;
==== Why RSpec? ====&lt;br /&gt;
RSpec is easy to learn and implement and can be used with other testing tools like Cucumber and Minitest independently. It is extremely powerful for testing states with complicated setup and also helps in tearing down complex code to access the objects required for testing&lt;br /&gt;
RSpec semantics encourage agile thinking and practice and it structures the tests in a more intuitive way.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
===Functions in answers.rb===&lt;br /&gt;
&lt;br /&gt;
'''Function Name : Compute_scores'''&lt;br /&gt;
&lt;br /&gt;
Compute_scores is a function in model answer.rb which gives the average, maximum and minimum scores obtained in a series a responses/assessments. It has two input parameters: List of assessments and questions. The function iterates over each assessment to get the total score of that assessment. If the response or review is invalid, that assessment won’t be considered in the calculation of the score average. After iterating over all assessments, Max score, and Min scores are calculated along with the average score based on the number of valid assessments. Their scores are returned by the function.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
'''Rspec Unit Test : Compute_scores'''&lt;br /&gt;
&lt;br /&gt;
Following scenarios are tested:&lt;br /&gt;
&lt;br /&gt;
* To return scores as nil if the input list of assessments is nil. This is to make sure no Null Pointer exceptions are thrown by the code&lt;br /&gt;
*To return a particular score when a single valid assessment is given as an input.&lt;br /&gt;
*To return a particular score when multiple valid assessments are given as an input. This is to test the looping functionality of the method.&lt;br /&gt;
*To return a particular score when invalid assessments are given as an input. The validity and total scores are returned by a mock and not by the actual functions. This is to make the test cases less rigid so that failure of dependent functions do not disrupt the functionality of interface level tests.&lt;br /&gt;
*To return a particular score when invalid flag is nil. Invalid flag can either be 0,1 or nil. Nil situation is tested to prevent NullPointer Exceptions&lt;br /&gt;
*To check if the method get_total_score is called with the right parameters.&lt;br /&gt;
&lt;br /&gt;
This unit test uses a stub and returns a mock value.&lt;br /&gt;
&amp;lt;pre&amp;gt;&lt;br /&gt;
Answer.stub(:get_total_score)&lt;br /&gt;
&amp;lt;/pre&amp;gt;&lt;br /&gt;
This is to eliminate tight coupling between compute_scores and get_total_scores. Failure in get_total_scores wouldn't break the compute_scores test cases.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
'''Function Name : Get_total_scores'''&lt;br /&gt;
&lt;br /&gt;
This function is called by the Compute_scores method of the answer.rb model to compute the total score of an assessment. The input consists of assessment for which the total score is being calculated and the list of questions being evaluated in the assessment. The method uses questionnaire id from the questions and response id to obtain a score view questionnaire data. This score view is a read-only record. The questionnaire data mainly consists of q1_max_question_score, sum_of_weights and weighted_score. Before calculating the score, the function performs two crucial tasks. &lt;br /&gt;
*Checks if the answer for a scored question is nil. If it is nil or unanswered, the question will be ignored and not counted towards the score of this response.&lt;br /&gt;
* Calls the submission_valid function by passing the response record to set the @invalid flag based on the validity of the response.&lt;br /&gt;
The total score is calculated using the below formula&lt;br /&gt;
&lt;br /&gt;
&amp;lt;pre&amp;gt;&lt;br /&gt;
(weighted_score / (sum_of_weights * max_question_score)) * 100&lt;br /&gt;
&amp;lt;/pre&amp;gt;&lt;br /&gt;
&lt;br /&gt;
Any edge cases would return -1 indicating no score&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
'''Rspec Unit Test : Get_total_scores'''&lt;br /&gt;
&lt;br /&gt;
Following scenarios are tested:&lt;br /&gt;
&lt;br /&gt;
*To return an anticipated total score of a single response without any edge cases. Since this function will be called only on one response at a time, there is no need to test for multiple responses at the same time.&lt;br /&gt;
*To return an anticipated total score of a response where nil answer is for a scored question. This is to check if its weight gets removed from the sum_of_weights.&lt;br /&gt;
*To return -1 when the sum of weights becomes 0. This can happen when all the scored questions are unanswered. Return value of -1 is checked at the calling function to ensure if a score is returned or not.&lt;br /&gt;
*To return -1 when weighted_score of questionnaireData is nil&lt;br /&gt;
* To check if submission_valid is called. This method is called to set invalid flag to indicate whether the response entered is valid or not. The validity criteria is explained in the submission_valid? Function.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
This unit test uses two stubs and returns mock results&lt;br /&gt;
&amp;lt;pre&amp;gt;&lt;br /&gt;
ScoreView.stub(:find_by_sql)&lt;br /&gt;
&amp;lt;/pre&amp;gt;&lt;br /&gt;
&amp;lt;pre&amp;gt;&lt;br /&gt;
Answer.stub(:where)&lt;br /&gt;
&amp;lt;/pre&amp;gt;&lt;br /&gt;
This is to reduce the outcome of the test to depend on DB calls. For example, in case the connection to DB fails, this unit test would still pass making it less rigid.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
'''Function Name : submission_valid?'''&lt;br /&gt;
&lt;br /&gt;
This purpose of this function is to verify the validity of a review based on a deadline.  This function obtains a list of AssignmentDueDate objects  in descending order which is then compared against the current time to determine which deadlines are valid and which ones are not. The flag variable is used to represent whether or not a deadline was available in the previous iteration of the loop. If the flag is set to TRUE and the deadline is less than the current date, then latest_review_phase_start_time is set to this deadline. A list of ResubmissionTime objects is also retrieved from the controller. These objects are then compared against the then latest_review_phase_start_time variable to determine a response. &lt;br /&gt;
&lt;br /&gt;
Observations: The current implementation of the function is bugged. It retrieves a list of sorted AssignmentDueDate objects and proceeds to check if this list is empty. However, instead of exiting if the function if the list is empty, it carries on execution and raises an exception on hitting the for loop. &lt;br /&gt;
&lt;br /&gt;
*Checks if a review is valid or not by comparing its date with a list of deadlines.&lt;br /&gt;
*Returns 1 or 0 depending on validity&lt;br /&gt;
*Current implementation is bugged. Throws an exception if no AssignmentDueDate objects are passed, returns nil if any objects are passed.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
'''Rspec Unit Test : submission_valid?'''&lt;br /&gt;
&lt;br /&gt;
Following scenarios are tested:&lt;br /&gt;
&lt;br /&gt;
*Passing valid AssignmentDueDate objects&lt;br /&gt;
*Not passing any AssignmentDueDate objects&lt;br /&gt;
&lt;br /&gt;
When valid AssignmentDueDate objects are passed, stubs are used to create fake AssignmentDueDate Objects and ResubmissionTime objects. These objects are then populated with valid deadline dates and deadline_type values. These values are then supplied when requested by the submission_valid? Function rather than actually calling the function.  The current implementation of this test case expects the program to throw an error when it reaches the for loop. Once this bug is fixed, this test case may be re-written to test a more legitimate test case.&lt;br /&gt;
&lt;br /&gt;
In case an empty list of AssignmentDueDate objects is passed back to the submission_valid?() method. This would cause the function to return nil. When this function is fixed, the following test case may be re-written to test for a more legitimate test-case.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
This unit test uses two stubs and returns mock results&lt;br /&gt;
&amp;lt;pre&amp;gt;&lt;br /&gt;
AssignmentDueDate.stub_chain(:where, :order)&lt;br /&gt;
&amp;lt;/pre&amp;gt;&lt;br /&gt;
The above stub returns two AssignmentDueDate objects whenever the where() and order() method are chained on AssignmentDueDate.&lt;br /&gt;
&amp;lt;pre&amp;gt;&lt;br /&gt;
ResubmissionTime.stub_chain(:where, :order)&lt;br /&gt;
&amp;lt;/pre&amp;gt;&lt;br /&gt;
The above stub returns two ResubmissionTime objects whenever the where() and order() method are chained on ResubmissionTime.&lt;br /&gt;
&amp;lt;pre&amp;gt;&lt;br /&gt;
AssignmentDueDate.stub_chain(:where, :order)&lt;br /&gt;
&amp;lt;/pre&amp;gt;&lt;br /&gt;
This stub is used in the second test case to return nil objects.&lt;br /&gt;
&lt;br /&gt;
the stub_chain method can be used to create stubs where chained methods are expected.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
'''Function Name : answers_by_question, answers_by_question_for_reviewee,answers_by_question_for_reviewee_in_round'''&lt;br /&gt;
&lt;br /&gt;
These three functions are sql queries that hit the DB to get a output record after a series of selections and joins. SQL queries that hit DB often do not have a high priority when it comes to testing, so the project does not aggressively test these functions. However, these functions are tested to make sure the queries are able to find the right column names and tables successfully. Any change in the table schema would be detected in these test cases. The functionality of these queries are not tested but instead existence of an output is tested. This ensures that answer.rb is able to make a successful db connection and is sync with the latest db schema. Since the function actually hits the DB, mocks can no longer be used, instead active records were created and saved in test db using FactoryGirl gem from the factories.rb. These records are cleared after every test case.&lt;br /&gt;
&lt;br /&gt;
Following factories were used to create records in the table&lt;br /&gt;
*question&lt;br /&gt;
*response_record&lt;br /&gt;
*response_map&lt;br /&gt;
*answer&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
'''Rspec Unit Test : answers_by_question, answers_by_question_for_reviewee,answers_by_question_for_reviewee_in_round'''&lt;br /&gt;
&lt;br /&gt;
The factories are created such a way that the query would return an output and the tests will pass if the query returns a non nil record. The functionality of these functions would be tested by the integration tests of the controller&lt;/div&gt;</summary>
		<author><name>Vdatla</name></author>
	</entry>
	<entry>
		<id>https://wiki.expertiza.ncsu.edu/index.php?title=CSC/ECE_517_Fall_2016/E1670._Unit_tests_for_answers.rb&amp;diff=102709</id>
		<title>CSC/ECE 517 Fall 2016/E1670. Unit tests for answers.rb</title>
		<link rel="alternate" type="text/html" href="https://wiki.expertiza.ncsu.edu/index.php?title=CSC/ECE_517_Fall_2016/E1670._Unit_tests_for_answers.rb&amp;diff=102709"/>
		<updated>2016-10-28T06:16:40Z</updated>

		<summary type="html">&lt;p&gt;Vdatla: &lt;/p&gt;
&lt;hr /&gt;
&lt;div&gt;==E1670 . Unit tests for answers.rb==&lt;br /&gt;
&lt;br /&gt;
This wiki page is for the description of changes made under E1670 OSS assignment for Fall 2016, CSC/ECE 517.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
__TOC__&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
===Background===&lt;br /&gt;
&lt;br /&gt;
Expertiza is an Open Source web application developed on Ruby On Rails platform. It is a platform which allows students to take assignments posted by the course instructors. Expertiza allows students to select assignment topics, form teams and submit their work. It also allows them to review other students' submissions and improve their work based on this feedback.&lt;br /&gt;
&lt;br /&gt;
===Project Description===&lt;br /&gt;
&lt;br /&gt;
In Expertiza, each questionnaire contains many questions, those question may have different types (e.g. checkbox, criterion, etc). When a user fills in a rubric, the responses for each question will become an answer record. The responses of rubrics are stored in answers table in DB. The answer.rb is the model for the answers table in DB. Answer.rb model does not have any test cases and the aim of the project is to write fast, effective and flexible unit test cases that offer maximum code coverage.&lt;br /&gt;
&lt;br /&gt;
===Files Created/Modified===&lt;br /&gt;
*answer_spec.rb&lt;br /&gt;
*factories.rb&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
===RSpec===&lt;br /&gt;
====RSpec Introduction====&lt;br /&gt;
RSpec is a testing framework for Ruby for behavior-driven development (BDD) licensed under MIT. It is inspired by JBehave and contains fully integrated JMock based framework which has a very rich and powerful DSL (domain-specific language) which resembles a natural language specification.&lt;br /&gt;
Composed of multiple libraries structured to work together, RSpec provides encapsulated testing via the describe block to specify the behavior of the class and the context for the unit test case.&lt;br /&gt;
&lt;br /&gt;
==== Why RSpec? ====&lt;br /&gt;
RSpec is easy to learn and implement and can be used with other testing tools like Cucumber and Minitest independently. It is extremely powerful for testing states with complicated setup and also helps in tearing down complex code to access the objects required for testing&lt;br /&gt;
RSpec semantics encourage agile thinking and practice and it structures the tests in a more intuitive way.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
===Functions in answers.rb===&lt;br /&gt;
&lt;br /&gt;
'''Function Name : Compute_scores'''&lt;br /&gt;
&lt;br /&gt;
Compute_scores is a function in model answer.rb which gives the average, maximum and minimum scores obtained in a series a responses/assessments. It has two input parameters: List of assessments and questions. The function iterates over each assessment to get the total score of that assessment. If the response or review is invalid, that assessment won’t be considered in the calculation of the score average. After iterating over all assessments, Max score, and Min scores are calculated along with the average score based on the number of valid assessments. Their scores are returned by the function.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
'''Rspec Unit Test : Compute_scores'''&lt;br /&gt;
&lt;br /&gt;
Following scenarios are tested:&lt;br /&gt;
&lt;br /&gt;
* To return scores as nil if the input list of assessments is nil. This is to make sure no Null Pointer exceptions are thrown by the code&lt;br /&gt;
*To return a particular score when a single valid assessment is given as an input.&lt;br /&gt;
*To return a particular score when multiple valid assessments are given as an input. This is to test the looping functionality of the method.&lt;br /&gt;
*To return a particular score when invalid assessments are given as an input. The validity and total scores are returned by a mock and not by the actual functions. This is to make the test cases less rigid so that failure of dependent functions do not disrupt the functionality of interface level tests.&lt;br /&gt;
*To return a particular score when invalid flag is nil. Invalid flag can either be 0,1 or nil. Nil situation is tested to prevent NullPointer Exceptions&lt;br /&gt;
*To check if the method get_total_score is called with the right parameters.&lt;br /&gt;
&lt;br /&gt;
This unit test uses a stub and returns a mock value.&lt;br /&gt;
&amp;lt;pre&amp;gt;&lt;br /&gt;
Answer.stub(:get_total_score)&lt;br /&gt;
&amp;lt;/pre&amp;gt;&lt;br /&gt;
This is to eliminate tight coupling between compute_scores and get_total_scores. Failure in get_total_scores wouldn't break the compute_scores test cases.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
'''Function Name : Get_total_scores'''&lt;br /&gt;
&lt;br /&gt;
This function is called by the Compute_scores method of the answer.rb model to compute the total score of an assessment. The input consists of assessment for which the total score is being calculated and the list of questions being evaluated in the assessment. The method uses questionnaire id from the questions and response id to obtain a score view questionnaire data. This score view is a read-only record. The questionnaire data mainly consists of q1_max_question_score, sum_of_weights and weighted_score. Before calculating the score, the function performs two crucial tasks. &lt;br /&gt;
*Checks if the answer for a scored question is nil. If it is nil or unanswered, the question will be ignored and not counted towards the score of this response.&lt;br /&gt;
* Calls the submission_valid function by passing the response record to set the @invalid flag based on the validity of the response.&lt;br /&gt;
The total score is calculated using the below formula&lt;br /&gt;
&lt;br /&gt;
&amp;lt;pre&amp;gt;&lt;br /&gt;
(weighted_score / (sum_of_weights * max_question_score)) * 100&lt;br /&gt;
&amp;lt;/pre&amp;gt;&lt;br /&gt;
&lt;br /&gt;
Any edge cases would return -1 indicating no score&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
'''Rspec Unit Test : Get_total_scores'''&lt;br /&gt;
&lt;br /&gt;
Following scenarios are tested:&lt;br /&gt;
&lt;br /&gt;
*To return an anticipated total score of a single response without any edge cases. Since this function will be called only on one response at a time, there is no need to test for multiple responses at the same time.&lt;br /&gt;
*To return an anticipated total score of a response where nil answer is for a scored question. This is to check if its weight gets removed from the sum_of_weights.&lt;br /&gt;
*To return -1 when the sum of weights becomes 0. This can happen when all the scored questions are unanswered. Return value of -1 is checked at the calling function to ensure if a score is returned or not.&lt;br /&gt;
*To return -1 when weighted_score of questionnaireData is nil&lt;br /&gt;
* To check if submission_valid is called. This method is called to set invalid flag to indicate whether the response entered is valid or not. The validity criteria is explained in the submission_valid? Function.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
This unit test uses two stubs and returns mock results&lt;br /&gt;
&amp;lt;pre&amp;gt;&lt;br /&gt;
ScoreView.stub(:find_by_sql)&lt;br /&gt;
&amp;lt;/pre&amp;gt;&lt;br /&gt;
&amp;lt;pre&amp;gt;&lt;br /&gt;
Answer.stub(:where)&lt;br /&gt;
&amp;lt;/pre&amp;gt;&lt;br /&gt;
This is to reduce the outcome of the test to depend on DB calls. For example, in case the connection to DB fails, this unit test would still pass making it less rigid.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
'''Function Name : submission_valid?'''&lt;br /&gt;
&lt;br /&gt;
This purpose of this function is to verify the validity of a review based on a deadline.  This function obtains a list of AssignmentDueDate objects  in descending order which is then compared against the current time to determine which deadlines are valid and which ones are not. The flag variable is used to represent whether or not a deadline was available in the previous iteration of the loop. If the flag is set to TRUE and the deadline is less than the current date, then latest_review_phase_start_time is set to this deadline. A list of ResubmissionTime objects is also retrieved from the controller. These objects are then compared against the then latest_review_phase_start_time variable to determine a response. &lt;br /&gt;
&lt;br /&gt;
Observations: The current implementation of the function is bugged. It retrieves a list of sorted AssignmentDueDate objects and proceeds to check if this list is empty. However, instead of exiting if the function if the list is empty, it carries on execution and raises an exception on hitting the for loop. &lt;br /&gt;
&lt;br /&gt;
*Checks if a review is valid or not by comparing its date with a list of deadlines.&lt;br /&gt;
*Returns 1 or 0 depending on validity&lt;br /&gt;
*Current implementation is bugged. Throws an exception if no AssignmentDueDate objects are passed, returns nil if any objects are passed.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
'''Rspec Unit Test : submission_valid?'''&lt;br /&gt;
&lt;br /&gt;
Following scenarios are tested:&lt;br /&gt;
&lt;br /&gt;
*Passing valid AssignmentDueDate objects&lt;br /&gt;
*Not passing any AssignmentDueDate objects&lt;br /&gt;
&lt;br /&gt;
When valid AssignmentDueDate objects are passed, stubs are used to create fake AssignmentDueDate Objects and ResubmissionTime objects. These objects are then populated with valid deadline dates and deadline_type values. These values are then supplied when requested by the submission_valid? Function rather than actually calling the function.  The current implementation of this test case expects the program to throw an error when it reaches the for loop. Once this bug is fixed, this test case may be re-written to test a more legitimate test case.&lt;br /&gt;
&lt;br /&gt;
In case an empty list of AssignmentDueDate objects is passed back to the submission_valid?() method. This would cause the function to return nil. When this function is fixed, the following test case may be re-written to test for a more legitimate test-case.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
This unit test uses two stubs and returns mock results&lt;br /&gt;
&amp;lt;pre&amp;gt;&lt;br /&gt;
AssignmentDueDate.stub_chain(:where, :order).and_return(due_date1, due_date2)&lt;br /&gt;
&amp;lt;/pre&amp;gt;&lt;br /&gt;
The above stub returns two AssignmentDueDate objects whenever the where() and order() method are chained on AssignmentDueDate.&lt;br /&gt;
&amp;lt;pre&amp;gt;&lt;br /&gt;
ResubmissionTime.stub_chain(:where, :order).and_return(ResubmissionTime1, ResubmissionTime2)&lt;br /&gt;
&amp;lt;/pre&amp;gt;&lt;br /&gt;
The above stub returns two ResubmissionTime objects whenever the where() and order() method are chained on ResubmissionTime.&lt;br /&gt;
&amp;lt;pre&amp;gt;&lt;br /&gt;
AssignmentDueDate.stub_chain(:where, :order).and_return(nil)&lt;br /&gt;
&amp;lt;/pre&amp;gt;&lt;br /&gt;
This stub is used in the second test case to return nil objects.&lt;br /&gt;
&lt;br /&gt;
the stub_chain method can be used to create stubs where chained methods are expected.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
'''Function Name : answers_by_question, answers_by_question_for_reviewee,answers_by_question_for_reviewee_in_round'''&lt;br /&gt;
&lt;br /&gt;
These three functions are sql queries that hit the DB to get a output record after a series of selections and joins. SQL queries that hit DB often do not have a high priority when it comes to testing, so the project does not aggressively test these functions. However, these functions are tested to make sure the queries are able to find the right column names and tables successfully. Any change in the table schema would be detected in these test cases. The functionality of these queries are not tested but instead existence of an output is tested. This ensures that answer.rb is able to make a successful db connection and is sync with the latest db schema. Since the function actually hits the DB, mocks can no longer be used, instead active records were created and saved in test db using FactoryGirl gem from the factories.rb. These records are cleared after every test case.&lt;br /&gt;
&lt;br /&gt;
Following factories were used to create records in the table&lt;br /&gt;
*question&lt;br /&gt;
*response_record&lt;br /&gt;
*response_map&lt;br /&gt;
*answer&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
'''Rspec Unit Test : answers_by_question, answers_by_question_for_reviewee,answers_by_question_for_reviewee_in_round'''&lt;br /&gt;
&lt;br /&gt;
The factories are created such a way that the query would return an output and the tests will pass if the query returns a non nil record. The functionality of these functions would be tested by the integration tests of the controller&lt;/div&gt;</summary>
		<author><name>Vdatla</name></author>
	</entry>
	<entry>
		<id>https://wiki.expertiza.ncsu.edu/index.php?title=CSC/ECE_517_Fall_2016/E1670._Unit_tests_for_answers.rb&amp;diff=102708</id>
		<title>CSC/ECE 517 Fall 2016/E1670. Unit tests for answers.rb</title>
		<link rel="alternate" type="text/html" href="https://wiki.expertiza.ncsu.edu/index.php?title=CSC/ECE_517_Fall_2016/E1670._Unit_tests_for_answers.rb&amp;diff=102708"/>
		<updated>2016-10-28T06:15:27Z</updated>

		<summary type="html">&lt;p&gt;Vdatla: &lt;/p&gt;
&lt;hr /&gt;
&lt;div&gt;==E1670 . Unit tests for answers.rb==&lt;br /&gt;
&lt;br /&gt;
This wiki page is for the description of changes made under E1670 OSS assignment for Fall 2016, CSC/ECE 517.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
__TOC__&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
===Background===&lt;br /&gt;
&lt;br /&gt;
Expertiza is an Open Source web application developed on Ruby On Rails platform. It is a platform which allows students to take assignments posted by the course instructors. Expertiza allows students to select assignment topics, form teams and submit their work. It also allows them to review other students' submissions and improve their work based on this feedback.&lt;br /&gt;
&lt;br /&gt;
===Project Description===&lt;br /&gt;
&lt;br /&gt;
In Expertiza, each questionnaire contains many questions, those question may have different types (e.g. checkbox, criterion, etc). When a user fills in a rubric, the responses for each question will become an answer record. The responses of rubrics are stored in answers table in DB. The answer.rb is the model for the answers table in DB. Answer.rb model does not have any test cases and the aim of the project is to write fast, effective and flexible unit test cases that offer maximum code coverage.&lt;br /&gt;
&lt;br /&gt;
===Files Created/Modified===&lt;br /&gt;
*answer_spec.rb&lt;br /&gt;
*factories.rb&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
===RSpec===&lt;br /&gt;
====RSpec Introduction====&lt;br /&gt;
RSpec is a testing framework for Ruby for behavior-driven development (BDD) licensed under MIT. It is inspired by JBehave and contains fully integrated JMock based framework which has a very rich and powerful DSL (domain-specific language) which resembles a natural language specification.&lt;br /&gt;
Composed of multiple libraries structured to work together, RSpec provides encapsulated testing via the describe block to specify the behavior of the class and the context for the unit test case.&lt;br /&gt;
&lt;br /&gt;
==== Why RSpec? ====&lt;br /&gt;
RSpec is easy to learn and implement and can be used with other testing tools like Cucumber and Minitest independently. It is extremely powerful for testing states with complicated setup and also helps in tearing down complex code to access the objects required for testing&lt;br /&gt;
RSpec semantics encourage agile thinking and practice and it structures the tests in a more intuitive way.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
===Functions in answers.rb===&lt;br /&gt;
&lt;br /&gt;
'''Function Name : Compute_scores'''&lt;br /&gt;
&lt;br /&gt;
Compute_scores is a function in model answer.rb which gives the average, maximum and minimum scores obtained in a series a responses/assessments. It has two input parameters: List of assessments and questions. The function iterates over each assessment to get the total score of that assessment. If the response or review is invalid, that assessment won’t be considered in the calculation of the score average. After iterating over all assessments, Max score, and Min scores are calculated along with the average score based on the number of valid assessments. Their scores are returned by the function.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
'''Rspec Unit Test : Compute_scores'''&lt;br /&gt;
&lt;br /&gt;
Following scenarios are tested:&lt;br /&gt;
&lt;br /&gt;
* To return scores as nil if the input list of assessments is nil. This is to make sure no Null Pointer exceptions are thrown by the code&lt;br /&gt;
*To return a particular score when a single valid assessment is given as an input.&lt;br /&gt;
*To return a particular score when multiple valid assessments are given as an input. This is to test the looping functionality of the method.&lt;br /&gt;
*To return a particular score when invalid assessments are given as an input. The validity and total scores are returned by a mock and not by the actual functions. This is to make the test cases less rigid so that failure of dependent functions do not disrupt the functionality of interface level tests.&lt;br /&gt;
*To return a particular score when invalid flag is nil. Invalid flag can either be 0,1 or nil. Nil situation is tested to prevent NullPointer Exceptions&lt;br /&gt;
*To check if the method get_total_score is called with the right parameters.&lt;br /&gt;
&lt;br /&gt;
This unit test uses a stub and returns a mock value.&lt;br /&gt;
&amp;lt;pre&amp;gt;&lt;br /&gt;
Answer.stub(:get_total_score)&lt;br /&gt;
&amp;lt;/pre&amp;gt;&lt;br /&gt;
This is to eliminate tight coupling between compute_scores and get_total_scores. Failure in get_total_scores wouldn't break the compute_scores test cases.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
'''Function Name : Get_total_scores'''&lt;br /&gt;
&lt;br /&gt;
This function is called by the Compute_scores method of the answer.rb model to compute the total score of an assessment. The input consists of assessment for which the total score is being calculated and the list of questions being evaluated in the assessment. The method uses questionnaire id from the questions and response id to obtain a score view questionnaire data. This score view is a read-only record. The questionnaire data mainly consists of q1_max_question_score, sum_of_weights and weighted_score. Before calculating the score, the function performs two crucial tasks. &lt;br /&gt;
*Checks if the answer for a scored question is nil. If it is nil or unanswered, the question will be ignored and not counted towards the score of this response.&lt;br /&gt;
* Calls the submission_valid function by passing the response record to set the @invalid flag based on the validity of the response.&lt;br /&gt;
The total score is calculated using the below formula&lt;br /&gt;
&lt;br /&gt;
&amp;lt;pre&amp;gt;&lt;br /&gt;
(weighted_score / (sum_of_weights * max_question_score)) * 100&lt;br /&gt;
&amp;lt;/pre&amp;gt;&lt;br /&gt;
&lt;br /&gt;
Any edge cases would return -1 indicating no score&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
'''Rspec Unit Test : Get_total_scores'''&lt;br /&gt;
&lt;br /&gt;
Following scenarios are tested:&lt;br /&gt;
&lt;br /&gt;
*To return an anticipated total score of a single response without any edge cases. Since this function will be called only on one response at a time, there is no need to test for multiple responses at the same time.&lt;br /&gt;
*To return an anticipated total score of a response where nil answer is for a scored question. This is to check if its weight gets removed from the sum_of_weights.&lt;br /&gt;
*To return -1 when the sum of weights becomes 0. This can happen when all the scored questions are unanswered. Return value of -1 is checked at the calling function to ensure if a score is returned or not.&lt;br /&gt;
*To return -1 when weighted_score of questionnaireData is nil&lt;br /&gt;
* To check if submission_valid is called. This method is called to set invalid flag to indicate whether the response entered is valid or not. The validity criteria is explained in the submission_valid? Function.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
This unit test uses two stubs and returns mock results&lt;br /&gt;
&amp;lt;pre&amp;gt;&lt;br /&gt;
ScoreView.stub(:find_by_sql)&lt;br /&gt;
&amp;lt;/pre&amp;gt;&lt;br /&gt;
&amp;lt;pre&amp;gt;&lt;br /&gt;
Answer.stub(:where)&lt;br /&gt;
&amp;lt;/pre&amp;gt;&lt;br /&gt;
This is to reduce the outcome of the test to depend on DB calls. For example, in case the connection to DB fails, this unit test would still pass making it less rigid.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
'''Function Name : submission_valid?'''&lt;br /&gt;
&lt;br /&gt;
This purpose of this function is to verify the validity of a review based on a deadline.  This function obtains a list of AssignmentDueDate objects  in descending order which is then compared against the current time to determine which deadlines are valid and which ones are not. The flag variable is used to represent whether or not a deadline was available in the previous iteration of the loop. If the flag is set to TRUE and the deadline is less than the current date, then latest_review_phase_start_time is set to this deadline. A list of ResubmissionTime objects is also retrieved from the controller. These objects are then compared against the then latest_review_phase_start_time variable to determine a response. &lt;br /&gt;
&lt;br /&gt;
Observations: The current implementation of the function is bugged. It retrieves a list of sorted AssignmentDueDate objects and proceeds to check if this list is empty. However, instead of exiting if the function if the list is empty, it carries on execution and raises an exception on hitting the for loop. &lt;br /&gt;
&lt;br /&gt;
*Checks if a review is valid or not by comparing its date with a list of deadlines.&lt;br /&gt;
*Returns 1 or 0 depending on validity&lt;br /&gt;
*Current implementation is bugged. Throws an exception if no AssignmentDueDate objects are passed, returns nil if any objects are passed.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
'''Rspec Unit Test : submission_valid?'''&lt;br /&gt;
&lt;br /&gt;
Following scenarios are tested:&lt;br /&gt;
&lt;br /&gt;
*Passing valid AssignmentDueDate objects&lt;br /&gt;
*Not passing any AssignmentDueDate objects&lt;br /&gt;
&lt;br /&gt;
When valid AssignmentDueDate objects are passed, stubs are used to create fake AssignmentDueDate Objects and ResubmissionTime objects. These objects are then populated with valid deadline dates and deadline_type values. These values are then supplied when requested by the submission_valid? Function rather than actually calling the function.  The current implementation of this test case expects the program to throw an error when it reaches the for loop. Once this bug is fixed, this test case may be re-written to test a more legitimate test case.&lt;br /&gt;
&lt;br /&gt;
In case an empty list of AssignmentDueDate objects is passed back to the submission_valid?() method. This would cause the function to return nil. When this function is fixed, the following test case may be re-written to test for a more legitimate test-case.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
This unit test uses two stubs and returns mock results&lt;br /&gt;
&amp;lt;pre&amp;gt;&lt;br /&gt;
AssignmentDueDate.stub_chain(:where, :order).and_return(due_date1, due_date2)&lt;br /&gt;
&amp;lt;/pre&amp;gt;&lt;br /&gt;
The above stub returns two AssignmentDueDate objects whenever the where() and order() method are chained on AssignmentDueDate.&lt;br /&gt;
&amp;lt;pre&amp;gt;&lt;br /&gt;
ResubmissionTime.stub_chain(:where, :order).and_return(ResubmissionTime1, ResubmissionTime2)&lt;br /&gt;
&amp;lt;/pre&amp;gt;&lt;br /&gt;
The above stub returns two ResubmissionTime objects whenever the where() and order() method are chained on ResubmissionTime.&lt;br /&gt;
&amp;lt;pre&amp;gt;&lt;br /&gt;
AssignmentDueDate.stub_chain(:where, :order).and_return(nil)&lt;br /&gt;
&amp;lt;/pre&amp;gt;&lt;br /&gt;
This stub is used in the second test case to return nil objects.&lt;br /&gt;
&lt;br /&gt;
the stub_chain method can be used to create stubs where chained methods are expected.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
'''Function Name : answers_by_question, answers_by_question_for_reviewee,answers_by_question_for_reviewee_in_round'''&lt;br /&gt;
&lt;br /&gt;
These three functions are sql queries that hit the DB to get a output record after a series of selections and joins. SQL queries that hit DB often do not have a high priority when it comes to testing, so the project does not aggressively test these functions. However, these functions are tested to make sure the queries are able to find the right column names and tables successfully. Any change in the table schema would be detected in these test cases. The functionality of these queries are not tested but instead existence of an output is tested. This ensures that answer.rb is able to make a successful db connection and is sync with the latest db schema. Since the function actually hits the DB, mocks can no longer be used, instead active records were created and saved in test db using FactoryGirl gem from the factories.rb. These records are cleared after every test case.&lt;br /&gt;
&lt;br /&gt;
Following factories were used to create records in the table&lt;br /&gt;
*question&lt;br /&gt;
*response_record&lt;br /&gt;
*response_map&lt;br /&gt;
*answer&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
'''Rspec Unit Test : answers_by_question, answers_by_question_for_reviewee,answers_by_question_for_reviewee_in_round'''&lt;br /&gt;
&lt;br /&gt;
The factories are created such a way that the query would return an output and the tests will pass if the query returns a non nil record.&lt;/div&gt;</summary>
		<author><name>Vdatla</name></author>
	</entry>
	<entry>
		<id>https://wiki.expertiza.ncsu.edu/index.php?title=CSC/ECE_517_Fall_2016/E1670._Unit_tests_for_answers.rb&amp;diff=102707</id>
		<title>CSC/ECE 517 Fall 2016/E1670. Unit tests for answers.rb</title>
		<link rel="alternate" type="text/html" href="https://wiki.expertiza.ncsu.edu/index.php?title=CSC/ECE_517_Fall_2016/E1670._Unit_tests_for_answers.rb&amp;diff=102707"/>
		<updated>2016-10-28T06:14:42Z</updated>

		<summary type="html">&lt;p&gt;Vdatla: &lt;/p&gt;
&lt;hr /&gt;
&lt;div&gt;==E1670 . Unit tests for answers.rb==&lt;br /&gt;
&lt;br /&gt;
This wiki page is for the description of changes made under E1670 OSS assignment for Fall 2016, CSC/ECE 517.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
__TOC__&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
===Background===&lt;br /&gt;
&lt;br /&gt;
Expertiza is an Open Source web application developed on Ruby On Rails platform. It is a platform which allows students to take assignments posted by the course instructors. Expertiza allows students to select assignment topics, form teams and submit their work. It also allows them to review other students' submissions and improve their work based on this feedback.&lt;br /&gt;
&lt;br /&gt;
===Project Description===&lt;br /&gt;
&lt;br /&gt;
In Expertiza, each questionnaire contains many questions, those question may have different types (e.g. checkbox, criterion, etc). When a user fills in a rubric, the responses for each question will become an answer record. The responses of rubrics are stored in answers table in DB. The answer.rb is the model for the answers table in DB. Answer.rb model does not have any test cases and the aim of the project is to write fast, effective and flexible unit test cases that offer maximum code coverage.&lt;br /&gt;
&lt;br /&gt;
===Files Created/Modified===&lt;br /&gt;
*answer_spec.rb&lt;br /&gt;
*factories.rb&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
===RSpec===&lt;br /&gt;
====RSpec Introduction====&lt;br /&gt;
RSpec is a testing framework for Ruby for behavior-driven development (BDD) licensed under MIT. It is inspired by JBehave and contains fully integrated JMock based framework which has a very rich and powerful DSL (domain-specific language) which resembles a natural language specification.&lt;br /&gt;
Composed of multiple libraries structured to work together, RSpec provides encapsulated testing via the describe block to specify the behavior of the class and the context for the unit test case.&lt;br /&gt;
&lt;br /&gt;
==== Why RSpec? ====&lt;br /&gt;
RSpec is easy to learn and implement and can be used with other testing tools like Cucumber and Minitest independently. It is extremely powerful for testing states with complicated setup and also helps in tearing down complex code to access the objects required for testing&lt;br /&gt;
RSpec semantics encourage agile thinking and practice and it structures the tests in a more intuitive way.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
===Functions in answers.rb===&lt;br /&gt;
&lt;br /&gt;
'''Function Name : Compute_scores'''&lt;br /&gt;
&lt;br /&gt;
Compute_scores is a function in model answer.rb which gives the average, maximum and minimum scores obtained in a series a responses/assessments. It has two input parameters: List of assessments and questions. The function iterates over each assessment to get the total score of that assessment. If the response or review is invalid, that assessment won’t be considered in the calculation of the score average. After iterating over all assessments, Max score, and Min scores are calculated along with the average score based on the number of valid assessments. Their scores are returned by the function.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
'''Rspec Unit Test : Compute_scores'''&lt;br /&gt;
&lt;br /&gt;
Following scenarios are tested:&lt;br /&gt;
&lt;br /&gt;
* To return scores as nil if the input list of assessments is nil. This is to make sure no Null Pointer exceptions are thrown by the code&lt;br /&gt;
*To return a particular score when a single valid assessment is given as an input.&lt;br /&gt;
*To return a particular score when multiple valid assessments are given as an input. This is to test the looping functionality of the method.&lt;br /&gt;
*To return a particular score when invalid assessments are given as an input. The validity and total scores are returned by a mock and not by the actual functions. This is to make the test cases less rigid so that failure of dependent functions do not disrupt the functionality of interface level tests.&lt;br /&gt;
*To return a particular score when invalid flag is nil. Invalid flag can either be 0,1 or nil. Nil situation is tested to prevent NullPointer Exceptions&lt;br /&gt;
*To check if the method get_total_score is called with the right parameters.&lt;br /&gt;
&lt;br /&gt;
This unit test uses a stub and returns a mock value.&lt;br /&gt;
&amp;lt;pre&amp;gt;&lt;br /&gt;
Answer.stub(:get_total_score)&lt;br /&gt;
&amp;lt;/pre&amp;gt;&lt;br /&gt;
This is to eliminate tight coupling between compute_scores and get_total_scores. Failure in get_total_scores wouldn't break the compute_scores test cases.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
'''Function Name : Get_total_scores'''&lt;br /&gt;
&lt;br /&gt;
This function is called by the Compute_scores method of the answer.rb model to compute the total score of an assessment. The input consists of assessment for which the total score is being calculated and the list of questions being evaluated in the assessment. The method uses questionnaire id from the questions and response id to obtain a score view questionnaire data. This score view is a read-only record. The questionnaire data mainly consists of q1_max_question_score, sum_of_weights and weighted_score. Before calculating the score, the function performs two crucial tasks. &lt;br /&gt;
*Checks if the answer for a scored question is nil. If it is nil or unanswered, the question will be ignored and not counted towards the score of this response.&lt;br /&gt;
* Calls the submission_valid function by passing the response record to set the @invalid flag based on the validity of the response.&lt;br /&gt;
The total score is calculated using the below formula&lt;br /&gt;
&lt;br /&gt;
&amp;lt;pre&amp;gt;&lt;br /&gt;
(weighted_score / (sum_of_weights * max_question_score)) * 100&lt;br /&gt;
&amp;lt;/pre&amp;gt;&lt;br /&gt;
&lt;br /&gt;
Any edge cases would return -1 indicating no score&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
'''Rspec Unit Test : Get_total_scores'''&lt;br /&gt;
&lt;br /&gt;
Following scenarios are tested:&lt;br /&gt;
&lt;br /&gt;
*To return an anticipated total score of a single response without any edge cases. Since this function will be called only on one response at a time, there is no need to test for multiple responses at the same time.&lt;br /&gt;
*To return an anticipated total score of a response where nil answer is for a scored question. This is to check if its weight gets removed from the sum_of_weights.&lt;br /&gt;
*To return -1 when the sum of weights becomes 0. This can happen when all the scored questions are unanswered. Return value of -1 is checked at the calling function to ensure if a score is returned or not.&lt;br /&gt;
*To return -1 when weighted_score of questionnaireData is nil&lt;br /&gt;
* To check if submission_valid is called. This method is called to set invalid flag to indicate whether the response entered is valid or not. The validity criteria is explained in the submission_valid? Function.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
This unit test uses two stubs and returns mock results&lt;br /&gt;
&amp;lt;pre&amp;gt;&lt;br /&gt;
ScoreView.stub(:find_by_sql)&lt;br /&gt;
&amp;lt;/pre&amp;gt;&lt;br /&gt;
&amp;lt;pre&amp;gt;&lt;br /&gt;
Answer.stub(:where)&lt;br /&gt;
&amp;lt;/pre&amp;gt;&lt;br /&gt;
This is to reduce the outcome of the test to depend on DB calls. For example, in case the connection to DB fails, this unit test would still pass making it less rigid.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
'''Function Name : submission_valid?'''&lt;br /&gt;
&lt;br /&gt;
This purpose of this function is to verify the validity of a review based on a deadline.  This function obtains a list of AssignmentDueDate objects  in descending order which is then compared against the current time to determine which deadlines are valid and which ones are not. The flag variable is used to represent whether or not a deadline was available in the previous iteration of the loop. If the flag is set to TRUE and the deadline is less than the current date, then latest_review_phase_start_time is set to this deadline. A list of ResubmissionTime objects is also retrieved from the controller. These objects are then compared against the then latest_review_phase_start_time variable to determine a response. &lt;br /&gt;
&lt;br /&gt;
Observations: The current implementation of the function is bugged. It retrieves a list of sorted AssignmentDueDate objects and proceeds to check if this list is empty. However, instead of exiting if the function if the list is empty, it carries on execution and raises an exception on hitting the for loop. &lt;br /&gt;
&lt;br /&gt;
*Checks if a review is valid or not by comparing its date with a list of deadlines.&lt;br /&gt;
*Returns 1 or 0 depending on validity&lt;br /&gt;
*Current implementation is bugged. Throws an exception if no AssignmentDueDate objects are passed, returns nil if any objects are passed.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
'''Rspec Unit Test : submission_valid?'''&lt;br /&gt;
&lt;br /&gt;
Following scenarios are tested:&lt;br /&gt;
&lt;br /&gt;
*Passing valid AssignmentDueDate objects&lt;br /&gt;
*Not passing any AssignmentDueDate objects&lt;br /&gt;
&lt;br /&gt;
When valid AssignmentDueDate objects are passed, stubs are used to create fake AssignmentDueDate Objects and ResubmissionTime objects. These objects are then populated with valid deadline dates and deadline_type values. These values are then supplied when requested by the submission_valid? Function rather than actually calling the function.  The current implementation of this test case expects the program to throw an error when it reaches the for loop. Once this bug is fixed, this test case may be re-written to test a more legitimate test case.&lt;br /&gt;
&lt;br /&gt;
In case an empty list of AssignmentDueDate objects is passed back to the submission_valid?() method. This would cause the function to return nil. When this function is fixed, the following test case may be re-written to test for a more legitimate test-case.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
This unit test uses two stubs and returns mock results&lt;br /&gt;
&amp;lt;pre&amp;gt;&lt;br /&gt;
AssignmentDueDate.stub_chain(:where, :order).and_return(due_date1, due_date2)&lt;br /&gt;
&amp;lt;/pre&amp;gt;&lt;br /&gt;
The above stub returns two AssignmentDueDate objects whenever the where() and order() method are chained on AssignmentDueDate.&lt;br /&gt;
&amp;lt;pre&amp;gt;&lt;br /&gt;
ResubmissionTime.stub_chain(:where, :order).and_return(ResubmissionTime1, ResubmissionTime2)&lt;br /&gt;
&amp;lt;/pre&amp;gt;&lt;br /&gt;
The above stub returns two ResubmissionTime objects whenever the where() and order() method are chained on ResubmissionTime.&lt;br /&gt;
&amp;lt;pre&amp;gt;&lt;br /&gt;
AssignmentDueDate.stub_chain(:where, :order).and_return(nil)&lt;br /&gt;
&amp;lt;/pre&amp;gt;&lt;br /&gt;
This stub is used in the second test case to return nil objects.&lt;br /&gt;
&lt;br /&gt;
the stub_chain method can be used to create stubs where chained methods are expected.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
'''Function Name : answers_by_question, answers_by_question_for_reviewee,answers_by_question_for_reviewee_in_round'''&lt;br /&gt;
&lt;br /&gt;
These three functions are sql queries that hit the DB to get a output record after a series of selections and joins. SQL queries that hit DB often do not have a high priority when it comes to testing, so the project does not aggressively test these functions. However, these functions are tested to make sure the queries are able to find the right column names and tables successfully. Any change in the table schema would be detected in these test cases. The functionality of these queries are not tested but instead existence of an output is tested. This ensures that answer.rb is able to make a successful db connection and is sync with the latest db schema. Since the function actually hits the DB, mocks can no longer be used, instead active records were created and saved in test db using FactoryGirl gem from the factories.rb. These records are cleared after every test case.&lt;br /&gt;
&lt;br /&gt;
Following factories were used to create records in the table&lt;br /&gt;
*question&lt;br /&gt;
*response_record&lt;br /&gt;
*response_map&lt;br /&gt;
*answer&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
'''Rspec Unit Test : answers_by_question, answers_by_question_for_reviewee,answers_by_question_for_reviewee_in_round'''&lt;br /&gt;
The factories are created such a way that the query would return an output and the tests will pass if the query returns a non nil record.&lt;/div&gt;</summary>
		<author><name>Vdatla</name></author>
	</entry>
	<entry>
		<id>https://wiki.expertiza.ncsu.edu/index.php?title=CSC/ECE_517_Fall_2016/E1670._Unit_tests_for_answers.rb&amp;diff=102706</id>
		<title>CSC/ECE 517 Fall 2016/E1670. Unit tests for answers.rb</title>
		<link rel="alternate" type="text/html" href="https://wiki.expertiza.ncsu.edu/index.php?title=CSC/ECE_517_Fall_2016/E1670._Unit_tests_for_answers.rb&amp;diff=102706"/>
		<updated>2016-10-28T06:12:52Z</updated>

		<summary type="html">&lt;p&gt;Vdatla: &lt;/p&gt;
&lt;hr /&gt;
&lt;div&gt;==E1670 . Unit tests for answers.rb==&lt;br /&gt;
&lt;br /&gt;
This wiki page is for the description of changes made under E1670 OSS assignment for Fall 2016, CSC/ECE 517.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
__TOC__&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
===Background===&lt;br /&gt;
&lt;br /&gt;
Expertiza is an Open Source web application developed on Ruby On Rails platform. It is a platform which allows students to take assignments posted by the course instructors. Expertiza allows students to select assignment topics, form teams and submit their work. It also allows them to review other students' submissions and improve their work based on this feedback.&lt;br /&gt;
&lt;br /&gt;
===Project Description===&lt;br /&gt;
&lt;br /&gt;
In Expertiza, each questionnaire contains many questions, those question may have different types (e.g. checkbox, criterion, etc). When a user fills in a rubric, the responses for each question will become an answer record. The responses of rubrics are stored in answers table in DB. The answer.rb is the model for the answers table in DB. Answer.rb model does not have any test cases and the aim of the project is to write fast, effective and flexible unit test cases that offer maximum code coverage.&lt;br /&gt;
&lt;br /&gt;
===Files Created/Modified===&lt;br /&gt;
*answer_spec.rb&lt;br /&gt;
*factories.rb&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
===RSpec===&lt;br /&gt;
====RSpec Introduction====&lt;br /&gt;
RSpec is a testing framework for Ruby for behavior-driven development (BDD) licensed under MIT. It is inspired by JBehave and contains fully integrated JMock based framework which has a very rich and powerful DSL (domain-specific language) which resembles a natural language specification.&lt;br /&gt;
Composed of multiple libraries structured to work together, RSpec provides encapsulated testing via the describe block to specify the behavior of the class and the context for the unit test case.&lt;br /&gt;
&lt;br /&gt;
==== Why RSpec? ====&lt;br /&gt;
RSpec is easy to learn and implement and can be used with other testing tools like Cucumber and Minitest independently. It is extremely powerful for testing states with complicated setup and also helps in tearing down complex code to access the objects required for testing&lt;br /&gt;
RSpec semantics encourage agile thinking and practice and it structures the tests in a more intuitive way.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
===Functions in answers.rb===&lt;br /&gt;
&lt;br /&gt;
'''Function Name : Compute_scores'''&lt;br /&gt;
&lt;br /&gt;
Compute_scores is a function in model answer.rb which gives the average, maximum and minimum scores obtained in a series a responses/assessments. It has two input parameters: List of assessments and questions. The function iterates over each assessment to get the total score of that assessment. If the response or review is invalid, that assessment won’t be considered in the calculation of the score average. After iterating over all assessments, Max score, and Min scores are calculated along with the average score based on the number of valid assessments. Their scores are returned by the function.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
'''Rspec Unit Test : Compute_scores'''&lt;br /&gt;
&lt;br /&gt;
Following scenarios are tested:&lt;br /&gt;
&lt;br /&gt;
* To return scores as nil if the input list of assessments is nil. This is to make sure no Null Pointer exceptions are thrown by the code&lt;br /&gt;
*To return a particular score when a single valid assessment is given as an input.&lt;br /&gt;
*To return a particular score when multiple valid assessments are given as an input. This is to test the looping functionality of the method.&lt;br /&gt;
*To return a particular score when invalid assessments are given as an input. The validity and total scores are returned by a mock and not by the actual functions. This is to make the test cases less rigid so that failure of dependent functions do not disrupt the functionality of interface level tests.&lt;br /&gt;
*To return a particular score when invalid flag is nil. Invalid flag can either be 0,1 or nil. Nil situation is tested to prevent NullPointer Exceptions&lt;br /&gt;
*To check if the method get_total_score is called with the right parameters.&lt;br /&gt;
&lt;br /&gt;
This unit tes uses a stub and returns a mock value.&lt;br /&gt;
&amp;lt;pre&amp;gt;&lt;br /&gt;
Answer.stub(:get_total_score)&lt;br /&gt;
&amp;lt;/pre&amp;gt;&lt;br /&gt;
This is to eliminate tight coupling between compute_scores and get_total_scores. Failure in get_total_scores would'nt break the compute_scores test cases.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
'''Function Name : Get_total_scores'''&lt;br /&gt;
&lt;br /&gt;
This function is called by the Compute_scores method of the answer.rb model to compute the total score of an assessment. The input consists of assessment for which the total score is being calculated and the list of questions being evaluated in the assessment. The method uses questionnaire id from the questions and response id to obtain a score view questionnaire data. This score view is a read-only record. The questionnaire data mainly consists of q1_max_question_score, sum_of_weights and wieghted_score. Before calculating the score, the function performs two crucial tasks. &lt;br /&gt;
*Checks if the answer for a scored question is nil. If it is nil or unanswered, the question will be ignored and not counted towards the score of this response.&lt;br /&gt;
* Calls the subsission_valid function by passing the response record to set the @invalid flag based on the validity of the response.&lt;br /&gt;
The total score is calculated using the below formula&lt;br /&gt;
&lt;br /&gt;
&amp;lt;pre&amp;gt;&lt;br /&gt;
(weighted_score / (sum_of_weights * max_question_score)) * 100&lt;br /&gt;
&amp;lt;/pre&amp;gt;&lt;br /&gt;
&lt;br /&gt;
Any edge cases would return -1 indicating no score&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
'''Rspec Unit Test : Get_total_scores'''&lt;br /&gt;
&lt;br /&gt;
Following scenarios are tested:&lt;br /&gt;
&lt;br /&gt;
*To return an anticipated total score of a single response without any edge cases. Since this function will be called only on one response at a time, there is no need to test for multiple responses at the same time.&lt;br /&gt;
*To return an anticipated total score of a response where nil answer is for a scored question. This is to check if its weight gets removed from the sum_of_weights.&lt;br /&gt;
*To return -1 when the sum of weights becomes 0. This can happen when all the scored questions are unanswered. Return value of -1 is checked at the calling function to ensure if a score is returned or not.&lt;br /&gt;
*To return -1 when weighted_score of questionnaireData is nil&lt;br /&gt;
* To check if submission_valid is called. This method is called to set invalid flag to indicate whether the response entered is valid or not. The validity criteria is explained in the submission_valid? Function.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
This unit test uses two stubs and returns mock results&lt;br /&gt;
&amp;lt;pre&amp;gt;&lt;br /&gt;
ScoreView.stub(:find_by_sql)&lt;br /&gt;
&amp;lt;/pre&amp;gt;&lt;br /&gt;
&amp;lt;pre&amp;gt;&lt;br /&gt;
Answer.stub(:where)&lt;br /&gt;
&amp;lt;/pre&amp;gt;&lt;br /&gt;
This is to reduce the outcome of the test to depend on DB calls. For example, in case the connection to DB fails, this unit test would still pass making it less rigid.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
'''Function Name : submission_valid?'''&lt;br /&gt;
&lt;br /&gt;
This purpose of this function is to verify the validity of a review based on a deadline.  This function obtains a list of AssignmentDueDate objects  in descending order which is then compared against the current time to determine which deadlines are valid and which ones are not. The flag variable is used to represent whether or not a deadline was available in the previous iteration of the loop. If the flag is set to TRUE and the deadline is less than the current date, then latest_review_phase_start_time is set to this deadline. A list of ResubmissionTime objects is also retrieved from the controller. These objects are then compared against the then latest_review_phase_start_time variable to determine a response. &lt;br /&gt;
&lt;br /&gt;
Observations: The current implementation of the function is bugged. It retrieves a list of sorted AssignmentDueDate objects and proceeds to check if this list is empty. However, instead of exiting if the function if the list is empty, it carries on execution and raises an exception on hitting the for loop. &lt;br /&gt;
&lt;br /&gt;
*Checks if a review is valid or not by comparing its date with a list of deadlines.&lt;br /&gt;
*Returns 1 or 0 depending on validity&lt;br /&gt;
*Current implementation is bugged. Throws an exception if no AssignmentDueDate objects are passed, returns nil if any objects are passed.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
'''Rspec Unit Test : submission_valid?'''&lt;br /&gt;
&lt;br /&gt;
Following scenarios are tested:&lt;br /&gt;
&lt;br /&gt;
*Passing valid AssignmentDueDate objects&lt;br /&gt;
*Not passing any AssignmentDueDate objects&lt;br /&gt;
&lt;br /&gt;
When valid AssignmentDueDate objects are passed, stubs are used to create fake AssignmentDueDate Objects and ResubmissionTime objects. These objects are then populated with valid deadline dates and deadline_type values. These values are then supplied when requested by the submission_valid? Function rather than actually calling the function.  The current implementation of this test case expects the program to throw an error when it reaches the for loop. Once this bug is fixed, this test case may be re-written to test a more legitimate test case.&lt;br /&gt;
&lt;br /&gt;
In case an empty list of AssignmentDueDate objects is passed back to the submission_valid?() method. This would cause the function to return nil. When this function is fixed, the following test case may be re-written to test for a more legitimate test-case.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
This unit test uses two stubs and returns mock results&lt;br /&gt;
&amp;lt;pre&amp;gt;&lt;br /&gt;
AssignmentDueDate.stub_chain(:where, :order).and_return(due_date1, due_date2)&lt;br /&gt;
&amp;lt;/pre&amp;gt;&lt;br /&gt;
The above stub returns two AssignmentDueDate objects whenever the where() and order() method are chained on AssignmentDueDate.&lt;br /&gt;
&amp;lt;pre&amp;gt;&lt;br /&gt;
ResubmissionTime.stub_chain(:where, :order).and_return(ResubmissionTime1, ResubmissionTime2)&lt;br /&gt;
&amp;lt;/pre&amp;gt;&lt;br /&gt;
The above stub returns two ResubmissionTime objects whenever the where() and order() method are chained on ResubmissionTime.&lt;br /&gt;
&amp;lt;pre&amp;gt;&lt;br /&gt;
AssignmentDueDate.stub_chain(:where, :order).and_return(nil)&lt;br /&gt;
&amp;lt;/pre&amp;gt;&lt;br /&gt;
This stub is used in the second test case to return nil objects.&lt;br /&gt;
&lt;br /&gt;
the stub_chain method can be used to create stubs where chained methods are expected.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
'''Function Name : answers_by_question, answers_by_question_for_reviewee,answers_by_question_for_reviewee_in_round'''&lt;br /&gt;
&lt;br /&gt;
These three functions are sql queries that hit the DB to get a output record after a series of selections and joins. SQL queries that hit DB often do not have a high priority when it comes to testing, so the project does not regressively test these functions. However, these functions are tested to make sure the queries are able to find the right column names and tables successfully. Any change in the table schema would be detected in these test cases. The functionality of these queries are not tested but instead existence of an output is tested. This ensures that answer.rb is able to make a successful db connection and is sync with the latest db schema. Since the function actually hits the DB, mocks can no longer be used, instead active records were created and saved in test db using FactoryGirl gem from the factories.rb. These records are cleared after every test case.&lt;br /&gt;
&lt;br /&gt;
Following factories were used to create records in the table&lt;br /&gt;
*question&lt;br /&gt;
*response_record&lt;br /&gt;
*response_map&lt;br /&gt;
*answer&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
'''Rspec Unit Test : answers_by_question, answers_by_question_for_reviewee,answers_by_question_for_reviewee_in_round'''&lt;br /&gt;
The factories are created such a way that the query would return an output and the tests will pass if the query returns a non nil record.&lt;/div&gt;</summary>
		<author><name>Vdatla</name></author>
	</entry>
	<entry>
		<id>https://wiki.expertiza.ncsu.edu/index.php?title=CSC/ECE_517_Fall_2016/E1670._Unit_tests_for_answers.rb&amp;diff=102703</id>
		<title>CSC/ECE 517 Fall 2016/E1670. Unit tests for answers.rb</title>
		<link rel="alternate" type="text/html" href="https://wiki.expertiza.ncsu.edu/index.php?title=CSC/ECE_517_Fall_2016/E1670._Unit_tests_for_answers.rb&amp;diff=102703"/>
		<updated>2016-10-28T05:48:37Z</updated>

		<summary type="html">&lt;p&gt;Vdatla: &lt;/p&gt;
&lt;hr /&gt;
&lt;div&gt;==E1670 . Unit tests for answers.rb==&lt;br /&gt;
&lt;br /&gt;
This wiki page is for the description of changes made under E1670 OSS assignment for Fall 2016, CSC/ECE 517.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
__TOC__&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
===Background===&lt;br /&gt;
&lt;br /&gt;
Expertiza is an Open Source web application developed on Ruby On Rails platform. It is a platform which allows students to take assignments posted by the course instructors. Expertiza allows students to select assignment topics, form teams and submit their work. It also allows them to review other students' submissions and improve their work based on this feedback.&lt;br /&gt;
&lt;br /&gt;
===Project Description===&lt;br /&gt;
&lt;br /&gt;
In Expertiza, each questionnaire contains many questions, those question may have different types (e.g. checkbox, criterion, etc). When a user fills in a rubric, the responses for each question will become an answer record. The responses of rubrics are stored in answers table in DB. The answer.rb is the model for the answers table in DB. Answer.rb model does not have any test cases and the aim of the project is to write fast, effective and flexible unit test cases that offer maximum code coverage.&lt;br /&gt;
&lt;br /&gt;
===Files Created/Modified===&lt;br /&gt;
*answer_spec.rb&lt;br /&gt;
*factories.rb&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
===RSpec===&lt;br /&gt;
====RSpec Introduction====&lt;br /&gt;
RSpec is a testing framework for Ruby for behavior-driven development (BDD) licensed under MIT. It is inspired by JBehave and contains fully integrated JMock based framework which has a very rich and powerful DSL (domain-specific language) which resembles a natural language specification.&lt;br /&gt;
Composed of multiple libraries structured to work together, RSpec provides encapsulated testing via the describe block to specify the behavior of the class and the context for the unit test case.&lt;br /&gt;
&lt;br /&gt;
==== Why RSpec? ====&lt;br /&gt;
RSpec is easy to learn and implement and can be used with other testing tools like Cucumber and Minitest independently. It is extremely powerful for testing states with complicated setup and also helps in tearing down complex code to access the objects required for testing&lt;br /&gt;
RSpec semantics encourage agile thinking and practice and it structures the tests in a more intuitive way.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
===Functions in answers.rb===&lt;br /&gt;
&lt;br /&gt;
'''Function Name : Compute_scores'''&lt;br /&gt;
&lt;br /&gt;
Compute_scores is a function in model answer.rb which gives the average, maximum and minimum scores obtained in a series a responses/assessments. It has two input parameters: List of assessments and questions. The function iterates over each assessment to get the total score of that assessment. If the response or review is invalid, that assessment won’t be considered in the calculation of the score average. After iterating over all assessments, Max score, and Min scores are calculated along with the average score based on the number of valid assessments. Their scores are returned by the function.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
'''Rspec Unit Test : Compute_scores'''&lt;br /&gt;
&lt;br /&gt;
Following scenarios are tested:&lt;br /&gt;
&lt;br /&gt;
* To return scores as nil if the input list of assessments is nil. This is to make sure no Null Pointer exceptions are thrown by the code&lt;br /&gt;
*To return a particular score when a single valid assessment is given as an input.&lt;br /&gt;
*To return a particular score when multiple valid assessments are given as an input. This is to test the looping functionality of the method.&lt;br /&gt;
*To return a particular score when invalid assessments are given as an input. The validity and total scores are returned by a mock and not by the actual functions. This is to make the test cases less rigid so that failure of dependent functions do not disrupt the functionality of interface level tests.&lt;br /&gt;
*To return a particular score when invalid flag is nil. Invalid flag can either be 0,1 or nil. Nil situation is tested to prevent NullPointer Exceptions&lt;br /&gt;
*To check if the method get_total_score is called with the right parameters.&lt;br /&gt;
&lt;br /&gt;
This unit tes uses a stub and returns a mock value.&lt;br /&gt;
&amp;lt;pre&amp;gt;&lt;br /&gt;
Answer.stub(:get_total_score)&lt;br /&gt;
&amp;lt;/pre&amp;gt;&lt;br /&gt;
This is to eliminate tight coupling between compute_scores and get_total_scores. Failure in get_total_scores would'nt break the compute_scores test cases.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
'''Function Name : Get_total_scores'''&lt;br /&gt;
&lt;br /&gt;
This function is called by the Compute_scores method of the answer.rb model to compute the total score of an assessment. The input consists of assessment for which the total score is being calculated and the list of questions being evaluated in the assessment. The method uses questionnaire id from the questions and response id to obtain a score view questionnaire data. This score view is a read-only record. The questionnaire data mainly consists of q1_max_question_score, sum_of_weights and wieghted_score. Before calculating the score, the function performs two crucial tasks. &lt;br /&gt;
*Checks if the answer for a scored question is nil. If it is nil or unanswered, the question will be ignored and not counted towards the score of this response.&lt;br /&gt;
* Calls the subsission_valid function by passing the response record to set the @invalid flag based on the validity of the response.&lt;br /&gt;
The total score is calculated using the below formula&lt;br /&gt;
&lt;br /&gt;
&amp;lt;pre&amp;gt;&lt;br /&gt;
(weighted_score / (sum_of_weights * max_question_score)) * 100&lt;br /&gt;
&amp;lt;/pre&amp;gt;&lt;br /&gt;
&lt;br /&gt;
Any edge cases would return -1 indicating no score&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
'''Rspec Unit Test : Get_total_scores'''&lt;br /&gt;
&lt;br /&gt;
Following scenarios are tested:&lt;br /&gt;
&lt;br /&gt;
*To return an anticipated total score of a single response without any edge cases. Since this function will be called only on one response at a time, there is no need to test for multiple responses at the same time.&lt;br /&gt;
*To return an anticipated total score of a response where nil answer is for a scored question. This is to check if its weight gets removed from the sum_of_weights.&lt;br /&gt;
*To return -1 when the sum of weights becomes 0. This can happen when all the scored questions are unanswered. Return value of -1 is checked at the calling function to ensure if a score is returned or not.&lt;br /&gt;
*To return -1 when weighted_score of questionnaireData is nil&lt;br /&gt;
* To check if submission_valid is called. This method is called to set invalid flag to indicate whether the response entered is valid or not. The validity criteria is explained in the submission_valid? Function.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
This unit test uses two stubs and returns mock results&lt;br /&gt;
&amp;lt;pre&amp;gt;&lt;br /&gt;
ScoreView.stub(:find_by_sql)&lt;br /&gt;
&amp;lt;/pre&amp;gt;&lt;br /&gt;
&amp;lt;pre&amp;gt;&lt;br /&gt;
Answer.stub(:where)&lt;br /&gt;
&amp;lt;/pre&amp;gt;&lt;br /&gt;
This is to reduce the outcome of the test to depend on DB calls. For example, in case the connection to DB fails, this unit test would still pass making it less rigid.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
'''Function Name : submission_valid?'''&lt;br /&gt;
&lt;br /&gt;
This purpose of this function is to verify the validity of a review based on a deadline.  This function obtains a list of AssignmentDueDate objects  in descending order which is then compared against the current time to determine which deadlines are valid and which ones are not. The flag variable is used to represent whether or not a deadline was available in the previous iteration of the loop. If the flag is set to TRUE and the deadline is less than the current date, then latest_review_phase_start_time is set to this deadline. A list of ResubmissionTime objects is also retrieved from the controller. These objects are then compared against the then latest_review_phase_start_time variable to determine a response. &lt;br /&gt;
&lt;br /&gt;
Observations: The current implementation of the function is bugged. It retrieves a list of sorted AssignmentDueDate objects and proceeds to check if this list is empty. However, instead of exiting if the function if the list is empty, it carries on execution and raises an exception on hitting the for loop. &lt;br /&gt;
&lt;br /&gt;
*Checks if a review is valid or not by comparing its date with a list of deadlines.&lt;br /&gt;
*Returns 1 or 0 depending on validity&lt;br /&gt;
*Current implementation is bugged. Throws an exception if no AssignmentDueDate objects are passed, returns nil if any objects are passed.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
'''Rspec Unit Test : submission_valid?'''&lt;br /&gt;
&lt;br /&gt;
Following scenarios are tested:&lt;br /&gt;
&lt;br /&gt;
*Passing valid AssignmentDueDate objects&lt;br /&gt;
*Not passing any AssignmentDueDate objects&lt;br /&gt;
&lt;br /&gt;
When valid AssignmentDueDate objects are passed, stubs are used to create fake AssignmentDueDate Objects and ResubmissionTime objects. These objects are then populated with valid deadline dates and deadline_type values. These values are then supplied when requested by the submission_valid? Function rather than actually calling the function.  The current implementation of this test case expects the program to throw an error when it reaches the for loop. Once this bug is fixed, this test case may be re-written to test a more legitimate test case.&lt;br /&gt;
&lt;br /&gt;
In case an empty list of AssignmentDueDate objects is passed back to the submission_valid?() method. This would cause the function to return nil. When this function is fixed, the following test case may be re-written to test for a more legitimate test-case.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
This unit test uses two stubs and returns mock results&lt;br /&gt;
&amp;lt;pre&amp;gt;&lt;br /&gt;
AssignmentDueDate.stub_chain(:where, :order).and_return(due_date1, due_date2)&lt;br /&gt;
&amp;lt;/pre&amp;gt;&lt;br /&gt;
The above stub returns two AssignmentDueDate objects whenever the where() and order() method are chained on AssignmentDueDate.&lt;br /&gt;
&amp;lt;pre&amp;gt;&lt;br /&gt;
ResubmissionTime.stub_chain(:where, :order).and_return(ResubmissionTime1, ResubmissionTime2)&lt;br /&gt;
&amp;lt;/pre&amp;gt;&lt;br /&gt;
The above stub returns two ResubmissionTime objects whenever the where() and order() method are chained on ResubmissionTime.&lt;br /&gt;
&amp;lt;pre&amp;gt;&lt;br /&gt;
AssignmentDueDate.stub_chain(:where, :order).and_return(nil)&lt;br /&gt;
&amp;lt;/pre&amp;gt;&lt;br /&gt;
This stub is used in the second test case to return nil objects.&lt;br /&gt;
&lt;br /&gt;
the stub_chain method can be used to create stubs where chained methods are expected.&lt;/div&gt;</summary>
		<author><name>Vdatla</name></author>
	</entry>
	<entry>
		<id>https://wiki.expertiza.ncsu.edu/index.php?title=CSC/ECE_517_Fall_2016/E1670._Unit_tests_for_answers.rb&amp;diff=102702</id>
		<title>CSC/ECE 517 Fall 2016/E1670. Unit tests for answers.rb</title>
		<link rel="alternate" type="text/html" href="https://wiki.expertiza.ncsu.edu/index.php?title=CSC/ECE_517_Fall_2016/E1670._Unit_tests_for_answers.rb&amp;diff=102702"/>
		<updated>2016-10-28T05:44:20Z</updated>

		<summary type="html">&lt;p&gt;Vdatla: &lt;/p&gt;
&lt;hr /&gt;
&lt;div&gt;==E1670 . Unit tests for answers.rb==&lt;br /&gt;
&lt;br /&gt;
This wiki page is for the description of changes made under E1670 OSS assignment for Fall 2016, CSC/ECE 517.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
__TOC__&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
===Background===&lt;br /&gt;
&lt;br /&gt;
Expertiza is an Open Source web application developed on Ruby On Rails platform. It is a platform which allows students to take assignments posted by the course instructors. Expertiza allows students to select assignment topics, form teams and submit their work. It also allows them to review other students' submissions and improve their work based on this feedback.&lt;br /&gt;
&lt;br /&gt;
===Project Description===&lt;br /&gt;
&lt;br /&gt;
In Expertiza, each questionnaire contains many questions, those question may have different types (e.g. checkbox, criterion, etc). When a user fills in a rubric, the responses for each question will become an answer record. The responses of rubrics are stored in answers table in DB. The answer.rb is the model for the answers table in DB. Answer.rb model does not have any test cases and the aim of the project is to write fast, effective and flexible unit test cases that offer maximum code coverage.&lt;br /&gt;
&lt;br /&gt;
===RSpec===&lt;br /&gt;
====RSpec Introduction====&lt;br /&gt;
RSpec is a testing framework for Ruby for behavior-driven development (BDD) licensed under MIT. It is inspired by JBehave and contains fully integrated JMock based framework which has a very rich and powerful DSL (domain-specific language) which resembles a natural language specification.&lt;br /&gt;
Composed of multiple libraries structured to work together, RSpec provides encapsulated testing via the describe block to specify the behavior of the class and the context for the unit test case.&lt;br /&gt;
&lt;br /&gt;
==== Why RSpec? ====&lt;br /&gt;
RSpec is easy to learn and implement and can be used with other testing tools like Cucumber and Minitest independently. It is extremely powerful for testing states with complicated setup and also helps in tearing down complex code to access the objects required for testing&lt;br /&gt;
RSpec semantics encourage agile thinking and practice and it structures the tests in a more intuitive way.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
===Functions in answers.rb===&lt;br /&gt;
&lt;br /&gt;
'''Function Name : Compute_scores'''&lt;br /&gt;
&lt;br /&gt;
Compute_scores is a function in model answer.rb which gives the average, maximum and minimum scores obtained in a series a responses/assessments. It has two input parameters: List of assessments and questions. The function iterates over each assessment to get the total score of that assessment. If the response or review is invalid, that assessment won’t be considered in the calculation of the score average. After iterating over all assessments, Max score, and Min scores are calculated along with the average score based on the number of valid assessments. Their scores are returned by the function.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
'''Rspec Unit Test : Compute_scores'''&lt;br /&gt;
&lt;br /&gt;
Following scenarios are tested:&lt;br /&gt;
&lt;br /&gt;
* To return scores as nil if the input list of assessments is nil. This is to make sure no Null Pointer exceptions are thrown by the code&lt;br /&gt;
*To return a particular score when a single valid assessment is given as an input.&lt;br /&gt;
*To return a particular score when multiple valid assessments are given as an input. This is to test the looping functionality of the method.&lt;br /&gt;
*To return a particular score when invalid assessments are given as an input. The validity and total scores are returned by a mock and not by the actual functions. This is to make the test cases less rigid so that failure of dependent functions do not disrupt the functionality of interface level tests.&lt;br /&gt;
*To return a particular score when invalid flag is nil. Invalid flag can either be 0,1 or nil. Nil situation is tested to prevent NullPointer Exceptions&lt;br /&gt;
*To check if the method get_total_score is called with the right parameters.&lt;br /&gt;
&lt;br /&gt;
This unit tes uses a stub and returns a mock value.&lt;br /&gt;
&amp;lt;pre&amp;gt;&lt;br /&gt;
Answer.stub(:get_total_score)&lt;br /&gt;
&amp;lt;/pre&amp;gt;&lt;br /&gt;
This is to eliminate tight coupling between compute_scores and get_total_scores. Failure in get_total_scores would'nt break the compute_scores test cases.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
'''Function Name : Get_total_scores'''&lt;br /&gt;
&lt;br /&gt;
This function is called by the Compute_scores method of the answer.rb model to compute the total score of an assessment. The input consists of assessment for which the total score is being calculated and the list of questions being evaluated in the assessment. The method uses questionnaire id from the questions and response id to obtain a score view questionnaire data. This score view is a read-only record. The questionnaire data mainly consists of q1_max_question_score, sum_of_weights and wieghted_score. Before calculating the score, the function performs two crucial tasks. &lt;br /&gt;
*Checks if the answer for a scored question is nil. If it is nil or unanswered, the question will be ignored and not counted towards the score of this response.&lt;br /&gt;
* Calls the subsission_valid function by passing the response record to set the @invalid flag based on the validity of the response.&lt;br /&gt;
The total score is calculated using the below formula&lt;br /&gt;
&lt;br /&gt;
&amp;lt;pre&amp;gt;&lt;br /&gt;
(weighted_score / (sum_of_weights * max_question_score)) * 100&lt;br /&gt;
&amp;lt;/pre&amp;gt;&lt;br /&gt;
&lt;br /&gt;
Any edge cases would return -1 indicating no score&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
'''Rspec Unit Test : Get_total_scores'''&lt;br /&gt;
&lt;br /&gt;
Following scenarios are tested:&lt;br /&gt;
&lt;br /&gt;
*To return an anticipated total score of a single response without any edge cases. Since this function will be called only on one response at a time, there is no need to test for multiple responses at the same time.&lt;br /&gt;
*To return an anticipated total score of a response where nil answer is for a scored question. This is to check if its weight gets removed from the sum_of_weights.&lt;br /&gt;
*To return -1 when the sum of weights becomes 0. This can happen when all the scored questions are unanswered. Return value of -1 is checked at the calling function to ensure if a score is returned or not.&lt;br /&gt;
*To return -1 when weighted_score of questionnaireData is nil&lt;br /&gt;
* To check if submission_valid is called. This method is called to set invalid flag to indicate whether the response entered is valid or not. The validity criteria is explained in the submission_valid? Function.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
This unit test uses two stubs and returns mock results&lt;br /&gt;
&amp;lt;pre&amp;gt;&lt;br /&gt;
ScoreView.stub(:find_by_sql)&lt;br /&gt;
&amp;lt;/pre&amp;gt;&lt;br /&gt;
&amp;lt;pre&amp;gt;&lt;br /&gt;
Answer.stub(:where)&lt;br /&gt;
&amp;lt;/pre&amp;gt;&lt;br /&gt;
This is to reduce the outcome of the test to depend on DB calls. For example, in case the connection to DB fails, this unit test would still pass making it less rigid.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
'''Function Name : submission_valid?'''&lt;br /&gt;
&lt;br /&gt;
This purpose of this function is to verify the validity of a review based on a deadline.  This function obtains a list of AssignmentDueDate objects  in descending order which is then compared against the current time to determine which deadlines are valid and which ones are not. The flag variable is used to represent whether or not a deadline was available in the previous iteration of the loop. If the flag is set to TRUE and the deadline is less than the current date, then latest_review_phase_start_time is set to this deadline. A list of ResubmissionTime objects is also retrieved from the controller. These objects are then compared against the then latest_review_phase_start_time variable to determine a response. &lt;br /&gt;
&lt;br /&gt;
Observations: The current implementation of the function is bugged. It retrieves a list of sorted AssignmentDueDate objects and proceeds to check if this list is empty. However, instead of exiting if the function if the list is empty, it carries on execution and raises an exception on hitting the for loop. &lt;br /&gt;
&lt;br /&gt;
*Checks if a review is valid or not by comparing its date with a list of deadlines.&lt;br /&gt;
*Returns 1 or 0 depending on validity&lt;br /&gt;
*Current implementation is bugged. Throws an exception if no AssignmentDueDate objects are passed, returns nil if any objects are passed.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
'''Rspec Unit Test : submission_valid?'''&lt;br /&gt;
&lt;br /&gt;
Following scenarios are tested:&lt;br /&gt;
&lt;br /&gt;
*Passing valid AssignmentDueDate objects&lt;br /&gt;
*Not passing any AssignmentDueDate objects&lt;br /&gt;
&lt;br /&gt;
When valid AssignmentDueDate objects are passed, stubs are used to create fake AssignmentDueDate Objects and ResubmissionTime objects. These objects are then populated with valid deadline dates and deadline_type values. These values are then supplied when requested by the submission_valid? Function rather than actually calling the function.  The current implementation of this test case expects the program to throw an error when it reaches the for loop. Once this bug is fixed, this test case may be re-written to test a more legitimate test case.&lt;br /&gt;
&lt;br /&gt;
In case an empty list of AssignmentDueDate objects is passed back to the submission_valid?() method. This would cause the function to return nil. When this function is fixed, the following test case may be re-written to test for a more legitimate test-case.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
This unit test uses two stubs and returns mock results&lt;br /&gt;
&amp;lt;pre&amp;gt;&lt;br /&gt;
AssignmentDueDate.stub_chain(:where, :order).and_return(due_date1, due_date2)&lt;br /&gt;
&amp;lt;/pre&amp;gt;&lt;br /&gt;
The above stub returns two AssignmentDueDate objects whenever the where() and order() method are chained on AssignmentDueDate.&lt;br /&gt;
&amp;lt;pre&amp;gt;&lt;br /&gt;
ResubmissionTime.stub_chain(:where, :order).and_return(ResubmissionTime1, ResubmissionTime2)&lt;br /&gt;
&amp;lt;/pre&amp;gt;&lt;br /&gt;
The above stub returns two ResubmissionTime objects whenever the where() and order() method are chained on ResubmissionTime.&lt;br /&gt;
&amp;lt;pre&amp;gt;&lt;br /&gt;
AssignmentDueDate.stub_chain(:where, :order).and_return(nil)&lt;br /&gt;
&amp;lt;/pre&amp;gt;&lt;br /&gt;
This stub is used in the second test case to return nil objects.&lt;br /&gt;
&lt;br /&gt;
the stub_chain method can be used to create stubs where chained methods are expected.&lt;/div&gt;</summary>
		<author><name>Vdatla</name></author>
	</entry>
	<entry>
		<id>https://wiki.expertiza.ncsu.edu/index.php?title=CSC/ECE_517_Fall_2016/E1670._Unit_tests_for_answers.rb&amp;diff=102690</id>
		<title>CSC/ECE 517 Fall 2016/E1670. Unit tests for answers.rb</title>
		<link rel="alternate" type="text/html" href="https://wiki.expertiza.ncsu.edu/index.php?title=CSC/ECE_517_Fall_2016/E1670._Unit_tests_for_answers.rb&amp;diff=102690"/>
		<updated>2016-10-28T05:00:24Z</updated>

		<summary type="html">&lt;p&gt;Vdatla: &lt;/p&gt;
&lt;hr /&gt;
&lt;div&gt;==E1670 . Unit tests for answers.rb==&lt;br /&gt;
&lt;br /&gt;
This wiki page is for the description of changes made under E1670 OSS assignment for Fall 2016, CSC/ECE 517.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
__TOC__&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
===Background===&lt;br /&gt;
&lt;br /&gt;
Expertiza is an Open Source web application developed on Ruby On Rails platform. It is a platform which allows students to take assignments posted by the course instructors. Expertiza allows students to select assignment topics, form teams and submit their work. It also allows them to review other students' submissions and improve their work based on this feedback.&lt;br /&gt;
&lt;br /&gt;
===Project Description===&lt;br /&gt;
&lt;br /&gt;
In Expertiza, each questionnaire contains many questions, those question may have different types (e.g. checkbox, criterion, etc). When a user fills in a rubric, the responses for each question will become an answer record. The responses of rubrics are stored in answers table in DB. The answer.rb is the model for the answers table in DB. Answer.rb model does not have any test cases and the aim of the project is to write fast, effective and flexible unit test cases that offer maximum code coverage.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
===Functions in answers.rb===&lt;br /&gt;
&lt;br /&gt;
'''Function Name : Compute_scores'''&lt;br /&gt;
&lt;br /&gt;
Compute_scores is a function in model answer.rb which gives the average, maximum and minimum scores obtained in a series a responses/assessments. It has two input parameters: List of assessments and questions. The function iterates over each assessment to get the total score of that assessment. If the response or review is invalid, that assessment won’t be considered in the calculation of the score average. After iterating over all assessments, Max score, and Min scores are calculated along with the average score based on the number of valid assessments. Their scores are returned by the function.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
'''Rspec Unit Test : Compute_scores'''&lt;br /&gt;
&lt;br /&gt;
Following scenarios are tested:&lt;br /&gt;
&lt;br /&gt;
* To return scores as nil if the input list of assessments is nil. This is to make sure no Null Pointer exceptions are thrown by the code&lt;br /&gt;
*To return a particular score when a single valid assessment is given as an input.&lt;br /&gt;
*To return a particular score when multiple valid assessments are given as an input. This is to test the looping functionality of the method.&lt;br /&gt;
*To return a particular score when invalid assessments are given as an input. The validity and total scores are returned by a mock and not by the actual functions. This is to make the test cases less rigid so that failure of dependent functions do not disrupt the functionality of interface level tests.&lt;br /&gt;
*To return a particular score when invalid flag is nil. Invalid flag can either be 0,1 or nil. Nil situation is tested to prevent NullPointer Exceptions&lt;br /&gt;
*To check if the method get_total_score is called with the right parameters.&lt;br /&gt;
&lt;br /&gt;
This unit tes uses a stub and returns a mock value.&lt;br /&gt;
&amp;lt;pre&amp;gt;&lt;br /&gt;
Answer.stub(:get_total_score)&lt;br /&gt;
&amp;lt;/pre&amp;gt;&lt;br /&gt;
This is to eliminate tight coupling between compute_scores and get_total_scores. Failure in get_total_scores would'nt break the compute_scores test cases.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
'''Function Name : Get_total_scores'''&lt;br /&gt;
&lt;br /&gt;
This function is called by the Compute_scores method of the answer.rb model to compute the total score of an assessment. The input consists of assessment for which the total score is being calculated and the list of questions being evaluated in the assessment. The method uses questionnaire id from the questions and response id to obtain a score view questionnaire data. This score view is a read-only record. The questionnaire data mainly consists of q1_max_question_score, sum_of_weights and wieghted_score. Before calculating the score, the function performs two crucial tasks. &lt;br /&gt;
*Checks if the answer for a scored question is nil. If it is nil or unanswered, the question will be ignored and not counted towards the score of this response.&lt;br /&gt;
* Calls the subsission_valid function by passing the response record to set the @invalid flag based on the validity of the response.&lt;br /&gt;
The total score is calculated using the below formula&lt;br /&gt;
&lt;br /&gt;
&amp;lt;pre&amp;gt;&lt;br /&gt;
(weighted_score / (sum_of_weights * max_question_score)) * 100&lt;br /&gt;
&amp;lt;/pre&amp;gt;&lt;br /&gt;
&lt;br /&gt;
Any edge cases would return -1 indicating no score&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
'''Rspec Unit Test : Get_total_scores'''&lt;br /&gt;
&lt;br /&gt;
Following scenarios are tested:&lt;br /&gt;
&lt;br /&gt;
*To return an anticipated total score of a single response without any edge cases. Since this function will be called only on one response at a time, there is no need to test for multiple responses at the same time.&lt;br /&gt;
*To return an anticipated total score of a response where nil answer is for a scored question. This is to check if its weight gets removed from the sum_of_weights.&lt;br /&gt;
*To return -1 when the sum of weights becomes 0. This can happen when all the scored questions are unanswered. Return value of -1 is checked at the calling function to ensure if a score is returned or not.&lt;br /&gt;
*To return -1 when weighted_score of questionnaireData is nil&lt;br /&gt;
* To check if submission_valid is called. This method is called to set invalid flag to indicate whether the response entered is valid or not. The validity criteria is explained in the submission_valid? Function.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
This unit test uses two stubs and returns mock results&lt;br /&gt;
&amp;lt;pre&amp;gt;&lt;br /&gt;
ScoreView.stub(:find_by_sql)&lt;br /&gt;
&amp;lt;/pre&amp;gt;&lt;br /&gt;
&amp;lt;pre&amp;gt;&lt;br /&gt;
Answer.stub(:where)&lt;br /&gt;
&amp;lt;/pre&amp;gt;&lt;br /&gt;
This is to reduce the outcome of the test to depend on DB calls. For example, in case the connection to DB fails, this unit test would still pass making it less rigid.&lt;/div&gt;</summary>
		<author><name>Vdatla</name></author>
	</entry>
	<entry>
		<id>https://wiki.expertiza.ncsu.edu/index.php?title=CSC/ECE_517_Fall_2016/E1670._Unit_tests_for_answers.rb&amp;diff=102685</id>
		<title>CSC/ECE 517 Fall 2016/E1670. Unit tests for answers.rb</title>
		<link rel="alternate" type="text/html" href="https://wiki.expertiza.ncsu.edu/index.php?title=CSC/ECE_517_Fall_2016/E1670._Unit_tests_for_answers.rb&amp;diff=102685"/>
		<updated>2016-10-28T04:59:45Z</updated>

		<summary type="html">&lt;p&gt;Vdatla: &lt;/p&gt;
&lt;hr /&gt;
&lt;div&gt;==E1670 . Unit tests for answers.rb==&lt;br /&gt;
&lt;br /&gt;
This wiki page is for the description of changes made under E1670 OSS assignment for Fall 2016, CSC/ECE 517.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
__TOC__&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
===Background===&lt;br /&gt;
&lt;br /&gt;
Expertiza is an Open Source web application developed on Ruby On Rails platform. It is a platform which allows students to take assignments posted by the course instructors. Expertiza allows students to select assignment topics, form teams and submit their work. It also allows them to review other students' submissions and improve their work based on this feedback.&lt;br /&gt;
&lt;br /&gt;
===Project Description===&lt;br /&gt;
&lt;br /&gt;
In Expertiza, each questionnaire contains many questions, those question may have different types (e.g. checkbox, criterion, etc). When a user fills in a rubric, the responses for each question will become an answer record. The responses of rubrics are stored in answers table in DB. The answer.rb is the model for the answers table in DB. Answer.rb model does not have any test cases and the aim of the project is to write fast, effective and flexible unit test cases that offer maximum code coverage.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
===Functions in answers.rb===&lt;br /&gt;
&lt;br /&gt;
'''Function Name : Compute_scores'''&lt;br /&gt;
&lt;br /&gt;
Compute_scores is a function in model answer.rb which gives the average, maximum and minimum scores obtained in a series a responses/assessments. It has two input parameters: List of assessments and questions. The function iterates over each assessment to get the total score of that assessment. If the response or review is invalid, that assessment won’t be considered in the calculation of the score average. After iterating over all assessments, Max score, and Min scores are calculated along with the average score based on the number of valid assessments. Their scores are returned by the function.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
'''Rspec Unit Test : Compute_scores'''&lt;br /&gt;
&lt;br /&gt;
Following scenarios are tested:&lt;br /&gt;
&lt;br /&gt;
* To return scores as nil if the input list of assessments is nil. This is to make sure no Null Pointer exceptions are thrown by the code&lt;br /&gt;
*To return a particular score when a single valid assessment is given as an input.&lt;br /&gt;
*To return a particular score when multiple valid assessments are given as an input. This is to test the looping functionality of the method.&lt;br /&gt;
*To return a particular score when invalid assessments are given as an input. The validity and total scores are returned by a mock and not by the actual functions. This is to make the test cases less rigid so that failure of dependent functions do not disrupt the functionality of interface level tests.&lt;br /&gt;
*To return a particular score when invalid flag is nil. Invalid flag can either be 0,1 or nil. Nil situation is tested to prevent NullPointer Exceptions&lt;br /&gt;
*To check if the method get_total_score is called with the right parameters.&lt;br /&gt;
&lt;br /&gt;
This unit tes uses a stub and returns a mock value.&lt;br /&gt;
&amp;lt;pre&amp;gt;&lt;br /&gt;
Answer.stub(:get_total_score)&lt;br /&gt;
&amp;lt;/pre&amp;gt;&lt;br /&gt;
This is to eliminate tight coupling between compute_scores and get_total_scores. Failure in get_total_scores would'nt break the compute_scores test cases.&lt;br /&gt;
&lt;br /&gt;
'''Function Name : Get_total_scores'''&lt;br /&gt;
&lt;br /&gt;
This function is called by the Compute_scores method of the answer.rb model to compute the total score of an assessment. The input consists of assessment for which the total score is being calculated and the list of questions being evaluated in the assessment. The method uses questionnaire id from the questions and response id to obtain a score view questionnaire data. This score view is a read-only record. The questionnaire data mainly consists of q1_max_question_score, sum_of_weights and wieghted_score. Before calculating the score, the function performs two crucial tasks. &lt;br /&gt;
*Checks if the answer for a scored question is nil. If it is nil or unanswered, the question will be ignored and not counted towards the score of this response.&lt;br /&gt;
* Calls the subsission_valid function by passing the response record to set the @invalid flag based on the validity of the response.&lt;br /&gt;
The total score is calculated using the below formula&lt;br /&gt;
&lt;br /&gt;
&amp;lt;pre&amp;gt;&lt;br /&gt;
(weighted_score / (sum_of_weights * max_question_score)) * 100&lt;br /&gt;
&amp;lt;/pre&amp;gt;&lt;br /&gt;
&lt;br /&gt;
Any edge cases would return -1 indicating no score&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
'''Rspec Unit Test : Get_total_scores'''&lt;br /&gt;
&lt;br /&gt;
Following scenarios are tested:&lt;br /&gt;
&lt;br /&gt;
*To return an anticipated total score of a single response without any edge cases. Since this function will be called only on one response at a time, there is no need to test for multiple responses at the same time.&lt;br /&gt;
*To return an anticipated total score of a response where nil answer is for a scored question. This is to check if its weight gets removed from the sum_of_weights.&lt;br /&gt;
*To return -1 when the sum of weights becomes 0. This can happen when all the scored questions are unanswered. Return value of -1 is checked at the calling function to ensure if a score is returned or not.&lt;br /&gt;
*To return -1 when weighted_score of questionnaireData is nil&lt;br /&gt;
* To check if submission_valid is called. This method is called to set invalid flag to indicate whether the response entered is valid or not. The validity criteria is explained in the submission_valid? Function.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
This unit test uses two stubs and returns mock results&lt;br /&gt;
&amp;lt;pre&amp;gt;&lt;br /&gt;
ScoreView.stub(:find_by_sql)&lt;br /&gt;
&amp;lt;/pre&amp;gt;&lt;br /&gt;
&amp;lt;pre&amp;gt;&lt;br /&gt;
Answer.stub(:where)&lt;br /&gt;
&amp;lt;/pre&amp;gt;&lt;br /&gt;
This is to reduce the outcome of the test to depend on DB calls. For example, in case the connection to DB fails, this unit test would still pass making it less rigid.&lt;/div&gt;</summary>
		<author><name>Vdatla</name></author>
	</entry>
	<entry>
		<id>https://wiki.expertiza.ncsu.edu/index.php?title=CSC/ECE_517_Fall_2016/E1670._Unit_tests_for_answers.rb&amp;diff=102677</id>
		<title>CSC/ECE 517 Fall 2016/E1670. Unit tests for answers.rb</title>
		<link rel="alternate" type="text/html" href="https://wiki.expertiza.ncsu.edu/index.php?title=CSC/ECE_517_Fall_2016/E1670._Unit_tests_for_answers.rb&amp;diff=102677"/>
		<updated>2016-10-28T04:53:09Z</updated>

		<summary type="html">&lt;p&gt;Vdatla: &lt;/p&gt;
&lt;hr /&gt;
&lt;div&gt;==E1670 . Unit tests for answers.rb==&lt;br /&gt;
&lt;br /&gt;
This wiki page is for the description of changes made under E1670 OSS assignment for Fall 2016, CSC/ECE 517.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
__TOC__&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
===Background===&lt;br /&gt;
&lt;br /&gt;
Expertiza is an Open Source web application developed on Ruby On Rails platform. It is a platform which allows students to take assignments posted by the course instructors. Expertiza allows students to select assignment topics, form teams and submit their work. It also allows them to review other students' submissions and improve their work based on this feedback.&lt;br /&gt;
&lt;br /&gt;
===Project Description===&lt;br /&gt;
&lt;br /&gt;
In Expertiza, each questionnaire contains many questions, those question may have different types (e.g. checkbox, criterion, etc). When a user fills in a rubric, the responses for each question will become an answer record. The responses of rubrics are stored in answers table in DB. The answer.rb is the model for the answers table in DB. Answer.rb model does not have any test cases and the aim of the project is to write fast, effective and flexible unit test cases that offer maximum code coverage.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
===Functions in answers.rb===&lt;br /&gt;
&lt;br /&gt;
'''Function Name : Compute_scores'''&lt;br /&gt;
&lt;br /&gt;
Compute_scores is a function in model answer.rb which gives the average, maximum and minimum scores obtained in a series a responses/assessments. It has two input parameters: List of assessments and questions. The function iterates over each assessment to get the total score of that assessment. If the response or review is invalid, that assessment won’t be considered in the calculation of the score average. After iterating over all assessments, Max score, and Min scores are calculated along with the average score based on the number of valid assessments. Their scores are returned by the function.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
'''Rspec Unit Test : Compute_scores'''&lt;br /&gt;
&lt;br /&gt;
Following scenarios are tested:&lt;br /&gt;
&lt;br /&gt;
* To return scores as nil if the input list of assessments is nil. This is to make sure no Null Pointer exceptions are thrown by the code&lt;br /&gt;
*To return a particular score when a single valid assessment is given as an input.&lt;br /&gt;
*To return a particular score when multiple valid assessments are given as an input. This is to test the looping functionality of the method.&lt;br /&gt;
*To return a particular score when invalid assessments are given as an input. The validity and total scores are returned by a mock and not by the actual functions. This is to make the test cases less rigid so that failure of dependent functions do not disrupt the functionality of interface level tests.&lt;br /&gt;
*To return a particular score when invalid flag is nil. Invalid flag can either be 0,1 or nil. Nil situation is tested to prevent NullPointer Exceptions&lt;br /&gt;
*To check if the method get_total_score is called with the right parameters.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
'''Function Name : Get_total_scores'''&lt;br /&gt;
&lt;br /&gt;
This function is called by the Compute_scores method of the answer.rb model to compute the total score of an assessment. The input consists of assessment for which the total score is being calculated and the list of questions being evaluated in the assessment. The method uses questionnaire id from the questions and response id to obtain a score view questionnaire data. This score view is a read-only record. The questionaire data mainly consists of q1_max_question_score, sum_of_weights and wieghted_score. Before calculating the score, the function performs two crucial tasks. &lt;br /&gt;
*Checks if the answer for a scored question is nil. If it is nil or unanswered, the the question will be ignored and not counted towards the score of this response.&lt;br /&gt;
* Calls the subsission_valid function by passing the response record to set the @invalid flag based on the validity of the response.&lt;br /&gt;
The total score is calculated using the below formula&lt;br /&gt;
&lt;br /&gt;
&amp;lt;pre&amp;gt;&lt;br /&gt;
(weighted_score / (sum_of_weights * max_question_score)) * 100&lt;br /&gt;
&amp;lt;/pre&amp;gt;&lt;br /&gt;
&lt;br /&gt;
Any edge cases would return -1 indicating no score&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
'''Rspec Unit Test : Get_total_scores'''&lt;br /&gt;
&lt;br /&gt;
Following scenarios are tested:&lt;br /&gt;
&lt;br /&gt;
*To return an anticipated total score of a single response without any edge cases. Since this function will be called only on one response at a time, there is no need to test for multiple responses at the same time.&lt;br /&gt;
*To return an anticipated total score of a response where nil answer is for a scored question. This is to check if its weight gets removed from the sum_of_weights.&lt;br /&gt;
*To return -1 when the sum of weights becomes 0. This can happen when all the scored questions are unanswered.Value of -1 is checked at the calling function to ensure if a score is returned or not.&lt;br /&gt;
*To return -1 when weighted_score of questionnaireData is nil&lt;br /&gt;
* To check if submission_valid is called. This method is called to set invalid flag to indicate whether the response entered is valid or not. The validity criteria is explained in the submission_valid? Function.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
This unit test uses two stubs and returns mock results&lt;br /&gt;
&amp;lt;pre&amp;gt;&lt;br /&gt;
ScoreView.stub(:find_by_sql)&lt;br /&gt;
&amp;lt;/pre&amp;gt;&lt;br /&gt;
&amp;lt;pre&amp;gt;&lt;br /&gt;
Answer.stub(:where)&lt;br /&gt;
&amp;lt;/pre&amp;gt;&lt;br /&gt;
This is to reduce the outcome of the test to depend on DB calls. For example, in case the connection to DB fails, this unit test would still pass making it less rigid.&lt;/div&gt;</summary>
		<author><name>Vdatla</name></author>
	</entry>
	<entry>
		<id>https://wiki.expertiza.ncsu.edu/index.php?title=CSC/ECE_517_Fall_2016/E1670._Unit_tests_for_answers.rb&amp;diff=102676</id>
		<title>CSC/ECE 517 Fall 2016/E1670. Unit tests for answers.rb</title>
		<link rel="alternate" type="text/html" href="https://wiki.expertiza.ncsu.edu/index.php?title=CSC/ECE_517_Fall_2016/E1670._Unit_tests_for_answers.rb&amp;diff=102676"/>
		<updated>2016-10-28T04:52:31Z</updated>

		<summary type="html">&lt;p&gt;Vdatla: &lt;/p&gt;
&lt;hr /&gt;
&lt;div&gt;==E1670 . Unit tests for answers.rb==&lt;br /&gt;
&lt;br /&gt;
This wiki page is for the description of changes made under E1670 OSS assignment for Fall 2016, CSC/ECE 517.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
__TOC__&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
===Background===&lt;br /&gt;
&lt;br /&gt;
Expertiza is an Open Source web application developed on Ruby On Rails platform. It is a platform which allows students to take assignments posted by the course instructors. Expertiza allows students to select assignment topics, form teams and submit their work. It also allows them to review other students' submissions and improve their work based on this feedback.&lt;br /&gt;
&lt;br /&gt;
===Project Description===&lt;br /&gt;
&lt;br /&gt;
In Expertiza, each questionnaire contains many questions, those question may have different types (e.g. checkbox, criterion, etc). When a user fills in a rubric, the responses for each question will become an answer record. The responses of rubrics are stored in answers table in DB. The answer.rb is the model for the answers table in DB. Answer.rb model does not have any test cases and the aim of the project is to write fast, effective and flexible unit test cases that offer maximum code coverage.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
===Functions in answers.rb===&lt;br /&gt;
&lt;br /&gt;
'''Function Name : Compute_scores'''&lt;br /&gt;
&lt;br /&gt;
Compute_scores is a function in model answer.rb which gives the average, maximum and minimum scores obtained in a series a responses/assessments. It has two input parameters: List of assessments and questions. The function iterates over each assessment to get the total score of that assessment. If the response or review is invalid, that assessment won’t be considered in the calculation of the score average. After iterating over all assessments, Max score, and Min scores are calculated along with the average score based on the number of valid assessments. Their scores are returned by the function.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
'''Rspec Unit Test : Compute_scores'''&lt;br /&gt;
&lt;br /&gt;
Following scenarios are tested:&lt;br /&gt;
&lt;br /&gt;
* To return scores as nil if the input list of assessments is nil. This is to make sure no Null Pointer exceptions are thrown by the code&lt;br /&gt;
*To return a particular score when a single valid assessment is given as an input.&lt;br /&gt;
*To return a particular score when multiple valid assessments are given as an input. This is to test the looping functionality of the method.&lt;br /&gt;
*To return a particular score when invalid assessments are given as an input. The validity and total scores are returned by a mock and not by the actual functions. This is to make the test cases less rigid so that failure of dependent functions do not disrupt the functionality of interface level tests.&lt;br /&gt;
*To return a particular score when invalid flag is nil. Invalid flag can either be 0,1 or nil. Nil situation is tested to prevent NullPointer Exceptions&lt;br /&gt;
*To check if the method get_total_score is called with the right parameters.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
'''Function Name : Get_total_scores'''&lt;br /&gt;
&lt;br /&gt;
This function is called by the Compute_scores method of the answer.rb model to compute the total score of an assessment. The input consists of assessment for which the total score is being calculated and the list of questions being evaluated in the assessment. The method uses questionnaire id from the questions and response id to obtain a score view questionnaire data. This score view is a read-only record. The questionaire data mainly consists of q1_max_question_score, sum_of_weights and wieghted_score. Before calculating the score, the function performs two crucial tasks. &lt;br /&gt;
*Checks if the answer for a scored question is nil. If it is nil or unanswered, the the question will be ignored and not counted towards the score of this response.&lt;br /&gt;
* Calls the subsission_valid function by passing the response record to set the @invalid flag based on the validity of the response.&lt;br /&gt;
The total score is calculated using the below formula&lt;br /&gt;
&lt;br /&gt;
&amp;lt;pre&amp;gt;&lt;br /&gt;
(weighted_score / (sum_of_weights * max_question_score)) * 100&lt;br /&gt;
&amp;lt;/pre&amp;gt;&lt;br /&gt;
&lt;br /&gt;
Any edge cases would return -1 indicating no score&lt;br /&gt;
&lt;br /&gt;
'''Rspec Unit Test : Get_total_scores'''&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
Following scenarios are tested:&lt;br /&gt;
&lt;br /&gt;
*To return an anticipated total score of a single response without any edge cases. Since this function will be called only on one response at a time, there is no need to test for multiple responses at the same time.&lt;br /&gt;
*To return an anticipated total score of a response where nil answer is for a scored question. This is to check if its weight gets removed from the sum_of_weights.&lt;br /&gt;
*To return -1 when the sum of weights becomes 0. This can happen when all the scored questions are unanswered.Value of -1 is checked at the calling function to ensure if a score is returned or not.&lt;br /&gt;
*To return -1 when weighted_score of questionnaireData is nil&lt;br /&gt;
* To check if submission_valid is called. This method is called to set invalid flag to indicate whether the response entered is valid or not. The validity criteria is explained in the submission_valid? Function.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
This unit test uses two stubs and returns mock results&lt;br /&gt;
&amp;lt;pre&amp;gt;&lt;br /&gt;
ScoreView.stub(:find_by_sql)&lt;br /&gt;
&amp;lt;/pre&amp;gt;&lt;br /&gt;
&amp;lt;pre&amp;gt;&lt;br /&gt;
Answer.stub(:where)&lt;br /&gt;
&amp;lt;/pre&amp;gt;&lt;br /&gt;
This is to reduce the outcome of the test to depend on DB calls. For example, in case the connection to DB fails, this unit test would still pass making it less rigid.&lt;/div&gt;</summary>
		<author><name>Vdatla</name></author>
	</entry>
	<entry>
		<id>https://wiki.expertiza.ncsu.edu/index.php?title=CSC/ECE_517_Fall_2016/E1670._Unit_tests_for_answers.rb&amp;diff=102649</id>
		<title>CSC/ECE 517 Fall 2016/E1670. Unit tests for answers.rb</title>
		<link rel="alternate" type="text/html" href="https://wiki.expertiza.ncsu.edu/index.php?title=CSC/ECE_517_Fall_2016/E1670._Unit_tests_for_answers.rb&amp;diff=102649"/>
		<updated>2016-10-28T03:48:43Z</updated>

		<summary type="html">&lt;p&gt;Vdatla: /* Functions in answers.rb */&lt;/p&gt;
&lt;hr /&gt;
&lt;div&gt;==E1670 . Unit tests for answers.rb==&lt;br /&gt;
&lt;br /&gt;
This wiki page is for the description of changes made under E1670 OSS assignment for Fall 2016, CSC/ECE 517.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
__TOC__&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
===Background===&lt;br /&gt;
&lt;br /&gt;
Expertiza is an Open Source web application developed on Ruby On Rails platform. It is a platform which allows students to take assignments posted by the course instructors. Expertiza allows students to select assignment topics, form teams and submit their work. It also allows them to review other students' submissions and improve their work based on this feedback.&lt;br /&gt;
&lt;br /&gt;
===Project Description===&lt;br /&gt;
&lt;br /&gt;
In Expertiza, each questionnaire contains many questions, those question may have different types (e.g. checkbox, criterion, etc). When a user fills in a rubric, the responses for each question will become an answer record. The responses of rubrics are stored in answers table in DB. The answer.rb is the model for the answers table in DB. Answer.rb model does not have any test cases and the aim of the project is to write fast, effective and flexible unit test cases that offer maximum code coverage.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
===Functions in answers.rb===&lt;br /&gt;
&lt;br /&gt;
'''Function Name : Compute_scores'''&lt;br /&gt;
&lt;br /&gt;
Compute_scores is a function in model answer.rb which gives the average, maximum and minimum scores obtained in a series a responses/assessments. It has two input parameters: List of assessments and questions. The function iterates over each assessment to get the total score of that assessment. If the response or review is invalid, that assessment won’t be considered in the calculation of the score average. After iterating over all assessments, Max score, and Min scores are calculated along with the average score based on the number of valid assessments. Their scores are returned by the function.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
'''Rspec Unit Test : Compute_scores'''&lt;br /&gt;
&lt;br /&gt;
Following scenarios are tested:&lt;br /&gt;
&lt;br /&gt;
* To return scores as nil if the input list of assessments is nil. This is to make sure no Null Pointer exceptions are thrown by the code&lt;br /&gt;
*To return a particular score when a single valid assessment is given as an input.&lt;br /&gt;
*To return a particular score when multiple valid assessments are given as an input. This is to test the looping functionality of the method.&lt;br /&gt;
*To return a particular score when invalid assessments are given as an input. The validity and total scores are returned by a mock and not by the actual functions. This is to make the test cases less rigid so that failure of dependent functions do not disrupt the functionality of interface level tests.&lt;br /&gt;
*To return a particular score when invalid flag is nil. Invalid flag can either be 0,1 or nil. Nil situation is tested to prevent NullPointer Exceptions&lt;br /&gt;
*To check if the method get_total_score is called with the right parameters.&lt;/div&gt;</summary>
		<author><name>Vdatla</name></author>
	</entry>
	<entry>
		<id>https://wiki.expertiza.ncsu.edu/index.php?title=CSC/ECE_517_Fall_2016/E1670._Unit_tests_for_answers.rb&amp;diff=102648</id>
		<title>CSC/ECE 517 Fall 2016/E1670. Unit tests for answers.rb</title>
		<link rel="alternate" type="text/html" href="https://wiki.expertiza.ncsu.edu/index.php?title=CSC/ECE_517_Fall_2016/E1670._Unit_tests_for_answers.rb&amp;diff=102648"/>
		<updated>2016-10-28T03:48:02Z</updated>

		<summary type="html">&lt;p&gt;Vdatla: &lt;/p&gt;
&lt;hr /&gt;
&lt;div&gt;==E1670 . Unit tests for answers.rb==&lt;br /&gt;
&lt;br /&gt;
This wiki page is for the description of changes made under E1670 OSS assignment for Fall 2016, CSC/ECE 517.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
__TOC__&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
===Background===&lt;br /&gt;
&lt;br /&gt;
Expertiza is an Open Source web application developed on Ruby On Rails platform. It is a platform which allows students to take assignments posted by the course instructors. Expertiza allows students to select assignment topics, form teams and submit their work. It also allows them to review other students' submissions and improve their work based on this feedback.&lt;br /&gt;
&lt;br /&gt;
===Project Description===&lt;br /&gt;
&lt;br /&gt;
In Expertiza, each questionnaire contains many questions, those question may have different types (e.g. checkbox, criterion, etc). When a user fills in a rubric, the responses for each question will become an answer record. The responses of rubrics are stored in answers table in DB. The answer.rb is the model for the answers table in DB. Answer.rb model does not have any test cases and the aim of the project is to write fast, effective and flexible unit test cases that offer maximum code coverage.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
===Functions in answers.rb===&lt;br /&gt;
&lt;br /&gt;
'''Function Name : Compute_scores'''&lt;br /&gt;
&lt;br /&gt;
Compute_scores is a function in model answer.rb which gives the average, maximum and minimum scores obtained in a series a responses/assessments. It has two input parameters: List of assessments and questions. The function iterates over each assessment to get the total score of that assessment. If the response or review is invalid, that assessment won’t be considered in the calculation of the score average. After iterating over all assessments, Max score, and Min scores are calculated along with the average score based on the number of valid assessments. Their scores are returned by the function.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
'''Rspec Unit Test : Compute_scores'''&lt;br /&gt;
&lt;br /&gt;
Following scenarios were tested:&lt;br /&gt;
&lt;br /&gt;
* To return scores as nil if the input list of assessments is nil. This is to make sure no Null Pointer exceptions are thrown by the code&lt;br /&gt;
*To return a particular score when a single valid assessment is given as an input.&lt;br /&gt;
*To return a particular score when multiple valid assessments are given as an input. This is to test the looping functionality of the method.&lt;br /&gt;
*To return a particular score when invalid assessments are given as an input. The validity and total scores are returned by a mock and not by the actual functions. This is to make the test cases less rigid so that failure of dependent functions do not disrupt the functionality of interface level tests.&lt;br /&gt;
*To return a particular score when invalid flag is nil. Invalid flag can either be 0,1 or nil. Nil situation is tested to prevent NullPointer Exceptions&lt;br /&gt;
*To check if the method get_total_score is called with the right parameters.&lt;/div&gt;</summary>
		<author><name>Vdatla</name></author>
	</entry>
	<entry>
		<id>https://wiki.expertiza.ncsu.edu/index.php?title=CSC/ECE_517_Fall_2016/E1670._Unit_tests_for_answers.rb&amp;diff=102516</id>
		<title>CSC/ECE 517 Fall 2016/E1670. Unit tests for answers.rb</title>
		<link rel="alternate" type="text/html" href="https://wiki.expertiza.ncsu.edu/index.php?title=CSC/ECE_517_Fall_2016/E1670._Unit_tests_for_answers.rb&amp;diff=102516"/>
		<updated>2016-10-27T17:45:09Z</updated>

		<summary type="html">&lt;p&gt;Vdatla: &lt;/p&gt;
&lt;hr /&gt;
&lt;div&gt;==E1670 . Unit tests for answers.rb==&lt;br /&gt;
&lt;br /&gt;
This wiki page is for the description of changes made under E1670 OSS assignment for Fall 2016, CSC/ECE 517.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
__TOC__&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
===Background===&lt;br /&gt;
&lt;br /&gt;
Expertiza is an Open Source web application developed on Ruby On Rails platform. It is a platform which allows students to take assignments posted by the course instructors. Expertiza allows students to select assignment topics, form teams and submit their work. It also allows them to review other students' submissions and improve their work based on this feedback.&lt;br /&gt;
&lt;br /&gt;
===Project Description===&lt;br /&gt;
&lt;br /&gt;
In Expertiza, each questionnaire contains many questions, those question may have different types (e.g. checkbox, criterion, etc). When a user fills in a rubric, the responses for each question will become an answer record. The responses of rubrics are stored in answers table in DB. The answer.rb is the model for the answers table  in DB. Answer.rb model does not have any test cases and the aim of the project is to write fast, effective and flexible unit test cases that offer maximum code coverage.&lt;/div&gt;</summary>
		<author><name>Vdatla</name></author>
	</entry>
	<entry>
		<id>https://wiki.expertiza.ncsu.edu/index.php?title=CSC/ECE_517_Fall_2016/E1670._Unit_tests_for_answers.rb&amp;diff=102515</id>
		<title>CSC/ECE 517 Fall 2016/E1670. Unit tests for answers.rb</title>
		<link rel="alternate" type="text/html" href="https://wiki.expertiza.ncsu.edu/index.php?title=CSC/ECE_517_Fall_2016/E1670._Unit_tests_for_answers.rb&amp;diff=102515"/>
		<updated>2016-10-27T16:55:48Z</updated>

		<summary type="html">&lt;p&gt;Vdatla: &lt;/p&gt;
&lt;hr /&gt;
&lt;div&gt;==E1670 . Unit tests for answers.rb==&lt;br /&gt;
&lt;br /&gt;
This wiki page is for the description of changes made under E1670 OSS assignment for Fall 2016, CSC/ECE 517.&lt;/div&gt;</summary>
		<author><name>Vdatla</name></author>
	</entry>
	<entry>
		<id>https://wiki.expertiza.ncsu.edu/index.php?title=CSC/ECE_517_Fall_2016/E1670._Unit_tests_for_answers.rb&amp;diff=102514</id>
		<title>CSC/ECE 517 Fall 2016/E1670. Unit tests for answers.rb</title>
		<link rel="alternate" type="text/html" href="https://wiki.expertiza.ncsu.edu/index.php?title=CSC/ECE_517_Fall_2016/E1670._Unit_tests_for_answers.rb&amp;diff=102514"/>
		<updated>2016-10-27T16:54:23Z</updated>

		<summary type="html">&lt;p&gt;Vdatla: This wiki page is for the description of changes made under E1670 OSS assignment for Fall 2016, CSC/ECE 517.&lt;/p&gt;
&lt;hr /&gt;
&lt;div&gt;This wiki page is for the description of changes made under E1670 OSS assignment for Fall 2016, CSC/ECE 517.&lt;/div&gt;</summary>
		<author><name>Vdatla</name></author>
	</entry>
</feed>