Skip to content

Instantly share code, notes, and snippets.

@danicuki
Created December 23, 2021 14:44
Show Gist options
  • Save danicuki/551d85299e30d85eeb0fe2c85636ce7f to your computer and use it in GitHub Desktop.
Save danicuki/551d85299e30d85eeb0fe2c85636ce7f to your computer and use it in GitHub Desktop.
Calculates NFT rarity using blockfrost Cardano API
require 'rest-client'
require 'json'
require 'csv'
require 'json_converter'
API_KEY = ENV['API_KEY']
HEADERS = {"project_id" => API_KEY}
policy_id = '90465e141ecb7b72ed0cdbcbd848673177cd52be5af5518e95d0de1d'
url = "https://cardano-mainnet.blockfrost.io/api/v0/assets/policy/#{policy_id}?count=100&page="
assets1 = (1..4).map do |page|
puts "Listing page #{page}"
result = RestClient.get("#{url}#{page}", HEADERS)
JSON.parse(result)
end.flatten.filter {|a| a['quantity'] == '1' }.map {|a| a['asset']}
asset_url = 'https://cardano-mainnet.blockfrost.io/api/v0/assets/'
assets_jsons = assets.map do |id|
puts "Fetching asset #{id}"
resp = RestClient.get(asset_url + id, HEADERS)
JSON.parse(resp)
end
@formated_jsons = assets_jsons.map { |a|
{ 'id' => a['asset'],
'name' => a['onchain_metadata']['name'],
'image' => a['onchain_metadata']['image']
}.merge!(a['onchain_metadata']['attributes'])
};1
@categories = @formated_jsons.first.keys - ["id", "name", "image"]
def asset_by_name(name)
asset = @formated_jsons.select {|a| a['name'] == name}.first
end
def rarity_by_name(name)
asset = asset_by_name(name)
if asset
rarity(asset)
else
puts 'asset not found'
end
end
def rarity(asset)
@categories.map do |c|
count = @formated_jsons.select {|x| x[c] == asset[c]}.count
r = count.to_f / @formated_jsons.count
# puts "#{c}: #{asset[c]} => #{r}"
r
end.reduce { |a, b| a * b }
end
def score(asset)
@categories.map do |c|
count = @formated_jsons.select {|x| x[c] == asset[c]}.count
r = count.to_f / @formated_jsons.count
# puts "#{c}: #{asset[c]} => #{r}"
r
end.reduce(0) { |acum, t| acum + 1/t }
end
@with_rarity = @formated_jsons.map do |m|
m.merge!({"rarity" => rarity(m), "score" => score(m) })
end;1
@sorted = @with_rarity.sort_by { |g| g['rarity'] };1
@score_sorted = @with_rarity.sort_by { |g| -g['score'] };1
def rank1(name)
asset = asset_by_name(name)
@sorted.find_index {|a| a['name'] == asset['name'] }
end
def rank2(name)
asset = asset_by_name(name)
@score_sorted.find_index {|a| a['name'] == asset['name'] }
end
json_converter = JsonConverter.new
csv = json_converter.generate_csv formated_jsons
File.open('3degens.csv', 'w') {|f| f.write csv }
my = %w{ 1578 1549 0165 0811 0409 1378 2919 1129 0561 0789 2628 }
my.each do |id|
r1 = rank1("3DEGENS ##{id}")
r2 = rank2("3DEGENS ##{id}")
puts "#{id}: #{r1} / #{r2}"
end
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment