Class: Familia::IndexDescriptor
- Inherits:
-
Data
- Object
- Data
- Familia::IndexDescriptor
- Defined in:
- lib/familia/index_descriptor.rb
Overview
IndexDescriptor pairs an owning Horreum class with one of its IndexingRelationship configs and exposes behavior that hides the index's method-naming and storage internals — iteration, rebuild, and format checks. The IndexingRelationship itself has no back-reference to its owner, so this wrapper supplies that pairing for project-wide use.
Obtain descriptors via the project-wide aggregators (Familia.unique_indexes, Familia.index_descriptors, ...) rather than constructing them directly.
Instance Attribute Summary collapse
-
#owner ⇒ Object
readonly
Returns the value of attribute owner.
-
#relationship ⇒ Object
readonly
Returns the value of attribute relationship.
Instance Method Summary collapse
- #cardinality ⇒ Object
- #class_level? ⇒ Boolean
-
#coordinate ⇒ String
Stable "Owner:index_name" coordinate, e.g.
-
#each_record(value: nil, scope: nil, **opts, &block) ⇒ Enumerator, Object
Iterate the indexed records, resolving the right backing collection so callers never touch +send(index_name)+ or the +_for+ factory:.
-
#field ⇒ Object
--- Delegated metadata (read-only views of the IndexingRelationship) ---.
-
#format_current?(**opts) ⇒ Boolean
Convenience inverse of #stale_format?.
- #index_name ⇒ Object
- #multi? ⇒ Boolean
- #query? ⇒ Boolean
-
#rebuild!(scope: nil, **opts) ⇒ Integer
Rebuild this index from the source of truth, delegating to the generated +rebuild_
+ method. - #scope_class ⇒ Object
-
#stale_format?(sample: 100) ⇒ Boolean
Whether the index's stored data predates the current (raw) storage format — i.e.
- #unique? ⇒ Boolean
- #within ⇒ Object
Instance Attribute Details
#owner ⇒ Object (readonly)
Returns the value of attribute owner
23 24 25 |
# File 'lib/familia/index_descriptor.rb', line 23 def owner @owner end |
#relationship ⇒ Object (readonly)
Returns the value of attribute relationship
23 24 25 |
# File 'lib/familia/index_descriptor.rb', line 23 def relationship @relationship end |
Instance Method Details
#cardinality ⇒ Object
28 |
# File 'lib/familia/index_descriptor.rb', line 28 def cardinality = relationship.cardinality |
#class_level? ⇒ Boolean
32 |
# File 'lib/familia/index_descriptor.rb', line 32 def class_level? = relationship.class_level? |
#coordinate ⇒ String
Stable "Owner:index_name" coordinate, e.g. "User:email_lookup".
39 40 41 |
# File 'lib/familia/index_descriptor.rb', line 39 def coordinate Familia.join(owner.name, index_name) end |
#each_record(value: nil, scope: nil, **opts, &block) ⇒ Enumerator, Object
Iterate the indexed records, resolving the right backing collection so callers never touch +send(index_name)+ or the +_for+ factory:
- class-level unique -> owner.
(HashKey, reference) - class-level multi -> owner.
_for(value) (UnsortedSet) [value:] - instance-scoped -> requires scope: (the within instance)
54 55 56 |
# File 'lib/familia/index_descriptor.rb', line 54 def each_record(value: nil, scope: nil, **opts, &block) backing(value: value, scope: scope).each_record(**opts, &block) end |
#field ⇒ Object
--- Delegated metadata (read-only views of the IndexingRelationship) ---
26 |
# File 'lib/familia/index_descriptor.rb', line 26 def field = relationship.field |
#format_current?(**opts) ⇒ Boolean
Convenience inverse of #stale_format?.
98 99 100 |
# File 'lib/familia/index_descriptor.rb', line 98 def format_current?(**opts) !stale_format?(**opts) end |
#index_name ⇒ Object
27 |
# File 'lib/familia/index_descriptor.rb', line 27 def index_name = relationship.index_name |
#multi? ⇒ Boolean
34 |
# File 'lib/familia/index_descriptor.rb', line 34 def multi? = cardinality == :multi |
#query? ⇒ Boolean
31 |
# File 'lib/familia/index_descriptor.rb', line 31 def query? = relationship.query |
#rebuild!(scope: nil, **opts) ⇒ Integer
Rebuild this index from the source of truth, delegating to the generated
+rebuild_
67 68 69 70 71 72 73 74 75 76 77 |
# File 'lib/familia/index_descriptor.rb', line 67 def rebuild!(scope: nil, **opts) target = resolve_target(scope) rebuilder = :"rebuild_#{index_name}" unless target.respond_to?(rebuilder) raise Familia::Problem, "#{coordinate} has no generated rebuilder (declared query: false). " \ 'Migrate it by re-saving the affected records, or declare it query: true.' end target.public_send(rebuilder, **opts) end |
#scope_class ⇒ Object
30 |
# File 'lib/familia/index_descriptor.rb', line 30 def scope_class = relationship.scope_class |
#stale_format?(sample: 100) ⇒ Boolean
Whether the index's stored data predates the current (raw) storage format — i.e. still holds legacy JSON-encoded identifiers from pre-2.10.0 writes. Samples raw values without deserializing, so no read-time warnings fire.
Only class-level unique indexes have a single backing key that can be sampled without a value/scope; multi and instance-scoped indexes return false here (check them per-bucket / per-scope with #each_record).
89 90 91 92 93 |
# File 'lib/familia/index_descriptor.rb', line 89 def stale_format?(sample: 100) return false unless class_level? && unique? sample_raw_values(sample).any? { |v| Familia.legacy_json_encoded?(v) } end |
#unique? ⇒ Boolean
33 |
# File 'lib/familia/index_descriptor.rb', line 33 def unique? = cardinality == :unique |
#within ⇒ Object
29 |
# File 'lib/familia/index_descriptor.rb', line 29 def within = relationship.within |