Skip to content

Commit 194c621

Browse files
Merge pull request #135 from ethscriptions-protocol/fix_collections
Refactor ERC721 Ethscriptions Collection Management
2 parents 09dbf24 + 466e4fc commit 194c621

16 files changed

+1410
-933
lines changed

app/models/erc721_ethscriptions_collection_parser.rb

Lines changed: 346 additions & 42 deletions
Large diffs are not rendered by default.

app/models/ethscription_transaction.rb

Lines changed: 22 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -180,8 +180,12 @@ def build_create_calldata
180180
esip6 = DataUri.esip6?(content_uri) || false
181181

182182
# Extract protocol params - returns [protocol, operation, encoded_data]
183-
protocol, operation, encoded_data = ProtocolExtractor.for_calldata(content_uri)
184-
183+
# Pass the ethscription_id context so parsers can inject it when needed
184+
protocol, operation, encoded_data = ProtocolExtractor.for_calldata(
185+
content_uri,
186+
ethscription_id: eth_transaction.transaction_hash
187+
)
188+
185189
# Hash the content for protocol uniqueness
186190
content_uri_hash_hex = Digest::SHA256.hexdigest(content_uri)
187191
content_uri_hash = [content_uri_hash_hex].pack('H*')
@@ -208,10 +212,22 @@ def build_create_calldata
208212
protocol_params # ProtocolParams tuple
209213
]
210214

211-
encoded = Eth::Abi.encode(
212-
['(bytes32,bytes32,address,bytes,string,bool,(string,string,bytes))'],
213-
[params]
214-
)
215+
begin
216+
encoded = Eth::Abi.encode(
217+
['(bytes32,bytes32,address,bytes,string,bool,(string,string,bytes))'],
218+
[params]
219+
)
220+
rescue Encoding::CompatibilityError => e
221+
Rails.logger.error "=== ABI Encoding Error (build_create_calldata) ==="
222+
Rails.logger.error "Error: #{e.message}"
223+
Rails.logger.error "content_uri: #{content_uri[0..100]}"
224+
Rails.logger.error "protocol: #{protocol.inspect[0..100]}, encoding: #{protocol.encoding.name}"
225+
Rails.logger.error "operation: #{operation.inspect[0..100]}, encoding: #{operation.encoding.name}"
226+
Rails.logger.error "encoded_data: #{encoded_data.inspect[0..100]}, encoding: #{encoded_data.encoding.name}, bytesize: #{encoded_data.bytesize}"
227+
Rails.logger.error "mimetype: #{mimetype.inspect}, encoding: #{mimetype.encoding.name}"
228+
Rails.logger.error "raw_content encoding: #{raw_content.encoding.name}, bytesize: #{raw_content.bytesize}"
229+
raise
230+
end
215231

216232
# Ensure binary encoding
217233
(function_sig + encoded).b

app/models/protocol_extractor.rb

Lines changed: 17 additions & 20 deletions
Original file line numberDiff line numberDiff line change
@@ -5,32 +5,26 @@ class ProtocolExtractor
55
COLLECTIONS_DEFAULT_PARAMS = Erc721EthscriptionsCollectionParser::DEFAULT_PARAMS
66
GENERIC_DEFAULT_PARAMS = GenericProtocolExtractor::DEFAULT_PARAMS
77

8-
def self.extract(content_uri)
9-
return nil unless content_uri.is_a?(String)
10-
11-
# Centralized validation: must be a valid data URI and JSON payload
12-
return nil unless DataUri.valid?(content_uri)
13-
begin
14-
payload = DataUri.new(content_uri).decoded_data
15-
rescue StandardError
16-
return nil
17-
end
18-
return nil unless payload.start_with?('{')
8+
def self.extract(content_uri, ethscription_id: nil)
9+
# begin
10+
# payload = DataUri.new(content_uri).decoded_data
11+
# rescue StandardError
12+
# return nil
13+
# end
14+
# return nil unless payload.start_with?('{')
1915

2016
# Try extractors in order of strictness
2117
# 1. Token protocol (most strict - exact character position matters)
22-
# 2. Collections protocol (strict - exact key order required) - gated by ENABLE_COLLECTIONS
18+
# 2. Collections protocol (strict - exact key order required)
2319
# 3. Generic protocol (flexible - for all other protocols) - gated by ENABLE_GENERIC_PROTOCOLS
2420

2521
# Try token extractor first (most strict)
2622
result = try_token_extractor(content_uri)
2723
return result if result
2824

2925
# Try collections extractor next (if enabled)
30-
if ENV['ENABLE_COLLECTIONS'] == 'true'
31-
result = try_collections_extractor(content_uri)
32-
return result if result
33-
end
26+
result = try_collections_extractor(content_uri, ethscription_id: ethscription_id)
27+
return result if result
3428

3529
# Try generic extractor last (if enabled)
3630
if ENV['ENABLE_GENERIC_PROTOCOLS'] == 'true'
@@ -63,9 +57,12 @@ def self.try_token_extractor(content_uri)
6357
end
6458
end
6559

66-
def self.try_collections_extractor(content_uri)
60+
def self.try_collections_extractor(content_uri, ethscription_id: nil)
6761
# Erc721EthscriptionsCollectionParser returns [''.b, ''.b, ''.b] if no match
68-
protocol, operation, encoded_data = Erc721EthscriptionsCollectionParser.extract(content_uri)
62+
protocol, operation, encoded_data = Erc721EthscriptionsCollectionParser.extract(
63+
content_uri,
64+
ethscription_id: ethscription_id
65+
)
6966

7067
# Check if extraction succeeded
7168
if protocol != ''.b && operation != ''.b
@@ -129,8 +126,8 @@ def self.encode_token_params(params)
129126

130127
# Get protocol data formatted for L2 calldata
131128
# Returns [protocol, operation, encoded_data] for contract consumption
132-
def self.for_calldata(content_uri)
133-
result = extract(content_uri)
129+
def self.for_calldata(content_uri, ethscription_id: nil)
130+
result = extract(content_uri, ethscription_id: ethscription_id)
134131

135132
if result.nil?
136133
# No protocol detected - return empty protocol params

config/derive_ethscriptions_blocks.rb

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -176,7 +176,7 @@ module Clockwork
176176
# Don't sleep here - the loop's sleep at line 192 will handle it
177177
rescue => e
178178
Rails.logger.error "Import error: #{e.class} - #{e.message}"
179-
Rails.logger.error e.backtrace.first(20).join("\n")
179+
Rails.logger.error e.backtrace.join("\n")
180180

181181
puts "[#{Time.now}] ❌ Error: #{e.message}"
182182

contracts/script/L2Genesis.s.sol

Lines changed: 2 additions & 12 deletions
Original file line numberDiff line numberDiff line change
@@ -230,18 +230,8 @@ contract L2Genesis is Script {
230230
ethscriptions.registerProtocol("erc-20-fixed-denomination", Predeploys.ERC20_FIXED_DENOMINATION_MANAGER);
231231
console.log("Registered erc-20-fixed-denomination protocol handler:", Predeploys.ERC20_FIXED_DENOMINATION_MANAGER);
232232

233-
// Check environment variable for collections
234-
// Default to true so forge tests work (they don't go through genesis_generator.rb)
235-
// Production explicitly sets ENABLE_COLLECTIONS=false
236-
bool enableCollections = vm.envOr("ENABLE_COLLECTIONS", true);
237-
238-
if (enableCollections) {
239-
// Register the collections protocol handler for ERC-721 Ethscriptions collections
240-
ethscriptions.registerProtocol("erc-721-ethscriptions-collection", Predeploys.ERC721_ETHSCRIPTIONS_COLLECTION_MANAGER);
241-
console.log("Registered erc-721-ethscriptions-collection protocol handler:", Predeploys.ERC721_ETHSCRIPTIONS_COLLECTION_MANAGER);
242-
} else {
243-
console.log("Collections protocol not registered (ENABLE_COLLECTIONS=false)");
244-
}
233+
ethscriptions.registerProtocol("erc-721-ethscriptions-collection", Predeploys.ERC721_ETHSCRIPTIONS_COLLECTION_MANAGER);
234+
console.log("Registered erc-721-ethscriptions-collection protocol handler:", Predeploys.ERC721_ETHSCRIPTIONS_COLLECTION_MANAGER);
245235
}
246236

247237
/// @notice Deploy L1Block contract (stores L1 block attributes)

0 commit comments

Comments
 (0)