【问题标题】:Getting database-driven from questions from one model and saving answers to another从一个模型的问题中获取数据库驱动并将答案保存到另一个模型
【发布时间】:2014-11-22 07:58:36
【问题描述】:

我正在尝试使用 Rails 创建一个灵活的数据库驱动表单系统,但在考虑使用该方法生成实际表单时遇到了一些麻烦。

我接近它的方法是拥有一个用作表单索引的模型(称为MyForms),一个处理所有表单问题的模型(称为MyQuestions)和一个模型处理表单的所有答案(称之为MyAnswers)。表格和问题已通过以下方式存储到数据库中:

mysql> select * from my_forms;                                                                                                                                                   
+----+------------+---------+---------------------+---------------------+                                                                                                           
| id | title      | company | created_at          | updated_at          |                                                                                                           
+----+------------+---------+---------------------+---------------------+
|  1 | First_Form |       1 | 2014-11-20 20:58:53 | 2014-11-20 20:58:53 |
+----+------------+---------+---------------------+---------------------+


mysql> select * from questions;
+----+--------------+-----------------+---------------+---------------------------------------------------------------------+---------------------+---------------------+
| id | my_form_id | question_number | question_type | the_question                                                        | created_at          | updated_at          |
+----+--------------+-----------------+---------------+---------------------------------------------------------------------+---------------------+---------------------+
|  1 |            1 |               1 | string        | lorem ipsum dolor sit amet consectetuer adipiscing elit proin risus | 2014-11-20 21:27:04 | 2014-11-20 21:27:04 |
|  2 |            1 |               2 | radio         | lorem ipsum dolor sit amet consectetuer adipiscing elit proin risus | 2014-11-20 21:27:04 | 2014-11-20 21:27:04 |
|  3 |            1 |               3 | check         | lorem ipsum dolor sit amet consectetuer adipiscing elit proin risus | 2014-11-20 21:27:04 | 2014-11-20 21:27:04 |
|  4 |            1 |               4 | radio         | lorem ipsum dolor sit amet consectetuer adipiscing elit proin risus | 2014-11-20 21:27:04 | 2014-11-20 21:27:04 |
|  5 |            1 |               5 | text-box      | lorem ipsum dolor sit amet consectetuer adipiscing elit proin risus | 2014-11-20 21:27:04 | 2014-11-20 21:27:04 |
|  6 |            1 |               6 | string        | lorem ipsum dolor sit amet consectetuer adipiscing elit proin risus | 2014-11-20 21:27:04 | 2014-11-20 21:27:04 |
|  7 |            1 |               7 | string        | lorem ipsum dolor sit amet consectetuer adipiscing elit proin risus | 2014-11-20 21:27:04 | 2014-11-20 21:27:04 |
|  8 |            1 |               8 | text-box      | lorem ipsum dolor sit amet consectetuer adipiscing elit proin risus | 2014-11-20 21:27:04 | 2014-11-20 21:27:04 |
|  9 |            1 |               9 | check         | lorem ipsum dolor sit amet consectetuer adipiscing elit proin risus | 2014-11-20 21:27:04 | 2014-11-20 21:27:04 |
| 10 |            1 |              10 | check         | lorem ipsum dolor sit amet consectetuer adipiscing elit proin risus | 2014-11-20 21:27:04 | 2014-11-20 21:27:04 |
+----+--------------+-----------------+---------------+---------------------------------------------------------------------+---------------------+---------------------+

答案数据库(目前为空)的结构如下:

mysql> show columns in answers;
+-----------------+----------+------+-----+---------+----------------+
| Field           | Type     | Null | Key | Default | Extra          |
+-----------------+----------+------+-----+---------+----------------+
| id              | int(11)  | NO   | PRI | NULL    | auto_increment |
| question_id     | int(11)  | YES  | MUL | NULL    |                |
| user_id         | int(11)  | YES  |     | NULL    |                |
| question_number | int(11)  | YES  |     | NULL    |                |
| the_answer      | text     | YES  |     | NULL    |                |
| created_at      | datetime | YES  |     | NULL    |                |
| updated_at      | datetime | YES  |     | NULL    |                |
+-----------------+----------+------+-----+---------+----------------+

这样,无论我要发布多少表格、问题/表格或他们有什么要求,我都可以轻松地启动和运行它们。

现在我可以很容易地展示问题,使用 show in legal_forms_controller.rb 使用以下内容:

def show
  @legalform = LegalForm.find(params[:id])
  @questions = @legalform.questions
end

然后在show.html.erb中显示如下

<% @questions.each do |client| %>
    <span><%= client.the_question %></span><br/>
<% end %>

但我正在努力弄清楚如何将它们与表单输入字段配对并将它们保存到答案数据库中。我认为获得空白答案可能涉及创建答案控制器,然后使用new 方法,然后我可以使用一些条件在视图中创建正确的输入类型,给定question type。但是,我不太明白如何有效地创建这个表单,然后在给定这种方法的情况下保存数据。对此的任何帮助将不胜感激。 (当然“天啊,你为什么要这样做你应该这样做……”的回应也是可以接受的。)

【问题讨论】:

    标签: ruby-on-rails forms ruby-on-rails-4


    【解决方案1】:

    我会将其建模为:

    # column :label, TEXT - the text body of the question
    # column :input_type, VARCHAR - maps to html input types
    # ...
    class Question 
        has_many :answers # since there may be several acceptable answers or options
    end
    
    # column :is_correct, BOOL
    # column :text, TEXT
    class Answer
        belongs_to :question
    end
    
    # Or test 
    class Test
        has_many :questions
        has_many :test_scores
    
        # generate a test with random questions
        def self.random(seed = nil)
            # ...
        end
    end
    
    class TestScore
        belongs_to :user
        belongs_to :test
    end
    

    这使我们可以重复使用testuser 的任何测试和查询分数中的任何问题(前提是您有某种用户模型)。

    您还可以构建用户界面,让管理员创建测试、问题和答案。

    要管理测试,您将使用 TestScoreController:

    class TestScoreController
        # administer a test
        def new
            @score = TestScore.new(user_id: current_user)
            @score.test = @test = Test.random()
        end
    
        # corrects test
        def create
            # ...
        end
    
        # Show a test result
        def show
           @score = TestScore.find(params[:id]).joins(:test)
        end
    end
    

    还有观点:new.html.erb

    <%= form_for(@score) do %>
        <%= @test.questions.each do |q| %>
            <%= f.fields_for :questions, question do |q| -%>
                <%= f.label q.label %>
                <%= QuestionHelper.input(q) %>
                <%= q.hidden_field :test_score_id, @score.id %>
            <%= end %>
        <%= end %>
    <%= end %>
    

    然后,您将创建一个辅助方法,该方法接受一个问题并返回输入。我会推荐simple_form,因为它有一个 DSL,可以轻松地动态生成输入。

    # app/helpers/question_helper
    module QuestionHelper
        def self.input(question)
            case question.input_type.to_sym
            when :text
            when :radio_button
            # ..    
            end
        end
    end
    

    【讨论】:

    • 这段代码是一个粗略的草图——它完全未经测试,甚至不能保证运行!
    • 哇,谢谢老兄!我会在今天晚些时候或明天试一试,以便我有时间理解它。非常感谢!
    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2017-05-05
    相关资源
    最近更新 更多