Class: HasHelpers::Cards::CardDataCommand
- Inherits:
-
Object
- Object
- HasHelpers::Cards::CardDataCommand
- Defined in:
- app/commands/has_helpers/cards/card_data_command.rb
Overview
Command object that resolves the effective card configuration (card + fields) for a given role/resource/identifier/record combo and returns serialized data for GraphQL or other consumers.
Usage:
result = HasHelpers::Cards::CardDataCommand.call(
role_id: role_id,
resource_id: resource_id,
identifier_id: identifier_id,
record_id: record_id
)
Usage (optimized API, receives a preloaded record to avoid N+1):
result = HasHelpers::Cards::CardDataCommand.call_with_record(
role_id: role_id,
resource_id: resource, # HasHelpers::Resource instance or id
identifier_id: identifier, # HasHelpers::Cards::CardIdentifier instance or id
record: record # ActiveRecord instance
)
result.card # => Hash
result.fields # => Array<Hash>
result.entries # => Array<Hash>
Defined Under Namespace
Classes: Response
Constant Summary collapse
- MAPPER_NOT_APPLIED =
Object.new
Class Method Summary collapse
-
.call(role_id:, resource_id:, identifier_id:, record_id:) ⇒ Object
Public entry point: original API, keeps backward compatibility.
-
.call_with_definition(resource_id:, card_definition:, record:) ⇒ Object
Public entry point: hover-only cards live entirely in-memory.
-
.call_with_record(role_id:, resource_id:, identifier_id:, record:) ⇒ Object
Public entry point: optimized variant that receives a preloaded record.
Instance Method Summary collapse
- #call ⇒ Object
-
#initialize(role_id:, resource_id:, identifier_id:, record_id: nil, record: nil, card_definition: nil) ⇒ CardDataCommand
constructor
Constructor supports both styles: - record_id only (classic) - record only (preloaded) - or both, but record takes precedence when present.
Constructor Details
#initialize(role_id:, resource_id:, identifier_id:, record_id: nil, record: nil, card_definition: nil) ⇒ CardDataCommand
Constructor supports both styles:
- record_id only (classic)
- record only (preloaded)
- or both, but record takes precedence when present.
71 72 73 74 75 76 77 78 79 80 |
# File 'app/commands/has_helpers/cards/card_data_command.rb', line 71 def initialize(role_id:, resource_id:, identifier_id:, record_id: nil, record: nil, card_definition: nil) @role = ::HasHelpers::Role.find_by(id: role_id) @resource = find_resource(resource_id) # Hover-only definitions are passed in-memory; we don't look up the CardIdentifier # option in the DB for those (the identifier may just be a plain string). @identifier = card_definition ? identifier_id : find_identifier(identifier_id) @record_id = record_id @record = record @card_definition = card_definition end |
Class Method Details
.call(role_id:, resource_id:, identifier_id:, record_id:) ⇒ Object
Public entry point: original API, keeps backward compatibility. It receives record_id and will load the record internally.
34 35 36 37 38 39 40 41 |
# File 'app/commands/has_helpers/cards/card_data_command.rb', line 34 def self.call(role_id:, resource_id:, identifier_id:, record_id:) new( role_id: role_id, resource_id: resource_id, identifier_id: identifier_id, record_id: record_id ).call end |
.call_with_definition(resource_id:, card_definition:, record:) ⇒ Object
Public entry point: hover-only cards live entirely in-memory. Caller supplies a pre-built (unpersisted) CardDefinition + preloaded record; no DB lookup for the definition is performed, and role customization is skipped.
57 58 59 60 61 62 63 64 65 |
# File 'app/commands/has_helpers/cards/card_data_command.rb', line 57 def self.call_with_definition(resource_id:, card_definition:, record:) new( role_id: nil, resource_id: resource_id, identifier_id: card_definition.identifier, record: record, card_definition: card_definition ).call end |
.call_with_record(role_id:, resource_id:, identifier_id:, record:) ⇒ Object
Public entry point: optimized variant that receives a preloaded record. This avoids doing resource.klass.find(record_id) for each card.
45 46 47 48 49 50 51 52 |
# File 'app/commands/has_helpers/cards/card_data_command.rb', line 45 def self.call_with_record(role_id:, resource_id:, identifier_id:, record:) new( role_id: role_id, resource_id: resource_id, identifier_id: identifier_id, record: record ).call end |
Instance Method Details
#call ⇒ Object
82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 116 |
# File 'app/commands/has_helpers/cards/card_data_command.rb', line 82 def call card_definition = @card_definition || find_card_definition! registry_card = registry_card_for(card_definition) role_resource_card = @card_definition ? nil : find_role_resource_card(card_definition) card_visible = resolve_card_visibility(card_definition, role_resource_card) card_position = resolve_card_position(card_definition, role_resource_card) # Build field configs with all metadata in memory. field_configs = build_field_configs(card_definition, role_resource_card, registry_card) # If the card is hidden for this role, we only return the card metadata. return Response.new( card: serialize_card(card_definition, card_visible, card_position), fields: [], entries: [] ) unless card_visible # In hover-only mode the parent record IS the target — no relationship navigation. relationship = @card_definition ? nil : relationship_for(card_definition, registry_card) targets = target_records( load_record, relationship, scope_for(card_definition, registry_card), expansion_scope_for(card_definition, registry_card), registry_card ) Response.new( card: serialize_card(card_definition, card_visible, card_position), fields: serialize_fields(field_configs), entries: build_entries(targets, field_configs, registry_card) ) end |