1

この質問には簡単な答えがあるはずですが、まだうまくいきません。

ユーザーがデータベースを使用してプロジェクトを管理できるようにする Ruby On Rails アプリがあります (作成、更新、表示、編集、破棄など)。たとえば、ユーザーがプロジェクトを編集すると、http://:3000/projects/3/edit のようなページに移動し、そこでフォームのエントリを変更できます。この例では、ユーザーがプロジェクト 3 を編集していることに注意してください。

プロジェクトを編集するには、ユーザーはこのボタンをクリックします

<td><%= button_to 'Edit', { :action => "edit", :id => project }, :method => :get %></td>

このメソッドを呼び出す

# GET /projects/1/edit
def edit
  @project = Project.find(params[:id])
end

そしてそれはうまくいきます。

ただし、別のメソッド呼び出し updateFields を追加したので、フィールドが変更されると、updateFields と呼ばれる JavaScript 関数が実行され、フォーム内の他の関連フィールドを変更する AJAX 要求が呼び出されます。以下は、updateFields からの抜粋です。

<script language="JavaScript" type="text/javascript">
function updateFields(){
    $.ajax({
        url: "<%= update_fields_projects_url %>",
        data: {
            project_year: $('.project_year_class').val(),
            project_type: $('.project_type_class').val(),

            <snip>

        }
    });
}
</script>

コントローラーでは、次のように params 配列で必要なすべての情報を取得できます。

# PUT /projects/1
# PUT /projects/1.json

def update_fields

  @project = Project.find(params[:project])
  @project_year = params[:project_year]
  @project_type = params[:project_type]

  <snip>

  respond_to do |format|
    if @project.update_attributes(params[:project])
      format.js
      format.html
    else
      format.html { render :action => "update" }
      format.json { render :json => @project.errors, :status => :unprocessable_entity }
    end
  end
end

私が抱えている問題は、フォームを更新できず、サーバー上に次のエラー メッセージが表示されることです。

ActiveRecord::RecordNotFound (Couldn't find Project without an ID):
app/controllers/projects_controller.rb:101:in `update_fields'

Rendered /var/lib/gems/1.8/gems/actionpack-3.2.9/lib/action_dispatch/middleware/templates/rescues/_trace.erb (1.5ms)
Rendered /var/lib/gems/1.8/gems/actionpack-3.2.9/lib/action_dispatch/middleware/templates/rescues/_request_and_response.erb (2.2ms)
Rendered /var/lib/gems/1.8/gems/actionpack-3.2.9/lib/action_dispatch/middleware/templates/rescues/diagnostics.erb within rescues/layout (10.8ms)

プロジェクトIDを直接指定すると、すべて正常に動作します

@project = Project.find(3)

私の質問は、project_year や project_type と同じ方法で、javascript 関数によってパラメーターで渡された ID を取得するにはどうすればよいですか? この例では 3 ですが、プロジェクトの作成時に割り当てられるため、プロジェクトごとに異なります。

アップデート1

<%= form_for(@project, :html => {:name => "ProjectInfo"}) do |f| %>

  <input type=button id=project_info_button_id value="Show Details" onclick="showHideDiv('project_info_id','project_info_button_id');">

  <div class="form input", id='project_info_id', style='display:none'>
    <% concat "Project Year" %>
    <%= f.text_field :ProjectYear, {:class=>"project_year_class", :Size=>6, :style=>"text-align:right"} %>

    <snip>

  <% end %>
<% end %>
4

2 に答える 2

0

ajax リクエストのデータ セクションでプロジェクト ID を渡す必要があります。

<script language="JavaScript" type="text/javascript">
function updateFields(){
    $.ajax({
        url: "<%= update_fields_projects_url %>",
        data: {
            project_year: $('.project_year_class').val(),
            project_type: $('.project_type_class').val(),
            id: <%= @project.id %>,
            <snip>

        }
    });
}
</script>
于 2012-11-16T18:31:25.693 に答える
0

ProjectsController正しいものを見つけようとしてProjectいますが、ID を指定していません。プロジェクト ID を指定するの値idに値を追加してから、 を に変更する必要があります。$.ajaxdatafindparams[:id]

余談ですが、update_fieldsへの更新を処理するために追加のメソッドは必要ありませんProject。Rails はすべてのPUTto/projects/:idProjectsControllerのメソッドにルーティングします (routes ファイルにあるとupdate仮定します)。使用する(またはプロジェクトを保存している変数) を指す代わりに、プロジェクト ID を手動で含める必要はありませんresources :projects$.ajaxupdate_fields_projects_urlproject_url(project)

詳細: Rails でリソースを更新できるデフォルトの方法をバイパスしています。つまり、必要のない多くの作業を手動で行っているということです。

ビューで、フォーム ヘルパーを使用します。

<%= form_for @project do |project_form| %>
    <%= project_form.text_field :year %>
    <%= project_form.text_field :type %>
<%= end %>

update次に、コントローラーのメソッドで作業するだけで済みます。これは、主に次のように記述されていupdate_fieldsます。

def update_fields

  @project = Project.find(params[:id])

  respond_to do |format|
    if @project.update_attributes(params[:project])
      format.js
      format.html
    else
      format.html { render :action => "update" }
      format.json { render :json => @project.errors, :status => :unprocessable_entity }
    end
  end
end

このようにすると、form_forはテキスト フィールドを作成し、その結果、コントローラは 内のすべてを取得しますparams[:project]。各属性を手動で抽出して適用する必要はありません。すべて無料で入手できます。

于 2012-11-16T18:11:55.147 に答える