hashgraph/hedera-sdk-cpp

QA: Get Token Info

Closed this issue · 5 comments

Get the current state of the token from the consensus nodes

Code Example

#include "AccountInfo.h"
#include "AccountInfoQuery.h"
#include "Client.h"
#include "ECDSAsecp256k1PrivateKey.h"
#include "ED25519PrivateKey.h"
#include "TokenCreateTransaction.h"
#include "TokenId.h"
#include "TokenMintTransaction.h"
#include "TokenNftInfo.h"
#include "TokenNftInfoQuery.h"
#include "TransactionReceipt.h"
#include "TransactionResponse.h"
#include "TransferTransaction.h"
#include "impl/Utilities.h"

#include <array>
#include <iostream>

using namespace Hedera;

int main(int argc, char** argv)
{
  if (argc < 3)
  {
    std::cout << "Please input account ID and private key" << std::endl;
    return 1;
  }

  const AccountId operatorAccountId = AccountId::fromString(argv[1]);
  const std::shared_ptr<ED25519PrivateKey> operatorPrivateKey = ED25519PrivateKey::fromString(argv[2]);

  // Get a client for the Hedera testnet, and set the operator account ID and key such that all generated transactions
  // will be paid for by this account and be signed by this key.
  Client client = Client::forTestnet();
  client.setOperator(operatorAccountId, operatorPrivateKey);

  // IPFS content identifiers for the NFT metadata
  const std::vector<std::vector<std::byte>> CIDs = {
    internal::Utilities::stringToByteVector("QmNPCiNA3Dsu3K5FxDPMG5Q3fZRwVTg14EXA92uqEeSRXn"),
    internal::Utilities::stringToByteVector("QmZ4dgAgt8owvnULxnKxNe8YqpavtVCXmc1Lt2XajFpJs9"),
    internal::Utilities::stringToByteVector("QmPzY5GxevjyfMUF5vEAjtyRoigzWp47MiKAtLBduLMC1T"),
    internal::Utilities::stringToByteVector("Qmd3kGgSrAwwSrhesYcY7K54f3qD7MDo38r7Po2dChtQx5"),
    internal::Utilities::stringToByteVector("QmWgkKz3ozgqtnvbCLeh7EaR1H8u5Sshx3ZJzxkcrT3jbw")
  };

  std::cout << "Example 1" << std::endl;
  std::cout << "---------" << std::endl;

  /**
   * Step 1: Create an NFT using the Hedera token service.
   */
  TokenId tokenId = TokenCreateTransaction()
                      .setTokenName("HIP-542 Example Collection")
                      .setTokenSymbol("HIP-542")
                      .setTokenType(TokenType::NON_FUNGIBLE_UNIQUE)
                      .setDecimals(0)
                      .setInitialSupply(0)
                      .setMaxSupply(CIDs.size())
                      .setTreasuryAccountId(operatorAccountId)
                      .setSupplyType(TokenSupplyType::FINITE)
                      .setAdminKey(operatorPrivateKey)
                      .setSupplyKey(operatorPrivateKey)
                      .execute(client)
                      .getReceipt(client)
                      .mTokenId.value();
  std::cout << "Created NFT with ID: " << tokenId.toString() << std::endl;

  /**
   * Step 2: Mint the NFTs.
   */
  TransactionReceipt txReceipt = TokenMintTransaction()
                                   .setMaxTransactionFee(Hbar(10LL))
                                   .setTokenId(tokenId)
                                   .setMetadata(CIDs)
                                   .execute(client)
                                   .getReceipt(client);
  std::cout << "Minted " << txReceipt.mSerialNumbers.size() << " NFTs" << std::endl;

  /**
   * Step 3: Create an ECDSAsecp256k1PublicKey alias.
   */
  std::shared_ptr<PublicKey> alias = ECDSAsecp256k1PrivateKey::generatePrivateKey()->getPublicKey();
  AccountId aliasAccountId = alias->toAccountId();
  std::cout << "Created alias: " << aliasAccountId.toString() << std::endl;

  /**
   * Step 4: Transfer an NFT to the ECDSAsecp256k1PublicKey alias.
   */
  const auto nftId = NftId(tokenId, txReceipt.mSerialNumbers.at(0));
  std::cout << "Transferring NFT " << nftId.toString() << " to alias account: "
            << gStatusToString.at(TransferTransaction()
                                    .addNftTransfer(nftId, operatorAccountId, aliasAccountId)
                                    .execute(client)
                                    .setValidateStatus(false)
                                    .getReceipt(client)
                                    .mStatus)
            << std::endl;

  /**
   * Step 5: Query the NFT to see the owner.
   */
  TokenNftInfo tokenNftInfo = TokenNftInfoQuery().setNftId(nftId).execute(client);
  std::cout << "NFT " << nftId.toString() << " owner: " << tokenNftInfo << std::endl;

  /**
   * Step 6: Get the new account ID of the alias.
   */
  std::cout << "The NFT owner account ID "
            << (AccountInfoQuery().setAccountId(aliasAccountId).execute(client).mAccountId == tokenNftInfo.mAccountId
                  ? "matches "
                  : "does not match ")
            << "the account ID created by HTS." << std::endl;

  std::cout << std::endl;
  std::cout << "Example 2" << std::endl;
  std::cout << "---------" << std::endl;

  /**
   * Step 1: Create a fungible token using the Hedera token service.
   */
  tokenId = TokenCreateTransaction()
              .setTokenName("HIP-542 Token")
              .setTokenSymbol("H542")
              .setTokenType(TokenType::FUNGIBLE_COMMON)
              .setTreasuryAccountId(operatorAccountId)
              .setInitialSupply(10000) // Total supply = 10000 / 10 ^ 2
              .setDecimals(2)
              .setAutoRenewAccountId(operatorAccountId)
              .execute(client)
              .getReceipt(client)
              .mTokenId.value();
  std::cout << "Created fungible token with ID: " << tokenId.toString() << std::endl;

  /**
   * Step 2: Create an ECDSAsecp256k1PublicKey alias.
   */
  alias = ECDSAsecp256k1PrivateKey::generatePrivateKey()->getPublicKey();
  aliasAccountId = alias->toAccountId();
  std::cout << "Created alias: " << aliasAccountId.toString() << std::endl;

  /**
   * Step 3: Transfer the fungible token to the ECDSAsecp256k1PublicKey alias.
   */
  std::cout << "Transferring token " << tokenId.toString() << " to alias account: "
            << gStatusToString.at(TransferTransaction()
                                    .addTokenTransfer(tokenId, operatorAccountId, -10LL)
                                    .addTokenTransfer(tokenId, aliasAccountId, 10LL)
                                    .execute(client)
                                    .setValidateStatus(false)
                                    .getReceipt(client)
                                    .mStatus)
            << std::endl;

  /**
   * Step 4: Get the new account ID of the alias.
   */
  std::cout << "The new account ID of the alias is "
            << AccountInfoQuery().setAccountId(aliasAccountId).execute(client).mAccountId.toString() << std::endl;

  return 0;
}

Output

Example 1
---------
Created NFT with ID: 0.0.5995532
Minted 5 NFTs
Created alias: 0.0.302D300706052B8104000A03220003C2DCF37694C92801BF1E897CF9C4C00758DD445FD5A7AC46417484006A5F5C9E
Transferring NFT 0.0.5995532/1 to alias account: SUCCESS
NFT 0.0.5995532/1 owner: 0.0.5995536
The NFT owner account ID matches the account ID created by HTS.

Example 2
---------
Created fungible token with ID: 0.0.5995539
Created alias: 0.0.302D300706052B8104000A0322000244A61A2A1EC9D8AFE7FB78A6A3F5A79B4BBF7373A0FD565F01D2B6DF4FF9F174
Transferring token 0.0.5995539 to alias account: SUCCESS
The new account ID of the alias is 0.0.5995540

The example has:

* Step 5: Query the NFT to see the owner.
*/
TokenNftInfo tokenNftInfo = TokenNftInfoQuery().setNftId(nftId).execute(client);
std::cout << "NFT " << nftId.toString() << " owner: " << tokenNftInfo.mAccountId.toString() << std::endl;

I want to print the entire response of the token info query response from the consensus nodes.

I tried this:

* Step 5: Query the NFT to see the owner.
*/
TokenNftInfo tokenNftInfo = TokenNftInfoQuery().setNftId(nftId).execute(client);
// Changed to have it print the entire response vs. just the account ID in the previous example
std::cout << "NFT " << nftId.toString() << " owner: " << tokenNftInfo << std::endl;

And it does not seem to like that. Is there something I am missing? @rwalworth
Screenshot 2023-11-27 at 6 09 49 PM

The example has:

* Step 5: Query the NFT to see the owner.
*/
TokenNftInfo tokenNftInfo = TokenNftInfoQuery().setNftId(nftId).execute(client);
std::cout << "NFT " << nftId.toString() << " owner: " << tokenNftInfo.mAccountId.toString() << std::endl;

I want to print the entire response of the token info query response from the consensus nodes.

I tried this:

* Step 5: Query the NFT to see the owner.
*/
TokenNftInfo tokenNftInfo = TokenNftInfoQuery().setNftId(nftId).execute(client);
// Changed to have it print the entire response vs. just the account ID in the previous example
std::cout << "NFT " << nftId.toString() << " owner: " << tokenNftInfo << std::endl;

And it does not seem to like that. Is there something I am missing? @rwalworth Screenshot 2023-11-27 at 6 09 49 PM

I would need to implement the same type of fix I did here: #602. Is this something that you think we would want for all objects?

yes you should be able to return the entire response from a query or return a specific piece of data from the query response

Ok I'll get working on this immediately