At the beginning of most flows, we create an `ocean` object, which is an instance of class [`Ocean`](https://github.com/oceanprotocol/ocean.py/blob/main/ocean\_lib/ocean/ocean.py). It exposes useful information, including the following.
In order to initialize a Ocean object, you must provide `config_dict` which is a `Dictionary` instance and optionally a `DataServiceProvider` instance.
*`config_dict`: `dict` which is mandatory and it contains the configuration as dictionary format.
*`data_provider`: `Optional[DataProvider]` which is optional with a default value of None. If it is not provided, the constructor will instantiate a new one from scratch.
It is a helper method for retrieving the OCEAN's token address.\
It can be called only by Ocean object and returns the address as a `string`.
```python
@property
@enforce_types
def OCEAN_address(self) -> str:
return get_ocean_token_address(self.config)
```
[`get_ocean_token_address`](https://github.com/oceanprotocol/ocean.py/blob/main/ocean\_lib/ocean/util.py#LL31C1-L38C89) function is an utilitary function which gets the address from `address.json` file
"""Returns the Ocean token address for given network or web3 instance
Requires either network name or web3 instance.
"""
addresses = get_contracts_addresses(config_dict)
return Web3.toChecksumAddress(addresses.get("Ocean").lower()) if addresses else None
```
{% endcode %}
</details>
<details>
<summary><ahref="https://github.com/oceanprotocol/ocean.py/blob/main/ocean_lib/ocean/ocean.py#LL105C1-L113C32"><code>ocean.OCEAN_token</code> or <code>ocean.OCEAN -> Datatoken</code></a></summary>
It is a helper method for retrieving the OCEAN token object (Datatoken class).\
It can be called within Ocean class and returns the OCEAN Datatoken.
It is a getter for a specific `datatoken` object based on its checksumed address.\
It can be called within Ocean class with a string `token_address` as parameter which returns the `DatatokenBase` instance depending on datatoken's template index.
Calls Provider to generate provider fees as dictionary for compute service.
As parameters:
1.`datasets` - list of `ComputeInput` which contains the data assets
2.`algorithm_data` - necessary data for algorithm and it can be either a `ComputeInput` object, either just the algorithm metadata, `AlgorithmMetadata`
3.`consumer_address` - address of the compute consumer wallet which is requesting the provider fees
4.`compute_environment` - id provided from the compute environment as `string`
5.`valid_until` - timestamp in UNIX miliseconds for the duration of provider fees for the compute service.
Creates asset of type "dataset", having `UrlFiles`, with good defaults.
It can be called after instantiating Ocean object.
Params:
1.`name` - name of the asset, `string`
2.`url` - url that is stored in the asset, `string`
3.`publisher_wallet` - wallet of the asset publisher/owner, `Brownie account`
4.`wait_for_aqua` - boolean value which default is `True`, waiting for aquarius to fetch the asset takes additional time, but if you want to be sure that your asset is indexed, keep the default value.
Return:
A tuple which contains the data NFT, datatoken and the data asset.
Create asset of type "algorithm", having `UrlFiles`, with good defaults
It can be called after instantiating Ocean object.
Params:
1.`name` - name of the asset, `string`
2.`url` - url that is stored in the asset, `string`
3.`publisher_wallet` - wallet of the asset publisher/owner, `Brownie account`
4.`image` - docker image of that algorithm, `string`
5.`tag` - docker tag for that algorithm image, `string`
6.`checksum` - docker checksum for algorithm's image, `string`
7.`wait_for_aqua` - boolean value which default is `True`, waiting for aquarius to fetch the asset takes additional time, but if you want to be sure that your asset is indexed, keep the default value.
Return:
A tuple which contains the algorithm NFT, algorithm datatoken and the algorithm asset.
Creates asset of type "data", having `ArweaveFile`, with good defaults.
It can be called after instantiating Ocean object.
Params:
1.`name` - name of the asset, `string`
2.`transaction_id` - transaction id from the arweave file, `string`
3.`publisher_wallet` - wallet of the asset publisher/owner, `Brownie account`
4.`wait_for_aqua` - boolean value which default is `True`, waiting for aquarius to fetch the asset takes additional time, but if you want to be sure that your asset is indexed, keep the default value.
Return:
A tuple which contains the data NFT, datatoken and the data asset.
{% code overflow="wrap" %}
```python
@enforce_types
def create_arweave_asset(
self,
name: str,
transaction_id: str,
publisher_wallet,
wait_for_aqua: bool = True,
) -> tuple:
"""Create asset of type "data", having ArweaveFiles, with good defaults"""
Creates asset of type "data", having `GraphqlQuery` files, with good defaults.
It can be called after instantiating Ocean object.
Params:
1.`name` - name of the asset, `string`
2.`url` - url of subgraph that you are using, `string`
3.`query` - GraphQL query, `string`
4.`publisher_wallet` - wallet of the asset publisher/owner, `Brownie account`
5.`wait_for_aqua` - boolean value which default is `True`, waiting for aquarius to fetch the asset takes additional time, but if you want to be sure that your asset is indexed, keep the default value.
Return:
A tuple which contains the data NFT, datatoken and the data asset.
{% code overflow="wrap" %}
```python
@enforce_types
def create_graphql_asset(
self,
name: str,
url: str,
query: str,
publisher_wallet,
wait_for_aqua: bool = True,
) -> tuple:
"""Create asset of type "data", having GraphqlQuery files, w good defaults"""
Creates asset of type "data", having `SmartContractCall` files, with good defaults.
It can be called after instantiating Ocean object.
Params:
1.`name` - name of the asset, `string`
2.`contract_address` - contract address that should be stored in the asset, `string`
3.`contract_abi` - ABI of functions presented in the contract, `string`
4.`publisher_wallet` - wallet of the asset publisher/owner, `Brownie account`
5.`wait_for_aqua` - boolean value which default is `True`, waiting for aquarius to fetch the asset takes additional time, but if you want to be sure that your asset is indexed, keep the default value.
Return:
A tuple which contains the data NFT, datatoken and the data asset.
{% code overflow="wrap" %}
```python
@enforce_types
def create_onchain_asset(
self,
name: str,
contract_address: str,
contract_abi: dict,
publisher_wallet,
wait_for_aqua: bool = True,
) -> tuple:
"""Create asset of type "data", having SmartContractCall files, w defaults"""
Register an asset on-chain. Asset = {data\_NFT, >=0 datatokens, DDO}
Creating/deploying a DataNFT contract and in the Metadata store (Aquarius).
Params:
*`metadata`: `dictionary` conforming to the Metadata accepted by Ocean Protocol. 
*`publisher_wallet`- `Brownie account` of the publisher registering this asset.
*`credentials` - credentials `dictionary` necessary for the asset, which establish who can consume the asset and who cannot.
*`data_nft_address`- hex string, the address of the data NFT. The new asset will be associated with this data NFT address.
*`data_nft_args`- object of DataNFTArguments type if creating a new one.
*`deployed_datatokens`- list of datatokens which are already deployed.
*`services` - list of `Service` objects if you want to run multiple services for a datatoken or you have multiple datatokens with a single service each.
*`datatoken_args` - list of objects of `DatatokenArguments` type if creating a new datatokens.
*`encrypt_flag`- bool for encryption of the DDO.
*`compress_flag`- bool for compression of the DDO.
*`wait_for_aqua`- bool for spending time waiting for DDO to be updated in Aquarius.
Return:
A tuple which contains the data NFT, datatoken and the data asset.
The DDO is stored on-chain. It's encrypted and compressed by default. Therefore it supports GDPR "right-to-be-forgotten" compliance rules by default.
You can control this during `create()`:
* To disable encryption, use `ocean.assets.create(..., encrypt_flag=False)`.
* To disable compression, use `ocean.assets.create(..., compress_flag=False)`.
* To disable both, use `ocean.assetspy.create(..., encrypt_flag=False, compress_flag=False)`.
#### Create _just_ a data NFT
Calling `create()` like above generates a data NFT, a datatoken for that NFT, and a ddo. This is the most common case. However, sometimes you may want _just_ the data NFT, e.g. if using a data NFT as a simple key-value store. Here's how:
If you call `create()` after this, you can pass in an argument `data_nft_address:string` and it will use that NFT rather than creating a new one.
#### Create a datatoken from a data NFT
Calling `create()` like above generates a data NFT, a datatoken for that NFT, and a ddo object. However, we may want a second datatoken. Or, we may have started with _just_ the data NFT, and want to add a datatoken to it. Here's how:
If you call `create()` after this, you can pass in an argument `deployed_datatokens:List[Datatoken1]` and it will use those datatokens during creation.
#### Create an asset & pricing schema simultaneously
Ocean Assets allows you to bundle several common scenarios as a single transaction, thus lowering gas fees.
Any of the `ocean.assets.create_<type>_asset()` functions can also take an optional parameter that describes a bundled pricing schema (Dispenser or Fixed Rate Exchange). 
Here is an example involving an exchange:
{% code overflow="wrap" %}
```python
from ocean_lib.models.fixed_rate_exchange import ExchangeArguments
*`consumer_wallet` - Brownie account for the wallet that "ordered" the asset.
*`destination` - destination path, as string, where the asset will be downloaded.
*`order_tx_id` - transaction ID for the placed order, string and bytes formats are accepted.
Optional params:
*`service` - optionally if you want to provide the `Service` object through you downloaded the asset.
*`index` - optionally if you want to download certain files, not the whole asset, you can specify how many files you want to download as positive `integer` format.
*`userdata` - `dictionary` additional data from user.
Return:
The full path to the downloaded file as `string`.
{% code overflow="wrap" %}
```python
@enforce_types
def download_asset(
self,
ddo: DDO,
consumer_wallet,
destination: str,
order_tx_id: Union[str, bytes],
service: Optional[Service] = None,
index: Optional[int] = None,
userdata: Optional[dict] = None,
) -> str:
service = service or ddo.services[0] # fill in good default
if index is not None:
assert isinstance(index, int), logger.error("index has to be an integer.")
assert index >= 0, logger.error("index has to be 0 or a positive integer.")
assert (
service and service.type == ServiceTypes.ASSET_ACCESS
), f"Service with type {ServiceTypes.ASSET_ACCESS} is not found."
Pays for compute service by calling `initializeCompute` endpoint from Provider to retrieve the provider fees and starting the order afterwards.
Params:
*`datasets` - list of `ComputeInput` objects, each of them includes mandatory the DDO and service.
*`algorithm_data` - which can be either a `ComputeInput` object which contains the whole DDO and service, either provide just the algorithm metadata as `AlgorithmMetadata`.
*`service_endpoint` - string Provider URL that is stored in compute service.
*`chain_id` - using Provider multichain, `chain_id` is required to specify the network for your environment. It has `int` type.
Return:
A list of objects containing information about each compute environment. For each compute environment, these are the following keys: `(id, feeToken, priceMin, consumerAddress, lastSeen, namespace, status)`.
*`service_endpoint` - string Provider URL that is stored in compute service.
*`chain_id` - using Provider multichain, `chain_id` is required to specify the network for your environment. It has `int` type.
Return:
A list of objects containing information about each compute environment. For each compute environment, these are the following keys: `(id, feeToken, priceMin, consumerAddress, lastSeen, namespace, status)`.
1.`tx_dict` - is the configuration `dictionary` for that specific transaction. Usually for `development` we include just the `from` wallet, but for remote networks, you can provide gas fees, required confirmations for that block etc. For more info, check [Brownie docs](https://eth-brownie.readthedocs.io/en/stable/).
2.`max_tokens` - maximum amount of tokens to dispense in wei. The default is a large number.
3.`max_balance` - maximum balance of requester in wei. The default is a large number.
2.`tx_dict` - is the configuration `dictionary` for that specific transaction. Usually for `development` we include just the `from` wallet, but for remote networks, you can provide gas fees, required confirmations for that block etc. For more info, check [Brownie docs](https://eth-brownie.readthedocs.io/en/stable/).
1.`consumer` - address of the consumer wallet that needs funding
2.`service_index` - service index as int for identifying the service that you want to further call [`start_order`](https://github.com/oceanprotocol/ocean.py/blob/4aa12afd8a933d64bc2ed68d1e5359d0b9ae62f9/ocean\_lib/models/datatoken.py#LL169C5-L197C10).
3.`transaction_parameters` - is the configuration `dictionary` for that specific transaction. Usually for `development` we include just the `from` wallet, but for remote networks, you can provide gas fees, required confirmations for that block etc. For more info, check [Brownie docs](https://eth-brownie.readthedocs.io/en/stable/).
4.`consume_market_fees` - [`TokenInfo` ](https://github.com/oceanprotocol/ocean.py/blob/4aa12afd8a933d64bc2ed68d1e5359d0b9ae62f9/ocean\_lib/models/datatoken.py#L31)object which contains the consume market fee amount, address & token address. If it is not explicitly specified, by default it has an empty `TokenInfo` object.
Returns a `DispenserStatus` object returned from `Dispenser.sol::status(dt_addr)` which is composed of:
* bool active
* address owner
* bool isMinter
* uint256 maxTokens
* uint256 maxBalance
* uint256 balance
* address allowedSwapper
These are Solidity return values & types, but `uint256` means int in Python and `address` is a `string` instance.
For tips & tricks, check [this section](https://github.com/oceanprotocol/ocean.py/blob/4aa12afd8a933d64bc2ed68d1e5359d0b9ae62f9/READMEs/main-flow.md#faucet-tips--tricks) from the [README](https://github.com/oceanprotocol/ocean.py/blob/4aa12afd8a933d64bc2ed68d1e5359d0b9ae62f9/READMEs/main-flow.md).
It is implemented in DatatokenBase, inherited by Datatoken2, so it can be called within both instances.
```python
@enforce_types
def dispenser_status(self):
""":return: DispenserStatus object"""
# import here to avoid circular import
from ocean_lib.models.dispenser import DispenserStatus
It is implemented in DatatokenBase, inherited by Datatoken2, so it can be called within both instances.
For this datatoken, create a single fixed-rate exchange (OneExchange).
This wraps the smart contract method `Datatoken.createFixedRate()` with a simpler interface.
Main params:
*`rate` - how many base tokens does 1 datatoken cost? In wei or string
*`base_token_addr` - e.g. OCEAN address
*`tx_dict` - is the configuration `dictionary` for that specific transaction. Usually for `development` we include just the `from` wallet, but for remote networks, you can provide gas fees, required confirmations for that block etc. For more info, check [Brownie docs](https://eth-brownie.readthedocs.io/en/stable/).
Optional params, with good defaults:
*`owner_addr` - owner of the datatoken
*`publish_market_fee_collector` - fee going to publish market address
*`publish_market_fee` - in wei or string, e.g. `int(1e15)` or `"0.001 ether"`
*`with_mint` - should the exchange mint datatokens as needed (`True`), or do they need to be supplied/allowed by participants like base token (`False`)?
*`allowed_swapper` - if `ZERO_ADDRESS`, anyone can swap
*`full_info` - return just `OneExchange`, or `(OneExchange, <other info>)`
This function is used to retrieve funds or datatokens for an user who wants to start an order.
It is implemented in Datatoken class and it is also inherited in Datatoken2 class.
Each parameter has the following meaning:
1.`consumer` - address of the consumer wallet that needs funding
2.`service_index` - service index as int for identifying the service that you want to further call [`start_order`](https://github.com/oceanprotocol/ocean.py/blob/4aa12afd8a933d64bc2ed68d1e5359d0b9ae62f9/ocean\_lib/models/datatoken.py#LL169C5-L197C10).
3.`transaction_parameters` - is the configuration `dictionary` for that specific transaction. Usually for `development` we include just the `from` wallet, but for remote networks, you can provide gas fees, required confirmations for that block etc. For more info, check [Brownie docs](https://eth-brownie.readthedocs.io/en/stable/).
4.`consume_market_fees` - [`TokenInfo` ](https://github.com/oceanprotocol/ocean.py/blob/4aa12afd8a933d64bc2ed68d1e5359d0b9ae62f9/ocean\_lib/models/datatoken.py#L31)object which contains the consume market fee amount, address & token address. If it is not explicitly specified, by default it has an empty `TokenInfo` object.
Return value is a hex string for transaction hash which denotes the proof of starting order.
It is implemented in Datatoken class and it is also inherited in Datatoken2 class.
Each parameter has the following meaning:
1.`consumer` - address of the consumer wallet that needs funding
2.`service_index` - service index as int for identifying the service that you want to apply `start_order`.
3.`provider_fees` - dictionary which includes provider fees generated when `initialize` endpoint from `Provider` was called.
4.`transaction_parameters` - is the configuration `dictionary` for that specific transaction. Usually for `development` we include just the `from` wallet, but for remote networks, you can provide gas fees, required confirmations for that block etc. For more info, check [Brownie docs](https://eth-brownie.readthedocs.io/en/stable/).
5.`consume_market_fees` - [`TokenInfo` ](https://github.com/oceanprotocol/ocean.py/blob/4aa12afd8a933d64bc2ed68d1e5359d0b9ae62f9/ocean\_lib/models/datatoken.py#L31)object which contains the consume market fee amount, address & token address. If it is not explicitly specified, by default it has an empty `TokenInfo` object.
Return value is a hex string for transaction hash which denotes the proof of starting order.
It is implemented in Datatoken class and it is also inherited in Datatoken2 class.
Each parameter has the following meaning:
1.`order_tx_id` - transaction hash of a previous order, string or bytes format.
2.`provider_fees` - dictionary which includes provider fees generated when `initialize` endpoint from `Provider` was called.
3.`transaction_parameters` - is the configuration `dictionary` for that specific transaction. Usually for `development` we include just the `from` wallet, but for remote networks, you can provide gas fees, required confirmations for that block etc. For more info, check [Brownie docs](https://eth-brownie.readthedocs.io/en/stable/).
Return value is a hex string for transaction hash which denotes the proof of reusing order.