All Downloads are FREE. Search and download functionalities are using the official Maven repository.

com.hedera.node.app.hapi.fees.pricing.AssetsLoader Maven / Gradle / Ivy

There is a newer version: 0.57.2
Show newest version
/*
 * Copyright (C) 2021-2024 Hedera Hashgraph, LLC
 *
 * Licensed under the Apache License, Version 2.0 (the "License");
 * you may not use this file except in compliance with the License.
 * You may obtain a copy of the License at
 *
 *      http://www.apache.org/licenses/LICENSE-2.0
 *
 * Unless required by applicable law or agreed to in writing, software
 * distributed under the License is distributed on an "AS IS" BASIS,
 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
 * See the License for the specific language governing permissions and
 * limitations under the License.
 */

package com.hedera.node.app.hapi.fees.pricing;

import com.fasterxml.jackson.databind.ObjectMapper;
import com.hederahashgraph.api.proto.java.HederaFunctionality;
import com.hederahashgraph.api.proto.java.SubType;
import java.io.IOException;
import java.math.BigDecimal;
import java.util.EnumMap;
import java.util.Map;
import javax.inject.Inject;
import javax.inject.Singleton;

/**
 * Loads assets used to generate a fee schedule from JSON resources on the classpath.
 *
 * 

Please see the individual methods for details. */ @Singleton public class AssetsLoader { private static final String CAPACITIES_RESOURCE = "capacities.json"; private static final String CONSTANT_WEIGHTS_RESOURCE = "constant-weights.json"; private static final String CANONICAL_PRICES_RESOURCE = "canonical-prices.json"; private Map cachedCapacities = null; private Map cachedConstWeights = null; private Map> cachedCanonicalPrices = null; @Inject public AssetsLoader() { // empty constructor for @Inject annotation. } /** * Loads a map that, for each supported operation, gives the fraction of that operation's total * price that should come from its constant term in the fee schedule. * *

This fraction is the "weight" of the constant term; and is currently set at 0.9 for * operations that create new entities, and 0.2 for other operations. * * @return the "weight" of the constant term for each operation * @throws IOException if the backing JSON resource cannot be loaded */ Map loadConstWeights() throws IOException { if (cachedConstWeights != null) { return cachedConstWeights; } try (final var fin = AssetsLoader.class.getClassLoader().getResourceAsStream(CONSTANT_WEIGHTS_RESOURCE)) { final var om = new ObjectMapper(); final var constWeights = om.readValue(fin, Map.class); final Map typedConstWeights = new EnumMap<>(HederaFunctionality.class); constWeights.forEach((funcName, weight) -> { final var function = HederaFunctionality.valueOf((String) funcName); final var bdWeight = BigDecimal.valueOf((Double) weight); typedConstWeights.put(function, bdWeight); }); cachedConstWeights = typedConstWeights; return typedConstWeights; } } /** * Loads a map that, for each resource type available in the network, gives the "capacity" of * that resource. These capacities do not have an absolute meaning, and are just compared to * infer the relative scarcity of each resource. * * @return the network "capacity" of each resource type * @throws IOException if the backing JSON resource cannot be loaded */ Map loadCapacities() throws IOException { if (cachedCapacities != null) { return cachedCapacities; } try (final var fin = AssetsLoader.class.getClassLoader().getResourceAsStream(CAPACITIES_RESOURCE)) { final var om = new ObjectMapper(); final var capacities = om.readValue(fin, Map.class); final Map typedCapacities = new EnumMap<>(UsableResource.class); capacities.forEach((resourceName, amount) -> { final var resource = UsableResource.valueOf((String) resourceName); final var bdAmount = (amount instanceof Long val) ? BigDecimal.valueOf(val) : BigDecimal.valueOf((Integer) amount); typedCapacities.put(resource, bdAmount); }); cachedCapacities = typedCapacities; return typedCapacities; } } /** * Loads a map that, for each supported operation, gives the desired price in USD for the "base * configuration" of each type of that operation. (Types are given by the values of the {@link * SubType} enum; that is, DEFAULT, TOKEN_NON_FUNGIBLE_UNIQUE, and TOKEN_FUNGIBLE_COMMON.) * * @return the desired per-type prices, in USD * @throws IOException if the backing JSON resource cannot be loaded */ public Map> loadCanonicalPrices() throws IOException { if (cachedCanonicalPrices != null) { return cachedCanonicalPrices; } try (final var fin = AssetsLoader.class.getClassLoader().getResourceAsStream(CANONICAL_PRICES_RESOURCE)) { final var om = new ObjectMapper(); final var prices = om.readValue(fin, Map.class); final Map> typedPrices = new EnumMap<>(HederaFunctionality.class); prices.forEach((funName, priceMap) -> { final var function = HederaFunctionality.valueOf((String) funName); final Map scopedPrices = new EnumMap<>(SubType.class); ((Map) priceMap).forEach((typeName, price) -> { final var type = SubType.valueOf((String) typeName); final var bdPrice = (price instanceof Double val) ? BigDecimal.valueOf(val) : BigDecimal.valueOf((Integer) price); scopedPrices.put(type, bdPrice); }); typedPrices.put(function, scopedPrices); }); cachedCanonicalPrices = typedPrices; return typedPrices; } } }





© 2015 - 2024 Weber Informatics LLC | Privacy Policy