active_record-associated_object 0.8.2 → 0.8.3
Sign up to get free protection for your applications and to get access to all the features.
- checksums.yaml +4 -4
- data/Gemfile.lock +1 -1
- data/README.md +74 -1
- data/lib/active_record/associated_object/railtie.rb +7 -7
- data/lib/active_record/associated_object/version.rb +1 -1
- metadata +2 -2
checksums.yaml
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
---
|
2
2
|
SHA256:
|
3
|
-
metadata.gz:
|
4
|
-
data.tar.gz:
|
3
|
+
metadata.gz: 4212b6fcecceb21ae133688c2a3332d29b8c0f5760f5a22a8ba3450037a95b20
|
4
|
+
data.tar.gz: 4b96fde3db82d00a3c94153cb9b212f1091bd0040d7d9771d300f2a0a0147d6f
|
5
5
|
SHA512:
|
6
|
-
metadata.gz:
|
7
|
-
data.tar.gz:
|
6
|
+
metadata.gz: 262b75fdf718925e7772b7c1dd4e49ab6b73f6706be97081433712a4f3efef524b1677194ff5376415fe32e770bfa080afd5b347c2ccf78786517dfe5a21a9fb
|
7
|
+
data.tar.gz: 47c40f2a351cd49fe9bc5e0488d37ce79bcb3d30332b3aabbaff681ef7ac7f937d81d01c60d6b7f8393d3fc28f7fa92fb9b4d5eb99ae607d95d0389deea12764
|
data/Gemfile.lock
CHANGED
data/README.md
CHANGED
@@ -60,7 +60,7 @@ We've fixed this so you don't need to care, but this is what's happening.
|
|
60
60
|
> `has_object` only requires a namespace and an initializer that takes a single argument. The above `Post::Publisher` is perfectly valid as an Associated Object — same goes for `class Post::Publisher < Data.define(:post); end`.
|
61
61
|
|
62
62
|
> [!TIP]
|
63
|
-
> You can pass multiple names too: `has_object :publisher, :classified, :fortification`. I recommend `-[i]er`, `-[i]ed` and `-ion` as the general naming conventions for your Associated Objects.
|
63
|
+
> You can pass multiple names too: `has_object :seats, :entitlements, :publisher, :classified, :fortification`. I recommend `-s`, `-[i]er`, `-[i]ed` and `-ion` as the general naming conventions for your Associated Objects.
|
64
64
|
|
65
65
|
> [!TIP]
|
66
66
|
> Plural Associated Object names are also supported: `Account.has_object :seats` will look up `Account::Seats`.
|
@@ -87,6 +87,17 @@ end
|
|
87
87
|
|
88
88
|
### See Associated Objects in action
|
89
89
|
|
90
|
+
#### RubyVideo.dev
|
91
|
+
|
92
|
+
The team at https://www.rubyvideo.dev has been using Associated Objects to clarify the boundaries of their Active Records and collaborator Associated Objects.
|
93
|
+
|
94
|
+
See the usage in the source here:
|
95
|
+
|
96
|
+
- [`ActiveRecord::AssociatedObject` instances](https://github.com/search?q=repo%3Aadrienpoly%2Frubyvideo%20ActiveRecord%3A%3AAssociatedObject&type=code)
|
97
|
+
- [`has_object` calls](https://github.com/search?q=repo%3Aadrienpoly%2Frubyvideo+has_object&type=code)
|
98
|
+
|
99
|
+
#### Flipper
|
100
|
+
|
90
101
|
The team at [Flipper](https://www.flippercloud.io) used Associated Objects to help keep their new billing structure clean.
|
91
102
|
|
92
103
|
You can see real life examples in these blog posts:
|
@@ -240,6 +251,68 @@ class Post::PublisherTest < ActiveSupport::TestCase
|
|
240
251
|
end
|
241
252
|
```
|
242
253
|
|
254
|
+
### Polymorphic Associated Objects
|
255
|
+
|
256
|
+
If you want to share logic between associated objects, you can do so via standard Ruby modules:
|
257
|
+
|
258
|
+
```ruby
|
259
|
+
# app/models/pricing.rb
|
260
|
+
module Pricing
|
261
|
+
# If you need to share an `extension` across associated objects you can override `Module::included` like this:
|
262
|
+
def self.included(object) = object.extension do
|
263
|
+
# Add common integration methods onto `Account`/`User` when the module is included.
|
264
|
+
# See the `extension` block in the `Extending` section above for an example.
|
265
|
+
end
|
266
|
+
|
267
|
+
def price_set?
|
268
|
+
# Instead of referring to `account` or `user`, use the `record` method to target either.
|
269
|
+
record.price_cents.positive?
|
270
|
+
end
|
271
|
+
end
|
272
|
+
|
273
|
+
# app/models/account/pricing.rb
|
274
|
+
class Account::Pricing < ActiveRecord::AssociatedObject
|
275
|
+
include ::Pricing
|
276
|
+
end
|
277
|
+
|
278
|
+
# app/models/user/pricing.rb
|
279
|
+
class User::Pricing < ActiveRecord::AssociatedObject
|
280
|
+
include ::Pricing
|
281
|
+
end
|
282
|
+
```
|
283
|
+
|
284
|
+
Now we can call `account.pricing.price_set?` & `user.pricing.price_set?`.
|
285
|
+
|
286
|
+
> [!NOTE]
|
287
|
+
> Polymorphic Associated Objects are definitely a more advanced topic,
|
288
|
+
> so you need to know your Ruby module hierarchy and how to track what `self` changes to fairly well.
|
289
|
+
|
290
|
+
#### Using `ActiveSupport::Concern` as an alternative
|
291
|
+
|
292
|
+
If you prefer the look of Active Support concerns, here's the equivalent to the above Ruby module:
|
293
|
+
|
294
|
+
```ruby
|
295
|
+
# app/models/pricing.rb
|
296
|
+
module Pricing
|
297
|
+
extend ActiveSupport::Concern
|
298
|
+
|
299
|
+
included do
|
300
|
+
extension do
|
301
|
+
# Add common integration methods onto `Account`/`User` when the concern is included.
|
302
|
+
end
|
303
|
+
end
|
304
|
+
|
305
|
+
def price_set?
|
306
|
+
# Instead of referring to `account` or `user`, use the `record` method to target either.
|
307
|
+
record.price_cents.positive?
|
308
|
+
end
|
309
|
+
end
|
310
|
+
```
|
311
|
+
|
312
|
+
Active Support concerns have some extra features that standard Ruby modules don't, like support for deeply-nested concerns and `class_methods do`.
|
313
|
+
|
314
|
+
In this case, if you're reaching for those, you're probably building something too intricate and potentially brittle.
|
315
|
+
|
243
316
|
### Active Job integration via GlobalID
|
244
317
|
|
245
318
|
Associated Objects include `GlobalID::Identification` and have automatic Active Job serialization support that looks like this:
|
@@ -6,14 +6,14 @@ class ActiveRecord::AssociatedObject::Railtie < Rails::Railtie
|
|
6
6
|
end
|
7
7
|
end
|
8
8
|
|
9
|
-
initializer "
|
10
|
-
|
11
|
-
|
12
|
-
|
13
|
-
|
14
|
-
|
15
|
-
end
|
9
|
+
initializer "active_job.performs" do
|
10
|
+
require "active_job/performs"
|
11
|
+
ActiveRecord::AssociatedObject.extend ActiveJob::Performs if defined?(ActiveJob::Performs)
|
12
|
+
rescue LoadError
|
13
|
+
# We haven't bundled active_job-performs, so we're continuing without it.
|
14
|
+
end
|
16
15
|
|
16
|
+
initializer "object_association.setup" do
|
17
17
|
ActiveSupport.on_load :active_record do
|
18
18
|
require "active_record/associated_object/object_association"
|
19
19
|
include ActiveRecord::AssociatedObject::ObjectAssociation
|
metadata
CHANGED
@@ -1,14 +1,14 @@
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
2
2
|
name: active_record-associated_object
|
3
3
|
version: !ruby/object:Gem::Version
|
4
|
-
version: 0.8.
|
4
|
+
version: 0.8.3
|
5
5
|
platform: ruby
|
6
6
|
authors:
|
7
7
|
- Kasper Timm Hansen
|
8
8
|
autorequire:
|
9
9
|
bindir: bin
|
10
10
|
cert_chain: []
|
11
|
-
date: 2024-
|
11
|
+
date: 2024-12-13 00:00:00.000000000 Z
|
12
12
|
dependencies:
|
13
13
|
- !ruby/object:Gem::Dependency
|
14
14
|
name: activerecord
|