Create a File

A transaction that creates a new file on a Hedera network. The file is referenced by its file ID which can be obtained from the receipt or record once the transaction reaches consensus on a Hedera network. The file does not have a file name. If the file is too big to create with a single FileCreateTransaction(), the file can be appended with the remaining content multiple times using the FileAppendTransaction()

Step 1: Imports

  • The code imports necessary modules from the Hedera JavaScript SDK (@hashgraph/sdk) such as FileCreateTransaction, FileAppendTransaction, FileContentsQuery, TransactionRecordQuery, Hbar, LocalProvider, and Wallet.

  • It also imports the fs module from Node.js to read the contents of a file synchronously, and the exit method from the process module.

const {
    FileCreateTransaction,
    FileAppendTransaction,
    FileContentsQuery,
    TransactionRecordQuery,
    Hbar,
    LocalProvider,
    Wallet
} = require("@hashgraph/sdk");
const fs = require('fs');
const { exit } = require("process");

Step 2 : Environment Variables Retrieval and Validation

  • The code loads environment variables from a .env file located in the File_Service directory using dotenv.

  • It checks whether the required environment variables (MY_ACCOUNT_ID and MY_PRIVATE_KEY) are present. If not, it throws an error.

require('dotenv').config({ path: 'File_Service/.env' });

if (process.env.MY_ACCOUNT_ID == null || process.env.MY_PRIVATE_KEY == null) {
    throw new Error(
        "Environment variables OPERATOR_ID, and OPERATOR_KEY are required."
    );
}

Step 3 : Wallet Initialization

  • It creates a new Wallet instance using the account ID and private key retrieved from the environment variables.

  • The wallet is initialized with a LocalProvider, indicating that it will be used for local signing of transactions.

const wallet = new Wallet(
    process.env.MY_ACCOUNT_ID,
    process.env.MY_PRIVATE_KEY,
    new LocalProvider()
);

Step 4 : Main Function

  • It reads the contents of a PDF file (hedera.pdf) synchronously using fs.readFileSync().

  • It creates a file on the Hedera network using FileCreateTransaction, sets the necessary parameters such as keys, contents, and transaction fee, and freezes the transaction for signing.

  • The file creation transaction is then signed with the wallet's signer and executed.

  • After execution, the receipt of the transaction is obtained to retrieve the new file ID.

  • Data from the PDF file is appended to the created file using FileAppendTransaction, with similar steps for signing and execution as the file creation transaction.

  • The contents of the file are retrieved using FileContentsQuery.

  • Transaction record queries are performed to get transaction fees for both the file creation and append transactions.

  • Exchange rates for the transactions are retrieved from the receipts.

  • Finally, various information such as file ID, file content length, transaction fees, and exchange rates are logged to the console.

async function main() {
    const data = fs.readFileSync('File_Service/artifacts/hedera.pdf');

    // Create a file on Hedera and store file
    let fileCreateTransaction = await new FileCreateTransaction()
        .setKeys([wallet.getAccountKey()]) 
        .setContents("")
        .setMaxTransactionFee(new Hbar(2))
        .freezeWithSigner(wallet);
    fileCreateTransaction = await fileCreateTransaction.signWithSigner(wallet);
    const txCreateResponse = await fileCreateTransaction.executeWithSigner(wallet);

    //Get the receipt of the transaction
    const createReceipt = await txCreateResponse.getReceiptWithSigner(wallet);

    //Grab the new file ID from the receipt
    const fileId = createReceipt.fileId;

    // Append data to the file
    const txAppendResponse = await (
        await (
            await new FileAppendTransaction()
                .setNodeAccountIds([txCreateResponse.nodeId])
                .setFileId(fileId)
                .setContents(data)
                .setMaxTransactionFee(new Hbar(5))
                .freezeWithSigner(wallet)
        ).signWithSigner(wallet)
    ).executeWithSigner(wallet);

    // Get the receipt of the append transaction
    const appendReceipt = await txAppendResponse.getReceiptWithSigner(wallet);

    // Get the contents of the file
    const contents = await new FileContentsQuery()
        .setFileId(fileId)
        .executeWithSigner(wallet);

    // Perform transaction record queries to get transaction fees
    const createQuery = await new TransactionRecordQuery().setTransactionId(txCreateResponse.transactionId).executeWithSigner(wallet);
    const appendQuery = await new TransactionRecordQuery().setTransactionId(txAppendResponse.transactionId).executeWithSigner(wallet);

    // Get the exchange rates
    const exchangeRateCreate = createReceipt.exchangeRate.exchangeRateInCents;
    const exchangeRateAppend = appendReceipt.exchangeRate.exchangeRateInCents;

    // Log various information
    console.log(`Your file ID is: ${fileId}`);
    console.log(`File content length according to \`FileInfoQuery\`: ${contents.length}`);
    console.log(`Fee for create: ${createQuery.transactionFee}`);
    console.log(`Fee for append: ${appendQuery.transactionFee}`);
    console.log(`Exchange Rate create (USD Cents) TX ${exchangeRateCreate}, append TX ${exchangeRateAppend}`);

    process.exit();
}

Step 5 : Execution

This line calls the main() function to start the execution of the script.

main();

Last updated