mirror of
https://github.com/luxfi/safe-ios.git
synced 2026-10-30 15:19:20 +00:00
60 lines
2.0 KiB
Swift
60 lines
2.0 KiB
Swift
//
|
|
// OwnerKeySelectionPolicy.swift
|
|
// Multisig
|
|
//
|
|
// Created by Dmitry Bespalov on 13.01.22.
|
|
// Copyright © 2022 Gnosis Ltd. All rights reserved.
|
|
//
|
|
|
|
import Foundation
|
|
import Solidity
|
|
|
|
class OwnerKeySelectionPolicy {
|
|
|
|
struct KeyCandidate: Equatable {
|
|
var key: KeyInfo
|
|
var balance: Sol.UInt256 = 0
|
|
var isOwner: Bool = false
|
|
}
|
|
|
|
/// Searches for the default key matching required amount on their balance.
|
|
/// - Parameters:
|
|
/// - keys: list of keys with balances and owner status. If balance is unknown, it should be set to 0.
|
|
/// - requiredAmount: if the required balance is known, it should be passed. Default is 0.
|
|
/// - Returns:
|
|
/// - Prefers owner to non-owners with enough balance
|
|
/// - Prefers higher-balance keys
|
|
/// - If none of the keys have enough balance or required amount is not specified, prefers owner key with the highest balance
|
|
func defaultExecutionKey(in candidates: [KeyCandidate], requiredAmount: Sol.UInt256 = 0) -> KeyCandidate? {
|
|
if candidates.isEmpty {
|
|
return nil
|
|
}
|
|
|
|
if candidates.count == 1 {
|
|
return candidates.first
|
|
}
|
|
|
|
let byBalanceDescending = { (lhs: KeyCandidate, rhs: KeyCandidate) -> Bool in
|
|
lhs.balance > rhs.balance
|
|
}
|
|
let sortedOwners = candidates.filter { $0.isOwner }.sorted(by: byBalanceDescending)
|
|
|
|
if let firstOwner = sortedOwners.first, firstOwner.balance >= requiredAmount {
|
|
return firstOwner
|
|
}
|
|
|
|
// now we know that owners don't have enough balance.
|
|
|
|
let sortedNonOwners = candidates.filter { !$0.isOwner }.sorted(by: byBalanceDescending)
|
|
|
|
if let firstNonOwner = sortedNonOwners.first, firstNonOwner.balance >= requiredAmount {
|
|
return firstNonOwner
|
|
}
|
|
|
|
// now we know that non-owners also don't have enough balance.
|
|
// return any owner or non-owner with the highest balance.
|
|
let result = sortedOwners.first ?? sortedNonOwners.first
|
|
return result
|
|
}
|
|
}
|