> For the complete documentation index, see [llms.txt](https://docs.chiliz.com/llms.txt). Markdown versions of documentation pages are available by appending `.md` to page URLs; this page is available as [Markdown](https://docs.chiliz.com/develop/basics/write-a-smart-contract.md).

# Write a Smart Contract

From the moment you decide to create a dApp on Chiliz Chain, you need to take the specifics of our blockchain into account.

While Chiliz Chain is EVM-compatible, treating it exactly like Ethereum can lead to usability issues, specifically regarding token decimals and gas mechanics.

Let's explore!

## Prerequisites

### Environment

Before you start writing your contract, make sure that your environment is ready.

First, you must have a wallet configured for Spicy Testnet (for development) or Chiliz Chain Mainnet (for production).

{% content-ref url="/pages/0UYb0mh54mqwYz8XblJv" %}
[Connect to Chiliz Chain](/develop/basics/connect-to-chiliz-chain.md)
{% endcontent-ref %}

Second, you will need $CHZ to pay for gas deployment on both Testnet and Mainnet. While you can buy Mainnet $CHZ on any crypto exchange, you can rely on faucets for Testnet tokens.

{% content-ref url="/pages/Af9548Yd4RQMNgtsUkq9" %}
[Obtain Free Testnet Tokens](/develop/basics/obtain-free-testnet-tokens.md)
{% endcontent-ref %}

In terms of tooling, you can rely on Hardhat or Remix. See for instance:

{% content-ref url="/pages/cwZqLlr1ee8FwupJJUCc" %}
[Deploy with Remix](/develop/basics/deploy-a-smart-contract/deploy-with-remix.md)
{% endcontent-ref %}

Finally, Chiliz Chain contracts are written in the Solidity language:

{% embed url="<https://www.soliditylang.org/>" %}

{% embed url="<https://solidity-by-example.org/>" %}

Use the recommended Solidity and EVM versions:

{% hint style="info" %}
**Recommended Solidity and EVM versions for Chiliz Chain:**

* **Solidity compiler version:** `0.8.30` (or lower)
* **Target EVM version:** `prague`
  {% endhint %}

### Fan Tokens / CAP-20

The most specific aspect of Chiliz Chain is the CAP-20 standard, used for Fan Tokens.

CAP-20 is technically equivalent to the ERC-20 standard. Since the 2026 Decimal Fan Token migration, CAP-20 tokens use 18 decimals of precision, just like standard ERC-20 tokens, so Fan Token balances, transfers, and total supply are denominated in the token's smallest unit and support fractional amounts.

{% hint style="info" %}
Fan Tokens used 0 decimals (whole units only) until the [2026 Migration to Decimal Fan Tokens](/learn/about-fan-tokens/2026-migration-to-decimal-fan-tokens.md), which upgraded them to 18-decimal precision. Contracts written against the old whole-unit assumption may need updating.
{% endhint %}

{% content-ref url="/pages/DUqAvWtmu3FJYbH3fPN4" %}
[About Fan Tokens](/learn/about-fan-tokens.md)
{% endcontent-ref %}

## Best practices in writing a smart contract

### Use Battle-Tested Libraries (OpenZeppelin)

Do not start from creating your contract from scratch.\
The single most effective security practice is to base your code on community-audited standards, to reduce the risk of vulnerabilities

For Chiliz Chain development, we strongly recommend using [OpenZeppelin Contracts](https://docs.openzeppelin.com/contracts). They provide secure and community-vetted implementations for tokens contracts.

By using standard contracts, your ensure that your tokens are compatible with known wallets (like MetaMask) and the Chiliz ecosystem (Socios.com).

### General EVM Best Practices

Regardless of the chain, these three patterns are non-negotiable for secure Solidity development.

#### The "Checks-Effects-Interactions" Pattern

This is your primary defense against [Reentrancy Attacks](https://solidity-by-example.org/hacks/re-entrancy/). Always structure your functions in this exact order:

1. Checks: Validate inputs and conditions (e.g., `require` statements).
2. Effects: Update the contract state (e.g., reduce balances).
3. Interactions: Interact with other contracts or send funds (e.g., `transfer`).

#### Robust Access Control

Never leave sensitive functions unprotected. If a function mints tokens, changes fees, or upgrades logic, it must be restricted.

* Simple: Use `Ownable` for single-admin contracts.
* Complex: Use `AccessControl` for contracts requiring multiple roles (e.g., `MINTER_ROLE`, `ADMIN_ROLE`).

#### Input Validation

Assume all input is malicious. Use `require()` statements at the very beginning of your functions to validate parameters.

For instance:

* Check for zero addresses (`address(0)`).
* Check for zero amounts when transferring.
* Verify array lengths match if passing multiple arrays.
* etc.

### Chiliz-Specific Implementation Details

While Chiliz Chain is EVM-compatible, certain "local rules" apply, specifically regarding token decimals.

#### CAP-20 Compliance (Fan Tokens)

If you are writing a contract that interacts with Fan Tokens (e.g., a Staking Pool for $PSG or $BAR), account for their decimals rather than assuming a fixed value.

Since the 2026 Decimal Fan Token migration, Fan Tokens use 18 decimals, so `1 Token = 10^18 units`, the same as most ERC-20 tokens. Older Fan Token contracts used 0 decimals (`1 Token = 1 unit`), and some may still be encountered on-chain.

* Do not hardcode a token's decimals. Read `token.decimals()` dynamically so your contract works whether a token uses 18 decimals or a legacy 0-decimal configuration.
* Scale amounts using the value returned by `decimals()` instead of assuming `1e18`.

### Gas Optimization on Chiliz

Transactions on Chiliz Chain are significantly cheaper than Ethereum, but unoptimized code can still lead to congestion or failed transactions during high-traffic events (e.g., during a live match).

Here are three ways to save on gas:

* Use Custom Errors: Instead of long string messages in `require`, use `error` definitions to save gas.
* Order your state variables to fit into 32-byte slots. Put `uint128`, `address`, and `bool` next to each other where possible.
* Prefer `external` for functions that are never called internally by the contract itself.


---

# Agent Instructions
This documentation is published with GitBook. GitBook is the documentation platform designed so that both humans and AI agents can read, navigate, and reason over technical content effectively. Learn more at gitbook.com.

## Querying This Documentation
If you need additional information that is not directly available in this page, you can query the documentation dynamically by asking a question.

Perform an HTTP GET request on the current page URL with the `ask` query parameter, and the optional `goal` query parameter:

```
GET https://docs.chiliz.com/develop/basics/write-a-smart-contract.md?ask=<question>&goal=<endgoal>
```

`ask` is the immediate question: it should be specific, self-contained, and written in natural language.
`goal` is optional and describes the broader end goal you are ultimately trying to accomplish on behalf of the user. GitBook uses it to tailor the answer towards what is most useful for that goal.

The response will contain a direct answer to the question and relevant excerpts and sources from the documentation.

Use this mechanism when the answer is not explicitly present in the current page, you need clarification or additional context, or you want to retrieve related documentation sections.
