Python-Cardano / pycardano

A lightweight Cardano library in Python
https://pycardano.readthedocs.io
MIT License
215 stars 67 forks source link

[bug]: BlockFrostChainContext is not correctly initialized #349

Closed chrissiwaffler closed 4 months ago

chrissiwaffler commented 5 months ago

Describe the bug The code of pycardano/backend/blockfrost.py seems to be faulty

class BlockFrostChainContext(ChainContext):
    """A `BlockFrost <https://blockfrost.io/>`_ API wrapper for the client code to interact with.

    Args:
        project_id (str): A BlockFrost project ID obtained from https://blockfrost.io.
        network (Network): Network to use.
        base_url (str): Base URL for the BlockFrost API. Defaults to the preprod url.
    """

    api: BlockFrostApi
    _epoch_info: Namespace
    _epoch: Optional[int] = None
    _genesis_param: Optional[GenesisParameters] = None
    _protocol_param: Optional[ProtocolParameters] = None

    def __init__(
        self,
        project_id: str,
        network: Optional[Network] = None,
        base_url: Optional[str] = None,
    ):
        if network is not None:
            warnings.warn(
                "`network` argument will be deprecated in the future. Directly passing `base_url` is recommended."
            )
            self._network = network
        else:
            self._network = Network.TESTNET

        self._project_id = project_id
        self._base_url = (
            base_url
            if base_url
            else ApiUrls.preprod.value
            if self.network == Network.TESTNET
            else ApiUrls.mainnet.value
        )
        self.api = BlockFrostApi(project_id=self._project_id, base_url=self._base_url)
        self._epoch_info = self.api.epoch_latest()
        self._epoch = None
        self._genesis_param = None
        self._protocol_param = None

In this initialization of the BlockFrostChainContext class, the self._network gets always set to Network.TESTNET regardless of the value of base_url.

To Reproduce initialize a context:

context = BlockFrostChainContext(
        blockfrost_project_id,
        base_url=(
            blockfrost.ApiUrls.mainnet.value
        ),
    )
    print("context network ", context.network)

output:

context network  Network.TESTNET

Expected behavior The self._network value should be correcly updated according to the value of base_url.

cffls commented 4 months ago

self._network is going to be deprecated, and it is not a commended way of getting network. base_url is a preferred way of getting and setting network for blockfrost chain context.

nielstron commented 4 months ago

The Problem is that only setting the base url is not enough and will lead to errors down the line - one needs to set network or an unusable context is obtained.

cffls commented 4 months ago

You are right @nielstron , I forgot that this network value is used when building addresses. It is fixed in this PR: https://github.com/Python-Cardano/pycardano/pull/353