ruby-on-rails - Rails Wicked Gem - 在一个向导中使用两个(嵌套)模型

标签 ruby-on-rails ruby-on-rails-3 gem wizard formwizard

在用户成功注册后,我正在尝试将 Wicked-Gem 用于我的向导。

第一步是用户应输入他的“一般信息”(个人简介和兴趣)。提交这些信息后,用户应输入一个特征(A user has many charactersitics)。

我遇到的问题如下:如何正确使用 Wicked 为第一步的用户模型和第二步的特征模型(属于用户)创建一个表单?

我得到的错误是:

Can't mass-assign protected attributes: characteristics

我不想使用嵌套属性,因为向导是我唯一会使用它们的地方。

这是我的源代码:

邪恶的控制者:

#!/bin/env ruby
# encoding: utf-8
class AfterFirstSignInController < ApplicationController
  include Wicked::Wizard

  skip_before_filter :check_if_profile_complete, only: [:show, :update]

  steps :general_infos, :characteristics

  def show
    @user = current_user
    @characteristic = @user.characteristics.new
    @title = t('controllers.after_first_sign_in_controller.show.title')
    render_wizard
  end

  def update
    @user = current_user
    @characteristic = @user.characteristics.new
    case step
      when :general_infos
        @user.attributes = params[:user]
        render_wizard @user
      else
        @characteristic.attributes = params[:characteristic]
        render_wizard @characteristic
    end
  end
end

“一般信息表单”

.container
  .row
    .span5.offset3
      .progress.progress-info.progress-striped
        .bar(style='width: 50%')
          1/2
      .page-header
        %h1
          = t('views.after_first_sign_in.general_infos.h1')
      = form_for(@user, url: wizard_path, method: :put) do |f|
        = render 'shared/error_messages', object: @user
        .control-group
          %label.control-label(for='bio')
            = t('views.after_first_sign_in.general_infos.labels.bio')
          .controls
            = f.text_area :bio, id: 'bio', rows: '6'
        .control-group
          %label.control-label(for='interest_list')
            = t('views.after_first_sign_in.general_infos.labels.interest_list')
          .controls
            = f.text_field :interest_list, id: 'interest_list'
        .form-actions
          = f.submit t('views.after_first_sign_in.general_infos.buttons.submit'), disable_with: t('views.after_first_sign_in.general_infos.buttons.submit'), class: 'btn btn-primary pull-right'

“特征-形式”

.container
  .row
    .span5.offset3
      .progress.progress-info.progress-striped
        .bar(style='width: 100%')
          2/2
      .page-header
        %h1
          = t('views.after_first_sign_in.characteristics.h1')
      = form_for([@user, @characteristic], url: wizard_path, method: :put) do |f|
        = render 'shared/error_messages', object: @characteristic
        = f.fields_for :characteristics do |builder|
          .control-group
            %label.control-label(for='title')
              = t('views.after_first_sign_in.characteristics.labels.title')
            .controls
              = builder.text_field :title, id: 'title'
          .control-group
            %label.control-label(for='description')
              = t('views.after_first_sign_in.characteristics.labels.description')
            .controls
              = builder.text_area :description, id: 'description', rows: '6'
        .form-actions
          = f.submit t('views.after_first_sign_in.characteristics.buttons.submit'), disable_with: t('views.after_first_sign_in.characteristics.buttons.submit'), class: 'btn btn-primary pull-right'
          = link_to t('views.after_first_sign_in.characteristics.buttons.general_infos_step'), after_first_sign_in_path(:general_infos), class: 'btn'

路由文件

Test::Application.routes.draw do
  scope '(:locale)' do
    resources :users do
      resources :characteristics
      resources :followings, only: [:create, :destroy, :index]
      resources :wall_entries, only: [:create, :destroy]
      resources :messages, only: [:create, :destroy, :index]
    end

    resources :characteristics do
      resources :votes, only: [:create, :destroy]
    end

    resources :after_first_sign_in

    match '/auth/:provider/callback', to: 'sessions#create'
    match '/auth/failure', to: redirect('/')
    match '/sign_out', to: 'sessions#destroy', as: 'sign_out'

    match '/change_locale', to: 'users#change_locale', as: 'change_locale'
    match '/home', to: 'users#home', as: 'home'
    match '/discover', to: 'users#discover', as: 'discover'

    match '/terms_of_service', to: 'pages#terms_of_service'
    match '/masthead', to: 'pages#masthead'
    match '/privacy', to: 'pages#privacy'

    root to: 'pages#index'
  end
end

非常感谢!

最佳答案

我猜你正在为 @user.characteristics 使用 nested_attributes。如果是这样,那么您应该将以下内容添加到您的用户模型中:

attr_accessible :characteristics_attributes
accepts_nested_attributes_for :characteristics

但是你的characteristics-form这部分还有一些不清楚的地方,你可能想要这样的东西:

= form_for(@user, url: wizard_path, method: :put) do |f|
    = render 'shared/error_messages', object: @user
    = f.fields_for :characteristics do |builder|

请注意,fields_for 可能会分别循环遍历每个特征并为每个特征呈现字段,因此您无需关心 @characteristic

关于ruby-on-rails - Rails Wicked Gem - 在一个向导中使用两个(嵌套)模型,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/16054675/

相关文章:

ruby-on-rails - Rails after_save 和 after_commit 陷阱

ruby-on-rails - 使用 Rails 的 asset pipeline 时如何获取实际文件路径(与 send_file 一起使用)

gem - 耙子释放不起作用

Ruby:自定义 gem 需要 'require' 用于其中的模块

ruby-on-rails - 一个干净的最小 gem 来添加一个简单的博客到现有的应用程序?

ruby-on-rails - 在 postgres : there is no transaction in progress 上测试规范时发出警告

ruby-on-rails - 如何撤消 bundle install --deployment?

ruby - 以 DRY 方式跨 rspec 规范共享工厂

ruby-on-rails - Rails catch-all/globbing 路线

ruby - rspec --drb 不适用于 Spork 的 RSpec