Warning: file_get_contents(/data/phpspider/zhask/data//catemap/2/ruby-on-rails/60.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
Mysql Rails:查找尚未通过联接表连接的所有资源_Mysql_Ruby On Rails_Ruby On Rails 3_Activerecord_Rails Activerecord - Fatal编程技术网

Mysql Rails:查找尚未通过联接表连接的所有资源

Mysql Rails:查找尚未通过联接表连接的所有资源,mysql,ruby-on-rails,ruby-on-rails-3,activerecord,rails-activerecord,Mysql,Ruby On Rails,Ruby On Rails 3,Activerecord,Rails Activerecord,我正试图重写将产品与项目连接和断开连接的操作。目前,我的select_to_项目视图显示所有产品,但我希望它仅显示尚未连接到给定项目的产品 产品和项目通过联接表连接 class Product < ActiveRecord::Base has_and_belongs_to_many :projects, :join_table => "projects_products" end class Project < ActiveRecord::Base has_and

我正试图重写将产品与项目连接和断开连接的操作。目前,我的select_to_项目视图显示所有产品,但我希望它仅显示尚未连接到给定项目的产品

产品和项目通过联接表连接

class Product < ActiveRecord::Base
  has_and_belongs_to_many :projects, :join_table => "projects_products"  
end

class Project < ActiveRecord::Base
  has_and_belongs_to_many :products, :join_table => "projects_products" 
end

class ProjectsProduct < ActiveRecord::Base
  attr_accessible :project_id, :product_id

  belongs_to :project
  belongs_to :product
end
显然,select_to_项目视图当前显示所有可能的产品,甚至是那些已经通过联接表连接的产品

我认为select_to_项目操作应该更改为如下内容:

def select_to_project
  @project = Project.find(params[:id])
  @products = Product.joins(:projects => :products).where('products_projects_join.product_id IS NOT ?', @product)
end
但我当前在尝试加载相对视图时遇到一个MySQL错误:

Mysql::Error: You have an error in your SQL syntax; check the manual that corresponds to your MySQL server version for the right syntax to use near '1)' at line 1: SELECT `products`.* FROM `products` INNER JOIN `projects_products` ON `projects_products`.`product_id` = `products`.`id` INNER JOIN `projects` ON `projects`.`id` = `projects_products`.`project_id` INNER JOIN `projects_products` `products_projects_join` ON `products_projects_join`.`project_id` = `projects`.`id` INNER JOIN `products` `products_projects` ON `products_projects`.`id` = `products_projects_join`.`product_id` WHERE (products_projects_join.project_id IS NOT 1)
如何让这个查询在Rails 3中工作

事先非常感谢

更新

多亏了@Sebastian Palma,视图现在已经构建,但查询结果并不正确

@products = Product.joins(:projects => :products).where('products_projects_join.project_id != ?', @project.id).uniq.order(:id, :order => 'id ASC')
将生成以下查询:

SELECT DISTINCT 'products'.* FROM 'products' INNER JOIN 'projects_products' ON 'projects_products'.'product_id' = 'products'.'id' INNER JOIN 'projects' ON 'projects'.'id' = 'projects_products'.'project_id' INNER JOIN 'projects_products' 'products_projects_join' ON 'products_projects_join'.'project_id' = 'projects'.'id' INNER JOIN 'products' 'products_projects' ON 'products_projects'.'id' = 'products_projects_join'.'product_id' WHERE (products_projects_join.project_id != 2) ORDER BY id, '--- \n:order: id ASC\n'
我有14个产品条目,项目2已经连接到其中的4个

projects_products_id / project_id / product_id
3 2 1
4 2 2
5 2 3
6 2 12
我的查询应该显示ID为:4、5、6、7、8、9、10、11、13、14的产品

它当前显示产品3、4、5、6、7、8、9、10、12、13

产品14当前不在联接表中,3和12已连接,11未连接

这就好像查询结果向左滑动了一个id值


理想情况下,我希望从products表中查找尚未在联接表上连接到给定项目的所有条目。

您已经设置了关联,因为有多个项目有_和_属于_,但HABTM是无头的,因此实际上也没有意义使用联接模型

相反,您希望将Association设置为通过:并为表使用常规名称

首先将联接表重命名为project_products,并确保它有一个id列

class Product < ActiveRecord::Base
  has_many :project_products 
  has_many :projects, through: project_products 
end

class Project < ActiveRecord::Base
  has_many :project_products 
  has_many :products, through: project_products 
end

class ProjectProduct < ActiveRecord::Base
  attr_accessible :project_id, :product_id
  belongs_to :project
  belongs_to :product
end
这将创建以下查询:

SELECT "products".* FROM "products" 
WHERE "products"."id" NOT IN (
  SELECT "products"."id" FROM "products" 
  INNER JOIN "project_products" ON "products"."id" = "project_products"."product_id" 
  WHERE "project_products"."project_id" = $1
) LIMIT $2
但是,在Rails 4.0中引入了where.not。作为一种解决方法,您可以在Rails 3中使用字符串

class Product < ApplicationRecord
  has_many :project_products
  has_many :projects, through: :project_products

  def self.not_assigned_to_project(project)
    Product.where("
      products.id NOT IN (#{project.products.select(:id).to_sql})
    ")
  end
end

你想用“不”来实现什么?在“产品项目加入.产品id!=?”中尝试@product.id.@SebastianPalma谢谢我一直以为不是==!=。现在,使用@products=Product.joins:projects=>:products.where'products\u projects\u join.project\u id!=?'@project.id.uniq.order:id,:order=>“id ASC”视图呈现,但查询结果不正确。我将在我的问题中添加更多信息。@SebastianPalma我添加了一些数据。结果似乎总是id-1。就像产品[0]是第一个条目一样。你知道为什么会这样吗?我怎么才能做到这一点呢?我没有安装Rails 3,所以这段代码只是在Rails 6中测试的。您的国籍可能不同。非常感谢。我怀疑我必须使用@products=Product.not_分配给_project@project在我的控制器里?根据您的输入,我得到:Mysql::错误:字段列表中的“id”列不明确:选择“产品”。*从“产品”中选择products.id不在“产品”中的“产品”内部连接“项目产品”。“id”=“项目产品”。“产品id”中的“项目产品”。“项目id”=2 HABTM和has之间的区别:是什么后者使用一个模型来连接,另外HABTM使用了一个愚蠢的表命名方案,这违反了rails中的所有其他约定。HABTM实际上非常无用,因为您无法查询联接表或向联接表添加任何附加数据。你设置它的方式似乎很愚蠢。这两种方法都有缺点,但都没有优点:。类名选项必须是类“Author”的实际名称。但是如果你问一个新问题会更好。
SELECT "products".* FROM "products" 
WHERE "products"."id" NOT IN (
  SELECT "products"."id" FROM "products" 
  INNER JOIN "project_products" ON "products"."id" = "project_products"."product_id" 
  WHERE "project_products"."project_id" = $1
) LIMIT $2
class Product < ApplicationRecord
  has_many :project_products
  has_many :projects, through: :project_products

  def self.not_assigned_to_project(project)
    Product.where("
      products.id NOT IN (#{project.products.select(:id).to_sql})
    ")
  end
end