【问题标题】:Rails Mongoid search parents elements that have at least one childRails Mongoid 搜索至少有一个子元素的父元素
【发布时间】:2014-07-24 05:45:04
【问题描述】:

我有一个 rails 4 应用程序,我有 2 个对象:商店和书籍(引用 1:n 关系)。 一家商店有很多书,每本书都属于一家商店。有些商店没有书。 如何进行查询以找到至少有 1 本书的 3 家最新的商店 - 以及没有书籍的 3 家最新的商店?

@stores = Store.order_by(:created_at => 'desc').limit(4).uniq
@books = Book.order_by(:created_at => 'desc').limit(4).uniq

这项工作,但我不知道如何为商店或 @books 做一个 where(book.exists?) 以确保每本书都属于一个独特的商店。

【问题讨论】:

    标签: search ruby-on-rails-4 mongoid children


    【解决方案1】:

    MongoDB 中的基本 CRUD 操作对 单个 集合进行操作, “加入”功能尚未实现,这将允许它们跨两个集合进行操作。 一旦你理解了这一点,你就可以很容易地构造两个操作来做你想做的事情。 鉴于您提供的架构提示,以下是最明显的。 要执行更多操作,您可能需要考虑架构更改,例如嵌入。

    根据定义,您提供的架构只允许一本书属于一个(根据定义是唯一的)商店。 您可以从对书籍的检查中看到这一点,每本书都有一个值 store_id。 希望这有助于您的理解。

    app/models/store.rb

    class Store
      include Mongoid::Document
      include Mongoid::Timestamps
      field :name, type: String
    
      has_many :books
    end
    

    app/models/book.rb

    class Book
      include Mongoid::Document
      include Mongoid::Timestamps
      field :title, type: String
    
      belongs_to :store
    end
    

    test/unit/store_test.rb

    需要'test_helper' 需要'pp'

    class StoreTest < ActiveSupport::TestCase
      def setup
        Mongoid.default_session.drop
      end
      test '0. mongoid version' do
        puts "\nMongoid::VERSION:#{Mongoid::VERSION}\nMoped::VERSION:#{Moped::VERSION}"
      end
      test 'store query has book, does not have book' do
        [
            ["Amazon.com", ["Outlander", "Taking It All"]],
            ["Barnes & Noble", ["Big Little Lies"]],
            ["Goodreads", []],
            ["Greenlight Bookstore", []],
            ["Powell's Books", ["Gone Girl", "Dark Skye"]],
            ["Strand Books", []]
        ].each do |store, books|
         store = Store.create(name: store)
         books.each do |title|
           store.books << Book.create(title: title)
         end
         sleep 1
        end
        assert_equal(6, Store.count)
        assert_equal(5, Book.count)
        puts
        store_ids_with_books = Book.distinct(:store_id)
        latest_stores_with_a_book = Store.in(_id: store_ids_with_books).order_by(:created_at => 'desc').limit(3).to_a
        puts "three latest stores with a book:"
        pp latest_stores_with_a_book
        latest_stores_without_a_book = Store.nin(_id: store_ids_with_books).order_by(:created_at => 'desc').limit(3).to_a
        puts "three latest stores without a book:"
        pp latest_stores_without_a_book
        puts "books:"
        pp Book.all.to_a
      end
    end
    

    耙式测试

    Run options: 
    
    # Running tests:
    
    [1/2] StoreTest#test_0._mongoid_version
    Mongoid::VERSION:3.1.6
    Moped::VERSION:1.5.2
    [2/2] StoreTest#test_store_query_has_book,_does_not_have_book
    three latest stores with a book:
    [#<Store _id: 53f257287f11ba75e5000008, created_at: 2014-08-18 19:42:32 UTC, updated_at: 2014-08-18 19:42:32 UTC, name: "Powell's Books">,
     #<Store _id: 53f257257f11ba75e5000004, created_at: 2014-08-18 19:42:29 UTC, updated_at: 2014-08-18 19:42:29 UTC, name: "Barnes & Noble">,
     #<Store _id: 53f257247f11ba75e5000001, created_at: 2014-08-18 19:42:27 UTC, updated_at: 2014-08-18 19:42:27 UTC, name: "Amazon.com">]
    three latest stores without a book:
    [#<Store _id: 53f257297f11ba75e500000b, created_at: 2014-08-18 19:42:33 UTC, updated_at: 2014-08-18 19:42:33 UTC, name: "Strand Books">,
     #<Store _id: 53f257277f11ba75e5000007, created_at: 2014-08-18 19:42:31 UTC, updated_at: 2014-08-18 19:42:31 UTC, name: "Greenlight Bookstore">,
     #<Store _id: 53f257267f11ba75e5000006, created_at: 2014-08-18 19:42:30 UTC, updated_at: 2014-08-18 19:42:30 UTC, name: "Goodreads">]
    books:
    [#<Book _id: 53f257247f11ba75e5000002, created_at: 2014-08-18 19:42:28 UTC, updated_at: 2014-08-18 19:42:28 UTC, title: "Outlander", store_id: "53f257247f11ba75e5000001">,
     #<Book _id: 53f257247f11ba75e5000003, created_at: 2014-08-18 19:42:28 UTC, updated_at: 2014-08-18 19:42:28 UTC, title: "Taking It All", store_id: "53f257247f11ba75e5000001">,
     #<Book _id: 53f257257f11ba75e5000005, created_at: 2014-08-18 19:42:29 UTC, updated_at: 2014-08-18 19:42:29 UTC, title: "Big Little Lies", store_id: "53f257257f11ba75e5000004">,
     #<Book _id: 53f257287f11ba75e5000009, created_at: 2014-08-18 19:42:32 UTC, updated_at: 2014-08-18 19:42:32 UTC, title: "Gone Girl", store_id: "53f257287f11ba75e5000008">,
     #<Book _id: 53f257287f11ba75e500000a, created_at: 2014-08-18 19:42:32 UTC, updated_at: 2014-08-18 19:42:32 UTC, title: "Dark Skye", store_id: "53f257287f11ba75e5000008">]
    Finished tests in 6.193234s, 0.3229 tests/s, 0.3229 assertions/s.             
    2 tests, 2 assertions, 0 failures, 0 errors, 0 skips
    

    【讨论】:

      猜你喜欢
      • 2023-04-03
      • 1970-01-01
      • 2011-01-30
      • 2019-08-20
      • 2013-12-28
      • 1970-01-01
      • 1970-01-01
      • 2020-08-26
      • 1970-01-01
      相关资源
      最近更新 更多