# Welcome to GoodDocs!

Here you will find all the documentation for the GoodDollar protocol Smart Contracts and Dapp interfaces.

Welcome! [GoodDollar](https://gooddollar.org/) is a decentralized currency for the commons initiative. Here you can find all the open-source documentation for the smart contracts and interfaces!

{% hint style="info" %}
Read project's [vision](/gooddollar-ecosystem-vision) and [whitepaper](https://whitepaper.gooddollar.org/) for deep dive into the philosophy and decision's rationals
{% endhint %}

Let's get started:

## Gooddollar - A currency for the commons

[GoodDollar](http://www.gooddollar.org/) is a people-powered economic framework to generate, finance, and distribute a global currency to fund the commons via the GoodDollar token (“G$ coin”). Its goal is to reduce wealth inequality through supporting local and digital commons communities with funding and through the creation of a universal basic income (UBI).&#x20;

GoodDollar leverages new protocols and smart contracts to deliver a “trickle-up” value structure, which places money in the hands of those who need it most. This is the reverse of the conventional trickle-down approach to capital, credit, and interest-bearing money.

A digital asset that operates within the emerging ecosystem of decentralized and open finance, G$ coin is backed by a monetary reserve of cryptocurrencies and thus has tangible value and is **always liquid**. G$ coins are liquid and convertible to other cryptocurrencies, and will be available to buy and sell directly via the GoodDollar GoodReserve smart contract.

The value in the GoodDollar reserve was initially seeded by eToro, Celo and XDC. Its growing value comes from the underlying demand for a G$ based economy. The more people and communities choose to transact with G$ the more value will accrue in the reserve. Cryptocurrencies held at the reserve can earn interest which further increases the value in the reserve.

The funding of the commons and UBI is done through a dynamic money creation rate that can change according to the economic conditions and is governed by the GoodDAO.

## Four main components to the Gooddollar project:

1. [Protocol](/how-gooddollar-works)
2. Easy to use [Wallet](#gooddollar-wallet) with built-in community features
3. Ecosystem [GoodDapp](/wallet-and-dapps/gooddapp) , [GoodCollective](/wallet-and-dapps/goodcollective) and more
4. Ecosystem [Dashboard](http://dashboard.gooddollar.org)

{% hint style="info" %}
If you wish to contribute please read [this](/for-developers/contributing).
{% endhint %}

Thanks for your interest!

**The GoodDollar Team <3**


# GoodDollar Ecosystem Vision

{% hint style="info" %}
Read more about the Ecosystem fund in this article:\
<https://medium.com/gooddollar/launching-goodbuilders-the-first-initiative-of-the-250k-gooddollar-ecosystem-fund-5aaf209cf892>
{% endhint %}

**The new chapter is GoodDollar UBI Economy 2.0** — transitioning from **simply distributing G$** to building a **sustainable digital economy** where G$ **circulates through investments, grants, and real economic activity**, ensuring lasting value creation.\
\
*Opportunity for* **developers or innovators in fintech**, [you can contribute by](https://gooddollar.notion.site/GoodBuilders-Program-1a6f258232f080fea8a6e3760bb8f53d) building **mechanisms for G$ users** – whether it’s peer-to-peer lending dApps, integration with existing finance platforms, or novel new models using GoodDollar data. As the ecosystem matures, recipients could gain access to financial tools and services previously out of reach, further **breaking the cycle of poverty**.

Oppurtunity **for protocols, communities and DAOs:**

### **GoodDollar Ecosystem Flow**&#x20;

Supporters can buy G$ or donate the **yield** to the GoodDollar Reserve and distribute grants in G$ (over simply grants in USD) , while investors, customers, and businesses add value by **buying G$ directly from the Reserve or on decentralized exchanges**. The protocol’s monetary mechanism then **creates new G$**, primarily by adjusting the reserve ratio and increasing reserve leverage.

These newly created tokens flow into the ecosystem as **daily UBI for citizens**, as well as incentives that support **savings, entrepreneurship, and real economic activity**. Recipients spend G$ with **businesses, dApps, and peers**, creating circulation and utility across the GoodDollar economy.

Entrepreneurs and projects can access additional incentives through ecosystem initiatives such as **matching funds, grants, community programs, and low-interest credit**, helping new ideas and local economies grow.

<img src="/files/Bit2H8AeQiETRrZni9nU" alt="" class="gitbook-drawing">

### **The GoodDollar ecosystem creates a circular flow of value**&#x20;

The GoodDollar ecosystem creates a **self-reinforcing cycle of value**. Investors and supporters strengthen the reserve by buying G$ or donating yield. The protocol leverage that value into more **digital money**, distributing it as UBI and ecosystem incentives.

Citizens use G$ in the real economy—buying goods, supporting businesses, and participating in dApps—which attracts **more builders, businesses, and investors** into the system.

The result is an open, transparent, on-chain economy where **anyone can participate**: fund it, claim it, build on it, or grow it. Each action helps expand a living experiment in **an economy for the commons powered by crypto**, proving that a more inclusive economy can be built—one G$ at a time. 🚀

## Win Rewards: Building something on GoodDollar!

There are various ways to earn rewards while working within the GoodDollar Ecosystem.\
\
*Scoutgame:*\
Scoutgame rewards builders who take up pre-defined tasks.\
Contribute to GoodDollar repositories and earn bounty rewards!\
More information about the program can be found on our ScoutGame[ page.](https://scoutgame.xyz/info/partner-rewards/gooddollar)\
\
*GoodDollar OpenSource Contributors Pool:*\
The GoodDollar OpenSource Contributors pool is for anyone who wants to contribute more autonomously.\
Maybe you have ideas of your own to build into GoodDapp or GoodCollective?\
Maybe you have ideas for expanding the core protocol?\
Please read up on our [GoodDollar OpenSource Contributors](https://app.gardens.fund/gardens/42220/0x62b8b11039fcfe5ab0c56e502b1c372a3d2a9c7a/0xf42c9ca2b10010142e2bac34ebdddb0b82177684/94) covenant on how to participate and apply.\
\
*GoodBuilders program:*\
Be sure to check out the [GoodBuilders Program!](https://ubi.gd/goodbuilders) offering mentorship and funding to support promising projects in their growth. Any project that demonstrates meaningful new integrations with the GoodDollar Protocol is eligible to apply!\
\
**Share your ideas, or ask for development support:**\
For discussion on Discord or various program events: [GoodDollar Builders](https://t.me/gooddollarbounties)\
We are also on Discord:  [GoodDollar Discord Development](https://discord.gg/B4bj9eXuWU)


# How GoodDollar Works

How does the GoodDollar protocol and G$ tokenomics work? Learn how we utilize DeFi to fund wealth creation for all.

The GoodDollar protocol presents a sustainable and scalable framework for the distribution of Universal Basic Income (UBI) as a means to improve financial access and empowerment. Built on blockchain technology, GoodDollar leverages decentralized finance (DeFi) and token engineering to **create money that powers the GoodDollar economy and the commons**, distributing it as **UBI and incentives that support real economic activity**.

GoodDollar stands out as a unique project with a mission that goes beyond financial gains. Rooted in a commitment to financial inclusion and wealth redistribution, the GoodDollar token (G$) is designed to support an open digital economy where new money can be created and directed toward inclusive growth. The protocol distributes G$ to a global community of users while also incentivizing economic participation and ecosystem development.

***

### Sustainability: A Natural Equilibrium 🌳

GoodDollar's foundational principle is sustainability, based on **G$ as a reserve-backed token**. Notably, there was no pre-mint or Token Generation Event (TGE) for GoodDollar (or allocation to founders or sponsors). Instead, G$ tokens are created through the protocol’s monetary mechanism tied to the GoodDollar Reserve.

The **primary value in the reserve comes from investors, customers, and businesses that purchase G$ tokens** in order to participate in and support the GoodDollar economy. These purchases add assets to the reserve and strengthen the system’s liquidity.

Additional value flows into the reserve from **supporters who donate the interest earned from capital they stake in decentralized finance protocols**. This model allows supporters to contribute ongoing yield to the system while retaining ownership of their underlying capital.

New G$ tokens are created primarily when purchased from the reserve or by **increasing reserve leverage through reductions in the reserve ratio**, allowing the protocol to mint additional G$ while maintaining reserve backing. The newly created tokens are then distributed as UBI and incentives that support the growth of the GoodDollar economy and commons.

***

### Stability: Striking the Right Balance 🎠

G$ is designed to maintain a level of price stability that is **“stable enough”** to encourage circulation and usage of G$ tokens for payments rather than pure speculation.

Its price is supported by the assets held in the GoodDollar Reserve and governed by the protocol’s bonding curve mechanism. This reserve-backed model helps moderate extreme volatility and provides a predictable pricing framework appropriate for a currency intended for everyday use within the GoodDollar economy.

***

### Liquidity: Trust and Incentives ♻️

Ensuring token liquidity is vital for a cryptocurrency’s success. **G$ tokens are always liquid and convertible to other cryptocurrencies through the GoodReserve smart contract**, which acts as the protocol’s primary market maker and a market maker of last resort.

This mechanism allows users to **buy or sell G$ directly against the reserve**, enabling participants to easily enter or exit the GoodDollar economy.

Liquidity is further supported on sidechains through decentralized exchanges (DEXs), enabling users to trade G$ into other cryptocurrencies, fiat gateways, mobile money systems, or other digital assets.

***

### The Basics of GoodDollar Tokenomics

#### Augmented Bonding Curve: The Heart of G$ 💙

The G$ token operates on an **Augmented Bonding Curve** backed by a monetary reserve. The token’s price is automatically calculated using a modified version of the Bancor V1 formula.

This mechanism dynamically adjusts the price of G$:

* When G$ is purchased from the reserve, the price increases.
* When G$ is sold back to the reserve, the price decreases.

The bonding curve allows the protocol to **create new money that funds UBI and the commons**, with the level of leverage determined by the **reserve ratio**. Lower reserve ratios increase leverage and enable the protocol to mint more G$ relative to the assets in the reserve.

***

#### On-Demand Issuance: Balancing Supply and Demand ⚖️

G$ issuance is governed by the bonding curve mechanism and reserve parameters. New G$ can be minted when users purchase G$ through the reserve or when reserve leverage increases through adjustments to the reserve ratio.

Conversely, G$ is burned when tokens are returned to the reserve through sales, helping maintain balance between supply and demand.

***

#### Sources of Reserve Value

The assets held in the GoodDollar Reserve originate from several sources:

**Market participation**\
Investors, users, and businesses purchasing G$ contribute the primary value to the reserve, strengthening the monetary base of the GoodDollar economy.

**Supporter yield contributions**\
Supporters may stake capital in third-party DeFi protocols and donate the **yield generated** to the GoodDollar Reserve, allowing them to support UBI without donating their principal capital.

**Ecosystem fees and contributions**\
Protocol revenues or ecosystem-generated fees may also be directed to the reserve to support the monetary system.

***

### G$ Distribution 🔷

The GoodDollar protocol distributes newly created G$ across several functions that support the GoodDollar economy and commons.

The protocol is **multi-chain by design**. Core monetary infrastructure exists on the base chain, while UBI distribution occurs on low-cost networks such as **Celo and XDC**, making participation accessible to users globally.

G$ created by the protocol is allocated across several categories:

* **UBI distribution** for verified users
* **Savings incentives** that reward long term holders
* **Community and governance treasury**
* **Ecosystem incentives** that support aligned projects and real economic activity

The UBI mechanism distributes G$ daily to verified users. The available UBI pool is divided among users who claim within each 24-hour period.

Identity verification and periodic revalidation create a filtering mechanism sometimes described as **Proof of Need**, where users with the greatest economic need are most likely to claim the UBI.

***

### Governance: GoodDAO 💪

The GoodDollar protocol is governed by **GoodDAO**, its decentralized governance system.

Membership in GoodDAO is determined by holding **non-transferable GOOD governance tokens**, which allow participants to propose, debate, and vote on protocol changes. Because GOOD tokens cannot be traded, governance power is designed to be distributed across the community rather than concentrated among wealthy token holders.


# Architecture & Value Flow

How does the protocol works?

G$ is a digital asset designed to power the GoodDollar economy and the commons by creating money and distributing it as **Universal Basic Income (UBI)** and incentives that support real economic activity. It operates within the emerging ecosystem of decentralized and open finance and is issued by the GoodDollar protocol against a reserve of cryptocurrencies held in the GoodDollar Reserve.

The primary value in the reserve comes from **investors, customers, and businesses that purchase G$ tokens** in order to participate in and support the GoodDollar economy. Additional value flows into the reserve from **supporters who donate the interest earned on capital they stake in decentralized finance protocols**, strengthening the system without requiring the underlying capital itself to be donated.

New G$ tokens are created primarily by **increasing reserve leverage through reductions in the reserve ratio**. The newly issued G$ is then distributed through the protocol to support **daily UBI payments to verified users, incentives for savings and participation, ecosystem development, and aligned projects**, helping grow a sustainable and inclusive digital economy.

G$ tokens are **always liquid and convertible to other cryptocurrencies**, and can be bought or sold directly through the **GoodDollar GoodReserve smart contract**, enabling participants to easily enter or exit the GoodDollar economy.

### **How the GoodDollar system works** <a href="#cbghnzkzyo0f" id="cbghnzkzyo0f"></a>

This is the money flow that underpins the generation of GoodDollar crypto UBI.

<figure><img src="/files/M7LxYrDXndlVcH48lFQt" alt=""><figcaption></figcaption></figure>

***

## Overview

The diagram describes how **GoodDollar governance, reserves, and distribution infrastructure operate across multiple chains (Celo, XDC, and Fuse)** to distribute **UBI and ecosystem incentives**.

Three types of flows are represented:

* **Governance (orange dashed arrows)** – decisions made by the DAO and Guardians
* **Money flow (blue arrows)** – movement of funds and G$ tokens
* **Identity verification (red arrows)** – required to claim UBI

***

## 1. Governance Layer

{% hint style="warning" %}

#### GoodDollar governance is going through a restructure follow on <https://discourse.gooddollar.org>

{% endhint %}

#### GoodDAO

The **GoodDAO** is the primary governance body of the system.\
It defines policies such as:

* distribution rules
* incentives
* supported chains
* reserve management

#### Guardians

**Guardians** act as an operational governance layer that executes or oversees decisions made by GoodDAO.

Governance flow:

**GoodDAO → Guardians → ecosystem components**

Guardians influence how reserves, bridges, and chains operate.

***

## 2. The Reserve (Money Creation)

The **Reserve** is the financial engine of the system.

It **creates G$ (GoodDollar tokens)** which are then allocated to several purposes.

The Reserve generates G$ that flows into the **Distribution Manager**, which allocates it to:

1. **UBI Distribution** – daily payments to verified users
2. **Savings incentives** – rewards for participating in savings mechanisms
3. **DAO Treasury** – funds for governance and ecosystem development
4. **House of Alignment incentives** – funding for ecosystem projects aligned with GoodDollar goals
5. **Other future utility** - credit, cashbacks and subsidies

***

## 3. Distribution Manager

The **Distribution Manager** receives newly created G$ from the Reserve and distributes it.

From here funds flow to:

* **UBI Distribution**
* **Savings incentives**
* **DAO Treasury**
* **House of Alignment projects**

This component acts as the **central allocator of G$ emissions**.

***

## 4. UBI Distribution and Identity

To receive UBI:

1. A user must pass **Identity verification**
2. The **UBI Distribution contract** releases G$ to verified users

Flow:

**Identity verification → UBI Distribution → Users**

This ensures **one-person-one-UBI**.

***

## 5. Cross-Chain Expansion via the Bridge

The **Bridge** connects the GoodDollar system across multiple chains.

Funds from the **Distribution Manager** can flow into the **Bridge**, which then routes them to:

* other supported chains
* ecosystem projects

***

## 6. House of Alignment

The **House of Alignment** is a coordination hub for ecosystem projects that support the GoodDollar mission.

Projects in this layer can receive **G$ incentives originating from the Reserve**.

Purpose:

* align external projects with GoodDollar’s goals
* incentivize ecosystem participation
* expand utility and adoption of G$

***

## 7. Multi-Chain Deployment

The system operates across multiple chains:

#### Celo

The main infrastructure currently includes:

* Reserve
* Distribution Manager
* Savings
* DAO Treasury
* UBI Distribution
* Identity

#### XDC

Replicates the UBI infrastructure:

* Reserve
* Distribution Manager
* UBI Distribution
* Identity

#### Fuse

A lighter deployment focusing on:

* UBI Distribution
* Identity

Funds can be bridged to these chains to enable local UBI distribution.

***

## End-to-End Flow

1. **Governance**
   * GoodDAO defines policy
   * Guardians oversee implementation
2. **Money Creation**
   * Reserves create **G$**
3. **Allocation**
   * Distribution Manager allocates G$ directly or via bridge to:
     * UBI
     * Savings incentives
     * DAO Treasury
     * House of Alignment incentives
4. **Cross-chain distribution**
   * Bridge routes funds to other chains and projects
5. **User payments**
   * Verified users receive **UBI**.

***

✅ **Summary**

The Reserve mints **G$ tokens** which fund UBI, savings incentives, the DAO treasury, and ecosystem projects.\
These funds are distributed by the Distribution Manager, can be bridged across chains, and also serve as incentives for **House of Alignment projects**, enabling a multi-chain ecosystem aligned around GoodDollar’s UBI mission.


# System's Elements

## 1. **The token (G$)**

The ***GoodDollar token (G$)*** is an ERC-20, ERC-677, ERC-777 and a [**pure Supertoken**](https://superfluid.org/) (on celo) crypto token with a max supply of 2.2 trillion. It is native to Ethereum and also operates on Fuse and Celo.

## **2. The Reserve** <a href="#reserve" id="reserve"></a>

The ***GoodDollar Reserve*** is the smart contract that governs the vault holding the assets that back G$ tokens. The algorithm that guides the reserve is based on the Bancor formula, which has been altered to fit GoodDollar’s needs. There are two important characteristics unique to the GoodDollar Reserve:

1. The reserve supports the generation of G$. Users can always convert to and from G$ via the reserve.
2. The reserve applies an "exit contribution" to all G$ sold back to the reserve.
3. The unique math of the GoodDollar Reserve lends G$ exceptional stability.

## **4. Savings rewards**

Rewards are fixed at 5% APY.

## **5. Distribution Manager** <a href="#r9w6swau5npq" id="r9w6swau5npq"></a>

The **Distribution Manager** receives newly created G$ from the Reserve and distributes it.

This component acts as the **central allocator of G$ emissions**.

## **6. UBI Contract (UBIScheme)** <a href="#r9w6swau5npq" id="r9w6swau5npq"></a>

The ***UBIScheme*** is a smart contract that handles the distribution of G$ to all white-listed addresses.

The daily amount per claimer is calculated by:\
Daily Pool = G$ in pool divided by Cycle Days (60)\
Daily Claim = Daily Pool divided by previous day claimers \* 1.05 (5% buffer)

## **7. Governance (DAO)**

The GoodDollar governance model is based on the Compound governance model and code, as set out [here](https://compound.finance/docs/governance#comp). Critical to the process is the **GOOD token**, a non-transferable token that controls all smart contracts within the GoodDollar ecosystem.


# Sybil-Resistance

What is GoodDollar’s sybil-resistance mechanism and how does it work?

GoodDollar’s mission is to enable anyone in the world with access to a smartphone to easily verify their unique identity and gain access to GoodDollar UBI while still maintaining the principles of one person, one UBI. The goal behind the design of GoodDollar’s Sybil-resistance solution is to enable non-financial and non-technical people to easily and quickly get onboard and start receiving UBI, while preventing fraud and abuse.

The sybil-resisitance solution is based upon each member verifying themselves and their associated EVM-wallet as an address associated with a unique, live member. This a crucial component that ensures the fair distribution of G$ while preventing individuals from registering multiple times.

When signing up for GoodDollar in GoodWallet or in a 3rd party wallet, a new member will be asked to verify that they are a unique and live person. This approaches utilizes best in class facial verification technology. Once an individual proves they are a live and unique human being, a hash is generated and associated with the wallet address that they have created (GoodWallet) or are attempting to verify (existing EVM-address, 3rd party wallet). At that point their GoodID has been generated, which means this wallet address is able to access and receive G$ tokens from the UBI pool. EVM-addresses that are identified as having a GoodID are authorized to claim G$ every day from the UBI smart contract pools.

GoodDollar utilizes face verification and liveness testing through Facetec’s Zoom 3D technology. FaceTec is the first and only \*\*face authenticator certified to Level 1 & 2 in the the i Beta/NIST. Presentation Attack Detection test based on the ISO 30107-3 standard. With an FAR setting of 1 / 4.2M @ <1% FRR, and patented 3D depth detection and human liveness detection that isn’t fooled by 2D photos, videos, or even 3D masks or dolls, FaceTec is able to ensure uniqueness up to 4.2 million faces per database. FaceTec is used by HSBC, TrustID, Department of homeland security, among many other companies. (More:<https://www.facetec.com>)

GoodDollar maintains an anonymized dataset of facemaps for all registrants, continuously striving to confirm the uniqueness of each newly submitted face against this repository. All this data is stored anonymously, without any linkage to the GoodDollar user profile, blockchain address, or internal records.

This approach establishes a robust safeguard, ensuring that even in the event of a database breach, potential attackers would be unable to link faces to any personally identifiable information. Neither the GoodDollar team nor any other entity possesses the capability to correlate this data.

Within this system, each user exclusively retains ownership of their facial record identifier, and when they opt to delete their GoodDollar account, the corresponding record is removed from the facemap database after the 6 months expiration period to prevent fraud.

More about it: <https://docs.gooddollar.org/products-and-sdks/identity-sybil-resistance>

Face verification F.A.Q: [Troubleshooting](/user-guides/frequently-asked-questions/troubleshooting)

Connecting multiple wallets to your identity: [Connect another wallet address to identity](/user-guides/connect-another-wallet-address-to-identity)

{% embed url="<https://medium.com/gooddollar/gooddollar-identity-pillar-balancing-identity-and-privacy-part-i-face-matching-d6864bcebf54>" %}

{% embed url="<https://www.facetec.com>" %}


# GoodDollar In Numbers

How is G$ being utilized, and by whom?

As of the current date (September 2023), a total of 624,100 individuals from 180 different countries have claimed G$.

* Today, G$ is the #1 ERC-777 token by tx in the world (newer upgrade standard on traditional etc-20 standard) & one of the top 20 ERC-20 tokens in the world by transaction. <https://dune.com/ilemi/erc-and-eip-starter-kit>
* GoodDollar is one of the top most used protocols in the world and by far the top protocol by usage on the sidechains where it is deployed. It attracts 110,000 weekly active users on Celo, and over 100,000 monthly users on Fuse.

Based on extensive data and surveys conducted by the GoodDollar team, we have uncovered several key insights on who these people are:

1. **Geographic Distribution:** Users are spread globally, with a notable presence in emerging markets, accounting for 67% of the user base.
2. **Income Levels:** A significant portion, 43%, of these users belong to households with annual incomes of less than $5,000.
3. **Entrepreneurial Aspirations:** Approximately 30% of our users are aspiring entrepreneurs, displaying an entrepreneurial spirit and a desire to uplift their financial status.
4. **Cryptocurrency Perception:** An astonishing 100% of our user community recognizes the pivotal role that cryptocurrency plays in their pursuit of financial goals.

The user base is prominently represented by individuals from various countries, with the highest engagement and UBI claim numbers originating from: Vietnam (161.1k), Indonesia (120,4k), Nigeria (96,9k) , India (89,8k) , United States (84,9k), Bangladesh (60k), Brazil (51,7k), Argentina (44,6k), Italy (40,4k), Spain (38,6k) and Taiwan (32,8k).

These statistics highlight the global reach and diverse demographics of the GoodDollar user community, emphasizing the platform's significance in addressing financial needs and aspirations on a worldwide scale.

These are some of the most common uses of G$:

* **Digital** **Peer-to Peer**: By leveraging their digital assets as payment tokens in peer-to-peer (P2P) online marketplaces, individuals empower the creation of circular economies within their local communities.
* **Airtime and Mobile Minutes Transactions**: G$ serves as a means for buying and selling airtime and mobile minutes.
* **Community Savings Groups (Tontines)**: Members are leveraging G$ to establish and manage community savings groups in G$ tokens, akin to tontines, and using G$ savings to deploy on DeFi savings programs and provide liquidity on DEXes.
* **Educational Initiatives**: G$ is being employed as an educational tool to enlighten individuals about concepts such as circular economies, decentralized finance (DeFi), and renewable finance (RE-FI), contributing to financial literacy.
* **Local Commerce**: Entrepreneurial users are opening local stores specializing in pre-owned clothing and handcrafted goods, where G$ serves as a medium of exchange.
* **Crowdfunding for Non-Profits**: G$ is also being employed as a crowdfunding tool to support local non-profit organizations, exemplifying its potential for philanthropic endeavors.
* **Swapping for other tokens / on and off ramp:** G$ stands as a fully liquid asset, offering the flexibility for instant swaps and cash withdrawals at any given moment.
* **Exploring and interacting with Web3 tools:** The G$ token has seamlessly integrated with a variety of dApps, enabling users to effortlessly immerse themselves in the realm of Web3 applications. Among the numerous use cases, users are actively engaging in activities such as exploring NFTs, saving through platforms like Halofi, exploring DeFI like adding liquidity among other applications.

***

More about the community: <https://www.youtube.com/watch?v=EIuhmK-CNdU><https://dashboard.gooddollar.org>


# Buy & Sell G$

There are key user and stakeholder hypotheses built into our theory of change and adoption. Ultimately, the success of the GoodDollar economy is contingent upon market demand from both those who support G$ and those who claim it, as the economy itself is a balance between supply and demand.&#x20;

G$ is designed to gain usage and to be widely adopted as a means of exchange over time. Like Bitcoin, the initial dollar value, or “price”, of each G$ will be low – in the tenths of a cent on the dollar range to begin with. Our belief is that, because it offers free access to an instantly liquid, global basic income network, G$ will first be adopted in markets where smartphone-enabled populations currently live on less than US$10 a day. We believe that, for these populations, G$ could emerge as a useful complementary currency for use in peer-to-peer digital marketplaces as well as for on-the-ground goods and services, particularly as the network grows.

{% hint style="info" %}
GoodDollar ERC20 is a reserve backed currency with issuance governed by an AMM (automated market maker) encoded in the GoodReserve contract. Each time you buy or sell, from or to, the reserve - tokens are respectively being minted or burned according to [equation 2](https://whitepaper.gooddollar.org/appendix) WhitePaper.
{% endhint %}

You are able to buy and sell G$ directly to, and from, the GoodDollar Reserve contract. This healthy activity grows the liquidity of the ecosystem and increases the impact of the UBI GoodDollar delivers. Two key enhancements to the Reserve AMM contract support this change:

* The introduction of a 3% “exit contribution” fee on all sales of G$ into the #GoodDollar Reserve in exchange for supported cryptocurrencies. All fees go back into the #GoodDollar Reserve and grow the value of the overall economy.
* The creation of a new ERC20 token – G$X – that lets people buy and sell G$ to the Reserve without a fee. All those who buy G$ from the reserve will also receive an equal number of G$X.

### Prerequisites <a href="#h.7qnl0y4984hv" id="h.7qnl0y4984hv"></a>

1. You should have a web3 wallet (like [MetaMask](https://metamask.io/)).
2. You should have enough ETH in your wallet in order to pay the gas fees of the transaction.
3. You should have enough balance of the currency you are using to buy/sell with.
4. You should approve to exchangeHelper enough allowance to use your balance in order to buy/sell G$.
   1. Go to the contract page of the currency you are willing to buy/sell with, for example [cDAI contract page](https://www.google.com/url?q=https://kovan.etherscan.io/address/0xf0d0eb522cfa50b716b3b1604c4f0fa6f04376ad\&sa=D\&source=editors\&ust=1634809220729000\&usg=AOvVaw2MhLThHQa8nApkfA9sj2vh) and click on “Contract”:

![](/files/G6o1oIMSstmkADJ6wvNr)

2\. Now click on “Write as Proxy”:&#x20;

![](/files/6TEPhH6gYNtGOMxUtIMQ)

3\. Connect to your wallet by clicking on “Connect to Web3”:&#x20;

![](/files/nWYeHt7BOhwcmlFUs7ts)

4\. Now scroll down and click on “11. approve”:&#x20;

![](/files/Dn7WvA0Uged9Kq1U4mHR)

5\. You will have to enter two parameters: Spender and Amount. The spender is the contract address of the ExchangeHelper (find the relevant exchangeHelper address in the references section on the bottom of the page), the amount is the amount you would like to approve in the currency you are buying with, click Write.

![](/files/PcMZxVBssAosbOKBoVF1)

### Buy G$ with DAI / cDAI <a href="#h.5xmwue139rg6" id="h.5xmwue139rg6"></a>

1. First, make sure you have done everything in the prerequisites section.
2. Optional step, using the buyReturn function you can check how much G$ you will get.
   1. Go to GoodMarketMaker (either Mainnet, Kovan or Ropsten, link in the references below).
   2. Click on “Contract”:

![](/files/WAKF98LnQfXjTJosunYd)

3\. Click on “Read as Proxy”:&#x20;

![](/files/rOZidaTnROHHAQKCw1DT)

4\. Click on “2. buyReturn”:&#x20;

![](/files/k7bvTd72AsOMwEQ8uTIX)

5\. At “\_token (address) insert the address of the token you are planning to buy with and at the “\_tokenAmount (uint256)” insert the amount that you would like to pay with (don’t forget to add the relevant amount of decimals.&#x20;

![](/files/tMEB9ahWruII4Ut1bNUj)

6\. For example, let’s check how much G$ you will get for 10 cDAI, so you will put cDAI contract address (in this case it’s Kovan network) at the first field and 1000000000 (which is 10 cDAI because cDAi has 8 decimals):

![](/files/5ftqk03WZ9yYHBrpgh7l)

And you got a result of 9080104 which is 90801.04 G$ because G$ has 2 decimals.

3\. Now, go to the exchangeHelper (either Mainnet, Kovan or Ropsten, link in the references below)

4\. Click on “Contract”:&#x20;

![](/files/BANs9iSD3xKc7xoYK8fY)

5\. Click on “Write as Proxy”:&#x20;

![](/files/gfAGejZw3cC3kiVI6wyd)

6\. Connect your wallet by clicking on “Connect to Web3” button:&#x20;

![](/files/K5kkqNXg8emJKdIayATP)

7\. Click on “1. buy”:&#x20;

![](/files/vGG2Eyd5hUZmkbG6u6kg)

8\. Finally, we are about to purchase G$, your screen should look like that now:&#x20;

![](/files/Nqdady8RSGJw675qDQXU)

9\. Now let’s explain those 6 parameters, followed by an example:

1. buy: Payable amount in ether, if you buy in DAI / cDAI insert 0.
2. \_buyPath (address\[]): The address of the token you want to buy with, if you buy with DAI / cDAI than insert one of those addresses.
3. \_tokenAmount (uint256): Amount of G$ you would like to buy in the currency you are paying with, don’t forget to add the correct amount of zeros according to the specific token, for example 8 zeros for cDAI and 18 zeros for DAI.
4. \_minReturn (uint256): Minimum amount of G$s expected after buy transaction.
5. \_minDAIAmount (uint256): If input token is not cDAI then this parameter must be provided in order to correct swap and this parameter for minimum DAI return amount from Uniswap swap transaction
6. \_targetAddress (address): Recipient address, if the recipient is you then insert 0x0000000000000000000000000000000000000000

Example with cDAI:

![](/files/6BbirJ37D4wZVFAuZO7h)

### Sell G$ to the reserve <a href="#h.hp4socu3xt98" id="h.hp4socu3xt98"></a>

{% hint style="danger" %}
G$X token lets people buy and sell G$ to the Reserve without an exit fee. All those who buy G$ from the reserve will also receive an equal number of G$X. See [Claim GOOD and G$X](broken://pages/-MkpnoJxbZw4f-JVvEZl)
{% endhint %}

1. Optional step, using the sellReturn function you can check how much you will get for the G$ you are planning to sell.
   1. Go to GoodMarketMaker (check the references section for the relevant link).
   2. Click “Read as Proxy”.
   3. Go to “13. sellReturn”.
   4. You will have two parameters to fill;
      1. \_token (address) - this is the address of the token contract you would like to check how much you will get for your GoodDollars you are planning to sell.
      2. \_gdAmount (uint256) - this is the G$ amount you would like to sell and check how much you will get for, don’t forget to add the two decimals.
2. Go to exchangeHelper contract page.
3. Click on “Contract”.
4. Click on “Write as Proxy”.
5. Connect to your wallet by clicking on “Connect to Web3” button.
6. Open the sell function by clicking on “3. Sell”.
7. Now the parameters here are almost the same as the parameters on the buy function.
   1. \_sellPath (address\[]): The address of the token you would like to get for the G$ you are selling, if you buy with DAI / cDAI than insert one of those addresses.
   2. \_gdAmount (uint256): Amount of G$ you would like to sell, don’t forget to add two zeros as G$ has two decimals.
   3. \_minReturn (uint256): Minimum amount of G$s expected after buy transaction.
   4. \_minTokenReturn (uint256): If input token is not cDAI then this parameter must be provided in order to correct swap and this parameter for minimum DAI return amount from Uniswap swap transaction
   5. \_targetAddress (address): Recipient address, if the recipient is you then insert 0x0000000000000000000000000000000000000000

### References <a href="#h.upoh0nurgire" id="h.upoh0nurgire"></a>

|                  |                                                                                                                                                                                                                                  |                                                                                                                                                                                                                                        |                                                                                                                                                                                                                                          |
| ---------------- | -------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------- | -------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------- | ---------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------- |
| Contract         | Mainnet                                                                                                                                                                                                                          | Kovan                                                                                                                                                                                                                                  | Ropsten                                                                                                                                                                                                                                  |
| Gooddollar ERC20 | [0x67C5870b4A41D4Ebef24d2456547A03F1f3e094B](https://www.google.com/url?q=https://etherscan.io/address/0x67C5870b4A41D4Ebef24d2456547A03F1f3e094B\&sa=D\&source=editors\&ust=1634809220741000\&usg=AOvVaw1bbGiPClubVwscJgJglVg7) | [0x46183b8822BB7Cbf27E10A1acc95DfB3b5f0ec79](https://www.google.com/url?q=https://kovan.etherscan.io/address/0x46183b8822BB7Cbf27E10A1acc95DfB3b5f0ec79\&sa=D\&source=editors\&ust=1634809220742000\&usg=AOvVaw3HZ1EHRDLx2LYM-EOaqtS5) | [0x4738C5e91C4F809da21DD0Df4B5aD5f699878C1c](https://www.google.com/url?q=https://ropsten.etherscan.io/address/0x4738C5e91C4F809da21DD0Df4B5aD5f699878C1c\&sa=D\&source=editors\&ust=1634809220742000\&usg=AOvVaw2FHfogHQnSCPQ5pWAMkcVi) |
| exchangeHelper   | Did not released yet                                                                                                                                                                                                             | [0x7C8f7F618c2F84C656aeb51D652848ce76990dB7](https://www.google.com/url?q=https://kovan.etherscan.io/address/0x7C8f7F618c2F84C656aeb51D652848ce76990dB7\&sa=D\&source=editors\&ust=1634809220744000\&usg=AOvVaw1kvQTVVy-URVnOw-kNe0EN) | [0xAaB60FE459C0eB809461d858ce9A98523d826c2A](https://www.google.com/url?q=https://ropsten.etherscan.io/address/0xAaB60FE459C0eB809461d858ce9A98523d826c2A\&sa=D\&source=editors\&ust=1634809220744000\&usg=AOvVaw1aJ9bSO1fOQ6i1wC6I_pEC) |
| GoodMarketMaker  | Did not released yet                                                                                                                                                                                                             | [0xE0fdF6e09C4ac5aa5A8952ac32b16446eE0D0b79](https://www.google.com/url?q=https://kovan.etherscan.io/address/0xE0fdF6e09C4ac5aa5A8952ac32b16446eE0D0b79\&sa=D\&source=editors\&ust=1634809220745000\&usg=AOvVaw26rKAL33Cf16cSBwO3fvwi) | [0xAaB60FE459C0eB809461d858ce9A98523d826c2A](https://www.google.com/url?q=https://ropsten.etherscan.io/address/0xAaB60FE459C0eB809461d858ce9A98523d826c2A\&sa=D\&source=editors\&ust=1634809220746000\&usg=AOvVaw2cYZ3zIeecxAP__MY5MECs) |
| DAI              | [0x6b175474e89094c44da98b954eedeac495271d0f](https://www.google.com/url?q=https://etherscan.io/token/0x6b175474e89094c44da98b954eedeac495271d0f\&sa=D\&source=editors\&ust=1634809220747000\&usg=AOvVaw1MRZngV3hpR8rfUgs-y14W)   | [0x4f96fe3b7a6cf9725f59d353f723c1bdb64ca6aa](https://www.google.com/url?q=https://kovan.etherscan.io/address/0x4f96fe3b7a6cf9725f59d353f723c1bdb64ca6aa\&sa=D\&source=editors\&ust=1634809220747000\&usg=AOvVaw3gjgN3ghme5qZRY_bSrFR9) | [0xB5E5D0F8C0cbA267CD3D7035d6AdC8eBA7Df7Cdd](https://www.google.com/url?q=https://ropsten.etherscan.io/address/0xB5E5D0F8C0cbA267CD3D7035d6AdC8eBA7Df7Cdd\&sa=D\&source=editors\&ust=1634809220748000\&usg=AOvVaw1dCTVb6_CzuK1rPAmYB9wF) |
| cDAI             | [0x5d3a536e4d6dbd6114cc1ead35777bab948e3643](https://www.google.com/url?q=https://etherscan.io/token/0x5d3a536e4d6dbd6114cc1ead35777bab948e3643\&sa=D\&source=editors\&ust=1634809220748000\&usg=AOvVaw0OUt3GFPvYTu9fNQ4o5ALz)   | [0xf0d0eb522cfa50b716b3b1604c4f0fa6f04376ad](https://www.google.com/url?q=https://kovan.etherscan.io/address/0xf0d0eb522cfa50b716b3b1604c4f0fa6f04376ad\&sa=D\&source=editors\&ust=1634809220749000\&usg=AOvVaw0ZdEx5I7AhPbJA5qJ1tYsD) | [0x6ce27497a64fffb5517aa4aee908b1e7eb63b9ff](https://www.google.com/url?q=https://ropsten.etherscan.io/address/0x6ce27497a64fffb5517aa4aee908b1e7eb63b9ff\&sa=D\&source=editors\&ust=1634809220750000\&usg=AOvVaw22fahaP8I7bpT8sPeR0XlJ) |


# Bridge GoodDollars

This is a smart contract guide for those who want to bridge between Ethereum<>Celo<>Fuse<>XDC using the explorer

Currently, there's no UI for bridging. This guide will teach how you can bridge using blockchain explorers and Metamask:

### Bridging Instructions

{% hint style="info" %}
In blocker explorer, make sure you press`connect to web3` button
{% endhint %}

<figure><img src="/files/Xl0PlnFriN2PFQ1zkxsg" alt=""><figcaption><p>Connect to Web3 Button</p></figcaption></figure>

{% hint style="info" %}
The current maximum amount you can bridge is 300M G$s.\
If you plan to bridge amounts in that order, you must first verify that your request is within limits. See the Verifying bridge limits section.
{% endhint %}

1. **Approve the bridge to spend G$ tokens**
   1. Go to the G$ Contract page on the chain you are bridging from
      * Fuse: <https://explorer.fuse.io/address/0x495d133B938596C9984d462F007B676bDc57eCEC/write-contract#address-tabs>
      * Celo: <https://celoscan.io/address/0x62b8b11039fcfe5ab0c56e502b1c372a3d2a9c7a#writeProxyContract>
      * Ethereum: <https://etherscan.io/address/0x67C5870b4A41D4Ebef24d2456547A03F1f3e094B#writeContract>
      * XDC:\
        <https://xdcscan.com/address/0xEC2136843a983885AebF2feB3931F73A8eBEe50c>
   2. Open the `approve` method box and enter in the `spender` box the bridge address `0xa3247276dbcc76dd7705273f766eb3e8a5ecf4a5` (same on all chains) and in the `value/amount` enter the number of G$ units you want to bridge.\
      **Notice: In Fuse/Ethereum the units are in 2 decimals meaning that if you want to bridge 1.15 tokens this is equal to 115 units. On Celo the units are in 18 decimals, so 1.15 is 1150000000000000000 units.**\
      Press the \`write\` button and approve the transaction in your wallet.
2. **Find out the estimated bridge fee by going to** [https://goodserver.gooddollar.org/bridge/estimatefees<br>](https://goodserver.gooddollar.org/bridge/estimatefees)Record the amount for the service and path you are bridging, for example if you are bridging from Ethereum to Celo using Axelar then use the value under `AXL_ETH_TO_CELO` if using LayerZero then use the value under `LZ_ETH_TO_CELO`\
   **At the moment Axelar service is usually cheaper.**\
   **Bridging from/to Fuse and XDC is only supported by LayerZero.**
3. **Issue bridge request**
   1. Go to the Bridge Contract page on the chain you are bridging from
      * Fuse: <https://explorer.fuse.io/address/0xa3247276DbCC76Dd7705273f766eB3E8a5ecF4a5/write-proxy#address-tabs>
      * Celo: <https://celoscan.io/address/0xa3247276dbcc76dd7705273f766eb3e8a5ecf4a5#writeProxyContract>
      * Ethereum: <https://etherscan.io/address/0xa3247276dbcc76dd7705273f766eb3e8a5ecf4a5#writeProxyContract>
      * XDC: <https://xdcscan.com/address/0xa3247276dbcc76dd7705273f766eb3e8a5ecf4a5#writeProxyContract>
   2. Open/Scroll to the bridgeTo method box and enter in `target` the wallet address of the recipient, in `targetChainId` enter the chain id you are bridging to (1-Ethereum 122-Fuse 42220-Celo 50-XDC), in `amount` enter the same value as used in step #1 (the approve step), in `bridge` enter 0 for Axelar and 1 for LayzerZero. Lastly in `value/payableAmount` enter the estimated bridge fee from step #2.\
      **Make sure you have at least that amount of native tokens in your wallet**\
      press the \`write\` button

{% hint style="info" %}
When bridging from Ethereum, it can take 15 minutes for the transfer to be executed.
{% endhint %}

### Verifying bridge limits

The bridge enforces some transfer limits for security. To make sure your request will go smoothly it is recommended to first check on the **target** chain that your request is within limits.

1. Go to the Bridge Contract page on the chain you are **bridging to**
   * Fuse: <https://explorer.fuse.io/address/0xa3247276DbCC76Dd7705273f766eB3E8a5ecF4a5/read-proxy#address-tabs>
   * Celo: <https://celoscan.io/address/0xa3247276dbcc76dd7705273f766eb3e8a5ecf4a5#readProxyContract>
   * Ethereum: <https://etherscan.io/address/0xa3247276dbcc76dd7705273f766eb3e8a5ecf4a5#readProxyContract>
   * XDC <https://xdcscan.com/address/0xa3247276dbcc76dd7705273f766eb3e8a5ecf4a5#readProxyContract>
2. Open/Scroll to the `canBridge` method and enter in `from` the wallet address where you are bridging from and in `amount` enter the amount of **units in 18 decimals** that you want to bridge then press the `Query` button.

### Troubleshooting

* You can see the status of your bridge request by copying the bridge request transaction hash from step #3 and pasting it in Axelar or Layerzero scanners according to the service you used.\
  Axelar Scanner: <https://axelarscan.io/>\
  Layzerzero Scanner: <https://layerzeroscan.com/>
* If the transaction did not reach the final step on Axelar or Layerzero consult with their documentation or support channels.\
  <https://docs.axelar.dev/dev/general-message-passing/recovery>
* In case the transaction has been executed by Axelar or Layzezero but still failed to transfer the G$s then contact us via our support form here:

{% embed url="<https://gooddollar.typeform.com/to/J47K2R26>" %}

### Fuse Bridge

Fuse runs a bridge that enables bridging between Ethereum and Fuse. It has an easy-to-use UI here: <https://app.voltage.finance/#/bridge>


# Connect another wallet address to identity

How to connect multiple wallet address with your verified wallet address.

Once connected, your new wallet address will resolve to your original wallet address that was verified in our Identity smart contract. That means you will be able to claim also with associated accounts. Other dapps that rely on G$ identity can also leverage connected accounts.<br>

{% hint style="info" %}
You can connect multiple wallet addresses with your verified address. However, this does not increase the total number of claims allowed. You can still make only one claim per day, regardless of the number of connected addresses
{% endhint %}

#### Connect Account Guide <a href="#steps" id="steps"></a>

Use the tool below to connect another wallet address to your verified GoodDollar account.If the widget below does not load, try opening the widget in a new tab: <https://h3n3kp.csb.app/>

{% embed url="<https://codesandbox.io/p/sandbox/h3n3kp>" %}

#### Steps <a href="#steps" id="steps"></a>

**Connect with your verified wallet address**

1. Connect your verified wallet using the connect wallet button.
2. If you later want to connect a different wallet, click the current wallet address at the top to disconnect and reconnect.

<figure><img src="/files/duxsIxlhGbdYBiC9JDOZ" alt="" width="375"><figcaption></figcaption></figure>

**Connect the Accounts**

1. Enter the address you want to connect to your primary account.
2. You can choose on which networks you want to connect this address.

<figure><img src="/files/6OtJ5L9QgBqDDmqzpexI" alt="" width="375"><figcaption></figcaption></figure>

3. Review the details, submit the transaction, and approve it in your wallet.

By following these steps, you will successfully call the `connectAccount` method.


# Frequently Asked Questions

Seeking clarity on GoodDollar? Explore our comprehensive FAQ page for answers to all your questions!

<table data-view="cards"><thead><tr><th></th><th></th><th></th><th data-hidden data-card-target data-type="content-ref"></th></tr></thead><tbody><tr><td><a href="/pages/fSfi0zzEpMW1HfQ74YwY">Web3 basic knowlegde and security tips - by Consensys</a></td><td></td><td></td><td><a href="/pages/fSfi0zzEpMW1HfQ74YwY">/pages/fSfi0zzEpMW1HfQ74YwY</a></td></tr><tr><td><a href="/pages/9Ug9MG4iHpSIwSLmV7xL">About GoodDollar</a></td><td></td><td></td><td><a href="/pages/9Ug9MG4iHpSIwSLmV7xL">/pages/9Ug9MG4iHpSIwSLmV7xL</a></td></tr><tr><td><a href="/pages/NbXjElmWNAFAssI8Nbvy">GoodDollar Protocol &#x26; G$ Token</a></td><td></td><td></td><td><a href="/pages/NbXjElmWNAFAssI8Nbvy">/pages/NbXjElmWNAFAssI8Nbvy</a></td></tr><tr><td><a href="/pages/MUAhy7U9pjbmAOXgpJ5V">Using GoodDollar</a></td><td></td><td></td><td><a href="/pages/MUAhy7U9pjbmAOXgpJ5V">/pages/MUAhy7U9pjbmAOXgpJ5V</a></td></tr><tr><td><a href="/pages/wXmPQevoZt1nl2wzX0bQ">GoodDollar Community</a></td><td></td><td></td><td><a href="/pages/wXmPQevoZt1nl2wzX0bQ">/pages/wXmPQevoZt1nl2wzX0bQ</a></td></tr><tr><td><a href="/pages/DWVI7dPr9daPcXeFnIZA">Troubleshooting</a></td><td></td><td></td><td><a href="/pages/DWVI7dPr9daPcXeFnIZA">/pages/DWVI7dPr9daPcXeFnIZA</a></td></tr></tbody></table>

{% hint style="info" %}
If you have questions about the GoodWallet, GoodDapp and other products, check out our [Wallet and Products section. ](broken://pages/9p1GBt0VeiOY3UgiYZOB)
{% endhint %}

{% hint style="info" %}
Need help? Please explore the [Wallet and Product sections](broken://pages/9p1GBt0VeiOY3UgiYZOB), as well as our [Frequently Asked Questions](/user-guides/frequently-asked-questions). If you still need assistance, feel free to contact our [community support group](https://t.me/+jay3UR6_rEwxNjY0).
{% endhint %}


# Web3 basic knowledge and security tips - by Consensys

<details>

<summary>What is Web3?</summary>

Web3, or Web 3.0, are terms used synonymously with “the decentralized web” and are often used to refer, broadly, to the blockchain and decentralized technology ecosystems and communities as a whole.

</details>

<details>

<summary>What is Blockchain</summary>

A digital ledger comprised of unchangeable, digitally recorded data in packages called blocks. Each block is ‘chained’ to the next block using a cryptographic signature. Ethereum is a public blockchain, open to the world; its digital ledger is distributed, or synced, between many nodes; these nodes arrive at consensus regarding whether a transaction is valid before encrypting it, along with a number of other valid transactions, into a block.

</details>

<details>

<summary>What is gas?</summary>

A measure of the computational steps required for a transaction on the Blockchain. This then equates to a fee for network users paid in small units of tokens.

</details>

<details>

<summary>What is on-ramp, off-ramp?</summary>

Based on a metaphor from the American highway system, “on-ramp” refers to a tool, or a service provider, or the action, of converting fiat currency into tokens on a blockchain. Conversely, “off-ramp” refers to exchanging on-chain assets for their value in a given fiat currency.

</details>

<details>

<summary>What is an address?</summary>

Used to send and receive transactions on a blockchain network, and to identify different users; also referred to as a ‘public key’. An address is an alphanumeric character string, which can also be represented as a scannable QR code. In Ethereum, the address begins with *0x*. For example: 0x06A85356DCb5b307096726FB86A78c59D38e08ee

When you open a GoodDollar account and pass face-verification to claim G$ UBI, your GoodDollar verified-address is created. This is your ‘public key’, or wallet address that is associated with your verified GoodDollar account.

</details>

<details>

<summary>What is a private key?</summary>

A private key is an alphanumeric string of data that corresponds to a single specific account in a wallet. Private keys can be thought of as a password that enables an individual to control a specific crypto account. **Never reveal your private key to anyone, as whoever controls the private key controls the account funds. If you lose your private key, then you lose access to, and control over, that account.**

</details>

<details>

<summary>What is a bridge?</summary>

A bridge is a tool built to move assets from one network to another. It’s also a verb, used to describe that action: “I bridged my ETH from Ethereum mainnet to Arbitrum.” Not all bridges are created equal, and you should be informed about what you’re doing before you use one.

GoodDollar operates across Ethereum, Celo and Fuse networks, and G$ tokens can be bridged across those networks. One of GoodWallet’s features is an embedded bridge to move G$ tokens seamlessly to and from Celo <> Fuse. Other GoodDollar bridges are visible on [GoodDapp.com](http://gooddapp.com/).

</details>

<details>

<summary>What is cryptocurrency?</summary>

Digital currency that is based on mathematics and uses encryption techniques to regulate the creation of units of currency as well as the verification of funds transfers. Cryptocurrencies operate independently of a central bank, and are kept track of through distributed ledger technology.

</details>

<details>

<summary>What is a DAO?</summary>

A Digital Decentralized Autonomous Organization (DAO, pronounced like the Chinese concept) is a powerful and very flexible organizational structure built on a blockchain.Alternatively, the first known example of a DAO is referred to as The DAO. The DAO served as a form of investor-directed venture capital fund, which sought to provide enterprises with new decentralized business models. Ethereum-based, The DAO’s code was open source. The organization set the record for the most crowdfunded project in 2016. Those funds were partially stolen by hackers. The hack caused an Ethereum hard-fork which lead to the creation of Ethereum Classic.

</details>

<details>

<summary>What is DeFi?</summary>

If cryptocurrency is Web3’s monetary system, its financial system is DeFi. This includes familiar concepts like loans and interest-bearing financial instruments, as well as so-called “DeFi primitives”, novel solutions like token swapping and liquidity pools.

</details>

<details>

<summary>What is a DEX?</summary>

A decentralized exchange is a platform for exchanging cryptocurrencies based on functionality programmed on the blockchain (i.e., in smart contracts). The trading is peer-to-peer, or between pools of liquidity. This is in contrast with a centralized exchange, which is more akin to a bank or investment firm that specializes in cryptocurrencies. Additionally, there are so-called on-ramp providers, who could be compared to currency brokers, exchanging traditional “fiat” money for cryptocurrencies, and do not hold customer’s funds “on deposit” the way a centralized exchange does. There are important technical and regulatory differences between these, which are constantly evolving.

</details>

<details>

<summary>What is Ethereum?</summary>

A public blockchain network and decentralized software platform upon which developers build and run applications. As it is a proper noun, it should always be capitalized.

</details>

<details>

<summary>What is liquidity?</summary>

An asset is considered more ‘liquid’ if it can easily be converted into cash, and therefore, ‘liquidity’ refers to the availability of assets to a company or market. Conversely, the harder it is to turn an asset into cash, the more illiquid the asset. For example, stocks are considered relatively liquid assets, as they can be easily converted to cash while real estate is considered an illiquid asset. The liquidity of an asset affects its risk potential and market price.

</details>

<details>

<summary>What is an NFT?</summary>

When discussing Non-Fungible Tokens (NFTs), “fungibility” refers to an object’s ability to be exchanged for another. For example, an individual dollar is considered fungible, as one dollar is fully interchangeable with another. Artwork is usually deemed non-fungible, as paintings or sculptures are likely to be unequal between them in quality, value, or other attributes. A non-fungible token is a type of token that is a unique digital asset and has no equal token. This is in contrast to cryptocurrencies like ether that are fungible in nature.

</details>

<details>

<summary>What is a protocol?</summary>

Formally speaking, a ‘protocol’ is a set of rules governing how a process is carried out. This concept is used throughout public blockchain networks and web3 to refer to the way smart contracts execute their functionality in the same way regardless of the user. The products or services built on top of smart contracts are often referred to as ‘protocols’ by extension.

</details>

<details>

<summary>What are sidechains?</summary>

A ‘sidechain’ refers to a chain that is connected to another (most often, to Ethereum) through a bridge, allowing assets to be transferred between them. In contrast to a Layer 2 network or a rollup, a sidechain is a full blockchain network in and of itself, and does not rely on Ethereum for consensus.

</details>

<details>

<summary>What are smart contracts?</summary>

Smart contracts are programs that have been published on a public blockchain, and can be used by anyone. While they often contain agreements or sets of actions between parties that emulate a traditional legal contract, they are not, in and of themselves, legal documents. Smart contracts are automated actions that can be coded and executed once a set of conditions is met, and are the dominant form of programming on the Ethereum Virtual Machine

</details>

<details>

<summary>What is a stablecoin?</summary>

A cryptocurrency whose value has been ‘pegged’ to that of something considered a ‘stable’ asset, like fiat currency or gold. It theoretically remains stable in price, as it is measured against a known amount of an asset which should be less subject to fluctuation. Always spelled as one word.

</details>

{% hint style="info" %}
[Check out more terms in this Blockchain Glossary for Beginners to find our more about crypto terminology](https://consensys.io/knowledge-base/a-blockchain-glossary-for-beginners).&#x20;
{% endhint %}

<details>

<summary>Security tips</summary>

1. Never share your private key with anyone - ever.
2. Never share your seed phrase with anyone - ever.
3. Be wary of any website or any link that requires you to connect to your wallet or have funds in your wallet before connecting.
4. Beware of links/private messages on Discord/X/Telegram and other social media messages.
5. Do Your Own Research (DYOR)

</details>


# About GoodDollar

<details>

<summary>What is GoodDollar?</summary>

GoodDollar is a permissionless protocol that creates and distributes free universal basic income (UBI) as a public good governed by its members. By leveraging blockchain technology, the mission of GoodDollar is to advance decentralized financial education, promote financial inclusion, and empower communities. GoodDollar strives to establish a global landscape where every individual has access to inclusive, basic economic assets and financial products. Launched in 2020, GoodDollar has emerged as the world's largest global UBI community, with over 750,000 members across 181 countries.

GoodDollar has been widely recognized as one of the leading projects fostering financial inclusion, acknowledged by prominent institutions such as the World Economic Forum, Milken Institute, and the Crypto Council for Innovation.

</details>

<details>

<summary>What is Universal Basic Income (UBI)?</summary>

Universal Basic Income (UBI) is a concept where every individual in a society receives a regular and unconditional amount of money, regardless of their employment status, income level, or other criteria.

</details>

<details>

<summary>What is the vision and mission of GoodDollar?</summary>

GoodDollar’s vision is to leverage blockchain technology and cryptocurrency to provide universal basic income (UBI) to people around the world.

GoodDollar’s mission is gettin money where is needed the most, enabling anyone in the world with access to a smartphone to easily verify their unique identity and gain access to GoodDollar UBI, all while still maintaining the principles of one person, one UBI.

</details>

<details>

<summary>When was the project launched?</summary>

GoodDollar was released live to the public on September 1st, 2020. GoodDollar was originally founded in 2018 by Yoni Assia.

</details>

<details>

<summary>You say it's a non-profit, how is funded?</summary>

GoodDollar is a non-profit protocol - this means 100% of all tokens minted go to support the UBI ecosystem. There is no founder allocation, no private sale. 100% mission-driven.

Good Labs Foundation is the core developer behind the GoodDollar protocol, and its operations are funded by corporate donations. eToro Group, the social trading network, has funded the primary build of GoodDollar since 2019 as its core corporate social responsibility project. Good Labs is also grateful to all other institutional and private donors that have supported its work.

</details>


# GoodDollar Protocol & G$ Token

<details>

<summary>What is the GoodDollar protocol?</summary>

GoodDollar is a multi-chain protocol (a standard enabled by smart contracts) to sustainably create and distribute crypto UBI.

Built on blockchain technology, GoodDollar leverages the power of decentralized finance (DeFI) and token engineering to sustainably mint and distribute basic income tokens (G$) to a worldwide community of users. GoodDollar stands out as a unique project with a mission that goes beyond financial gains. Rooted in a commitment to financial inclusion and wealth redistribution, the GoodDollar token (G$) is underpinned by a set of core design principles that make it both sustainable and a practical approach to delivering a useful universal basic income.

Learn all about it in [GoodDollar's White Paper](https://whitepaper.gooddollar.org/) and in the [Protocol Documentation](https://docs.gooddollar.org/).

</details>

<details>

<summary>What is G$ token?</summary>

G$ is a digital cryptocurrency that is the utility token that powers the GoodDollar protocol and its ecosystem. G$ token is minted and distributed as UBI, and currently operates on Ethereum, Celo and Fuse.\
\
[G$ is the #1 ERC-777](https://dune.com/ilemi/erc-and-eip-starter-kit)[ token by tx in the world](https://dune.com/ilemi/erc-and-eip-starter-kit) (newer upgrade standard on traditional etc-20 standard) & one of the top 20 ERC-20 tokens in the world by transaction. \
\
G$ token address on Celo: [0x62B8B11039FcfE5aB0C56E502b1C372A3d2a9c7A](https://explorer.celo.org/mainnet/address/0x62B8B11039FcfE5aB0C56E502b1C372A3d2a9c7A) \
\
G$ token address on Fuse: [0x495d133B938596C9984d462F007B676bDc57eCEC ](https://explorer.fuse.io/address/0x495d133B938596C9984d462F007B676bDc57eCEC/transactions)\
\
G$ token address on Ethereum: [0x67C5870b4A41D4Ebef24d2456547A03F1f3e094B](https://etherscan.io/address/0x67C5870b4A41D4Ebef24d2456547A03F1f3e094B)

</details>

<details>

<summary>What is G$ token address?</summary>

G$ token address on Celo: [0x62B8B11039FcfE5aB0C56E502b1C372A3d2a9c7A](https://explorer.celo.org/mainnet/address/0x62B8B11039FcfE5aB0C56E502b1C372A3d2a9c7A) \
\
G$ token address on Fuse: [0x495d133B938596C9984d462F007B676bDc57eCEC ](https://explorer.fuse.io/address/0x495d133B938596C9984d462F007B676bDc57eCEC/transactions)\
\
G$ token address on Ethereum: [0x67C5870b4A41D4Ebef24d2456547A03F1f3e094B](https://etherscan.io/address/0x67C5870b4A41D4Ebef24d2456547A03F1f3e094B)

</details>

<details>

<summary>What is the GOOD token?</summary>

GOOD is the non-transferrable governance token that rules GoodDollar protocol and therefore its economics. It is distributed: 50% to claimers, 25% to Supporters and 25% to G$ stakers. GOOD token is used to vote in [GoodDAO governance proposals](https://discourse.gooddollar.org/). \
\
GOOD token address on Celo: [0xa9000Aa66903b5E26F88Fa8462739CdCF7956EA6](https://explorer.celo.org/mainnet/address/0xa9000Aa66903b5E26F88Fa8462739CdCF7956EA6) \
GOOD token address on Fuse: [0x603B8C0F110E037b51A381CBCacAbb8d6c6E4543](https://explorer.fuse.io/address/0x603B8C0F110E037b51A381CBCacAbb8d6c6E4543/transactions)[ ](https://explorer.fuse.io/address/0x495d133B938596C9984d462F007B676bDc57eCEC/transactions)\
GOOD token address on Ethereum: [0x603b8c0f110e037b51a381cbcacabb8d6c6e4543](https://etherscan.io/address/0x603b8c0f110e037b51a381cbcacabb8d6c6e4543)

</details>

<details>

<summary>What is the GOOD token address?</summary>

GOOD token address on Celo: [0xa9000Aa66903b5E26F88Fa8462739CdCF7956EA6](https://explorer.celo.org/mainnet/address/0xa9000Aa66903b5E26F88Fa8462739CdCF7956EA6) \
GOOD token address on Fuse: [0x603B8C0F110E037b51A381CBCacAbb8d6c6E4543](https://explorer.fuse.io/address/0x603B8C0F110E037b51A381CBCacAbb8d6c6E4543/transactions)[ ](https://explorer.fuse.io/address/0x495d133B938596C9984d462F007B676bDc57eCEC/transactions)\
GOOD token address on Ethereum: [0x603b8c0f110e037b51a381cbcacabb8d6c6e4543](https://etherscan.io/address/0x603b8c0f110e037b51a381cbcacabb8d6c6e4543)

</details>

<details>

<summary>What is the GoodDAO?</summary>

The GoodDAO is the governance protocol that governs the GoodDollar protocol, and empowers community members to take an active role in determining its future: shaping GoodDollar’s destiny as it seeks to create free money as a public good for all.

In the GoodDAO, all GoodDollar community members have the chance to play a more active role! All GoodDAO decisions are meant to maintain a protocol capable of generating, financing, sustaining and distributing a digital basic income in the form of the G$ token to claimers all over the world.

</details>

<details>

<summary>What networks does GoodDollar operate on?</summary>

The GoodDollar protocol is multi-chain by nature: all core protocol contracts related to the creation of G$ token occur on Ethereum mainnet, and all distribution of G$ tokens as UBI to end-users happens on L2s or side-chains, which make it practical and accessible for lower-income users. Currently, G$ is distributed as UBI on two [sidechains](/user-guides/frequently-asked-questions/web3-basic-knowledge-and-security-tips-by-consensys#what-are-sidechains), Celo and Fuse.

</details>

<details>

<summary>Can you explain how the UBI is distributed?</summary>

GoodDollar’s UBI distribution mechanism is based upon a daily distribution of G$ tokens to all verified members. G$ tokens are minted regularly in accordance to the [rules of the protocol](https://docs.gooddollar.org/). These tokens are then taken and divided between between contracts to be distributed as UBI, or allocated for other ecosystem need. The pool of G$ universal income is divided equally among all users who log in within a 24-hour period to make a claim. This mechanism encourages the flow of G$ to those who exhibit the greatest appetite for it. The enforced 24-hour gap between claims and the periodic requirement to re-validate identity creates a natural filtering method, referred to as “Proof of Need”.&#x20;

</details>

<details>

<summary>How does GoodDollar maintain the principle of one person, one UBI?</summary>

Sybil resistance is a term used in computer security and distributed systems to describe a system's ability to resist attacks from a single entity creating multiple fake identities, known as Sybil identities.&#x20;

GoodDollar’s sybil-resisitance solution is based upon each member verifying themselves and their associated EVM-wallet as an address associated with a unique, live member. This a crucial component that ensures the fair distribution of G$ while preventing individuals from registering multiple times.&#x20;

GoodDollar utilizes face verification and liveness testing through Facetec’s Zoom 3D technology. FaceTec is the first and only \*\*face authenticator certified to Level 1 & 2 in the the i Beta/NIST (More [here](https://www.facetec.com/))&#x20;

GoodDollar maintains an anonymized dataset of facemaps for all registrants, continuously striving to confirm the uniqueness of each newly submitted face against this repository. All this data is stored anonymously, without any linkage to the GoodDollar user profile, blockchain address, or internal records.

</details>

<details>

<summary>Where can I see statistics?</summary>

<https://dashboard.gooddollar.org>

</details>

<details>

<summary>Can I exchange G$ for other currencies?</summary>

Yes, you can exchange your G$ for other currencies on different DEXes on Celo and Fuse Network. \
\
You also have access to[ swap through GoodDapp](https://gooddapp.org/#/swap).&#x20;

</details>

<details>

<summary>Where can I buy, sell or swap G$?</summary>

To date, G$ is listed on Decentralized Exchanges (aka DEXes), where you can buy, sell, or swap your G$.

On Celo, you can exchange your G$ on [Uniswap](https://uniswap.org/), and on Fuse, on [Voltatge.finance](https://voltage.finance/home).

Exchanging on other DEXes is also possible but depends on the liquidity provided by DeFi users.

</details>

<details>

<summary>Where can I see more technical documentation?</summary>

In [GoodDollar’s docs ](https://docs.gooddollar.org/)and also on [GoodDollar’s Github repository](https://github.com/GoodDollar).&#x20;

</details>

<details>

<summary>What is the G$ token price?</summary>

G$ is a digital token that has a real price in USD. The live price of GoodDollar, circulating supply, and the value of can be found on the [GoodDollar dashboard](https://dashboard.gooddollar.org/).&#x20;

</details>

<details>

<summary>Are there a fixed number of G$?</summary>

GoodDollar is a fixed supply currency with the total number of G$ coins to be minted set at 2.2 trillion. All G$ are minted by the GoodDollar Reserve. You can check the current G$ supply  [here](https://dashboard.gooddollar.org).&#x20;

</details>

<details>

<summary>Can I stake my G$?</summary>

In the GoodDapp, you have the opportunity to [stake](https://gooddapp.org/#/stakes) your G$s on the Fuse Network. As a reward, you'll earn GOODs, the non-transferrable governance token of our GoodDAO.

Soon you will be able to stake your G$ to earn more G$!

</details>

<details>

<summary>How can I provide G$ liquidity?</summary>

If you are interested in learning more about GoodDollar liquidity, including how to provide liquidity, [please click here](https://docs.gooddollar.org/liquidity).&#x20;

</details>


# Using GoodDollar

<details>

<summary>How do I claim G$ UBI?</summary>

Open [GoodWallet](https://wallet.gooddollar.org) or [GoodDapp](https://gooddapp.org) and click on “Claim”! Your newly claimed G$ will appear in your wallet. A countdown will indicate the time remaining until your next opportunity to claim.

</details>

<details>

<summary>Why do I have to wait for my next claim?</summary>

The claiming window resets every day at 12pm UTC. After you claim, you'll need to wait until the same time the following day to claim again. A countdown will indicate the time remaining until your next opportunity to claim.

</details>

<details>

<summary>How many G$ do I get every day (24 hours)?</summary>

While G$ is distributed every day, there is no way of knowing in advance how much a GoodDollar claimer will receive on any given day when making the claim. The distribution process depends on a daily basis. Within each 24-hour cycle, a specific amount of G$ is earmarked for distribution as basic income. \
\
The amount of G$ distributed is determined by the average number of active users over the past 14 days (with the number of claimers potentially varying each day). This daily allocation is distributed evenly, ensuring each claimer receives an equal share. Any unclaimed G$ is then rolled over to augment the distribution pool for the following day.\
\
&#x20;<https://docs.gooddollar.org/protocol-v3-documentation/core-contracts-and-api/ubischeme>

</details>

<details>

<summary>What blockchains and networks does G$ operate on?</summary>

GoodDollar is deployed on Ethereum, Fuse and Celo.

Daily distribution happens on [sidechains](/user-guides/frequently-asked-questions/web3-basic-knowledge-and-security-tips-by-consensys#what-are-sidechains): Fuse and Celo.

</details>

<details>

<summary>How do I move my G$ across blockchains and networks? What bridges are integrated?</summary>

G$ is deployed on Ethereum, Fuse and Celo. To Tranfer G$ from one chain to another one you need to use a [bridge](/user-guides/frequently-asked-questions/web3-basic-knowledge-and-security-tips-by-consensys#what-is-a-bridge). In the [GoodWallet](https://wallet.gooddollar.org) you can find a bridge to move your funds from Fuse<>Celo.

</details>

<details>

<summary>How do I use my G$ in dApps?</summary>

The [G$ token](/user-guides/frequently-asked-questions/gooddollar-protocol-and-gusd-token#what-is-gusd-token) is a standard ERC-20 token that, to date, has been deployed on Ethereum, Fuse, and Celo Networks. You can use your G$ in different dApps within these ecosystems. You can find a list of dApps [here](/wallet-and-dapps/3rd-party-partners-and-integrations).

Remember that if you want to use G$ from one chain in another, you will need to [bridge](/user-guides/frequently-asked-questions/web3-basic-knowledge-and-security-tips-by-consensys#what-is-a-bridge) them.

</details>

<details>

<summary>How do I move my G$ to another wallet?</summary>

You can send G$ to wallets compatible with the Fuse and Celo Networks, depending on the chain you're sending G$ from. However, sending G$ to wallets incompatible with these networks will result in the loss of your funds. To ensure compatibility, consult the wallet documentation of the respective wallets.

Sending G$ from one GoodWallet address to another GoodWallet address is always compatible.

To send G$ to another wallet, you just need the wallet address to which you want to send money.

If you want to send G$ from your GoodWallet:

1. Make sure you are in the right Network where you want to send your G$. You can check and switch Network on the top left corner of your wallet.
2. Select “send” in the left side of the big button “Claim”.
3. Write the amount of G$ you want to send and select “send via address”
4. Write the Wallet Address (remember make sure is compatible with Fuse or Celo)
5. Follow the prompts and confirm your transaction.

</details>

<details>

<summary>Is G$ listed on exchanges?</summary>

G$ is available on [decentralized exchanges](/user-guides/frequently-asked-questions/web3-basic-knowledge-and-security-tips-by-consensys#what-is-a-dex) such as [Uniswap](https://uniswap.org) on Celo Network or [Voltage.Finance](https://voltage.finance) on Fuse.

</details>

<details>

<summary>Can I switch my GoodDollar registered account to a different blockchain address?</summary>

No, not at this time. Your GoodDollar registered account is linked to your proof of unique humanity, and is non-transferrable at this time.

</details>

<details>

<summary>How do transactions work in Web3?</summary>

Web3 transactions are a type of digital transaction that occur on the Ethereum blockchain. They are used to transfer Ether or other tokens between accounts, execute smart contracts, or interact with decentralized applications (dApps).

When a user initiates a transaction, they create a message that includes the recipient's address, the amount to be sent, and any additional data required for the transaction to be executed. This message is then signed with the user's private key and broadcasted to the Ethereum network.

Miners on the network then validate the transaction by checking that the sender has enough funds to complete the transaction and that the transaction meets all the requirements specified in the message. Once validated, the transaction is added to a block and the block is added to the blockchain. This process is known as mining.

Once the transaction is confirmed, the recipient's account balance is updated and the transaction is recorded on the blockchain, making it a permanent and immutable record of the transaction.

The cost of executing a transaction on the Ethereum network is determined by the gas price, which is a fee paid in Ether to compensate miners for processing the transaction. The gas price is set by the user and the higher the gas price, the quicker the transaction is likely to be processed.

In summary, Web3 transactions involve creating a message, validating the transaction, and adding it to the blockchain. The cost of executing the transaction is determined by the gas price paid by the user, and once confirmed, the transaction is a permanent and immutable record on the blockchain.

</details>


# GoodDollar Community

#### Where can I find my local GoodDollar Community?

The GoodDollar Community is a diverse vibrant network that spans across the globe, active in over 183 countries and territories, and communicating in more than 17 languages. You can find your local community on the [community page](https://community.gooddollar.org).&#x20;

#### What is a GoodDollar Ambassador?

GoodDollar Ambassadors are the unsung heroes of the GoodDollar Community, volunteers who have stepped forward to be driving behind our outreach efforts. Mee the GoodDollar Ambassadors in our [community page](https://community.gooddollar.org).

#### I'm a developer. Help?

Check out our [technical documentation](https://docs.gooddollar.org/) and GoodDollar’s [Github](https://github.com/GoodDollar/).&#x20;


# Troubleshooting

<details>

<summary>Passing face-verification</summary>

To claim free G$’s, you’ll need to go through a short Face Verification (FV) process to verify that you are a unique and live user. This is to prevent duplicate accounts and misuse of the system.

Here are some tips to successfully complete the face verification so you can access your GoodDollar wallet. That’s where the fun begins.

* The face verification has strong requirements for image quality (e.g. image detail and color balance). Make sure your selfie is high-resolution (check your camera settings), not blurry, and has lots of light.
* If you face issues, try using another browser. Face Verification works best on your phone's native browser, so Chrome for Android and Safari for iOS.<br>

If you get the error message that your image “won't pass liveness check,” try these tricks:

* Adjust the lights in the room you're passing FV. Your face shouldn't be overexposed or too dark, having pixel artifacts.
* Clean your webcam lens using the special lens cleaning wipes (for digital cams) or LCD display cleaning wipes or at least with a soft cloth and isopropyl alcohol.
* Adjust your webcam settings. Make sure you are using the highest resolution setting possible.
* Check your webcam connection. Some webcam models require a USB 3.0 or type C connection to provide the maximum resolution
* Try using another webcam with a higher resolution (more megapixels) to pass the face verification step. You can also try using a smart phone camera (yours or a friends) to complete the step.&#x20;

</details>

<details>

<summary>Can I change account Login Method for GoodWallet?</summary>

No, you can’t change your login method for GoodWallet. However, you can delete your wallet account and create a new one. Just make sure to transfer your G$ to another wallet before deleting the old wallet account so you don’t lose them.

If you need to do it, follow these steps:

1. Create a new wallet account using a different log-in method.
2. Do not click "claim" on the new account to avoid passing the Face Verification process. This wallet can still receive funds.
3. Go to your profile in the new account and copy your new wallet address.
4. Log out of your new wallet account.
5. Log in to your old wallet account and send your G$ to your new wallet address.
6. If you wish to continue claiming from the new wallet you should follow [this guide](/user-guides/connect-another-wallet-address-to-identity) to connect your identity to the new wallet.
7. After you’ve confirmed the funds were sent successfully, go to the menu, select "Settings," and choose "Delete Account." Follow the prompts to confirm.
8. You will get a message that your account is being deleted. **Notice**: to claim from the new wallet you will need to either wait until the specified expiration date or follow the guide in step 6.
9. You now have a new wallet account where you can claim everyday!

Please note that while doing this process, you will have to wait 24 hours, so you will miss a claim for one day.

</details>

<details>

<summary>Help! It says "I have a Twin"</summary>

If you're seeing this message, it's likely because you've created multiple **GoodWallet** accounts or previously verified your identity through another app / wallet. Try to remember which sign-up method you originally used to create your account.

#### **What You Can Do:**

1. **Recover Your Verified Account**
   * Try logging in with different sign-in options: **Gmail, Facebook, or passwordless (mobile).**
2. **Use Your Already Verified Wallet**
   * If you’ve verified your identity before, continue using your existing wallet.
3. **Link Additional Wallet Addresses**
   * You can connect more wallet addresses to your verified identity by following [this guide](/user-guides/connect-another-wallet-address-to-identity).
4. **Wait for Verification Expiry**
   * If you prefer to verify with a new wallet, wait until the expiration period passes before attempting verification again.

</details>

<details>

<summary>Help! It says I'm under 18</summary>

If you are seeing this message, it is likely because the face verification algorithm has estimated your age as under 18.

If you think this is a mistake please email us at <contact@gooddollar.org>.\
In your email provide your wallet address and an official identity document.

</details>

<details>

<summary>Lost access to my GoodDollar wallet</summary>

If you lose access to your account entirely, you can still access and claim from GoodDapp if you have exported your G$ wallet or possess the [private key required for exporting your G$ wallet](broken://pages/q0oOIBacGnaNMINxmVxd#where-can-i-find-my-private-key).

</details>

<details>

<summary>Delete  my wallet account</summary>

To delete your wallet account, follow these steps:

1. Open your GoodWallet and click on the menu icon located at the top right corner.
2. Select “Settings” from the menu.
3. Tap on “Delete Account” at the bottom of your screen.
4. Confirm by tapping the red “Delete” button.

Before deleting your wallet account, ensure you've transferred your funds to another wallet to prevent loss.

After deleting your account, you may opt to open a new one. However, you will not be able to claim until the specified expiration date or by connecting your identity to the new wallet by following [this guide](/user-guides/connect-another-wallet-address-to-identity)

</details>

<details>

<summary>I have not received my rewards from inviting a friend</summary>

To check your invitee status, go to the Rewards section of your GoodWallet, located on the bottom left sidebar.

If your invitee is labeled as "Pending," it indicates that they have not yet made their first claim. Once they do, you'll receive your reward.

If you do not see your invitee listed, it means they haven't utilized your invite link or input your invite code during account creation. In such instances, kindly resend your link to your invitee and request them to navigate to their Referral screen, where they can paste your code into the designated field labeled "Use Invite Code”

</details>

{% hint style="info" %}
Need help? Please explore the [Wallet and Product sections](broken://pages/9p1GBt0VeiOY3UgiYZOB), as well as our [Frequently Asked Questions](/user-guides/frequently-asked-questions). If you still need assistance, feel free to contact our [community support group](https://t.me/+jay3UR6_rEwxNjY0).
{% endhint %}


# Useful Links


# Liquidity

How can you become a GoodDollar liquidity provider?

{% hint style="warning" %}
**Notice of Potential Information Variability**

As of December 21, 2023, the information in GoodDocs may not reflect the most current updates. The team is diligently working to review and revise the documentation to ensure accuracy. Please check back at a later date for the most up-to-date information.
{% endhint %}

Providing liquidity to the GoodDollar ecosystem and participating as a G$ liquidity provider is a great way to support the [GoodDollar ecosystem and the mission to let money flow to where it is needed most](https://whitepaper.gooddollar.org). [G$ token](https://docs.gooddollar.org/tokenomics) is a reserve-backed ERC20 token deployed on three different networks: Ethereum, Celo and Fuse. It is designed to maintain a level of [price](https://dashboard.gooddollar.org/) stability that is "stable enough” to encourage circulation and usage of G$ tokens for payments. It is fully liquid, providing seamless exchangeability through the GoodDollar Reserve, which effectively serves as the primary market maker on the Ethereum Network. Most importantly, new G$ are only issued as new funds are added to the GoodDollar Reserve according to a price curve modified by the Bancor formula, ensuring a transparent and predictable view into the protocol’s token supply. \
\
GoodDollar liquidity on side-chains ([Celo](#provide-liquidity-on-celo) and [Fuse](#provide-liquidity-on-fuse)) is facilitated through decentralized exchanges (DEXes), which also facilitate G$ liquidity to other tokens. This enables users to cash out into various forms, including other currencies, fiat, mobile money, or airtime as needed. Liquidity providers play a critical role in the GoodDollar ecosystem through supporting G$ liquidity on side-chains, which is where the members seek to cash-in, cash-out, or conduct all other “real money” functions.\
\
Contributing to G$ liquidity not only results in earning fees for each pool trade but also plays a vital role in fortifying the GoodDollar economy and network for hundreds of thousands of individuals worldwide. This support reaches UBI claimers, community members, and ambassadors who utilize their G$ to convert into various crypto assets and currencies, promoting the development of a more robust ecosystem.

### Liquidity on Ethereum

{% hint style="info" %}
G$ Token address on Ethereum: [0x67C5870b4A41D4Ebef24d2456547A03F1f3e094B](https://etherscan.io/address/0x67C5870b4A41D4Ebef24d2456547A03F1f3e094B)
{% endhint %}

The [GoodDollar Reserve](https://docs.gooddollar.org/protocol-v3-documentation/core-contracts-and-api/goodreservecdai) serves as both the liquidity pool and Automatic Market Maker (AMM) for G$, facilitating buying and selling. The GoodDollar Reserve is a smart contract overlaid on the Ethereum network that is governed by a modified version of the Bancor Formula. The formula stipulates that the price of the G$ token moves in proportion to the aggregated value in the reserve (i.e. the pool of liquidity that supports G$) and in inverse proportion to the circulating total supply. Its rate of leverage is managed according to the reserve ratio, the current Reserve Ratio is 55.39% and declining 15% per year. \
\
The GoodDollar Reserve functions as the principal market maker. For tracking the G$ price from the GoodDollar Reserve, navigate to the GoodDollar [Dashboard](https://dashboard.gooddollar.org/).

{% hint style="info" %}
**Contracts:**

[**GoodDollarReserveCDAI**](https://docs.gooddollar.org/protocol-v3-documentation/previous-protocol-versions/protocol-v2/core-contracts-and-api/goodreservecdai) The contracts acts as the GoodDollar liquidity pool and AMM (Automatic Market Maker) and enables methods to buy and sell G$s. It aslo mints G$. \
[**0xa150a825d425B36329D8294eeF8bD0fE68f8F6E0**](https://etherscan.io/address/0xa150a825d425B36329D8294eeF8bD0fE68f8F6E0)

[**GoodMarketMaker**](https://docs.gooddollar.org/protocol-v3-documentation/previous-protocol-versions/protocol-v2/core-contracts-and-api/goodmarketmaker) Helper contract for the GoodReserveCDai. It serves ad a dynamic reserve ratio market maker. [**0xDAC6A0c973Ba7cF3526dE456aFfA43AB421f659F**](https://etherscan.io/address/0xDAC6A0c973Ba7cF3526dE456aFfA43AB421f659F)
{% endhint %}

To interact with the GoodDollar Reserve contracts for buying and selling G$, check out this [guide](https://docs.gooddollar.org/user-guides/buy-and-sell-gusd).

To interact with the GoodDollar Reserve UI, visit <https://gooddapp.org/#/swap> (ensure you are on the Ethereum network). When using GoodDapp on the Ethereum blockchain, you are interfacing with the core protocol contracts and accessing the primary G$ market.

<figure><img src="/files/rS4tLMRqHK0qXydWtM6z" alt=""><figcaption><p><a href="https://gooddapp.org/#/swap ">https://gooddapp.org/#/swap </a></p></figcaption></figure>

**Note:** New liquidity pools on DExes on Ethereum can be opened permissionlessly!

### Provide liquidity on Celo

{% hint style="info" %}
G$ Token Address on Celo: [0x62B8B11039FcfE5aB0C56E502b1C372A3d2a9c7A](https://explorer.celo.org/mainnet/address/0x62B8B11039FcfE5aB0C56E502b1C372A3d2a9c7A)
{% endhint %}

#### DEXes and Pools

| DEX     | Pool Pair                                                                                     | Contract                                                                                                                           |
| ------- | --------------------------------------------------------------------------------------------- | ---------------------------------------------------------------------------------------------------------------------------------- |
| Uniswap | [G$/cUSD](https://info.uniswap.org/#/celo/pools/0x9491d57c5687ab75726423b55ac2d87d1cda2c3f)   | [0x9491d57c5687AB75726423B55AC2d87D1cDa2c3F](https://celoscan.io//address/0x9491d57c5687ab75726423b55ac2d87d1cda2c3f)              |
| Uniswap | [USDGLO/G$](https://info.uniswap.org/#/celo/pools/0x0dbb0769b00d01d241ba4f7b2891fb5c2a975d51) | [0x0DBb0769B00d01d241BA4F7B2891fB5C2A975D51](https://celoscan.io//address/0x0dbb0769b00d01d241ba4f7b2891fb5c2a975d51)              |
| Uniswap | [Celo/G$](https://info.uniswap.org/#/celo/pools/0xcb037f27eb3952222810966e28e0ceb650c65cd9)   | [0xCB037f27eB3952222810966e28E0cEB650c65CD9](https://celoscan.io//address/0xcb037f27eb3952222810966e28e0ceb650c65cd9)              |
| Uniswap | [PACT/G$](https://info.uniswap.org/#/celo/pools/0xf6ba006abf768ab2d1b5bba2d22d9f13eb1269d4)   | [0xF6Ba006aBf768AB2d1B5bbA2D22d9F13EB1269d4](https://celoscan.io//address/0xf6ba006abf768ab2d1b5bba2d22d9f13eb1269d4)              |
| Ubeswap | [Celo/G$](https://info.ubeswap.org/pair/0x25878951ae130014e827e6f54fd3b4cca057a7e8)           | [0x25878951ae130014e827e6f54fd3b4cca057a7e8](https://explorer.celo.org/mainnet/address/0x25878951ae130014E827e6f54fd3B4CCa057a7e8) |

**Note:** New liquidity pools on DExes on Celo can be opened permissionlessly!

#### Other ways to get G$ on Celo

* Purchase G$ from the GoodDollar Reserve on Ethereum and bridge to Celo via smart contracts. Check the information and guides [here](https://docs.gooddollar.org/user-guides/bridge-gooddollars).
* Purchase G$ on Celo from any chain and supported token via [Squid](https://app.squidrouter.com/).
* Purchase G$ on Celo with your credit card (coming soon!).

### Provide Liquidity on Fuse

{% hint style="info" %}
G$ Token address on Fuse: [0x495d133B938596C9984d462F007B676bDc57eCEC](https://explorer.fuse.io/address/0x495d133B938596C9984d462F007B676bDc57eCEC/transactions)
{% endhint %}

| DEX              | Pool Pair                                                                                                                                     | Contract                                                                                                                 |
| ---------------- | --------------------------------------------------------------------------------------------------------------------------------------------- | ------------------------------------------------------------------------------------------------------------------------ |
| Voltatge.finance | [G$/WFuse](https://app.voltage.finance/index.html#/add/0x0be9e53fd7edac9f859882afdda116645287c629/0x495d133b938596c9984d462f007b676bdc57ecec) | [0xa02ed9fe9e3351fe2cd1f588b23973c1542dcbc](https://explorer.fuse.io/address/0xa02ed9fe9e3351fe2cd1f588b23973c1542dcbcc) |

Note: New liquidity pools on DExes on Fuse can be opened permissionlessly!

#### Other ways to get G$ on Fuse

* Purchase G$ from the GoodDollar Reserve on Ethereum and bridge via smart contracts. Check the information and guides [here](https://docs.gooddollar.org/user-guides/bridge-gooddollars).
* Purchase G$ from the GoodDollar Reserve on Ethereum and bridge via [Fuse Bridge](https://app.voltage.finance/index.html#/bridge).

### Provide liquidity on XDC

{% hint style="info" %}
G$ Token Address on XDC: [0xEC2136843a983885AebF2feB3931F73A8eBEe50c](https://xdcscan.com/address/0xec2136843a983885aebf2feb3931f73a8ebee50c)
{% endhint %}

#### DEXes and Pools

| DEX     | Pool Pair                                                                                                                              | Contract                                                                                                             |
| ------- | -------------------------------------------------------------------------------------------------------------------------------------- | -------------------------------------------------------------------------------------------------------------------- |
| Uniswap | [G$/USDC](https://app.xspswap.finance/#/add/0xfA2958CB79b0491CC627c1557F441eF849Ca8eb1/0xEC2136843a983885AebF2feB3931F73A8eBEe50c/500) | [0xe8c6E330B16242792c0E79635581D0b2fd031AD5](https://xdcscan.com/address/0xe8c6E330B16242792c0E79635581D0b2fd031AD5) |

**Note:** New liquidity pools on DExes on Celo can be opened permissionlessly!

{% hint style="danger" %}
**Disclaimer:** This is not financial advice. Please Do Your Own Research (DYOR) before making a decision.
{% endhint %}


# New GoodWallet

<details>

<summary>What is the New GoodWallet &#x26; what are the key features?</summary>

The New GoodWallet is mobile-friendly, simple non-custodial multi-chain wallet interface. It facilitates G$ claiming, G$ onboarding, WalletConnect, as well as sending, receiving and exchanging thousands of cryptocurrencies on several blockchain networks, including but not limited to Ethereum, Polygon, Optimism, Base, BNB, Celo and Fuse.

</details>

<details>

<summary>How do I login to the new GoodWallet?</summary>

If you are new to GoodWallet, simply pick an authentication provider (Google is recommended) and type in your credentials. If you’ve been using GoodWallet before, see below.

</details>

<details>

<summary>Do existing GoodWallet users have access to the same wallet address in the New GoodWallet?</summary>

Yes! When logging in with the same authentication provider (Google, Facebook or SMS ) and credentials (email, user or phone number) as used in GoodWallet you will get access to your existing holdings and can seamlessly enjoy the new features provided by the New GoodWallet.

</details>

<details>

<summary>What chains and tokens are supported in the new GoodWallet?</summary>

Thousands of tokens across Ethereum, Polygon, Optimism, Base, BNB, Celo and Fuse. The specific Tokens and networks supported, can be seen in the “To” field of the “Exchange” application.\
\
In case You received a unsupported token, You can gain access to it by exporting Your private key (See “Where can I find my Private Key?”) and importing it to e.g. [MetaMask](https://support.metamask.io/managing-my-wallet/accounts-and-addresses/how-to-import-an-account/#importing-using-a-private-key);

</details>

<details>

<summary>Where can I find my public Key?</summary>

The public key (wallet address) can be found in the main page’s Profile Card, the “Receive” page as well as from the options page accessible via the upper left cog on the main page.

</details>

<details>

<summary>Where can I find my private Key?</summary>

The private key can be exported from the options page accessible by the upper left cog on the main page. Beware that exporting the private Key can lead to loss of funds if not handled securely. Learn more about web3 and security tips [here](https://docs.gooddollar.org/frequently-asked-questions/web3-basic-knowledge-and-security-tips-by-consensys).&#x20;

</details>

<details>

<summary>How do I claim G$ UBI?</summary>

By accessing the “Claim” application on the mainpage. Claiming GoodDollars requires the user to verify uniqueness and liveness through Face Verification. This check will occasionally need to be redone. More information about GoodDollar and this process can be found [here](https://docs.gooddollar.org/frequently-asked-questions).&#x20;

</details>

<details>

<summary>What about gas?</summary>

All blockchain transactions [require gas](https://docs.gooddollar.org/frequently-asked-questions/web3-basic-knowledge-and-security-tips-by-consensys). Gas is typically paid with the network in question’s native token and it’s the users responsibility to ensure sufficient gas is available for sending and exchanging tokens.

GoodDollar’s faucet provides the user with just sufficient gas on Celo and Fuse to claim G$ daily, meaning that sending and exchanging token may not necessarily be possible until the user have accrued sufficient gas by other means. It also means that if the user chooses to spend the GoodDollar sponsored gas on sending or exchanging tokens, the user will not necessarily have enough gas to perform the UBI claims for up to a few days.

</details>

<details>

<summary>How can I connect my wallet to other dapps?</summary>

Via the “[Wallet Connect](https://learn.bybit.com/crypto/how-to-use-walletconnect/)” application accessible from the main page. Requests from the dapp will popup to be rejected or approved in the wallet.

</details>

<details>

<summary>How do I bridge G$ from Fuse to Celo, or vice versa?</summary>

By connecting to [GoodDapp](https://gooddapp.org/#/microbridge) via WalletConnect and go to [Microbridge](https://gooddapp.org/#/microbridge).

</details>

<details>

<summary>How do users send cryptocurrencies in the New GoodWallet?</summary>

By using the “send” function on the mainpage. Beware that only direct transfers are currently supported by the New GoodWallet, meaning that the public address or ENS name, of the recipient are required.

</details>

<details>

<summary>How do users receive cryptocurrencies in the New GoodWallet?</summary>

By supplying the sender with your public Key (wallet address)

</details>

<details>

<summary>How do users exchange cryptocurrencies in the New GoodWallet?</summary>

By accessing the “Exchange” function from the main page. Exchange covers both Bridging & Swapping using [Li.Fi](http://li.fi/). Beware exchanging tokens across different networks may take several minutes to execute and complex transactions may require splitting it up into multiple transactions.

</details>

<details>

<summary>Can users invite friend to the New GoodWallet?</summary>

Users can share the [New GoodWallet](https://goodwallet.xyz/en) link to friends. However there is not yet Invite Rewards in the new wallet, and sharing the New GoodWallet link will not earn any rewards.

</details>

{% hint style="info" %}
Need help? Please explore the [Wallet and Product sections](https://docs.gooddollar.org/wallet-and-products), as well as our [Frequently Asked Questions](https://docs.gooddollar.org/frequently-asked-questions). If you still need assistance, feel free to contact our [community support group](https://t.me/+jay3UR6_rEwxNjY0).
{% endhint %}


# GoodDapp

#### What is GoodDapp?

GoodDapp offers tools and features for any EVM-compliant wallet to interact with the GoodDollar protocol.

GoodDapp is a dApp (decentralized application) interface that supports interacting with the GoodDollar protocol, including its core protocol Ethereum contracts. Key features include interacting with the GoodReserve on Ethereum, staking of G$ to access bonus G$ and GOOD rewards, and stake stablecoins in 3rd party protocols to support the issuance of G$. Also claim G$ through connecting their GoodDollar Verified Address to GoodDapp.

#### How can I stake for GOOD governance tokens on GoodDapp?

You can stake your G$ for [GOOD tokens](/user-guides/frequently-asked-questions/gooddollar-protocol-and-gusd-token#what-is-the-good-token) (GoodDollar governance token) on the '[Stake' tab of GoodDapp](https://gooddapp.org/#/stakes) within the GoodDAO staking platform. Currently, the option to stake your G$ is only available on the Fuse Network.

You can use your GOOD tokens to [vote on GoodDAO elections](https://snapshot.org/#/thegooddao.eth).

#### How can I swap G$ tokens on GoodDapp?

You can swap your [G$ tokens ](/user-guides/frequently-asked-questions/gooddollar-protocol-and-gusd-token#what-is-gusd-token)on Fuse and Celo for other assets on the [Swap tab of GoodDapp](https://gooddapp.org/#/swap). The swap on this page happens through decentralized exchanges ([DEXs](/user-guides/frequently-asked-questions/web3-basic-knowledge-and-security-tips-by-consensys#what-is-a-dex)). When you swap, your funds are sent directly to the DEX service (Voltage on Fuse Network or Uniswap on Celo Network).&#x20;


# GoodCollective

<details>

<summary>What is GoodCollective</summary>

[GoodCollective](https://goodcollective.xyz/) is a platform that supports direct digital payments to individuals who fit specific criteria. Individuals access these funds by participating in payment pools (also referred to as Collectives). They may qualify for pools based on who they are and where they live, or be added via a partner organization who has created a pool on their behalf. [Learn more about the types of pools and how to access them here. ](https://www.gooddollar.org/goodcollective-how-it-work)

</details>

<details>

<summary>How do GoodCollective climate stewards get paid for climate action using results-based financing?</summary>

GoodCollective stewards get paid every time they take a measurement or make a claim through a partner's platform that is verified by that partners methodology. Technically, comma, this happens when an NFT is meant to confirm the verification of their activity, which triggers a payment in a smart contract, which has specific parameters about how much each steward is compensated per activity that are set for that specific good collective and the context of the measurement.

</details>

<details>

<summary>Why would I want to start a GoodCollective?</summary>

If your company or community works with individuals who would benefit from a supplemental income stream to support their climate positive activities, GoodCollective can help.\
\
If you are interested in running a Collective[ fill in this form](https://gooddollar.typeform.com/creategood?typeform-source=www.gooddollar.org).

</details>

<details>

<summary>Who can start a GoodCollective?</summary>

Anyone! There are 3 different types of GoodCollectives that can be started. [Visit GoodCollective How it Works page](https://www.gooddollar.org/goodcollective-how-it-work) to find the GoodCollective type that works for you and your organization.&#x20;

</details>

<details>

<summary>How do I donate to GoodCollective</summary>

Easy! You visit the [GoodCollective dApp](https://goodcollective.xyz/), connect your wallet, find a collective you want to fund and donate! You can either provide a one-time donation or a recurrent (streaming) donation.\
\
Don’t have a crypto wallet? [Here’s how to get started.](https://courses.consensys.net/courses/what-is-a-crypto-wallet)

</details>

<details>

<summary>Can I only donate in GoodDollar</summary>

Donations can be made using a variety of cryptocurrencies available on the Celo blockchain.

</details>

<details>

<summary>What is GoodDollar?</summary>

GoodDollar is a permissionless protocol that creates and distributes free universal basic income (UBI) as a public good governed by its members. By leveraging blockchain technology, the mission of GoodDollar is to advance decentralized financial education, promote financial inclusion, and empower communities. GoodDollar strives to establish a global landscape where every individual has access to inclusive, basic economic assets and financial products. Launched in 2020, GoodDollar has emerged as the world's largest global UBI community, with over 540,000 members across 181 countries. GoodDollar has been widely recognized as one of the leading projects fostering financial inclusion, acknowledged by prominent institutions such as the World Economic Forum, Milken Institute, and the Crypto Council for Innovation

</details>

<details>

<summary>What are the fees associated with starting or funding a GoodCollective</summary>

Starting a collective / setting up your own pool is free. A 5% network fee is charged for each donation made. The network fee goes directly to fund the [GoodDollar UBI pool.](https://celoscan.io/address/0x43d72Ff17701B2DA814620735C39C620Ce0ea4A1) Pool administrators may also configure their Collective to collect a per-donation administrative fee.

</details>


# 3rd Party Partners and Integrations

<details>

<summary>HaloFi</summary>

<https://docs.halofi.me/faq>

</details>

<details>

<summary>Masa Finance</summary>

* Email: <support@masa.finance>
* Discord: [https:/](https://www.google.com/url?q=https://discord.com/invite/HyHGaKhaKs\&sa=D\&source=editors\&ust=1709588727337580\&usg=AOvVaw36qI-ebHf8N7QlAn4WvzTS)[discord.gg/masafinance](https://www.google.com/url?q=https://t.co/3jsTLxWrvi\&sa=D\&source=editors\&ust=1709588727337687\&usg=AOvVaw3ZlNpDLKUDnd2SCB8UqkLZ)
* Telegram:<https://t.me/masafinance>

</details>

<details>

<summary>Fonbnk</summary>

<https://fonbnk.zendesk.com/hc/en-us>

</details>

<details>

<summary>Opera MiniPay Wallet</summary>

[https://www.opera.com/es/products/minipay\
\
https://blogs.opera.com/africa/2023/09/minipay-frequently-asked-questions/](<https://www.opera.com/es/products/minipay&#xA;&#xA;https://blogs.opera.com/africa/2023/09/minipay-frequently-asked-questions/>)

</details>

<details>

<summary>Uniswap</summary>

<https://uniswap.org/faq>

</details>

<details>

<summary>Valora Wallet</summary>

<https://support.valoraapp.com/hc/en-us>

</details>

<details>

<summary>XSwap</summary>

<https://docs.xspswap.finance/xswap-protocol/>

</details>


# GoodID & GoodOffers

<details>

<summary>What is GoodID?</summary>

*GoodID is currently in its pilot stage, and therefore has limited functionality.*

GoodID is a decentralized identification solution (DID). This means that you own your data and credentials, and decide who can “write” new data and credentials, as well as who can “read” your data and credentials. We built GoodID to allow partners an easy access to GoodDollar's community and to distribute campaigns, funds, and other opportunities to members of the GoodDollar protocol.

</details>

<details>

<summary>What is GoodOffers?</summary>

GoodOffers are opportunities to earn additional income, available to you based on your GoodID information. Note that you will only see GoodOffers if you said “Yes, I accept” to the screen “You might qualify for extra money disbursements.”

</details>

<details>

<summary>What happens if I’ve disputed part of my GoodID?</summary>

Information you've marked as incorrect will show as "Unverified" on your GoodID.

</details>

<details>

<summary>Can I accept an offer I’ve skipped in the past?</summary>

When you skip an offer, you can choose to see that offer again. It will show up next time you claim. If you chose to not be shown the offer again, you will need to delete and then redo your Face ID / GoodID upgrade to see the offer again.

</details>

<details>

<summary>Why don’t I see all my GoodID information on my device?</summary>

You will only see all GoodID upgrade info on the device you used to make the upgrade.

If you want to use another device or dapp, you can upgrade again on that device. For GoodDapp, this can be done by visiting <https://gooddapp.org/> > GoodID, connecting your wallet and pressing "upgrade.”

</details>

<details>

<summary>How are my age and gender determined?</summary>

We use [Amazon Rekognition ](https://docs.aws.amazon.com/rekognition/latest/APIReference/API_Gender.html)to predict your age and gender.

</details>

<details>

<summary>How do you know my location?</summary>

There are two different ways that we determine location:

* Using your IP address (the location through which you are accessing the internet).
* (If you sign into GoodWallet via your mobile number) the country code of your phone number.

</details>

<details>

<summary>Why does my location show as Unverified?</summary>

There are a few reasons your location may show as Unverified:

* You did not grant device permissions. Sometimes, to enable location, you need to adjust your phone settings. Please check your device to learn how to enable location permissions for the browser or app version you are using
* You are using a VPN
* Due to another error, for example if we could not match your location with a country

If you would like your location to show in the future, please resolve the issue above and delete then redo your FaceID / GoodID upgrade by using another device or deleting your device or browser’s local storage.

</details>

<details>

<summary>Why are you collecting my video?</summary>

Red Tent’s offers are the first (pilot) offers utilizing GoodID and GoodOffers. As such, we are collecting some information for this short pilot period for the purpose of internal learning & refinement.

Your video may be reviewed by the GoodLabs or partner teams for verification purposes. Your video will not be shared or used publicly, and will be erased after a period of time.

</details>


# Contributing to GoodDollar

Everyone is welcome — developers, designers, writers, founders, students, and hobbyists alike. Whatever your background, there's a path to contribute that fits your skills and availability.

GoodDollar is a nonprofit, open-source protocol building Universal Basic Income (UBI) on-chain through the G$ token. We maintain smart contracts, SDKs, and dApps that make it easy for anyone  to integrate G$ into real-world products.

**Useful links**

* Docs: <https://docs.gooddollar.org>
* Website: <https://gooddollar.org>
* GitHub: <https://github.com/GoodDollar>

***

### Ways to Contribute

#### 1. Build a Project with G$

The **GoodBuilders Program** supports teams building on GoodDollar with mentorship and funding.

* Apply: <https://ubi.gd/goodbuilders>
* Community Telegram: <https://ubi.gd/GoodBuildersTG>

#### 2. Solve/Review a Bounty&#x20;

Bounties are how most open source contributors get involved. There are four roles in the pipeline:

**Contributor** — the AI opens a PR with a first-pass solution. You take it from there: review the AI's code, fix what's wrong, fill gaps, and get it to a standard worth reviewing by a human.

**Reviewer** — a human reviewer checks the Contributor's corrected version. You validate correctness, catch anything still missed, and approve it for QA.

**QA** — test the actual behavior of the changes in a real environment. You confirm the fix works end-to-end and file structured bug reports for anything that doesn't pass.

**Maintainer** — final sign-off before merge and payout approval.

{% hint style="info" %}
[Browse Open Bounties Github Board](https://github.com/orgs/GoodDollar/projects/5). \
Issues are labeled `gd-bounty-<tier>` (e.g. `gd-bounty-basic`)
{% endhint %}

> A single person can hold both Reviewer and QA roles on the same bounty. See \[Open Source Contributors] for the full role guide and how to progress.

* We follow the [GitHub contribution guidelines](https://guides.github.com/introduction/flow/) — everything below builds on top of that.

{% hint style="info" %}
Learn the [growth path for Gooddollar Open Source Contributors](/for-developers/contributing/open-source-contributors/contributor-growth-path)&#x20;
{% endhint %}

#### 3. Propose Your Own Idea

Have something in mind? Propose it through the Gardens Pool for Open Source Contributors.

* Forum: <https://forum.gooddollar.org>

***

### Summary of how a Bounty Works

Each bounty follows this flow. [Learn more](/for-developers/contributing/open-source-contributors#every-bounty-follows-the-same-path)

```
Bounty posted → AI opens PR → Contributor fixes AI code → Reviewer checks → QA tests → Maintainer sign-off → Merge & payout
```

{% hint style="info" %}
&#x20;New here?&#x20;

Start with  [Open Source Contributors ](/for-developers/contributing/open-source-contributors/contributor-growth-path)to find the right role for you, then head over to the [Bounty Tiers](/for-developers/contributing/open-source-contributors/payments-for-reviews-contributors-and-qa) to understand scope and rewards
{% endhint %}

***

### Repositories

* <https://github.com/GoodDollar/GoodProtocolUI>
* <https://github.com/GoodDollar/GoodSdks>
* <https://github.com/GoodDollar/GoodCollective>
* <https://github.com/GoodDollar/GoodWeb3-Mono>

***

### Need Help?

* Bounty questions: Builders Telegram → <https://ubi.gd/GoodBuildersTG>
* General questions: Comment directly on the GitHub issue or PR

***

**Your contributions, large or small, help advance GoodDollar's mission to reduce wealth inequality through open, decentralized tools.**

Thank you for your interest building with us, and welcome to **GoodDollar**!


# Open Source Contributors

Human contributors review, test, fix and validate AI-generated bounty pull requests before merge and payout.

Human contributors and reviewers turn AI-generated bounty PRs into production-ready changes. You do not need to write the first draft. You need to own the final quality. \
How the Workflow is structured:

#### Every bounty follows the same path:

```
Bounty posted → AI opens PR → Contributor fixes AI code → Reviewer checks → QA tests → Maintainer sign-off → Merge & payout
```

| Stage               | Who                   | Responsibility                                                  |
| ------------------- | --------------------- | --------------------------------------------------------------- |
| AI solution         | AI                    | Opens the initial PR                                            |
| Contribution        | Contributor           | Takes the AI's code, fixes issues, and gets it ready for review |
| Review              | Reviewer              | Validates logic, correctness, and codebase fit                  |
| QA                  | QA contributor        | Tests real behavior and files structured bug reports            |
| Maintainer sign-off | GoodDollar maintainer | Approves the final merge                                        |

{% hint style="info" %}
For Basic and Common bounties, one person often handles both review and QA. For Rare and higher tiers, these roles are usually split.
{% endhint %}

***

### The Roles

#### Contributor

You take the AI-generated PR and make it production-ready. You run the branch locally, validate the implementation against the issue requirements, and fix anything blocking approval — not just comment on it.

Typical checks include: logic and correctness, security and edge cases, tests, style, and codebase consistency.

→ [Read the full Contributor  guide](/for-developers/contributing/open-source-contributors/contributor-role)

#### Reviewer

You review the Contributor's corrected version. You validate that the fixes are sound, nothing was missed, and the PR is ready for QA.

#### Becoming a  Reviewer

* Have prior code review or open-source experience
* Message the [`GoodBounties`](https://t.me/gooddollarbounties/4115) Telegram group to request access
* Share links to past open-source work and your weekly availability

Use this template to request access:

```
Hi everyone! I'd like to join the Contributor + Reviewer pool.

Name:
Previous open-source contributions:
Availability (hours/week):
```

Access is granted manually within 24–48 hours. Once approved, you are added to the pool and can receive assignments. Reviewers are expected to respond within 48 hours to requests, changes, and follow-ups.

> Your first review is evaluated by a maintainer before payout is approved. This is a one-time check — after that, accepted work follows the normal flow.

→ [Read the full Code Review guide](/for-developers/contributing/open-source-contributors/human-reviewer-role)

#### QA Contributor

You test the approved changes in a real environment. You document what you tested, what passed, and what failed. If you find bugs, you file structured reports with evidence.

Typical checks include: acceptance criteria from the issue, runtime behavior and regressions, UI behavior on real devices or browsers.

### Join as a QA Contributor

* Pick up an open QA bounty&#x20;
* Test the PR in a local or preview environment
* Submit a structured QA report as a comment on the PR

Once approved, you join the contributor pool for QA assignments. Assignments can be delegated to another approved contributor when needed.

→[ Read the full QA Process guide](/for-developers/contributing/open-source-contributors/qa-role)

***

### What Counts as Accepted Work

Reviews and QA reports only count when they are substantive.

* **Contributor/ Reviewer:** You ran the branch locally, made fixes or validated the implementation, and left clear findings
* **QA:** Your report is reproducible, scoped to the PR changes, and backed by evidence

Rubber-stamp approvals and vague reports are rejected and do not qualify for payout.

→ [See Payments for Contributions, Review and QA](/for-developers/contributing/open-source-contributors/payments-for-reviews-contributors-and-qa)

{% hint style="info" %}
Your first review is evaluated by a maintainer before payout is approved.

This is a one-time check. After that, accepted reviews follow the normal flow.
{% endhint %}


# Contributor Growth Path

The more you contribute, the more you unlock. Each level opens higher-tier bounties — which means more responsibility and higher rewards.

GoodDollar has three contribution tracks. You can enter more than one, but never hold two roles on the same bounty.

<figure><img src="/files/YEnK34N0j1nyc9WrS4jh" alt=""><figcaption></figcaption></figure>

### The Tracks at a Glance

| Track       | Entry                    | Approval needed? |
| ----------- | ------------------------ | ---------------- |
| Contributor | Open to anyone           | No               |
| Reviewer    | Application + prior work | Yes              |
| QA          | Open to anyone           | No               |

> Contributor and Reviewer must always be different people on the same bounty. A person can hold both Reviewer and QA roles, but not on the same bounty.

### Contributor Track

**Contributor** — Pick up a bounty, fix the AI's code, hand it off to a Reviewer. No approval needed.

**Senior Contributor** — Earned after 5 accepted contributions with a low rework rate and consistency over time. Not volume — quality.

What this unlocks: priority access to Mythic and Legendary bounties before they open to the general pool.

PS: Senior Contributors get **priority access to Mythic and Legendary bounties** — these are surfaced to them first before opening to the general pool. This is how we reward consistency and quality over time without creating a purely financial incentive system.

The exact mechanism for how priority is surfaced will be communicated in the `goodbuilders` channel when a high-tier bounty opens.

***

### Reviewer Track

**Reviewer** — Application-based. Share previous review work and availability in the `goodbuilders` Telegram. Prior experience from any codebase counts.

**Senior Reviewer** — Earned after 3 accepted reviews with consistent quality. Unlocks all tiers and a vote on contributor pool decisions.

**Maintainer** — Internal nomination only. No application. Earned through exceptional work over time.

***

### QA Track

**QA Contributor** — Open to all. Pick up a QA bounty, test the changes, submit a structured report.

***

### Cross-Track Rules

* Reviewer and QA can be held by the same person, but not on the same bounty
* There is no required path between tracks

***

### Ready to Start?

→ See the [Contibutor Role ](/for-developers/contributing/open-source-contributors/contributor-role) to learn the basics of contributing to Gooddollar

> → Browse open bounties on the [Bounties Board](https://github.com/orgs/GoodDollar/projects)

→ See the [Reviewer Role](/for-developers/contributing/open-source-contributors/human-reviewer-role) to understand what a good review looks like&#x20;

→ See the [QA Role](/for-developers/contributing/open-source-contributors/qa-role) to understand what a good QA report looks like&#x20;


# Contributor Role

When a bounty is posted, the AI opens a Pull Request with a first-pass solution. As a Contributor, you take that code and make it production-ready before it goes to a Reviewer.

{% hint style="info" %}
[See Bounties Github Board](https://github.com/orgs/GoodDollar/projects/5)
{% endhint %}

No approval needed — anyone can contribute. Find an open bounty, claim it, and get to work.

> Contributor and Reviewer must be different people on the same bounty.

***

### The Process

* [ ] Find [an issue](https://github.com/orgs/GoodDollar/projects/5) labeled `GoodBounties - <tier>` in **Ready-For-Assignment** status
* [ ] Comment to claim it — e.g. *"I'd like to contribute to this. ETA: 2–3 days"*
* [ ] Check out the AI's branch locally and test it — do not just read the diff
* [ ] Review against the issue requirements — does the solution actually solve the problem?
* [ ] Fix errors — don't just comment, make the changes needed
* [ ] Check for: logic errors, security issues, missing tests, code style, codebase consistency
* [ ] Verify the PR has a proper description, tags the right issue, and clearly explains what's included
* [ ] If UI is involved, add demo videos or screenshots (desktop + mobile)
* [ ] Once done, post in the `goodbuilders` channel to request a Reviewer

***

### Checklist Before Handing Off

* [ ] Does the solution actually solve what the issue describes?
* [ ] Are there edge cases or error states not handled?
* [ ] Does the code follow existing patterns and conventions in the repo?
* [ ] Are there any TypeScript typing issues or linting failures?
* [ ] For UI changes — does it work on both desktop and mobile?
* [ ] Is anything over-engineered or unnecessarily complex?
* [ ] Are existing helpers/components reused where they could be?
* [ ] All fixes applied, not just commented on

***

### Tips

* Read the issue carefully before looking at the code — understand the intent first
* Run the changes locally; don't just read the diff, test it
* Check edge cases the AI may have missed (error states, empty inputs, mobile views)
* Ask questions early if the scope or approach isn't clear — on the issue or in the Builders Telegram

***

### Timelines

* Begin work within **2–3 days** of claiming
* Share progress at least every **3 days**; draft PRs are fine for visibility
* If no update or response after 3 days, the issue may be unassigned

***

### Ground Rules

* Do not resolve comments left by the maintainer or AI — reply with what you changed, and let them resolve it
* You may use AI tools to assist, but the judgment and fixes must be yours


# Human Reviewer Role

Reviewers require approval before picking up bounties. See Getting Reviewer Access below.

As a Reviewer, you validate the Contributor's corrected version of the AI-generated PR before it moves to QA. You are not reviewing the AI's original code — you are reviewing the Contributor's fixes.

Getting Reviewer Access.

> Contributor and Reviewer must be different people on the same bounty.

**The Reviewer's job:**

* Check out the Contributor's branch locally and test it
* Validate that the fixes are correct and complete
* Check for anything still missed — logic, security, edge cases, consistency
* Submit your review: **Approve**, **Comment**, or **Request Changes**
* After approving, request a maintainer sign-off from the `goodbuilders-maintainers` GitHub team
* Re-review within **48 hours** when the Contributor pushes changes and tags you

> See the image below for where to find the GitHub Teams. **Green** is for contributors requesting a code review, and **purple** is for reviewers requesting a maintainer sign-off.

<figure><img src="/files/aA3xJc72LfqlbyvgPhHP" alt=""><figcaption></figcaption></figure>

### Getting Reviewer Access

Reach out in the [`goodbounties`](https://t.me/gooddollarbounties/4115) Telegram channel or tag a maintainer on GitHub. Permissions are granted manually within 24–48 hours.

**What this unlocks:**

* Assignment as a Reviewer on incoming bounty PRs
* Eligibility for review payouts
* After **3 accepted reviews**, you become a Senior Contributor and Reviewer — you get a vote on who joins the contributor pool, what gets built next, and can propose your own ideas

You can use this template to request access:

```
Hi everyone! I'd like to join the Contributor + Reviewer pool.

Name:
Previous open-source contributions:
Availability (hours/week):
```

Your job is not to rewrite the solution. It is to validate it, catch what the AI missed, fix errors noted and ensure it is production-ready.

> **Note:** Once approved for Human Review, you join the reviewer pool and are assigned PRs. Assignments can be delegated to other approved reviewers

### What Makes a Review Accepted

A review is accepted when it is substantive — you have actually tested the code or caught something meaningful.

> 🚫 **Not acceptable:** "LGTM" with no substance. Purely stylistic comments. Generic feedback not tied to the actual changes. Any of these will result in payout rejection.

**✅ Good review comment:**

\`File: StakeModal.tsx — line 147

Issue: The distribute() function does not check whether `amount` exceeds the pool balance before transferring. If it does, the transaction will revert on-chain but state will already be updated on line 143, leaving the contract in an inconsistent state.

Fix: Add a balance check before the state update: require(poolBalance >= amount, "Insufficient pool balance"); Or move the state update after the transfer so it only commits if the transfer succeeds.\`

**❌ Weak comment (not acceptable):**

`"This function looks a bit risky, might want to double check the logic here."`

***

### Timelines

* First review response: within 48 **hours** of assignment
* Re-review after changes: within **48 hours** of being tagged
* If your assigned PR has been waiting more than 2 days with no response, ping in [GoodBounties Telegram](https://t.me/gooddollarbounties)

### Review Process & Ground Rules

**As a reviewer, your job is to bring judgment the AI can't — context, common sense, real-world testing, fixes and familiarity with how the codebase is actually used.**

**Ground rules:**

* Do not resolve comments left by the maintainer or AI — reply with what you changed, and let them resolve it
* Share progress at least every 3 days; draft PRs are fine for visibility
* If no update or response after 3 days, the issue may be unassigned
* You may use your own AI tools to assist your review, but the human review judgment must be yours

***

### PR Review Checklist

When reviewing the AI-generated PR, check for:

* [ ] Does the solution actually solve what the issue describes?
* [ ] Are there edge cases or error states not handled?
* [ ] Does the code follow existing patterns and conventions in the repo?
* [ ] Are there any TypeScript typing issues or linting failures?
* [ ] For UI changes — does it work on both desktop and mobile?
* [ ] Is anything over-engineered or unnecessarily complex?
* [ ] Are there fixes that need to happen to make code acceptable?
* [ ] Are existing helpers/components reused where they could be?

***

### Tips for a Good Review

* Read the issue carefully before looking at the code — understand the intent first
* Run the changes locally where possible; don't just read, test
* Check edge cases the AI may have missed (error states, empty inputs, mobile views)
* Look for consistency with the rest of the codebase — patterns, naming, component reuse
* Ask questions early if the scope or approach isn't clear — on the issue or in the Builders Telegram

<details>

<summary><strong>Getting Review Permissions on GitHub</strong></summary>

Once you have 2 merged PRs, reach out on the telegram channel or tag a maintainer on GitHub. Permissions are granted manually — it usually happens within 24–48 hours.

**What This Unlocks**

After **3 accepted reviews**, you become a **Senior Contributor (Level 3)**. You get a vote on who joins the contributor pool and what gets built next.

→[ Revisit the full growth path](https://app.gitbook.com/o/-LdiTCmTgO528x-BXAcj/s/-LfsEjhezedCgGFXCkms/~/edit/~/changes/303/for-developers/contributing/open-source-contributors/contributor-growth-path)

</details>


# QA Role

QA happens after the Human Reviewer approves a PR. Your job is to test the actual behavior of the changes in a real environment — catching what code review cannot. Runtime issues, edge cases, UI on real devices, and flows that break under real conditions.

***

### The QA Process

1. Claim a `GoodBounties - QA` issue or get assigned one from the pool
2. Check out the branch locally or use the preview environment linked in the PR
3. Test against every criterion listed in the issue — not just the happy path
4. Document what you tested, what passed, and what failed
5. Submit your QA report as a comment on the PR (use the QA report format below)
6. If bugs are found, file separate structured bug reports on the PR
7. Tag the maintainer team (`goodbuilders-maintainers`) when your report is complete

> 🚫 **Not acceptable:** Vague claims with no steps. Non-reproducible reports. AI-generated content not verified against actual behavior.

***

### QA Report Format

Post your report as a comment on the PR using this structure:

* **QA Report**\
  Env: \[Browser / OS / Wallet / Network]\
  Branch: \[name or commit]
*

```
**Tests**
```

```
| Scenario | Expected | Actual | ✅/❌ |
| -------- | -------- | ------ | --- |
|          |          |        |     |
```

* **Bugs**: \[# / None]
* **Verdict**: Pass / Fail / Minor issues
* **Evidence**: \[links]

***

### Filing a Bug Report

File each bug as a **separate comment** on the PR. Use this format:

**✅ Good bug report:**

\`Severity: Blocker Summary: Staking flow fails silently when wallet has insufficient G$ balance

Environment: Chrome 123 / MacOS 14.4 / MetaMask 11.9 / Fuse network

Steps to reproduce:

1. Connect wallet with 0 G$ balance
2. Navigate to the Stake tab
3. Enter any amount and click Confirm

Expected: Error message — insufficient balance Actual: Modal closes, no error shown, no transaction sent

Evidence: \[screen recording link] Related to this PR? Yes — balance check removed on line 89 of StakeModal.tsx\`

**❌ Weak bug report (not acceptable):**

`"The staking thing doesn't seem to work on my end"`

***

### Bug Severity

| Severity    | Definition                                                                       | Examples                                                                                    |
| ----------- | -------------------------------------------------------------------------------- | ------------------------------------------------------------------------------------------- |
| **Blocker** | Feature broken, data loss, security issue, or breaks an existing working feature | Transaction fails silently, funds sent to wrong address, previously working flow now broken |
| **Major**   | Feature works but behaves incorrectly under normal usage                         | Wrong amount shown, confirmation missing, edge case affecting many users                    |
| **Minor**   | Small cosmetic or UX issue                                                       | Typo, misaligned element, brief flicker                                                     |

When unsure, go one level higher — maintainers can downgrade. Maintainers may cap bug bonuses per PR; if a cap applies it will be stated in the PR announcement.

***

### What Counts as an Accepted Bug

A bug is accepted when it is:

* **Reproducible** using your documented steps
* **In scope** — directly caused by changes in this PR
* **Not pre-existing** — not a known issue before this PR

Pre-existing bugs should be filed as a new GitHub issue — they may become a separate bounty.

***


# Payments for Reviews, contributors & QA

Please note: Payout requests has to be done by a G$ verified wallet.

### Bounty Tiers & Rewards

| Tier      | Scope                                             | USD  | G$        |
| --------- | ------------------------------------------------- | ---- | --------- |
| Basic     | Small fixes, docs, UI tweaks                      | $25  | 250,000   |
| Common    | Medium features, some codebase familiarity needed | $50  | 500,000   |
| Rare      | Larger features, touches multiple areas           | $150 | 1,500,000 |
| Epic      | Significant features                              | $250 | 2,500,000 |
| Mythic    | Architecture or performance work                  | $350 | 3,500,000 |
| Legendary | Major features or protocol-level changes          | $450 | 4,500,000 |

> Learn more about solving for bounties and the roles that exist  →[ Open Source Contributors](/for-developers/contributing/open-source-contributors)

{% hint style="info" %}
G$ rewards use a base price of 0.0001/G$. Market price fluctuations may affect actual value at distribution. Tier is set upfront — taking longer does not change payout.
{% endhint %}

#### **Payments for Contributions, Reviews and QA**

<table><thead><tr><th width="184.56640625">Role</th><th>Reward</th><th>Condition</th></tr></thead><tbody><tr><td>Code Contributor</td><td>50% bounty reward</td><td>Deliverables met + PR merged</td></tr><tr><td>Code Reviewer </td><td>40% bounty reward</td><td>Deliverables met + PR merged</td></tr><tr><td>QA Tester — clean pass</td><td>10% of bounty reward</td><td>Deliverables met + evidence on PR</td></tr><tr><td>QA Tester — bug bonus</td><td>+50,000 G$ per accepted bug</td><td>Reproducible, in scope, not pre-existing</td></tr><tr><td>Code Reviewer + QA</td><td>50% of bounty reward</td><td>Deliverables met + PR merged</td></tr><tr><td></td><td></td><td></td></tr></tbody></table>

Please note: Payments happen after merge/acceptance. Not before. See below on how to request for payments.

{% hint style="info" %}
**Please note: Payout requests has to be done by a G$ verified wallet.**\
If you dont have a G$ verified wallet, you can open a GoodWallet on <https://goodwallet.xyz> and claim UBI, or you can choose your own wallet, connect the wallet to <https://gooddapp.org> and claim your first UBI.\
\
After merging, request your payout by following these steps:

1. Connect your wallet to [Gardens](https://gardens.fund)
2. Visit the GoodBuilders Community
3. Join the community by staking 105,000 G$ *(this is a one-time membership step, not adding funds to the pool)*
4. Go to the **OS Contributors Pool**
5. Create a payment request using the bounty title as the payment title, with this description:
   * PR link
   * Issue link
   * Bounty tier
   * Payout address

A maintainer will review and approve your request
{% endhint %}


# Developer Guides

<table data-view="cards"><thead><tr><th></th><th data-hidden data-card-target data-type="content-ref"></th></tr></thead><tbody><tr><td>Deploy your own GoodDapp UI</td><td><a href="/pages/wEtmnJzPFVR5QARabZ7V">/pages/wEtmnJzPFVR5QARabZ7V</a></td></tr><tr><td>How to integrate the G$ token</td><td><a href="/pages/pZSiNG9t7ZJY7zrBzRJ0">/pages/pZSiNG9t7ZJY7zrBzRJ0</a></td></tr><tr><td>use G$ Streaming</td><td><a href="/pages/swsk90RfT991SvSJyt03">/pages/swsk90RfT991SvSJyt03</a></td></tr><tr><td>Ethers V5/UseDApp context Setup</td><td><a href="/pages/iawhyt9r7pY83q4rRcUQ">/pages/iawhyt9r7pY83q4rRcUQ</a></td></tr></tbody></table>

## Win Rewards: Building something on GoodDollar!

There are various ways to earn rewards while working within the GoodDollar Ecosystem.\
\
*Scoutgame:*\
Scoutgame rewards builders who take up pre-defined tasks.\
Contribute to GoodDollar repositories and earn bounty rewards!\
More information about the program can be found on our ScoutGame[ page.](https://scoutgame.xyz/info/partner-rewards/gooddollar)\
\
*GoodDollar OpenSource Contributors Pool:*\
The GoodDollar OpenSource Contributors pool is for anyone who wants to contribute more autonomously.\
Maybe you have ideas of your own to build into GoodDapp or GoodCollective?\
Maybe you have ideas for expanding the core protocol?\
Please read up on our [GoodDollar OpenSource Contributors](https://app.gardens.fund/gardens/42220/0x62b8b11039fcfe5ab0c56e502b1c372a3d2a9c7a/0xf42c9ca2b10010142e2bac34ebdddb0b82177684/94) covenant on how to participate and apply.\
\
*GoodBuilders program:*\
Be sure to check out the [GoodBuilders Program!](https://ubi.gd/goodbuilders) offering mentorship and funding to support promising projects in their growth. Any project that demonstrates meaningful new integrations with the GoodDollar Protocol is eligible to apply!\
\
**Share your ideas, or ask for development support:**\
For discussion on Discord or various program events: [GoodDollar Builders](https://t.me/gooddollarbounties)\
We are also on Discord:  [GoodDollar Discord Development](https://discord.gg/B4bj9eXuWU)


# Deploy your own GoodDapp UI

This is a step-by-step guide to deploy your own instance of the GoodDapp to interact with the V2 smart contracts on Mainnet.

GoodDollar is currently not running its frontend — making the system more decentralized and censorship-resistant.&#x20;

In the case of users who can't use any Community Deployed front-end, they can choose to deploy their own Gooddollar Protocol V2 User Interface (UI) by forking the ProtocolUI code from the Open-Sourced GoodDollar Github repository.

### Deploy your own GoodDollar UI Tutorial

#### This will be done by a few simple steps based on the open-source repository you can find [here](https://github.com/GoodDollar/GoodProtocolUI).

This tutorial will show you how to deploy it using Netlify, but you can use Vercel, Heroku, or other services.

1. Go to the [GoodProtocolUI repository on Github](https://github.com/GoodDollar/GoodProtocolUI) and fork it to your Github account.
2. Clone it locally and install the dependencies by running the command 'yarn' on your terminal.
3. Run the 'yarn start' command in your terminal in order to run it locally on your machine.
4. Make any changes relevant for you and push them to your repository on Github.
5. Go to [Netlify](https://www.netlify.com/) and log in using your Github account.
6. Go to your [Netlify app](https://app.netlify.com/) and click on "New site from Git":                                                      &#x20;
7. Select Github:                                                                                                                                                                                     <img src="/files/gcqQ3DFPNzAKXhDdzklI" alt="" data-size="original">
8. Choose the \<your\_github\_username>/GoodProtocolUI
9. Click on Show advanced button:                                                                                                                                                     <img src="/files/yiBmQDMm4TddrpHyfRMQ" alt="" data-size="original">
10. Add a new variable with this key-value pair:                                                                                                                                         ![](/files/oqc7VKz4xgTVT5mVViyF)
11. Deploy your site:                                                                                                                                                                              ![](/files/pmQJOdZyNQ4yhvOQSOmt) &#x20;
12. It will take a few minutes, you could see the progress here:                                                        ![](/files/IZ9ARgmE5NdHrUmYE8xQ)
13. After it's finished your site is basically on air and is accessible through the address shown at the top of the page, you could connect your own domain by clicking here:                                                        ![](/files/8AFTEsGD4Xax3oo9d8yw)&#x20;
14. Every change you will make and push to your 'master' branch on your forked repo will automatically be deployed to your website.

![](/files/x2YS6SqrQ78nGo9H8E7V)

### Community Deployed GoodDollar UI <a href="#community-ui" id="community-ui"></a>

* <https://gooddapp.org>


# How to integrate the G$ token

## Integrating the G$ Token

The **G$ token** is an [ERC-677](https://github.com/ethereum/EIPs/issues/677) compliant token used to power Universal Basic Income (UBI) within the **GoodDollar** ecosystem. This guide helps you integrate G$ into your dApp, with practical examples using **Viem/Wagmi** (React) and **Ethers v6** (JavaScript). You'll learn how to use `transferAndCall` for streamlined contract interactions, and when to fall back on the standard `approve` + `transferFrom` method.

***

#### Contracts

```javascript
  g$Contract: {
    production: {
      celo: "https://celoscan.io/address/0x62B8B11039FcfE5aB0C56E502b1C372A3d2a9c7A",
      fuse: "https://explorer.fuse.io/address/0x495d133B938596C9984d462F007B676bDc57eCEC",
    },
    staging: {
      celo: "https://celoscan.io/address/0x61FA0fB802fd8345C06da558240E0651886fec69",
      fuse: "https://explorer.fuse.io/address/0xe39236a9Cf13f65DB8adD06BD4b834C65c523d2b",
    },
    development: {
      celo: "https://celoscan.io/address/0xFa51eFDc0910CCdA91732e6806912Fa12e2FD475",
      fuse: "https://explorer.fuse.io/address/0x79BeecC4b165Ccf547662cB4f7C0e83b3796E5b3",
    },
  },
```

### Prerequisites

Before integrating, ensure you are familiar with:

* ERC-20 and ERC-677/ERC-777 token standards
* React & Wagmi hooks (for frontend apps)
* Ethers v6 (for browser or Node environments)
* The G$ token contract on supported chains (e.g. Celo, Fuse, Ethereum)

***

For making G$ transfers for your dapps users, below are some options to consider&#x20;

### Option 1: `transferAndCall` (Recommended)

#### Overview

Use `transferAndCall` to send G$ and call a contract function in a **single transaction**. This improves gas efficiency and simplifies the user experience when the receiving contract implements:

```solidity
function onTokenTransfer(address from, uint256 value, bytes calldata data) external returns (bool)
```

You can see an example implementation of this in our faucet contract: <https://github.com/GoodDollar/GoodProtocol/blob/cd82c575f7b78392a18e72f700a423f53b436f10/contracts/fuseFaucet/FuseFaucetV2.sol#L252>

#### Use Case Example

In a marketplace dApp, a user can pay 10 G$ and specify an item ID, completing a purchase in one click.

***

Example: Viem/Wagmi (React)

```tsx
import { useContractWrite, usePrepareContractWrite } from 'wagmi';
import { parseUnits, encodeAbiParameters } from 'viem';

const G$Address = '0x...'; // G$ token contract
const marketplaceAddress = '0x...';
const amount = parseUnits('10', 18); // 10 G$
const itemId = 1;
const data = encodeAbiParameters([{ type: 'uint256' }], [itemId]);

const { config } = usePrepareContractWrite({
  address: G$Address,
  abi: [{
    name: 'transferAndCall',
    type: 'function',
    stateMutability: 'nonpayable',
    inputs: [
      { name: 'to', type: 'address' },
      { name: 'value', type: 'uint256' },
      { name: 'data', type: 'bytes' },
    ],
    outputs: [{ name: '', type: 'bool' }],
  }],
  functionName: 'transferAndCall',
  args: [marketplaceAddress, amount, data],
});

const { write } = useContractWrite(config);

return <button onClick={() => write?.()}>Buy Item with G$</button>;
```

***

#### Example: Ethers v6

```ts
import { ethers } from 'ethers';

const provider = new ethers.BrowserProvider(window.ethereum);
const signer = await provider.getSigner();

const G$Contract = new ethers.Contract(G$Address, abi, signer);
const marketplaceAddress = '0x...';
const amount = ethers.parseUnits('10', 18);
const itemId = 1;
const data = ethers.AbiCoder.defaultAbiCoder().encode(['uint256'], [itemId]);

await G$Contract.transferAndCall(marketplaceAddress, amount, data);
```

***

### Option 2: Leveraging ERC-777 for Token Transfers

Overview

The GoodDollar token (G$) also embraces the ERC-777 standard, offering another advanced way to handle token interactions, particularly when sending tokens to smart contracts. Similar to ERC-677's `transferAndCall`, ERC-777 allows for a token transfer and a subsequent action on the recipient contract within a single transaction. This is achieved using the `send` function and a "tokens received hook."

**Key Benefits of using ERC-777 `send`:**

* **Single Transaction Efficiency**: Just like `transferAndCall`, the `send` function in ERC-777 transfers G$ tokens and notifies the recipient contract in one go, saving on gas and simplifying the user experience.
* **Standardized Reception**: Recipient contracts can implement the `tokensReceived` hook. This function is automatically called by the G$ token contract when it receives tokens via the `send` function.

**How it Works:**

When you use the `send` function from an ERC-777 compliant G$ token contract:

`send(address to, uint256 amount, bytes calldata data)`

1. The G$ tokens are transferred to the `to` address.
2. If the `to` address is a contract that implements the `IERC777Recipient` interface, its `tokensReceived` hook will be called with details of the transfer:

   ```solidity
   function tokensReceived(
       address operator,
       address from,
       address to,
       uint256 amount,
       bytes calldata userData,
       bytes calldata operatorData
   ) external;
   ```

   * `operator`: The address that initiated the token movement (could be the `from` address or an authorized operator).
   * `from`: The address that sent the tokens.
   * `to`: The recipient address (your contract).
   * `amount`: The amount of G$ tokens received.
   * `userData`: Arbitrary data passed by the sender, similar to the `data` in `transferAndCall`.
   * `operatorData`: Arbitrary data passed by the operator, if different from the sender.

**When to Consider ERC-777:**

* If you're building contracts that need to react to incoming G$ tokens in a standardized way.
* When you appreciate the broader features of ERC-777, such as operator approvals (which offer more flexibility than ERC-20 allowances) and sender/recipient hooks for various use cases.
* If you aim for compatibility with other protocols or tools that specifically leverage ERC-777 hooks.

**Example:**

While we showcased `transferAndCall` with our FuseFaucetV2 for ERC-677, a contract designed to work with ERC-777 G$ tokens would implement the `tokensReceived` Hook like this:

```solidity
// SPDX-License-Identifier: MIT
pragma solidity ^0.8.0;

import "@openzeppelin/contracts/token/ERC777/IERC777Recipient.sol";
// Assuming your G$ token contract implements IERC777
// import "path/to/your/IERC777GoodDollar.sol";

contract MyGoodDollarAwareContract is IERC777Recipient {

    // Make sure your contract is registered with the ERC1820 registry
    // to declare that it implements the IERC777Recipient interface.
    // This is often done in the constructor.
    // See OpenZeppelin's ERC777Recipient documentation for details.

    // GoodDollar Token (G$)
    // IERC777GoodDollar public goodDollarToken;

    // constructor(address _goodDollarTokenAddress) {
    //     goodDollarToken = IERC777GoodDollar(_goodDollarTokenAddress);
    //     // Additional setup for ERC1820 registry might be needed here
    // }

    function tokensReceived(
        address operator,
        address from,
        address to,
        uint256 amount,
        bytes calldata userData,
        bytes calldata operatorData
    ) external override {
        // Ensure this hook is only callable by the G$ token contract
        // require(msg.sender == address(goodDollarToken), "Only G$ token can call this");

        // Your custom logic here when G$ tokens are received
        // For example, log the reception, update state, or trigger another action.
        // The 'userData' can be used to pass instructions or parameters.
        // emit TokensReceived(from, amount, userData);
    }

    // Fallback function to receive plain Ether, if needed
    // receive() external payable {}
}
```

### Option 3: `approve` + `transferFrom`

#### Overview

Use this method when the receiving contract **does not** implement `onTokenTransfer`, or when the dApp needs explicit allowance control. This requires **two transactions**:

1. Approve the contract to spend G$
2. Call the function that uses `transferFrom` internally

***

#### Example: Viem/Wagmi (React)

**Step 1: Approve G$ spending**

```tsx
const amountToApprove = parseUnits('10', 18);

const { config: approveConfig } = usePrepareContractWrite({
  address: G$Address,
  abi: [{
    name: 'approve',
    type: 'function',
    stateMutability: 'nonpayable',
    inputs: [
      { name: 'spender', type: 'address' },
      { name: 'amount', type: 'uint256' },
    ],
    outputs: [{ name: '', type: 'bool' }],
  }],
  functionName: 'approve',
  args: [marketplaceAddress, amountToApprove],
});

const { write: approve } = useContractWrite(approveConfig);

<button onClick={() => approve?.()}>Approve Marketplace</button>
```

**Step 2: Call buy function**

```tsx
const itemId = 1;

const { config: buyConfig } = usePrepareContractWrite({
  address: marketplaceAddress,
  abi: [{
    name: 'buyItem',
    type: 'function',
    stateMutability: 'nonpayable',
    inputs: [{ name: 'itemId', type: 'uint256' }],
    outputs: [],
  }],
  functionName: 'buyItem',
  args: [itemId],
});

const { write: buy } = useContractWrite(buyConfig);

<button onClick={() => buy?.()}>Buy Item</button>
```

***

#### Example: Ethers v6

```ts
const provider = new ethers.BrowserProvider(window.ethereum);
const signer = await provider.getSigner();

const G$Contract = new ethers.Contract(G$Address, abi, signer);
const marketplaceContract = new ethers.Contract(marketplaceAddress, marketplaceAbi, signer);

const amountToApprove = ethers.parseUnits('10', 18);
const itemId = 1;

await G$Contract.approve(marketplaceAddress, amountToApprove);
await marketplaceContract.buyItem(itemId);
```

***

### Additional Considerations

#### Transaction Fees

G$ transfers may include a **protocol fee** via the `_processFees` function. This can result in the recipient receiving slightly less than the sent amount. Always account for this in your logic or inform users ahead of time.

#### Token Decimals

G$ uses **18 decimals** on Celo, and **2 decimals** on Fuse and Ethereum . Use utilities like `parseUnits` or `formatUnits` for correct calculations.

#### Balance Checks

Check the user's balance with `balanceOf()` before calling transfer methods to reduce the risk of failed transactions.

#### Contract Compatibility

Ensure the recipient contract supports this function for `transferAndCall` to succeed:

```solidity
function onTokenTransfer(address from, uint256 value, bytes calldata data) external returns (bool);
```

If not, fall back to `approve + transferFrom` or add a wrapper contract that can handle the callback.

***

### Notes on Ethers v6

* **Provider updates**: Use `BrowserProvider` instead of `Web3Provider`
* **Signers**: `getSigner()` is now async
* **Utility changes**: Use `ethers.parseUnits`, `ethers.AbiCoder.defaultAbiCoder().encode`
* **BigInt usage**: Native BigInt replaces BigNumber throughout the library

***

### Example Use Case: Marketplace Checkout

| Method                   | Flow                         | Pros                                     | Cons                               |
| ------------------------ | ---------------------------- | ---------------------------------------- | ---------------------------------- |
| `transferAndCall`        | Send G$ + buy item in one tx | <p>✅ Gas-efficient<br>✅ One-click UX</p> | ⚠️ Requires `onTokenTransfer`      |
| `approve + transferFrom` | Approve first, then buy      | ✅ Compatible with most ERC20 apps        | <p>❌ Two steps<br>❌ Higher gas</p> |

***

### 📚 References

* [GoodDollar Token Docs](https://docs.gooddollar.org/)
* [ERC-677 Specification](https://github.com/ethereum/EIPs/issues/677)
* [Ethers v6 Docs](https://docs.ethers.org/v6/)

***


# Use G$ streaming

**First-step:**

* Superfluid concepts: [What is Superfluid?](https://docs.superfluid.org/docs/concepts/superfluid)

***

### TL;DR (one-minute overview)

Streaming Payments with G$ Token\
GoodDollar’s G$ is deployed as a pure Superfluid SuperToken on the Celo network—no wrapping needed, so it can be streamed second-by-second out of the box.\
Streaming turns one-off transfers into continuous flows, enabling payroll, vesting, or loan payments. \
For other example use cases, see[ here.](https://docs.superfluid.org/docs/category/examples-1)\
For simple second-by-second transfers called **'streaming',** powered by the SuperFluid Protocol, you talk **directly** to the immutable **`CFAv1Forwarder`** contract (`0xcfA132E3…B125) and pass in G$’s address (`0x62B8…C7A\`).\
All flows boil down to three methods:

```solidity
createFlow(ISuperToken token, address sender, address receiver, int96 flowRate, bytes userData)
updateFlow(ISuperToken token, address sender, address receiver, int96 newRate, bytes userData)
deleteFlow(ISuperToken token, address sender, address receiver, bytes userData)
```

Optional next steps:

* **GDAv1Forwarder** → pool-style distribution streams, optimized to work with off-chain interactions. ([docs.superfluid.finance](https://docs.superfluid.finance/docs/technical-reference/GDAv1Forwarder))
* **Super-Apps** → have your contracts *react* to flow events once you register them with the Host. ([docs.superfluid.finance](https://docs.superfluid.finance/docs/concepts/advanced-topics/super-apps), [GitHub](https://github.com/superfluid-org/protocol-monorepo/wiki/About-App-Registry))

***

### Prerequisites

| What                                             | Why                                                                                                                                                                                                                                                                                                                                                                                                                                               |
| ------------------------------------------------ | ------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------- |
| Node ≥ 18 & bundler (Vite / Next)                | To build a web client                                                                                                                                                                                                                                                                                                                                                                                                                             |
| **ethers v6** *or* **viem + wagmi**              | Low-level EVM calls                                                                                                                                                                                                                                                                                                                                                                                                                               |
| A wallet on **Celo Mainnet** (`chainId = 42220`) | Only Celo currently has G$ streaming capabilities.                                                                                                                                                                                                                                                                                                                                                                                                |
| G$ token address                                 | <p>(<strong>Recommended for testing</strong>: Development G$)<br><a href="https://celoscan.io/address/0xFa51eFDc0910CCdA91732e6806912Fa12e2FD475">0xFa51eFDc0910CCdA91732e6806912Fa12e2FD475</a><br><br>(production G$) <a href="https://celoscan.io/address/0x62b8b11039fcfe5ab0c56e502b1c372a3d2a9c7a?a=0xe738edd568147d3fc4583894ff0ad19d2ced11f8&#x26;utm_source=chatgpt.com"><code>0x62B8B11039fcfE5AB0C56E502b1C372A3D2a9C7A</code></a></p> |
| `CFAv1Forwarder` universal address               | `0xcfA132E353cB4E398080B9700609bb008eceB125` ([docs.superfluid.finance](https://docs.superfluid.finance/docs/technical-reference/CFAv1Forwarder))                                                                                                                                                                                                                                                                                                 |

***

### Project Setup

```bash
npm i ethers wagmi viem
```

```ts
// lib/superfluid.ts
import { BrowserProvider } from 'ethers';

export const provider = new BrowserProvider(window.ethereum);
export const forwarderAddr = '0xcfA132E353cB4E398080B9700609bb008eceB125';
export const gDollar     = '0x62B8B11039fcfE5AB0C56E502b1C372A3D2a9C7A';

// paste the CFAv1Forwarder ABI snippet from the tech-ref page ↓
import { CFAv1ForwarderAbi } from './CFAv1ForwarderAbi';

export const forwarder = new ethers.Contract(
  forwarderAddr,
  CFAv1ForwarderAbi,
  provider.getSigner()
);
```

*The full ABI is on the technical-reference page and includes helpers like `getBufferAmountByFlowrate`.* ([docs.superfluid.finance](https://docs.superfluid.finance/docs/technical-reference/CFAv1Forwarder))

***

### Creating a Flow (React / wagmi example)

```tsx
import { useState } from 'react';
import { useAccount } from 'wagmi';
import { forwarder, gDollar } from './lib/superfluid';

// helper – convert “tokens per month” → int96 wad/sec
const perMonthToRate = (pm: string) =>
  BigInt(pm) * 10n ** 18n / 2592000n; // 30 × 24 × 60 × 60

export default function CreateFlow() {
  const { address } = useAccount();
  const [receiver, setReceiver] = useState('');
  const [perMonth, setPerMonth] = useState('10');

  async function start() {
    const tx = await forwarder.createFlow(
      gDollar,
      address!,        // sender (caller)
      receiver,
      perMonthToRate(perMonth), // int96 flowRate
      '0x'             // userData
    );
    await tx.wait();
  }

  return (
    <>
      <input value={receiver} onChange={e=>setReceiver(e.target.value)} />
      <button onClick={start}>
        Stream {perMonth} G$/mo
      </button>
    </>
  );
}
```

The same pattern works for **`updateFlow`** and **`deleteFlow`**; just swap the method. ([docs.superfluid.finance](https://docs.superfluid.finance/docs/sdk/money-streaming/create-update-delete-flow))

***

### Reading Live Data

```ts
// How fast am I sending right now?
const { flowrate } = await forwarder.getFlowInfo(
  gDollar,
  sender,
  receiver
);

// How big a safety buffer does Superfluid require for 10 G$/mo?
const buffer = await forwarder.getBufferAmountByFlowrate(
  gDollar,
  perMonthToRate('10')
);
```

These helper views are defined in the same contract. ([docs.superfluid.finance](https://docs.superfluid.finance/docs/technical-reference/CFAv1Forwarder))\
For historical analytics use the **Superfluid Subgraph** or Explorer. ([docs.superfluid.finance](https://docs.superfluid.finance/docs/sdk/money-streaming/subgraph))

***

### Registering Your dApp as a Super-App (optional)

If your contract should *react* to incoming/outgoing streams (e.g. auto-staking or NFT minting), you want your dApp to be registered as Super-App.

{% hint style="warning" %}
For instructions please follow: <https://docs.superfluid.org/docs/protocol/advanced-topics/super-apps/register>\
\
The Celo network requires a 'deployer' to be whitelisted before it can be registered. [Please reach out to us to help you get whitelisted.](https://t.me/gooddollarbounties/1)
{% endhint %}

***

### 6 Next Steps & Gotchas

<table><thead><tr><th width="217">Topic</th><th width="532.39990234375">What to watch for</th></tr></thead><tbody><tr><td><strong>GDAv1Forwarder</strong></td><td>Needed for pool-style “one-to-many” distributions; interface is analogous to CFA but targets pools. (<a href="https://docs.superfluid.finance/docs/technical-reference/GDAv1Forwarder">docs.superfluid.finance</a>)</td></tr><tr><td><strong>Flow-rate math</strong></td><td><code>rate = amountPerMonth × 1e18 / 2 592 000</code>. Keep <code>int96</code> limits (~10^27 total). (<a href="https://docs.superfluid.finance/docs/sdk/money-streaming/create-update-delete-flow">docs.superfluid.finance</a>)</td></tr><tr><td><strong>Buffer deposits</strong></td><td>Use <code>getBufferAmountByFlowrate</code> before creating a stream to make sure the sender holds ≥ buffer + first few minutes. (<a href="https://docs.superfluid.finance/docs/technical-reference/CFAv1Forwarder">docs.superfluid.finance</a>)</td></tr><tr><td><strong>Protocol fees</strong></td><td>G$ applies its <code>_processFees</code> on each streamed “drip”; receiver gets <code>flowRate – feeRate</code>.</td></tr><tr><td><strong>Network support</strong></td><td>Streaming live only on Celo today; G$ on Fuse &#x26; ETH can still use one-off transfers.</td></tr><tr><td><strong>Testing</strong></td><td>Use GoodDollar’s dev contract <code>0xFa51eFDc0910CCdA91732e6806912Fa12e2FD475</code>. You can claim some free dev G$'s by creating a dev wallet here: <a href="https://goodwallet.dev/">https://goodwallet.dev</a></td></tr></tbody></table>

***

### Reference Links

1. **Create/Update/Delete Flows guide** (Superfluid SDK) ([docs.superfluid.finance](https://docs.superfluid.finance/docs/sdk/money-streaming/create-update-delete-flow))
2. **CFAv1Forwarder technical reference** ([docs.superfluid.finance](https://docs.superfluid.finance/docs/technical-reference/CFAv1Forwarder))
3. **GDAv1Forwarder reference** (for next steps) ([docs.superfluid.finance](https://docs.superfluid.finance/docs/technical-reference/GDAv1Forwarder?utm_source=chatgpt.com))
4. **SuperTokenV1Library** (Solidity helper) ([docs.superfluid.finance](https://docs.superfluid.finance/docs/technical-reference/SuperTokenV1Library))
5. **Super-Apps concepts** page ([docs.superfluid.finance](https://docs.superfluid.finance/docs/concepts/advanced-topics/super-apps))
6. **Host & Super-App architecture** ([docs.superfluid.finance](https://docs.superfluid.finance/docs/protocol/advanced-topics/super-apps/register))
7. **App-Registry wiki / registerApp** ([GitHub](https://github.com/superfluid-org/protocol-monorepo/wiki/About-App-Registry))
8. **Agreement Forwarders overview** ([GitHub](https://github.com/superfluid-org/protocol-monorepo/wiki/About-Agreement-Forwarders))
9. **G$ token contract on CeloScan** ([Celo Chain Blockchain Explorer](https://celoscan.io/address/0x62b8b11039fcfe5ab0c56e502b1c372a3d2a9c7a?a=0xe738edd568147d3fc4583894ff0ad19d2ced11f8))

***


# Ethers V5/useDapp Context Setup

{% hint style="warning" %}
This setup is required when using the ethers-v5 compatible SDK's from the [GoodWeb3-Mono Repo.](https://github.com/GoodDollar/GoodWeb3-Mono)

For ethers-v6 sdk's, see the viem/wagmi sdk's documentation for [Identity](/for-developers/apis-and-sdks/sybil-resistance/identity-viem-wagmi) or [Claiming](/for-developers/apis-and-sdks/ubi/claim-ubi-viem-wagmi). Or take a look at the [GoodSdks Repository](https://github.com/GoodDollar/GoodSdks)&#x20;
{% endhint %}

We write our components in react-native-web to be compatible with web and mobile platforms.

\
We use the following packages for the web3 react experience:

* native-base
* react-native-web
* useDapp
* ethers (the web3-sdkv2 uses ethers\@5)

To use the react hooks SDK (web3sdk-v2 in the [mono-repo](https://github.com/GoodDollar/GoodWeb3-Mono)), you'll need to make sure you have the following installed:

```sh
yarn install @usedapp/core ethers@5.8.0 @react-native-async-storage/async-storage react react-native react-native-web @reown/appkit @reown/appkit-adapter-wagmi @tanstack/react-query viem wagmi

```

Then, you'll need to create a context provider which is a wrapper around[ useDapp context provider](https://usedapp-docs.netlify.app/docs/api%20reference/providers/#dappprovider):

```jsx
import { Celo, Fuse, Web3Provider, AsyncStorage } from '@gooddollar/web3sdk-v2'
import { Goerli, Mainnet } from '@usedapp/core'

...
...

const contractsEnv = "production"
..

return (<Web3Provider
                web3Provider={webprovider}
                env={contractsEnv}
                config={{
                    pollingInterval: 15000,
                    networks: [Goerli, Mainnet, Fuse, Celo],
                    readOnlyChainId: undefined,
                    readOnlyUrls: {
                        1: 'https://rpc.ankr.com/eth',
                        122: 'https://rpc.fuse.io',
                        42220: 'https://forno.celo.org',
                    },
                }}
            >
                {children}
</Web3Provider>)
```

## NextJS configuration

This is a working configuration when using webpack.

```javascript
** @type {import('next').NextConfig} */
const nodeExternals = require("webpack-node-externals");
module.exports = {
  webpack: (config, { isServer }) => {
    if (isServer) {
      config.externals = [
        nodeExternals({
          allowlist: ["react-native", "@gooddollar/web3sdk-v2"],
        }),
      ];
    }

    config.resolve.alias = {
      ...(config.resolve.alias || {}),
      "react-native": "react-native-web",
    };

    config.externals.push({
      "expo-file-system": "commonjs expo-file-system",
      "react-native-navigation": "commonjs react-native-navigation",
      "@react-navigation/native": "commonjs @react-navigation/native",
    });

    config.resolve.extensions = [
      ".web.js",
      ".web.jsx",
      ".web.ts",
      ".web.tsx",
      ...config.resolve.extensions,
    ];
    return config;
  },
};

```

Make sure the components used are not rendered on server side. this can be done by dynamic importing:

```jsx
import dynamic from "next/dynamic";
const Web3SdkProvider = dynamic(() => import("./api/Web3Context"), {
  ssr: false,
});
```

## Win Rewards: Building something on GoodDollar!

There are various ways to earn rewards while working within the GoodDollar Ecosystem.\
\
*Scoutgame:*\
Scoutgame rewards builders who take up pre-defined tasks.\
Contribute to GoodDollar repositories and earn bounty rewards!\
More information about the program can be found on our ScoutGame[ page.](https://scoutgame.xyz/info/partner-rewards/gooddollar)\
\
*GoodDollar OpenSource Contributors Pool:*\
The GoodDollar OpenSource Contributors pool is for anyone who wants to contribute more autonomously.\
Maybe you have ideas of your own to build into GoodDapp or GoodCollective?\
Maybe you have ideas for expanding the core protocol?\
Please read up on our [GoodDollar OpenSource Contributors](https://app.gardens.fund/gardens/42220/0x62b8b11039fcfe5ab0c56e502b1c372a3d2a9c7a/0xf42c9ca2b10010142e2bac34ebdddb0b82177684/94) covenant on how to participate and apply.\
\
*GoodBuilders program:*\
Be sure to check out the [GoodBuilders Program!](https://ubi.gd/goodbuilders) offering mentorship and funding to support promising projects in their growth. Any project that demonstrates meaningful new integrations with the GoodDollar Protocol is eligible to apply!\
\
**Share your ideas, or ask for development support:**\
For discussion on Discord or various program events: [GoodDollar Builders](https://t.me/gooddollarbounties)\
We are also on Discord:  [GoodDollar Discord Development](https://discord.gg/B4bj9eXuWU)


# APIs & SDKs

You can leverage G$ infrastructure for payments and Identity solutions and interact with the wallet users

<table data-view="cards"><thead><tr><th></th><th></th><th></th><th data-hidden data-card-target data-type="content-ref"></th></tr></thead><tbody><tr><td><strong>Identity/Sybil Resistance</strong></td><td></td><td></td><td><a href="/pages/Q8cJnHId17d69TX0YQzW">/pages/Q8cJnHId17d69TX0YQzW</a></td></tr><tr><td><strong>Claim UBI</strong></td><td></td><td></td><td><a href="/pages/sUrCiyDGPC0z9NrBKmeK">/pages/sUrCiyDGPC0z9NrBKmeK</a></td></tr><tr><td><strong>G$ Price</strong></td><td></td><td></td><td><a href="/pages/nTEBaPrR1XUcp3mcyzIN">/pages/nTEBaPrR1XUcp3mcyzIN</a></td></tr><tr><td><strong>React Hooks</strong></td><td></td><td></td><td><a href="/pages/iawhyt9r7pY83q4rRcUQ">/pages/iawhyt9r7pY83q4rRcUQ</a></td></tr><tr><td><strong>GoodWallet</strong></td><td></td><td></td><td><a href="https://wallet.gooddollar.org">https://wallet.gooddollar.org</a></td></tr><tr><td><strong>GoodDAPP</strong></td><td></td><td></td><td><a href="https://gooddapp.org">https://gooddapp.org</a></td></tr></tbody></table>

## Win Rewards: Building something on GoodDollar!

There are various ways to earn rewards while working within the GoodDollar Ecosystem.\
\
*Scoutgame:*\
Scoutgame rewards builders who take up pre-defined tasks.\
Contribute to GoodDollar repositories and earn bounty rewards!\
More information about the program can be found on our ScoutGame[ page.](https://scoutgame.xyz/info/partner-rewards/gooddollar)\
\
*GoodDollar OpenSource Contributors Pool:*\
The GoodDollar OpenSource Contributors pool is for anyone who wants to contribute more autonomously.\
Maybe you have ideas of your own to build into GoodDapp or GoodCollective?\
Maybe you have ideas for expanding the core protocol?\
Please read up on our [GoodDollar OpenSource Contributors](https://app.gardens.fund/gardens/42220/0x62b8b11039fcfe5ab0c56e502b1c372a3d2a9c7a/0xf42c9ca2b10010142e2bac34ebdddb0b82177684/94) covenant on how to participate and apply.\
\
*GoodBuilders program:*\
Be sure to check out the [GoodBuilders Program!](https://ubi.gd/goodbuilders) offering mentorship and funding to support promising projects in their growth. Any project that demonstrates meaningful new integrations with the GoodDollar Protocol is eligible to apply!\
\
**Share your ideas, or ask for development support:**\
For discussion on Discord or various program events: [GoodDollar Builders](https://t.me/gooddollarbounties)\
We are also on Discord:  [GoodDollar Discord Development](https://discord.gg/B4bj9eXuWU)


# UBI

Every verified person is eligible to claim daily free UBI in the form of G$ tokens.

#### UBI Contracts

```javascript
  ubiContract: {
    production: {
      celo: "https://celoscan.io/address/0x43d72Ff17701B2DA814620735C39C620Ce0ea4A1",
      fuse: "https://explorer.fuse.io/address/0xd253A5203817225e9768C05E5996d642fb96bA86",
    },
    staging: {
      celo: "https://celoscan.io/address/0x2881d417dA066600372753E73A3570F0781f18cB",
      fuse: "https://explorer.fuse.io/address/0x54469071Ca82B46A2C01C09D38ca6Ca4347EB21d",
    },
    development: {
      celo: "https://celoscan.io/address/0x6B86F82293552C3B9FE380FC038A89e0328C7C5f",
      fuse: "https://explorer.fuse.io/address/0x3bdeB796950301FfC9568fAF89B7370f8B217321",
    },
```

{% content-ref url="/pages/ubhc8mi3bPFyQdWJ54Wx" %}
[Claim UBI (Ethers v5/ React)](/for-developers/apis-and-sdks/ubi/claim-ubi-ethers-v5-react)
{% endcontent-ref %}

{% content-ref url="/pages/ZJBzcRpau32N7RQrggig" %}
[Claim UBI (Viem/Wagmi)](/for-developers/apis-and-sdks/ubi/claim-ubi-viem-wagmi)
{% endcontent-ref %}

{% content-ref url="/pages/ijxUDlUVcuAqQ3XEpRXh" %}
[Claim UBI (Web-components)](/for-developers/apis-and-sdks/ubi/claim-ubi-web-components)
{% endcontent-ref %}


# Claim UBI (Ethers v5/ React)

Every verified person is eligible to claim daily free UBI in the form of G$ tokens.

{% hint style="warning" %}
Please ensure you have [followed the steps to set up the context provider](/for-developers/developer-guides/ethers-v5-usedapp-context-setup) for this SDK.
{% endhint %}

Make sure user wallet is whitelisted, see [Identity](/for-developers/apis-and-sdks/sybil-resistance).

First, create the SDK.\
The first argument should be an ethers Web3Provider, since the user will need to sign transactions.\
Second argument is which environment and chain contract set to use.<br>

{% hint style="info" %}
Every user can claim every day from every chain that has a UBI pool
{% endhint %}

```typescript
import { ClaimSDK } from "@gooddollar/web3sdk-v2"

const sdk = new ClaimSDK(web3provider, "production" | "production-celo")
```

Check if the user is currently eligible to claim today:

```typescript
const claimAmount = await sdk.checkEntitlement() // if claimAmount > 0 user can claim
```

Then, perform claim:

```typescript
await sdk.claim()
```

You can also get the next `Date` when the user will be eligible to claim again

```typescript
const nextClaimTime = await sdk.getNextClaimTime()
```

### React hooks

You can also use our react hooks to manage claim.

See the Claim/Identity react hooks code [here](https://github.com/GoodDollar/GoodWeb3-Mono/blob/master/packages/sdk-v2/src/sdk/claim/react.ts).\
Storybook examples [here](https://github.com/GoodDollar/GoodWeb3-Mono/tree/master/packages/sdk-v2/src/stories/claim).\
You will need to first setup our context provider as explained [here](/for-developers/developer-guides/ethers-v5-usedapp-context-setup).

## Win Rewards: Building something on GoodDollar!

There are various ways to earn rewards while working within the GoodDollar Ecosystem.\
\
*Scoutgame:*\
Scoutgame rewards builders who take up pre-defined tasks.\
Contribute to GoodDollar repositories and earn bounty rewards!\
More information about the program can be found on our ScoutGame[ page.](https://scoutgame.xyz/info/partner-rewards/gooddollar)\
\
*GoodDollar OpenSource Contributors Pool:*\
The GoodDollar OpenSource Contributors pool is for anyone who wants to contribute more autonomously.\
Maybe you have ideas of your own to build into GoodDapp or GoodCollective?\
Maybe you have ideas for expanding the core protocol?\
Please read up on our [GoodDollar OpenSource Contributors](https://app.gardens.fund/gardens/42220/0x62b8b11039fcfe5ab0c56e502b1c372a3d2a9c7a/0xf42c9ca2b10010142e2bac34ebdddb0b82177684/94) covenant on how to participate and apply.\
\
*GoodBuilders program:*\
Be sure to check out the [GoodBuilders Program!](https://ubi.gd/goodbuilders) offering mentorship and funding to support promising projects in their growth. Any project that demonstrates meaningful new integrations with the GoodDollar Protocol is eligible to apply!\
\
**Share your ideas, or ask for development support:**\
For discussion on Discord or various program events: [GoodDollar Builders](https://t.me/gooddollarbounties)\
We are also on Discord:  [GoodDollar Discord Development](https://discord.gg/B4bj9eXuWU)


# Claim UBI (Viem/Wagmi)

The Claim SDK enables developers to integrate Universal Basic Income (UBI) claiming functionality into their applications, allowing users to claim GoodDollars (G$) on supported blockchain networks like Celo and Fuse. Built to work seamlessly with the GoodDollar protocol, it relies on the Identity SDK for whitelisting checks and supports both Wagmi (for React) and Viem (for non-React) environments.

### Installation

To use the Claim SDK, install the `@goodsdks/citizen-sdk` package, which includes the necessary components:

```bash
npm install @goodsdks/citizen-sdk
```

Or with Yarn:

```bash
yarn add @goodsdks/citizen-sdk
```

### Available Methods

The `ClaimSDK` class provides the following methods:

* `checkEntitlement(pClient?: PublicClient): Promise<bigint>`
* `claim(): Promise<TransactionReceipt | any>`
* `nextClaimTime(): Promise<Date>`
* `getDailyStats(): Promise<{ claimers: bigint; amount: bigint }>`

Refer to the package documentation for detailed information on each method, including parameters and return types. \<todo: add link after PR merge>

### Using the Wagmi SDK

The Claim SDK integrates with Wagmi for React applications, leveraging the `useIdentitySDK` hook for easy setup. Below is an example of initializing the SDK and performing basic operations like checking eligibility and claiming UBI.

```typescript
import { useAccount, usePublicClient, useWalletClient } from 'wagmi';
import { useIdentitySDK } from '@goodsdks/identity-sdk/wagmi-sdk';
import { ClaimSDK } from '@goodsdks/identity-sdk/viem-claim-sdk';

const ClaimComponent = () => {
  const { address } = useAccount();
  const publicClient = usePublicClient();
  const { data: walletClient } = useWalletClient();
  const identitySDK = useIdentitySDK('production');

  if (!address || !publicClient || !walletClient || !identitySDK) {
    return <div>Loading...</div>;
  }

  const claimSDK = new ClaimSDK({
    account: address,
    publicClient,
    walletClient,
    identitySDK,
    env: 'production',
  });

  const checkEntitlement = async () => {
    try {
      const entitlement = await claimSDK.checkEntitlement();
      console.log('Entitlement:', entitlement.toString());
    } catch (error) {
      console.error('Entitlement check failed:', error);
    }
  };

  const claimUBI = async () => {
    try {
      await claimSDK.claim();
      console.log('Claim successful');
    } catch (error) {
      console.error('Claim failed:', error);
    }
  };

  return (
    <div>
      <button onClick={checkEntitlement}>Check Entitlement</button>
      <button onClick={claimUBI}>Claim UBI</button>
    </div>
  );
};
```

For a more comprehensive example, including state management and user feedback, see \<link to demo app>

### Using the Viem SDK

For non-React environments or backend services, the Viem-based Claim SDK offers a straightforward way to interact with the UBI Scheme Contract. The `ClaimSDK.init` the method simplifies initialization.

```typescript
import { PublicClient, WalletClient } from 'viem';
import { IdentitySDK } from '@goodsdks/identity-sdk/viem-identity-sdk';
import { ClaimSDK } from '@goodsdks/identity-sdk/viem-claim-sdk';

const publicClient = new PublicClient({ /* configuration */ });
const walletClient = new WalletClient({ /* configuration */ });
const identitySDK = new IdentitySDK(publicClient, walletClient, 'production');

const claimSDK = await ClaimSDK.init({
  publicClient,
  walletClient,
  identitySDK,
  env: 'production',
});

try {
  const entitlement = await claimSDK.checkEntitlement();
  console.log('Entitlement:', entitlement.toString());
} catch (error) {
  console.error('Entitlement check failed:', error);
}

try {
  await claimSDK.claim();
  console.log('Claim successful');
} catch (error) {
  console.error('Claim failed:', error);
}
```

Additional methods like `nextClaimTime` and `getDailyStats` are detailed in the [GitHub README](https://github.com/GoodDollar).

### References

* [Viem Documentation](https://viem.sh/)
* [Wagmi Documentation](https://wagmi.sh/)
* [OpenZeppelin Contracts](https://docs.openzeppelin.com/contracts/)
* [UBISchemeV2 Contract](https://github.com/GoodDollar/GoodProtocol/blob/master/contracts/ubi/UBISchemeV2.sol)


# Claim UBI (Web-components)

## Claim Button Web Component

The `claim-button` web component provides a simple and interactive way for users to claim Universal Basic Income (UBI) in the form of GoodDollars (G$) on supported blockchain networks (Celo and Fuse). It integrates with the GoodDollar ecosystem to manage wallet connections, eligibility checks, and token claims, offering a seamless experience for users within any web application.

### What It Does

The `claim-button` enables users to:

* Connect their cryptocurrency wallet (via Reown AppKit).
* Check their eligibility to claim G$ tokens based on the GoodDollar protocol.
* If this is a new user, they will be guided through our [Face-Verification flow](https://docs.gooddollar.org/about-the-protocol/sybil-resistance)
* Claim their UBI with a single click, handling all blockchain transactions.
* View their G$ token balance.
* See a countdown timer until their next claim if they’ve already claimed for the current period.
* Switch between supported chains (Celo and Fuse) if entitlements are available on another network.

### Prerequisites

Make sure you register your wallet on [re-own cloud dashboard](https://cloud.reown.com/sign-in). You want to register an dapp which integrates 'appkit'

### How to Use It

You can integrate the `claim-button` into your project in two ways:

#### Option 1: Using the Standalone Script

Can be used in any website, for a quick setup:

1. **Download the Script**: Download the `claim-button.global.js` file from the project releases or build it from the source.
2. **Include in HTML**: Add the script to your HTML file.
3. **Add the Component**: Use the `<claim-button>` tag where you want it to appear.

```html
<!DOCTYPE html>
<html lang="en">
  <head>
    <meta charset="UTF-8" />
    <meta name="viewport" content="width=device-width, initial-scale=1.0" />
    <title>Claim Button Example</title>
  </head>
  <body>
    <claim-button id="claimBtn" environment="production"></claim-button>
    <script src="path/to/claim-button.global.js"></script>
    <script type="module">
      // Wait for the component to be defined
      customElements.whenDefined("claim-button").then(() => {
        const claimBtn = document.getElementById("claimBtn")
        claimBtn.appkitConfig = {
          projectId: "71dd03d057d89d0af68a4c627ec59694",
          metadata: {
            name: "AppKit",
            description: "AppKit Example",
            url: "https://example.com",
            icons: ["https://avatars.githubusercontent.com/u/179229932"],
          },
        }
      })
    </script>
  </body>
</html>
```

#### Option 2: Using ESM Modules

**Note:**: see above example for the metadata configuration, for simplicity removed from\
below examples.

For projects with a modern JavaScript setup:

1. **Install the Package**: Add the `@goodsdks/ui-components` package to your project.

   ```bash
   npm install @goodsdks/ui-components
   ```
2. **Import the Component**: Import it in your JavaScript or TypeScript file.

   ```javascript
   import "@goodsdks/ui-components"
   ```
3. **For use in HTML**: Place the `<claim-button>` tag in your template.

   ```html
   <claim-button environment="production"></claim-button>
   ```
4. **For use in React**": Place the `<claim-button>` tag in your render method.

   ```javascript
   render(<claim-button environment="production"></claim-button>)
   ```

### Configurable Options

Customize the `claim-button` using these properties:

* **`environment`**: Defines the environment for contract interactions.
  * Values: `"production"`, `"staging"`, or `"development"`.
  * Default: `"development"`.
  * Example:

    ```html
    <claim-button environment="production"></claim-button>
    ```
* **`appkitConfig`**: *(Set via JavaScript property)*\
  Provides configuration for wallet connection and custom branding in wallet dialogs.
  * Expected to be an object with at least `projectId` and a `metadata` object containing your app's details.
  * Example:

    ```js
    // In your JavaScript, after the component is defined:
    customElements.whenDefined("claim-button").then(() => {
      document.querySelector("claim-button").appkitConfig = {
        projectId: "YOUR_PROJECT_ID",
        metadata: {
          name: "YourAppName",
          description: "A short app description",
          url: "https://yourapp.example.com",
          icons: ["https://yourapp.example.com/icon.png"],
        },
      }
    })
    ```
  * **Note:** `appkitConfig` cannot be set as an HTML attribute; it must be set on the element as a property from JavaScript.

### Interactive Demo

Try out the `claim-button` in action using the interactive widget below. This sandbox environment lets you see how the component works in a live setting, making it easier to understand its behavior and integration.

{% hint style="info" %}
Below is using development contracts, so even if you have whitelisted a primary account in our apps, you'll have to do face verification again for this demo widget.\
You can see the code by clicking or sliding the left sidebar. (and it's really all the code there is)\
(Social login does not work in this demo)
{% endhint %}

{% embed url="<https://codesandbox.io/p/sandbox/r73t52>" %}

### Additional Notes

* **Dependencies**: The component uses `@reown/appkit` for wallet connections, `@goodsdks/citizen-sdk` for claim logic, `viem` for blockchain interactions, and `lit` for the reactive UI.
* If you want to build your own widget, see [Claim UBI (Viem/Wagmi)](/for-developers/apis-and-sdks/ubi/claim-ubi-viem-wagmi)
* **Supported Chains**: Works on Celo and Fuse networks.
* **Feedback**: Displays loading states, success messages, errors, and a countdown timer as needed.


# Sybil Resistance

To be able to distribute free money while ensuring each unique person registers only once, we need to verify the liveness and uniqueness of people.

{% hint style="info" %}
or more information read this article: \
<https://medium.com/gooddollar/gooddollar-identity-pillar-balancing-identity-and-privacy-part-i-face-matching-d6864bcebf54>
{% endhint %}

With the Identity service you can perform two actions:

* Proof you are a unique, live individual and whitelist a new wallet address into the GoodDollar protocol by generating a unique Face Verification link.
* Query the status of a connected wallet in your dapp eg.:
  * Expiry Date
  * Verify a new wallet address is owned by a live and unique person.
  * If a person connected different wallets, the root whitelisted address can be retrieved

There are two SDK's available for builders to integrate the identity flow into their dapps:

{% content-ref url="/pages/qCkuyCiUxW6bkmBKZity" %}
[Identity (Ethers v5 / React)](/for-developers/apis-and-sdks/sybil-resistance/identity-ethers-v5-react)
{% endcontent-ref %}

{% content-ref url="/pages/0JNkCR7hOtuwszwKtvOp" %}
[Identity (Viem/Wagmi)](/for-developers/apis-and-sdks/sybil-resistance/identity-viem-wagmi)
{% endcontent-ref %}

## Win Rewards: Building something on GoodDollar!

There are various ways to earn rewards while working within the GoodDollar Ecosystem.\
\
*Scoutgame:*\
Scoutgame rewards builders who take up pre-defined tasks.\
Contribute to GoodDollar repositories and earn bounty rewards!\
More information about the program can be found on our ScoutGame[ page.](https://scoutgame.xyz/info/partner-rewards/gooddollar)\
\
*GoodDollar OpenSource Contributors Pool:*\
The GoodDollar OpenSource Contributors pool is for anyone who wants to contribute more autonomously.\
Maybe you have ideas of your own to build into GoodDapp or GoodCollective?\
Maybe you have ideas for expanding the core protocol?\
Please read up on our [GoodDollar OpenSource Contributors](https://app.gardens.fund/gardens/42220/0x62b8b11039fcfe5ab0c56e502b1c372a3d2a9c7a/0xf42c9ca2b10010142e2bac34ebdddb0b82177684/94) covenant on how to participate and apply.\
\
*GoodBuilders program:*\
Be sure to check out the [GoodBuilders Program!](https://ubi.gd/goodbuilders) offering mentorship and funding to support promising projects in their growth. Any project that demonstrates meaningful new integrations with the GoodDollar Protocol is eligible to apply!\
\
**Share your ideas, or ask for development support:**\
For discussion on Discord or various program events: [GoodDollar Builders](https://t.me/gooddollarbounties)\
We are also on Discord:  [GoodDollar Discord Development](https://discord.gg/B4bj9eXuWU)


# Identity (Ethers v5 / React)

Follow below steps to integrate the Identity flow into your dapp!

{% hint style="warning" %}
Please ensure you have [followed the steps to set up the context provider](/for-developers/developer-guides/ethers-v5-usedapp-context-setup) for this SDK.
{% endhint %}

### Install the javascript/react SDK

```bash
yarn install @gooddollar/web3sdk-v2
```

### Register and verify a new wallet address

First, create the SDK:\
The first argument should be an ethers Web3Provider, since the user will need to sign his Identifier.\
Second argument is which environment and chain contract set to use.

```typescript
import { ClaimSDK } from "@gooddollar/web3sdk-v2"

const sdk = new ClaimSDK(web3provider, "production" | "production-celo")
```

Then, trigger the signing request and get the link to redirect the user to the FaceVerification process and either open the link in a popup or redirect the user.

```typescript
const firstName = "John"
const callbackUrl = "https://mywebsite.com/redirectBackAfterFV" // for native mobile this should be a deeplink
const popupMode = false
const chainId = 42220 // or 122 for fuse. 
try {
 const link = await sdk.generateFVLink(firstName,callbackUrl,popupMode, chainId)
 if(popupMode)
  window.open(link)
 else window.location = link
}
catch(e) {
  console.log("User didn't sign his identifier")
}
```

#### Options

```typescript
function generateFVLink(firstName: string, callbackUrl?: string, popupMode = false, chainId?: number)
```

* firstName - Display only. Used to greet user on the face verification screen.
* callbackUrl (optional defaults to current window location) - In case of popupMode is true, then a POST call will be made to the callbackUrl. Otherwise, the user will be redirected to the callbackUrl.
* popupMode (optional defaults to false)
  * If false, it is assumed user was redirected to the FaceVerification process and he will be redirected back to the callbackUrl with result params encoded in query string.&#x20;
  * False should be used for mobile together with a deeplink callback.
  * If true it is assumed a popup window/tab was opened with the FaceVerification link. Once user finishes FV it will try to close the popup and make a POST call to the callback url with JSON encoded params in body.
* chainId (optional) - Addresses will always be registered on all active chains. This simply marks on which chain the user was originally from. It can be used for invite campaigns and to prevent claiming invite rewards on multiple chains.

#### Callback Params

The callbackUrl will be called with two params containing the result of the FV process.

* isVerified - true if user passed FV, false otherwise
* reason - If isVerified is false this can contain an error message.

### Query the status of a wallet address

Use the isAddressVerified method to query the status of a wallet directly from the [Identity](broken://pages/s7QvNTzyiLioWJl1i3Kb) smart contract.

```typescript
const isVerified = await sdk.isAddressVerified("0x66582D24FEaD72555adaC681Cc621caCbB208324")
```

### Delete an identity record and unregister a wallet

Since no connection is kept between the identity record and a user's wallet in our database, to delete an identity the user has to send to our server his unique identifier (generated by signing a message).\
The backend will then unregister the wallet from the Identity contracts on all active chains.\
info

{% hint style="info" %}
The user identity record will be deleted after 24 hours to prevent fraud. After 24 hours the user will also be able to register again.
{% endhint %}

```typescript
const { success, error } = await sdk.deleteFVRecord()
```

### React hooks

You can also use our react hooks to manage identity.

See the Claim/Identity react hooks code [here](https://github.com/GoodDollar/GoodWeb3-Mono/blob/master/packages/sdk-v2/src/sdk/claim/react.ts).\
Storybook examples [here](https://github.com/GoodDollar/GoodWeb3-Mono/tree/master/packages/sdk-v2/src/stories/claim).\
You will need to first setup our context provider as explained [here](/for-developers/developer-guides/ethers-v5-usedapp-context-setup).

## Win Rewards: Building something on GoodDollar!

There are various ways to earn rewards while working within the GoodDollar Ecosystem.\
\
*Scoutgame:*\
Scoutgame rewards builders who take up pre-defined tasks.\
Contribute to GoodDollar repositories and earn bounty rewards!\
More information about the program can be found on our ScoutGame[ page.](https://scoutgame.xyz/info/partner-rewards/gooddollar)\
\
*GoodDollar OpenSource Contributors Pool:*\
The GoodDollar OpenSource Contributors pool is for anyone who wants to contribute more autonomously.\
Maybe you have ideas of your own to build into GoodDapp or GoodCollective?\
Maybe you have ideas for expanding the core protocol?\
Please read up on our [GoodDollar OpenSource Contributors](https://app.gardens.fund/gardens/42220/0x62b8b11039fcfe5ab0c56e502b1c372a3d2a9c7a/0xf42c9ca2b10010142e2bac34ebdddb0b82177684/94) covenant on how to participate and apply.\
\
*GoodBuilders program:*\
Be sure to check out the [GoodBuilders Program!](https://ubi.gd/goodbuilders) offering mentorship and funding to support promising projects in their growth. Any project that demonstrates meaningful new integrations with the GoodDollar Protocol is eligible to apply!\
\
**Share your ideas, or ask for development support:**\
For discussion on Discord or various program events: [GoodDollar Builders](https://t.me/gooddollarbounties)\
We are also on Discord:  [GoodDollar Discord Development](https://discord.gg/B4bj9eXuWU)


# Identity (Viem/Wagmi)

For a live demo of the identity integration (using development identity contracts), visit: [Demo Identity App](https://demo-identity-app.vercel.app/)

#### Contracts

```javascript
    production: {
      celo: "https://celoscan.io/address/0xC361A6E67822a0EDc17D899227dd9FC50BD62F42",
      fuse: "https://explorer.fuse.io/address/0x2F9C28de9e6d44b71B91b8BA337A5D82e308E7BE",
    },
    staging: {
      celo: "https://celoscan.io/address/0x0108BBc09772973aC27983Fc17c7D82D8e87ef4D",
      fuse: "https://explorer.fuse.io/address/0xb0cD4828Cc90C5BC28f4920Adf2Fd8F025003D7E",
    },
    development: {
      celo: "https://celoscan.io/address/0xF25fA0D4896271228193E782831F6f3CFCcF169C",
      fuse: "https://explorer.fuse.io/address/0x1e006225cff7d37411db28f652e0Da9D20325eBb",
    }
```

### Installation

To integrate `identity-sdk` into your project, you can easily install it from npm:

```bash
npm install @goodsdks/citizen-sdk
```

or if you prefer using Yarn:

```bash
yarn add @goodsdks/citizen-sdk
```

**Available Methods in the Identity SDK:**

* `getWhitelistedRoot(account: Address): Promise<{ isWhitelisted: boolean; root: Address }>`
* `getIdentityExpiryData(account: Address): Promise<IdentityExpiryData>`
* `generateFVLink(popupMode?: boolean, callbackUrl?: string, chainId?: number): Promise<string>`
* `submitAndWait(params: SimulateContractParameters, onHash?: (hash:` 0x${string}`) => void): Promise<any>`
* `calculateIdentityExpiry(lastAuthenticated: bigint, authPeriod: bigint): IdentityExpiry`

#### Using the Wagmi SDK

The Identity SDK is built on top of `Wagmi` and provides a React hook for interacting with the Identity smart contracts. It abstracts the complexity of blockchain interactions, making it easier to integrate identity functionalities into your React applications.

**Initialization**

First, ensure that you have set up `Wagmi` in your React application. Then, import and use the `useIdentitySDK` hook as shown below.

```typescript
import React from 'react';
import { WagmiProvider } from 'wagmi';
import { useIdentitySDK } from '@goodsdks/citizen-sdk';

const IdentityComponent = () => {
  const identitySDK = useIdentitySDK('production');

  const checkWhitelistedRoot = async (account: string) => {
    try {
      const { isWhitelisted, root } = await identitySDK.getWhitelistedRoot(account);
      console.log(`Is Whitelisted: ${isWhitelisted}, Root: ${root}`);
    } catch (error) {
      console.error(error);
    }
  };

  return (
    <div>
      <button onClick={() => checkWhitelistedRoot('0xYourEthereumAddress')}>
        Check Whitelisted Root
      </button>
    </div>
  );
};

const App = () => (
  <WagmiProvider>
    <IdentityComponent />
  </WagmiProvider>
);
```

#### Using the Viem SDK

The Viem SDK provides a set of utility functions to interact directly with the Identity smart contracts. It is suitable for backend services or environments where React is not used.

**Initialization**

```typescript
import { PublicClient, WalletClient } from "viem"
import { initializeIdentityContract, IdentitySDK } from "./viem-sdk"

const publicClient = new PublicClient({
  /* configuration */
})
const walletClient = new WalletClient({
  /* configuration */
})
const contractAddress = "0xYourContractAddress"

const identitySDK = new IdentitySDK(publicClient, walletClient, "production")
```

### References

* [GoodSdks](https://github.com/GoodDollar/GoodSdks)
* [Viem Documentation](https://viem.sh/)
* [Wagmi Documentation](https://wagmi.sh/)
* [OpenZeppelin Contracts](https://docs.openzeppelin.com/contracts/)
* [IdentityV2 Smart Contract](https://github.com/GoodDollar/GoodProtocol/blob/master/contracts/identity/IdentityV2.sol)
* [Live Demo Identity App](https://demo-identity-app.vercel.app/)


# Core Contracts

## Abstract

GoodDollar Protocol is deployed on Celo, XDC, Fuse and Ethereum. Reserve contracts are deployed both on XDC and Celo. UBIScheme are on the Fuse, Celo and XDC. Certain contracts, such as the DAO and G$ Token contracts, are deployed on all networks.

{% hint style="info" %}
For the complete list of contracts, including those in the staging and dev environments, please refer to [GitHub.](https://github.com/GoodDollar/GoodProtocol/blob/master/releases/deployment.json)
{% endhint %}

### Core Contracts

#### [GoodDollar ERC20](/for-developers/core-contracts/gooddollar)

GoodDollar is the ERC20 and also a streamable pure [Supertoken](https://superfluid.org/) on Celo

* Mainnet: [0x67C5870b4A41D4Ebef24d2456547A03F1f3e094B](https://etherscan.io/address/0x67C5870b4A41D4Ebef24d2456547A03F1f3e094B)
* Fuse: [0x495d133B938596C9984d462F007B676bDc57eCEC](https://explorer.fuse.io/address/0x495d133B938596C9984d462F007B676bDc57eCEC/transactions)
* Celo: [0x62B8B11039FcfE5aB0C56E502b1C372A3d2a9c7A](https://explorer.celo.org/mainnet/address/0x62B8B11039FcfE5aB0C56E502b1C372A3d2a9c7A)
* XDC: [0xEC2136843a983885AebF2feB3931F73A8eBEe50c](https://xdcscan.com/address/0xec2136843a983885aebf2feb3931f73a8ebee50c)
* Source
  * [GoodDollar.sol](https://github.com/GoodDollar/GoodContracts/blob/master/contracts/token/GoodDollar.sol) (Fuse / Ethereum)
  * [SuperGoodDollar.sol](https://github.com/GoodDollar/GoodProtocol/blob/master/contracts/token/superfluid/SuperGoodDollar.sol) (Celo / Xdc)

#### [ContributionCalculation](/for-developers/core-contracts/contributioncalculation)

* Mainnet: [0x8eEC64bb6807c0178f96277cCE6a334B4e565E5C](https://etherscan.io/address/0x8eEC64bb6807c0178f96277cCE6a334B4e565E5C)
* Fuse: not deployed
* Celo: not deployed
* XDC: not deployed
* Source: [ContributionCalculation.sol](https://github.com/GoodDollar/GoodContracts/blob/master/stakingModel/contracts/ContributionCalculation.sol)

#### [UBIScheme](/for-developers/core-contracts/ubischeme)

* Mainnet: not deployed
* Fuse: [0xd253A5203817225e9768C05E5996d642fb96bA86](https://explorer.fuse.io/address/0xd253A5203817225e9768C05E5996d642fb96bA86/transactions)
* Celo: [0x43d72Ff17701B2DA814620735C39C620Ce0ea4A1](https://explorer.celo.org/mainnet/address/0x43d72Ff17701B2DA814620735C39C620Ce0ea4A1)
* XDC: [0x22867567E2D80f2049200E25C6F31CB6Ec2F0faf](https://xdcscan.com/address/0x22867567e2d80f2049200e25c6f31cb6ec2f0faf)
* Source: [UBIScheme.sol](https://github.com/GoodDollar/GoodProtocol/blob/master/contracts/ubi/UBIScheme.sol)

#### [Identity](/for-developers/core-contracts/identity)

* Mainnet: [0x76e76e10Ac308A1D54a00f9df27EdCE4801F288b](https://etherscan.io/address/0x76e76e10Ac308A1D54a00f9df27EdCE4801F288b)
* Fuse: [0xFa8d865A962ca8456dF331D78806152d3aC5B84F](https://explorer.fuse.io/address/0xFa8d865A962ca8456dF331D78806152d3aC5B84F/transactions)
* Celo: [0xC361A6E67822a0EDc17D899227dd9FC50BD62F42](https://explorer.celo.org/mainnet/address/0xC361A6E67822a0EDc17D899227dd9FC50BD62F42)
* XDC: [0x27a4a02C9ed591E1a86e2e5D05870292c34622C9](https://xdcscan.com/address/0x27a4a02c9ed591e1a86e2e5d05870292c34622c9)
* Source: [Identity.sol](https://github.com/GoodDollar/GoodProtocol/blob/master/contracts/identity/IdentityV2.sol)

#### [OneTimePayments](/for-developers/core-contracts/onetimepayments)

* Mainnet: not deployed
* Fuse: [0xd9Aa86e0Ddb932bD78ab8c71C1B98F83cF610Bd4](https://explorer.fuse.io/address/0xd9Aa86e0Ddb932bD78ab8c71C1B98F83cF610Bd4/transactions)
* Celo: [0xB27D247f5C2a61D2Cb6b6E67FEE51d839447e97d](https://celoscan.io/address/0xB27D247f5C2a61D2Cb6b6E67FEE51d839447e97d)
* XDC: not deployed
* Source: [OneTimePayments.sol](https://github.com/GoodDollar/GoodContracts/blob/master/contracts/dao/schemes/OneTimePayments.sol)

#### [NameService](/for-developers/core-contracts/nameservice)

* Mainnet: [0xec6dcE387B1616a0c44fF2E4fA9E90E53Cf14eb0](https://etherscan.io/address/0xec6dcE387B1616a0c44fF2E4fA9E90E53Cf14eb0)
* Fuse: [0xec6dcE387B1616a0c44fF2E4fA9E90E53Cf14eb0](https://explorer.fuse.io/address/0xec6dcE387B1616a0c44fF2E4fA9E90E53Cf14eb0/transactions)
* Celo: [0x0F5dB7a64A6a64052693676CA898EC7F7A94FF4e](https://explorer.celo.org/mainnet/address/0x0F5dB7a64A6a64052693676CA898EC7F7A94FF4e)
* XDC: [0x1e5154Bf5e31FF56051bbd45958b879Fb7a290FE](https://xdcscan.com/address/0x1e5154bf5e31ff56051bbd45958b879fb7a290fe)
* Source: [NameService.sol](https://github.com/GoodDollar/GoodProtocol/blob/master/contracts/utils/NameService.sol)

#### [Faucet](/for-developers/core-contracts/faucet)

* Mainnet: not deployed
* Fuse: [0x01ab5966C1d742Ae0CFF7f14cC0F4D85156e83d9](https://explorer.fuse.io/address/0x01ab5966C1d742Ae0CFF7f14cC0F4D85156e83d9/transactions)
* Celo: [0x4F93Fa058b03953C851eFaA2e4FC5C34afDFAb84](https://celoscan.io/address/0x4F93Fa058b03953C851eFaA2e4FC5C34afDFAb84)
* XDC: [0x7344Da1Be296f03fbb8082aDaC5696058B5a9bd9](https://xdcscan.com/address/0x7344da1be296f03fbb8082adac5696058b5a9bd9)
* Source: [Faucet.sol](https://github.com/GoodDollar/GoodProtocol/blob/master/contracts/fuseFaucet/Faucet.sol)

#### [MentoReserve](/for-developers/core-contracts/mentoreserve)

* Mainnet: not deployed
* Fuse: not deployed
* Celo: [0x94A3240f484A04F5e3d524f528d02694c109463b](https://celoscan.io/address/0x94A3240f484A04F5e3d524f528d02694c109463b)
* XDC: [0x94A3240f484A04F5e3d524f528d02694c109463b](https://celoscan.io/address/0x94A3240f484A04F5e3d524f528d02694c109463b)
* Source: [Reserve.sol](https://github.com/GoodDollar/mento-core/blob/develop/contracts/swap/Reserve.sol)

#### [MentoExpansionController](/for-developers/core-contracts/mentoexpansioncontroller)

* Mainnet: not deployed
* Fuse: not deployed
* Celo: [0x94A3240f484A04F5e3d524f528d02694c109463b](https://celoscan.io/address/0x94A3240f484A04F5e3d524f528d02694c109463b)
* XDC: [0x94A3240f484A04F5e3d524f528d02694c109463b](https://celoscan.io/address/0x94A3240f484A04F5e3d524f528d02694c109463b)
* Source: [GoodDollarExpansionController.sol](https://github.com/GoodDollar/mento-core/blob/develop/contracts/goodDollar/GoodDollarExpansionController.sol)

#### [MentoExchangeProvider](/for-developers/core-contracts/mentoexchangeprovider)

* Mainnet: not deployed
* Fuse: not deployed
* Celo: [0x94A3240f484A04F5e3d524f528d02694c109463b](https://celoscan.io/address/0x94A3240f484A04F5e3d524f528d02694c109463b)
* XDC: [0x94A3240f484A04F5e3d524f528d02694c109463b](https://celoscan.io/address/0x94A3240f484A04F5e3d524f528d02694c109463b)
* Source: [GoodDollarExchangeProvider.sol](https://github.com/GoodDollar/mento-core/blob/develop/contracts/goodDollar/GoodDollarExchangeProvider.sol)

#### [MentoBroker](/for-developers/core-contracts/mentobroker)

* Mainnet: not deployed
* Fuse: not deployed
* Celo: [0x94A3240f484A04F5e3d524f528d02694c109463b](https://celoscan.io/address/0x94A3240f484A04F5e3d524f528d02694c109463b)
* XDC: [0x94A3240f484A04F5e3d524f528d02694c109463b](https://celoscan.io/address/0x94A3240f484A04F5e3d524f528d02694c109463b)
* Source: [Broker.sol](https://github.com/GoodDollar/mento-core/blob/develop/contracts/swap/Broker.sol)

### Bridge Contracts

* MessagePassingBridge
  * Mainnet: [0xa3247276DbCC76Dd7705273f766eB3E8a5ecF4a5](https://etherscan.io/address/0xa3247276dbcc76dd7705273f766eb3e8a5ecf4a5)
  * Fuse: [0xa3247276DbCC76Dd7705273f766eB3E8a5ecF4a5](https://explorer.fuse.io/address/0xa3247276DbCC76Dd7705273f766eB3E8a5ecF4a5)
  * Celo: [0xa3247276DbCC76Dd7705273f766eB3E8a5ecF4a5](https://celo.blockscout.com/address/0xa3247276DbCC76Dd7705273f766eB3E8a5ecF4a5)
  * XDC: [0xa3247276DbCC76Dd7705273f766eB3E8a5ecF4a5](https://xdcscan.com/address/0xa3247276DbCC76Dd7705273f766eB3E8a5ecF4a5)
  * Source: [MessagePassingBridge.sol](https://github.com/GoodDollar/GoodBridge/blob/master/packages/bridge-contracts/contracts/messagePassingBridge/MessagePassingBridge.sol)

### DAO Contracts

DAO contracts were developed by [DAOStack](https://daostack.io)

* Controller
  * Mainnet: [0x95C0d9dCEA1E243ED696F34CAc5e6559C3c128a3](https://etherscan.io/address/0x95C0d9dCEA1E243ED696F34CAc5e6559C3c128a3)
  * Fuse: [0xBcE053b99e22158f8B62f4DBFbEdE1f936b2D4e4](https://explorer.fuse.io/address/0xBcE053b99e22158f8B62f4DBFbEdE1f936b2D4e4)
  * Celo: [0x0be7C592374EE0bD0CcBFC76Be758a138BcaEc6E](https://explorer.celo.org/mainnet/address/0x0be7C592374EE0bD0CcBFC76Be758a138BcaEc6E)
  * XDC: [0x75a8bE0C2dEaDEd8Fc9ECEB5F01ad0B979b7AD03](https://xdcscan.com/address/0x75a8be0c2deaded8fc9eceb5f01ad0b979b7ad03)
  * Source: [Controller.sol](http://github.com/daostack/arc/tree/master/contracts/controller/Controller.sol)
* Avatar
  * Mainnet: [0x1ecFD1afb601C406fF0e13c3485f2d75699b6817](https://etherscan.io/address/0x1ecFD1afb601C406fF0e13c3485f2d75699b6817)
  * Fuse: [0xf96dADc6D71113F6500e97590760C924dA1eF70e](https://explorer.fuse.io/address/0xf96dADc6D71113F6500e97590760C924dA1eF70e)
  * Celo: [0x495d133B938596C9984d462F007B676bDc57eCEC](https://explorer.celo.org/mainnet/address/0x495d133B938596C9984d462F007B676bDc57eCEC)
  * XDC: [0x21eaC3fE218307BeE0463F77EBcA3b50F452C0Ce](https://xdcscan.com/address/0x21eac3fe218307bee0463f77ebca3b50f452c0ce)
  * Source: [Avatar.sol](http://github.com/daostack/arc/tree/master/contracts/controller/Avatar.sol)


# GoodDollar

The GoodDollar G$ token follows the ERC-20 token standard and also supports ERC-677.

### Events

#### Transfer

Emitted when `value` tokens are moved from one account (`from`) to another (`to`).

<table><thead><tr><th width="150">Parameter name</th><th>Annotation</th></tr></thead><tbody><tr><td>from</td><td>The address from which tokens are moved.</td></tr><tr><td>to</td><td>The address to which tokens are moved.</td></tr><tr><td>value</td><td>The value to be processed and then transferred.</td></tr></tbody></table>

Note that `value` may be zero.

```
event Transfer(address indexed from, address indexed to, uint256 value);
```

#### Approval

Emitted when the allowance of a `spender` for an `owner` is set by a call to {approve}. `value` is the new allowance.

<table><thead><tr><th width="150">Parameter name</th><th>Annotation</th></tr></thead><tbody><tr><td>owner</td><td>The address of the tokens owner.</td></tr><tr><td>spender</td><td>The address which can spend tokens in allowance.</td></tr><tr><td>value</td><td>The tokens amount to be spent on behave of the tokens owner.</td></tr></tbody></table>

```
event Approval(address indexed owner, address indexed spender, uint256 value);
```

### transfer

Processes fees from given value and sends remainder to given address.

<table><thead><tr><th width="150">Parameter name</th><th>Annotation</th></tr></thead><tbody><tr><td>to</td><td>The address to be sent to.</td></tr><tr><td>value</td><td>The value to be processed and then transferred.</td></tr></tbody></table>

Returns: a boolean that indicates if the operation was successful.

```
function transfer(address to, uint256 value) public returns (bool);
```

### approve

Approve the passed address to spend the specified amount of tokens on behalf of `msg.sender`.

<table><thead><tr><th width="150">Parameter name</th><th>Annotation</th></tr></thead><tbody><tr><td>spender</td><td>The address which will spend the funds.</td></tr><tr><td>value</td><td>The amount of tokens to be spent.</td></tr></tbody></table>

Returns: a boolean that indicates if the operation was successful.

```
function approve(address spender, uint256 value) public returns (bool);
```

### transferFrom

Transfer tokens from one address to another on behalf of the third party as `msg.sender`.

<table><thead><tr><th width="150">Parameter name</th><th>Annotation</th></tr></thead><tbody><tr><td>from</td><td>The address which you want to send tokens from.</td></tr><tr><td>to</td><td>The address which you want to transfer to.</td></tr><tr><td>value</td><td>The amount of tokens to be transferred.</td></tr></tbody></table>

Returns: a boolean that indicates if the operation was successful.

```
function transferFrom(
        address from,
        address to,
        uint256 value
    ) public returns (bool);
```

### transferAndCall

Processes transfer fees and calls ERC677Token transferAndCall function.

<table><thead><tr><th width="150">Parameter name</th><th>Annotation</th></tr></thead><tbody><tr><td>from</td><td>The address to transfer to.</td></tr><tr><td>value</td><td>The amount to transfer.</td></tr><tr><td>data</td><td>The data to be used in further execution according to ERC677.</td></tr></tbody></table>

Returns: a boolean that indicates if the operation was successful.

```
function transferAndCall(
        address to,
        uint256 value,
        bytes calldata data
    ) external returns (bool);
```

### mint

Minting function.

<table><thead><tr><th width="150">Parameter name</th><th>Annotation</th></tr></thead><tbody><tr><td>to</td><td>The address that will receive the minted tokens. Must be out of blocklist. The blocklist is managed by the administrator of the contract.</td></tr><tr><td>value</td><td>Value the amount of tokens to mint.</td></tr></tbody></table>

Who can execute: An address who is in minter role.

Returns: a boolean that indicates if the operation was successful.

```
function mint(address to, uint256 value) public;
```

### burn

Burns a specific amount of tokens.

<table><thead><tr><th width="150">Parameter name</th><th>Annotation</th></tr></thead><tbody><tr><td>value</td><td>The amount of token to be burned..</td></tr></tbody></table>

Who can execute: An address who is not blocklisted by the administration.

```
function burn(uint256 value) public;
```

### burnFrom

Burns a specific amount of tokens from the target address and decreases an allowance.

<table><thead><tr><th width="150">Parameter name</th><th>Annotation</th></tr></thead><tbody><tr><td>from</td><td>The address which you want to burn tokens from. Must not be in blocklist.</td></tr><tr><td>value</td><td>The amount of token to be burned.</td></tr></tbody></table>

Who can execute: An address who is not blocklisted by the administration.

```
function burnFrom(address from, uint256 value) public;
```

### increaseAllowance

Increase the amount of tokens that an owner allows a spender.

<table><thead><tr><th width="150">Parameter name</th><th>Annotation</th></tr></thead><tbody><tr><td>spender</td><td>The address which will spend the funds.</td></tr><tr><td>addedValue</td><td>The amount of tokens to increase the allowance by.</td></tr></tbody></table>

Returns: a boolean that indicates if the operation was successful.

```
function increaseAllowance(address spender, uint256 addedValue) public returns (bool);
```

### decreaseAllowance

Decrease the amount of tokens that an owner allowed to a spender.

<table><thead><tr><th width="150">Parameter name</th><th>Annotation</th></tr></thead><tbody><tr><td>spender</td><td>The address which will spend the funds.</td></tr><tr><td>subtractedValue</td><td>The amount of tokens to decrease the allowance by.</td></tr></tbody></table>

Returns: a boolean that indicates if the operation was successful.

```
function decreaseAllowance(address spender, uint256 subtractedValue) public returns (bool);
```

### getFees

Gets the current transaction fees.

<table><thead><tr><th width="150">Parameter name</th><th>Annotation</th></tr></thead><tbody><tr><td>value</td><td>Value the amount of tokens to mint.</td></tr></tbody></table>

Returns: tuple of `uint256` and `bool`, first is an absolute amount of fees based on value and the second is whether `msg.sender` paying or not.

```
function getFees(uint256 value) public view returns (uint256, bool);
```

### setFeeRecipient

Sets the address that receives the transactional fees.

<table><thead><tr><th width="150">Parameter name</th><th>Annotation</th></tr></thead><tbody><tr><td>_feeRecipient</td><td>The new address to receive transactional fees.</td></tr></tbody></table>

Who can execute: An adminstrator only.

```
function setFeeRecipient(address _feeRecipient) public;
```


# Identity

The Identity contract controls addresses that are whitelisted to "Claim" UBI.

* **Face Verification** GoodDollar currently whitelists users based on a user proving "uniqueness" by signing up with a live and unique face. All image data and details are anonymized in order to allow the user to create a new account in case he is unable to recover his wallet. Facial details are deleted after `authenticationPeriod` and users are required to perform face verification again every `authenticationPeriod` days.
* **Social Profile** Each blockchain address is linked to the user's public profile as created in the wallet. The DID is the node id in the public p2p GunDB database. Mappings from wallet address to DID are held in `addrToDID`.

### Events

#### BlacklistAdded

Emitted when the address is added to blacklist.

<table><thead><tr><th width="285.809320129277">Parameter name</th><th>Annotation</th></tr></thead><tbody><tr><td>account</td><td>The address of the account to add.</td></tr></tbody></table>

```
event BlacklistAdded(address indexed account);
```

#### BlacklistRemoved

Emitted when the address is removed from blacklist.

<table><thead><tr><th width="285.809320129277">Parameter name</th><th>Annotation</th></tr></thead><tbody><tr><td>account</td><td>The address of the account to remove.</td></tr></tbody></table>

```
event BlacklistRemoved(address indexed account);
```

#### WhitelistedRemoved

Emitted when the address is removed from whitelist.

<table><thead><tr><th width="285.809320129277">Parameter name</th><th>Annotation</th></tr></thead><tbody><tr><td>account</td><td>The address of the account to remove.</td></tr></tbody></table>

```
event WhitelistedRemoved(address indexed account);
```

#### WhitelistedAdded

Emitted when the address is added to whitelist.

<table><thead><tr><th width="285.809320129277">Parameter name</th><th>Annotation</th></tr></thead><tbody><tr><td>account</td><td>The address of the account to add.</td></tr></tbody></table>

```
event WhitelistedAdded(address indexed account);
```

#### ContractAdded

Emitted when the contract address is added to whitelist.

<table><thead><tr><th width="285.809320129277">Parameter name</th><th>Annotation</th></tr></thead><tbody><tr><td>account</td><td>The address of the contract to add.</td></tr></tbody></table>

```
event ContractAdded(address indexed account);
```

#### ContractRemoved

Emitted when the contract address is removed from the whitelist.

<table><thead><tr><th width="285.809320129277">Parameter name</th><th>Annotation</th></tr></thead><tbody><tr><td>account</td><td>The address of the contract to add.</td></tr></tbody></table>

```
event ContractRemoved(address indexed account);
```

### getWhitelistedRoot

The getWhitelistedRoot function returns the whitelisted address tied to an account: the account itself if whitelisted, the whitelisted account it’s connected to via connectedAccounts, or the zero address (0x0) if neither is whitelisted.

<table><thead><tr><th width="285.809320129277">Parameter name</th><th>Annotation</th></tr></thead><tbody><tr><td>account</td><td>The address to check.</td></tr></tbody></table>

Return&#x73;**:** whitelisted root address, or 0x0

```
function getWhitelistedRoot(address account) external view returns (address whitelisted)
```

### isWhitelisted

The function checks if given address has been added to whitelist.

<table><thead><tr><th width="301.8711599216471">Parameter name</th><th>Annotation</th></tr></thead><tbody><tr><td>account</td><td>The address to check.</td></tr></tbody></table>

Returns: a boolean indicating weather the address is present in whitelist.

```
function isWhitelisted(address account) public view returns (bool);
```

**Note on connected wallets:** A connected wallet will not itself be whitelisted and isWhitelisted will return false. The only way to check if an address is connected, use `getWhitelistedRoot`

### lastAuthenticated

Function that gives the date the given user was added.

<table><thead><tr><th width="150">Parameter name</th><th>Annotation</th></tr></thead><tbody><tr><td>account</td><td>The address to check.</td></tr></tbody></table>

Returns: the date the address was added.

```
function lastAuthenticated(address account) public view returns (uint256);
```

### authenticationPeriod

Field that contains the number of days an authentication is valid for.

Returns: a time duration in days.

```
function authenticationPeriod() external view returns (uint256);
```

### addrToDID

Function that gives the DID representation for given address.

<table><thead><tr><th width="150">Parameter name</th><th>Annotation</th></tr></thead><tbody><tr><td>account</td><td>The address to check.</td></tr></tbody></table>

Returns: the string representation of DID

```
function addrToDID(address account) external view returns (string memory);
```


# UBIScheme

Holds all the G$s that were transferred via bridge from the FundManager.

The pool of G$s is divided equally by the amount of current active users, and distributed every day. Each active user can then "claim" his quota. If a user fails to claim his quota it becomes part of the next day's pool of G$ to be distributed as basic income.

### Events

#### WithdrawFromDao

Emits when a withdraw has been succeded.

<table><thead><tr><th width="285.809320129277">Parameter name</th><th>Annotation</th></tr></thead><tbody><tr><td>prevBalance</td><td>The balance before the withdraw.</td></tr><tr><td>newBalance</td><td>The balance after the withdraw.</td></tr></tbody></table>

```
event WithdrawFromDao(uint256 prevBalance, uint256 newBalance);
```

#### ActivatedUser

Emits when a user is activated.

<table><thead><tr><th width="285.809320129277">Parameter name</th><th>Annotation</th></tr></thead><tbody><tr><td>account</td><td>The user that was activated.</td></tr></tbody></table>

```
event ActivatedUser(address indexed account);
```

#### InactiveUserFished

Emits when a `fish` call has been succeded.

<table><thead><tr><th width="285.809320129277">Parameter name</th><th>Annotation</th></tr></thead><tbody><tr><td>caller</td><td>The user that doing "fishing".</td></tr><tr><td>fished_account</td><td>The user that has beed "fished".</td></tr><tr><td>claimAmount</td><td>The amount of tokens caller got for "fishing".</td></tr></tbody></table>

```
event InactiveUserFished(
    address indexed caller,
    address indexed fished_account,
    uint256 claimAmount
);
```

#### TotalFished

Emits when finishing a "multi fish" execution. Indicates the number of users from the given array who actually been fished. It might not be finished going over all the array if there no gas left.

<table><thead><tr><th width="285.809320129277">Parameter name</th><th>Annotation</th></tr></thead><tbody><tr><td>total</td><td>The amount of total user that were "fished".</td></tr></tbody></table>

```
event TotalFished(uint256 total);
```

#### UBICalculated

Emits when daily UBI is calculated.

<table><thead><tr><th width="285.809320129277">Parameter name</th><th>Annotation</th></tr></thead><tbody><tr><td>day</td><td>The timestamp when this event was emitted.</td></tr><tr><td>dailyUbi</td><td>The amount of UBI per daily cycle.</td></tr><tr><td>blockNumber</td><td>The block number when this event was emitted.</td></tr></tbody></table>

```
event UBICalculated(uint256 day, uint256 dailyUbi, uint256 blockNumber);
```

#### UBICycleCalculated

Emits whenever a new multi day cycle starts.

<table><thead><tr><th width="285.809320129277">Parameter name</th><th>Annotation</th></tr></thead><tbody><tr><td>day</td><td>The amount of days from the start when the event was emitted.</td></tr><tr><td>pool</td><td>The balance of the UBI scheme in G$.</td></tr><tr><td>cycleLength</td><td>The duration that used to calculate a frequency of daily cycle pool distribution.</td></tr><tr><td>dailyUBIPool</td><td>The amount of the pool.</td></tr></tbody></table>

```
event UBICycleCalculated(
    uint256 day,
    uint256 pool,
    uint256 cycleLength,
    uint256 dailyUBIPool
);
```

#### UBIClaimed

Emits when someone claims the UBI.

<table><thead><tr><th width="285.809320129277">Parameter name</th><th>Annotation</th></tr></thead><tbody><tr><td>claimer</td><td>The claimer of the UBI user.</td></tr><tr><td>amount</td><td>The amount of the UBI the user gathered after claim reward call.</td></tr></tbody></table>

```
event UBIClaimed(address indexed claimer, uint256 amount);
```

#### CycleLengthSet

Emits when the Avatar sets the cycle length.

<table><thead><tr><th width="285.809320129277">Parameter name</th><th>Annotation</th></tr></thead><tbody><tr><td>newCycleLength</td><td>The duration of the collect UBI cycle..</td></tr></tbody></table>

```
event CycleLengthSet(uint256 newCycleLength);
```

#### CycleLengthSet

Emits when the Avatar sets the cycle length.

<table><thead><tr><th width="285.809320129277">Parameter name</th><th>Annotation</th></tr></thead><tbody><tr><td>newCycleLength</td><td>The duration of the collect UBI cycle..</td></tr></tbody></table>

```
event CycleLengthSet(uint256 newCycleLength);
```

#### DaySet

Emits when the Avatar sets the day.

<table><thead><tr><th width="285.809320129277">Parameter name</th><th>Annotation</th></tr></thead><tbody><tr><td>newDay</td><td>New days amount from the start of the UBI work.</td></tr></tbody></table>

```
event DaySet(uint256 newDay);
```

#### DaySet

Emits when the Avatar sets up he is not eligible for G$.

<table><thead><tr><th width="285.809320129277">Parameter name</th><th>Annotation</th></tr></thead><tbody><tr><td>ShouldWithdrawFromDAO</td><td>Accounts whether to also withdraw G$ from Avatar for UBI.</td></tr></tbody></table>

```
event ShouldWithdrawFromDAOSet(bool ShouldWithdrawFromDAO);
```

### checkEntitlement

Checks the amount which the `_member` address is eligible to claim for, regardless if they have been whitelisted or not. In case the user is active, then the current day must be equal to the actual day, i.e. claim or fish has already been executed today.

<table><thead><tr><th width="298.08152046943655">Parameter name</th><th>Annotation</th></tr></thead><tbody><tr><td>_member</td><td>Potential claimers address.</td></tr></tbody></table>

Returns: the amount of G$ tokens the address can claim.

```
function checkEntitlement(address _member) public view returns (uint256);
```

**Note on connected wallets:** checkEntitlement is based on primary/root whitelisted wallet. To support users who might be claiming using connected wallets, you'll need to verify whitelistRoot using [`getWhitelistedRoot`](/for-developers/core-contracts/identity#getwhitelistedroot) in the identity contract and use the root address to verify the entitlement amount. It does not matter which connected account has claimed for that day.

### claim

Function for claiming UBI. Requires contract to be active and claimer to be whitelisted. Calls `distributionFormula`, calculates the amount the caller can claim, and transfers the amount to the caller.

Returns: a boolean indicating if UBI was claimed.

```
function claim() public returns (bool);
```

### fish

In order to update users from active to inactive, we give out incentive to people to update the status of inactive users, this action is called "Fishing". Anyone can send a tx to the contract to mark inactive users. The "fisherman" receives a reward equal to the daily UBI (i.e. instead of the “fished” user). User that “last claimed” > 14 can be "fished" and made inactive (reduces active users count by one). Requires contract to be active.

<table><thead><tr><th width="298.08152046943655">Parameter name</th><th>Annotation</th></tr></thead><tbody><tr><td>_account</td><td>The account to "fish".</td></tr></tbody></table>

Returns: a bool indicating if UBI was fished.

```
function fish(address _account) public returns (bool);
```

### fishMulti

Executes `fish` with multiple addresses.

<table><thead><tr><th width="298.08152046943655">Parameter name</th><th>Annotation</th></tr></thead><tbody><tr><td>_accounts</td><td>The accounts to "fish".</td></tr></tbody></table>

Returns: a bool indicating if all the UBIs were fished.

```
function fishMulti(address[] memory _accounts) public returns (uint256);
```


# MentoReserve

The contract manages collateral assets and reserve tokens for the Mento protocol exchange system.

## MentoReserve

The contract manages collateral assets for the GoodDollar protocol.&#x20;

### Contract Specs

The MentoReserve contract is a critical component of GoodDollar's reserve-backed token system. GoodDollar (G$) is a Universal Basic Income (UBI) token that provides daily distributions to verified users. The reserve holds collateral assets (such as CUSD on Celo, USDC on XDC, or native tokens) that back the value of GoodDollar tokens and enable the exchange mechanism.

### Events

#### TokenAdded

Emitted when a new token is added to the reserve for stabilization.

| Parameter name | Annotation                                           |
| -------------- | ---------------------------------------------------- |
| `token`        | The address of the token being added to the reserve. |

**When emitted:** This event is emitted when the owner calls `addToken()` to register a new stable token that the reserve will stabilize.

```solidity
event TokenAdded(address indexed token);
```

#### TokenRemoved

Emitted when a token is removed from the reserve and will no longer be stabilized.

| Parameter name | Annotation                                                         |
| -------------- | ------------------------------------------------------------------ |
| `token`        | The address of the token being removed from the reserve.           |
| `index`        | The index of the token in the tokens array at the time of removal. |

**When emitted:** This event is emitted when the owner calls `removeToken()` to deregister a stable token from the reserve.

```solidity
event TokenRemoved(address indexed token, uint256 index);
```

#### CollateralAssetAdded

Emitted when a new collateral asset is added to the reserve.

| Parameter name    | Annotation                                                      |
| ----------------- | --------------------------------------------------------------- |
| `collateralAsset` | The address of the collateral asset being added to the reserve. |

**When emitted:** This event is emitted when the owner calls `addCollateralAsset()` to register a new collateral asset (such as CUSD, USDC, or other ERC20 tokens) that can be used to back GoodDollar tokens.

```solidity
event CollateralAssetAdded(address collateralAsset);
```

#### CollateralAssetRemoved

Emitted when a collateral asset is removed from the reserve.

| Parameter name    | Annotation                                                          |
| ----------------- | ------------------------------------------------------------------- |
| `collateralAsset` | The address of the collateral asset being removed from the reserve. |

**When emitted:** This event is emitted when the owner calls `removeCollateralAsset()` to deregister a collateral asset from the reserve.

```solidity
event CollateralAssetRemoved(address collateralAsset);
```

### Functions

#### getTokens

Returns array of all registered tokens in the reserve.

**Returns:** Array of all registered token addresses in the reserve.

```solidity
function getTokens() external view returns (address[] memory);
```

#### isStableAsset

Checks if an asset is a stable asset.

| Parameter name | Annotation                         |
| -------------- | ---------------------------------- |
| `asset`        | The address of the asset to check. |

**Returns:** True if the asset is a stable asset, false otherwise.

```solidity
function isStableAsset(address asset) external view returns (bool);
```

#### isCollateralAsset

Checks if an asset is a collateral asset.

| Parameter name | Annotation                         |
| -------------- | ---------------------------------- |
| `asset`        | The address of the asset to check. |

**Returns:** True if the asset is a collateral asset, false otherwise.

```solidity
function isCollateralAsset(address asset) external view returns (bool);
```

#### isExchangeSpender

Checks if an address is an authorized exchange spender.

| Parameter name | Annotation            |
| -------------- | --------------------- |
| `exchange`     | The address to check. |

**Returns:** True if the address is an authorized exchange spender, false otherwise.

```solidity
function isExchangeSpender(address exchange) external view returns (bool);
```

#### isSpender

Checks if an address is an authorized spender.

| Parameter name | Annotation            |
| -------------- | --------------------- |
| `spender`      | The address to check. |

**Returns:** True if the address is an authorized spender, false otherwise.

```solidity
function isSpender(address spender) external view returns (bool);
```

#### getExchangeSpenders

Returns array of all exchange spender addresses.

**Returns:** Array of all exchange spender addresses.

```solidity
function getExchangeSpenders() external view returns (address[] memory);
```


# MentoExpansionController

The contract controls how new GoodDollar tokens are minted and distributed for UBI.

## MentoExpansionController

The contract controls how new GoodDollar tokens are minted and distributed for UBI.

### Contract Specs

The MentoExpansionController is the heart of GoodDollar's UBI (Universal Basic Income) distribution mechanism. It controls how new GoodDollar tokens are minted and distributed to users. The contract generates UBI tokens through two primary mechanisms: (1) interest earned on reserve collateral, and (2) expansion based on configured rates. These newly minted tokens are then distributed to verified users through the distribution helper, fulfilling GoodDollar's mission of providing universal basic income.

### Events

#### ExpansionConfigSet

Emitted when the expansion config is set for an exchange.

| Parameter name       | Annotation                                                |
| -------------------- | --------------------------------------------------------- |
| `exchangeId`         | The ID of the exchange.                                   |
| `expansionRate`      | The rate of expansion in percentage with 1e18 being 100%. |
| `expansionfrequency` | The frequency of expansion in seconds.                    |

```solidity
event ExpansionConfigSet(
    bytes32 indexed exchangeId,
    uint64 expansionRate,
    uint32 expansionfrequency
);
```

#### RewardMinted

Emitted when a reward is minted.

| Parameter name | Annotation                                  |
| -------------- | ------------------------------------------- |
| `exchangeId`   | The ID of the exchange.                     |
| `to`           | The address of the recipient of the reward. |
| `amount`       | The amount of G$ tokens minted as reward.   |

```solidity
event RewardMinted(
    bytes32 indexed exchangeId,
    address indexed to,
    uint256 amount
);
```

#### InterestUBIMinted

Emitted when UBI is minted through collecting reserve interest.

| Parameter name | Annotation                                           |
| -------------- | ---------------------------------------------------- |
| `exchangeId`   | The ID of the exchange.                              |
| `amount`       | The amount of G$ tokens minted as UBI from interest. |

```solidity
event InterestUBIMinted(bytes32 indexed exchangeId, uint256 amount);
```

#### ExpansionUBIMinted

Emitted when UBI is minted through expansion.

| Parameter name | Annotation                                            |
| -------------- | ----------------------------------------------------- |
| `exchangeId`   | The ID of the exchange.                               |
| `amount`       | The amount of G$ tokens minted as UBI from expansion. |

```solidity
event ExpansionUBIMinted(bytes32 indexed exchangeId, uint256 amount);
```

### Functions

#### setExpansionConfig

Sets the expansion configuration for the given exchange. The expansion rate is in percentage with 1e18 being 100%, and expansion frequency is in seconds.

| Parameter name       | Annotation                                                |
| -------------------- | --------------------------------------------------------- |
| `exchangeId`         | The ID of the exchange to set the expansion config for.   |
| `expansionRate`      | The rate of expansion in percentage with 1e18 being 100%. |
| `expansionFrequency` | The frequency of expansion in seconds.                    |

```solidity
function setExpansionConfig(
    bytes32 exchangeId,
    uint64 expansionRate,
    uint32 expansionFrequency
) external;
```

#### mintUBIFromInterest

Mints UBI for the given exchange from collecting reserve interest. Calls the exchange provider's mintFromInterest and distributes minted tokens through the distribution helper.

| Parameter name    | Annotation                                            |
| ----------------- | ----------------------------------------------------- |
| `exchangeId`      | The ID of the exchange to mint UBI for.               |
| `reserveInterest` | The amount of reserve tokens collected from interest. |

```solidity
function mintUBIFromInterest(
    bytes32 exchangeId,
    uint256 reserveInterest
) external;
```

#### mintUBIFromReserveBalance

Mints UBI for the given exchange by comparing the actual reserve balance of the contract to the virtual balance. Calculates the difference and mints tokens accordingly.

| Parameter name | Annotation                              |
| -------------- | --------------------------------------- |
| `exchangeId`   | The ID of the exchange to mint UBI for. |

**Returns:** The amount of G$ tokens minted.

```solidity
function mintUBIFromReserveBalance(
    bytes32 exchangeId
) external returns (uint256 amountMinted);
```

#### mintUBIFromExpansion

Mints UBI for the given exchange by calculating the expansion rate. Checks if expansionFrequency time has passed since lastExpansion, calculates expansion scaler, and mints tokens accordingly.

| Parameter name | Annotation                              |
| -------------- | --------------------------------------- |
| `exchangeId`   | The ID of the exchange to mint UBI for. |

**Returns:** The amount of G$ tokens minted.

```solidity
function mintUBIFromExpansion(
    bytes32 exchangeId
) external returns (uint256 amountMinted);
```

#### mintRewardFromRR

Mints a reward amount of tokens for a specific recipient. Updates the reserve ratio through the exchange provider and mints tokens directly to the recipient address.

| Parameter name | Annotation                                  |
| -------------- | ------------------------------------------- |
| `exchangeId`   | The ID of the exchange.                     |
| `to`           | The address of the recipient of the reward. |
| `amount`       | The amount of G$ tokens to mint as reward.  |

```solidity
function mintRewardFromRR(
    bytes32 exchangeId,
    address to,
    uint256 amount
) external;
```


# MentoExchangeProvider

The contract implements the core exchange mechanism for GoodDollar using a Bancor-style bonding curve.

## MentoExchangeProvider

The contract implements the core exchange mechanism for GoodDollar using a Bancor-style bonding curve.

### Contract Specs

The MentoExchangeProvider contract implements the core exchange mechanism for GoodDollar using a Bancor-style bonding curve. It creates and manages liquidity pools (PoolExchanges) that define the relationship between reserve assets and GoodDollar tokens. This contract is essential for maintaining the price stability and liquidity of GoodDollar tokens, which is crucial for the UBI distribution system. It calculates mint amounts from expansion and reserve interest, updates reserve ratios, and provides continuous pricing through the Bancor formula.

### Events

#### ExchangeCreated

Emitted when a new PoolExchange has been created.

| Parameter name | Annotation                                        |
| -------------- | ------------------------------------------------- |
| `exchangeId`   | The ID of the newly created exchange.             |
| `reserveAsset` | The address of the reserve asset in the exchange. |
| `tokenAddress` | The address of the token in the exchange.         |

```solidity
event ExchangeCreated(
    bytes32 indexed exchangeId,
    address indexed reserveAsset,
    address indexed tokenAddress
);
```

#### ExchangeDestroyed

Emitted when a PoolExchange has been destroyed.

| Parameter name | Annotation                                        |
| -------------- | ------------------------------------------------- |
| `exchangeId`   | The ID of the destroyed exchange.                 |
| `reserveAsset` | The address of the reserve asset in the exchange. |
| `tokenAddress` | The address of the token in the exchange.         |

```solidity
event ExchangeDestroyed(
    bytes32 indexed exchangeId,
    address indexed reserveAsset,
    address indexed tokenAddress
);
```

#### ExitContributionSet

Emitted when the exit contribution for a pool is set.

| Parameter name     | Annotation                                    |
| ------------------ | --------------------------------------------- |
| `exchangeId`       | The ID of the exchange.                       |
| `exitContribution` | The exit contribution value set for the pool. |

```solidity
event ExitContributionSet(
    bytes32 indexed exchangeId,
    uint256 exitContribution
);
```

#### ReserveRatioUpdated

Emitted when reserve ratio for exchange is updated.

| Parameter name | Annotation                   |
| -------------- | ---------------------------- |
| `exchangeId`   | The ID of the exchange.      |
| `reserveRatio` | The new reserve ratio value. |

```solidity
event ReserveRatioUpdated(bytes32 indexed exchangeId, uint32 reserveRatio);
```

### Functions

#### createExchange

Creates a new PoolExchange with the provided parameters. Returns the exchangeId for the created exchange.

| Parameter name | Annotation                                                                                                                                        |
| -------------- | ------------------------------------------------------------------------------------------------------------------------------------------------- |
| `exchange`     | The PoolExchange struct containing exchange parameters (reserveAsset, tokenAddress, tokenSupply, reserveBalance, reserveRatio, exitContribution). |

**Returns:** The ID of the newly created exchange.

```solidity
function createExchange(
    IBancorExchangeProvider.PoolExchange calldata exchange
) external returns (bytes32 exchangeId);
```

#### getPoolExchange

Retrieves the PoolExchange struct for a given exchangeId.

| Parameter name | Annotation                          |
| -------------- | ----------------------------------- |
| `exchangeId`   | The ID of the exchange to retrieve. |

**Returns:** The PoolExchange struct containing exchange parameters.

```solidity
function getPoolExchange(
    bytes32 exchangeId
) external view returns (PoolExchange memory exchange);
```

#### getExchangeIds

Returns array of all exchange IDs.

**Returns:** Array of all exchange IDs.

```solidity
function getExchangeIds() external view returns (bytes32[] memory exchangeIds);
```

#### currentPrice

Gets the current price based on the Bancor formula for the specified exchange.

| Parameter name | Annotation                                   |
| -------------- | -------------------------------------------- |
| `exchangeId`   | The ID of the exchange to get the price for. |

**Returns:** The current price based on the Bancor formula.

```solidity
function currentPrice(bytes32 exchangeId) external view returns (uint256 price);
```

#### mintFromExpansion

Calculates and returns the amount of tokens to be minted as a result of expansion. Uses expansion scaler to determine the new reserve ratio.

| Parameter name    | Annotation                                                    |
| ----------------- | ------------------------------------------------------------- |
| `exchangeId`      | The ID of the exchange.                                       |
| `expansionScaler` | The expansion scaler used to determine the new reserve ratio. |

**Returns:** The amount of tokens to be minted as a result of expansion.

```solidity
function mintFromExpansion(
    bytes32 exchangeId,
    uint256 expansionScaler
) external returns (uint256 amountToMint);
```

#### mintFromInterest

Calculates the amount of tokens to be minted as a result of the reserve interest. Interest is added to reserve balance, and tokens are minted to maintain the ratio.

| Parameter name    | Annotation                                |
| ----------------- | ----------------------------------------- |
| `exchangeId`      | The ID of the exchange.                   |
| `reserveInterest` | The amount of reserve interest collected. |

**Returns:** The amount of tokens to be minted as a result of the reserve interest.

```solidity
function mintFromInterest(
    bytes32 exchangeId,
    uint256 reserveInterest
) external returns (uint256);
```

#### updateRatioForReward

Calculates and updates the reserve ratio needed to mint the reward.

| Parameter name | Annotation                           |
| -------------- | ------------------------------------ |
| `exchangeId`   | The ID of the exchange.              |
| `reward`       | The amount of reward tokens to mint. |

```solidity
function updateRatioForReward(bytes32 exchangeId, uint256 reward) external;
```


# MentoBroker

The contract executes token swaps between reserve assets and GoodDollar tokens through exchange providers.

## MentoBroker

The contract executes token swaps between reserve assets and GoodDollar tokens through exchange providers.

### Contract Specs

The MentoBroker contract is the primary interface for users to buy and sell GoodDollar tokens. It executes swaps between reserve assets (like CUSD, USDC, or native tokens) and GoodDollar (G$) tokens through the exchange provider system. This enables the core economic mechanism of GoodDollar: users can purchase G$ tokens by providing collateral, and sell G$ tokens to receive collateral back. The contract manages trading limits, calculates swap amounts using Bancor-style formulas, and provides both fixed input and fixed output swap types.

### Events

#### Swap

Emitted when a swap occurs between tokens.

| Parameter name     | Annotation                                                   |
| ------------------ | ------------------------------------------------------------ |
| `exchangeProvider` | The address of the exchange provider that executed the swap. |
| `exchangeId`       | The ID of the exchange used for the swap.                    |
| `trader`           | The address of the trader who initiated the swap.            |
| `tokenIn`          | The address of the input token.                              |
| `tokenOut`         | The address of the output token.                             |
| `amountIn`         | The amount of input tokens swapped.                          |
| `amountOut`        | The amount of output tokens received.                        |

```solidity
event Swap(
    address exchangeProvider,
    bytes32 indexed exchangeId,
    address indexed trader,
    address indexed tokenIn,
    address tokenOut,
    uint256 amountIn,
    uint256 amountOut
);
```

#### TradingLimitConfigured

Emitted when a new trading limit is configured for an exchange and token pair.

| Parameter name | Annotation                                                          |
| -------------- | ------------------------------------------------------------------- |
| `exchangeId`   | The ID of the exchange.                                             |
| `token`        | The address of the token for which the trading limit is configured. |
| `config`       | The trading limit configuration struct.                             |

```solidity
event TradingLimitConfigured(bytes32 exchangeId, address token, ITradingLimits.Config config);
```

### Functions

#### getAmountIn

Calculates the amount of tokenIn needed to receive a given amountOut of tokenOut. Uses the exchange provider's pricing formula.

| Parameter name     | Annotation                                   |
| ------------------ | -------------------------------------------- |
| `exchangeProvider` | The address of the exchange provider to use. |
| `exchangeId`       | The ID of the exchange.                      |
| `tokenIn`          | The address of the input token.              |
| `tokenOut`         | The address of the output token.             |
| `amountOut`        | The desired amount of output tokens.         |

**Returns:** The amount of input tokens needed to receive the specified amount of output tokens.

```solidity
function getAmountIn(
    address exchangeProvider,
    bytes32 exchangeId,
    address tokenIn,
    address tokenOut,
    uint256 amountOut
) external view returns (uint256 amountIn);
```

#### getAmountOut

Calculates the amount of tokenOut received for a given amountIn of tokenIn. Uses the exchange provider's pricing formula.

| Parameter name     | Annotation                                   |
| ------------------ | -------------------------------------------- |
| `exchangeProvider` | The address of the exchange provider to use. |
| `exchangeId`       | The ID of the exchange.                      |
| `tokenIn`          | The address of the input token.              |
| `tokenOut`         | The address of the output token.             |
| `amountIn`         | The amount of input tokens.                  |

**Returns:** The amount of output tokens that will be received.

```solidity
function getAmountOut(
    address exchangeProvider,
    bytes32 exchangeId,
    address tokenIn,
    address tokenOut,
    uint256 amountIn
) external view returns (uint256 amountOut);
```

#### swapIn

Executes a token swap with fixed input amount. Transfers tokenIn from msg.sender and returns tokenOut. Enforces amountOutMin to prevent excessive slippage.

| Parameter name     | Annotation                                                            |
| ------------------ | --------------------------------------------------------------------- |
| `exchangeProvider` | The address of the exchange provider to use.                          |
| `exchangeId`       | The ID of the exchange.                                               |
| `tokenIn`          | The address of the input token.                                       |
| `tokenOut`         | The address of the output token.                                      |
| `amountIn`         | The amount of input tokens to swap.                                   |
| `amountOutMin`     | The minimum amount of output tokens to receive (slippage protection). |

**Returns:** The amount of output tokens received.

```solidity
function swapIn(
    address exchangeProvider,
    bytes32 exchangeId,
    address tokenIn,
    address tokenOut,
    uint256 amountIn,
    uint256 amountOutMin
) external returns (uint256 amountOut);
```

#### swapOut

Executes a token swap with fixed output amount. Transfers tokenIn from msg.sender (up to amountInMax) and returns the specified amountOut.

| Parameter name     | Annotation                                                         |
| ------------------ | ------------------------------------------------------------------ |
| `exchangeProvider` | The address of the exchange provider to use.                       |
| `exchangeId`       | The ID of the exchange.                                            |
| `tokenIn`          | The address of the input token.                                    |
| `tokenOut`         | The address of the output token.                                   |
| `amountOut`        | The desired amount of output tokens to receive.                    |
| `amountInMax`      | The maximum amount of input tokens to spend (slippage protection). |

**Returns:** The amount of input tokens actually spent.

```solidity
function swapOut(
    address exchangeProvider,
    bytes32 exchangeId,
    address tokenIn,
    address tokenOut,
    uint256 amountOut,
    uint256 amountInMax
) external returns (uint256 amountIn);
```

#### burnStableTokens

Permissionless function to burn stable tokens directly. Transfers tokens from msg.sender and burns them.

| Parameter name | Annotation                               |
| -------------- | ---------------------------------------- |
| `token`        | The address of the stable token to burn. |
| `amount`       | The amount of tokens to burn.            |

**Returns:** True if the burn was successful.

```solidity
function burnStableTokens(address token, uint256 amount) external returns (bool);
```

#### getExchangeProviders

Returns the list of all registered exchange provider addresses.

**Returns:** Array of all registered exchange provider addresses.

```solidity
function getExchangeProviders() external view returns (address[] memory);
```

#### isExchangeProvider

Checks if an address is a registered exchange provider.

| Parameter name     | Annotation            |
| ------------------ | --------------------- |
| `exchangeProvider` | The address to check. |

**Returns:** True if the address is a registered exchange provider, false otherwise.

```solidity
function isExchangeProvider(address exchangeProvider) external view returns (bool);
```


# Faucet

The contract is to provide functionality of topping the users with native tokens to pay transaction fees.

### Events

#### WalletTopped

Emitted when user is topped by G$.

<table><thead><tr><th width="389.63805195347794">Parameter name</th><th>Annotation</th></tr></thead><tbody><tr><td>user</td><td>The address of the <code>user</code> who is being top.</td></tr><tr><td>amount</td><td>The amount of Fuse sent to the <code>user</code>.</td></tr></tbody></table>

```
event WalletTopped(address indexed user, uint256 amount);
```

### canTop

The function allows to check if the user address can be topped with Fuse.

<table><thead><tr><th width="301.8711599216471">Parameter name</th><th>Annotation</th></tr></thead><tbody><tr><td>_user</td><td>The user who is being checked if he could be topped.</td></tr></tbody></table>

Returns: `true` if user could be topped, `false` otherwise.

```
function canTop(address _user) public view returns (bool);
```

### topWallet

The function is utilized to top given address with amount of Fuse given in constructor. The amount of times specified in constructor per day.

<table><thead><tr><th width="301.8711599216471">Parameter name</th><th>Annotation</th></tr></thead><tbody><tr><td>_user</td><td>The address to transfer to.</td></tr></tbody></table>

Can only be called by admin.

```
function canTop(address _user) public view returns (bool);
```


# ContributionCalculation

Helper contract for calculating the exit contribution (i.e. when selling G$ back to the reserve).

### Events

#### SellContributionRatioUpdated

Emits when the contribution ratio is updated.

<table><thead><tr><th width="320.9082692632695">Parameter name</th><th>Annotation</th></tr></thead><tbody><tr><td>caller</td><td>The address of the Avatar.</td></tr><tr><td>nom</td><td>The nominator of the ratio.</td></tr><tr><td>denom</td><td>The denominator of the ratio.</td></tr></tbody></table>

```
event SellContributionRatioUpdated(
    address indexed caller, 
    uint256 nom, 
    uint256 denom
);
```

### calculateContribution

Calculate the amount after contribution during the sell action. There is a `sellContributionRatio` percent contribution.

| Parameter name | Annotation                              |
| -------------- | --------------------------------------- |
| \_marketMaker  | The market maker address.               |
| \_reserve      | The reserve address.                    |
| \_contributer  | The contributer address.                |
| \_token        | The token to convert from.              |
| \_gdAmount     | The total G$ amount to contribute from. |

Returns: the contribution amount for sell.

```
function calculateContribution(
   GoodMarketMaker _marketMaker,
   GoodReserveCDai _reserve,
   address _contributer,
   ERC20 _token,
   uint256 _gdAmount
) external view returns (uint256);
```


# OneTimePayments

Payments on the GoodDollar wallet are done via payment links.

G$s are held in an escrow and the recipient can retrieve the funds if he has the key. While the money is in escrow the sender can choose to cancel the payment and retrieve the funds. Based on [Celo's](https://github.com/celo) payments contract.

### Events

#### PaymentDeposit

Emitted when payment was performed. Occurs only during the token contract call.

<table><thead><tr><th width="389.63805195347794">Parameter name</th><th>Annotation</th></tr></thead><tbody><tr><td>from</td><td>The address of the tokens sender.</td></tr><tr><td>paymentId</td><td>The address representing an ID of the payment.</td></tr><tr><td>amount</td><td>Amount of the payment.</td></tr></tbody></table>

```
event PaymentDeposit(address indexed from, address paymentId, uint256 amount);
```

To deposit a payment to a one time payment address call perform the further:

```
GoodDollar.transferAndCall(value, data);
```

The above will trigger OneTimePayments onTokenTransfer callback, which will trigger the PaymentDeposit.

#### PaymentCancel

Emitted when payment was cancelled.

<table><thead><tr><th width="223.06025121092682">Parameter name</th><th>Annotation</th></tr></thead><tbody><tr><td>from</td><td>The address of the tokens sender.</td></tr><tr><td>paymentId</td><td>The address representing an ID of the payment.</td></tr><tr><td>amount</td><td>Amount of the payment.</td></tr></tbody></table>

```
event PaymentCancel(address indexed from, address paymentId, uint256 amount);
```

#### PaymentWithdraw

Emitted when payment was withdrawn.

<table><thead><tr><th width="223.06025121092682">Parameter name</th><th>Annotation</th></tr></thead><tbody><tr><td>from</td><td>The address of the tokens sender.</td></tr><tr><td>to</td><td>The address of the tokens receiver.</td></tr><tr><td>paymentId</td><td>The address representing an ID of the payment.</td></tr><tr><td>amount</td><td>Amount of the payment.</td></tr></tbody></table>

```
event PaymentWithdraw(
    address indexed from,
    address indexed to,
    address indexed paymentId,
    uint256 amount
);
```

### withdraw

Withdrawal function.

<table><thead><tr><th width="301.8711599216471">Parameter name</th><th>Annotation</th></tr></thead><tbody><tr><td>paymentId</td><td>The address of the public key that the rightful receiver of the payment knows the private key to.</td></tr><tr><td>signature</td><td>The signature of a the message containing the <code>msg.sender</code> address signed with the private key.</td></tr></tbody></table>

```
function withdraw(address paymentId, bytes memory signature) public;
```

### cancel

Payments cancel function.

<table><thead><tr><th width="301.8711599216471">Parameter name</th><th>Annotation</th></tr></thead><tbody><tr><td>_paymentId</td><td>The ID of the payment to cancel.</td></tr></tbody></table>

Allows only creator of payment to cancel.

```
function cancel(address paymentId) public;
```


# NameService

Helper contract, basically simple name to address resolver.

### Events

#### AddressChanged

Emitted when address under the name was changed.

<table><thead><tr><th width="389.63805195347794">Parameter name</th><th>Annotation</th></tr></thead><tbody><tr><td>name</td><td>Name of the address.</td></tr><tr><td>addr</td><td>The address itself.</td></tr></tbody></table>

```
event AddressChanged(string name, address addr);
```

### setAddress

The function that sets the new address under the name.

<table><thead><tr><th width="301.8711599216471">Parameter name</th><th>Annotation</th></tr></thead><tbody><tr><td>name</td><td>The name of an address.</td></tr><tr><td>addr</td><td>The new address itself.</td></tr></tbody></table>

Can only be called by the Avatar.

```
function setAddress(string memory name, address addr) external;
```

### setAddresses

The function that sets the new group of addresses under the names.

<table><thead><tr><th width="301.8711599216471">Parameter name</th><th>Annotation</th></tr></thead><tbody><tr><td>hash</td><td>The array of keccak256's of names.</td></tr><tr><td>addrs</td><td>The new addresses themselfs.</td></tr></tbody></table>

Can only be called by the Avatar.

```
function setAddresses(bytes32[] calldata hash, address[] calldata addrs) external;
```

### getAddress

The function that gets the address under the name.

<table><thead><tr><th width="301.8711599216471">Parameter name</th><th>Annotation</th></tr></thead><tbody><tr><td>name</td><td>The name of an address.</td></tr></tbody></table>

Returns: the address under the given name.

```
function getAddress(string memory name) external view returns (address);
```


# Previous Protocol Versions


# Protocol V1

An introduction to the key components and members in the GoodDollar protocol V1.

**“GoodDollar V1 refers to the initial GoodDollar protocol smart contracts deployed in August 2020. GoodDollar V2 refers to a significant smart contract upgrade with expanded functionality and updated contract addresses. PAY ATTENTION to confirm you are interacting with the correct and most current version of the smart contracts.”**

## Key Components

### Supporters

Members who are "supporters" of the GoodDollar system and "stake" their crypto to GoodDollar. Supporters stake their crypto holdings to the GoodStaking contract, and accept interest payouts in G$ instead of the crypto-asset used for staking.

### Claimers

Members of the GoodDollar wallet who receive daily basic income in GoodDollar coins (G$) via "claiming" G$ daily in the GoodDollar wallet.

### GoodDollar Token (G$)

A digital currency that complies with the ERC-20 standard and initially built on the Ethereum public blockchain. G$ is a reserve-based token - cDAI is the first reserve currency.

### Permissionless Third Party Protocol

An existing algorithmic autonomous interest-bearing protocol developed by third parties where Stakers can deposit cryptocurrencies and earn interest.

### GoodDollar Reserve (GoodReserve)

A smart contract that is the monetary reserve of G$; that holds other crypto-assets (not G$) in it. Members of GoodDollar can buy or sell GoodDollar by depositing or withdrawing supported crypto-assets (initially cDAI) directly to or from the reserve (based on Bancor Formula, see below).

### GoodStaking Smart Contract

A smart contract that:

* (a) receives cryptocurrencies from the Supporters / Stakers and sends it to the permissionless third-party protocol
* (b) issues the GoodStaking record to the Stakers and accepts the transactions from the stakers and sends the protocol the the principle deposited;
* (c) receives the interest in-return directly from the permissionless third-party protocols and automatically transfer it to the GoodDollar GoodReserve contract

**For now - the interest can only be donated to the GoodReserve; supporters are not able to receive interest payouts in G$ at this point in time (coming soon!)**

### UBI Scheme

A smart contract that collects the total minted GoodDollars that are set aside for distribution as basic income on a given day, and distributes G$ equally amongst all claimers.

### Bancor™ Formula

An automatic pricing formula which balances supply and demand for the Smart Token while holding a constant ratio between a Smart Token’s total value (market cap) and its connector token balances (see more [here](https://support.bancor.network/hc/en-us/articles/360000503372-How-does-automatic-pricing-and-market-making-work-)).

### GoodDAO

Decentralized and autonomous entity, a smart contract that will eventually be 100% owned by the community of GoodDollar members.

* Controls the GoodReserve Smart Contract


# Architecture & Value Flow

This page provides an overview of the GoodDollar smart contracts architecture and value flow within the system.

## Smart Contract Architecture Diagram

![](/files/pIOnWUXH9YxdE9Oll88c)

## Money Flow in the GoodDollar Ecosystem

1. Supporter “stakes” crypto-asset to GoodStaking contract
   * Currently only accepting stakes in DAI
2. GoodStaking deposits crypto-asset to permissionless protocol
   * Currently integrated only with Compound
3. Permissionless protocol issues a “staking token”, cDAI
4. GoodStaking issues a non-transferable record to the Supporter’s wallet
   * Supporter can withdraw “stake” at any time
5. GoodStaking issues a non-transferable record to the Supporter’s wallet
   * Supporter can withdraw “stake” at any time
6. GoodDAO contract sends a daily request to GoodStaking to collect earned interest
7. GoodStaking sends interest to GoodReserve
8. GoodDAO triggers the GoodReserve to mint G$ and send newly minted G$ to the GoodDAO. G$ minted are used for interest yield-payouts (currently inactive) and pool of daily basic income
   * Interest pay-outs are sent back to GoodStaking (**currently INACTIVE**)
9. GoodDAO sends G$ for pool of daily basic income to the UBI Scheme Smart Contract, via the Fuse bridge
10. G$ in the UBI Scheme Smart Contract is divided between all “active” users/Claimers
11. Each Claimer has a 24-hour window to log-in and claim their share of the daily basic income pool


# Core Contracts & API

This page provides contract addresses for key components of GoodDollar protocol.

## Contracts & API

GoodDollar Protocol is deployed on both the Ethereum mainnet and on the Fuse sidechain. Contracts like the GoodReserve are only on Mainnet, and other contracts like the UBIScheme are only on the Fuse sidechain. Certain contracts, such as the DAO and G$ Token contracts, are deployed on both networks.

## Core Contracts

### Core Contracts

| Contract                                                                                                            | Mainnet                                                                                                                                 | Fuse                                                                                                                                   | Source code                                                                                                                               |
| ------------------------------------------------------------------------------------------------------------------- | --------------------------------------------------------------------------------------------------------------------------------------- | -------------------------------------------------------------------------------------------------------------------------------------- | ----------------------------------------------------------------------------------------------------------------------------------------- |
| [GoodDollar ERC20](https://docs.gooddollar.org/smart-contracts-guide/core-contracts-and-api#gooddollar-gusd-erc-20) | [0x67C5870b4A41D4Ebef24d2456547A03F1f3e094B](https://etherscan.io/address/0x67C5870b4A41D4Ebef24d2456547A03F1f3e094B)                   | [0x495d133B938596C9984d462F007B676bDc57eCEC](https://explorer.fuse.io/address/0x495d133b938596c9984d462f007b676bdc57ecec)              | [GoodDollar.sol](https://github.com/GoodDollar/GoodContracts/blob/master/contracts/token/GoodDollar.sol)                                  |
| [GoodStaking](https://docs.gooddollar.org/smart-contracts-guide#goodstaking)                                        | [0xEa12bB3917cf6aE2FDE97cE4756177703426d41F](https://etherscan.io/address/0xEa12bB3917cf6aE2FDE97cE4756177703426d41F)                   |                                                                                                                                        | [SimpleDAIStaking.sol](https://github.com/GoodDollar/GoodContracts/blob/master/stakingModel/contracts/SimpleDAIStaking.sol)               |
| [GoodReserve](https://docs.gooddollar.org/smart-contracts-guide/core-contracts-and-api#goodreserve)                 | [0x5C16960F2Eeba27b7de4F1F6e84E616C1977e070](https://etherscan.io/address/0x5C16960F2Eeba27b7de4F1F6e84E616C1977e070)                   |                                                                                                                                        | [GoodReserveCDai.sol](https://github.com/GoodDollar/GoodContracts/blob/master/stakingModel/contracts/GoodReserveCDai.sol)                 |
| [GoodFundManager](https://docs.gooddollar.org/smart-contracts-guide/core-contracts-and-api#goodfundmanager)         | [0xbDFD60f3aE73329D33ebe17d78383DEfd72643Ad](https://etherscan.io/address/0xbDFD60f3aE73329D33ebe17d78383DEfd72643Ad)                   |                                                                                                                                        | [GoodFundManager.sol](https://github.com/GoodDollar/GoodContracts/blob/master/stakingModel/contracts/GoodFundManager.sol)                 |
| [GoodMarketMaker](https://docs.gooddollar.org/smart-contracts-guide#goodmarketmaker)                                | [0xEDbE438Cd865992fDB72dd252E6055A71b02BE72](https://etherscan.io/address/0xEDbE438Cd865992fDB72dd252E6055A71b02BE72)                   |                                                                                                                                        | [GoodMarketMaker.sol](https://github.com/GoodDollar/GoodContracts/blob/master/stakingModel/contracts/GoodMarketMaker.sol)                 |
| [ContributionCalculation](broken://pages/-MGYPfw6VgPVhg9KAn0l)                                                      | [0x8eEC64bb6807c0178f96277cCE6a334B4e565E5C](https://etherscan.io/address/0x8eEC64bb6807c0178f96277cCE6a334B4e565E5C)                   |                                                                                                                                        | [ContributionCalculation.sol](https://github.com/GoodDollar/GoodContracts/blob/master/stakingModel/contracts/ContributionCalculation.sol) |
| [UBIScheme](https://docs.gooddollar.org/smart-contracts-guide/core-contracts-and-api#ubischeme)                     |                                                                                                                                         | [0xD7aC544F8A570C4d8764c3AAbCF6870CBD960D0D](https://explorer.fuse.io/address/0xD7aC544F8A570C4d8764c3AAbCF6870CBD960D0D/transactions) | [UBIScheme.sol](https://github.com/GoodDollar/GoodContracts/blob/master/stakingModel/contracts/UBIScheme.sol)                             |
| [Identity](https://docs.gooddollar.org/smart-contracts-guide/core-contracts-and-api#identity)                       | [0x76e76e10Ac308A1D54a00f9df27EdCE4801F288b](https://etherscan.io/address/0x76e76e10Ac308A1D54a00f9df27EdCE4801F288b)                   | [0xFa8d865A962ca8456dF331D78806152d3aC5B84F](https://explorer.fuse.io/address/0xFa8d865A962ca8456dF331D78806152d3aC5B84F)              | [Identity.sol](https://github.com/GoodDollar/GoodContracts/blob/master/contracts/identity/Identity.sol)                                   |
| [FirstClaimPool](https://docs.gooddollar.org/smart-contracts-guide/core-contracts-and-api#firstclaimpool)           |                                                                                                                                         | [0x18BcdF79A724648bF34eb06701be81bD072A2384](https://explorer.fuse.io/address/0x18BcdF79A724648bF34eb06701be81bD072A2384)              | [FirstClaimPool.sol](https://github.com/GoodDollar/GoodContracts/blob/master/stakingModel/contracts/FirstClaimPool.sol)                   |
| [AdminWallet](https://docs.gooddollar.org/smart-contracts-guide#adminwallet)                                        |                                                                                                                                         | [0x9F75dAcB77419b87f568d417eBc84346e134144E](https://explorer.fuse.io/address/0x9F75dAcB77419b87f568d417eBc84346e134144E)              | [AdminWallet.sol](https://github.com/GoodDollar/GoodContracts/blob/master/contracts/wallet/AdminWallet.sol)                               |
| [OneTimePayments](https://docs.gooddollar.org/smart-contracts-guide/core-contracts-and-api#onetimepayments)         |                                                                                                                                         | [0xd9Aa86e0Ddb932bD78ab8c71C1B98F83cF610Bd4](https://explorer.fuse.io/address/0xd9Aa86e0Ddb932bD78ab8c71C1B98F83cF610Bd4)              | [OneTimePayments.sol](https://github.com/GoodDollar/GoodContracts/blob/master/contracts/dao/schemes/OneTimePayments.sol)                  |
| [DonationsStaking](https://docs.gooddollar.org/smart-contracts-guide/core-contracts-and-api#donationsstaking)       | [0x93fb057eec37abc11d955d1c09e6a0d218f35cff](https://etherscan.io/address/0x93fb057eec37abc11d955d1c09e6a0d218f35cff#readProxyContract) |                                                                                                                                        | [DonationsStakinng.sol](https://github.com/GoodDollar/GoodContracts/blob/master/upgradables/contracts/staking/DonationsStaking.sol)       |

### GoodDollar G$ ERC-20

#### GoodDollar G$ ERC-20

The GoodDollar G$ token follows the ERC-20 token standard and also supports ERC-677.

#### GoodStaking

#### GoodStaking

Supporters / stakers can stake crypto which is then sent to permissionless protocols which earn interest. The FundManager has permissions to collect interest-earned from this contract.

```
/**
 * @dev Allows a staker to deposit DAI tokens. Notice that `approve` is
 * needed to be executed before the execution of this method.
 * Can be executed only when the contract is not paused.
 * @param _amount The amount of DAI to stake
 */
function stakeDAI(uint256 _amount) public whenNotPaused

/**
 * @dev Withdraws the sender staked DAI.
 */
function withdrawStake() public
```

### GoodReserve

#### GoodReserve

The GoodReserve mints G$ based on the interest transferred from the FundManager. Only the FundManager can trigger minting. The GoodReserve also acts as the GoodDollar liquidity pool and AMM (Automatic Market Maker) and enables methods to buy and sell G$s.

```
/**
 * @dev Converts `buyWith` tokens to GD tokens and updates the bonding curve params.
 * `buy` occurs only if the GD return is above the given minimum. It is possible
 * to buy only with cDAI and when the contract is set to active. 
 * MUST `approve` prior this action to allow this contract to accomplish the
 * conversion.
 * @param _buyWith The tokens that should be converted to GD tokens
 * @param _tokenAmount The amount of `buyWith` tokens that should be converted to GD tokens
 * @param _minReturn The minimum allowed return in GD tokens
 * @return (gdReturn) How much GD tokens were transferred
 */
function buy(ERC20 _buyWith,uint256 _tokenAmount,uint256 _minReturn) public requireActive onlyCDai(_buyWith) returns (uint256)

/**
 * @dev Converts GD tokens to `sellTo` tokens and update the bonding curve params.
 * `sell` occurs only if the token return is above the given minimum. Notice that
 * there is a contribution amount from the given GD that remains in the reserve.
 * It is only possible to sell to cDAI and only when the contract is set to
 * active. MUST make call to G$ `approve` prior to this action to allow this
 * contract to accomplish the conversion.
 * @param _sellTo The tokens that will be received after the conversion
 * @param _gdAmount The amount of GD tokens that should be converted to `_sellTo` tokens
 * @param _minReturn The minimum allowed `sellTo` tokens return
 * @return (tokenReturn) How much `sellTo` tokens were transferred
 */

function sell(
    ERC20 _sellTo,
    uint256 _gdAmount,
    uint256 _minReturn
) public requireActive onlyCDai(_sellTo) returns (uint256)

/**
 * @dev Current price of GD in `token`. currently only cDAI is supported.
 * @param _token The desired reserve token to have
 * @return price of GD
 */
function currentPrice(ERC20 _token) public view returns (uint256)
```

### GoodFundManager

#### GoodFundManager

Has permissions to collect interest from the GoodStaking contract and permissions to tell GoodReserve to mint. Anyone can trigger the collection and minting process

```
/**
 * @dev Collects UBI interest in cDai from a given staking contract and transfers
 * that interest to the reserve contract. Then transfers the gd
 * received from the reserve contract back to the staking contract and to the
 * bridge, which locks the funds and then same amount of G$ tokens are minted to the
 * ubiRecipient address on the sidechain
 *
 * @param _staking Contract that implements `collectUBIInterest` and transfer cDai to
 * a given address. The given address should be the same whitelisted `reserve`
 * address in the current contract, in case that the given staking contract transfers
 * the funds to another contract, zero GD tokens will be minted by the reserve contract.
 * Emits `FundsTransferred` event in case which interest has been passed to the `reserve`
 */
function transferInterest(StakingContract _staking)
    public
    requireActive
    reserveHasInitialized
    requireDAOContract(address(_staking))
```

### UBIScheme

#### UBIScheme

Holds all the G$s that were transferred via bridge from the FundManager. The pool of G$s is divided equally by the amount of current active users, and distributed every day. Each active user can then "claim" his quota. If a user fails to claim his quota it becomes part of the next day's pool of G$ to be distributed as basic income.

```
/**
 * @dev Checks the amount which the sender address is eligible to claim for,
 * regardless if they have been whitelisted or not.
 * @return The amount of GD tokens the address can claim.
 */
function checkEntitlement() public view requireActive returns (uint256)

/**
 * @dev Function for claiming UBI. Requires contract to be active and claimer to be whitelisted.
 * Calls distributionFormula, calculats the amount the caller can claim, and transfers the amount
 * to the caller. Emits the address of caller and amount claimed.
 * @return A bool indicating if UBI was claimed
 */
function claim() public requireActive onlyWhitelisted returns (bool)

/**
 * @dev In order to update users from active to inactive, we give out incentive to people
 * to update the status of inactive users, this action is called "Fishing". Anyone can
 * send a tx to the contract to mark inactive users. The "fisherman" receives a reward
 * equal to the daily UBI (ie instead of the “fished” user). User that “last claimed” > 14
 * can be "fished" and made inactive (reduces active users count by one). Requires
 * contract to be active.
 * @param _account to fish
 * @return A bool indicating if UBI was fished
 */
function fish(address _account) public requireActive returns (bool)

/**
 * @dev executes `fish` with multiple addresses. emits the number of users from the given
 * array who actually been tried being fished.
 * @param _accounts to fish
 * @return A bool indicating if all the UBIs were fished
 */
function fishMulti(address[] memory _accounts)
```

### Identity

#### Identity

The identity contract controls addresses that are whitelisted to "Claim" UBI.

* **Face Verification** GoodDollar currently whitelists users based on a user proving "uniqueness" by signing up with a live and unique face. All image data and details are anonymized in order to allow the user to create a new account in case he is unable to recover his wallet. Facial details are deleted after `authenticationPeriod` and users are required to perform face verification again every `authenticationPeriod` days.
* **Social Profile** Each blockchain address is linked to the user's public profile as created in the wallet. The DID is the node id in the public p2p GunDB database. Mappings from wallet address to DID are held in `addrTODID`

```
/* 
 * @dev Returns true if given address has been added to whitelist
 * @param account the address to check
 * @return a bool indicating weather the address is present in whitelist
*/
function isWhitelisted(address account) public view returns (bool)

/* 
 * @dev Function that gives the date the given user was added
 * @param account The address to check
 * @return The date the address was added
*/
function lastAuthenticated(address account) public view returns (uint256)

/* the number of days an authentication is valid for*/
uint256 public authenticationPeriod

mapping(address => string) public addrToDID;
```

### OneTimePayments

#### OneTimePayments

Payments on the GoodDollar wallet are done via payment links. G$s are held in escrow and the recipient can retrieve the funds if he has the key. While the money is in escrow the sender can choose to cancel the payment and retrieve the funds. Based on [Celo's](https://github.com/celo) payments contract.

```
/* 
* @dev ERC677 on token transfer function. When transferAndCall is called on this contract,
 * this function is called, depositing the payment amount under the hash of the given bytes.
 * Reverts if hash is already in use. Can only be called by token contract.
 * @param sender the address of the sender
 * @param value the amount to deposit
 * @param data The given paymentId which should be a fresh public key
 */

to deposit a payment to a one time payment address call:
GoodDollar.transferAndCall(value,data) this will trigger OneTimePayments onTokenTransfer

/* @dev Withdrawal function.
 * allows the sender that proves ownership of paymentId to withdraw
 * @param paymentId the address of the public key that the
 *   rightful receiver of the payment knows the private key to
 * @param signature the signature of a the message containing the msg.sender address signed
 *   with the private key.
 */
function withdraw(address paymentId, bytes memory signature) public onlyRegistered

/* @dev Cancel function
 * allows only creator of payment to cancel
 * @param paymentId The paymentId of the payment to cancelæ
 */
function cancel(address paymentId) public
```

### DonationsStaking

#### DonationsStaking

Any ETH/DAI sent to this contract address is donated to the GoodDollar DAO and will generate interest to fund UBI. The funds are periodically staked in the GoodStaking contract by calling the `stakeDonations`method.

```
    uint256 public totalETHDonated;
    uint256 public totalDAIDonated;

    event DonationStaked(
        address caller,
        uint256 stakedDAI,
        uint256 ethDonated,
        uint256 daiDonated
    );

    /**
     * @dev stake available funds. It
     * take balance in eth and buy DAI from uniswap then stake outstanding DAI balance.
     * anyone can call this.
     * @param _minDAIAmount enforce expected return from uniswap when converting eth balance to DAI
     */
    function stakeDonations(uint256 _minDAIAmount) public payable isActive {
        uint256 daiDonated = DAI.balanceOf(address(this));
        uint256 ethDonated = _buyDAI(_minDAIAmount);

        uint256 daiBalance = DAI.balanceOf(address(this));
        require(daiBalance > 0, "no DAI to stake");

        stakingContract.stakeDAI(daiBalance);
        totalETHDonated += ethDonated;
        totalDAIDonated += daiDonated;
        emit DonationStaked(msg.sender, daiBalance, ethDonated, daiDonated);
    }

    /**
     * @dev total DAI value staked
     * @return DAI value staked
     */
    function totalStaked() public view returns (uint256) {
        Staking.Staker memory staker = stakingContract.stakers(address(this));
        return staker.stakedDAI;
    }
```

### GoodMarketMaker

#### GoodMarketMaker

Helper contract for the GoodReserve.

### ContributionCalculation

#### ContributionCalculation

Helper contract for calculating the exit contribution (ie when selling G$ back to the reserve)

### FirstClaimPool

#### FirstClaimPool

Helper contract for UBIScheme. Manually funded by the Foundation to give 1G$ for "inactive" users when they claim. Since a new user (inactive) becomes active and eligible to claim UBI only in the next UBI epoch. So for new users not go empty handed on their first claim we give out a 1G$.

### AdminWallet

#### AdminWallet

Helper contract for our backend servers to whitelist users and to fill their Fuse network gas.

## Token Bridge Contracts

### Token Bridge Contracts

Bridge contracts were developed by [Fuse](https://fuse.io).

{% hint style="info" %}
Note: for regular users it is recommended to use FuseSwap Bridge in order to avoid losing your tokens ([help](https://docs.fuse.io/fuseswap/bridge-fuse-erc20-tokens)). FuseSwap Bridge: [Mainnet -> Fuse](https://fuseswap.com/#/bridge/0x67C5870b4A41D4Ebef24d2456547A03F1f3e094B) | [Fuse -> Mainnet](https://fuseswap.com/#/bridge/0x495d133B938596C9984d462F007B676bDc57eCEC).
{% endhint %}

Note: for regular users it is recommended to use FuseSwap Bridge in order to avoid losing your tokens ([help](https://docs.fuse.io/fuseswap/bridge-fuse-erc20-tokens)). FuseSwap Bridge: [Mainnet -> Fuse](https://fuseswap.com/#/bridge/0x67C5870b4A41D4Ebef24d2456547A03F1f3e094B) | [Fuse -> Mainnet](https://fuseswap.com/#/bridge/0x495d133B938596C9984d462F007B676bDc57eCEC).

## DAO Contracts

| Contract                        | Mainnet                                                                                                               | Fuse                                                                                                                      | Source Code                                                                                                                                                                   |
| ------------------------------- | --------------------------------------------------------------------------------------------------------------------- | ------------------------------------------------------------------------------------------------------------------------- | ----------------------------------------------------------------------------------------------------------------------------------------------------------------------------- |
| ForeignBridge (mainnet -> fuse) | [0xD5D11eE582c8931F336fbcd135e98CEE4DB8CCB0](https://etherscan.io/address/0xD5D11eE582c8931F336fbcd135e98CEE4DB8CCB0) |                                                                                                                           | [ForeignAMBErc677ToErc677.sol](https://github.com/fuseio/tokenbridge-contracts/blob/master/contracts/upgradeable_contracts/amb_erc677_to_erc677/ForeignAMBErc677ToErc677.sol) |
| HomeBridge (fuse -> mainnet)    |                                                                                                                       | [0xD39021DB018E2CAEadb4B2e6717D31550e7918D0](https://explorer.fuse.io/address/0xD39021DB018E2CAEadb4B2e6717D31550e7918D0) | [HomeAMBErc677ToErc677.sol](https://github.com/fuseio/tokenbridge-contracts/blob/master/contracts/upgradeable_contracts/amb_erc677_to_erc677/HomeAMBErc677ToErc677.sol)       |

### DAO Contracts

DAO contracts were developed by [DAOStack](https://daostack.io)

<table><thead><tr><th width="224">Contract</th><th>Mainnet</th><th>Fuse</th><th>Source Code</th></tr></thead><tbody><tr><td>Controller</td><td><a href="https://etherscan.io/address/0x95C0d9dCEA1E243ED696F34CAc5e6559C3c128a3">0x95C0d9dCEA1E243ED696F34CAc5e6559C3c128a3</a></td><td><a href="https://explorer.fuse.io/address/0xBcE053b99e22158f8B62f4DBFbEdE1f936b2D4e4">0xBcE053b99e22158f8B62f4DBFbEdE1f936b2D4e4</a></td><td><a href="http://github.com/daostack/arc/tree/master/contracts/controller/Controller.sol">Controller.sol</a></td></tr><tr><td>Avatar</td><td><a href="https://etherscan.io/address/0x1ecFD1afb601C406fF0e13c3485f2d75699b6817">0x1ecFD1afb601C406fF0e13c3485f2d75699b6817</a></td><td><a href="https://explorer.fuse.io/address/0xf96dADc6D71113F6500e97590760C924dA1eF70e">0xf96dADc6D71113F6500e97590760C924dA1eF70e</a></td><td><a href="http://github.com/daostack/arc/tree/master/contracts/controller/Avatar.sol">Avatar.sol</a></td></tr><tr><td>Reputation</td><td><a href="https://etherscan.io/address/0xCb4a6aF3b15D64E8f50B3cea54c4f481d9E434C1">0xCb4a6aF3b15D64E8f50B3cea54c4f481d9E434C1</a></td><td><a href="https://explorer.fuse.io/address/0x0be7C592374EE0bD0CcBFC76Be758a138BcaEc6E">0x0be7C592374EE0bD0CcBFC76Be758a138BcaEc6E</a></td><td><a href="http://github.com/daostack/infra/tree/master/contracts/Reputation.sol">Reputation.sol</a></td></tr><tr><td>SchemeRegistrar</td><td><a href="https://etherscan.io/address/0x098148534aC15A44CFF52387bA81Ed929589eCAf">0x098148534aC15A44CFF52387bA81Ed929589eCAf</a></td><td><a href="https://explorer.fuse.io/address/0x12F706FaafCBf8093282Dba0c40eD0D4Eb5CAF54">0x12F706FaafCBf8093282Dba0c40eD0D4Eb5CAF54</a></td><td><a href="http://github.com/daostack/arc/tree/master/contracts/universalSchemes/SchemeRegistrar.sol">SchemeRegistrar.sol</a></td></tr><tr><td>AbsoluteVote</td><td><a href="https://etherscan.io/address/0xCb4a6aF3b15D64E8f50B3cea54c4f481d9E434C1">0xf6b5F7a885CBc57d739aDBEe76E52A70Bc04D795</a></td><td><a href="https://explorer.fuse.io/address/0x0be7C592374EE0bD0CcBFC76Be758a138BcaEc6E">0xf6b5F7a885CBc57d739aDBEe76E52A70Bc04D795</a></td><td><a href="http://github.com/daostack/infra/tree/master/contracts/votingMachines/AbsoluteVote.sol">AbsoluteVote.sol</a></td></tr><tr><td>UpgradeScheme</td><td><a href="https://etherscan.io/address/0xF9B357d83BDAD6881feb09d909095872B93203d0">0xF9B357d83BDAD6881feb09d909095872B93203d0</a></td><td><a href="https://explorer.fuse.io/address/0x653c67Be5b3739708e84B61641253822405d78D8">0x653c67Be5b3739708e84B61641253822405d78D8</a></td><td><a href="http://github.com/daostack/arc/tree/master/contracts/universalSchemes/UpgradeScheme.sol">UpgradeScheme.sol</a></td></tr></tbody></table>


# Protocol V2

GoodDollar V2 refers to GoodDollar protocol smart contracts deployed in December 2021. PAY ATTENTION to confirm you are interacting with the correct and most current version of the smart contracts.

## **Intro**

**GoodDollarV2 is a smart contract upgrade that enables core functions for the GoodDollar protocol to scale.**

{% hint style="info" %}
[This blog post](https://www.gooddollar.org/gooddollarv2-launches-the-epoch-of-defi-for-good/) provides an overview of what V2 does and why it matters to you and the world.
{% endhint %}

* GoodDollar leverages yield farming and liquidity mining rewards to encourage capital to flow towards the protocol, enabling the sustainable generation of UBI.
* V2 is a smart contract upgrade to expand functionality and open-source launch of a [protocol user interface](/for-developers/developer-guides/deploy-your-own-gooddapp-ui), deployed by community members.
* V2 enables members to [stake](broken://pages/-Mk3RGiSa9NiLmGlZC18) in Compound or Aave and earn #GoodRewards while at the same time funding [#CryptoUBI](https://twitter.com/search?q=%23cryptoubi\&src=typed_query) for all.
* Now, members can buy and sell G$ directly in the [GoodDollar Reserve](/user-guides/buy-and-sell-gusd), a key feature that enables the economy to scale.
* V2 introduces a new governance model with the launch of the community-owned [GoodDAO](broken://pages/fhrgxq64M5bDD5zTRTpY#_x9v4kk8jp487), which will determine the protocol’s future direction.&#x20;

![V1 (POC) vs. V2](/files/dEZH7jawZzytGFDgnFIO)

## What you can do in V2:

### Stake for GoodDollar UBI and earn rewards&#x20;

* [Stake](broken://pages/-Mk3RGiSa9NiLmGlZC18) your stablecoins using GoodDollar Trust&#x20;
* Get benefits from the Liquidity Rewards Scheme

### Interact directly with GoodDollar Reserve&#x20;

* Swap any ERC-20 token in [exchange for G$ ](/user-guides/buy-and-sell-gusd)
* Earn G$X by buying G$ from the reserve, a token that enables users to sell to the GoodReserve without penalty.

### Community governance via GoodDAO&#x20;

* Community governance for all smart contract upgrades&#x20;
* [Claim GOOD allocation](broken://pages/-MkpnoJxbZw4f-JVvEZl) based on snapshot results and ongoing distribution
* Integrate Your Protocol with GoodDollar and assign G$ rewards

### Developer Tools&#x20;

* Contribute with GoodDollar repository and security and hunt some [bounties](https://github.com/GoodDollar/Bounties/issues).&#x20;
* Integrate your Protocol with GoodDollar (coming soon!)&#x20;
* [Deploy Your Own UI](/for-developers/developer-guides/deploy-your-own-gooddapp-ui)


# Architecture & Value Flow

This page provides an overview of the GoodDollar V2 smart contracts architecture and value flow within the system.

### **GoodDollar Money Flow** <a href="#d7389pq6vqpd" id="d7389pq6vqpd"></a>

GoodDollar is a new kind of digital economy with a UBI distribution model. The protocol is able to sustainably generate a crypto token (G$) for onward distribution in two ways:

1. Through the addition of funds to the GoodDollar Reserve via interest earned on capital staked with third-party protocols, or the purchase of G$ from the GoodDollar Reserve.
2. Through reductions in the reserve ratio.

### **How the GoodDollar system works** <a href="#cbghnzkzyo0f" id="cbghnzkzyo0f"></a>

This is the money flow that underpins the generation of GoodDollar crypto UBI.

![](/files/pKhkNxubKRCu2Q1CQ0Oh)

1. Supporter stakes crypto to the GoodDollar Trust.
2. The GoodDollar Trust stakes that money to a third-party DeFi protocol.
3. The third-party DeFi protocol issues a staking token (e.g. CDAI) to the GoodDollar Trust.
4. In return for staking, the supporter is entitled to be rewarded with a sum of G$. The staker can then either withdraw these rewards, or waive this entitlement.
   1. The staker can withdraw his stake at any time.
5. Keeper (any player in the ecosystem who wants to do this work) activates the Fund Manager, to funnel interest back to the GoodDollar Trust:
   1. The keeper is also rewarded with G$.
6. Fund Manager:
   1. Collects interest from the different GoodStaking contracts and sends this to the GoodDollar Reserve.
   2. Converts any extra tokens generated through staking to CDAI.
   3. Swaps the interest payments into G$.
   4. Sends the G$ over the Bridge to the Disco.
7. The DisCo then divides the G$ among all whitelisted wallets that have clicked “claim” on the app within the preceding 24 hours.


# System's Elements

## [1. **The token (G$)**](broken://pages/ui5Tqh4tBPqE8fVLwESv) <a href="#coklhq47qt9q" id="coklhq47qt9q"></a>

The ***GoodDollar token (G$)*** is an ERC 20 crypto token with a max supply of 2.2 trillion. It is native to Ethereum and also operates on Fuse.

## [**2. The Reserve**](broken://pages/9bXnFHB1ygXEOjEmvW6N) <a href="#reserve" id="reserve"></a>

The ***GoodDollar Reserve*** is the smart contract that governs the vault holding the assets that back G$ tokens. The algorithm that guides the reserve is based on the Bancor formula, which has been altered to fit GoodDollar’s needs. There are two important characteristics unique to the GoodDollar Reserve:

1. The reserve supports the generation of G$. Users can always convert to and from G$ via the reserve.
2. The unique math of the GoodDollar Reserve lends G$ exceptional stability.

### **Exit Contributions** <a href="#mebn0hpwchkh" id="mebn0hpwchkh"></a>

In addition to the G$ coin and the GOOD governance token, the GoodDollar ecosystem includes a third type of crypto token: ***G$X***. Members who hold G$X tokens can use these to reduce their exit contributions when selling G$ to the reserve by an amount set by the DAO. Users acquire G$X tokens as a reward for buying G$ from the reserve (currently, a user who buys 100 G$ will also receive 100 G$X).

### **Helpers** <a href="#p1dxu7aswyt0" id="p1dxu7aswyt0"></a>

***Helper contracts*** are smart contracts that connect the GoodDollar Reserve to other liquidity networks in order to allow liquidity to flow from G$ to any other token that has an automated market maker (AMM). For example, if a user wants to convert token X to G$, the helper contract will first convert token X to DAI using Uniswap, and then convert DAI to CDAI using Compound. Finally, it will convert the CDAI to G$ using the GoodDollar Reserve. Future versions of the protocol may extend this functionality to additional protocols, such as Bancor.

## [**3. The Trust**](broken://pages/LKyti9GD5rgLxsW0fwHr) <a href="#mn9xjitr972u" id="mn9xjitr972u"></a>

The aim of the ***GoodDollar Trust*** is to generate an ongoing flow of money into the GoodDollar Reserve. What we refer to as the GoodDollar Trust is in actuality a collection of trust funds, or staking contracts, that “wrap” third-party deposit-taking DeFi protocols. Each protocol and token has a separate trust fund.&#x20;

## [**4. Staking rewards (APR)**](broken://pages/88xJNCkaYYDX36Q80Az9)

Rewards are calculated based on the formula set out [here](https://eips.ethereum.org/EIPS/eip-2917). Simply put, users are rewarded in each block, according to the following calculation: \
**(User’s total stake/Total staked in contract) \* (Reward per block).**

{% hint style="success" %}
**Initial staking rewards**

* Compound DAI Total reward per block = 138.88 G$s | Yearly Reward = 291M G$s
* AAVE USDC Total reward per block = 69.44 G$s | Yearly Reward = 145.5M G$s
  {% endhint %}

## [**5. The Fund Manager**](broken://pages/RoaBXNoaA4rC2JSPwQ5A) <a href="#q0skiu5ion2h" id="q0skiu5ion2h"></a>

Responsible for several critical processes in the GoodDollar protocol. These include:

* The activation of UBI generation.
* The transfer of interest from the GoodDollar Trust to the GoodDollar Reserve.
* The transfer of funds to the Bridge and onward to the DisCo for distribution to UBI Claimers via the Fuse blockchain.

## [**6. The Distribution Contract (DisCo)**](broken://pages/Gsj54pFNZ7XkOkC6jjPf) <a href="#r9w6swau5npq" id="r9w6swau5npq"></a>

The ***DisCo***, or ***Distribution Contract***, is a smart contract that handles the distribution of G$ to all white-listed addresses.

## [**7. Governance (DAO)**](broken://pages/fhrgxq64M5bDD5zTRTpY)

The GoodDollar governance model is based on the Compound governance model and code, as set out [here](https://compound.finance/docs/governance#comp). Critical to the process is the **GOOD token**, a non-transferable token that controls all smart contracts within the GoodDollar ecosystem.


# 1. The token (G$)

The ***GoodDollar token (G$)*** is an ERC 20 crypto token with a max supply of 2.2 trillion. It is native to Ethereum and also operates on Fuse.


# 2. The Reserve

The ***GoodDollar Reserve*** is the smart contract that governs the vault holding the assets that back G$ tokens. The algorithm that guides the reserve is based on the Bancor formula, which has been altered to fit GoodDollar’s needs. There are two important characteristics unique to the GoodDollar Reserve:

1. The reserve supports the generation of G$. Users can always convert to and from G$ via the reserve.
2. The unique math of the GoodDollar Reserve lends G$ exceptional stability.

### **Key Terms**

**Reserve:** The pool of tokens backing G$ generation.

**Reserve Ratio (Rr):** The ratio between the total G$ market cap and the value of the reserve.

**Supply (S):** The current circulating supply of G$.

**Price (P):** The price of G$ relative to the tokens in reserve.

**Exit Contribution:** A contribution paid when selling G$ into the reserve in exchange for another currency.

**G$X:** A token earned as a reward for buying G$ from the reserve that can be used to reduce a user’s exit contribution in a subsequent sale of G$.

#### **The Reserve Ratio (Rr)**

*The ratio between the value of the reserve and the market capitalization of G$. The lower the ratio, the more G$ the protocol can generate.*

### **Reserve Functions:** <a href="#ifxdlmghjtme" id="ifxdlmghjtme"></a>

The GoodDollar Reserve performs three different functions important to the GoodDollar Economy: ***Expansion***; ***Conversion***; ***Interest Deposits***. These are outlined below (for more on the underlying math, please see the [appendix ](https://whitepaper.gooddollar.org/appendix)of the GoodDollar white paper).

* ***Expansion*** is the pre-set annual rate by which the token supply increases, thereby reducing the reserve ratio. For instance, if the expansion rate is set to 10% annually and the year begins with a reserve ratio of 1, then by the end of the first year the reserve ratio would be 0.9, by the end of year two, 0.81, and so on ([Equation 3](https://whitepaper.gooddollar.org/appendix#equation-3-expansion-rate-formula)).
* ***Conversion*** is the process that enables users to exchange G$ for CDAI and vice versa. Since the GoodDollar Reserve is essentially an automated market maker (AMM) that works on a bonding curve, the amount of G$ minted or burned depends upon how much collateral is added or removed from the reserve. Users who buy G$ receive a matching number of G$X tokens as a reward for their purchases, which can be used to reduce their exit contributions when they choose to sell G$ (see below).
* ***Interest deposits*** into the GoodDollar Reserve from a third-party protocol are converted to G$ in a different way than during the crypto exchange process outlined above. When a user buys G$ from the GoodDollar Reserve in exchange for a supported currency, new tokens are minted and the price of G$ rises. In contrast, when a user deposits interest, there are more tokens minted, but the price of G$ doesn’t change.

### **Exit Contributions** <a href="#mebn0hpwchkh" id="mebn0hpwchkh"></a>

#### **G$X Tokens** <a href="#id-511bw6p5w9as" id="id-511bw6p5w9as"></a>

In addition to the G$ coin and the GOOD governance token, the GoodDollar ecosystem includes a third type of crypto token: ***G$X***. Members who hold G$X tokens can use these to reduce their exit contributions when selling G$ to the reserve by an amount set by the DAO. Users acquire G$X tokens as a reward for buying G$ from the reserve (currently, a user who buys 100 G$ will also receive 100 G$X).

#### **Exit contribution calculation including G$X**

1. Discount = 1 - G$X/G$sold
   1. If Discount <= 0 Then Discount = 0
2. Exit contribution = Setcontribution\*Discount

#### **G$X Supply & Burn policies**

For every G$ token bought from the GoodDollar Reserve, the reserve will issue 1 G$X token. For every G$ token sold to the GoodDollar Reserve, the reserve will burn 1 G$X token.

### **Stability** <a href="#qz61jetq3map" id="qz61jetq3map"></a>

As described above, the impact of buying and selling currencies to and from the GoodDollar Reserve depends on three factors:

1. The size of the reserve ratio.
2. The size of each transaction.
3. The total reserve value.

### **Simulator**

A Price similator with dynamic reseerve rate function is available [here](https://docs.google.com/spreadsheets/d/1laUPAf-ZH1kjKaOkgwQizHT1wohfDj_b5Fq6Z7GGJDY/edit#gid=137486606) :&#x20;

{% embed url="<https://docs.google.com/spreadsheets/d/1laUPAf-ZH1kjKaOkgwQizHT1wohfDj_b5Fq6Z7GGJDY/edit#gid=137486606>" %}

### **Helper contracts** <a href="#p1dxu7aswyt0" id="p1dxu7aswyt0"></a>

***Helper contracts*** are smart contracts that connect the GoodDollar Reserve to other liquidity networks in order to allow liquidity to flow from G$ to any other token that has an automated market maker (AMM). For example, if a user wants to convert token X to G$, the helper contract will first convert token X to DAI using Uniswap, and then convert DAI to CDAI using Compound. Finally, it will convert the CDAI to G$ using the GoodDollar Reserve. Future versions of the protocol may extend this functionality to additional protocols, such as Bancor and Aave.


# 3. The Trust

The aim of the ***GoodDollar Trust*** is to generate an ongoing flow of money into the GoodDollar Reserve. What we refer to as the GoodDollar Trust is in actuality a collection of trust funds, or staking contracts, that “wrap” third-party deposit-taking DeFi protocols. Each protocol and token has a separate trust fund. For example, Compound DAI is one trust fund; Compound ETH is another; and Aave DAI will be a third.

Each separate trust fund takes the interest generated by staked assets in the protocol it wraps and donates this to the GoodDollar Reserve, for the support of crypto UBI generation. As a reward for their commitment, stakers have the option of receiving a sum of newly minted G$ tokens. They can either withdraw these tokens, at which point they will be minted, or opt not to.


# 4. Staking rewards (APR)

1. The ***staking rewards structure*** is a new parameter that is governed by the GoodDAO
2. Rewards vary depending on the third-party protocol (e.g. Compound, DAI etc.) and currency pair involved.
3. Staking rewards are calculated in G$ values, as set out in the smart contract (e.g. 1M G$ in rewards per month).
4. Rewards are prorated based on the amount of capital staked per block.

Rewards are calculated based on the formula set out [here](https://eips.ethereum.org/EIPS/eip-2917). Simply put, users are rewarded in each block, according to the following calculation: **(User’s total stake/Total staked in contract) \* (Reward per block).**

{% hint style="success" %}
**Initial staking rewards**

* Compound DAI Total reward per block = 138.88 G$s | Yearly Reward = 291M G$s
* AAVE USDC Total reward per block = 69.44 G$s | Yearly Reward = 145.5M G$s
  {% endhint %}

#### **Rewards effects on the Reserve Ratio**

The minting of G$ rewards affects the reserve ratio in the same way as the minting of G$ for UBI. The minting of new tokens both to pay rewards and to supply UBI to members increases the total supply of G$, and thus reduces the reserve ratio.

The decline in the reserve ratio following the minting of tokens for staking rewards can be determined as follows:

1. Current state (before the minting of staking rewards):
   1. S\*P=R/Rr
2. Newly minted tokens as **S**taking **R**ewards:
   1. SR
3. New **R**eserve **r**atio: Rr1
4. (S+SR)\*P=R/Rr1
5. Rr1 = R/((S+SR)\*P)

Because stakers have the option not to withdraw the rewards to which they are entitled, tokens are minted only at the point a user makes a claim, not at the point of entitlement.

#### **Multiplier rewards**

***Multiplier rewards*** are designed to encourage users to leave their principal and rewards locked, rather than withdrawing and converting all or part of this amount the moment they are entitled to claim their rewards.

In the first month of staking, for instance, the user will earn only 50% of the reward to which he/she is entitled: i.e. a multiplier of 0.5. From the second month onward, the user will earn the full allocation of rewards: i.e. a multiplier of 1.

When a user takes any of the below steps, his/her multiplier resets to 0.5:

1. Withdraws part or all of the capital staked.
2. Withdraws all or part of the accrued rewards.
3. Transfers LP staking tokens.

#### **Social Rewards (Social annual percentage yield)** <a href="#iutabpno9adx" id="iutabpno9adx"></a>

Staking is critical to GoodDollar’s ability to generate and distribute crypto UBI. To show users the power of their contribution, we use a calculation called the ***Social APY (annual percentage yield).*** This sets out for each user how much G$ will be distributed to GoodDollar claimers each year as a result of his/her stake.

**Social APY calculation:**

Social APY is calculated according to the following equation:

**Social APY = CAPR / Rr**

Wherein:

* **CAPR** (contract annual percentage return) = The annual percentage return offered by the third-party protocol a user has staked to
* **Rr** (reserve ratio) = The ratio between capital in the GoodDollar Reserve and the total market capitalization of G$

For example, a stake of $100 to the GoodDollar Trust would enable the protocol to mint and distribute $10 worth of G$. If that stake is made to the Aave protocol (with an APR of 10%) and the reserve ratio stands at 85%, the Social APY calculation would be as follows:

**Social APY** = 10% / 85%

**Social APY** = 11.7%


# 5. The Fund Manager

The ***Fund Manager*** is a smart contract responsible for several critical processes in the GoodDollar protocol. These include:

* The activation of UBI generation.
* The transfer of interest from the GoodDollar Trust to the GoodDollar Reserve.
* The transfer of funds to the Bridge and onward to the DisCo for distribution to UBI Claimers via the Fuse blockchain.

### **Keepers**

As with all smart contracts, processes handled by the Fund Manager must be triggered manually. The task of triggering these processes falls to a group of volunteers called ***Keepers***. In exchange for instructing the Fund Manager to execute tasks, these users earn rewards as well as compensation for transaction fees incurred during the process.

In addition to the above tasks handled by the Fund Manager, Keepers can also earn G$ rewards for converting the status of verified users who have not made a claim in the past 14 days from “active” to “inactive”. This function is called “fishing”.

### **Keepers's rewards**

Keepers incur “gas” or blockchain transaction fees in the course of fulfilling their tasks. The protocol compensates them for these, and pays them additional rewards for the work they carry out. Keepers are rewarded according to the following rules:

1. When a Keeper performs the “collect interest” function, they are rewarded with newly minted G$s worth the gas fees incurred + 10%:
   1. For example, if the gas fees for activating the function amount to $200, the user will receive $220 in return for activation.
2. Keepers will only be able to “activate” the function when the accumulated interest to be transferred is 4 times greater than the cost of the gas fees that would be incurred in the execution of the transfer.
3. If no Keeper has executed the “activate” function for two months, the above limit no longer applies and anyone can execute this task.


# 6. The Distribution Contract (DisCo)

### **Key Terms**

**Daily reward:** The amount of G$ a verified user can claim in a 24-hour period.

**Verified user:** A user verified as real and unique.

**Active user:** A verified user who has claimed at least once in the last 2 weeks.

**Epoch:** The DisCo operates according to a three-month cycle known as an “epoch” (N.B. the duration of this cycle can be changed by the GoodDAO). The DisCo will initiate a new epoch before the cycle is completed *if* it has accepted 30% or more than the current pool left to distribute and the pool is now 80% or more of the total value of the pool at the start of the last epoch.

**Identity Contract:** A smart contract on Fuse that holds a list of all members of the GoodDollar ecosystem who are verified as real and unique. The DisCo draws upon this for distribution.

### **How the DiscCo works**

The ***DisCo***, or ***Distribution Contract***, is a smart contract that handles the distribution of G$ to all white-listed addresses (i.e. addresses verified as belonging to real and unique people in the GoodDollar ecosystem) housed in the **Identity Contract**. The DisCo is responsible for accepting G$ from elsewhere in the system and distributing this to all verified active users who have clicked “claim” in the GoodDollar Wallet app within the preceding 24 hours.

The DisCo is also responsible for calculating daily rewards, according to the below calculation:\
**Daily rewards** = (G$ in DisCo **/** days remaining in an epoch) / Active users)


# 7. Governance (DAO)

## **7. GoodDollar Governance**

The GoodDollar governance model is based on the Compound governance model and code, as set out [here](https://compound.finance/docs/governance#comp). Critical to the process is the **GOOD token**, a non-transferable token that controls all smart contracts within the GoodDollar ecosystem.

### **Governance components** <a href="#id-2e4lrx4bta1p" id="id-2e4lrx4bta1p"></a>

1. **Avatar:** A master smart contract that houses permissions for all other GoodDollar smart contracts. The Avatar can interact with external smart contracts and is able to function as a “smart wallet” for the GoodDAO.
2. **Governance module:** A VotingMachine contract that implements the Governance Specs. The governance module has permission to control the Avatar when a proposal passes.
3. **GOOD:** A Reputation Token contract that supports delegation and initial state merkle proof, used for voting in the governance module.
4. **Staker distribution:** A smart contract that distributes GOOD to users who stake capital to the GoodDollar Trust.
5. **Claimer distribution:** A smart contract that distributes GOOD to users who claim G$ tokens through the GoodDollar Wallet app.
6. **Governance Staking:** A smart contract that distributes GOOD to users who stake their G$ in this contract.

### **GoodDAO** <a href="#x9v4kk8jp487" id="x9v4kk8jp487"></a>

The ***GoodDAO*** is the decentralized autonomous organization responsible for oversight of the GoodDollar protocol. All GoodDAO members have the power to propose changes to the protocol or to the governance process. They may also vote on the proposals of others.

The GoodDAO can vote on anything directly affecting the protocol. Successful proposals for edits/additions/changes to the functionality of existing smart contracts are implemented through code upgrades. Code upgrade proposals must include the proposed new code in its final format.

### **GOOD**

***GOOD*** is the GoodDollar governance token used for voting on proposals related to the GoodDollar protocol. There are **two important points** to remember about GOOD:

1. 1 GOOD = 1 vote.
2. GOOD is a non-transferable token and therefore has no market value.

#### **Delegation**

1. Allows users to delegate/undelegate to another community member’s address.
2. Users cannot delegate the GOOD that has been delegated to them.

#### **Initial distribution of GOOD**

1. 48M (InitialAmount) GOOD goes to to the G$ **claimers**:
   1. Each Claimer receives (48M/Total Claims)\*(# times the user claimed). For example, if there have been 10,000 claims logged by the app, and the user has claimed 60 times, he will receive(48M/10,000)\*60 = 288,000
2. 24M (InitialAmount) GOOD goes to the G$ **holders**:
   1. Each G$ Holders receives (24M / Total G$ supply) \* (user holdings)
   2. For example, if the total G$ supply = 10M and a user holds 100 G$, he will receive (24M/10,000,000)\*100 = 240 GOOD.
3. 24M (initialAmount) GOOD to G$ **stakers)**:
   1. Each supporter is rewarded in proportion to their stake in DAI.

#### **Ongoing distribution of GOOD** <a href="#nhdrjwrgi6c4" id="nhdrjwrgi6c4"></a>

GOOD tokens are minted on a monthly basis for ongoing distributions. Every month, 8M GOOD will be minted and distributed as follows:

1. **4M GOOD to the G$ claimers:**
   1. Each Claimer receives (4m/Total Claims in the preceding month)\*(# times the user claimed)
   2. For example, if there were 10,000 total claims in the past month and a user has claimed 20 times, he/she will receive (4M/10,000)\*20.
2. **2M GOOD to G$ stakers:**
   1. G$ staking is a new staking contract, unrelated to all other staking contracts.
   2. G$ staking is open only on Fuse network
   3. The distribution of GDAO should be based on the calculation set out [here](https://eips.ethereum.org/EIPS/eip-2917).
3. **2M GOOD goes to users who stake via the GoodDollar Trust in proportion to the amount they have staked:**
   1. For example, if only one user has staked $1000 in the GoodDollar Trust would earn a full 2M GOOD each month.
   2. If 10 users staked 1000$ each in goodstaking they would earn 200K each.
   3. When there are multiple staking contracts, then the amount of GOOD tokens each contract rewards its stakers is proportional to the dollar value staked in that contract.

### **New Proposal and Voting processes**

#### **Key Terms**&#x20;

**The governance module:** GoodDollar’s governance module will initially be based on Compound’s contracts. The GoodDAO can elect to change this in future.\
**The proposal threshold:** The percentage of total GOOD tokens a voter must hold and/or have delegated to him/her to make a proposal. This amount is currently set at **0.25%**.\
**Quorum:** The minimum number of votes required for a proposal to be approved/overruled. This amount is currently set at **3%**.\
**The proposal period:** The time limit for a proposal to reach a quorum (3%). If a proposal does not reach a quorum within this timeframe, it is automatically overruled.\
**The countdown period:** The period allocated for voting on a proposal that has reached a quorum. This period is set at a minimum of two days. If there is a significant shift in voting within the last 24 hours of voting, the clock is reset to a full 24 hours. If voting again shifts abruptly, further 24-hour extensions will occur.

#### **Making proposals**

Any GoodDollar community member who controls more than 0.25% GOOD, either directly or through delegation, is entitled to make a proposal related to the project. There is, however, no minimum requirement for voting. Holders of any amount of GOOD can vote on proposals as they arise.

#### **Voting on proposals**

1. Proposals can only be made by community members whose wallets contain more than 0.25% GOOD (the **proposal threshold**).
2. Any GOOD holder can vote on whether to accept a proposal.
3. Voting on each proposal is open for a period of 14 days.
4. Each proposal has a threshold of 3% (the **quorum**).
   1. If fewer than 3% GOOD tokens are voted in favor of a proposal, it is overruled.
   2. If more than 3% GOOD tokens are voted in favor and fewer than 3% against, the proposal is considered approved.
   3. If more than 3% GOOD tokens are voted in favor, and more than 3% against, the proposal will be turned over to the relative voting mechanism.
5. The relative voting mechanism countdown takes place over two days, during which votes are accrued for one side or the other.
6. If there is a significant shift in voting within the last 24 hours, the clock is reset to permit a full 24 hours. If voting again shifts abruptly, further 24-hour extensions will occur.
7. Any proposal that earns more than 51% approval will be automatically approved for implementation with a shorter execution delay.

#### **Proposal status** <a href="#s7xzj9buebqs" id="s7xzj9buebqs"></a>

**Pending:** A proposal has been made but voting on it cannot yet begin.

**Active:** A proposal that can be voted on (within 14 days or, if threshold passed, until the holding period ends).

**Succeeded:** A proposal that has passed the majority threshold but has not yet been executed.

**Defeated:** A proposal that has not earned enough votes to pass within 14 days.

**Expired:** A proposal approved by a majority that was not executed within the execution threshold period (currently set at two days).

**Executed:** A proposal that was approved by a majority that has had its code executed within the execution threshold period.

**Canceled:** A proposal that lapses because a) the proposer's GOOD holdings decline below the proposal threshold, or b) the Guardian (see below) cancels the vote.

#### **Guardian rights** <a href="#mm6flsmeeyzy" id="mm6flsmeeyzy"></a>

As the GoodDollar protocol will be fully decentralized under its new governance model. As such, there is a need to safeguard the protocol from two potential vectors of attack:

1. Attempts to withdraw capital from the GoodDollar Reserve. These could be disguised within proposals to “upgrade the reserve contract”.
2. Attempts to mint G$ to line a user’s pocket. These could be hiding within proposals requesting “a grant from the protocol”.

To ensure no nefarious actor can misuse GoodDollar in such ways, the Foundation will retain the right to cancel any proposal harmful to the project or its financial integrity. The Foundation has committed to act in good faith, and will not step in unless the circumstances above arise. The GoodDAO can vote to change this from January 2023.


# Core Contracts & API

## Abstract

GoodDollar Protocol is deployed on both the Ethereum mainnet and on the Fuse sidechain. Contracts like the GoodReserve are only on Mainnet, and other contracts like the UBIScheme are only on the Fuse sidechain. Certain contracts, such as the DAO and G$ Token contracts, are deployed on both networks.

## Tables of addresses

### Core Contracts

### Core Contracts

<table><thead><tr><th width="177">Contract</th><th>Mainnet</th><th width="200">Fuse</th><th>Source code</th></tr></thead><tbody><tr><td><a href="/pages/WVvYdvIg3Av19Wz32tvh">GoodDollar ERC20</a></td><td><a href="https://etherscan.io/address/0x67C5870b4A41D4Ebef24d2456547A03F1f3e094B">0x67C5870b4A41D4Ebef24d2456547A03F1f3e094B</a></td><td><a href="https://explorer.fuse.io/address/0x495d133B938596C9984d462F007B676bDc57eCEC/transactions">0x495d133B938596C9984d462F007B676bDc57eCEC</a></td><td><a href="https://github.com/GoodDollar/GoodContracts/blob/master/contracts/token/GoodDollar.sol">GoodDollar.sol</a></td></tr><tr><td><a href="/pages/JCoaznr90CthiBiZQUte">GoodCompoundStaking V3 (DAI)</a></td><td><a href="https://etherscan.io/address/0x7b7246c78e2f900d17646ff0cb2ec47d6ba10754">0x7b7246c78e2f900d17646ff0cb2ec47d6ba10754</a></td><td></td><td><a href="https://github.com/GoodDollar/GoodProtocol/blob/master/contracts/staking/compound/GoodCompoundStakingV2.sol">GoodCompoundStakingV2.sol</a></td></tr><tr><td><a href="/pages/tDliriK1iGsri36rFzzs">GoodAaveStaking V3 (USDC)</a></td><td><a href="https://etherscan.io/address/0x3ff2d8eb2573819a9ef7167d2ba6fd6d31b17f4f">0x3ff2d8eb2573819a9ef7167d2ba6fd6d31b17f4f</a></td><td></td><td><a href="https://github.com/GoodDollar/GoodProtocol/blob/master/contracts/staking/aave/GoodAaveStakingV2.sol">GoodAaveStakingV2.sol</a></td></tr><tr><td><a href="/pages/xsNIHspuckeUUhGRPR3y">GoodReserveCDai</a></td><td><a href="https://etherscan.io/address/0xa150a825d425B36329D8294eeF8bD0fE68f8F6E0">0xa150a825d425B36329D8294eeF8bD0fE68f8F6E0</a></td><td></td><td><a href="https://github.com/GoodDollar/GoodProtocol/blob/master/contracts/reserve/GoodReserveCDai.sol">GoodReserveCDai.sol</a></td></tr><tr><td><a href="/pages/m4p7uJL6CrMypfzLOOQh">GoodFundManager</a></td><td><a href="https://etherscan.io/address/0x0c6c80d2061afa35e160f3799411d83bdeea0a5a">0x0c6c80d2061afa35e160f3799411d83bdeea0a5a</a></td><td></td><td><a href="https://github.com/GoodDollar/GoodProtocol/blob/master/contracts/staking/GoodFundManager.sol">GoodFundManager.sol</a></td></tr><tr><td><a href="/pages/kNZU3Ug6UDCTct3fzxW7">GoodMarketMaker</a></td><td><a href="https://etherscan.io/address/0xDAC6A0c973Ba7cF3526dE456aFfA43AB421f659F">0xDAC6A0c973Ba7cF3526dE456aFfA43AB421f659F</a></td><td></td><td><a href="https://github.com/GoodDollar/GoodProtocol/blob/master/contracts/reserve/GoodMarketMaker.sol">GoodMarketMaker.sol</a></td></tr><tr><td><a href="/pages/HJjWAb8trQBhladelAMY">ContributionCalculation</a></td><td><a href="https://etherscan.io/address/0x8eEC64bb6807c0178f96277cCE6a334B4e565E5C">0x8eEC64bb6807c0178f96277cCE6a334B4e565E5C</a></td><td></td><td><a href="https://github.com/GoodDollar/GoodContracts/blob/master/stakingModel/contracts/ContributionCalculation.sol">ContributionCalculation.sol</a></td></tr><tr><td><a href="/pages/U0NrK5OjVuxykl6FriMT">UBIScheme</a></td><td></td><td><a href="https://explorer.fuse.io/address/0xd253A5203817225e9768C05E5996d642fb96bA86/transactions">0xd253A5203817225e9768C05E5996d642fb96bA86</a></td><td><a href="https://github.com/GoodDollar/GoodProtocol/blob/master/contracts/ubi/UBIScheme.sol">UBIScheme.sol</a></td></tr><tr><td><a href="/pages/ur9ml5PhmQL5vwUtmGK7">Identity</a></td><td><a href="https://etherscan.io/address/0x76e76e10Ac308A1D54a00f9df27EdCE4801F288b">0x76e76e10Ac308A1D54a00f9df27EdCE4801F288b</a></td><td><a href="https://explorer.fuse.io/address/0xFa8d865A962ca8456dF331D78806152d3aC5B84F/transactions">0xFa8d865A962ca8456dF331D78806152d3aC5B84F</a></td><td><a href="https://github.com/GoodDollar/GoodContracts/blob/master/contracts/identity/Identity.sol">Identity.sol</a></td></tr><tr><td><a href="/pages/09pQYh4kBR8draZ9gbRm">FirstClaimPool</a></td><td></td><td><a href="https://explorer.fuse.io/address/0x18BcdF79A724648bF34eb06701be81bD072A2384/transactions">0x18BcdF79A724648bF34eb06701be81bD072A2384</a></td><td><a href="https://github.com/GoodDollar/GoodContracts/blob/master/stakingModel/contracts/FirstClaimPool.sol">FirstClaimPool.sol</a></td></tr><tr><td><a href="/pages/fCVOXpqYIbUzy9WlzJJy">AdminWallet</a></td><td></td><td><a href="https://explorer.fuse.io/address/0x9F75dAcB77419b87f568d417eBc84346e134144E/transactions">0x9F75dAcB77419b87f568d417eBc84346e134144E</a></td><td><a href="https://github.com/GoodDollar/GoodContracts/blob/master/contracts/wallet/AdminWallet.sol">AdminWallet.sol</a></td></tr><tr><td><a href="/pages/nFY87axjuFqot5J2Qzcs">OneTimePayments</a></td><td></td><td><a href="https://explorer.fuse.io/address/0xd9Aa86e0Ddb932bD78ab8c71C1B98F83cF610Bd4/transactions">0xd9Aa86e0Ddb932bD78ab8c71C1B98F83cF610Bd4</a></td><td><a href="https://github.com/GoodDollar/GoodContracts/blob/master/contracts/dao/schemes/OneTimePayments.sol">OneTimePayments.sol</a></td></tr><tr><td><a href="/pages/BNGLX2iHVllDB0Xyp3TZ">NameService</a></td><td><a href="https://etherscan.io/address/0xec6dcE387B1616a0c44fF2E4fA9E90E53Cf14eb0">0xec6dcE387B1616a0c44fF2E4fA9E90E53Cf14eb0</a></td><td><a href="https://explorer.fuse.io/address/0xec6dcE387B1616a0c44fF2E4fA9E90E53Cf14eb0/transactions">0xec6dcE387B1616a0c44fF2E4fA9E90E53Cf14eb0</a></td><td><a href="https://github.com/GoodDollar/GoodProtocol/blob/master/contracts/utils/NameService.sol">NameService.sol</a></td></tr><tr><td><a href="/pages/8Ko9iZn0EYD7X1eWpKtN">GReputation</a></td><td><a href="https://etherscan.io/address/0x603b8c0f110e037b51a381cbcacabb8d6c6e4543">0x603b8c0f110e037b51a381cbcacabb8d6c6e4543</a></td><td><a href="https://explorer.fuse.io/address/0x603B8C0F110E037b51A381CBCacAbb8d6c6E4543/transactions">0x603B8C0F110E037b51A381CBCacAbb8d6c6E4543</a></td><td><a href="https://github.com/GoodDollar/GoodProtocol/blob/master/contracts/governance/GReputation.sol">GReputation.sol</a></td></tr><tr><td><a href="/pages/YFGE3QTjq6Do6GQDGB2p">CompoundVotingMachine</a></td><td><a href="https://etherscan.io/address/0x57ee6ceff51cb30ecb1245934a882c500fbec1e9">0x57ee6ceff51cb30ecb1245934a882c500fbec1e9</a></td><td><a href="https://explorer.fuse.io/address/0x57Ee6Ceff51CB30Ecb1245934a882c500Fbec1e9/transactions">0x57Ee6Ceff51CB30Ecb1245934a882c500Fbec1e9</a></td><td><a href="https://github.com/GoodDollar/GoodProtocol/blob/master/contracts/governance/CompoundVotingMachine.sol">CompoundVotingMachine.sol</a></td></tr><tr><td><a href="/pages/g9vLkmjW75RZj7rUXJuk">ClaimersDistribution</a></td><td></td><td><a href="https://explorer.fuse.io/address/0x1aE4929090258A9D5000D98Cfb8A27174d345834/transactions">0x1aE4929090258A9D5000D98Cfb8A27174d345834</a></td><td><a href="https://github.com/GoodDollar/GoodProtocol/blob/master/contracts/governance/ClaimersDistribution.sol">ClaimersDistribution.sol</a></td></tr><tr><td><a href="/pages/QlJQ7skKYcpvT8vfdEC5">GovernanceStaking</a></td><td></td><td><a href="https://explorer.fuse.io/address/0xB7C3e738224625289C573c54d402E9Be46205546/transactions">0xB7C3e738224625289C573c54d402E9Be46205546</a></td><td><a href="https://github.com/GoodDollar/GoodProtocol/blob/master/contracts/governance/GovernanceStaking.sol">GovarnanceStaking.sol</a></td></tr><tr><td><a href="/pages/0XNVD4lePHhcxSDE1Fcf">Invites</a></td><td></td><td><a href="https://explorer.fuse.io/address/0xCa2F09c3ccFD7aD5cB9276918Bd1868f2b922ea0/transactions">0xCa2F09c3ccFD7aD5cB9276918Bd1868f2b922ea0</a></td><td><a href="https://github.com/GoodDollar/GoodProtocol/blob/master/contracts/invite/InvitesV1.sol">InvitesV1.sol</a></td></tr><tr><td><a href="/pages/6BzF3KwnUVIKlAMcPcwc">ExchangeHelper</a></td><td><a href="https://etherscan.io/address/0x98FA532Dd5C3a6b66fbf370813803192DE4e0abd">0x98FA532Dd5C3a6b66fbf370813803192DE4e0abd</a></td><td></td><td><a href="https://github.com/GoodDollar/GoodProtocol/blob/master/contracts/reserve/ExchangeHelper.sol">ExchangeHelper.sol</a></td></tr><tr><td><a href="/pages/qMMTIyF1b0MgoUJkkomi">StakersDistribution</a></td><td><a href="https://etherscan.io/address/0x5766cf4b2fdb09d986eb1783d276013c224e28c8">0x5766cf4b2fdb09d986eb1783d276013c224e28c8</a></td><td></td><td><a href="https://github.com/GoodDollar/GoodProtocol/blob/master/contracts/governance/StakersDistribution.sol">StakersDistribution.sol</a></td></tr><tr><td><a href="/pages/ty8W5lHNdl33tldltgkl">UniswapV2SwapHelper</a></td><td><a href="https://etherscan.io/address/0x62305662fA7c4BC442803b940d9192DbDC92D710">0x62305662fA7c4BC442803b940d9192DbDC92D710</a></td><td></td><td><a href="https://github.com/GoodDollar/GoodProtocol/blob/master/contracts/staking/UniswapV2SwapHelper.sol">UniswapV2SwapHelper.sol</a></td></tr><tr><td><a href="/pages/M34S5OPzgQZHHVL28kPr">CompoundStakingFactory</a></td><td><a href="https://etherscan.io/address/0x78cc5ab2f0990b5fe58f95baebf8f37879534aeb">0x78cc5ab2f0990b5fe58f95baebf8f37879534aeb</a></td><td></td><td><a href="https://github.com/GoodDollar/GoodProtocol/blob/master/contracts/staking/compound/CompoundStakingFactory.sol">CompoundStakingFactory.sol</a></td></tr><tr><td><a href="/pages/bPOsGIDtvRz86xbwksOX">AaveStakingFactory</a></td><td><a href="https://etherscan.io/address/0xf4411c22766947DB2da39Ad534A040b770B51153">0xf4411c22766947DB2da39Ad534A040b770B51153</a></td><td></td><td><a href="https://github.com/GoodDollar/GoodProtocol/blob/master/contracts/staking/aave/AaveStakingFactory.sol">AaveStakingFactory.sol</a></td></tr><tr><td><a href="/pages/fxq7rDYxc42Xg9fLR8JD">BancorFormula</a></td><td><a href="https://etherscan.io/address/0xA049894d5dcaD406b7C827D6dc6A0B58CA4AE73a">0xA049894d5dcaD406b7C827D6dc6A0B58CA4AE73a</a></td><td></td><td><a href="https://github.com/GoodDollar/GoodProtocol/blob/master/contracts/utils/BancorFormula.sol">BancorFormula.sol</a></td></tr><tr><td><a href="/pages/24diZjOp7ztwWUGv2KZQ">FuseFaucet</a></td><td></td><td><a href="https://explorer.fuse.io/address/0x01ab5966C1d742Ae0CFF7f14cC0F4D85156e83d9/transactions">0x01ab5966C1d742Ae0CFF7f14cC0F4D85156e83d9</a></td><td><a href="https://github.com/GoodDollar/GoodProtocol/blob/master/contracts/fuseFaucet/FuseFaucet.sol">FuseFaucet.sol</a></td></tr></tbody></table>

### Token Bridge Contracts

Bridge contracts were developed by [Fuse](https://fuse.io).

{% hint style="info" %}
Note: for regular users it is recommended to use FuseSwap Bridge in order to avoid losing your tokens ([help](https://docs.fuse.io/fuseswap/bridge-fuse-erc20-tokens)). FuseSwap Bridge: [Mainnet -> Fuse](https://fuseswap.com/#/bridge/0x67C5870b4A41D4Ebef24d2456547A03F1f3e094B) | [Fuse -> Mainnet](https://fuseswap.com/#/bridge/0x495d133B938596C9984d462F007B676bDc57eCEC).
{% endhint %}

Note: for regular users it is recommended to use FuseSwap Bridge in order to avoid losing your tokens ([help](https://docs.fuse.io/fuseswap/bridge-fuse-erc20-tokens)). FuseSwap Bridge: [Mainnet -> Fuse](https://fuseswap.com/#/bridge/0x67C5870b4A41D4Ebef24d2456547A03F1f3e094B) | [Fuse -> Mainnet](https://fuseswap.com/#/bridge/0x495d133B938596C9984d462F007B676bDc57eCEC).

### Bridge Contracts

| Contract                        | Mainnet                                                                                                               | Fuse                                                                                                                      | Source code                                                                                                                                                                   |
| ------------------------------- | --------------------------------------------------------------------------------------------------------------------- | ------------------------------------------------------------------------------------------------------------------------- | ----------------------------------------------------------------------------------------------------------------------------------------------------------------------------- |
| ForeignBridge (mainnet -> fuse) | [0xD5D11eE582c8931F336fbcd135e98CEE4DB8CCB0](https://etherscan.io/address/0xD5D11eE582c8931F336fbcd135e98CEE4DB8CCB0) |                                                                                                                           | [ForeignAMBErc677ToErc677.sol](https://github.com/fuseio/tokenbridge-contracts/blob/master/contracts/upgradeable_contracts/amb_erc677_to_erc677/ForeignAMBErc677ToErc677.sol) |
| HomeBridge (fuse -> mainnet)    |                                                                                                                       | [0xD39021DB018E2CAEadb4B2e6717D31550e7918D0](https://explorer.fuse.io/address/0xD39021DB018E2CAEadb4B2e6717D31550e7918D0) | [HomeAMBErc677ToErc677.sol](https://github.com/fuseio/tokenbridge-contracts/blob/master/contracts/upgradeable_contracts/amb_erc677_to_erc677/HomeAMBErc677ToErc677.sol)       |

### DAO Contracts

DAO contracts were developed by [DAOStack](https://daostack.io)

| Contract   | Mainnet                                                                                                               | Fuse                                                                                                                      | Source code                                                                                      |
| ---------- | --------------------------------------------------------------------------------------------------------------------- | ------------------------------------------------------------------------------------------------------------------------- | ------------------------------------------------------------------------------------------------ |
| Controller | [0x95C0d9dCEA1E243ED696F34CAc5e6559C3c128a3](https://etherscan.io/address/0x95C0d9dCEA1E243ED696F34CAc5e6559C3c128a3) | [0xBcE053b99e22158f8B62f4DBFbEdE1f936b2D4e4](https://explorer.fuse.io/address/0xBcE053b99e22158f8B62f4DBFbEdE1f936b2D4e4) | [Controller.sol](http://github.com/daostack/arc/tree/master/contracts/controller/Controller.sol) |
| Avatar     | [0x1ecFD1afb601C406fF0e13c3485f2d75699b6817](https://etherscan.io/address/0x1ecFD1afb601C406fF0e13c3485f2d75699b6817) | [0xf96dADc6D71113F6500e97590760C924dA1eF70e](https://explorer.fuse.io/address/0xf96dADc6D71113F6500e97590760C924dA1eF70e) | [Avatar.sol](http://github.com/daostack/arc/tree/master/contracts/controller/Avatar.sol)         |


# GoodDollar

The GoodDollar G$ token follows the ERC-20 token standard and also supports ERC-677.

### Events

#### Transfer

Emitted when `value` tokens are moved from one account (`from`) to another (`to`).

<table><thead><tr><th width="150">Parameter name</th><th>Annotation</th></tr></thead><tbody><tr><td>from</td><td>The address from which tokens are moved.</td></tr><tr><td>to</td><td>The address to which tokens are moved.</td></tr><tr><td>value</td><td>The value to be processed and then transferred.</td></tr></tbody></table>

Note that `value` may be zero.

```
event Transfer(address indexed from, address indexed to, uint256 value);
```

#### Approval

Emitted when the allowance of a `spender` for an `owner` is set by a call to {approve}. `value` is the new allowance.

<table><thead><tr><th width="150">Parameter name</th><th>Annotation</th></tr></thead><tbody><tr><td>owner</td><td>The address of the tokens owner.</td></tr><tr><td>spender</td><td>The address which can spend tokens in allowance.</td></tr><tr><td>value</td><td>The tokens amount to be spent on behave of the tokens owner.</td></tr></tbody></table>

```
event Approval(address indexed owner, address indexed spender, uint256 value);
```

### transfer

Processes fees from given value and sends remainder to given address.

<table><thead><tr><th width="150">Parameter name</th><th>Annotation</th></tr></thead><tbody><tr><td>to</td><td>The address to be sent to.</td></tr><tr><td>value</td><td>The value to be processed and then transferred.</td></tr></tbody></table>

Returns: a boolean that indicates if the operation was successful.

```
function transfer(address to, uint256 value) public returns (bool);
```

### approve

Approve the passed address to spend the specified amount of tokens on behalf of `msg.sender`.

<table><thead><tr><th width="150">Parameter name</th><th>Annotation</th></tr></thead><tbody><tr><td>spender</td><td>The address which will spend the funds.</td></tr><tr><td>value</td><td>The amount of tokens to be spent.</td></tr></tbody></table>

Returns: a boolean that indicates if the operation was successful.

```
function approve(address spender, uint256 value) public returns (bool);
```

### transferFrom

Transfer tokens from one address to another on behalf of the third party as `msg.sender`.

<table><thead><tr><th width="150">Parameter name</th><th>Annotation</th></tr></thead><tbody><tr><td>from</td><td>The address which you want to send tokens from.</td></tr><tr><td>to</td><td>The address which you want to transfer to.</td></tr><tr><td>value</td><td>The amount of tokens to be transferred.</td></tr></tbody></table>

Returns: a boolean that indicates if the operation was successful.

```
function transferFrom(
        address from,
        address to,
        uint256 value
    ) public returns (bool);
```

### transferAndCall

Processes transfer fees and calls ERC677Token transferAndCall function.

<table><thead><tr><th width="150">Parameter name</th><th>Annotation</th></tr></thead><tbody><tr><td>from</td><td>The address to transfer to.</td></tr><tr><td>value</td><td>The amount to transfer.</td></tr><tr><td>data</td><td>The data to be used in further execution according to ERC677.</td></tr></tbody></table>

Returns: a boolean that indicates if the operation was successful.

```
function transferAndCall(
        address to,
        uint256 value,
        bytes calldata data
    ) external returns (bool);
```

### mint

Minting function.

<table><thead><tr><th width="150">Parameter name</th><th>Annotation</th></tr></thead><tbody><tr><td>to</td><td>The address that will receive the minted tokens. Must be out of blocklist. The blocklist is managed by the administrator of the contract.</td></tr><tr><td>value</td><td>Value the amount of tokens to mint.</td></tr></tbody></table>

Who can execute: An address who is in minter role.

Returns: a boolean that indicates if the operation was successful.

```
function mint(address to, uint256 value) public;
```

### burn

Burns a specific amount of tokens.

<table><thead><tr><th width="150">Parameter name</th><th>Annotation</th></tr></thead><tbody><tr><td>value</td><td>The amount of token to be burned..</td></tr></tbody></table>

Who can execute: An address who is not blocklisted by the administration.

```
function burn(uint256 value) public;
```

### burnFrom

Burns a specific amount of tokens from the target address and decreases an allowance.

<table><thead><tr><th width="150">Parameter name</th><th>Annotation</th></tr></thead><tbody><tr><td>from</td><td>The address which you want to burn tokens from. Must not be in blocklist.</td></tr><tr><td>value</td><td>The amount of token to be burned.</td></tr></tbody></table>

Who can execute: An address who is not blocklisted by the administration.

```
function burnFrom(address from, uint256 value) public;
```

### increaseAllowance

Increase the amount of tokens that an owner allows a spender.

<table><thead><tr><th width="150">Parameter name</th><th>Annotation</th></tr></thead><tbody><tr><td>spender</td><td>The address which will spend the funds.</td></tr><tr><td>addedValue</td><td>The amount of tokens to increase the allowance by.</td></tr></tbody></table>

Returns: a boolean that indicates if the operation was successful.

```
function increaseAllowance(address spender, uint256 addedValue) public returns (bool);
```

### decreaseAllowance

Decrease the amount of tokens that an owner allowed to a spender.

<table><thead><tr><th width="150">Parameter name</th><th>Annotation</th></tr></thead><tbody><tr><td>spender</td><td>The address which will spend the funds.</td></tr><tr><td>subtractedValue</td><td>The amount of tokens to decrease the allowance by.</td></tr></tbody></table>

Returns: a boolean that indicates if the operation was successful.

```
function decreaseAllowance(address spender, uint256 subtractedValue) public returns (bool);
```

### getFees

Gets the current transaction fees.

<table><thead><tr><th width="150">Parameter name</th><th>Annotation</th></tr></thead><tbody><tr><td>value</td><td>Value the amount of tokens to mint.</td></tr></tbody></table>

Returns: tuple of `uint256` and `bool`, first is an absolute amount of fees based on value and the second is whether `msg.sender` paying or not.

```
function getFees(uint256 value) public view returns (uint256, bool);
```

### setFeeRecipient

Sets the address that receives the transactional fees.

<table><thead><tr><th width="150">Parameter name</th><th>Annotation</th></tr></thead><tbody><tr><td>_feeRecipient</td><td>The new address to receive transactional fees.</td></tr></tbody></table>

Who can execute: An adminstrator only.

```
function setFeeRecipient(address _feeRecipient) public;
```


# GoodCompoundStaking V2 (DAI)

Supporters / stakers can stake their DAI which is sent to permissionless protocols which earn interest. The FundManager has permissions to collect interest-earned from this contract.

### Events

#### Staked

Emitted when `staker` stake `value` tokens of `token`.

<table><thead><tr><th width="150">Parameter name</th><th>Annotation</th></tr></thead><tbody><tr><td>staker</td><td>The address of the staker.</td></tr><tr><td>token</td><td>The address of the staking token.</td></tr><tr><td>value</td><td>The value to be staked.</td></tr></tbody></table>

```
event Staked(address indexed staker, address token, uint256 value);
```

#### StakeWithdraw

Emitted when `staker` withdraws their stake `value` tokens of `token`.

<table><thead><tr><th width="150">Parameter name</th><th>Annotation</th></tr></thead><tbody><tr><td>staker</td><td>The address of the staker.</td></tr><tr><td>token</td><td>The address of the staking token that beign withdrawn.</td></tr><tr><td>value</td><td>The value to be withdrawn.</td></tr></tbody></table>

```
event StakeWithdraw(address indexed staker, address token, uint256 value);
```

#### InterestCollected

Emitted when fundmanager transfers interest collected from DeFi protrocol.

<table><thead><tr><th width="150">Parameter name</th><th>Annotation</th></tr></thead><tbody><tr><td>recipient</td><td>The recipient address of the interest</td></tr><tr><td>iTokenGains</td><td>The amount of intereset accrued.</td></tr><tr><td>tokenGains</td><td>The amount of interest worth in underlying token value.</td></tr><tr><td>actualTokenRedeemed</td><td>Actual token redeemed in Uniswap V2 (max 0.3% of liquidity) to token (in this case DAI).</td></tr><tr><td>actualRewardTokenEarned</td><td>Actual amount of reward tokens earned.</td></tr><tr><td>interestCollectedInDAI</td><td>Actual DAI amount sent to the reserve as interest from converting token and optionally reward token in Uniswap V2.</td></tr></tbody></table>

```
event InterestCollected(
		address recipient,
		uint256 iTokenGains,
		uint256 tokenGains,
		uint256 actualTokenRedeemed,
		uint256 actualRewardTokenEarned,
		uint256 interestCollectedInDAI
	);
```

### getSettings

View function to get protocol management fees.

Returns: a tuple of `_collectInterestGasCost` and `_compCollectGasCost` which represents the gas cost fee for collecting interest from the contract and gas cost fee for collecting COMP rewards.

```
function getSettings() external view returns (uint32 _collectInterestGasCost, uint32 _compCollectGasCost);
```

### currentGains

Function that calculates current interest gains of this staking contract.

<table><thead><tr><th width="150">Parameter name</th><th>Annotation</th></tr></thead><tbody><tr><td>_returnTokenBalanceInUSD</td><td>Determine return token balance of staking contract in USD.</td></tr><tr><td>_returnTokenGainsInUSD</td><td>Determine return token gains of staking contract in USD.</td></tr></tbody></table>

<table><thead><tr><th width="278.57142857142856">Return parameter name</th><th>Annotation</th></tr></thead><tbody><tr><td>iTokenGains</td><td>Gains in iToken (in this case cDAI).</td></tr><tr><td>tokenGains</td><td>Gains in token (in this case DAI).</td></tr><tr><td>tokenBalance</td><td>Total tokens locked.</td></tr><tr><td>balanceInUSD</td><td>Locked tokens worth in USD.</td></tr><tr><td>tokenGainsInUSD</td><td>Gains in USD.</td></tr></tbody></table>

```
function currentGains(
	bool _returnTokenBalanceInUSD,
	bool _returnTokenGainsInUSD
)
	public
	view
	override
	returns (
		uint256 iTokenGains,
		uint256 tokenGains,
		uint256 tokenBalance,
		uint256 balanceInUSD,
		uint256 tokenGainsInUSD
	);
```

### stake

Allows a staker to deposit Tokens (in this case DAI). Notice that `approve` is needed to be executed before the execution of this method.

<table><thead><tr><th width="150">Parameter name</th><th>Annotation</th></tr></thead><tbody><tr><td>_amount</td><td>The amount of Token (in this case DAI) or iToken (in this case cDAI) to stake (it depends on <code>_inInterestToken</code> parameter).</td></tr><tr><td>_donationPer</td><td>The % of interest staker want to donate.</td></tr><tr><td>_inInterestToken</td><td>Specificy if stake in iToken (in this case cDAI) or Token (in this case DAI).</td></tr></tbody></table>

Can be executed only when the contract is not paused.

```
function stake(
		uint256 _amount,
		uint256 _donationPer,
		bool _inInterestToken
	) external virtual;
```

### withdrawStake

Withdraws the sender staked Token (in this case DAI).

<table><thead><tr><th width="301.8711599216471">Parameter name</th><th>Annotation</th></tr></thead><tbody><tr><td>_amount</td><td>Amount to withdraw in Token (in this case DAI) or iToken (in this case cDAI).</td></tr><tr><td>_inInterestToken</td><td>If <code>true</code> <code>_amount</code> is in iToken (in this case cDAI) and also returned in iToken otherwise use Token (in this case DAI).</td></tr></tbody></table>

Can be executed only when the contract is not paused.

```
function withdrawStake(uint256 _amount, bool _inInterestToken) external virtual;
```

### withdrawRewards

Withdraw staker G$ rewards + GDAO (GOOD) rewards to the caller (staker).

```
function withdrawRewards() external;
```

### claimReputation

Withdraw staker GDAO (GOOD) rewards to the caller (staker).

```
function claimReputation() public;
```

### collectUBIInterest

Collects gained interest (in G$) by fundmanager.

<table><thead><tr><th width="150">Parameter name</th><th>Annotation</th></tr></thead><tbody><tr><td>_recipient</td><td>The recipient of iToken (in this case cDAI) gains.</td></tr></tbody></table>

<table><thead><tr><th width="278.57142857142856">Return parameter name</th><th>Annotation</th></tr></thead><tbody><tr><td>actualTokensRedeemed</td><td>Collected interest from token.</td></tr><tr><td>actualRewardTokenRedeemed</td><td>Collected interest from reward token.</td></tr><tr><td>actualDai</td><td>Total Token (in this case DAI) received from swapping token + reward token.</td></tr></tbody></table>

```
function collectUBIInterest(address _recipient)
		public
		virtual
		returns (
			uint256 actualTokenRedeemed,
			uint256 actualRewardTokenRedeemed,
			uint256 actualDai
		);
```

### getTokenValueInUSD

The function is to calculate Token (in this case DAI) price in USD.

<table><thead><tr><th width="150">Parameter name</th><th>Annotation</th></tr></thead><tbody><tr><td>_oracle</td><td>Chainlink oracle usd/token oralce.</td></tr><tr><td>_amount</td><td>Amount of Token to calculate worth of it.</td></tr><tr><td>_decimals</td><td>Decimals of Token.</td></tr></tbody></table>

Returns: worth of Tokens in USD, the decimals are 8.

```
function getTokenValueInUSD(
		address _oracle,
		uint256 _amount,
		uint256 _decimals
	) public view returns (uint256);
```

### getUserMintedAndPending

The function that can provide information about minted and pending rewards in G$ of the `_staker`.

<table><thead><tr><th width="150">Parameter name</th><th>Annotation</th></tr></thead><tbody><tr><td>_staker</td><td>Account to get rewards status for.</td></tr></tbody></table>

Returns: The first element of the tuple is Minted value and the second is Pending value in G$; 2 decimals.

```
function getUserMintedAndPending(address _staker)
		external
		view
		returns (uint256, uint256);
```


# GoodAaveStaking V2 (USDC)

Supporters / stakers can stake their USDC which is sent to permissionless protocols which earn interest. The FundManager has permissions to collect interest-earned from this contract.

### Events

#### Staked

Emitted when `staker` stake `value` tokens of `token`.

<table><thead><tr><th width="285.809320129277">Parameter name</th><th>Annotation</th></tr></thead><tbody><tr><td>staker</td><td>The address of the staker.</td></tr><tr><td>token</td><td>The address of the staking token.</td></tr><tr><td>value</td><td>The value to be staked.</td></tr></tbody></table>

```
event Staked(address indexed staker, address token, uint256 value);
```

#### StakeWithdraw

Emitted when `staker` withdraws their stake `value` tokens of `token`.

<table><thead><tr><th width="150">Parameter name</th><th>Annotation</th></tr></thead><tbody><tr><td>staker</td><td>The address of the staker.</td></tr><tr><td>token</td><td>The address of the staking token that beign withdrawn.</td></tr><tr><td>value</td><td>The value to be withdrawn.</td></tr></tbody></table>

```
event StakeWithdraw(address indexed staker, address token, uint256 value);
```

#### InterestCollected

Emitted when fundmanager transfers interest collected from DeFi protrocol.

<table><thead><tr><th width="150">Parameter name</th><th>Annotation</th></tr></thead><tbody><tr><td>recipient</td><td>The recipient address of the interest</td></tr><tr><td>iTokenGains</td><td>The amount of intereset accrued.</td></tr><tr><td>tokenGains</td><td>The amount of interest worth in underlying token value.</td></tr><tr><td>actualTokenRedeemed</td><td>Actual token redeemed in Uniswap V2 (max 0.3% of liquidity) to token (in this case USDC).</td></tr><tr><td>actualRewardTokenEarned</td><td>Actual amount of reward tokens earned.</td></tr><tr><td>interestCollectedInDAI</td><td>The DAI amount of USDC tokens sent to the reserve as interest from converting token and optionally reward token in Uniswap V2.</td></tr></tbody></table>

```
event InterestCollected(
		address recipient,
		uint256 iTokenGains,
		uint256 tokenGains,
		uint256 actualTokenRedeemed,
		uint256 actualRewardTokenEarned,
		uint256 interestCollectedInDAI
	);
```

### currentGains

Function that calculates current interest gains of this staking contract.

<table><thead><tr><th width="150">Parameter name</th><th>Annotation</th></tr></thead><tbody><tr><td>_returnTokenBalanceInUSD</td><td>Determine return token balance of staking contract in USD.</td></tr><tr><td>_returnTokenGainsInUSD</td><td>Determine return token gains of staking contract in USD.</td></tr></tbody></table>

<table><thead><tr><th width="278.57142857142856">Return parameter name</th><th>Annotation</th></tr></thead><tbody><tr><td>iTokenGains</td><td>Gains in iToken (in this case cUSDC).</td></tr><tr><td>tokenGains</td><td>Gains in token (in this case USDC).</td></tr><tr><td>tokenBalance</td><td>Total tokens locked.</td></tr><tr><td>balanceInUSD</td><td>Locked tokens worth in USD.</td></tr><tr><td>tokenGainsInUSD</td><td>Gains in USD.</td></tr></tbody></table>

```
function currentGains(
	bool _returnTokenBalanceInUSD,
	bool _returnTokenGainsInUSD
)
	public
	view
	override
	returns (
		uint256 iTokenGains,
		uint256 tokenGains,
		uint256 tokenBalance,
		uint256 balanceInUSD,
		uint256 tokenGainsInUSD
	);
```

### stake

Allows a staker to deposit Tokens (in this case DAI). Notice that `approve` is needed to be executed before the execution of this method.

<table><thead><tr><th width="150">Parameter name</th><th>Annotation</th></tr></thead><tbody><tr><td>_amount</td><td>The amount of Token (in this case USDC) or iToken (in this case cUSDC) to stake (it depends on <code>_inInterestToken</code> parameter).</td></tr><tr><td>_donationPer</td><td>The % of interest staker want to donate.</td></tr><tr><td>_inInterestToken</td><td>Specificy if stake in iToken (in this case cUSDC) or Token (in this case USDC).</td></tr></tbody></table>

Can be executed only when the contract is not paused.

```
function stake(
		uint256 _amount,
		uint256 _donationPer,
		bool _inInterestToken
	) external virtual;
```

### withdrawStake

Withdraws the sender staked Token (in this case USDC).

<table><thead><tr><th width="225.57142857142856">Parameter name</th><th>Annotation</th></tr></thead><tbody><tr><td>_amount</td><td>Amount to withdraw in Token (in this case USDC) or iToken (in this case cUSDC).</td></tr><tr><td>_inInterestToken</td><td>If <code>true</code> <code>_amount</code> is in iToken (in this case cUSDC) and also returned in iToken otherwise use Token (in this case USDC).</td></tr></tbody></table>

Can be executed only when the contract is not paused.

```
function withdrawStake(uint256 _amount, bool _inInterestToken) external virtual;
```

### withdrawRewards

Withdraw staker G$ rewards + GDAO (GOOD) rewards to the caller (staker).

```
function withdrawRewards() external;
```

### claimReputation

Withdraw staker GDAO (GOOD) rewards to the caller (staker).

```
function claimReputation() public;
```

### collectUBIInterest

Collects gained interest (in G$) by fundmanager.

<table><thead><tr><th width="150">Parameter name</th><th>Annotation</th></tr></thead><tbody><tr><td>_recipient</td><td>The recipient of iToken (in this case cUSDC) gains.</td></tr></tbody></table>

<table><thead><tr><th width="278.57142857142856">Return parameter name</th><th>Annotation</th></tr></thead><tbody><tr><td>actualTokensRedeemed</td><td>Collected interest from token.</td></tr><tr><td>actualRewardTokenRedeemed</td><td>Collected interest from reward token.</td></tr><tr><td>actualDai</td><td>Total Token (in this case USDC amount equal to DAI amount) received from swapping token + reward token.</td></tr></tbody></table>

```
function collectUBIInterest(address _recipient)
		public
		virtual
		returns (
			uint256 actualTokenRedeemed,
			uint256 actualRewardTokenRedeemed,
			uint256 actualDai
		);
```

### getTokenValueInUSD

The function is to calculate Token (in this case USDC) price in USD.

<table><thead><tr><th width="150">Parameter name</th><th>Annotation</th></tr></thead><tbody><tr><td>_oracle</td><td>Chainlink oracle usd/token oralce.</td></tr><tr><td>_amount</td><td>Amount of Token to calculate worth of it.</td></tr><tr><td>_decimals</td><td>Decimals of Token.</td></tr></tbody></table>

Returns: worth of Tokens in USD, the decimals are 8.

```
function getTokenValueInUSD(
		address _oracle,
		uint256 _amount,
		uint256 _decimals
	) public view returns (uint256);
```

### getUserMintedAndPending

The function that can provide information about minted and pending rewards in G$ of the `_staker`.

<table><thead><tr><th width="150">Parameter name</th><th>Annotation</th></tr></thead><tbody><tr><td>_staker</td><td>Account to get rewards status for.</td></tr></tbody></table>

Returns: The first element of the tuple is Minted value and the second is Pending value in G$; 2 decimals.

```
function getUserMintedAndPending(address _staker)
		external
		view
		returns (uint256, uint256);
```

### getGasCostForInterestTransfer

Function to get interest transfer cost for this particular staking contract.

Returns: Gas cost in wei.

```
function getGasCostForInterestTransfer()
		external
		view
		override
		returns (uint32);
```


# GoodReserveCDai

The GoodReserveCDai mints G$ based on the interest transferred from the FundManager. Only the FundManager can trigger minting.

The contract also acts as the GoodDollar liquidity pool and AMM (Automatic Market Maker) and enables methods to buy and sell G$s.

### Events

#### UBIMinted

Emitted when new G$ tokens are minted.

<table><thead><tr><th width="281.57142857142856">Parameter name</th><th>Annotation</th></tr></thead><tbody><tr><td>day</td><td>Epoch of UBI.</td></tr><tr><td>interestToken</td><td>The token paid as interest.</td></tr><tr><td>interestReceived</td><td>Wei amount of interest paid in <code>interestToken</code>.</td></tr><tr><td>gdInterestMinted</td><td>Amount of G$ tokens that was added to the supply as result of <code>mintInterest</code> function.</td></tr><tr><td>gdExpansionMinted</td><td>Amount of G$ tokens that was added to the supply as a result of <code>mintExpansion</code> function.</td></tr><tr><td>gdUbiTransferred</td><td>Amount of G$ tokens that was minted to the <code>ubiCollector</code> contract.</td></tr></tbody></table>

```
event UBIMinted(
    uint256 indexed day,
    address indexed interestToken,
    uint256 interestReceived,
    uint256 gdInterestMinted,
    uint256 gdExpansionMinted,
    uint256 gdUbiTransferred
);
```

#### TokenPurchased

Emitted when G$ tokens are purchased from the reserve.

<table><thead><tr><th width="281.57142857142856">Parameter name</th><th>Annotation</th></tr></thead><tbody><tr><td>caller</td><td>The initiate person of the event.</td></tr><tr><td>inputToken</td><td>The convertible token address which the G$ tokens were purchased with.</td></tr><tr><td>inputAmount</td><td>Reserve tokens amount.</td></tr><tr><td>actualReturn</td><td>Actual return of the tokens after the conversion.</td></tr><tr><td>receiverAddress</td><td>The address of the receiver of tokens.</td></tr></tbody></table>

```
event TokenPurchased(
    address indexed caller,
    address indexed inputToken,
    uint256 inputAmount,
    uint256 actualReturn,
    address indexed receiverAddress
);
```

#### TokenSold

Emitted when G$ tokens are sold to the reserve.

<table><thead><tr><th width="281.57142857142856">Parameter name</th><th>Annotation</th></tr></thead><tbody><tr><td>caller</td><td>The initiate person of the event.</td></tr><tr><td>outputToken</td><td>The convertible token address which the G$ tokens were sold to.</td></tr><tr><td>gdAmount</td><td>Reserve tokens amount.</td></tr><tr><td>contributionAmount</td><td>Actual return of the tokens after the conversion.</td></tr><tr><td>actualReturn</td><td>The address of the receiver of tokens.</td></tr><tr><td>receiverAddress</td><td>The address of the receiver of the tokens.</td></tr></tbody></table>

```
event TokenSold(
	address indexed caller,
	address indexed outputToken,
	uint256 gdAmount,
	uint256 contributionAmount,
	uint256 actualReturn,
	address indexed receiverAddress
);
```

### buy

Converts cDai tokens to GD tokens and updates the bonding curve params. The `buy` occurs only if the G$ return is above the given minimum. It is possible to buy only with cDAI and when the contract is set to active. MUST call to cDAI `approve` prior this action to allow this contract to accomplish the conversion.

| Parameter name  | Annotation                                                       |
| --------------- | ---------------------------------------------------------------- |
| \_tokenAmount   | The amount of cDAI tokens that should be converted to G$ tokens. |
| \_minReturn     | The minimum allowed return in G$ tokens.                         |
| \_targetAddress | Address of G$ and GOOD recipient if different than `msg.sender`. |

Returns: How much G$ tokens were transferred.

```
function buy(
    uint256 _tokenAmount,
    uint256 _minReturn,
    address _targetAddress
) external returns (uint256);
```

### sell

The `sell` helper function burns G$ tokens and update the bonding curve params. The `sell` occurs only if the token return is above the given minimum. Notice that there is a contribution amount from the given GD that remains in the reserve.

<table><thead><tr><th width="181.24390236164845">Parameter name</th><th>Annotation</th></tr></thead><tbody><tr><td>_gdAmount</td><td>The amount of GD tokens that should be converted to cDAI tokens.</td></tr><tr><td>_minReturn</td><td>The minimum allowed amount of cDAI tokens to return.</td></tr><tr><td>_target</td><td>Address of the receiver of cDAI when sell G$.</td></tr><tr><td>_seller</td><td>Address of the seller when using helper contract.</td></tr></tbody></table>

Returns: The tuple of two: cDAI received amount and G$ exit contribution.

```
function sell(
		uint256 _gdAmount,
		uint256 _minReturn,
		address _target,
		address _seller
	) external returns (uint256, uint256);
```

### mintRewardFromRR

Mint rewards for staking contracts in G$ and update RR requires minting permissions which is enforced by [`_mintGoodDollars`](https://github.com/GoodDollar/GoodProtocol/blob/master/contracts/reserve/GoodReserveCDai.sol#L305) function.

<table><thead><tr><th width="181.24390236164845">Parameter name</th><th>Annotation</th></tr></thead><tbody><tr><td>_token</td><td>The amount of GD tokens that should be converted to cDAI tokens.</td></tr><tr><td>_to</td><td>The minimum allowed amount of cDAI tokens to return.</td></tr><tr><td>_amount</td><td>Address of the receiver of cDAI when sell G$.</td></tr></tbody></table>

Returns: The tuple of two: cDAI received amount and G$ exit contribution.

```
function mintRewardFromRR(
		address _token,
		address _to,
		uint256 _amount
	) public;
```

### mintUBI

Only FundManager or other with mint G$ permission can call this to trigger minting. Reserve sends UBI + interest to FundManager.

<table><thead><tr><th width="181.24390236164845">Parameter name</th><th>Annotation</th></tr></thead><tbody><tr><td>_daiToConvert</td><td>DAI amount to convert cDAI.</td></tr><tr><td>_startingCDAIBalance</td><td>Initial cDAI balance before staking collect process start.</td></tr><tr><td>_interestToken</td><td>The token that was transfered to the reserve.</td></tr></tbody></table>

Returns: The tuple of two: how much GD UBI was minted and how much cDAI collected from staking contracts.

```
function mintUBI(
		uint256 _daiToConvert,
		uint256 _startingCDAIBalance,
		ERC20 _interestToken
	) public returns (uint256, uint256)
```


# GoodFundManager

Has permissions to collect interest from the staking contracts and permissions to tell GoodMarketMaker to mint. Anyone can trigger the collection and minting process.

### Events

#### StakingRewardSet

Emitted when admin sets the reward for particular staking contract.

<table><thead><tr><th width="281.57142857142856">Parameter name</th><th>Annotation</th></tr></thead><tbody><tr><td>_rewardsPerBlock</td><td>The amount of rewards per block that should be distributed.</td></tr><tr><td>_stakingAddress</td><td>An address of the staking contract.</td></tr><tr><td>_blockStart</td><td>The number of block from which the distribution starts.</td></tr><tr><td>_blockEnd</td><td>The number of block from which the distribution ends.</td></tr><tr><td>_isBlackListed</td><td>Answers the question: is the staking contract allowed to mint the rewards.</td></tr></tbody></table>

```
event StakingRewardSet(
    uint32 _rewardsPerBlock,
    address _stakingAddress,
    uint32 _blockStart,
    uint32 _blockEnd,
    bool _isBlackListed
);
```

#### GasCostSet

Emitted when admin sets the gas cost for G$ minting.

<table><thead><tr><th width="281.57142857142856">Parameter name</th><th>Annotation</th></tr></thead><tbody><tr><td>_newGasCost</td><td>The amount of gas it costs for minting G$ reward.</td></tr></tbody></table>

```
event GasCostSet(uint256 newGasCost);
```

#### CollectInterestTimeThresholdSet

Emitted when admin sets the number that is used in a calculation of time after `collectInterest` method call.

<table><thead><tr><th width="281.57142857142856">Parameter name</th><th>Annotation</th></tr></thead><tbody><tr><td>newCollectInterestTimeThreshold</td><td>This number is used in a calculation that should determine how much time should pass after <code>collectInterest</code> method called.</td></tr></tbody></table>

```
event CollectInterestTimeThresholdSet(uint256 newCollectInterestTimeThreshold);
```

#### InterestMultiplierSet

Emitted when admin sets the multiplier.

<table><thead><tr><th width="281.57142857142856">Parameter name</th><th>Annotation</th></tr></thead><tbody><tr><td>newInterestMultiplier</td><td>This amount is used in determination of how much times larger should be collected interest than spent gas when <code>collectInterestTimeThreshold</code> did not pass.</td></tr></tbody></table>

```
event InterestMultiplierSet(uint8 newInterestMultiplier);
```

#### GasCostSet

Emitted when admin sets the gas cost for G$ minting.

<table><thead><tr><th width="281.57142857142856">Parameter name</th><th>Annotation</th></tr></thead><tbody><tr><td>newGasCostExceptInterestCollect</td><td>The new gas cost for required transactions after collecting interest in <code>collectInterest</code> function. The aim of this is to know if caller has enough gas left to keep collecting interest.</td></tr></tbody></table>

```
event GasCostExceptInterestCollectSet(uint256 newGasCostExceptInterestCollect);
```

### buy

Converts cDai tokens to GD tokens and updates the bonding curve params. The `buy` occurs only if the G$ return is above the given minimum. It is possible to buy only with cDAI and when the contract is set to active. MUST call to cDAI `approve` prior this action to allow this contract to accomplish the conversion.

| Parameter name  | Annotation                                                       |
| --------------- | ---------------------------------------------------------------- |
| \_tokenAmount   | The amount of cDAI tokens that should be converted to G$ tokens. |
| \_minReturn     | The minimum allowed return in G$ tokens.                         |
| \_targetAddress | Address of G$ and GOOD recipient if different than `msg.sender`. |

Returns: How much G$ tokens were transferred.

```
function buy(
    uint256 _tokenAmount,
    uint256 _minReturn,
    address _targetAddress
) external returns (uint256);
```

### collectInterest

Collects UBI interest in iToken from a given staking contract and transfers that interest to the reserve contract. Then transfers the given G$ which received from the reserve contract back to the staking contract and to the bridge, which locks the funds and then the G$ tokens are been minted to the given address on the sidechain.

| Parameter name          | Annotation                                                                                                                                                      |
| ----------------------- | --------------------------------------------------------------------------------------------------------------------------------------------------------------- |
| \_stakingContracts      | An array of staking contract addresses from which contracts to collect interest.                                                                                |
| \_forceAndWaiverRewards | The boolean flag, that if it is set to true, it'll collect interest even if threshold is not passed, but won't reward caller with gas refund and reward itself. |

```
function collectInterest(
	address[] calldata _stakingContracts,
	bool _forceAndWaiverRewards
) external;
```

### calcSortedContracts

The function gets interest informations of staking contracts in the sorted array. By highest interest to lowest interest amount.

Returns: An array of struct instances. The struct explained below.

| Field name                  | Annotation                                                                                  | Field type |
| --------------------------- | ------------------------------------------------------------------------------------------- | ---------- |
| contractAddress             | Staking contract address which interest will be collected.                                  | address    |
| interestBalance             | Interest amount that staking contract has.                                                  | uint256    |
| collectedInterestSoFar      | Collected interest amount so far including the contract to which the stuct instance belong. | uint256    |
| gasCostSoFar                | Spent gas amount so far including this contract.                                            | uin256     |
| maxGasAmountSoFar           | Max gas amount that can spend to collect this interest according to interest amount.        | uin256     |
| maxGasLargerOrEqualRequired | Bool that indicates if max gas amount larger or equal to actual gas needed.                 | bool       |

```
function calcSortedContracts() public view returns (InterestInfo[] memory);
```

### mintReward

This function mint to users reward tokens which they earned by staking contract.

| Parameter name | Annotation                                  |
| -------------- | ------------------------------------------- |
| \_token        | Reserve token (currently can be just cDAI). |
| \_user         | User to get rewards.                        |

```
function mintReward(address _token, address _user) public;
```


# GoodMarketMaker

Helper contract for the GoodReserveCDai. It serves as a dynamic reserve ratio market maker.

### Events

#### BalancesUpdated

Emits when a change has occurred in a reserve balance, i.e. buy / sell will change the balance.

<table><thead><tr><th width="200.9737758180553">Parameter name</th><th>Annotation</th></tr></thead><tbody><tr><td>caller</td><td>The account who initiated the action.</td></tr><tr><td>reserveToken</td><td>The address of the reserve token.</td></tr><tr><td>amount</td><td>The incoming amount.</td></tr><tr><td>returnAmount</td><td>The return value.</td></tr><tr><td>totalSupply</td><td>The updated total supply.</td></tr><tr><td>reserveBalance</td><td>The updated reserve balance.</td></tr></tbody></table>

```
event BalancesUpdated(
    address indexed caller,
    address indexed reserveToken,
    uint256 amount,
    uint256 returnAmount,
    uint256 totalSupply,
    uint256 reserveBalance
);
```

#### ReserveRatioUpdated

Emits when the ratio changed. The caller should be the Avatar by definition.

<table><thead><tr><th width="200.9737758180553">Parameter name</th><th>Annotation</th></tr></thead><tbody><tr><td>caller</td><td>The address of the staker.</td></tr><tr><td>nom</td><td>Nominator of the ratio.</td></tr><tr><td>denom</td><td>Denominator of the ratio.</td></tr></tbody></table>

```
event ReserveRatioUpdated(address indexed caller, uint256 nom, uint256 denom);
```

### calculateNewReserveRatio

Calculates how much to decrease the reserve ratio for `_token` by the `reserveRatioDailyExpansion`.

| Parameter name | Annotation                                            |
| -------------- | ----------------------------------------------------- |
| \_token        | The reserve token to calculate the reserve ratio for. |

Returns: the new reserve ratio.

```
function calculateNewReserveRatio(ERC20 _token) public view returns (uint32);
```

### buyReturn

Calculates the buy return in G$ according to the given `_tokenAmount`.

| Parameter name | Annotation                               |
| -------------- | ---------------------------------------- |
| \_token        | The reserve token buying with.           |
| \_tokenAmount  | The amount of reserve token buying with. |

Returns: A number of G$ that should be given in exchange as calculated by the bonding curve.

```
function buyReturn(ERC20 _token, uint256 _tokenAmount);
```

### sellReturn

Calculates the sell return in `_token` according to the given `_gdAmount`.

| Parameter name | Annotation                               |
| -------------- | ---------------------------------------- |
| \_token        | The reserve token buying with.           |
| \_gdAmount     | The amount of reserve token buying with. |

Returns: A number of tokens that should be given in exchange as calculated by the bonding curve.

```
function sellReturn(ERC20 _token, uint256 _gdAmount);
```

### buy

Updates the `_token` bonding curve params. Emits `BalancesUpdated` with the new reserve token information.

| Parameter name | Annotation                               |
| -------------- | ---------------------------------------- |
| \_token        | The reserve token buying with.           |
| \_tokenAmount  | The amount of reserve token buying with. |

Returns: A number of G$ that will be given in exchange as calculated by the bonding curve.

```
function buy(ERC20 _token, uint256 _tokenAmount);
```

### sellWithContribution

Calculates the sell return with contribution in `_token` and update the bonding curve params. Emits `BalancesUpdated` with the new reserve token information.

| Parameter name         | Annotation                                                             |
| ---------------------- | ---------------------------------------------------------------------- |
| \_token                | The desired reserve token to have.                                     |
| \_gdAmount             | The amount of G$ that are sold.                                        |
| \_contributionGdAmount | The number of G$ tokens that will not be traded for the reserve token. |

Returns: A number of tokens that will be given in exchange as calculated by the bonding curve.

```
function sellWithContribution(
	ERC20 _token,
	uint256 _gdAmount,
	uint256 _contributionGdAmount
) public returns (uint256);
```


# ContributionCalculation

Helper contract for calculating the exit contribution (i.e. when selling G$ back to the reserve).

### Events

#### SellContributionRatioUpdated

Emits when the contribution ratio is updated.

<table><thead><tr><th width="320.9082692632695">Parameter name</th><th>Annotation</th></tr></thead><tbody><tr><td>caller</td><td>The address of the Avatar.</td></tr><tr><td>nom</td><td>The nominator of the ratio.</td></tr><tr><td>denom</td><td>The denominator of the ratio.</td></tr></tbody></table>

```
event SellContributionRatioUpdated(
    address indexed caller, 
    uint256 nom, 
    uint256 denom
);
```

### calculateContribution

Calculate the amount after contribution during the sell action. There is a `sellContributionRatio` percent contribution.

| Parameter name | Annotation                              |
| -------------- | --------------------------------------- |
| \_marketMaker  | The market maker address.               |
| \_reserve      | The reserve address.                    |
| \_contributer  | The contributer address.                |
| \_token        | The token to convert from.              |
| \_gdAmount     | The total G$ amount to contribute from. |

Returns: the contribution amount for sell.

```
function calculateContribution(
   GoodMarketMaker _marketMaker,
   GoodReserveCDai _reserve,
   address _contributer,
   ERC20 _token,
   uint256 _gdAmount
) external view returns (uint256);
```


# UBIScheme

Holds all the G$s that were transferred via bridge from the FundManager.

The pool of G$s is divided equally by the amount of current active users, and distributed every day. Each active user can then "claim" his quota. If a user fails to claim his quota it becomes part of the next day's pool of G$ to be distributed as basic income.

### Events

#### WithdrawFromDao

Emits when a withdraw has been succeded.

<table><thead><tr><th width="285.809320129277">Parameter name</th><th>Annotation</th></tr></thead><tbody><tr><td>prevBalance</td><td>The balance before the withdraw.</td></tr><tr><td>newBalance</td><td>The balance after the withdraw.</td></tr></tbody></table>

```
event WithdrawFromDao(uint256 prevBalance, uint256 newBalance);
```

#### ActivatedUser

Emits when a user is activated.

<table><thead><tr><th width="285.809320129277">Parameter name</th><th>Annotation</th></tr></thead><tbody><tr><td>account</td><td>The user that was activated.</td></tr></tbody></table>

```
event ActivatedUser(address indexed account);
```

#### InactiveUserFished

Emits when a `fish` call has been succeded.

<table><thead><tr><th width="285.809320129277">Parameter name</th><th>Annotation</th></tr></thead><tbody><tr><td>caller</td><td>The user that doing "fishing".</td></tr><tr><td>fished_account</td><td>The user that has beed "fished".</td></tr><tr><td>claimAmount</td><td>The amount of tokens caller got for "fishing".</td></tr></tbody></table>

```
event InactiveUserFished(
    address indexed caller,
    address indexed fished_account,
    uint256 claimAmount
);
```

#### TotalFished

Emits when finishing a "multi fish" execution. Indicates the number of users from the given array who actually been fished. It might not be finished going over all the array if there no gas left.

<table><thead><tr><th width="285.809320129277">Parameter name</th><th>Annotation</th></tr></thead><tbody><tr><td>total</td><td>The amount of total user that were "fished".</td></tr></tbody></table>

```
event TotalFished(uint256 total);
```

#### UBICalculated

Emits when daily UBI is calculated.

<table><thead><tr><th width="285.809320129277">Parameter name</th><th>Annotation</th></tr></thead><tbody><tr><td>day</td><td>The timestamp when this event was emitted.</td></tr><tr><td>dailyUbi</td><td>The amount of UBI per daily cycle.</td></tr><tr><td>blockNumber</td><td>The block number when this event was emitted.</td></tr></tbody></table>

```
event UBICalculated(uint256 day, uint256 dailyUbi, uint256 blockNumber);
```

#### UBICycleCalculated

Emits whenever a new multi day cycle starts.

<table><thead><tr><th width="285.809320129277">Parameter name</th><th>Annotation</th></tr></thead><tbody><tr><td>day</td><td>The amount of days from the start when the event was emitted.</td></tr><tr><td>pool</td><td>The balance of the UBI scheme in G$.</td></tr><tr><td>cycleLength</td><td>The duration that used to calculate a frequency of daily cycle pool distribution.</td></tr><tr><td>dailyUBIPool</td><td>The amount of the pool.</td></tr></tbody></table>

```
event UBICycleCalculated(
    uint256 day,
    uint256 pool,
    uint256 cycleLength,
    uint256 dailyUBIPool
);
```

#### UBIClaimed

Emits when someone claims the UBI.

<table><thead><tr><th width="285.809320129277">Parameter name</th><th>Annotation</th></tr></thead><tbody><tr><td>claimer</td><td>The claimer of the UBI user.</td></tr><tr><td>amount</td><td>The amount of the UBI the user gathered after claim reward call.</td></tr></tbody></table>

```
event UBIClaimed(address indexed claimer, uint256 amount);
```

#### CycleLengthSet

Emits when the Avatar sets the cycle length.

<table><thead><tr><th width="285.809320129277">Parameter name</th><th>Annotation</th></tr></thead><tbody><tr><td>newCycleLength</td><td>The duration of the collect UBI cycle..</td></tr></tbody></table>

```
event CycleLengthSet(uint256 newCycleLength);
```

#### CycleLengthSet

Emits when the Avatar sets the cycle length.

<table><thead><tr><th width="285.809320129277">Parameter name</th><th>Annotation</th></tr></thead><tbody><tr><td>newCycleLength</td><td>The duration of the collect UBI cycle..</td></tr></tbody></table>

```
event CycleLengthSet(uint256 newCycleLength);
```

#### DaySet

Emits when the Avatar sets the day.

<table><thead><tr><th width="285.809320129277">Parameter name</th><th>Annotation</th></tr></thead><tbody><tr><td>newDay</td><td>New days amount from the start of the UBI work.</td></tr></tbody></table>

```
event DaySet(uint256 newDay);
```

#### DaySet

Emits when the Avatar sets up he is not eligible for G$.

<table><thead><tr><th width="285.809320129277">Parameter name</th><th>Annotation</th></tr></thead><tbody><tr><td>ShouldWithdrawFromDAO</td><td>Accounts whether to also withdraw G$ from Avatar for UBI.</td></tr></tbody></table>

```
event ShouldWithdrawFromDAOSet(bool ShouldWithdrawFromDAO);
```

### checkEntitlement

Checks the amount which the `_member` address is eligible to claim for, regardless if they have been whitelisted or not. In case the user is active, then the current day must be equal to the actual day, i.e. claim or fish has already been executed today.

<table><thead><tr><th width="298.08152046943655">Parameter name</th><th>Annotation</th></tr></thead><tbody><tr><td>_member</td><td>Potential claimers address.</td></tr></tbody></table>

Returns: the amount of G$ tokens the address can claim.

```
function checkEntitlement(address _member) public view returns (uint256);
```

### claim

Function for claiming UBI. Requires contract to be active and claimer to be whitelisted. Calls `distributionFormula`, calculates the amount the caller can claim, and transfers the amount to the caller.

Returns: a boolean indicating if UBI was claimed.

```
function claim() public returns (bool);
```

### fish

In order to update users from active to inactive, we give out incentive to people to update the status of inactive users, this action is called "Fishing". Anyone can send a tx to the contract to mark inactive users. The "fisherman" receives a reward equal to the daily UBI (i.e. instead of the “fished” user). User that “last claimed” > 14 can be "fished" and made inactive (reduces active users count by one). Requires contract to be active.

<table><thead><tr><th width="298.08152046943655">Parameter name</th><th>Annotation</th></tr></thead><tbody><tr><td>_account</td><td>The account to "fish".</td></tr></tbody></table>

Returns: a bool indicating if UBI was fished.

```
function fish(address _account) public returns (bool);
```

### fishMulti

Executes `fish` with multiple addresses.

<table><thead><tr><th width="298.08152046943655">Parameter name</th><th>Annotation</th></tr></thead><tbody><tr><td>_accounts</td><td>The accounts to "fish".</td></tr></tbody></table>

Returns: a bool indicating if all the UBIs were fished.

```
function fishMulti(address[] memory _accounts) public returns (uint256);
```


# Identity

The Identity contract controls addresses that are whitelisted to "Claim" UBI.

* **Face Verification** GoodDollar currently whitelists users based on a user proving "uniqueness" by signing up with a live and unique face. All image data and details are anonymized in order to allow the user to create a new account in case he is unable to recover his wallet. Facial details are deleted after `authenticationPeriod` and users are required to perform face verification again every `authenticationPeriod` days.
* **Social Profile** Each blockchain address is linked to the user's public profile as created in the wallet. The DID is the node id in the public p2p GunDB database. Mappings from wallet address to DID are held in `addrToDID`.

### Events

#### BlacklistAdded

Emitted when the address is added to blacklist.

<table><thead><tr><th width="285.809320129277">Parameter name</th><th>Annotation</th></tr></thead><tbody><tr><td>account</td><td>The address of the account to add.</td></tr></tbody></table>

```
event BlacklistAdded(address indexed account);
```

#### BlacklistRemoved

Emitted when the address is removed from blacklist.

<table><thead><tr><th width="285.809320129277">Parameter name</th><th>Annotation</th></tr></thead><tbody><tr><td>account</td><td>The address of the account to remove.</td></tr></tbody></table>

```
event BlacklistRemoved(address indexed account);
```

#### WhitelistedRemoved

Emitted when the address is removed from whitelist.

<table><thead><tr><th width="285.809320129277">Parameter name</th><th>Annotation</th></tr></thead><tbody><tr><td>account</td><td>The address of the account to remove.</td></tr></tbody></table>

```
event WhitelistedRemoved(address indexed account);
```

#### WhitelistedAdded

Emitted when the address is added to whitelist.

<table><thead><tr><th width="285.809320129277">Parameter name</th><th>Annotation</th></tr></thead><tbody><tr><td>account</td><td>The address of the account to add.</td></tr></tbody></table>

```
event WhitelistedAdded(address indexed account);
```

#### ContractAdded

Emitted when the contract address is added to whitelist.

<table><thead><tr><th width="285.809320129277">Parameter name</th><th>Annotation</th></tr></thead><tbody><tr><td>account</td><td>The address of the contract to add.</td></tr></tbody></table>

```
event ContractAdded(address indexed account);
```

#### ContractRemoved

Emitted when the contract address is removed from whitelist.

<table><thead><tr><th width="285.809320129277">Parameter name</th><th>Annotation</th></tr></thead><tbody><tr><td>account</td><td>The address of the contract to add.</td></tr></tbody></table>

```
event ContractRemoved(address indexed account);
```

### isWhitelisted

The function checks if given address has been added to whitelist.

<table><thead><tr><th width="301.8711599216471">Parameter name</th><th>Annotation</th></tr></thead><tbody><tr><td>account</td><td>The address to check.</td></tr></tbody></table>

Returns: a boolean indicating weather the address is present in whitelist.

```
function isWhitelisted(address account) public view returns (bool);
```

### lastAuthenticated

Function that gives the date the given user was added.

<table><thead><tr><th width="150">Parameter name</th><th>Annotation</th></tr></thead><tbody><tr><td>account</td><td>The address to check.</td></tr></tbody></table>

Returns: the date the address was added.

```
function lastAuthenticated(address account) public view returns (uint256);
```

### authenticationPeriod

Field that contains the number of days an authentication is valid for.

Returns: a time duration in days.

```
function authenticationPeriod() external view returns (uint256);
```

### addrToDID

Function that gives the DID representation for given address.

<table><thead><tr><th width="150">Parameter name</th><th>Annotation</th></tr></thead><tbody><tr><td>account</td><td>The address to check.</td></tr></tbody></table>

Returns: the string representation of DID

```
function addrToDID(address account) external view returns (string memory);
```


# FirstClaimPool

Helper contract for UBIScheme. Manually funded by the Foundation to give 1G$ for "inactive" users when they claim.

Since a new user (inactive) becomes active and eligible to claim UBI only in the next UBI epoch. So new users will not go empty-handed on their first claim we give out a 1G$.

### start

Start function. Adds this contract to identity as a feeless scheme. Can only be called if scheme is registered.

```
function start() public;
```

### setUBIScheme

Sets the whitelisted ubi scheme.

<table><thead><tr><th width="225.57142857142856">Parameter name</th><th>Annotation</th></tr></thead><tbody><tr><td>_ubi</td><td>The new UBI scheme to be whitelisted.</td></tr></tbody></table>

Can be executed only by the Avatar.

```
function setUBIScheme(address _ubi) public;
```

### setClaimAmount

Sets the claim amount.

<table><thead><tr><th width="225.57142857142856">Parameter name</th><th>Annotation</th></tr></thead><tbody><tr><td>_claimAmount</td><td>The new claim amount.</td></tr></tbody></table>

Can be executed only by the Avatar.

```
function setClaimAmount(uint256 _claimAmount) public;
```

### awardUser

Transfers claim amount to the given account address. Only the whitelisted UBI scheme can call this method.

<table><thead><tr><th width="225.57142857142856">Parameter name</th><th>Annotation</th></tr></thead><tbody><tr><td>_account</td><td>The address which recieves the claim amount.</td></tr></tbody></table>

Returns: the amount that was transferred to the given `_account`.

```
function awardUser(address _account) public returns (uint256);
```

### end

Making the contract inactive after it has transferred funds to `_avatar`. Only the Avatar can destroy the contract.

```
function end() public;
```


# AdminWallet

Helper contract for our backend servers to whitelist users and to fill their Fuse network gas.

### Events

#### AdminsAdded

Emitted when new admins were added.

<table><thead><tr><th width="285.809320129277">Parameter name</th><th>Annotation</th></tr></thead><tbody><tr><td>admins</td><td>The addresses of the admins that were added.</td></tr></tbody></table>

```
event AdminsAdded(address payable[] indexed admins);
```

#### AdminsRemoved

Emitted when old admins were removed.

<table><thead><tr><th width="285.809320129277">Parameter name</th><th>Annotation</th></tr></thead><tbody><tr><td>admins</td><td>The addresses of the admins that were removed.</td></tr></tbody></table>

```
event AdminsRemoved(address[] indexed admins);
```

#### WalletTopped

Emitted when the specific user address was topped.

<table><thead><tr><th width="285.809320129277">Parameter name</th><th>Annotation</th></tr></thead><tbody><tr><td>user</td><td>The users address that was topped.</td></tr><tr><td>amount</td><td>The amount that was sent.</td></tr></tbody></table>

```
event WalletTopped(address indexed user, uint256 amount);
```

#### GenericCall

Emitted when the wallet is performing some tx.

<table><thead><tr><th width="285.809320129277">Parameter name</th><th>Annotation</th></tr></thead><tbody><tr><td>_contract</td><td>The contract that was called.</td></tr><tr><td>_data</td><td>The data of the tx.</td></tr><tr><td>_value</td><td>The amount of the native token that was sent.</td></tr><tr><td>_success</td><td>The status of the performed tx.</td></tr></tbody></table>

```
event GenericCall(
        address indexed _contract,
        bytes _data,
        uint256 _value,
        bool _success
);
```

### setBonusContract

Sets the SignUpBonus contract address.

<table><thead><tr><th width="301.8711599216471">Parameter name</th><th>Annotation</th></tr></thead><tbody><tr><td>_bonus</td><td>The new address of the SignUpBonus contract.</td></tr></tbody></table>

Can only be called by the admin.

```
function setBonusContract(address _bonus) public;
```

### addAdmins

Function to add list of addresses to admins list.

<table><thead><tr><th width="301.8711599216471">Parameter name</th><th>Annotation</th></tr></thead><tbody><tr><td>_admins</td><td>The list of addresses to add as admins list.</td></tr></tbody></table>

Can only be called by the admin.

```
function addAdmins(address payable[] memory _admins) public;
```

### removeAdmins

Function to remove list of addresses from admins list.

<table><thead><tr><th width="301.8711599216471">Parameter name</th><th>Annotation</th></tr></thead><tbody><tr><td>_admins</td><td>The list of addresses to remove from admins list.</td></tr></tbody></table>

Can only be called by the admin.

```
function removeAdmins(address[] memory _admins) public;
```

### topAdmins

Function to top group of admins by indicies with amount of G$ given in constructor. The amount of times per day specified in the constructor.

<table><thead><tr><th width="301.8711599216471">Parameter name</th><th>Annotation</th></tr></thead><tbody><tr><td>startIndex</td><td>Starting index in the admins list.</td></tr><tr><td>endIndex</td><td>Ending index in the admins list.</td></tr></tbody></table>

```
function topAdmins(uint256 startIndex, uint256 endIndex) public;
```

Below there is the overriden variant which performs like the original except the `endIndex` is set to 50 by default.

```
function topAdmins(uint256 startIndex) public;
```

### isAdmin

Function to check if given account is the admin.

<table><thead><tr><th width="301.8711599216471">Parameter name</th><th>Annotation</th></tr></thead><tbody><tr><td>_user</td><td>The account address to check.</td></tr></tbody></table>

Returns: `true` if `_user` is the admin, `false` elsewise.

```
function isAdmin(address _user) public view returns (bool)
```

### whitelist

Function to add given address to whitelist of identity contract.

<table><thead><tr><th width="301.8711599216471">Parameter name</th><th>Annotation</th></tr></thead><tbody><tr><td>_user</td><td>The account address to be added to whitelist.</td></tr><tr><td>_did</td><td>The DID of the <code>_user</code>.</td></tr></tbody></table>

Can only be called by admins of wallet and if wallet is an IdentityAdmin.

```
function whitelist(address _user, string memory _did) public;
```

### removeWhitelist

Function to remove given address from whitelist of identity contract.

<table><thead><tr><th width="301.8711599216471">Parameter name</th><th>Annotation</th></tr></thead><tbody><tr><td>_user</td><td>The account address to whitelist.</td></tr></tbody></table>

Can only be called by admins of wallet and if wallet is an IdentityAdmin.

```
function removeWhitelist(address _user) public;
```

### blacklist

Function to add given address to blacklist of identity contract.

<table><thead><tr><th width="301.8711599216471">Parameter name</th><th>Annotation</th></tr></thead><tbody><tr><td>_user</td><td>The account address to be added to blacklist.</td></tr></tbody></table>

Can only be called by admins of wallet and if wallet is an IdentityAdmin.

```
function blacklist(address _user) public;
```

### removeBlacklist

Function to remove given address from blacklist of identity contract.

<table><thead><tr><th width="301.8711599216471">Parameter name</th><th>Annotation</th></tr></thead><tbody><tr><td>_user</td><td>The account address to be removed from blacklist.</td></tr></tbody></table>

Can only be called by admins of wallet and if wallet is an IdentityAdmin.

```
function removeBlacklist(address _user) public;
```

### topWallet

Function to top given address with amount of G$ given in constructor.

<table><thead><tr><th width="301.8711599216471">Parameter name</th><th>Annotation</th></tr></thead><tbody><tr><td>_user</td><td>The address to transfer to.</td></tr></tbody></table>

Can only be done by admin. The amount of times per day specified in constructor.

```
function topWallet(address payable _user) public;
```

### whitelistAndAwardUser

Function to whitelist user and also award him pending bonuses, it can be used also later when the user is already whitelisted to just award pending bonuses.

<table><thead><tr><th width="301.8711599216471">Parameter name</th><th>Annotation</th></tr></thead><tbody><tr><td>_user</td><td>The address to transfer to and whitelist.</td></tr><tr><td>_amount</td><td>The bonus amount to give.</td></tr><tr><td>_did</td><td>Decentralized ID of user, pointer to some profile.</td></tr></tbody></table>

Can only be done by admin.

```
function whitelistAndAwardUser(
        address _user,
        uint256 _amount,
        string memory _did
) public;
```

### awardUser

Function to award user with pending bonuses, can only be done by admin.

<table><thead><tr><th width="301.8711599216471">Parameter name</th><th>Annotation</th></tr></thead><tbody><tr><td>_user</td><td>The address to transfer to and whitelist.</td></tr><tr><td>_amount</td><td>The bonus amount to give.</td></tr></tbody></table>

```
function awardUser(address _user, uint256 _amount) public;
```

### genericCall

Perform a generic call to an arbitrary contract.

<table><thead><tr><th width="301.8711599216471">Parameter name</th><th>Annotation</th></tr></thead><tbody><tr><td>_contract</td><td>The contract's address to call.</td></tr><tr><td>_data</td><td>ABI-encoded contract call to call <code>_contract</code> address.</td></tr><tr><td>_value</td><td>Value (native token) to transfer with the transaction.</td></tr></tbody></table>

Returns: pair of bool and bytes - success or fail and bytes of the called contract's function.

```
function genericCall(
        address _contract,
        bytes memory _data,
        uint256 _value
 ) public returns (bool success, bytes memory returnValue)
```

### destroy

Destroy wallet and return funds to owner. Can only be executed by the admin.

```
function destroy() public;
```


# OneTimePayments

Payments on the GoodDollar wallet are done via payment links.

G$s are held in an escrow and the recipient can retrieve the funds if he has the key. While the money is in escrow the sender can choose to cancel the payment and retrieve the funds. Based on [Celo's](https://github.com/celo) payments contract.

### Events

#### PaymentDeposit

Emitted when payment was performed. Occurs only during the token contract call.

<table><thead><tr><th width="389.63805195347794">Parameter name</th><th>Annotation</th></tr></thead><tbody><tr><td>from</td><td>The address of the tokens sender.</td></tr><tr><td>paymentId</td><td>The address representing an ID of the payment.</td></tr><tr><td>amount</td><td>Amount of the payment.</td></tr></tbody></table>

```
event PaymentDeposit(address indexed from, address paymentId, uint256 amount);
```

To deposit a payment to a one time payment address call perform the further:

```
GoodDollar.transferAndCall(value, data);
```

The above will trigger OneTimePayments onTokenTransfer callback, which will trigger the PaymentDeposit.

#### PaymentCancel

Emitted when payment was cancelled.

<table><thead><tr><th width="223.06025121092682">Parameter name</th><th>Annotation</th></tr></thead><tbody><tr><td>from</td><td>The address of the tokens sender.</td></tr><tr><td>paymentId</td><td>The address representing an ID of the payment.</td></tr><tr><td>amount</td><td>Amount of the payment.</td></tr></tbody></table>

```
event PaymentCancel(address indexed from, address paymentId, uint256 amount);
```

#### PaymentWithdraw

Emitted when payment was withdrawn.

<table><thead><tr><th width="223.06025121092682">Parameter name</th><th>Annotation</th></tr></thead><tbody><tr><td>from</td><td>The address of the tokens sender.</td></tr><tr><td>to</td><td>The address of the tokens receiver.</td></tr><tr><td>paymentId</td><td>The address representing an ID of the payment.</td></tr><tr><td>amount</td><td>Amount of the payment.</td></tr></tbody></table>

```
event PaymentWithdraw(
    address indexed from,
    address indexed to,
    address indexed paymentId,
    uint256 amount
);
```

### withdraw

Withdrawal function.

<table><thead><tr><th width="301.8711599216471">Parameter name</th><th>Annotation</th></tr></thead><tbody><tr><td>paymentId</td><td>The address of the public key that the rightful receiver of the payment knows the private key to.</td></tr><tr><td>signature</td><td>The signature of a the message containing the <code>msg.sender</code> address signed with the private key.</td></tr></tbody></table>

```
function withdraw(address paymentId, bytes memory signature) public;
```

### cancel

Payments cancel function.

<table><thead><tr><th width="301.8711599216471">Parameter name</th><th>Annotation</th></tr></thead><tbody><tr><td>_paymentId</td><td>The ID of the payment to cancel.</td></tr></tbody></table>

Allows only creator of payment to cancel.

```
function cancel(address paymentId) public;
```


# DonationsStaking

Any ETH/DAI sent to this contract address is donated to the GoodDollar DAO and will generate interest to fund UBI.

The funds are periodically staked in the staking contract by calling the `stakeDonations`method.

### Events

#### DonationStaked

Emitted when donation is staked.

<table><thead><tr><th width="271.38606540841545">Parameter name</th><th>Annotation</th></tr></thead><tbody><tr><td>caller</td><td>The user who staked.</td></tr><tr><td>stakedDAI</td><td>The balance of the contract in DAI that was staked.</td></tr><tr><td>ethDonated</td><td>Amount of the donated native token.</td></tr><tr><td>daiDonated</td><td>Amount of the donated DAI.</td></tr></tbody></table>

```
event DonationStaked(
    address caller,
    uint256 stakedDAI,
    uint256 ethDonated,
    uint256 daiDonated
);
```

The funds are periodically staked in the GoodStaking contract by calling the `stakeDonations`method.

### stakeDonations

Stake all available funds on the contract. It take balance in native token and buy DAI from Uniswap then stake outstanding DAI balance.

<table><thead><tr><th width="301.8711599216471">Parameter name</th><th>Annotation</th></tr></thead><tbody><tr><td>_minDAIAmount</td><td>Enforce expected return from Uniswap when converting native token balance to DAI.</td></tr></tbody></table>

```
function stakeDonations(uint256 _minDAIAmount) public payable;
```

### totalStaked

Total DAI value staked. Returns: DAI value staked.

```
function totalStaked() public view returns (uint256);
```


# NameService

Helper contract, basically simple name to address resolver.

### Events

#### AddressChanged

Emitted when address under the name was changed.

<table><thead><tr><th width="389.63805195347794">Parameter name</th><th>Annotation</th></tr></thead><tbody><tr><td>name</td><td>Name of the address.</td></tr><tr><td>addr</td><td>The address itself.</td></tr></tbody></table>

```
event AddressChanged(string name, address addr);
```

### setAddress

The function that sets the new address under the name.

<table><thead><tr><th width="301.8711599216471">Parameter name</th><th>Annotation</th></tr></thead><tbody><tr><td>name</td><td>The name of an address.</td></tr><tr><td>addr</td><td>The new address itself.</td></tr></tbody></table>

Can only be called by the Avatar.

```
function setAddress(string memory name, address addr) external;
```

### setAddresses

The function that sets the new group of addresses under the names.

<table><thead><tr><th width="301.8711599216471">Parameter name</th><th>Annotation</th></tr></thead><tbody><tr><td>hash</td><td>The array of keccak256's of names.</td></tr><tr><td>addrs</td><td>The new addresses themselfs.</td></tr></tbody></table>

Can only be called by the Avatar.

```
function setAddresses(bytes32[] calldata hash, address[] calldata addrs) external;
```

### getAddress

The function that gets the address under the name.

<table><thead><tr><th width="301.8711599216471">Parameter name</th><th>Annotation</th></tr></thead><tbody><tr><td>name</td><td>The name of an address.</td></tr></tbody></table>

Returns: the address under the given name.

```
function getAddress(string memory name) external view returns (address);
```


# GReputation

The contract extends Reputation contract with delegation and cross blockchain merkle states.

To be noticed: the contract breaks DAOStack nativeReputation usage, since it is not possiible to upgrade the original nativeReputation token. it means you can no longer rely on `avatar.nativeReputation()` or `controller.nativeReputation()` to return the current reputation token.

The DAO avatar will be the owner of this reputation token and not the Controller. Minting by the DAO will be done using `controller.genericCall` and not via `controller.mintReputation`.

### Events

#### DelegateVotesChanged

Emitted when a delegate account's vote balance changes.

<table><thead><tr><th width="389.63805195347794">Parameter name</th><th>Annotation</th></tr></thead><tbody><tr><td>delgate</td><td>The address of delegate account.</td></tr><tr><td>delegator</td><td>The address of delegator account.</td></tr><tr><td>previousBalance</td><td>The previous amount of vote power balance.</td></tr><tr><td>newBalance</td><td>The new amount of vote power balance.</td></tr></tbody></table>

```
event DelegateVotesChanged(
    address indexed delegate,
    address indexed delegator,
    uint256 previousBalance,
    uint256 newBalance
);
```

#### StateHash

Emitted when a state hash of a blockhain is set.

<table><thead><tr><th width="389.63805195347794">Parameter name</th><th>Annotation</th></tr></thead><tbody><tr><td>blockchain</td><td>The blockchain name.</td></tr><tr><td>merkleRoot</td><td>The state hash.</td></tr><tr><td>totalSupply</td><td>The total supply of reputation on the specific blockchain.</td></tr></tbody></table>

```
event StateHash(string blockchain, bytes32 merkleRoot, uint256 totalSupply);
```

#### StateHashProof

Emitted when user balance in a specific blockchain state hash is proved.

<table><thead><tr><th width="389.63805195347794">Parameter name</th><th>Annotation</th></tr></thead><tbody><tr><td>blockchain</td><td>The name of the blockchain.</td></tr><tr><td>user</td><td>The user whose balance if proved.</td></tr><tr><td>repBalance</td><td>The balance in reputation of the user that is being proved.</td></tr></tbody></table>

```
event StateHashProof(string blockchain, address user, uint256 repBalance);
```

### setBlockchainStateHash

Sets the state hash of a blockchain.

<table><thead><tr><th width="301.8711599216471">Parameter name</th><th>Annotation</th></tr></thead><tbody><tr><td>_id</td><td>The string name of the blockchain (will be hashed to produce byte32 id).</td></tr><tr><td>_hash</td><td>The state hash.</td></tr><tr><td>_totalSupply</td><td>Total supply of reputation on the specific blockchain.</td></tr></tbody></table>

Can only be called by the admin.

```
function setBlockchainStateHash(
    string memory _id,
    bytes32 _hash,
    uint256 _totalSupply
) public;
```

### getVotesAt

Get the number of active votes a user holds after delegation (vs the basic balance of reputation he holds).

<table><thead><tr><th width="301.8711599216471">Parameter name</th><th>Annotation</th></tr></thead><tbody><tr><td>_user</td><td>The user to get active votes for.</td></tr><tr><td>_global</td><td>Flag whether to include reputation from other blockchains.</td></tr><tr><td>_blockNumber</td><td>Get votes state at specific block.</td></tr></tbody></table>

Returns: the number of votes.

```
function getVotesAt(
    address _user,
    bool _global,
    uint256 _blockNumber
) public view returns (uint256);
```

### totalSupplyLocal

<table><thead><tr><th width="301.8711599216471">Parameter name</th><th>Annotation</th></tr></thead><tbody><tr><td>_blockNumber</td><td>Specific block.</td></tr></tbody></table>

Returns: total supply in current blockchain.

```
function totalSupplyLocal(uint256 _blockNumber) public view returns (uint256);
```

### totalSupplyAt

<table><thead><tr><th width="301.8711599216471">Parameter name</th><th>Annotation</th></tr></thead><tbody><tr><td>_blockNumber</td><td>Specific block.</td></tr></tbody></table>

Returns: total supply in all blockchain aggregated.

```
function totalSupplyAt(uint256 _blockNumber) public view returns (uint256);
```

### getVotesAtBlockchain

The function that gets the number of active votes a user holds after delegation in specific blockchain.

<table><thead><tr><th width="301.8711599216471">Parameter name</th><th>Annotation</th></tr></thead><tbody><tr><td>_id</td><td>The keccak256 hash of the blockchain string ID.</td></tr><tr><td>_user</td><td>The user to get active votes for.</td></tr><tr><td>_blockNumber</td><td>Specific block.</td></tr></tbody></table>

Returns: the number of votes.

```
function getVotesAtBlockchain(
    bytes32 _id,
    address _user,
    uint256 _blockNumber
) public view returns (uint256);
```

### proveBalanceOfAtBlockchain

The function that proves user balance in a specific blockchain state hash

<table><thead><tr><th width="301.8711599216471">Parameter name</th><th>Annotation</th></tr></thead><tbody><tr><td>_id</td><td>The string ID of the blockchain we supply proof for.</td></tr><tr><td>_user</td><td>The user to prove his balance.</td></tr><tr><td>_balance</td><td>The balance we are proving.</td></tr><tr><td>_proof</td><td>Array of byte32 with proof data (currently merkle tree path).</td></tr><tr><td>_nodeIndex</td><td>Index of node in the tree (for unsorted merkle tree proof).</td></tr></tbody></table>

Returns: `true` if proof is valid.

```
function proveBalanceOfAtBlockchain(
    string memory _id,
    address _user,
    uint256 _balance,
    bytes32[] memory _proof,
    uint256 _nodeIndex
) public returns (bool)
```

### delegateTo

The function that delegate votes to another user.

<table><thead><tr><th width="301.8711599216471">Parameter name</th><th>Annotation</th></tr></thead><tbody><tr><td>_delegate</td><td>The to whom to delegate address.</td></tr></tbody></table>

```
function delegateTo(address _delegate) public;
```

### undelegate

The function that cancels user delegation.

```
function undelegate() public;
```


# CompoundVotingMachine

CompoundVotingMachine based on Compound's governance with a few differences.

The differences between CompoundVotingMachine and Compound's governance:&#x20;

* no timelock, once vote has passed it stays open for 'queuePeriod' (2 days by default), if vote decision has changed, execution will be delayed so at least 24 hours are left to vote;
* execution modified to support DAOStack Avatar/Controller.

The contract based on [GovernorAlpha](https://github.com/compound-finance/compound-protocol/blob/b9b14038612d846b83f8a009a82c38974ff2dcfe/contracts/Governance/GovernorAlpha.sol).

### Events

#### ProposalCreated

An event emitted when a new proposal is created.

<table><thead><tr><th width="389.63805195347794">Parameter name</th><th>Annotation</th></tr></thead><tbody><tr><td>id</td><td>The ID of the proposal.</td></tr><tr><td>proposer</td><td>The address of the proposer.</td></tr><tr><td>targets</td><td>The targets list of contracts to be executed on.</td></tr><tr><td>values</td><td>The list of native token value to be used in each contract call.</td></tr><tr><td>signatures</td><td>The list of functions signatures to execute on <code>targets</code>.</td></tr><tr><td>calldatas</td><td>The list of parameters to pass to each function in <code>signatures</code>.</td></tr><tr><td>startBlock</td><td>Starting block number of voting.</td></tr><tr><td>endBlock</td><td>Ending block number of voting.</td></tr><tr><td>description</td><td>Short description of the proposal.</td></tr></tbody></table>

```
event ProposalCreated(
    uint256 id,
    address proposer,
    address[] targets,
    uint256[] values,
    string[] signatures,
    bytes[] calldatas,
    uint256 startBlock,
    uint256 endBlock,
    string description
);
```

#### ProposalSucceeded

An event emitted when using blockchain proposal bridge.

<table><thead><tr><th width="389.63805195347794">Parameter name</th><th>Annotation</th></tr></thead><tbody><tr><td>id</td><td>The ID of the proposal.</td></tr><tr><td>proposer</td><td>The address of the proposer.</td></tr><tr><td>targets</td><td>The targets list of contracts to be executed on.</td></tr><tr><td>values</td><td>The list of native token value to be used in each contract call.</td></tr><tr><td>signatures</td><td>The list of functions signatures to execute on <code>targets</code>.</td></tr><tr><td>calldatas</td><td>The list of parameters to pass to each function in <code>signatures</code>.</td></tr><tr><td>startBlock</td><td>Starting block number of voting.</td></tr><tr><td>endBlock</td><td>Ending block number of voting.</td></tr><tr><td>forBlockchain</td><td>The chain ID.</td></tr><tr><td>eta</td><td>An exact time of the proposal bridging.</td></tr><tr><td>forVotes</td><td>An amount of vote power "FOR".</td></tr><tr><td>againstVotes</td><td>An amount of vote power "AGAINST".</td></tr></tbody></table>

```
event ProposalSucceeded(
    uint256 id,
    address proposer,
    address[] targets,
    uint256[] values,
    string[] signatures,
    bytes[] calldatas,
    uint256 startBlock,
    uint256 endBlock,
    uint256 forBlockchain,
    uint256 eta,
    uint256 forVotes,
    uint256 againstVotes
);
```

#### ProposalBridge

Emitted when proposal made for a different blockchain.

<table><thead><tr><th width="389.63805195347794">Parameter name</th><th>Annotation</th></tr></thead><tbody><tr><td>id</td><td>The ID of the proposal.</td></tr><tr><td>forBlockchain</td><td>The chain ID of the blockchain proposal made for.</td></tr></tbody></table>

```
event ProposalBridge(uint256 id, uint256 indexed forBlockchain);
```

#### VoteCast

An event emitted when a vote has been cast on a proposal.

<table><thead><tr><th width="389.63805195347794">Parameter name</th><th>Annotation</th></tr></thead><tbody><tr><td>voter</td><td>The voter address.</td></tr><tr><td>proposalId</td><td>The proposal ID for which the vote was cast.</td></tr><tr><td>support</td><td>Check whether the vote cast was "FOR" or "AGAINST".</td></tr><tr><td>votes</td><td>The amount of voting power for the vote cast.</td></tr></tbody></table>

```
event VoteCast(
    address voter,
    uint256 proposalId,
    bool support,
    uint256 votes
);
```

#### ProposalCanceled

An event emitted when a proposal has been canceled.

<table><thead><tr><th width="389.63805195347794">Parameter name</th><th>Annotation</th></tr></thead><tbody><tr><td>id</td><td>The ID of the proposal.</td></tr></tbody></table>

```
event ProposalCanceled(uint256 id);
```

#### ProposalQueued

An event emitted when a proposal has been queued.

<table><thead><tr><th width="389.63805195347794">Parameter name</th><th>Annotation</th></tr></thead><tbody><tr><td>id</td><td>The ID of the proposal.</td></tr><tr><td>eta</td><td>The timestamp of the queueing.</td></tr></tbody></table>

```
event ProposalQueued(uint256 id, uint256 eta);
```

#### ProposalExecuted

An event emitted when a proposal has been executed.

<table><thead><tr><th width="389.63805195347794">Parameter name</th><th>Annotation</th></tr></thead><tbody><tr><td>id</td><td>The ID of the proposal.</td></tr></tbody></table>

```
event ProposalExecuted(uint256 id);
```

#### ProposalExecutionResult

An event emitted when a proposal call has been executed.

<table><thead><tr><th width="389.63805195347794">Parameter name</th><th>Annotation</th></tr></thead><tbody><tr><td>id</td><td>The ID of the proposal.</td></tr><tr><td>index</td><td>The index of the target contract from proposal.</td></tr><tr><td>ok</td><td>The status of the proposal call.</td></tr><tr><td>result</td><td>The result of the proposal call.</td></tr></tbody></table>

```
event ProposalExecutionResult(
    uint256 id,
    uint256 index,
    bool ok,
    bytes result
);
```

#### GuardianSet

An event emitted when a new guardian set.

<table><thead><tr><th width="389.63805195347794">Parameter name</th><th>Annotation</th></tr></thead><tbody><tr><td>newGuardian</td><td>The new guardian address.</td></tr></tbody></table>

```
event GuardianSet(address newGuardian);
```

#### ParametersSet

An event emitted when a new voting parameters set.

<table><thead><tr><th width="389.63805195347794">Parameter name</th><th>Annotation</th></tr></thead><tbody><tr><td>params</td><td>The voting parameters.</td></tr></tbody></table>

Here's the per index description of each parameter.

<table><thead><tr><th width="150">Index</th><th>Annotation</th></tr></thead><tbody><tr><td>0</td><td>The default voting period.</td></tr><tr><td>1</td><td>The default quorum percentage.</td></tr><tr><td>2</td><td>The proposal percentage.</td></tr><tr><td>3</td><td>The proposal max operations.</td></tr><tr><td>4</td><td>The delay in blocks before the newly created proposal would work.</td></tr><tr><td>5</td><td>The duration of time (in seconds) after proposal passed thershold before it can be executed.</td></tr><tr><td>6</td><td>The duration of time (in seconds) after proposal passed with absolute majority before it can be executed.</td></tr><tr><td>7</td><td>During the queue period if vote decision has changed, the queue period time duration is extended so that at least this amount of time in seconds is left.</td></tr><tr><td>8</td><td>The duration of time (in seconds) a succeeded proposal has to be executed on the blockchain.</td></tr></tbody></table>

```
event ParametersSet(uint256[9] params);
```

### propose

The function creates a proposal to be voted on.

<table><thead><tr><th width="301.8711599216471">Parameter name</th><th>Annotation</th></tr></thead><tbody><tr><td>targets</td><td>The address of the contracts on which proposal actions should be executed.</td></tr><tr><td>values</td><td>The amounts of native tokens that should be sent to the <code>targets</code> addresses.</td></tr><tr><td>signatures</td><td>The function selectors (signatures) that should be called as proposals actions should a proposal succeed.</td></tr><tr><td>calldatas</td><td>The call arguments for the <code>signatures</code>.</td></tr><tr><td>description</td><td>The short description of a proposal.</td></tr></tbody></table>

Returns: the ID of a newly created proposal.

```
function propose(
    address[] memory targets,
    uint256[] memory values,
    string[] memory signatures,
    bytes[] memory calldatas,
    string memory description
) public returns (uint256);
```

Also here's an overloaded variant of the function with additional parameter `forBlockchain` . The parameter is used to create a proposal in a specific sidechain.

```
function propose(
    address[] memory targets,
    uint256[] memory values,
    string[] memory signatures,
    bytes[] memory calldatas,
    string memory description,
    uint256 forBlockchain
) public returns (uint256);
```

### execute

The function is to execute the proposal list of transactions.

<table><thead><tr><th width="301.8711599216471">Parameter name</th><th>Annotation</th></tr></thead><tbody><tr><td>proposalId</td><td>The ID of the proposal that should be executed.</td></tr></tbody></table>

Anyone can call this once it's ETA has arrived.

```
function execute(uint256 proposalId) public payable;
```

### cancel

The function is to cancel a proposal. In case if a proposer are no longer hold the votes that were required to propose.

<table><thead><tr><th width="301.8711599216471">Parameter name</th><th>Annotation</th></tr></thead><tbody><tr><td>proposalId</td><td>The ID of the proposal that should be canceled.</td></tr></tbody></table>

```
function cancel(uint256 proposalId) public;
```

### state

The function is to get the current status of a proposal.

<table><thead><tr><th width="301.8711599216471">Parameter name</th><th>Annotation</th></tr></thead><tbody><tr><td>proposalId</td><td>The ID of the proposal that should be canceled.</td></tr></tbody></table>

```
function state(uint256 proposalId) public view returns (ProposalState);
```

The `ProposalState` enum is:

| Field name     | Annotation                                                                                       |
| -------------- | ------------------------------------------------------------------------------------------------ |
| Pending        | The proposal is pending.                                                                         |
| Active         | The proposal is pending and voters can vote now.                                                 |
| ActiveTimelock | The proposal is pending and passed quorum, time lock of 2 days activated, still open for voting. |
| Canceled       | The proposal is canceled.                                                                        |
| Defeated       | The voters voted against.                                                                        |
| Succeded       | The voters voted for.                                                                            |
| Expired        | The proposal time has passed. And it's no longer votable for.                                    |
| Executed       | The proposal transactions has been executed.                                                     |

### castVote

The function is to cast the users vote on a proposal.

<table><thead><tr><th width="301.8711599216471">Parameter name</th><th>Annotation</th></tr></thead><tbody><tr><td>proposalId</td><td>The ID of the proposal.</td></tr><tr><td>support</td><td>Is the vote "FOR" or "AGAINST".</td></tr></tbody></table>

```
function castVote(uint256 proposalId, bool support) public;
```

### getChainId

The function is to return the chain ID on which the contract was deployed.

```
function getChainId() public view returns (uint256);
```

### emitSucceeded

The function allows anyone to emit details about proposal that passed. Can be used for cross-chain proposals using blockheader proofs.

<table><thead><tr><th width="301.8711599216471">Parameter name</th><th>Annotation</th></tr></thead><tbody><tr><td>proposalId</td><td>The ID of the proposal.</td></tr></tbody></table>

```
function emitSucceeded(uint256 _proposalId) public;
```


# StakersDistribution

Staking contracts will update this contract with staker token stake amount.

This contract will be able to mint GDAO. 2M GDAO that will be allocated between staking contracts each month pro-rate based on $ value staked. Each staker will receive his share pro rata per staking contract he participates in.

### Events

#### ReputationEarned

Emitted when the staker claims the reputation.

<table><thead><tr><th width="389.63805195347794">Parameter name</th><th>Annotation</th></tr></thead><tbody><tr><td>staker</td><td>The stakers address.</td></tr><tr><td>stakingContracts</td><td>The contracts for which the <code>staker</code> claims reputation.</td></tr><tr><td>reputation</td><td>Reputation token amount.</td></tr></tbody></table>

```
event ReputationEarned(
    address staker,
    address[] stakingContracts,
    uint256 reputation
);
```

### getChainBlocksPerMonth

The function returns amount of blocks in month.

```
function getChainBlocksPerMonth() public pure override returns (uint256);
```

### setMonthlyReputationDistribution

The function updates the monthly reputation distribution.

<table><thead><tr><th width="301.8711599216471">Parameter name</th><th>Annotation</th></tr></thead><tbody><tr><td>newMonthlyReputationDistribution</td><td>The name of an address.</td></tr></tbody></table>

Can only be called by the Avatar.

```
function setMonthlyReputationDistribution(uint256 newMonthlyReputationDistribution) external;
```

### userStaked

The staking contract can call this function to increase user current contribution.

<table><thead><tr><th width="301.8711599216471">Parameter name</th><th>Annotation</th></tr></thead><tbody><tr><td>_staker</td><td>The user address to update.</td></tr><tr><td>_value</td><td>The value to increase by.</td></tr></tbody></table>

```
function userStaked(address _staker, uint256 _value) external;
```

### userWithdraw

The staking contract can call this to decrease user current contribution.

<table><thead><tr><th width="301.8711599216471">Parameter name</th><th>Annotation</th></tr></thead><tbody><tr><td>_staker</td><td>The user address to update.</td></tr><tr><td>_value</td><td>The value to decrease by.</td></tr></tbody></table>

```
function userWithdraw(address _staker, uint256 _value) external;
```

### claimReputation

The function mints reputation to user according to his share in the different staking contracts.

<table><thead><tr><th width="150">Parameter name</th><th>Annotation</th></tr></thead><tbody><tr><td>_staker</td><td>The user  address to distribute reputation to.</td></tr><tr><td>_stakingContracts</td><td>The user to distribute reputation to.</td></tr></tbody></table>

```
function claimReputation(address _staker, address[] calldata _stakingContracts) external;
```

### getUserPendingRewards

The function gets user reputation rewards accrued in GoodStaking contracts.

<table><thead><tr><th width="150">Parameter name</th><th>Annotation</th></tr></thead><tbody><tr><td>_contracts</td><td>The list of contracts to check for rewards.</td></tr><tr><td>_user</td><td>The user to check rewards for.</td></tr></tbody></table>

Returns: reputation rewards pending amount for user.

```
function getUserPendingRewards(address[] memory _contracts, address _user) public view returns (uint256);
```

### getUserMintedAndPending

The staking contract can call this to decrease user current contribution.

<table><thead><tr><th width="301.8711599216471">Parameter name</th><th>Annotation</th></tr></thead><tbody><tr><td>_contracts</td><td>The staking contracts to sum <code>_user</code> minted and pending.</td></tr><tr><td>_user</td><td>The account to get rewards status for.</td></tr></tbody></table>

Returns: a tuple of two items: (minted, pending) in GDAO tokens in wei.

```
function getUserMintedAndPending(address[] memory _contracts, address _user) public view returns (uint256, uint256);
```


# UniswapV2SwapHelper

The utilitary library which is helping to perform swaps in Uniswap V2.

### maxSafeTokenAmount

A helper function to calculate percentage out of token liquidity in pool that is safe to exchange against sandwich attack.&#x20;

Also checks if token->Native token has better safe limit, so perhaps doing tokenA->Native token->tokenB is better than tokenA->tokenB.&#x20;

In that case it could be that Native token->tokenB can be attacked because we dont know if Native token received for tokenA->Native token is less than `_maxPercentage` of the liquidity in Native token->tokenB.&#x20;

In our use case it is always eth->dai so either it will be safe or very minimal.

<table><thead><tr><th width="301.8711599216471">Parameter name</th><th>Annotation</th></tr></thead><tbody><tr><td>_iHasRouter</td><td>The contract address which instance has router address.</td></tr><tr><td>_inToken</td><td>The address of the token we are swapping.</td></tr><tr><td>_outToken</td><td>The address of swap result token.</td></tr><tr><td>_inTokenAmount</td><td>The amount of in token required to swap.</td></tr><tr><td>_maxLiquidityPercentageSwap</td><td>Max percentage of liquidity to swap to token. When swapping tokens and this value is out of 100000, so for example if you want to set it to 0.3 you need set it to 300.</td></tr></tbody></table>

Returns: safe amount of token that could be swapped.

```
function maxSafeTokenAmount(
    address _iHasRouter,
    address _inToken,
    address _outToken,
    uint256 _inTokenAmount,
    uint256 _maxLiquidityPercentageSwap
) public view returns (uint256 safeAmount);
```

### swap

A helper function to perform swap tokens in the Uniswap V2.

<table><thead><tr><th width="301.8711599216471">Parameter name</th><th>Annotation</th></tr></thead><tbody><tr><td>_iHasRouter</td><td>The contract address which instance has router address.</td></tr><tr><td>_path</td><td>The path of the swap.</td></tr><tr><td>_tokenAmount</td><td>The token amount to swap.</td></tr><tr><td>_mintTokenReturn</td><td>Minimum token amount to get in swap transaction.</td></tr><tr><td>_receiver</td><td>The receiver of tokens after swap transaction.</td></tr></tbody></table>

Can only be called by the Avatar.

```
function swap(
    address _iHasRouter,
    address[] memory _path,
    uint256 _tokenAmount,
    uint256 _minTokenReturn,
    address _receiver
) internal returns (uint256 swapResult);
```


# Invites

The contract that handles invites with pre allocated bounty pool with invitee bonus.

### Events

#### InviteeJoined

Emitted when user is joined.

<table><thead><tr><th width="389.63805195347794">Parameter name</th><th>Annotation</th></tr></thead><tbody><tr><td>inviter</td><td>The address of the user who invited.</td></tr><tr><td>invitee</td><td>he address of the user who is being invited.</td></tr></tbody></table>

```
event InviteeJoined(address indexed inviter, address indexed invitee);
```

#### InviterBounty

Emitted when inviter bounty is paid.

<table><thead><tr><th width="389.63805195347794">Parameter name</th><th>Annotation</th></tr></thead><tbody><tr><td>inviter</td><td>The address of the user who invited.</td></tr><tr><td>invitee</td><td>The address of the user who is being invited.</td></tr><tr><td>bountyPaid</td><td>The amount of bounty.</td></tr><tr><td>inviterLevel</td><td>The inviter level.</td></tr><tr><td>earnedLevel</td><td>The level which the inviter is earned.</td></tr></tbody></table>

```
event InviterBounty(
    address indexed inviter,
    address indexed invitee,
    uint256 bountyPaid,
    uint256 inviterLevel,
    bool earnedLevel
);
```

### join

The function is to be called by the user to join.

<table><thead><tr><th width="301.8711599216471">Parameter name</th><th>Annotation</th></tr></thead><tbody><tr><td>_myCode</td><td>The users invitation code.</td></tr><tr><td>_inviterCode</td><td>The inviters invitation code.</td></tr></tbody></table>

```
function join(bytes32 _myCode, bytes32 _inviterCode) public;
```

### canCollectBountyFor

The function is to clarify for the user who invited someone if he can claim bounty for the user who was being invited.

<table><thead><tr><th width="301.8711599216471">Parameter name</th><th>Annotation</th></tr></thead><tbody><tr><td>_invitee</td><td>The user who was being invited.</td></tr></tbody></table>

```
function canCollectBountyFor(address _invitee) public view returns (bool);
```

### getInvitees

The function is to be called to get the list of the invitees of the `_inviter`.

<table><thead><tr><th width="301.8711599216471">Parameter name</th><th>Annotation</th></tr></thead><tbody><tr><td>_inviter</td><td>The inviter address.</td></tr></tbody></table>

Returns: list of the invitees of the particular inviter.

```
function getInvitees(address _inviter) public view returns (address[] memory);
```

### getPendingInvitees

The function is to be called to get the list of the pending invitees of the `_inviter`.

<table><thead><tr><th width="301.8711599216471">Parameter name</th><th>Annotation</th></tr></thead><tbody><tr><td>_inviter</td><td>The inviter address.</td></tr></tbody></table>

Returns: list of the pending invitees of the particular inviter.

```
function getPendingInvitees(address _inviter) public view returns (address[] memory);
```

### getPendingBounties

The function is to be called to get the list of the pending bounties of the `_inviter`.

<table><thead><tr><th width="301.8711599216471">Parameter name</th><th>Annotation</th></tr></thead><tbody><tr><td>_inviter</td><td>The inviter address.</td></tr></tbody></table>

Returns: list of the pending bounties of the particular inviter.

```
function getPendingBounties(address _inviter) public view returns (uint256);
```

### bountyFor

The function is to be called to pay bounty for the inviter of `_invitee`.

<table><thead><tr><th width="301.8711599216471">Parameter name</th><th>Annotation</th></tr></thead><tbody><tr><td>_invitee</td><td>The invitee address.</td></tr></tbody></table>

```
function bountyFor(address _invitee) public;
```

### collectBounties

The function collects bounties for invitees by `msg.sender` that are now whitelisted.

```
function collectBounties() public;
```

### bountyFor

The function is to be called to pay bounty for the inviter of `_invitee`.

<table><thead><tr><th width="301.8711599216471">Parameter name</th><th>Annotation</th></tr></thead><tbody><tr><td>_invitee</td><td>The invitee address.</td></tr></tbody></table>

```
function bountyFor(address _invitee) public;
```


# GovernanceStaking

This is the staking contract that allows citizens to stake G$ to get GOOD rewards.

### Events

#### ReputationEarned

Emitted when `staker` earns an `amount` of GOOD tokens.

<table><thead><tr><th width="389.63805195347794">Parameter name</th><th>Annotation</th></tr></thead><tbody><tr><td>staker</td><td>The staker address who earned reputation.</td></tr><tr><td>amount</td><td>The amount of reputation.</td></tr></tbody></table>

```
event ReputationEarned(address indexed staker, uint256 amount);
```

#### Staked

Emitted when `staker` stakes an `amount` of GoodDollars.

<table><thead><tr><th width="389.63805195347794">Parameter name</th><th>Annotation</th></tr></thead><tbody><tr><td>staker</td><td>The staker address who earned reputation.</td></tr><tr><td>amount</td><td>The amount of stake.</td></tr></tbody></table>

```
event Staked(address indexed staker, uint256 amount);
```

#### StakeWithdraw

Emitted when `staker` withdraws an `amount` of staked GoodDollars.

<table><thead><tr><th width="389.63805195347794">Parameter name</th><th>Annotation</th></tr></thead><tbody><tr><td>staker</td><td>The staker address who earned reputation.</td></tr><tr><td>amount</td><td>The amount of stake.</td></tr></tbody></table>

```
event StakeWithdraw(address indexed staker, uint256 amount);
```

### stake

The function allows a staker to deposit Tokens. Notice that `approve` is needed to be executed before the execution of this method.

<table><thead><tr><th width="150">Parameter name</th><th>Annotation</th></tr></thead><tbody><tr><td>_amount</td><td>The amount of G$ to stake.</td></tr></tbody></table>

Can be executed only when the contract is not paused.

```
function stake(uint256 _amount) external;
```

### withdrawStake

The function withdraws the senders staked G$.

<table><thead><tr><th width="150">Parameter name</th><th>Annotation</th></tr></thead><tbody><tr><td>_amount</td><td>The amount of G$ to withdraw.</td></tr></tbody></table>

Can be executed only when the contract is not paused.

```
function withdrawStake(uint256 _amount) external;
```

### withdrawRewards

The function allows staker to withdraw their rewards without withdraw their stake.

Returns: amount of rewards that were sent to the `msg.sender`.

```
function withdrawRewards() public returns (uint256);
```

### getUserPendingReward

The function allows to acquire the number of G$ rewards for a specific `_user`.

<table><thead><tr><th width="150">Parameter name</th><th>Annotation</th></tr></thead><tbody><tr><td>_user</td><td>User to check the pending rewards.</td></tr></tbody></table>

Returns: an amount of G$ rewards for the user.

```
function getUserPendingReward(address _user) public view returns (uint256);
```


# ClaimersDistribution

The contract provides callbacks that can be used by UBIScheme contract to update when a citizen has claimed. It will distribute GOOD tokens each month pro rata based on number of claims.

### Events

#### ReputationEarned

Emitted when user claims the reputation rewards.

<table><thead><tr><th width="389.63805195347794">Parameter name</th><th>Annotation</th></tr></thead><tbody><tr><td>claimer</td><td>The user who claimed the rewards.</td></tr><tr><td>month</td><td>The number of months for which the <code>claimer</code> has acquired reputation rewards.</td></tr><tr><td>claims</td><td>The amount of claimers claims.</td></tr><tr><td>reputation</td><td>The size of the reputation reward in wei.</td></tr></tbody></table>

```
event ReputationEarned(
    address claimer,
    uint256 month,
    uint256 claims,
    uint256 reputation
);
```

#### MonthlyDistributionSet

Emitted when the Avatar updates the monthly reputation distribution.

<table><thead><tr><th width="389.63805195347794">Parameter name</th><th>Annotation</th></tr></thead><tbody><tr><td>reputationAmount</td><td>The new value of the parameter.</td></tr></tbody></table>

```
event MonthlyDistributionSet(uint256 reputationAmount);
```

### updateClaim

The function increases user count of claims if he claimed today. (This function is called automatically by latest version of the UBIScheme contract).

<table><thead><tr><th width="150">Parameter name</th><th>Annotation</th></tr></thead><tbody><tr><td>_claimer</td><td>The user address to update.</td></tr></tbody></table>

```
function updateClaim(address _claimer) external;
```

### claimReputation

The function mints reputation to the user according to his share in last month claims.

<table><thead><tr><th width="150">Parameter name</th><th>Annotation</th></tr></thead><tbody><tr><td>_claimer</td><td>The user to distribute reputation to.</td></tr></tbody></table>

```
function claimReputation(address _claimer) public;
```


# CompoundStakingFactory

The staking contract that donates earned interest to the DAO.

The contract allow stakers to deposit Token (DAI) or withdraw their stake in Token (DAI) the contracts buy cToken (cDAI) and can transfer the daily interest to the DAO.

### Events

#### Deployed

Emitted when new clone of the Compound staking contract was deployed.

<table><thead><tr><th width="389.63805195347794">Parameter name</th><th>Annotation</th></tr></thead><tbody><tr><td>proxy</td><td>The ERC1167 clones factory.</td></tr><tr><td>cToken</td><td>The compound token which is accepted in the deployed staking contract clone.</td></tr><tr><td>impl</td><td>The amount of claimers claims.</td></tr></tbody></table>

```
event Deployed(address proxy, address cToken, address impl);
```

### cloneAndInit

The function instantiates and initalizes an EIP 1167 proxy contract as minimal clone of the staking contract at public field `impl`.

<table><thead><tr><th width="301.8711599216471">Parameter name</th><th>Annotation</th></tr></thead><tbody><tr><td>_cToken</td><td>The compound token to be used for staking in this contract.</td></tr><tr><td>_ns</td><td>The NameService contract address which holds all the necessary addresses.</td></tr><tr><td>_maxRewardThreshold</td><td>The amount of blocks that need to pass in order to user would get their rewards with 1x multiplier instead of 0.5x.</td></tr><tr><td>_tokenUsdOracle</td><td>The address of the TOKEN/USD oracle. (TOKEN is the underlying token of <code>_cToken</code>.)</td></tr><tr><td>_compUsdOracle</td><td>The address of the AAVE/USD oracle.</td></tr><tr><td>_tokenToDaiSwapPath</td><td>The UniswapV2 swap path from TOKEN to DAI. (TOKEN is the underlying token of <code>_cToken</code>.)</td></tr></tbody></table>

```
function cloneAndInit(
    address _cToken,
    address _ns,
    uint64 _maxRewardThreshold,
    address _tokenUsdOracle,
    address _compUsdOracle,
    address[] memory _tokenToDaiSwapPath
) public;
```

There is another overloaded version of the signature:&#x20;

```
function cloneAndInit(
    address _impl,
    address _cToken,
    address _ns,
    uint64 _maxRewardThreshold,
    address _tokenUsdOracle,
    address _compUsdOracle,
    address[] memory _tokenToDaiSwapPath
) public;
```

Here you can specify the `_impl` of the clone proxy.

### predictAddress

The function is to compute the address of the proxy clone of the staking contract to deploy.

<table><thead><tr><th width="150">Parameter name</th><th>Annotation</th></tr></thead><tbody><tr><td>_impl</td><td>The imlementation of the staking contract.</td></tr><tr><td>cToken</td><td>First parameter of the constructor for <code>_impl</code>. (The compound token to stake.)</td></tr><tr><td>paramsHash</td><td>The keccak256 hash of remaining parameters of the constructor for <code>_impl</code>.</td></tr></tbody></table>

Returns: an address of the clone to be deployed.

```
function predictAddress(
    address _impl,
    address cToken,
    bytes32 paramsHash
) public view returns (address);
```


# AaveStakingFactory

The staking contracts factory. Producing contracts donate earned interest to the DAO allowing stakers to deposit or withdraw their stake.

The producing contracts are buying Aave-wrapped tokens and can transfer the daily interest to the DAO.

### Events

#### Deployed

Emitted when new clone of the Aave staking contract was deployed.

<table><thead><tr><th width="389.63805195347794">Parameter name</th><th>Annotation</th></tr></thead><tbody><tr><td>proxy</td><td>The ERC1167 clones factory.</td></tr><tr><td>token</td><td>The token which is accepted in the deployed staking contract clone.</td></tr><tr><td>impl</td><td>The amount of claimers claims.</td></tr></tbody></table>

```
event Deployed(address proxy, address cToken, address impl);
```

### cloneAndInit

The function instantiates and initalizes an EIP 1167 proxy contract as minimal clone of the staking contract at public field `impl`.

<table><thead><tr><th width="301.8711599216471">Parameter name</th><th>Annotation</th></tr></thead><tbody><tr><td>token</td><td>The token to be used for staking in this contract.</td></tr><tr><td>_lendingPool</td><td></td></tr><tr><td>_ns</td><td>The NameService contract address which holds all the necessary addresses.</td></tr><tr><td>_maxRewardThreshold</td><td>The amount of blocks that need to pass in order to user would get their rewards with 1x multiplier instead of 0.5x.</td></tr><tr><td>_tokenUsdOracle</td><td>The address of the TOKEN/USD oracle.</td></tr><tr><td>_incentiveController</td><td>Incentive Controller of AAVE protocol. It is utilized to claim rewards from AAVE.</td></tr><tr><td>_aaveUSDOracle</td><td>The address of the AAVE token/USD oracle.</td></tr><tr><td>_tokenToDaiSwapPath</td><td>The UniswapV2 swap path from TOKEN to DAI. (TOKEN is the underlying token of <code>_cToken</code>.)</td></tr></tbody></table>

```
function cloneAndInit(
    address token,
    address _lendingPool,
    address _ns,
    uint64 _maxRewardThreshold,
    address _tokenUsdOracle,
    address _incentiveController,
    address _aaveUSDOracle,
    address[] memory _tokenToDaiSwapPath
) public;
```

There is another overloaded version of the signature:&#x20;

```
function cloneAndInit(
    address _impl,
    address token,
    address _lendingPool,
    address _ns,
    uint64 _maxRewardThreshold,
    address _tokenUsdOracle,
    address _incentiveController,
    address _aaveUSDOracle,
    address[] memory _tokenToDaiSwapPath
) public;
```

Here you can specify the `_impl` of the clone proxy.

### predictAddress

The function is to compute the address of the proxy clone of the staking contract to deploy.

<table><thead><tr><th width="150">Parameter name</th><th>Annotation</th></tr></thead><tbody><tr><td>_impl</td><td>The imlementation of the staking contract.</td></tr><tr><td>token</td><td>First parameter of the constructor for <code>_impl</code>. (The token to stake.)</td></tr><tr><td>paramsHash</td><td>The keccak256 hash of remaining parameters of the constructor for <code>_impl</code>.</td></tr></tbody></table>

Returns: an address of the clone to be deployed.

```
function predictAddress(
    address _impl,
    address token,
    bytes32 paramsHash
) public view returns (address);
```


# ExchangeHelper

Helper contract to buy/sell G$ at GoodReserve with any token supported by Uniswap V2. Since reserve only supports cDAI.

### Events

#### TokenPurchased

Emitted when G$ tokens are purchased.

<table><thead><tr><th width="389.63805195347794">Parameter name</th><th>Annotation</th></tr></thead><tbody><tr><td>caller</td><td>The address who initiated the action.</td></tr><tr><td>inputToken</td><td>The convertible token address which the G$ tokens were purchased with.</td></tr><tr><td>inputAmount</td><td>Reserve tokens amount.</td></tr><tr><td>actualReturn</td><td>Actual return after the conversion.</td></tr><tr><td>receiverAddress</td><td>Address of the receiver of the tokens.</td></tr></tbody></table>

```
event TokenPurchased(
    address indexed caller,
    address indexed inputToken,
    uint256 inputAmount,
    uint256 actualReturn,
    address indexed receiverAddress
);
```

#### TokenSold

Emitted when G$ tokens are sold.

<table><thead><tr><th width="389.63805195347794">Parameter name</th><th>Annotation</th></tr></thead><tbody><tr><td>caller</td><td>The address who initiated the action.</td></tr><tr><td>outputToken</td><td>The convertible token address which the G$ tokens were sold to.</td></tr><tr><td>gdAmount</td><td>The G$ tokens amount.</td></tr><tr><td>contributionAmount</td><td>The amount of G$ tokens that was contributed during the conversion.</td></tr><tr><td>actualReturn</td><td>Actual return after the conversion.</td></tr><tr><td>receiverAddress</td><td>Address of the receiver of tokens.</td></tr></tbody></table>

```
event TokenSold(
    address indexed caller,
    address indexed outputToken,
    uint256 gdAmount,
    uint256 contributionAmount,
    uint256 actualReturn,
    address indexed receiverAddress
);
```

### buy

The function converts any "buyWith" tokens to DAI. Then call to reserve's buy function is occured. It is to convert the tokens to G$ tokens.

<table><thead><tr><th width="150">Parameter name</th><th>Annotation</th></tr></thead><tbody><tr><td>_buyPath</td><td>The tokens swap path in order to buy G$ if initial token is not DAI or cDAI. The end of the path must be set to DAI.</td></tr><tr><td>_tokenAmount</td><td>The amount of "buyWith" tokens that should be converted to G$ tokens.</td></tr><tr><td>_minReturn</td><td>The minimum allowed return in G$ tokens.</td></tr><tr><td>_minDAIAmount</td><td>The minimum DAI out amount from Exchange swap function.</td></tr><tr><td>_targetAddress</td><td>The address of G$ and GDX recipient if different than <code>msg.sender</code>.</td></tr></tbody></table>

Returns: how much G$ tokens were transferred.

```
function buy(
    address[] memory _buyPath,
    uint256 _tokenAmount,
    uint256 _minReturn,
    uint256 _minDAIAmount,
    address _targetAddress
) public payable returns (uint256);
```

### sell

The function converts G$ tokens to cDAI through reserve then it makes further transactions according to desired `_sellTo` token. The user could either send cDAI or DAI directly or desired token through Uniswap V2.

<table><thead><tr><th width="150">Parameter name</th><th>Annotation</th></tr></thead><tbody><tr><td>_sellPath</td><td>The tokens swap path in order to sell G$ to target token. If target token is not DAI or cDAI then first element of the path must be DAI.</td></tr><tr><td>_gdAmount</td><td>The amount of G$ tokens that should be converted to "_sellTo" tokens.</td></tr><tr><td>_minReturn</td><td>The minimum allowed "sellTo" tokens return.</td></tr><tr><td>_minTokenReturn</td><td>The mininmum DAI out amount from Exchange swap function.</td></tr><tr><td>_targetAddress</td><td>The address of "_sellTo" token recipient if different than <code>msg.sender</code>.</td></tr></tbody></table>

Returns: how much "sellTo" tokens were transferred.

```
function sell(
    address[] memory _sellPath,
    uint256 _gdAmount,
    uint256 _minReturn,
    uint256 _minTokenReturn,
    address _targetAddress
) public returns (uint256);
```


# FuseFaucet

The contract is to provide functionality of topping the users with Fuse to pay transaction fees.

### Events

#### WalletTopped

Emitted when user is topped by G$.

<table><thead><tr><th width="389.63805195347794">Parameter name</th><th>Annotation</th></tr></thead><tbody><tr><td>user</td><td>The address of the <code>user</code> who is being top.</td></tr><tr><td>amount</td><td>The amount of Fuse sent to the <code>user</code>.</td></tr></tbody></table>

```
event WalletTopped(address indexed user, uint256 amount);
```

### canTop

The function allows to check if the user address can be topped with Fuse.

<table><thead><tr><th width="301.8711599216471">Parameter name</th><th>Annotation</th></tr></thead><tbody><tr><td>_user</td><td>The user who is being checked if he could be topped.</td></tr></tbody></table>

Returns: `true` if user could be topped, `false` otherwise.

```
function canTop(address _user) public view returns (bool);
```

### topWallet

The function is utilized to top given address with amount of Fuse given in constructor. The amount of times specified in constructor per day.

<table><thead><tr><th width="301.8711599216471">Parameter name</th><th>Annotation</th></tr></thead><tbody><tr><td>_user</td><td>The address to transfer to.</td></tr></tbody></table>

Can only be called by admin.

```
function canTop(address _user) public view returns (bool);
```


# Protocol V3

An introduction to the key components and users in the GoodDollar protocol V3. This is the current version of the GoodDollar smart contracts.

{% hint style="warning" %}
**Notice of Potential Information Variability**

As of December 21, 2023, the information in GoodDocs may not reflect the most current updates. The team is diligently working to review and revise the documentation to ensure accuracy. Please check back at a later date for the most up-to-date information.
{% endhint %}

## **Intro**

**GoodDollar V3 is a smart contract upgrade that enables core functions for the GoodDollar protocol to scale.**

{% hint style="info" %}
[This blog post](https://www.gooddollar.org/gooddollarv3-is-coming/) provides an overview of what V3 does and why it matters to you and the world.
{% endhint %}

GoodDollar protocol’s mission is to issue a sustainable crypto universal basic income, as a public good, that members are able to use G$ as a medium of exchange.&#x20;

All proposed changes are designed to:

* encourage usage and engagement among active G$ holders and community members
* reduce the rate of leverage of the currency, to encourage sustainable growth with minimal price volatility
* lay the groundwork for the GoodDAO to begin to propose, lead and fund community-led initiatives
* V3 eliminates G$ Staking APY Rewards for Mainnet Stakers
* The Speed of Annual G$ Minting/Issuance has been reduced by the passing of Protocol V3: Reserves Ratio Decline from 20% → 15% annually
* V3 also allocate 10% of the daily G$ UBI mint towards savings rewards and another 10% of the daily G$ UBI mint to fund a GoodDAO controlled community fund.
* Expand G$ token and protocol to Celo blockchain

## What you can do in V3:

### Stake for GoodDollar UBI and earn Governance Tokens (GOOD)&#x20;

* Stake your stablecoins using GoodDollar Trust&#x20;
* Automatically donate your yield towards UBI
* Increase your voting power by claiming your GOOD tokens

### Stake GoodDollars through Savings for rewards

* Swap any ERC-20 token in [exchange for G$ ](/user-guides/buy-and-sell-gusd)
* Earn G$ by staking in the Savings contract

### Submit proposals and get them funded via GoodDAO&#x20;

* 10% of the daily UBI mint is directed to the community fund
* Submit your proposal to the GoodDAO for funding
* If it passes, community fund guardians will approve the transaction and fund your proposal.

### Developer Tools&#x20;

* Contribute with GoodDollar repository and security and hunt some [bounties](https://github.com/GoodDollar/Bounties/issues).&#x20;
* [Deploy Your Own UI](/for-developers/developer-guides/deploy-your-own-gooddapp-ui)


# Architecture & Value Flow

How does the protocol works?

{% hint style="warning" %}
**Notice of Potential Information Variability**

As of December 21, 2023, the information in GoodDocs may not reflect the most current updates. The team is diligently working to review and revise the documentation to ensure accuracy. Please check back at a later date for the most up-to-date information.
{% endhint %}

Summary: A digital asset that operates within the emerging ecosystem of decentralized and open finance, G$ is backed by a monetary reserve of cryptocurrencies and thus has tangible value. G$ tokens are liquid and convertible to other cryptocurrencies, and are available to buy and sell directly via the GoodDollar GoodReserve smart contract.

The value in the GoodDollar reserve comes from the interest that is generated from Supporters who stake cryptocurrencies in decentralized third-party protocols. Through the amassed reserve interest, G$ tokens are minted. They are used to pay Supporters market-rate interest payments, while a daily amount of G$ tokens is set aside to be distributed as basic income.

### **GoodDollar Money Flow, in detail** <a href="#d7389pq6vqpd" id="d7389pq6vqpd"></a>

GoodDollar is a new kind of digital economy with a UBI distribution model. The protocol is able to sustainably generate a crypto token (G$) for onward distribution in two ways:

1. Through the addition of funds to the GoodDollar Reserve via interest earned on capital staked with third-party protocols, or the purchase of G$ from the GoodDollar Reserve.
2. Through reductions in the reserve ratio.

### **How the GoodDollar system works** <a href="#cbghnzkzyo0f" id="cbghnzkzyo0f"></a>

This is the money flow that underpins the generation of GoodDollar crypto UBI.

<figure><img src="/files/u7fm4cfjMvosDt5kBtsu" alt=""><figcaption></figcaption></figure>

1. Supporter stakes crypto to the GoodDollar Trust.
2. The GoodDollar Trust stakes that money to a third-party DeFi protocol.
3. The third-party DeFi protocol issues a staking token (e.g. CDAI) to the GoodDollar Trust.
4. In return for staking, the supporter is entitled to be rewarded with a sum of GOOD (governance tokens). The staker can then either withdraw these rewards.
   1. The staker can withdraw his stake at any time.
5. Keeper (any player in the ecosystem who wants to do this work) activates the Fund Manager, to funnel interest back to the GoodDollar Trust:
   1. The keeper is also rewarded with G$.
6. Fund Manager:
   1. Collects interest from the different GoodStaking contracts and sends this to the GoodDollar Reserve.
   2. Converts any extra tokens generated through staking to CDAI.
   3. Swaps the interest payments into G$.
   4. Sends the G$ over the Bridge to all distribution contracts.
7. The DisCo then divides the G$ among all whitelisted wallets that have clicked “claim” on the app within the preceding 24 hours.

**Notes:**

In V3, the reserve allows for setting multiple recipients for the minted UBI.


# System's Elements

{% hint style="warning" %}
**Notice of Potential Information Variability**

As of December 21, 2023, the information in GoodDocs may not reflect the most current updates. The team is diligently working to review and revise the documentation to ensure accuracy. Please check back at a later date for the most up-to-date information.
{% endhint %}

## 1. **The token (G$)**

The ***GoodDollar token (G$)*** is an ERC-20 crypto token with a max supply of 2.2 trillion. It is native to Ethereum and also operates on Fuse and Celo.

## **2. The Reserve** <a href="#reserve" id="reserve"></a>

The ***GoodDollar Reserve*** is the smart contract that governs the vault holding the assets that back G$ tokens. The algorithm that guides the reserve is based on the Bancor formula, which has been altered to fit GoodDollar’s needs. There are two important characteristics unique to the GoodDollar Reserve:

1. The reserve supports the generation of G$. Users can always convert to and from G$ via the reserve.
2. The unique math of the GoodDollar Reserve lends G$ exceptional stability.

### **Exit Contributions** <a href="#mebn0hpwchkh" id="mebn0hpwchkh"></a>

In addition to the G$ coin and the GOOD governance token, the GoodDollar ecosystem includes a third type of crypto token: ***G$X***. Members who hold G$X tokens can use these to reduce their exit contributions when selling G$ to the reserve by an amount set by the DAO. Users acquire G$X tokens as a reward for buying G$ from the reserve (currently, a user who buys 100 G$ will also receive 100 G$X).

### **Helpers** <a href="#p1dxu7aswyt0" id="p1dxu7aswyt0"></a>

***Helper contracts*** are smart contracts that connect the GoodDollar Reserve to other liquidity networks in order to allow liquidity to flow from G$ to any other token that has an automated market maker (AMM). For example, if a user wants to convert token X to G$, the helper contract will first convert token X to DAI using Uniswap, and then convert DAI to CDAI using Compound. Finally, it will convert the CDAI to G$ using the GoodDollar Reserve. Future versions of the protocol may extend this functionality to additional protocols, such as Bancor.

## **3. The Trust** <a href="#mn9xjitr972u" id="mn9xjitr972u"></a>

The aim of the ***GoodDollar Trust*** is to generate an ongoing flow of money into the GoodDollar Reserve. What we refer to as the GoodDollar Trust is in actuality a collection of trust funds, or staking contracts, that “wrap” third-party deposit-taking DeFi protocols. Each protocol and token has a separate trust fund.&#x20;

## **4. Savings rewards**

Rewards are fixed at 5% APY.

## **5. The Fund Manager** <a href="#q0skiu5ion2h" id="q0skiu5ion2h"></a>

Responsible for several critical processes in the GoodDollar protocol. These include:

* The activation of UBI generation.
* The transfer of interest from the GoodDollar Trust to the GoodDollar Reserve.
* The transfer of funds to the Bridge and onward to the DisCo for distribution to UBI Claimers via the Fuse blockchain.

## **6. The Distribution Contract (DisCo)** <a href="#r9w6swau5npq" id="r9w6swau5npq"></a>

The ***DisCo***, or ***Distribution Contract***, is a smart contract that handles the distribution of G$ to all white-listed addresses.

## **7. Governance (DAO)**

The GoodDollar governance model is based on the Compound governance model and code, as set out [here](https://compound.finance/docs/governance#comp). Critical to the process is the **GOOD token**, a non-transferable token that controls all smart contracts within the GoodDollar ecosystem.


# Core Contracts & API

## Abstract

GoodDollar Protocol is deployed on both the Ethereum mainnet, on the Fuse sidechain and on Celo. Contracts like the GoodReserve are only on Mainnet, and other contracts like the UBIScheme are on the Fuse sidechain and Celo. Certain contracts, such as the DAO and G$ Token contracts, are deployed on all networks.

## Tables of addresses

### Core Contracts

<table><thead><tr><th width="209">Contract</th><th width="139">Mainnet</th><th width="143">Fuse</th><th width="132">Celo</th><th>XDC</th><th width="193">Source code</th><th width="221" data-type="files">Audits</th></tr></thead><tbody><tr><td><a href="/pages/WVvYdvIg3Av19Wz32tvh">GoodDollar ERC20</a></td><td><a href="https://etherscan.io/address/0x67C5870b4A41D4Ebef24d2456547A03F1f3e094B">0x67C5870b4A41D4Ebef24d2456547A03F1f3e094B</a></td><td><a href="https://explorer.fuse.io/address/0x495d133B938596C9984d462F007B676bDc57eCEC/transactions">0x495d133B938596C9984d462F007B676bDc57eCEC</a></td><td><a href="https://explorer.celo.org/mainnet/address/0x62B8B11039FcfE5aB0C56E502b1C372A3d2a9c7A">0x62B8B11039FcfE5aB0C56E502b1C372A3d2a9c7A</a></td><td><a href="https://xdcscan.com/address/0xec2136843a983885aebf2feb3931f73a8ebee50c">0xEC2136843a983885AebF2feB3931F73A8eBEe50c</a></td><td><a href="https://github.com/GoodDollar/GoodContracts/blob/master/contracts/token/GoodDollar.sol">GoodDollar.sol</a><br><a href="https://github.com/GoodDollar/GoodProtocol/blob/master/contracts/token/superfluid/SuperGoodDollar.sol">SuperGoodDollar.sol (celo only)</a></td><td></td></tr><tr><td><a href="/pages/JCoaznr90CthiBiZQUte">GoodCompoundStaking V3 (DAI)</a></td><td><a href="https://etherscan.io/address/0x7b7246c78e2f900d17646ff0cb2ec47d6ba10754">0x7b7246c78e2f900d17646ff0cb2ec47d6ba10754</a></td><td></td><td></td><td></td><td><a href="https://github.com/GoodDollar/GoodProtocol/blob/master/contracts/staking/compound/GoodCompoundStakingV2.sol">GoodCompoundStakingV2.sol</a></td><td></td></tr><tr><td><a href="/pages/tDliriK1iGsri36rFzzs">GoodAaveStaking V3 (USDC)</a></td><td><a href="https://etherscan.io/address/0x3ff2d8eb2573819a9ef7167d2ba6fd6d31b17f4f">0x3ff2d8eb2573819a9ef7167d2ba6fd6d31b17f4f</a></td><td></td><td></td><td></td><td><a href="https://github.com/GoodDollar/GoodProtocol/blob/master/contracts/staking/aave/GoodAaveStakingV2.sol">GoodAaveStakingV2.sol</a></td><td></td></tr><tr><td><a href="/pages/xsNIHspuckeUUhGRPR3y">GoodReserveCDai</a></td><td><a href="https://etherscan.io/address/0xa150a825d425B36329D8294eeF8bD0fE68f8F6E0">0xa150a825d425B36329D8294eeF8bD0fE68f8F6E0</a></td><td></td><td></td><td></td><td><a href="https://github.com/GoodDollar/GoodProtocol/blob/master/contracts/reserve/GoodReserveCDai.sol">GoodReserveCDai.sol</a></td><td><a href="/files/iXaiNoDNM5XAQpaYH4R3">/files/iXaiNoDNM5XAQpaYH4R3</a></td></tr><tr><td><a href="/pages/m4p7uJL6CrMypfzLOOQh">GoodFundManager</a></td><td><a href="https://etherscan.io/address/0x0c6c80d2061afa35e160f3799411d83bdeea0a5a">0x0c6c80d2061afa35e160f3799411d83bdeea0a5a</a></td><td></td><td></td><td></td><td><a href="https://github.com/GoodDollar/GoodProtocol/blob/master/contracts/staking/GoodFundManager.sol">GoodFundManager.sol</a></td><td><a href="/files/iXaiNoDNM5XAQpaYH4R3">/files/iXaiNoDNM5XAQpaYH4R3</a></td></tr><tr><td><a href="/pages/kNZU3Ug6UDCTct3fzxW7">GoodMarketMaker</a></td><td><a href="https://etherscan.io/address/0xDAC6A0c973Ba7cF3526dE456aFfA43AB421f659F">0xDAC6A0c973Ba7cF3526dE456aFfA43AB421f659F</a></td><td></td><td></td><td></td><td><a href="https://github.com/GoodDollar/GoodProtocol/blob/master/contracts/reserve/GoodMarketMaker.sol">GoodMarketMaker.sol</a></td><td></td></tr><tr><td><a href="/pages/HJjWAb8trQBhladelAMY">ContributionCalculation</a></td><td><a href="https://etherscan.io/address/0x8eEC64bb6807c0178f96277cCE6a334B4e565E5C">0x8eEC64bb6807c0178f96277cCE6a334B4e565E5C</a></td><td></td><td></td><td></td><td><a href="https://github.com/GoodDollar/GoodContracts/blob/master/stakingModel/contracts/ContributionCalculation.sol">ContributionCalculation.sol</a></td><td></td></tr><tr><td><a href="/pages/U0NrK5OjVuxykl6FriMT">UBIScheme</a></td><td></td><td><a href="https://explorer.fuse.io/address/0xd253A5203817225e9768C05E5996d642fb96bA86/transactions">0xd253A5203817225e9768C05E5996d642fb96bA86</a></td><td><a href="https://explorer.celo.org/mainnet/address/0x43d72Ff17701B2DA814620735C39C620Ce0ea4A1">0x43d72Ff17701B2DA814620735C39C620Ce0ea4A1</a></td><td><a href="https://xdcscan.com/address/0x22867567e2d80f2049200e25c6f31cb6ec2f0faf">0x22867567E2D80f2049200E25C6F31CB6Ec2F0faf</a></td><td><a href="https://github.com/GoodDollar/GoodProtocol/blob/master/contracts/ubi/UBIScheme.sol">UBIScheme.sol</a></td><td></td></tr><tr><td><a href="/pages/ur9ml5PhmQL5vwUtmGK7">Identity</a></td><td><a href="https://etherscan.io/address/0x76e76e10Ac308A1D54a00f9df27EdCE4801F288b">0x76e76e10Ac308A1D54a00f9df27EdCE4801F288b</a></td><td><a href="https://explorer.fuse.io/address/0xFa8d865A962ca8456dF331D78806152d3aC5B84F/transactions">0xFa8d865A962ca8456dF331D78806152d3aC5B84F</a></td><td><a href="https://explorer.celo.org/mainnet/address/0xC361A6E67822a0EDc17D899227dd9FC50BD62F42">0xC361A6E67822a0EDc17D899227dd9FC50BD62F42</a></td><td><a href="https://xdcscan.com/address/0x27a4a02c9ed591e1a86e2e5d05870292c34622c9">0x27a4a02C9ed591E1a86e2e5D05870292c34622C9</a></td><td><a href="https://github.com/GoodDollar/GoodProtocol/blob/master/contracts/identity/IdentityV2.sol">Identity.sol</a></td><td></td></tr><tr><td><a href="/pages/09pQYh4kBR8draZ9gbRm">FirstClaimPool</a></td><td></td><td><a href="https://explorer.fuse.io/address/0x18BcdF79A724648bF34eb06701be81bD072A2384/transactions">0x18BcdF79A724648bF34eb06701be81bD072A2384</a></td><td></td><td></td><td><a href="https://github.com/GoodDollar/GoodContracts/blob/master/stakingModel/contracts/FirstClaimPool.sol">FirstClaimPool.sol</a></td><td></td></tr><tr><td><a href="/pages/fCVOXpqYIbUzy9WlzJJy">AdminWallet</a></td><td></td><td><a href="https://explorer.fuse.io/address/0x9F75dAcB77419b87f568d417eBc84346e134144E/transactions">0x9F75dAcB77419b87f568d417eBc84346e134144E</a></td><td></td><td><a href="https://xdcscan.com/address/0x66fc1be551f752706130b6f54d84141f8c2ae8bb">0x66fc1bE551f752706130b6f54d84141F8c2Ae8Bb</a></td><td><a href="https://github.com/GoodDollar/GoodContracts/blob/master/contracts/wallet/AdminWallet.sol">AdminWallet.sol</a></td><td></td></tr><tr><td><a href="/pages/nFY87axjuFqot5J2Qzcs">OneTimePayments</a></td><td></td><td><a href="https://explorer.fuse.io/address/0xd9Aa86e0Ddb932bD78ab8c71C1B98F83cF610Bd4/transactions">0xd9Aa86e0Ddb932bD78ab8c71C1B98F83cF610Bd4</a></td><td><a href="https://celoscan.io/address/0xB27D247f5C2a61D2Cb6b6E67FEE51d839447e97d">0xB27D247f5C2a61D2Cb6b6E67FEE51d839447e97d</a></td><td></td><td><a href="https://github.com/GoodDollar/GoodContracts/blob/master/contracts/dao/schemes/OneTimePayments.sol">OneTimePayments.sol</a></td><td></td></tr><tr><td><a href="/pages/BNGLX2iHVllDB0Xyp3TZ">NameService</a></td><td><a href="https://etherscan.io/address/0xec6dcE387B1616a0c44fF2E4fA9E90E53Cf14eb0">0xec6dcE387B1616a0c44fF2E4fA9E90E53Cf14eb0</a></td><td><a href="https://explorer.fuse.io/address/0xec6dcE387B1616a0c44fF2E4fA9E90E53Cf14eb0/transactions">0xec6dcE387B1616a0c44fF2E4fA9E90E53Cf14eb0</a></td><td><a href="https://explorer.celo.org/mainnet/address/0x0F5dB7a64A6a64052693676CA898EC7F7A94FF4e">0x0F5dB7a64A6a64052693676CA898EC7F7A94FF4e</a></td><td><a href="https://xdcscan.com/address/0x1e5154bf5e31ff56051bbd45958b879fb7a290fe">0x1e5154Bf5e31FF56051bbd45958b879Fb7a290FE</a></td><td><a href="https://github.com/GoodDollar/GoodProtocol/blob/master/contracts/utils/NameService.sol">NameService.sol</a></td><td></td></tr><tr><td><a href="/pages/8Ko9iZn0EYD7X1eWpKtN">GReputation</a></td><td><a href="https://etherscan.io/address/0x603b8c0f110e037b51a381cbcacabb8d6c6e4543">0x603b8c0f110e037b51a381cbcacabb8d6c6e4543</a></td><td><a href="https://explorer.fuse.io/address/0x603B8C0F110E037b51A381CBCacAbb8d6c6E4543/transactions">0x603B8C0F110E037b51A381CBCacAbb8d6c6E4543</a></td><td><a href="https://explorer.celo.org/mainnet/address/0xa9000Aa66903b5E26F88Fa8462739CdCF7956EA6">0xa9000Aa66903b5E26F88Fa8462739CdCF7956EA6</a></td><td></td><td><a href="https://github.com/GoodDollar/GoodProtocol/blob/master/contracts/governance/GReputation.sol">GReputation.sol</a></td><td></td></tr><tr><td><a href="/pages/YFGE3QTjq6Do6GQDGB2p">CompoundVotingMachine</a></td><td><a href="https://etherscan.io/address/0x57ee6ceff51cb30ecb1245934a882c500fbec1e9">0x57ee6ceff51cb30ecb1245934a882c500fbec1e9</a></td><td><a href="https://explorer.fuse.io/address/0x57Ee6Ceff51CB30Ecb1245934a882c500Fbec1e9/transactions">0x57Ee6Ceff51CB30Ecb1245934a882c500Fbec1e9</a></td><td></td><td></td><td><a href="https://github.com/GoodDollar/GoodProtocol/blob/master/contracts/governance/CompoundVotingMachine.sol">CompoundVotingMachine.sol</a></td><td></td></tr><tr><td><a href="/pages/g9vLkmjW75RZj7rUXJuk">ClaimersDistribution</a></td><td></td><td><a href="https://explorer.fuse.io/address/0x1aE4929090258A9D5000D98Cfb8A27174d345834/transactions">0x1aE4929090258A9D5000D98Cfb8A27174d345834</a></td><td></td><td></td><td><a href="https://github.com/GoodDollar/GoodProtocol/blob/master/contracts/governance/ClaimersDistribution.sol">ClaimersDistribution.sol</a></td><td></td></tr><tr><td><a href="/pages/QlJQ7skKYcpvT8vfdEC5">GovernanceStaking</a></td><td></td><td><a href="https://explorer.fuse.io/address/0xB7C3e738224625289C573c54d402E9Be46205546/transactions">0xB7C3e738224625289C573c54d402E9Be46205546</a></td><td></td><td></td><td><a href="https://github.com/GoodDollar/GoodProtocol/blob/master/contracts/governance/GovernanceStaking.sol">GovarnanceStaking.sol</a></td><td></td></tr><tr><td><a href="/pages/0XNVD4lePHhcxSDE1Fcf">Invites</a></td><td></td><td><a href="https://explorer.fuse.io/address/0xCa2F09c3ccFD7aD5cB9276918Bd1868f2b922ea0/transactions">0xCa2F09c3ccFD7aD5cB9276918Bd1868f2b922ea0</a></td><td><a href="https://celoscan.io/address/0x36829D1Cda92FFF5782d5d48991620664FC857d3">0x36829D1Cda92FFF5782d5d48991620664FC857d3</a></td><td><a href="https://xdcscan.com/address/0x6bd698566632bf2e81e2278f1656cb24aaf06d2e">0x6bd698566632bf2e81e2278f1656CB24aAF06D2e</a></td><td><a href="https://github.com/GoodDollar/GoodProtocol/blob/master/contracts/invite/InvitesV1.sol">InvitesV1.sol</a></td><td></td></tr><tr><td><a href="/pages/6BzF3KwnUVIKlAMcPcwc">ExchangeHelper</a></td><td><a href="https://etherscan.io/address/0x98FA532Dd5C3a6b66fbf370813803192DE4e0abd">0x98FA532Dd5C3a6b66fbf370813803192DE4e0abd</a></td><td></td><td></td><td></td><td><a href="https://github.com/GoodDollar/GoodProtocol/blob/master/contracts/reserve/ExchangeHelper.sol">ExchangeHelper.sol</a></td><td></td></tr><tr><td><a href="/pages/qMMTIyF1b0MgoUJkkomi">StakersDistribution</a></td><td><a href="https://etherscan.io/address/0x5766cf4b2fdb09d986eb1783d276013c224e28c8">0x5766cf4b2fdb09d986eb1783d276013c224e28c8</a></td><td></td><td></td><td></td><td><a href="https://github.com/GoodDollar/GoodProtocol/blob/master/contracts/governance/StakersDistribution.sol">StakersDistribution.sol</a></td><td></td></tr><tr><td><a href="/pages/ty8W5lHNdl33tldltgkl">UniswapV2SwapHelper</a></td><td><a href="https://etherscan.io/address/0x62305662fA7c4BC442803b940d9192DbDC92D710">0x62305662fA7c4BC442803b940d9192DbDC92D710</a></td><td></td><td></td><td></td><td><a href="https://github.com/GoodDollar/GoodProtocol/blob/master/contracts/staking/UniswapV2SwapHelper.sol">UniswapV2SwapHelper.sol</a></td><td></td></tr><tr><td><a href="/pages/M34S5OPzgQZHHVL28kPr">CompoundStakingFactory</a></td><td><a href="https://etherscan.io/address/0x78cc5ab2f0990b5fe58f95baebf8f37879534aeb">0x78cc5ab2f0990b5fe58f95baebf8f37879534aeb</a></td><td></td><td></td><td></td><td><a href="https://github.com/GoodDollar/GoodProtocol/blob/master/contracts/staking/compound/CompoundStakingFactory.sol">CompoundStakingFactory.sol</a></td><td></td></tr><tr><td><a href="/pages/bPOsGIDtvRz86xbwksOX">AaveStakingFactory</a></td><td><a href="https://etherscan.io/address/0xf4411c22766947DB2da39Ad534A040b770B51153">0xf4411c22766947DB2da39Ad534A040b770B51153</a></td><td></td><td></td><td></td><td><a href="https://github.com/GoodDollar/GoodProtocol/blob/master/contracts/staking/aave/AaveStakingFactory.sol">AaveStakingFactory.sol</a></td><td></td></tr><tr><td><a href="/pages/fxq7rDYxc42Xg9fLR8JD">BancorFormula</a></td><td><a href="https://etherscan.io/address/0xA049894d5dcaD406b7C827D6dc6A0B58CA4AE73a">0xA049894d5dcaD406b7C827D6dc6A0B58CA4AE73a</a></td><td></td><td></td><td></td><td><a href="https://github.com/GoodDollar/GoodProtocol/blob/master/contracts/utils/BancorFormula.sol">BancorFormula.sol</a></td><td></td></tr><tr><td><a href="/pages/24diZjOp7ztwWUGv2KZQ">FuseFaucet</a></td><td></td><td><a href="https://explorer.fuse.io/address/0x01ab5966C1d742Ae0CFF7f14cC0F4D85156e83d9/transactions">0x01ab5966C1d742Ae0CFF7f14cC0F4D85156e83d9</a></td><td></td><td></td><td><a href="https://github.com/GoodDollar/GoodProtocol/blob/master/contracts/fuseFaucet/FuseFaucet.sol">FuseFaucet.sol</a></td><td></td></tr><tr><td>CeloFaucet</td><td></td><td></td><td><a href="https://celoscan.io/address/0x4F93Fa058b03953C851eFaA2e4FC5C34afDFAb84">0x4F93Fa058b03953C851eFaA2e4FC5C34afDFAb84</a></td><td></td><td></td><td></td></tr><tr><td>XDCFaucet</td><td></td><td></td><td></td><td><a href="https://xdcscan.com/address/0x7344da1be296f03fbb8082adac5696058b5a9bd9">0x7344Da1Be296f03fbb8082aDaC5696058B5a9bd9</a></td><td></td><td></td></tr></tbody></table>

### Token Bridge Contracts

### Bridge Contracts

<table><thead><tr><th>Contract</th><th width="128">Mainnet</th><th width="130.6666259765625">Fuse</th><th width="135.1109619140625">Celo</th><th>XDC</th><th>Source code</th><th data-type="files">Audits</th></tr></thead><tbody><tr><td>GoodDollarMintBurnWrapper</td><td></td><td></td><td><a href="https://explorer.celo.org/mainnet/address/0x5566b6E4962BA83e05a426Ad89031ec18e9CadD3">0x5566b6E4962BA83e05a426Ad89031ec18e9CadD3</a></td><td></td><td></td><td></td></tr><tr><td>MessagePassingBridge</td><td>0xa3247276DbCC76Dd7705273f766eB3E8a5ecF4a5</td><td>0xa3247276DbCC76Dd7705273f766eB3E8a5ecF4a5</td><td>0xa3247276DbCC76Dd7705273f766eB3E8a5ecF4a5</td><td>0xa3247276DbCC76Dd7705273f766eB3E8a5ecF4a5</td><td>MessagePassingBridge.Sol</td><td><a href="/files/iXaiNoDNM5XAQpaYH4R3">/files/iXaiNoDNM5XAQpaYH4R3</a></td></tr><tr><td>ForeignBridge (mainnet -> fuse)</td><td><a href="https://etherscan.io/address/0xD5D11eE582c8931F336fbcd135e98CEE4DB8CCB0">0xD5D11eE582c8931F336fbcd135e98CEE4DB8CCB0</a></td><td></td><td></td><td></td><td><a href="https://github.com/fuseio/tokenbridge-contracts/blob/master/contracts/upgradeable_contracts/amb_erc677_to_erc677/ForeignAMBErc677ToErc677.sol">ForeignAMBErc677ToErc677.sol</a></td><td></td></tr><tr><td>HomeBridge (fuse -> mainnet)</td><td></td><td><a href="https://explorer.fuse.io/address/0xD39021DB018E2CAEadb4B2e6717D31550e7918D0">0xD39021DB018E2CAEadb4B2e6717D31550e7918D0</a></td><td></td><td></td><td><a href="https://github.com/fuseio/tokenbridge-contracts/blob/master/contracts/upgradeable_contracts/amb_erc677_to_erc677/HomeAMBErc677ToErc677.sol">HomeAMBErc677ToErc677.sol</a></td><td></td></tr></tbody></table>

Fuse bridge contracts were developed by [Fuse](https://fuse.io).

{% hint style="info" %}
Note: for regular users it is recommended to use FuseSwap Bridge in order to avoid losing your tokens ([help](https://docs.fuse.io/fuseswap/bridge-fuse-erc20-tokens)). FuseSwap Bridge: [Mainnet -> Fuse](https://fuseswap.com/#/bridge/0x67C5870b4A41D4Ebef24d2456547A03F1f3e094B) | [Fuse -> Mainnet](https://fuseswap.com/#/bridge/0x495d133B938596C9984d462F007B676bDc57eCEC).
{% endhint %}

Note: for regular users it is recommended to use FuseSwap Bridge in order to avoid losing your tokens ([help](https://docs.fuse.io/fuseswap/bridge-fuse-erc20-tokens)). FuseSwap Bridge: [Mainnet -> Fuse](https://fuseswap.com/#/bridge/0x67C5870b4A41D4Ebef24d2456547A03F1f3e094B) | [Fuse -> Mainnet](https://fuseswap.com/#/bridge/0x495d133B938596C9984d462F007B676bDc57eCEC).

### DAO Contracts

DAO contracts were developed by [DAOStack](https://daostack.io)

<table><thead><tr><th width="127.111083984375">Contract</th><th width="134.55560302734375">Mainnet</th><th width="129.1109619140625">Fuse</th><th width="133.5555419921875">Celo</th><th width="136.888916015625">XDC</th><th>Source code</th></tr></thead><tbody><tr><td>Controller</td><td><a href="https://etherscan.io/address/0x95C0d9dCEA1E243ED696F34CAc5e6559C3c128a3">0x95C0d9dCEA1E243ED696F34CAc5e6559C3c128a3</a></td><td><a href="https://explorer.fuse.io/address/0xBcE053b99e22158f8B62f4DBFbEdE1f936b2D4e4">0xBcE053b99e22158f8B62f4DBFbEdE1f936b2D4e4</a></td><td><a href="https://explorer.celo.org/mainnet/address/0x0be7C592374EE0bD0CcBFC76Be758a138BcaEc6E">0x0be7C592374EE0bD0CcBFC76Be758a138BcaEc6E</a></td><td><a href="https://xdcscan.com/address/0x75a8be0c2deaded8fc9eceb5f01ad0b979b7ad03">0x75a8bE0C2dEaDEd8Fc9ECEB5F01ad0B979b7AD03</a></td><td><a href="http://github.com/daostack/arc/tree/master/contracts/controller/Controller.sol">Controller.sol</a></td></tr><tr><td>Avatar</td><td><a href="https://etherscan.io/address/0x1ecFD1afb601C406fF0e13c3485f2d75699b6817">0x1ecFD1afb601C406fF0e13c3485f2d75699b6817</a></td><td><a href="https://explorer.fuse.io/address/0xf96dADc6D71113F6500e97590760C924dA1eF70e">0xf96dADc6D71113F6500e97590760C924dA1eF70e</a></td><td><a href="https://explorer.celo.org/mainnet/address/0x495d133B938596C9984d462F007B676bDc57eCEC">0x495d133B938596C9984d462F007B676bDc57eCEC</a></td><td><a href="https://xdcscan.com/address/0x21eac3fe218307bee0463f77ebca3b50f452c0ce">0x21eaC3fE218307BeE0463F77EBcA3b50F452C0Ce</a></td><td><a href="http://github.com/daostack/arc/tree/master/contracts/controller/Avatar.sol">Avatar.sol</a></td></tr><tr><td>DAOCreator</td><td></td><td></td><td><a href="https://explorer.celo.org/mainnet/address/0x76e76e10Ac308A1D54a00f9df27EdCE4801F288b">0x76e76e10Ac308A1D54a00f9df27EdCE4801F288b</a></td><td><a href="https://xdcscan.com/address/0xa2b9993d198904e4bdce48379fdff65405607f42">0xa2B9993D198904e4bdCE48379FDff65405607F42</a></td><td></td></tr></tbody></table>

#### For the complete list of contracts, including those in the staging and dev environments, please refer to [GitHub.](https://github.com/GoodDollar/GoodProtocol/blob/master/releases/deployment.json)




---

[Next Page](/llms-full.txt/1)

