Class: MixinBot::Computer

Inherits:
Object
  • Object
show all
Defined in:
lib/mixin_bot/computer.rb

Overview

Mixin Computer API client (computer.mixin.one).

Constant Summary collapse

BASE_URI =
'https://computer.mixin.one'
OPERATION_TYPE_ADD_USER =
1
OPERATION_TYPE_SYSTEM_CALL =
2
OPERATION_TYPE_USER_DEPOSIT =
3
SOLANA_CHAIN_ID =
'64692c23-8971-4cf4-84a7-4dd1271dd887'

Class Method Summary collapse

Class Method Details

.build_system_call_extra(uid, cid, skip_process: false, fid: nil) ⇒ Object



102
103
104
105
106
107
108
# File 'lib/mixin_bot/computer.rb', line 102

def build_system_call_extra(uid, cid, skip_process: false, fid: nil)
  extra = user_id_to_bytes(uid)
  extra += MixinBot::UUID.new(hex: cid).packed
  extra += [skip_process ? 1 : 0].pack('C')
  extra += MixinBot::UUID.new(hex: fid).packed if fid.present?
  extra
end

.connectionObject



15
16
17
18
19
20
21
# File 'lib/mixin_bot/computer.rb', line 15

def connection
  @connection ||= Faraday.new(url: BASE_URI) do |f|
    f.request :json
    f.response :json
    f.adapter Faraday.default_adapter
  end
end

.decode_computer_extra_base64(extra) ⇒ Object



119
120
121
122
123
124
125
# File 'lib/mixin_bot/computer.rb', line 119

def decode_computer_extra_base64(extra)
  data = Base64.urlsafe_decode64(extra)
  return ['', nil] if data.length < 16

  app_id = MixinBot::UUID.new(raw: data[0, 16]).unpacked
  [app_id, data[16..]]
end

.deploy_external_assets(assets) ⇒ Object Also known as: computer_deploy_external_asset

Raises:



58
59
60
61
62
63
# File 'lib/mixin_bot/computer.rb', line 58

def deploy_external_assets(assets)
  assets = Array(assets)
  raise ArgumentError, "cannot deploy asset from Solana: #{SOLANA_CHAIN_ID}" if assets.include?(SOLANA_CHAIN_ID)

  request 'POST', '/deployed_assets', assets
end

.deployed_assetsObject Also known as: get_computer_deployed_assets



48
49
50
# File 'lib/mixin_bot/computer.rb', line 48

def deployed_assets
  request 'GET', '/deployed_assets'
end

.encode_mtg_extra(app_id, extra) ⇒ Object



114
115
116
117
# File 'lib/mixin_bot/computer.rb', line 114

def encode_mtg_extra(app_id, extra)
  data = MixinBot::UUID.new(hex: app_id).packed + extra.to_s
  Base64.urlsafe_encode64(data, padding: false)
end

.encode_operation_memo(operation, extra = +'')) ⇒ Object



110
111
112
# File 'lib/mixin_bot/computer.rb', line 110

def encode_operation_memo(operation, extra = +'')
  [operation].pack('C') + extra.to_s
end

.fee_on_xin_from_sol(sol_amount) ⇒ Object Also known as: get_fee_on_xin_based_on_sol



71
72
73
# File 'lib/mixin_bot/computer.rb', line 71

def fee_on_xin_from_sol(sol_amount)
  request 'POST', '/fee', { sol_amount: sol_amount.to_s }
end

.infoObject Also known as: get_computer_info



38
39
40
# File 'lib/mixin_bot/computer.rb', line 38

def info
  request 'GET', '/'
end

.lock_nonce_account(mix) ⇒ Object Also known as: lock_computer_nonce_account



66
67
68
# File 'lib/mixin_bot/computer.rb', line 66

def (mix)
  request 'POST', '/nonce_accounts', { mix: }
end

.register_computer(api) ⇒ Object



76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
# File 'lib/mixin_bot/computer.rb', line 76

def register_computer(api)
  info_data = info
  mix = MixinBot::MixAddress.from_members(members: [api.config.app_id], threshold: 1).address
  memo = encode_mtg_extra(
    info_data.dig('members', 'app_id'),
    encode_operation_memo(OPERATION_TYPE_ADD_USER, mix)
  )
  trace = MixinBot.utils.unique_object_id(mix, 'computer_register')
  api.create_safe_transfer(
    members: info_data.dig('members', 'members'),
    threshold: info_data.dig('members', 'threshold'),
    asset_id: info_data.dig('params', 'operation', 'asset'),
    amount: info_data.dig('params', 'operation', 'price'),
    trace_id: trace,
    memo:
  )
end

.request(method, path, body = nil) ⇒ Object

Raises:

  • (MixinBot::ServerError)


23
24
25
26
27
28
29
30
31
32
33
34
35
36
# File 'lib/mixin_bot/computer.rb', line 23

def request(method, path, body = nil)
  response =
    case method.to_s.upcase
    when 'GET'
      connection.get(path)
    when 'POST'
      connection.post(path, body)
    else
      raise ArgumentError, "unsupported method #{method}"
    end
  raise MixinBot::ServerError, "computer HTTP #{response.status}" if response.status >= 500

  response.body
end

.solana_asset_id_for(deployed) ⇒ Object



127
128
129
# File 'lib/mixin_bot/computer.rb', line 127

def solana_asset_id_for(deployed)
  MixinBot.utils.unique_object_id(SOLANA_CHAIN_ID, deployed['address'])
end

.system_call(id) ⇒ Object Also known as: get_computer_system_call



53
54
55
# File 'lib/mixin_bot/computer.rb', line 53

def system_call(id)
  request 'GET', "/system_calls/#{id}"
end

.user(addr) ⇒ Object Also known as: get_computer_user



43
44
45
# File 'lib/mixin_bot/computer.rb', line 43

def user(addr)
  request 'GET', "/users/#{addr}"
end

.user_id_to_bytes(id) ⇒ Object Also known as: computer_user_id_to_bytes

Raises:



94
95
96
97
98
99
# File 'lib/mixin_bot/computer.rb', line 94

def user_id_to_bytes(id)
  n = Integer(id, 10)
  raise ArgumentError, "invalid user id: #{id}" if n.negative?

  [n].pack('Q>')
end