Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Mongoid: embedded documents automatically initializing on construction of parent

Is there a way to get embedded documents to initialize automatically on construction in mongoid? What I mean is given that User which embeds a garage document. I have to write the following code to fully set up the user with the garage:

user = User.create!(name: "John")
user.build_garage
user.garage.cars << Car.create!(name: "Bessy")

Is there a way I can skip calling user.build_garage?

Thanks

like image 392
GTDev Avatar asked Nov 09 '11 05:11

GTDev


People also ask

What is embedded document in MongoDB?

Embedded documents are an efficient and clean way to store related data, especially data that’s regularly accessed together. In general, when designing schemas for MongoDB, you should prefer embedding by default, and use references and application-side or database-side joins only when they’re worthwhile.

What is a relation object in Mongoid?

All relation objects in Mongoid are proxies to the actual document or documents themselves, which provide extra functionality for accessing, replacing, appending and persisting.

How many levels can a document be nested in MongoDB?

In MongoDB, you can only nest document up to 100 levels. The overall document size must not exceed 16 MB. Creating Embedded Documents – In MongoDB, you can easily embed a document inside another document.

How to design a high-performing MongoDB schema?

In general, when designing schemas for MongoDB, you should prefer embedding by default, and use references and application-side or database-side joins only when they’re worthwhile. The more often a given workload can retrieve a single document and have all the data it needs, the more consistently high-performance your application will be.


2 Answers

Mongoid 3 have autobuild option which tells Mongoid to instantiate a new document when the relation is accessed and it is nil.

embeds_one :label, autobuild: true
has_one :producer, autobuild: true
like image 116
jpalumickas Avatar answered Sep 19 '22 16:09

jpalumickas


You can add a callback to the User model like this:

class User
  ...
  after_initialize do |u|
    u.build_garage unless u.garage
  end
  ...
end

This callback fires after each instantiation of the class, so it fires after 'find' and 'new'.

like image 22
moritz Avatar answered Sep 19 '22 16:09

moritz