All files / src/powerup cpu.ts

80.95% Statements 34/42
40% Branches 8/20
61.53% Functions 8/13
82.85% Lines 29/35

Press n or j to go to the next uncovered block, b, p or k for the previous block.

1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 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 89 90 91 92 93 94 95 96185x   1x 1x       31x   31x                                   2x             17x       31x     31x       15x 15x 15x 15x 15x 15x       31x       31x 10x         13x 13x   13x   13x   13x 13x 13x 13x 13x             13x                   13x      
import {Asset, Int64, Int64Type, Struct, UInt128, UInt128Type} from '@wharfkit/antelope'
 
import {BNPrecision, intToBigDecimal, SampleUsage} from '..'
import {PowerUpStateResource} from './abstract'
import {PowerUpStateOptions} from './options'
 
@Struct.type('powerupstateresourcecpu')
export class PowerUpStateResourceCPU extends PowerUpStateResource {
    // Return smallest units per day, μs (microseconds)
    per_day = (options?: PowerUpStateOptions) => this.us_per_day(options)
 
    // Return ms (milliseconds) per day
    ms_per_day(options?: PowerUpStateOptions) {
        return this.us_per_day(options) / 1000
    }
 
    // Return μs (microseconds) per day
    us_per_day(options?: PowerUpStateOptions) {
        const limit =
            options && options.virtual_block_cpu_limit
                ? options.virtual_block_cpu_limit
                : this.default_block_cpu_limit
        return Number(limit) * 2 * 60 * 60 * 24
    }
 
    // Convert weight to μs (microseconds)
    weight_to_us(sample: UInt128Type, weight: Int64Type): UInt128 {
        return UInt128.from(
            UInt128.from(weight).multiplying(Int64.from(sample)).dividing(BNPrecision, 'ceil')
        )
    }
 
    // Convert μs (microseconds) to weight
    us_to_weight(sample: UInt128, us: Int64Type): Int64 {
        return Int64.from(us).multiplying(BNPrecision).dividing(sample, 'floor')
    }
 
    // Default frac generation by smallest unit type
    frac = (usage: SampleUsage, us: number) => this.frac_by_us(usage, us)
 
    // Frac generation by ms (milliseconds)
    frac_by_ms = (usage: SampleUsage, ms: number) => this.frac_by_us(usage, ms * 1000)
 
    // Frac generation by μs (microseconds)
    frac_by_us(usage: SampleUsage, us: Int64Type): Int64 {
        const precision = 15
        const converted = intToBigDecimal(this.us_to_weight(usage.cpu, us))
        const current = intToBigDecimal(this.weight)
        const multiplier = intToBigDecimal(Math.pow(10, precision))
        const frac = converted.divide(current, precision).multiply(multiplier)
        return Int64.from(frac.getValue())
    }
 
    // Price generation by smallest units, μs (microseconds)
    price_per = (usage: SampleUsage, us = 1000, options?: PowerUpStateOptions): number =>
        this.price_per_us(usage, us, options)
 
    // Price generation by ms (milliseconds)
    price_per_ms = (usage: SampleUsage, ms = 1, options?: PowerUpStateOptions): number =>
        this.price_per_us(usage, ms * 1000, options)
 
    // Price generation by μs (microseconds)
    price_per_us(usage: SampleUsage, us = 1000, options?: PowerUpStateOptions): number {
        // Determine the utilization increase by this action
        const frac = UInt128.from(this.frac(usage, us))
        const utilization_increase = this.utilization_increase(frac)
        // Determine the adjusted utilization if needed
        const adjusted_utilization = this.determine_adjusted_utilization(options)
        // Derive the fee from the increase and utilization
        const fee = this.fee(utilization_increase, adjusted_utilization)
        // Force the fee up to the next highest value of precision
        const precision = Math.pow(10, this.max_price.symbol.precision)
        const price = fee * precision
        const value = Math.ceil(price) / precision
        const asset = Asset.fromFloat(fee, this.symbol)
        Iif (price < 1) {
            throw new Error(
                `Price (${String(
                    asset
                )}) for requested CPU amount (${us}us) below required precision, increase requested amount.`
            )
        }
        Iif (options && options.min_payment && options.min_payment.units.gt(asset.units)) {
            throw new Error(
                `Price (${String(
                    asset
                )}) for requested CPU amount (${us}us) below minimum required payment (${String(
                    options.min_payment
                )}), increase requested CPU amount.`
            )
        }
        // Return the modified fee
        return value
    }
}