Rails Has_Many通过添加多个

问题描述

我有一个具有交付和项目模型的应用程序,该模型通过delivery_item模型加入。

class Delivery < ApplicationRecord
  belongs_to :project
  has_many :delivery_items,dependent: :destroy
  has_many :items,through: :delivery_items

  enum status: [ :unapproved,:approved,:scheduled ]
end

 class Item < ApplicationRecord
  has_many :delivery_items,dependent: :destroy
  has_many :deliveries,through: :delivery_items

  enum status: [:unscheduled,:scheduled,:delivered]

end

class DeliveryItem < ApplicationRecord
  belongs_to :delivery
  belongs_to :item
end

我已经创建了以下表单,将每个项目添加到交货中

<h6>Add to Delivery</h6>
<%= form_for @delivery_item,html: {class: 'form-inline'} do |form| %>

  <div class="form-group">
    <%= form.collection_select :delivery_id,@project.deliveries.all,:id,:date,placeholder: 'Add to Delivery',class: 'form-control' %>
  </div>
    <%= form.hidden_field :item_id,value: item.id %>
  
  <div class="form-group">
    <%= form.submit "Add",class: 'btn btn-primary' %>

  </div>
<% end %>

这非常适合单独添加每个项目,但是当我尝试通过表单添加多个项目时

<%= form_for @delivery_item do |form| %>
              <div class="form-group">
                <%= form.collection_select :delivery_id,class: 'form-control' %>
              </div>
              <div class="form-group">
                <%= form.collection_check_boxes :item_id,location.items.unscheduled.all,:assembly_name %>
              </div>
              <div class="form-group">
            
                <%= form.submit class: 'btn btn-primary btn-block' %>
            
              </div>

我收到1条错误,禁止保存该delivery_item: 项目必须存在

然后我将item_id更改为item_ids,但得到了:

undefined method `item_ids' for #<DeliveryItem:0x00007fce6f6e0948>
Did you mean?  item_id
               item_id=
               item_id?

控制器

class Projects::DeliveriesController < ApplicationController
  before_action :set_delivery,only: [:show,:edit,:update,:destroy,:reset_item_status]
  before_action :reset_item_status,only: [:destroy]
  
  def show
    @delivery = Delivery.find(params[:id])
    @delivery_items = @delivery.items.all
    respond_to do |format|
      format.html
      format.pdf do
        render pdf: "some_name",template: "projects/deliveries/show.pdf.erb",layout: "pdf.html",margin: { top: 35,bottom: 35 }
      end
    end
  end
  # GET /deliveries/new
  def new
    @project = Project.find(params[:project_id])
    @delivery = Delivery.new
  end

  # GET /deliveries/1/edit
  def edit
  end

  # POST /deliveries
  # POST /deliveries.json
  def create
    @project = Project.find(params[:project_id])
    @delivery = Delivery.new(delivery_params)
    @delivery.project_id = @project.id
    respond_to do |format|
      if @delivery.save
        format.html { redirect_to @delivery.project,notice: 'Delivery was successfully created.' }
        format.json { render :show,status: :created,location: @delivery.project }
      else
        format.html { render :new }
        format.json { render json: @delivery.project.errors,status: :unprocessable_entity }
      end
    end
  end

  # PATCH/PUT /deliveries/1
  # PATCH/PUT /deliveries/1.json
  def update
    respond_to do |format|
      if @delivery.update(delivery_params)
        format.html { redirect_to @delivery.project,notice: 'Delivery was successfully updated.' }
        format.json { render :show,status: :ok,location: @delivery.project }
      else
        format.html { render :edit }
        format.json { render json: @delivery.project.errors,status: :unprocessable_entity }
      end
    end
  end

  # DELETE /deliveries/1
  # DELETE /deliveries/1.json
  def destroy
    @delivery = Delivery.find(params[:id])
    @project = Project.find(params[:project_id])
    title = @delivery.date
    if @delivery.destroy
      flash[:notice] = "One \'#{title}' was successfully destroyed."
      redirect_to @project 
    else
      flash[:notice] = "Error Yo"
      render :show
    end
  end
  
  def send_delivery_to_project_admin
    @delivery = Delivery.find(params[:delivery_id])
    @project = Project.find(params[:project_id])
    if @project.project_users.project_administrator.present?
      @project_administrator = @project.project_users.project_administrator
      DeliveryMailer.delivery_ready_to_schedule_email(@delivery,@project_administrator).deliver_now
      redirect_to approval_confirmation_path,notice: 'Mail was successfully sent.'
    else
      redirect_to @project,:flash => { error: 'Email not sent,no Project Administrator present' }
    end
  end

  def send_delivery_approval_request_to_project_manager
    @delivery = Delivery.find(params[:delivery_id])
    @project = Project.find(params[:project_id])
    if @project.project_users.project_manager.present?
      @project_manager = @project.project_users.project_manager
      DeliveryMailer.delivery_requires_approval_email(@delivery,@project_manager).deliver
      redirect_to @project,no Project Manager present' }
    end
  end

  def approval
    @delivery = Delivery.find(params[:delivery_id])
    @project = Project.find(params[:project_id])
    @delivery.approved!
    redirect_to project_delivery_send_delivery_to_project_admin_path,notice: 'Delivery was approved.'
  end

  def scheduled
    @delivery = Delivery.find(params[:delivery_id])
    @project = Project.find(params[:project_id])
    @delivery.scheduled!
    redirect_to delivery_confirmation_path,notice: 'Delivery was scheduled.'
  end

  def reset_item_status
    @delivery.items.update_all(status: 0)
  end

  private
  def set_delivery
    @delivery = Delivery.find(params[:id])
  end

    # Never trust parameters from the scary internet,only allow the white list through.
    def delivery_params
      params.require(:delivery).permit(:date,:project_id,:search,item_ids: [])
    end
end

class Projects::ItemsController < ApplicationController

  # GET /items/new
  def new
    @project = Project.find(params[:project_id])
    @item = Item.new
  end

  def index
    @project = Project.find(params[:project_id])
    @items = @project.items.all
    respond_to do |format|
      format.html
      format.csv { send_data @items.to_csv }
    end
  end
  # GET /items/1/edit
  def edit
  end

  # POST /items
  # POST /items.json
  def create
    @project = Project.find(params[:project_id])
    @item = Item.new(item_params)
    @item.project_id = @project.id
    respond_to do |format|
      if @item.save
        format.html { redirect_to @item.project,notice: 'Item was successfully created.' }
        format.json { render :show,location: @item.project }
      else
        format.html { redirect_to @item.project,error: 'Item had an issue' }
        puts @item.errors.full_messages
        format.json { render json: @item.project.errors,status: :unprocessable_entity }
      end
    end
  end

  # PATCH/PUT /items/1
  # PATCH/PUT /items/1.json
  def update
    @item = Item.find(params[:id])
    @project = Project.find(params[:project_id])
    respond_to do |format|
      if @item.update(item_params)
        format.html { redirect_to @item.project,notice: 'Item was successfully updated.' }
        format.json { render :show,location: @item.project }
      else
        format.html { render :edit }
        format.json { render json: @item.project.errors,status: :unprocessable_entity }
      end
    end
  end

  # DELETE /items/1
  # DELETE /items/1.json
  def destroy
    @item = Item.find(params[:id])
    @project = Project.find(params[:project_id])
    if @item.destroy
      flash[:notice] = "One \'#{@item.part_number.name}' was successfully destroyed."
      redirect_to @project 
    else
      flash[:notice] = "Error Yo"
      render :show
    end
  end

  def import
    @project = Project.find(params[:project_id])
    @project.items.import(params[:file])
    redirect_to project_path(@project),notice: "Sucessfully Imported Items!"
   end

  private
    # Use callbacks to share common setup or constraints between actions.

    # Never trust parameters from the scary internet,only allow the white list through.
    def item_params
      params.require(:item).permit(:project_id,:part_number_id,:assembly_id,:location_id)
    end
end

class DeliveryItemsController < ApplicationController
 before_action :set_delivery_item,only: [:destroy]
 before_action :set_items,only: [:new,:edit]
  # GET /delivery_items/new
  def new
    @delivery_item = DeliveryItem.new
  end

  # GET /delivery_items/1/edit
  def edit
  end

  # POST /delivery_items
  # POST /delivery_items.json
  def create
    @delivery_item = DeliveryItem.new(delivery_item_params)
    respond_to do |format|
      if @delivery_item.save
        @delivery_item.item.status = 1
        @delivery_item.item.save!
        format.html { redirect_to @delivery_item.item.project,notice: 'Item Added to Delivery' }
        format.json { render :show,location: @delivery_item.item.project }
      else
        format.html { render :new }
        format.json { render json: @delivery_item.item.project.errors,status: :unprocessable_entity }
      end
    end
  end

  # PATCH/PUT /delivery_items/1
  # PATCH/PUT /delivery_items/1.json


  # DELETE /delivery_items/1
  # DELETE /delivery_items/1.json
  def destroy
    @delivery_item.destroy
    respond_to do |format|
      @delivery_item.item.status = 0
      @delivery_item.item.save!
      format.html { redirect_to @delivery_item.item.project,notice: 'Delivery item was successfully destroyed.' }
      format.json { head :no_content }
    end
  end

  

  private
    # Use callbacks to share common setup or constraints between actions.
    def set_delivery_item
      @delivery_item = DeliveryItem.find(params[:id])
    end
    
    def set_items
      @items = Item.all
    end

    # Never trust parameters from the scary internet,only allow the white list through.
    def delivery_item_params
      params.require(:delivery_item).permit(:delivery_id,:item_id,item_ids:[])
    end
end

路线

Rails.application.routes.draw do
  resources :locations
  resources :part_numbers
  resources :assemblies
  resources :delivery_items
  resources :projects do
    resources :project_users,path: :users,module: :projects
    resources :items,controller: 'projects/items' do
      collection {post :import}
    end
    resources :locations,controller: 'projects/locations'
    resources :deliveries,controller: 'projects/deliveries' do
      get :send_delivery_approval_request_to_project_manager,to: 'projects/deliveries#send_delivery_approval_request_to_project_manager',as: :send_delivery_approval_request_to_project_manager
      get :send_delivery_to_project_admin,to: 'projects/deliveries#send_delivery_to_project_admin',as: :send_delivery_to_project_admin
      get :approval,to: 'projects/deliveries#approval',as: :approval
    end
    resources :assemblies,controller: 'projects/assemblies'
  end

我已经搜索了尽可能多的教程/问题等等,我将不胜感激

解决方法

暂无找到可以解决该程序问题的有效方法,小编努力寻找整理中!

如果你已经找到好的解决方法,欢迎将解决方案带上本链接一起发送给小编。

小编邮箱:dio#foxmail.com (将#修改为@)