Overriding entrypoint mint for nft

I woould like to override an entrypoint for minting nfts, in a contract where there is a maximal amount of tokens - how to achive that based on :

import smartpy as sp
from smartpy.templates import fa2_lib as fa2

Main template for FA2 contracts

main = fa2.main

@sp.module
def my_module():
import main

# Order of inheritance: [Admin], [<policy>], <base class>, [<other mixins>].
class MyNFTContract(
    main.Admin,
    main.Nft,
    main.MintNft,
    main.BurnNft,
    main.OnchainviewBalanceOf,
):
    def __init__(self, admin_address, contract_metadata, ledger, token_metadata):
        """Initializes the contract with NFT functionalities.
        The base class is required; all mixins are optional.
        The initialization must follow this order:

        - Other mixins such as OnchainviewBalanceOf, MintNFT, and BurnNFT
        - Base class: NFT
        - Transfer policy
        - Admin
        """

        # Initialize on-chain balance view
        main.OnchainviewBalanceOf.__init__(self)

        # Initialize the NFT-specific entrypoints
        main.BurnNft.__init__(self)
        main.MintNft.__init__(self)

        # Initialize the NFT base class
        main.Nft.__init__(self, contract_metadata, ledger, token_metadata)

        main.Admin.__init__(self, admin_address)

    

    # Override this function so anyone can mint for the purposes of the tutorial
    @sp.private()
    def is_administrator_(self):
        return True

    @sp.entrypoint
    def mint(self, param):
        sp.cast(param, sp.record(address=sp.address, value=sp.nat))
        assert self.is_administrator_(sp.sender), "Fa1.2_NotAdmin"
        receiver_balance = self.data.ledger.get(
            param.address, default=sp.record(balance=0, approvals={})
        )
        receiver_balance.balance += param.value
        self.data.ledger[param.address] = receiver_balance
        self.data.total_supply += param.value

def _get_balance(fa2_contract, args):
“”“Utility function to call the contract’s get_balance view to get an account’s token balance.”“”
return sp.View(fa2_contract, “get_balance”)(args)

def _total_supply(fa2_contract, args):
“”“Utility function to call the contract’s total_supply view to get the total amount of tokens.”“”
return sp.View(fa2_contract, “total_supply”)(args)

Create token metadata

Adapted from fa2.make_metadata

def create_metadata(symbol, name, decimals, displayUri, artifactUri, description, thumbnailUri):
return sp.map(
l={
“name”: sp.scenario_utils.bytes_of_string(name),
“decimals”: sp.scenario_utils.bytes_of_string(“%d” % decimals),
“symbol”: sp.scenario_utils.bytes_of_string(symbol),
“displayUri”: sp.scenario_utils.bytes_of_string(displayUri),
“artifactUri”: sp.scenario_utils.bytes_of_string(artifactUri),
“description”: sp.scenario_utils.bytes_of_string(description),
“thumbnailUri”: sp.scenario_utils.bytes_of_string(thumbnailUri),
}
)

@sp.add_test()
def test():
# Create and configure the test scenario
# Import the types from the FA2 library, the library itself, and the contract module, in that order.
scenario = sp.test_scenario(“fa2_lib_nft”, my_module)
scenario.h1(“FA2 NFT contract test”)

# Define test accounts
#admin = sp.test_account("Admin")
admin = sp.address("tz1eTaZePB1rHygDV9fwt3zJ2FXo9fgGetTe")
alice = sp.test_account("Alice")
bob = sp.test_account("Bob")

# Precreated image on IPFS
token_thumb_uri = "https://gateway.pinata.cloud/ipfs/QmRCp4Qc8afPrEqtM1YdRvNagWCsFGXHgGjbBYrmNsBkcE"

# Define initial token metadata and ownership
tok0_md = create_metadata(
        "Tok0",
        "Token Zero",
        0,
        token_thumb_uri,
        token_thumb_uri,
        "My first token",
        token_thumb_uri,
)
tok1_md = create_metadata(
        "Tok1",
        "Token One",
        0,
        token_thumb_uri,
        token_thumb_uri,
        "My second token",
        token_thumb_uri,
)
tok2_md = create_metadata(
        "Tok2",
        "Token Two",
        0,
        token_thumb_uri,
        token_thumb_uri,
        "My third token",
        token_thumb_uri,
)
token_metadata = [tok0_md, tok1_md, tok2_md]
ledger = {0: alice.address, 1: alice.address, 2: bob.address}

# Instantiate the FA2 NFT contract
#contract = my_module.MyNFTContract(
 #   alice.address, sp.big_map(), ledger, token_metadata
#)

contract = my_module.MyNFTContract(
    admin, sp.big_map(), ledger, token_metadata
)

# Build contract metadata content
contract_metadata = sp.create_tzip16_metadata(
    name="My FA2 NFT contract",
    description="This is an FA2 NFT contract using SmartPy.",
    version="1.0.0",
    license_name="CC-BY-SA",
    license_details="Creative Commons Attribution Share Alike license 4.0 https://creativecommons.org/licenses/by/4.0/",
    interfaces=["TZIP-012", "TZIP-016"],
    authors=["SmartPy <https://smartpy.io/#contact>"],
    homepage="https://smartpy.io/ide?template=fa2_lib_nft.py",
    # Optionally, upload the source code to IPFS and add the URI here
    source_uri=None,
    offchain_views=contract.get_offchain_views(),
)

# Add the info specific to FA2 permissions
contract_metadata["permissions"] = {
    # The operator policy chosen:
    # owner-or-operator-transfer is the default.
    "operator": "owner-or-operator-transfer",
    # Those two options should always have these values.
    # It means that the contract doesn't use the hook mechanism.
    "receiver": "owner-no-hook",
    "sender": "owner-no-hook",
}

# You must upload the contract metadata to IPFS and get its URI.
# You can write the contract_metadata object to a JSON file with json.dumps() and upload it manually.
# You can also use sp.pin_on_ipfs() to upload the object via pinata.cloud and get the IPFS URI:
# metadata_uri = sp.pin_on_ipfs(contract_metadata, api_key=None, secret_key=None, name = "Metadata for my FA2 contract")

# This is a placeholder value. In production, replace it with your metadata URI.
metadata_uri = "ipfs://example"

# Create the metadata big map based on the IPFS URI
contract_metadata = sp.scenario_utils.metadata_of_url(metadata_uri)

# Update the scenario instance with the new metadata
contract.data.metadata = contract_metadata

# Originate the contract in the test scenario
scenario += contract

if scenario.simulation_mode() is sp.SimulationMode.MOCKUP:
    scenario.p("mockups - fix transfer based testing")
    return

# Run tests

scenario.h2("Verify the initial owners of the tokens")
scenario.verify(
    _get_balance(contract, sp.record(owner=alice.address, token_id=0)) == 1
)
scenario.verify(
    _get_balance(contract, sp.record(owner=bob.address, token_id=0)) == 0
)
scenario.verify(
    _get_balance(contract, sp.record(owner=alice.address, token_id=1)) == 1
)
scenario.verify(
    _get_balance(contract, sp.record(owner=bob.address, token_id=1)) == 0
)
scenario.verify(
    _get_balance(contract, sp.record(owner=alice.address, token_id=2)) == 0
)
scenario.verify(
    _get_balance(contract, sp.record(owner=bob.address, token_id=2)) == 1
)

# Verify the token supply
scenario.verify(_total_supply(contract, sp.record(token_id=0)) == 1)
scenario.verify(_total_supply(contract, sp.record(token_id=1)) == 1)
scenario.verify(_total_supply(contract, sp.record(token_id=2)) == 1)

scenario.h2("Transfer a token")
contract.transfer(
    [
        sp.record(
            from_=alice.address,
            txs=[sp.record(to_=bob.address, amount=1, token_id=0)],
        ),
    ],
    _sender=alice,
)
# Verify the result
scenario.verify(
    _get_balance(contract, sp.record(owner=alice.address, token_id=0)) == 0
)
scenario.verify(
    _get_balance(contract, sp.record(owner=bob.address, token_id=0)) == 1
)
# Transfer it back
contract.transfer(
    [
        sp.record(
            from_=bob.address,
            txs=[sp.record(to_=alice.address, amount=1, token_id=0)],
        ),
    ],
    _sender=bob,
)

scenario.h2("Mint a token")
nft3_md = fa2.make_metadata(name="Token Three", decimals=1, symbol="Tok3")
# Mint a token
contract.mint(
    [
        sp.record(metadata=nft3_md, to_=bob.address),
    ],
    _sender=bob,
)
# Verify the result
scenario.verify(_total_supply(contract, sp.record(token_id=3)) == 1)
scenario.verify(
    _get_balance(contract, sp.record(owner=alice.address, token_id=3)) == 0
)
scenario.verify(
    _get_balance(contract, sp.record(owner=bob.address, token_id=3)) == 1
)

scenario.h2("Burn a token")
# Verify that you can't burn someone else's token
contract.burn(
    [sp.record(token_id=3, from_=bob.address, amount=1)],
    _sender=alice,
    _valid=False,
)

# Verify that you can burn your own token
contract.burn([sp.record(token_id=3, from_=bob.address, amount=1)], _sender=bob)