<?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=Penaman</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=Penaman"/>
	<link rel="alternate" type="text/html" href="https://wiki.expertiza.ncsu.edu/index.php?title=Special:Contributions/Penaman"/>
	<updated>2026-07-21T19:41:42Z</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_2022_-_E2277._Further_Refactoring_questionnaires_controller.rb&amp;diff=147206</id>
		<title>CSC/ECE 517 Fall 2022 - E2277. Further Refactoring questionnaires controller.rb</title>
		<link rel="alternate" type="text/html" href="https://wiki.expertiza.ncsu.edu/index.php?title=CSC/ECE_517_Fall_2022_-_E2277._Further_Refactoring_questionnaires_controller.rb&amp;diff=147206"/>
		<updated>2022-12-06T03:06:55Z</updated>

		<summary type="html">&lt;p&gt;Penaman: &lt;/p&gt;
&lt;hr /&gt;
&lt;div&gt;==Introduction==&lt;br /&gt;
This page gives a description of the changes made related to the CRUD operations related to the questionnaire of the Expertiza-based OSS project.&lt;br /&gt;
&lt;br /&gt;
===Expertiza Background ===&lt;br /&gt;
Expertiza is a web application where students can submit and peer-review learning objects (articles, codes, websites, etc). Instructors add and grade the assignments submitted by students to Expertiza. Students can be assigned in teams based on their selection of the topics. It has functionalities such as peer reviews in which students can provide feedback on others' work which helps peer in better developing the project. The National Science Foundation supports it.&lt;br /&gt;
&lt;br /&gt;
== Problems Encountered ==&lt;br /&gt;
&lt;br /&gt;
This project builds on E2257.  That project focused only on simplifying the methods in questionnaires_controller, while this project's objective is wider. It involves looking at any code related to the questionnaire and performing bug fixes, refactoring and cleanup. This code also introduces the changes made in E2257, as PR related to that required some changes to be made before merging. This was done as some of the current changes build upon changes made in the previous round.&lt;br /&gt;
&lt;br /&gt;
&amp;lt;b&amp;gt; Suggestion provided in the documentation of the problem &amp;lt;/b&amp;gt; &lt;br /&gt;
* Use of temporary variables instead of instance variables wherever possible to narrow their scope.&lt;br /&gt;
* question.rb contains a large number of constants. Make explicit comments on their usage, and remove them if not used.&lt;br /&gt;
* Since a controller should only create objects of one type the questions_controller could be introduced to create and edit questions moving the logic of dealing with individual questions into a separate controller and improving the separation of responsibility.&lt;br /&gt;
&lt;br /&gt;
&amp;lt;b&amp;gt; What we have considered &amp;lt;/b&amp;gt;&lt;br /&gt;
*Checked the flow of the code, by adding comments to figure out unused functions.&lt;br /&gt;
*Check for unused constants.&lt;br /&gt;
*Checked code climate issues found.&lt;br /&gt;
*Found bugs where expected behaviour wasn't happening.&lt;br /&gt;
&lt;br /&gt;
Since this is an important piece of code with usage at a lot of places we had to be very careful with making changes. We were able to fix most of the bugs and issues we found, but there still exist a few that we didn't have enough time to fix. These have been added to future work so that it can be easier for anyone who picks up the project.&lt;br /&gt;
&lt;br /&gt;
&amp;lt;b&amp;gt; The issues we have handled are as follows: &amp;lt;/b&amp;gt;&lt;br /&gt;
*Presence of many unused functions in the questionnaire questionnaire_controller.rb&lt;br /&gt;
*Presence of many unused constants in the model questions.rb&lt;br /&gt;
*Unable to update questionnaire parameters.&lt;br /&gt;
*Error in the logic used to assign sequence numbers to questions in a questionnaire.&lt;br /&gt;
*High severity issue in the way questionnaire and question objects are created (Code Climate)&lt;br /&gt;
*Updates made to issues fixed in E2257&lt;br /&gt;
&lt;br /&gt;
==Files Changed==&lt;br /&gt;
&lt;br /&gt;
*app/controllers/questionnaires_controller.rb&lt;br /&gt;
*app/models/question.rb&lt;br /&gt;
*app/helpers/questionnaire_helper.rb&lt;br /&gt;
*app/views/questionnaires/_questionnaire.html.erb&lt;br /&gt;
*spec/controllers/questionnaires_controller_spec.rb&lt;br /&gt;
&lt;br /&gt;
== Files Added ==&lt;br /&gt;
*app/helpers/question_helper.rb&lt;br /&gt;
&lt;br /&gt;
==Implementation==&lt;br /&gt;
&lt;br /&gt;
* Creating an object of the required questionnaire type is currently performed using Object.const_get, based on user input values. This is a very bad approach (Severity: Critical) according to CodeClimate reports, thus we aim to look at alternative approaches to create an object of the required questionnaire type using Factory Design pattern.&lt;br /&gt;
* As discussed before try to move the save functionality out of questionnaire_controller, and into questions_controller. Call it from there where ever needed.&lt;br /&gt;
* The questionnaire apparently has a lot of items and not just questions, thus try to rename the usages of questions to items.&lt;br /&gt;
* The code has been cleaned many times and functionalities have been moved around a lot, which has made the code messy with a lot of dead code. Have a closer look at each functionality and flow, add comments to each of them (eg. create_node) and remove unnecessary code (eg. many constants).&lt;br /&gt;
===Flowchart===&lt;br /&gt;
&lt;br /&gt;
The following will be the process carried out to move the save functionality from questionnaires_controller into questions_controller. But we will also be be using it on every other functionality in both the controllers just to make sure they are at the right places.&lt;br /&gt;
&lt;br /&gt;
[[File:flowchart2277.jpg]]&lt;br /&gt;
&lt;br /&gt;
==Testing==&lt;br /&gt;
&lt;br /&gt;
''''' Testing Plan '''''&lt;br /&gt;
# Since we are removing the use of  'Object.const_get' we ran the tests again to see that it is functioning properly.&lt;br /&gt;
&lt;br /&gt;
=== RSPEC Test Cases ===&lt;br /&gt;
The current version of expertiza included tests for the questionnaire_controller and qeustions_controller. we plan to modify a few of these tests so that it fits the changes that we have proposed.&lt;br /&gt;
&lt;br /&gt;
To run the tests, run the following commands from the expertiza directory&lt;br /&gt;
&amp;lt;pre&amp;gt;&lt;br /&gt;
rspec ./spec/controllers/questionnaires_controller_spec.rb&lt;br /&gt;
&amp;lt;/pre&amp;gt;&lt;br /&gt;
&amp;lt;pre&amp;gt;&lt;br /&gt;
rspec ./spec/controllers/questions_controller_spec.rb&lt;br /&gt;
&amp;lt;/pre&amp;gt;&lt;br /&gt;
&lt;br /&gt;
===Manual Testing===&lt;br /&gt;
&lt;br /&gt;
''''' Testing as Instructor'''''&lt;br /&gt;
# Login as Instructor.&lt;br /&gt;
# Click on Questionnaires.&lt;br /&gt;
# Choose a topic and create a new questionnaire.&lt;br /&gt;
# Check the save functionality.&lt;br /&gt;
# Add a new question to the questionnaire and check the save question functionality.&lt;br /&gt;
# delete a question and check if it's reflected properly.&lt;br /&gt;
&lt;br /&gt;
==SOLID Principle==&lt;br /&gt;
&lt;br /&gt;
SOLID is a set of rules that guide us on how to achieve that in object-oriented programming. Using SOLID guidelines you can avoid bad design in your code and give a well-structured architecture to your design. Bad design leads to an inflexible and brittle codebase, a simple and small change can result in bugs with bad design.&lt;br /&gt;
&lt;br /&gt;
We implemented the single responsibility principle to divide the questionnaires_controller into questionnaires and questions controller thus ensuring that each controller does only one job.&lt;br /&gt;
&lt;br /&gt;
==Factory Design pattern==&lt;br /&gt;
&lt;br /&gt;
In Factory pattern, we create object without exposing the creation logic to the client and refer to newly created object using a common interface.&lt;br /&gt;
&lt;br /&gt;
We implemented the factory design pattern to create questionnaire objects based on the type selected by the user. We implemented similar approach for creation of question objects as well.&lt;br /&gt;
&lt;br /&gt;
==References==&lt;br /&gt;
&lt;br /&gt;
* [https://github.com/kailash1998s/expertiza GitHub]&lt;br /&gt;
&lt;br /&gt;
* [https://github.com/expertiza/expertiza/pull/2492 github PR]&lt;br /&gt;
&lt;br /&gt;
* [https://www.rubyguides.com/2015/12/ruby-refactoring/ Introduction to Refactoring in Ruby]&lt;br /&gt;
&lt;br /&gt;
* [http://rspec.info/documentation/3.8/rspec-core/ Rspec Documentation]&lt;br /&gt;
&lt;br /&gt;
==Team Members==&lt;br /&gt;
&lt;br /&gt;
* [mailto:aumasan@ncsu.edu Ashwin Shankar Umasankar] &lt;br /&gt;
* [mailto:ksingar2@ncsu.edu Kailash Singaravelu]&lt;br /&gt;
* [mailto:penaman@ncsu.edu Pujitha Enamandala]&lt;/div&gt;</summary>
		<author><name>Penaman</name></author>
	</entry>
	<entry>
		<id>https://wiki.expertiza.ncsu.edu/index.php?title=CSC/ECE_517_Fall_2022_-_E2257:_Refactor_questionnaires_controller.rb&amp;diff=146048</id>
		<title>CSC/ECE 517 Fall 2022 - E2257: Refactor questionnaires controller.rb</title>
		<link rel="alternate" type="text/html" href="https://wiki.expertiza.ncsu.edu/index.php?title=CSC/ECE_517_Fall_2022_-_E2257:_Refactor_questionnaires_controller.rb&amp;diff=146048"/>
		<updated>2022-10-27T01:40:11Z</updated>

		<summary type="html">&lt;p&gt;Penaman: &lt;/p&gt;
&lt;hr /&gt;
&lt;div&gt;==Introduction==&lt;br /&gt;
&amp;lt;nowiki&amp;gt;In Expertiza, Questionnaire is the superclass for all kinds of questionnaires and rubrics—rubrics for evaluating submissions and teammate contributions, and taking quizzes and surveys.  All of these are subclasses of Questionnaire.  questionnaires_controller.rb is charged with creating, displaying, and managing Questionnaires.  Because it is used so widely, malfunctions could cause bugs in many parts of the system; hence it is especially important that the code be clear.&amp;lt;/nowiki&amp;gt;&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
==Issues Fixed==&lt;br /&gt;
# Removed create_questionnaire&lt;br /&gt;
# Split create method into smaller self-documenting methods.&lt;br /&gt;
# QuizQuestionnaire check&lt;br /&gt;
# Refactor add_new_questions method&lt;br /&gt;
# Remove redundant variables in QuestionnairesController&lt;br /&gt;
&lt;br /&gt;
==Files Changed==&lt;br /&gt;
*app/controllers/questionnaires_controller.rb&lt;br /&gt;
*spec/controllers/questionnaires_controller_spec.rb&lt;br /&gt;
*app/models/question.rb&lt;br /&gt;
&lt;br /&gt;
==Changes==&lt;br /&gt;
===Fix #1===&lt;br /&gt;
The &amp;lt;code&amp;gt;create_questionnnaires&amp;lt;/code&amp;gt; method was present but its related functionality had been removed. Some kind of link to it is still present in one of the initial migrations which was populating a database to show values for a drop-down that is no longer in use. Thus ended up removing the function and its corresponding test cases.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
===Fix #2===&lt;br /&gt;
The &amp;lt;code&amp;gt;create&amp;lt;/code&amp;gt; method itself is 49 lines long.  This is much too long to be viewable at a glance. Thus the method was broken into &amp;lt;code&amp;gt;adding_question_variables&amp;lt;/code&amp;gt;  and &amp;lt;code&amp;gt;create_node&amp;lt;/code&amp;gt; method so that they are clear enough to be self-documenting.&lt;br /&gt;
 &amp;lt;nowiki&amp;gt;&lt;br /&gt;
   def create&lt;br /&gt;
    if params[:questionnaire][:name].blank?&lt;br /&gt;
      flash[:error] = 'A rubric or survey must have a title.'&lt;br /&gt;
      redirect_to controller: 'questionnaires', action: 'new', model: params[:questionnaire][:type], private: params[:questionnaire][:private]&lt;br /&gt;
    else&lt;br /&gt;
      questionnaire_private = params[:questionnaire][:private] == 'true'&lt;br /&gt;
      display_type = params[:questionnaire][:type].split('Questionnaire')[0]&lt;br /&gt;
      begin&lt;br /&gt;
        @questionnaire = Object.const_get(params[:questionnaire][:type]).new if Questionnaire::QUESTIONNAIRE_TYPES.include? params[:questionnaire][:type]&lt;br /&gt;
      rescue StandardError&lt;br /&gt;
        flash[:error] = $ERROR_INFO&lt;br /&gt;
      end&lt;br /&gt;
      begin&lt;br /&gt;
        # Zhewei: Right now, the display_type in 'questionnaires' table and name in 'tree_folders' table are not consistent.&lt;br /&gt;
        # In the future, we need to write migration files to make them consistency.&lt;br /&gt;
        # E1903 : We are not sure of other type of cases, so have added a if statement. If there are only 5 cases, remove the if statement&lt;br /&gt;
        if %w[AuthorFeedback CourseSurvey TeammateReview GlobalSurvey AssignmentSurvey BookmarkRating].include?(display_type)&lt;br /&gt;
          display_type = display_type.split(/(?=[A-Z])/).join('%')&lt;br /&gt;
        end&lt;br /&gt;
        # setting the object variables&lt;br /&gt;
        adding_question_variables(questionnaire_private, display_type)&lt;br /&gt;
        # Create node&lt;br /&gt;
        create_node()&lt;br /&gt;
      rescue StandardError&lt;br /&gt;
        flash[:error] = $ERROR_INFO&lt;br /&gt;
      end&lt;br /&gt;
      redirect_to controller: 'questionnaires', action: 'edit', id: @questionnaire.id&lt;br /&gt;
    end&lt;br /&gt;
  end&amp;lt;/nowiki&amp;gt;&lt;br /&gt;
&lt;br /&gt;
----&lt;br /&gt;
&lt;br /&gt;
 &amp;lt;nowiki&amp;gt;&lt;br /&gt;
  # Assigns corrresponding variables to questionnaire object.&lt;br /&gt;
  def adding_question_variables(prv,display)&lt;br /&gt;
    @questionnaire.private = prv&lt;br /&gt;
    @questionnaire.name = params[:questionnaire][:name]&lt;br /&gt;
    @questionnaire.instructor_id = session[:user].id&lt;br /&gt;
    @questionnaire.min_question_score = params[:questionnaire][:min_question_score]&lt;br /&gt;
    @questionnaire.max_question_score = params[:questionnaire][:max_question_score]&lt;br /&gt;
    @questionnaire.type = params[:questionnaire][:type]&lt;br /&gt;
    @questionnaire.display_type = display&lt;br /&gt;
    @questionnaire.instruction_loc = Questionnaire::DEFAULT_QUESTIONNAIRE_URL&lt;br /&gt;
    @questionnaire.save&lt;br /&gt;
  end&lt;br /&gt;
 &amp;lt;/nowiki&amp;gt;&lt;br /&gt;
&lt;br /&gt;
----&lt;br /&gt;
&lt;br /&gt;
 &amp;lt;nowiki&amp;gt;&lt;br /&gt;
  # Creates tree node&lt;br /&gt;
  def create_node()&lt;br /&gt;
    tree_folder = TreeFolder.where(['name like ?', @questionnaire.display_type]).first&lt;br /&gt;
    parent = FolderNode.find_by(node_object_id: tree_folder.id)&lt;br /&gt;
    QuestionnaireNode.create(parent_id: parent.id, node_object_id: @questionnaire.id, type: 'QuestionnaireNode')&lt;br /&gt;
    flash[:success] = 'You have successfully created a questionnaire!'&lt;br /&gt;
  end&lt;br /&gt;
 &amp;lt;/nowiki&amp;gt;&lt;br /&gt;
&lt;br /&gt;
===Fix #3===&lt;br /&gt;
There are three checks for whether a questionnaire is a QuizQuestionnaire.  Testing the class of an object is always suspect, though, in a controller, which has to control a whole hierarchy of objects, it is not necessarily wrong.  However, they probably aren’t necessary. 2 of them seem to have been removed already and the only remaining check was in create_questionnaire, thus it got removed while applying Fix #1.&lt;br /&gt;
&lt;br /&gt;
===Fix #4===&lt;br /&gt;
&lt;br /&gt;
According to the code climate, it was suggested that usage of &amp;lt;code&amp;gt;each_key&amp;lt;/code&amp;gt; is preferable instead of &amp;lt;code&amp;gt;keys.each&amp;lt;/code&amp;gt; . Rubocop suggests this due to performance. Using large sets of data is where this becomes noticeable. Chaining methods is going to be slower than using the built-in method (in this case) which accomplishes the task with a single special enumerator. &lt;br /&gt;
&lt;br /&gt;
 &amp;lt;nowiki&amp;gt;&lt;br /&gt;
    params[:question].keys.each do |question_key|&lt;br /&gt;
 &amp;lt;/nowiki&amp;gt;&lt;br /&gt;
&lt;br /&gt;
 &amp;lt;nowiki&amp;gt;&lt;br /&gt;
    params[:question].each_key do |question_key|&lt;br /&gt;
 &amp;lt;/nowiki&amp;gt;&lt;br /&gt;
&lt;br /&gt;
===Fix #5===&lt;br /&gt;
&lt;br /&gt;
According to the code climate, it was suggested that the use of parentheses around a method call should be avoided.&lt;br /&gt;
&lt;br /&gt;
 &amp;lt;nowiki&amp;gt;&lt;br /&gt;
    display_type = (display_type.split(/(?=[A-Z])/)).join('%') &lt;br /&gt;
 &amp;lt;/nowiki&amp;gt;&lt;br /&gt;
&lt;br /&gt;
 &amp;lt;nowiki&amp;gt;&lt;br /&gt;
    display_type = display_type.split(/(?=[A-Z])/).join('%') &lt;br /&gt;
 &amp;lt;/nowiki&amp;gt;&lt;br /&gt;
&lt;br /&gt;
===Fix #6===&lt;br /&gt;
&lt;br /&gt;
The add_new_questions method has string literal values like 'Strongly agree', 'Strongly disagree', '50, 3', '0|1|2|3|4|5' for max_label, min_label, size and alternatives. The literals are removed by introducing constants in question.rb.&lt;br /&gt;
 &amp;lt;nowiki&amp;gt;&lt;br /&gt;
      if question.is_a? ScoredQuestion&lt;br /&gt;
        question.weight = params[:question][:weight]&lt;br /&gt;
        question.max_label = 'Strongly agree'&lt;br /&gt;
        question.min_label = 'Strongly disagree'&lt;br /&gt;
      end&lt;br /&gt;
&lt;br /&gt;
      question.size = '50, 3' if question.is_a? Criterion&lt;br /&gt;
      question.size = '50, 3' if question.is_a? Cake&lt;br /&gt;
      question.alternatives = '0|1|2|3|4|5' if question.is_a? Dropdown&lt;br /&gt;
      question.size = '60, 5' if question.is_a? TextArea&lt;br /&gt;
      question.size = '30' if question.is_a? TextField&lt;br /&gt;
&lt;br /&gt;
 &amp;lt;/nowiki&amp;gt;&lt;br /&gt;
&lt;br /&gt;
 &amp;lt;nowiki&amp;gt;&lt;br /&gt;
      if question.is_a? ScoredQuestion&lt;br /&gt;
        question.weight = params[:question][:weight]&lt;br /&gt;
        question.max_label = Question::MAX_LABEL&lt;br /&gt;
        question.min_label = Question::MIN_LABEL&lt;br /&gt;
      end&lt;br /&gt;
&lt;br /&gt;
      if Question::SIZES.key?(question.class.name)&lt;br /&gt;
        question.size = Question::SIZES[question.class.name]&lt;br /&gt;
      end&lt;br /&gt;
      if Question::ALTERNATIVES.key?(question.class.name)&lt;br /&gt;
        question.alternatives = Question::ALTERNATIVES[question.class.name]&lt;br /&gt;
      end&lt;br /&gt;
 &amp;lt;/nowiki&amp;gt;&lt;br /&gt;
&lt;br /&gt;
===Fix #7===&lt;br /&gt;
&lt;br /&gt;
The add_new_questions and save_all_questions methods have reduntant variable defined called questionnaire_id. The variable declaration is redundant as we can access it using params[:id].&lt;br /&gt;
&lt;br /&gt;
 &amp;lt;nowiki&amp;gt;&lt;br /&gt;
     questionnaire_id = params[:id] unless params[:id].nil?&lt;br /&gt;
     num_of_existed_questions = Questionnaire.find(questionnaire_id).questions.size&lt;br /&gt;
 &amp;lt;/nowiki&amp;gt;&lt;br /&gt;
&lt;br /&gt;
 &amp;lt;nowiki&amp;gt;&lt;br /&gt;
     num_of_existed_questions = Questionnaire.find(params[:id]).questions.size&lt;br /&gt;
 &amp;lt;/nowiki&amp;gt;&lt;br /&gt;
&lt;br /&gt;
=== Future scope ===&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
===Project Mentor===&lt;br /&gt;
&lt;br /&gt;
Edward Gehringer (efg@ncsu.edu)&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
===Team Member===&lt;br /&gt;
&lt;br /&gt;
Ashwin Shankar Umasankar [[(aumasan@ncsu.edu)]]&lt;br /&gt;
&lt;br /&gt;
Kailash Singaravelu [[(ksingar2@ncsu.edu)]]&lt;br /&gt;
&lt;br /&gt;
Pujitha Enamandala [[(penaman@ncsu.edu)]]&lt;br /&gt;
&lt;br /&gt;
===Reference===&lt;br /&gt;
#[http://152.7.177.154:8080/ VCL link]&lt;br /&gt;
#[https://github.com/Ashwinshankar98/expertiza Github Repo]&lt;br /&gt;
#[https://github.com/expertiza/expertiza/pull/2470 Github Pull Request]&lt;br /&gt;
#[https://github.com/expertiza/expertiza Expertiza on GitHub]&lt;br /&gt;
#[http://wikis.lib.ncsu.edu/index.php/Expertiza Expertiza Project Documentation Wiki]&lt;br /&gt;
#[https://codeclimate.com/github/expertiza/expertiza/app/controllers/questionnaires_controller.rb CodeClimate Documentation]&lt;/div&gt;</summary>
		<author><name>Penaman</name></author>
	</entry>
	<entry>
		<id>https://wiki.expertiza.ncsu.edu/index.php?title=CSC/ECE_517_Fall_2022_-_E2257:_Refactor_questionnaires_controller.rb&amp;diff=146038</id>
		<title>CSC/ECE 517 Fall 2022 - E2257: Refactor questionnaires controller.rb</title>
		<link rel="alternate" type="text/html" href="https://wiki.expertiza.ncsu.edu/index.php?title=CSC/ECE_517_Fall_2022_-_E2257:_Refactor_questionnaires_controller.rb&amp;diff=146038"/>
		<updated>2022-10-27T00:54:19Z</updated>

		<summary type="html">&lt;p&gt;Penaman: &lt;/p&gt;
&lt;hr /&gt;
&lt;div&gt;==Introduction==&lt;br /&gt;
&amp;lt;nowiki&amp;gt;In Expertiza, Questionnaire is the superclass for all kinds of questionnaires and rubrics—rubrics for evaluating submissions and teammate contributions, and taking quizzes and surveys.  All of these are subclasses of Questionnaire.  questionnaires_controller.rb is charged with creating, displaying, and managing Questionnaires.  Because it is used so widely, malfunctions could cause bugs in many parts of the system; hence it is especially important that the code be clear.&amp;lt;/nowiki&amp;gt;&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
==Issues Fixed==&lt;br /&gt;
# Removed create_questionnaire&lt;br /&gt;
# Refactor create method ( usage of local variable instead of instance variables)&lt;br /&gt;
# QuizQuestionnaire check&lt;br /&gt;
# Refactor add_new_questions method&lt;br /&gt;
# Remove reduntant variables in QuestionnairesController&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
==Files Changed==&lt;br /&gt;
*app/controllers/questionnaires_controller.rb&lt;br /&gt;
*spec/controllers/questionnaires_controller_spec.rb&lt;br /&gt;
*app/models/question.rb&lt;br /&gt;
&lt;br /&gt;
==Changes==&lt;br /&gt;
===Fix #1===&lt;br /&gt;
The &amp;lt;code&amp;gt;create_questionnnaires&amp;lt;/code&amp;gt; method was present but its related functionality had been removed. Some kind of link to it is still present in one of the initial migrations which was populating a database to show values for a drop-down that is no longer in use. Thus ended up removing the function and its corresponding test cases.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
===Fix #2===&lt;br /&gt;
The instance variable &amp;lt;code&amp;gt;@questionnaire&amp;lt;/code&amp;gt; is converted to local &amp;lt;code&amp;gt;questionnaire&amp;lt;/code&amp;gt; object to reduce its scope. Since in any other method &amp;lt;code&amp;gt;@questionnaire&amp;lt;/code&amp;gt; object is initialized again.&lt;br /&gt;
 &amp;lt;nowiki&amp;gt;&lt;br /&gt;
  def create&lt;br /&gt;
    if params[:questionnaire][:name].blank?&lt;br /&gt;
      flash[:error] = 'A rubric or survey must have a title.'&lt;br /&gt;
      redirect_to controller: 'questionnaires', action: 'new', model: params[:questionnaire][:type], private: params[:questionnaire][:private]&lt;br /&gt;
    else&lt;br /&gt;
      questionnaire_private = params[:questionnaire][:private] == 'true'&lt;br /&gt;
      display_type = params[:questionnaire][:type].split('Questionnaire')[0]&lt;br /&gt;
      begin&lt;br /&gt;
        questionnaire = Object.const_get(params[:questionnaire][:type]).new if Questionnaire::QUESTIONNAIRE_TYPES.include? params[:questionnaire][:type]&lt;br /&gt;
      rescue StandardError&lt;br /&gt;
        flash[:error] = $ERROR_INFO&lt;br /&gt;
      end&lt;br /&gt;
      begin&lt;br /&gt;
        questionnaire.private = questionnaire_private&lt;br /&gt;
        questionnaire.name = params[:questionnaire][:name]&lt;br /&gt;
        questionnaire.instructor_id = session[:user].id&lt;br /&gt;
        questionnaire.min_question_score = params[:questionnaire][:min_question_score]&lt;br /&gt;
        questionnaire.max_question_score = params[:questionnaire][:max_question_score]&lt;br /&gt;
        questionnaire.type = params[:questionnaire][:type]&lt;br /&gt;
        # Zhewei: Right now, the display_type in 'questionnaires' table and name in 'tree_folders' table are not consistent.&lt;br /&gt;
        # In the future, we need to write migration files to make them consistency.&lt;br /&gt;
        # E1903 : We are not sure of other type of cases, so have added a if statement. If there are only 5 cases, remove the if statement&lt;br /&gt;
        if %w[AuthorFeedback CourseSurvey TeammateReview GlobalSurvey AssignmentSurvey BookmarkRating].include?(display_type)&lt;br /&gt;
          display_type = (display_type.split(/(?=[A-Z])/)).join('%')&lt;br /&gt;
        end&lt;br /&gt;
        questionnaire.display_type = display_type&lt;br /&gt;
        questionnaire.instruction_loc = Questionnaire::DEFAULT_QUESTIONNAIRE_URL&lt;br /&gt;
        questionnaire.save&lt;br /&gt;
        # Create node&lt;br /&gt;
        tree_folder = TreeFolder.where(['name like ?', questionnaire.display_type]).first&lt;br /&gt;
        parent = FolderNode.find_by(node_object_id: tree_folder.id)&lt;br /&gt;
        QuestionnaireNode.create(parent_id: parent.id, node_object_id: questionnaire.id, type: 'QuestionnaireNode')&lt;br /&gt;
        flash[:success] = 'You have successfully created a questionnaire!'&lt;br /&gt;
      rescue StandardError&lt;br /&gt;
        flash[:error] = $ERROR_INFO&lt;br /&gt;
      end&lt;br /&gt;
      redirect_to controller: 'questionnaires', action: 'edit', id: questionnaire.id&lt;br /&gt;
    end&lt;br /&gt;
  end&amp;lt;/nowiki&amp;gt;&lt;br /&gt;
&lt;br /&gt;
===Fix #3===&lt;br /&gt;
There are three checks for whether a questionnaire is a QuizQuestionnaire.  Testing the class of an object is always suspect, though, in a controller, which has to control a whole hierarchy of objects, it is not necessarily wrong.  However, they probably aren’t necessary. 2 of them seem to have been removed already and the only remaining check was in create_questionnaire, thus it got removed while applying Fix #1.&lt;br /&gt;
&lt;br /&gt;
===Fix #4===&lt;br /&gt;
&lt;br /&gt;
According to the code climate, it was suggested that usage of &amp;lt;code&amp;gt;each_key&amp;lt;/code&amp;gt; is preferable instead of &amp;lt;code&amp;gt;keys.each&amp;lt;/code&amp;gt; . Rubocop suggests this due to performance. Using large sets of data is where this becomes noticeable. Chaining methods is going to be slower than using the built-in method (in this case) which accomplishes the task with a single special enumerator. &lt;br /&gt;
&lt;br /&gt;
 &amp;lt;nowiki&amp;gt;&lt;br /&gt;
    params[:question].keys.each do |question_key|&lt;br /&gt;
 &amp;lt;/nowiki&amp;gt;&lt;br /&gt;
&lt;br /&gt;
 &amp;lt;nowiki&amp;gt;&lt;br /&gt;
    params[:question].each_key do |question_key|&lt;br /&gt;
 &amp;lt;/nowiki&amp;gt;&lt;br /&gt;
&lt;br /&gt;
===Fix #5===&lt;br /&gt;
&lt;br /&gt;
According to the code climate, it was suggested that the use of parentheses around a method call should be avoided.&lt;br /&gt;
&lt;br /&gt;
 &amp;lt;nowiki&amp;gt;&lt;br /&gt;
    display_type = (display_type.split(/(?=[A-Z])/)).join('%') &lt;br /&gt;
 &amp;lt;/nowiki&amp;gt;&lt;br /&gt;
&lt;br /&gt;
 &amp;lt;nowiki&amp;gt;&lt;br /&gt;
    display_type = display_type.split(/(?=[A-Z])/).join('%') &lt;br /&gt;
 &amp;lt;/nowiki&amp;gt;&lt;br /&gt;
&lt;br /&gt;
===Fix #6===&lt;br /&gt;
&lt;br /&gt;
The add_new_questions method has string literal values like 'Strongly agree', 'Strongly disagree', '50, 3', '0|1|2|3|4|5' for max_label, min_label, size and alternatives. String literals are removed by introducing constants in question.rb.&lt;br /&gt;
&lt;br /&gt;
 &amp;lt;nowiki&amp;gt;&lt;br /&gt;
      if question.is_a? ScoredQuestion&lt;br /&gt;
        question.weight = params[:question][:weight]&lt;br /&gt;
        question.max_label = Question::MAX_LABEL&lt;br /&gt;
        question.min_label = Question::MIN_LABEL&lt;br /&gt;
      end&lt;br /&gt;
&lt;br /&gt;
      if Question::SIZES.key?(question.class.name)&lt;br /&gt;
        question.size = Question::SIZES[question.class.name]&lt;br /&gt;
      end&lt;br /&gt;
      if Question::ALTERNATIVES.key?(question.class.name)&lt;br /&gt;
        question.alternatives = Question::ALTERNATIVES[question.class.name]&lt;br /&gt;
      end&lt;br /&gt;
 &amp;lt;/nowiki&amp;gt;&lt;br /&gt;
&lt;br /&gt;
===Fix #7===&lt;br /&gt;
&lt;br /&gt;
The add_new_questions and save_all_questions methods have reduntant variable defined called questionnaire_id. The variable declaration is redundant as we can access it using params[:id].&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
=== Future scope ===&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
===Project Mentor===&lt;br /&gt;
&lt;br /&gt;
Edward Gehringer (efg@ncsu.edu)&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
===Team Member===&lt;br /&gt;
&lt;br /&gt;
Ashwin Shankar Umasankar [[(aumasan@ncsu.edu)]]&lt;br /&gt;
&lt;br /&gt;
Kailash Singaravelu [[(ksingar2@ncsu.edu)]]&lt;br /&gt;
&lt;br /&gt;
Pujitha Enamandala [[(penaman@ncsu.edu)]]&lt;br /&gt;
&lt;br /&gt;
===Reference===&lt;br /&gt;
#[http://152.7.177.154:8080/ VCL link]&lt;br /&gt;
#[https://github.com/Ashwinshankar98/expertiza Github Repo]&lt;br /&gt;
#[https://github.com/expertiza/expertiza/pull/2470 Github Pull Request]&lt;br /&gt;
#[https://github.com/expertiza/expertiza Expertiza on GitHub]&lt;br /&gt;
#[http://wikis.lib.ncsu.edu/index.php/Expertiza Expertiza Project Documentation Wiki]&lt;br /&gt;
#[https://codeclimate.com/github/expertiza/expertiza/app/controllers/questionnaires_controller.rb CodeClimate Documentation]&lt;/div&gt;</summary>
		<author><name>Penaman</name></author>
	</entry>
	<entry>
		<id>https://wiki.expertiza.ncsu.edu/index.php?title=CSC/ECE_517_Fall_2022_-_E2257:_Refactor_questionnaires_controller.rb&amp;diff=146036</id>
		<title>CSC/ECE 517 Fall 2022 - E2257: Refactor questionnaires controller.rb</title>
		<link rel="alternate" type="text/html" href="https://wiki.expertiza.ncsu.edu/index.php?title=CSC/ECE_517_Fall_2022_-_E2257:_Refactor_questionnaires_controller.rb&amp;diff=146036"/>
		<updated>2022-10-27T00:52:06Z</updated>

		<summary type="html">&lt;p&gt;Penaman: &lt;/p&gt;
&lt;hr /&gt;
&lt;div&gt;==Introduction==&lt;br /&gt;
&amp;lt;nowiki&amp;gt;In Expertiza, Questionnaire is the superclass for all kinds of questionnaires and rubrics—rubrics for evaluating submissions and teammate contributions, and taking quizzes and surveys.  All of these are subclasses of Questionnaire.  questionnaires_controller.rb is charged with creating, displaying, and managing Questionnaires.  Because it is used so widely, malfunctions could cause bugs in many parts of the system; hence it is especially important that the code be clear.&amp;lt;/nowiki&amp;gt;&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
==Issues Fixed==&lt;br /&gt;
# Removed create_questionnaire&lt;br /&gt;
# Refactor create method ( usage of local variable instead of instance variables)&lt;br /&gt;
# QuizQuestionnaire check&lt;br /&gt;
# Refactor add_new_questions method&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
==Files Changed==&lt;br /&gt;
*app/controllers/questionnaires_controller.rb&lt;br /&gt;
*spec/controllers/questionnaires_controller_spec.rb&lt;br /&gt;
*app/models/question.rb&lt;br /&gt;
&lt;br /&gt;
==Changes==&lt;br /&gt;
===Fix #1===&lt;br /&gt;
The &amp;lt;code&amp;gt;create_questionnnaires&amp;lt;/code&amp;gt; method was present but its related functionality had been removed. Some kind of link to it is still present in one of the initial migrations which was populating a database to show values for a drop-down that is no longer in use. Thus ended up removing the function and its corresponding test cases.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
===Fix #2===&lt;br /&gt;
The instance variable &amp;lt;code&amp;gt;@questionnaire&amp;lt;/code&amp;gt; is converted to local &amp;lt;code&amp;gt;questionnaire&amp;lt;/code&amp;gt; object to reduce its scope. Since in any other method &amp;lt;code&amp;gt;@questionnaire&amp;lt;/code&amp;gt; object is initialized again.&lt;br /&gt;
 &amp;lt;nowiki&amp;gt;&lt;br /&gt;
  def create&lt;br /&gt;
    if params[:questionnaire][:name].blank?&lt;br /&gt;
      flash[:error] = 'A rubric or survey must have a title.'&lt;br /&gt;
      redirect_to controller: 'questionnaires', action: 'new', model: params[:questionnaire][:type], private: params[:questionnaire][:private]&lt;br /&gt;
    else&lt;br /&gt;
      questionnaire_private = params[:questionnaire][:private] == 'true'&lt;br /&gt;
      display_type = params[:questionnaire][:type].split('Questionnaire')[0]&lt;br /&gt;
      begin&lt;br /&gt;
        questionnaire = Object.const_get(params[:questionnaire][:type]).new if Questionnaire::QUESTIONNAIRE_TYPES.include? params[:questionnaire][:type]&lt;br /&gt;
      rescue StandardError&lt;br /&gt;
        flash[:error] = $ERROR_INFO&lt;br /&gt;
      end&lt;br /&gt;
      begin&lt;br /&gt;
        questionnaire.private = questionnaire_private&lt;br /&gt;
        questionnaire.name = params[:questionnaire][:name]&lt;br /&gt;
        questionnaire.instructor_id = session[:user].id&lt;br /&gt;
        questionnaire.min_question_score = params[:questionnaire][:min_question_score]&lt;br /&gt;
        questionnaire.max_question_score = params[:questionnaire][:max_question_score]&lt;br /&gt;
        questionnaire.type = params[:questionnaire][:type]&lt;br /&gt;
        # Zhewei: Right now, the display_type in 'questionnaires' table and name in 'tree_folders' table are not consistent.&lt;br /&gt;
        # In the future, we need to write migration files to make them consistency.&lt;br /&gt;
        # E1903 : We are not sure of other type of cases, so have added a if statement. If there are only 5 cases, remove the if statement&lt;br /&gt;
        if %w[AuthorFeedback CourseSurvey TeammateReview GlobalSurvey AssignmentSurvey BookmarkRating].include?(display_type)&lt;br /&gt;
          display_type = (display_type.split(/(?=[A-Z])/)).join('%')&lt;br /&gt;
        end&lt;br /&gt;
        questionnaire.display_type = display_type&lt;br /&gt;
        questionnaire.instruction_loc = Questionnaire::DEFAULT_QUESTIONNAIRE_URL&lt;br /&gt;
        questionnaire.save&lt;br /&gt;
        # Create node&lt;br /&gt;
        tree_folder = TreeFolder.where(['name like ?', questionnaire.display_type]).first&lt;br /&gt;
        parent = FolderNode.find_by(node_object_id: tree_folder.id)&lt;br /&gt;
        QuestionnaireNode.create(parent_id: parent.id, node_object_id: questionnaire.id, type: 'QuestionnaireNode')&lt;br /&gt;
        flash[:success] = 'You have successfully created a questionnaire!'&lt;br /&gt;
      rescue StandardError&lt;br /&gt;
        flash[:error] = $ERROR_INFO&lt;br /&gt;
      end&lt;br /&gt;
      redirect_to controller: 'questionnaires', action: 'edit', id: questionnaire.id&lt;br /&gt;
    end&lt;br /&gt;
  end&amp;lt;/nowiki&amp;gt;&lt;br /&gt;
&lt;br /&gt;
===Fix #3===&lt;br /&gt;
There are three checks for whether a questionnaire is a QuizQuestionnaire.  Testing the class of an object is always suspect, though, in a controller, which has to control a whole hierarchy of objects, it is not necessarily wrong.  However, they probably aren’t necessary. 2 of them seem to have been removed already and the only remaining check was in create_questionnaire, thus it got removed while applying Fix #1.&lt;br /&gt;
&lt;br /&gt;
===Fix #4===&lt;br /&gt;
&lt;br /&gt;
According to the code climate, it was suggested that usage of &amp;lt;code&amp;gt;each_key&amp;lt;/code&amp;gt; is preferable instead of &amp;lt;code&amp;gt;keys.each&amp;lt;/code&amp;gt; . Rubocop suggests this due to performance. Using large sets of data is where this becomes noticeable. Chaining methods is going to be slower than using the built-in method (in this case) which accomplishes the task with a single special enumerator. &lt;br /&gt;
&lt;br /&gt;
 &amp;lt;nowiki&amp;gt;&lt;br /&gt;
    params[:question].keys.each do |question_key|&lt;br /&gt;
 &amp;lt;/nowiki&amp;gt;&lt;br /&gt;
&lt;br /&gt;
 &amp;lt;nowiki&amp;gt;&lt;br /&gt;
    params[:question].each_key do |question_key|&lt;br /&gt;
 &amp;lt;/nowiki&amp;gt;&lt;br /&gt;
&lt;br /&gt;
===Fix #5===&lt;br /&gt;
&lt;br /&gt;
According to the code climate, it was suggested that the use of parentheses around a method call should be avoided.&lt;br /&gt;
&lt;br /&gt;
 &amp;lt;nowiki&amp;gt;&lt;br /&gt;
    display_type = (display_type.split(/(?=[A-Z])/)).join('%') &lt;br /&gt;
 &amp;lt;/nowiki&amp;gt;&lt;br /&gt;
&lt;br /&gt;
 &amp;lt;nowiki&amp;gt;&lt;br /&gt;
    display_type = display_type.split(/(?=[A-Z])/).join('%') &lt;br /&gt;
 &amp;lt;/nowiki&amp;gt;&lt;br /&gt;
&lt;br /&gt;
===Fix #6===&lt;br /&gt;
&lt;br /&gt;
The add_new_questions method has string literal values like 'Strongly agree', 'Strongly disagree', '50, 3', '0|1|2|3|4|5' for max_label, min_label, size and alternatives. String literals are removed by introducing constants.&lt;br /&gt;
&lt;br /&gt;
 &amp;lt;nowiki&amp;gt;&lt;br /&gt;
      if question.is_a? ScoredQuestion&lt;br /&gt;
        question.weight = params[:question][:weight]&lt;br /&gt;
        question.max_label = Question::MAX_LABEL&lt;br /&gt;
        question.min_label = Question::MIN_LABEL&lt;br /&gt;
      end&lt;br /&gt;
&lt;br /&gt;
      if Question::SIZES.key?(question.class.name)&lt;br /&gt;
        question.size = Question::SIZES[question.class.name]&lt;br /&gt;
      end&lt;br /&gt;
      if Question::ALTERNATIVES.key?(question.class.name)&lt;br /&gt;
        question.alternatives = Question::ALTERNATIVES[question.class.name]&lt;br /&gt;
      end&lt;br /&gt;
 &amp;lt;/nowiki&amp;gt;&lt;br /&gt;
&lt;br /&gt;
===Fix #7===&lt;br /&gt;
&lt;br /&gt;
The add_new_questions and save_all_questions method has a reduntant variable defined called questionnaire_id. The variable declaration is redundant as we can access it using params[:id].&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
=== Future scope ===&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
===Project Mentor===&lt;br /&gt;
&lt;br /&gt;
Edward Gehringer (efg@ncsu.edu)&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
===Team Member===&lt;br /&gt;
&lt;br /&gt;
Ashwin Shankar Umasankar [[(aumasan@ncsu.edu)]]&lt;br /&gt;
&lt;br /&gt;
Kailash Singaravelu [[(ksingar2@ncsu.edu)]]&lt;br /&gt;
&lt;br /&gt;
Pujitha Enamandala [[(penaman@ncsu.edu)]]&lt;br /&gt;
&lt;br /&gt;
===Reference===&lt;br /&gt;
#[http://152.7.177.154:8080/ VCL link]&lt;br /&gt;
#[https://github.com/Ashwinshankar98/expertiza Github Repo]&lt;br /&gt;
#[https://github.com/expertiza/expertiza/pull/2470 Github Pull Request]&lt;br /&gt;
#[https://github.com/expertiza/expertiza Expertiza on GitHub]&lt;br /&gt;
#[http://wikis.lib.ncsu.edu/index.php/Expertiza Expertiza Project Documentation Wiki]&lt;br /&gt;
#[https://codeclimate.com/github/expertiza/expertiza/app/controllers/questionnaires_controller.rb CodeClimate Documentation]&lt;/div&gt;</summary>
		<author><name>Penaman</name></author>
	</entry>
</feed>