/**
 * Copyright (C) 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.
 *
 */
import { AccountId, PrivateKey } from '@hashgraph/sdk';
import { GenesisNetworkNodeDataWrapper } from './genesis_network_node_data_wrapper.js';
import * as constants from '../constants.js';
import { GenesisNetworkRosterEntryDataWrapper } from './genesis_network_roster_entry_data_wrapper.js';
import { Templates } from '../templates.js';
import path from 'path';
/**
 * Used to construct the nodes data and convert them to JSON
 */
export class GenesisNetworkDataConstructor {
    nodeAliases;
    keyManager;
    keysDir;
    networkNodeServiceMap;
    nodes = {};
    rosters = {};
    constructor(nodeAliases, keyManager, keysDir, networkNodeServiceMap) {
        this.nodeAliases = nodeAliases;
        this.keyManager = keyManager;
        this.keysDir = keysDir;
        this.networkNodeServiceMap = networkNodeServiceMap;
        nodeAliases.forEach(nodeAlias => {
            const adminPrivateKey = PrivateKey.fromStringED25519(constants.GENESIS_KEY);
            const adminPubKey = adminPrivateKey.publicKey;
            const nodeDataWrapper = new GenesisNetworkNodeDataWrapper(+networkNodeServiceMap.get(nodeAlias).nodeId, adminPubKey, nodeAlias);
            this.nodes[nodeAlias] = nodeDataWrapper;
            nodeDataWrapper.accountId = AccountId.fromString(networkNodeServiceMap.get(nodeAlias).accountId);
            const rosterDataWrapper = new GenesisNetworkRosterEntryDataWrapper(+networkNodeServiceMap.get(nodeAlias).nodeId);
            this.rosters[nodeAlias] = rosterDataWrapper;
            rosterDataWrapper.weight = this.nodes[nodeAlias].weight = constants.HEDERA_NODE_DEFAULT_STAKE_AMOUNT;
            const externalPort = +constants.HEDERA_NODE_EXTERNAL_GOSSIP_PORT;
            const namespace = networkNodeServiceMap.get(nodeAlias).namespace;
            const externalIP = Templates.renderFullyQualifiedNetworkSvcName(namespace, nodeAlias);
            // Add gossip endpoints
            nodeDataWrapper.addGossipEndpoint(externalIP, externalPort);
            rosterDataWrapper.addGossipEndpoint(externalIP, externalPort);
            const haProxyFqdn = Templates.renderFullyQualifiedHaProxyName(nodeAlias, namespace);
            // Add service endpoints
            nodeDataWrapper.addServiceEndpoint(haProxyFqdn, constants.GRPC_PORT);
        });
    }
    static async initialize(nodeAliases, keyManager, keysDir, networkNodeServiceMap) {
        const instance = new GenesisNetworkDataConstructor(nodeAliases, keyManager, keysDir, networkNodeServiceMap);
        await instance.load();
        return instance;
    }
    /**
     * Loads the gossipCaCertificate and grpcCertificateHash
     */
    async load() {
        await Promise.all(this.nodeAliases.map(async (nodeAlias) => {
            const signingCertFile = Templates.renderGossipPemPublicKeyFile(nodeAlias);
            const signingCertFullPath = path.join(this.keysDir, signingCertFile);
            const derCertificate = this.keyManager.getDerFromPemCertificate(signingCertFullPath);
            //* Assign the DER formatted certificate
            this.rosters[nodeAlias].gossipCaCertificate = this.nodes[nodeAlias].gossipCaCertificate =
                Buffer.from(derCertificate).toString('base64');
            //* Generate the SHA-384 hash
            this.nodes[nodeAlias].grpcCertificateHash = '';
        }));
    }
    toJSON() {
        const nodeMetadata = [];
        Object.keys(this.nodes).forEach(nodeAlias => {
            nodeMetadata.push({
                node: this.nodes[nodeAlias].toObject(),
                rosterEntry: this.rosters[nodeAlias].toObject(),
            });
        });
        return JSON.stringify({ nodeMetadata: nodeMetadata });
    }
}
//# sourceMappingURL=genesis_network_data_constructor.js.map