Class: BSV::Registry::Client
- Inherits:
-
Object
- Object
- BSV::Registry::Client
- Defined in:
- lib/bsv/registry/client.rb
Overview
Client for managing on-chain registry definitions for protocols, baskets, and certificate types on the BSV overlay network.
Registry operators use this client to establish canonical references for basket IDs, protocol specifications, and certificate schemas via PushDrop-based UTXOs.
All overlay dependencies (broadcaster, resolver) are injectable for testing.
Instance Method Summary collapse
-
#initialize(wallet:, originator: nil, broadcaster: nil, resolver: nil) ⇒ Client
constructor
A new instance of Client.
-
#list_own_registry_entries(definition_type) ⇒ Array<RegisteredDefinition>
Lists the registry operator’s own published definitions for the given type.
-
#register_definition(definition_type, data) ⇒ BSV::Overlay::OverlayBroadcastResult
Publishes a new on-chain definition for baskets, protocols, or certificates.
-
#resolve(definition_type, query) ⇒ Array<RegisteredDefinition>
Resolves registry definitions of a given type using the overlay lookup service.
-
#resolve_basket(query = {}) ⇒ Array<RegisteredDefinition>
Resolves basket registry definitions.
-
#resolve_certificate(query = {}) ⇒ Array<RegisteredDefinition>
Resolves certificate type registry definitions.
-
#resolve_protocol(query = {}) ⇒ Array<RegisteredDefinition>
Resolves protocol registry definitions.
-
#revoke_definition(registered_definition) ⇒ BSV::Overlay::OverlayBroadcastResult
Revokes an existing registry definition by spending its UTXO.
-
#update_definition(registered_definition, new_data) ⇒ BSV::Overlay::OverlayBroadcastResult
Updates an existing registry definition by revoking it and registering new data.
Constructor Details
#initialize(wallet:, originator: nil, broadcaster: nil, resolver: nil) ⇒ Client
Returns a new instance of Client.
37 38 39 40 41 42 |
# File 'lib/bsv/registry/client.rb', line 37 def initialize(wallet:, originator: nil, broadcaster: nil, resolver: nil) @wallet = wallet @originator = originator @broadcaster = broadcaster @resolver = resolver end |
Instance Method Details
#list_own_registry_entries(definition_type) ⇒ Array<RegisteredDefinition>
Lists the registry operator’s own published definitions for the given type.
Queries the wallet for spendable outputs in the appropriate basket, then parses the PushDrop scripts back into structured definition data.
164 165 166 167 168 169 170 171 172 173 174 175 176 177 178 179 180 181 182 183 184 185 186 187 188 |
# File 'lib/bsv/registry/client.rb', line 164 def list_own_registry_entries(definition_type) basket_name = basket_name_for(definition_type) list_result = @wallet.list_outputs( basket: basket_name, include: 'entire transactions', originator: @originator ) outputs = list_result[:outputs] || list_result['outputs'] || [] beef_raw = list_result[:beef] || list_result['beef'] || list_result[:BEEF] || list_result['BEEF'] normalised_beef = normalise_beef(beef_raw) return [] if normalised_beef.nil? || outputs.empty? beef = BSV::Transaction::Beef.from_binary(normalised_beef) outputs.filter_map do |output| next unless spendable?(output) begin parse_own_output_to_registered_definition(definition_type, output, beef, beef_raw) rescue StandardError nil end end end |
#register_definition(definition_type, data) ⇒ BSV::Overlay::OverlayBroadcastResult
Publishes a new on-chain definition for baskets, protocols, or certificates.
The definition data is encoded in a PushDrop-based UTXO and broadcast to the appropriate overlay topic for the given definition type.
56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 |
# File 'lib/bsv/registry/client.rb', line 56 def register_definition(definition_type, data) registry_operator = identity_key fields = build_pushdrop_fields(definition_type, data, registry_operator) protocol_id = protocol_for(definition_type) template = BSV::Script::PushDropTemplate.new(wallet: @wallet, originator: @originator) locking_script = template.lock( fields: fields, protocol_id: protocol_id, key_id: Constants::KEY_ID, counterparty: 'anyone' ) basket_name = basket_name_for(definition_type) create_result = @wallet.create_action( description: "Register a new #{definition_type} definition", outputs: [ { satoshis: Constants::TOKEN_AMOUNT, locking_script: locking_script.to_hex, output_description: "New #{definition_type} registration token", basket: basket_name } ], options: { randomize_outputs: false }, originator: @originator ) raise "Register failed: could not create #{definition_type} registration transaction" if create_result[:tx].nil? tx = BSV::Transaction::Tx.from_beef(normalise_beef(create_result[:tx])) broadcaster_for(definition_type).broadcast(tx).raise_if_error! end |
#resolve(definition_type, query) ⇒ Array<RegisteredDefinition>
Resolves registry definitions of a given type using the overlay lookup service.
98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 |
# File 'lib/bsv/registry/client.rb', line 98 def resolve(definition_type, query) service = service_for(definition_type) question = BSV::Overlay::LookupQuestion.new( service: service, query: query ) answer = resolver_for.query(question) return [] unless answer.type == 'output-list' answer.outputs.filter_map do |output| parse_output_to_registered_definition(definition_type, output) rescue StandardError nil end end |
#resolve_basket(query = {}) ⇒ Array<RegisteredDefinition>
Resolves basket registry definitions.
Thin wrapper around #resolve for cross-SDK parity with the Go SDK’s ResolveBasket method.
125 126 127 |
# File 'lib/bsv/registry/client.rb', line 125 def resolve_basket(query = {}) resolve(DefinitionType::BASKET, query) end |
#resolve_certificate(query = {}) ⇒ Array<RegisteredDefinition>
Resolves certificate type registry definitions.
Thin wrapper around #resolve for cross-SDK parity with the Go SDK’s ResolveCertificate method.
153 154 155 |
# File 'lib/bsv/registry/client.rb', line 153 def resolve_certificate(query = {}) resolve(DefinitionType::CERTIFICATE, query) end |
#resolve_protocol(query = {}) ⇒ Array<RegisteredDefinition>
Resolves protocol registry definitions.
Thin wrapper around #resolve for cross-SDK parity with the Go SDK’s ResolveProtocol method.
139 140 141 |
# File 'lib/bsv/registry/client.rb', line 139 def resolve_protocol(query = {}) resolve(DefinitionType::PROTOCOL, query) end |
#revoke_definition(registered_definition) ⇒ BSV::Overlay::OverlayBroadcastResult
Revokes an existing registry definition by spending its UTXO.
Verifies that the definition belongs to the current wallet before spending.
198 199 200 201 202 203 204 205 206 207 208 209 210 211 212 213 214 215 216 217 218 219 220 221 222 |
# File 'lib/bsv/registry/client.rb', line 198 def revoke_definition(registered_definition) verify_ownership(registered_definition) definition_type = registered_definition.definition_type # Registry API boundary: outpoint uses display-order hex txid from RegisteredDefinition outpoint = "#{registered_definition.txid}.#{registered_definition.output_index}" create_result = @wallet.create_action( description: "Revoke #{definition_type} definition: #{item_identifier(registered_definition)}", input_beef: registered_definition.beef, inputs: [ { outpoint: outpoint, unlocking_script_length: BSV::Script::PushDropTemplate::Unlocker::ESTIMATED_LENGTH, input_description: "Revoking #{definition_type} token" } ], options: { randomize_outputs: false, no_send: true }, originator: @originator ) raise 'Revoke failed: could not create signable transaction' if create_result[:signable_transaction].nil? sign_and_broadcast(definition_type, create_result) end |
#update_definition(registered_definition, new_data) ⇒ BSV::Overlay::OverlayBroadcastResult
Updates an existing registry definition by revoking it and registering new data.
The update is performed as two sequential operations: revoke then register. This is not atomic — if registration fails after revocation, the definition will have been removed without replacement.
236 237 238 239 240 241 242 243 244 |
# File 'lib/bsv/registry/client.rb', line 236 def update_definition(registered_definition, new_data) unless registered_definition.definition_type == new_data.definition_type raise ArgumentError, "Cannot change definition type from #{registered_definition.definition_type} to #{new_data.definition_type}" end revoke_definition(registered_definition) register_definition(registered_definition.definition_type, new_data) end |