AccessControl Role-Based Control, unable to grant desired role?

Hi everyone, I’m very new to learning Ethereum and employing Smart Contract and I am facing an issue regarding AccessControl that is not able to grant a role to other blocks, despite having an admin role.

From the Docs:
"Each role has an associated admin role, and only accounts that have a role’s admin role can call grantRole and revokeRole "

^From above, how do I go about “calling” said commands to execute into Ganache/Metamask?

Here is the snippet of the Smart Contract using AccessControl:

// SPDX-License-Identifier: MIT
pragma solidity ^0.6.12;

import "@openzeppelin/contracts/access/AccessControl.sol";

contract VaccinationCertificates is AccessControl {
  // Certificate Authority can issue certificates
  bytes32 public constant CERTIFICATE_AUTHORITY_ROLE = keccak256("CERTIFICATE_AUTHORITY_ROLE");
  // Certificate Authority Admin can issue Certificate Authority roles
  bytes32 public constant CERTIFICATE_AUTHORITY_ADMIN_ROLE = keccak256("CERTIFICATE_AUTHORITY_ADMIN_ROLE");

  mapping(address => bytes32) public certificateAuthorityNames;

  event CertificateAuthorityNameSet(
    address authority,
    bytes32 name
  );

  struct Certificate {
    bytes32 signature;
    address authority;
    uint timestamp;
  }

  mapping(bytes32 => Certificate) public certificates;
  bytes32[] public signatures;

  event CertificateIssued(
    bytes32 signature,
    address authority,
    uint timestamp
  );

  constructor() public {
    // Defining Admin role for Certificate Authority role
    _setRoleAdmin(CERTIFICATE_AUTHORITY_ROLE, CERTIFICATE_AUTHORITY_ADMIN_ROLE);
    
    // Owner is an admin
    _setupRole(DEFAULT_ADMIN_ROLE, msg.sender);
  }

  function issueCertificate(bytes32 _signature) public {
    require(hasRole(CERTIFICATE_AUTHORITY_ROLE, msg.sender), "Caller is not a Certificate Authority");
    require(certificates[_signature].timestamp == 0, "Can't overwrite existing certificate");

    signatures.push(_signature);

    certificates[_signature] = Certificate({
      signature: _signature,
      authority: msg.sender,
      timestamp: now
    });

    emit CertificateIssued(_signature, msg.sender, now);
  }

  function setCertificateAuthorityName(address _address, bytes32 _name) public {
    require(hasRole(CERTIFICATE_AUTHORITY_ADMIN_ROLE, msg.sender), "Caller is not a Certificate Authority Admin");
    require(hasRole(CERTIFICATE_AUTHORITY_ROLE, _address), "Given address is not a Certificate Authority");

    certificateAuthorityNames[_address] = _name;

    emit CertificateAuthorityNameSet(_address, _name);
  }

  // TODO: Implement pagination
  function getSignatures() public view returns(bytes32[] memory) {
    return signatures;
  }
}

Deployment to Truffle is via:

const VaccinationCertificates = artifacts.require("VaccinationCertificates");

module.exports = function (deployer) {
  deployer.deploy(VaccinationCertificates);
};

Hence, what am I doing wrong such that the admin role is incapable of granting/revoking the roles for the accounts in the blockchain? Otherwise, how do I go about setting authority for every new block (Account in Metamask) to be granted?

Thanks in advance for the help!

Your roles are organized like this currently:

Where A → B means “A is admin of B”.

In your constructor you assign the default admin role to the deployer (msg.sender). This means the msg.sender is able to grant and revoke the certificate authority admin role. But until you grant that other role to an account, no one is able to grant the certificate authority role.

Consider adding:

_setupRole(CERTIFICATE_AUTHORITY_ADMIN_ROLE, msg.sender);