Skip to content

Add phoenix-protocol (phUSD staking)#2682

Open
gititGoro wants to merge 2 commits into
DefiLlama:masterfrom
Behodler:add-phoenix-protocol
Open

Add phoenix-protocol (phUSD staking)#2682
gititGoro wants to merge 2 commits into
DefiLlama:masterfrom
Behodler:add-phoenix-protocol

Conversation

@gititGoro
Copy link
Copy Markdown

@gititGoro gititGoro commented May 15, 2026

Summary

Adds a yield adapter for the Phoenix Protocol phUSD staking contract on Ethereum mainnet, exposing a single pool searchable as phUSD.

Pool

  • Contract: 0x3984eBC84d45a889dDAc595d13dc0aC2E54819F4 (phUSD staking)
  • Symbol: phUSD
  • Project: phoenix-protocol
  • Chain: Ethereum

Stakers deposit phUSD and receive two emission-based rewards.

APY methodology

  • USDC reward — distributed via linear depletion. Spot rate rewardBalance / depletionDuration is annualized and divided by USD TVL.
  • phUSD reward — auto-minted to hit the contract's desiredAPYBps target. Computed directly as desiredAPYBps / 100 (currently 0; will activate when governance enables it).

apyReward is the sum of the two; apyBase is null (the staking action itself produces no organic yield).

Pricing

phUSD is priced from the Balancer V3 phUSD/sUSDS 50/50 weighted pool:

  1. Read pool balances via Vault getPoolTokens + getCurrentLiveBalances (both tokens 18-dec, no rate provider).
  2. Compute spot: phUsdPriceInSUsds = sUsdsBalance / phUsdBalance.
  3. Convert sUSDS → USDS via the sUSDS ERC4626 convertToAssets(1e18) live exchange rate.
  4. Treat USDS as $1.

Falls back to $1 peg with a warning if any of the on-chain reads fail.

USDC is hardcoded to $1.

Test plan

  • npm run test --adapter=phoenix-protocol — 11/11 passing.
  • Verified pool returned: 1 pool, symbol === 'phUSD', sane TVL (~$11.5k at time of writing).
  • All on-chain reads cross-checked against mainnet RPC.

🤖 Generated with Claude Code

Summary by CodeRabbit

  • New Features

    • Added support for the Phoenix Protocol phUSD staking pool on DefiLlama yields, featuring real-time APY calculations that incorporate both USDC and phUSD emission-based rewards with intelligent pricing fallback mechanisms.
  • Documentation

    • Added comprehensive documentation explaining how rewards are calculated and how phUSD pricing is derived from Balancer pool data.

Review Change Stack

Single-pool adapter for the Phoenix Protocol phUSD staking contract on
Ethereum. Computes USDC reward APY from rewardBalance/depletionDuration
and reads the phUSD-emission APY directly from the contract's
desiredAPYBps target. Prices phUSD via the Balancer V3 phUSD/sUSDS pool
and the sUSDS ERC4626 conversion to USDS.

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
@coderabbitai
Copy link
Copy Markdown
Contributor

coderabbitai Bot commented May 15, 2026

Warning

Rate limit exceeded

@gititGoro has exceeded the limit for the number of commits that can be reviewed per hour. Please wait 54 minutes and 21 seconds before requesting another review.

You’ve run out of usage credits. Purchase more in the billing tab.

⌛ How to resolve this issue?

After the wait time has elapsed, a review can be triggered using the @coderabbitai review command as a PR comment. Alternatively, push new commits to this PR.

We recommend that you space out your commits to avoid hitting the rate limit.

🚦 How do rate limits work?

CodeRabbit enforces hourly rate limits for each developer per organization.

Our paid plans have higher rate limits than the trial, open-source and free plans. In all cases, we re-allow further reviews after a brief timeout.

Please see our FAQ for further information.

ℹ️ Review info
⚙️ Run configuration

Configuration used: defaults

Review profile: CHILL

Plan: Pro

Run ID: 19fd60e9-640d-438a-b0d1-4d5ff913e733

📥 Commits

Reviewing files that changed from the base of the PR and between eba9023 and dcf531c.

📒 Files selected for processing (1)
  • src/adaptors/phoenix-protocol/index.js
📝 Walkthrough

Walkthrough

This PR introduces a new Phoenix Protocol adapter for the yield-server repository. It adds an APY calculation module that fetches phUSD staking TVL and reward rates, derives phUSD pricing from Balancer V3 pool reserves, and computes dual-component yields (USDC-based reward emission and phUSD-based APY from protocol settings).

Changes

Phoenix Protocol Staking Adapter

Layer / File(s) Summary
Adapter implementation and documentation
src/adaptors/phoenix-protocol/README.md, src/adaptors/phoenix-protocol/index.js
README documents phUSD reward and pricing formulas; index.js implements Balancer-based price derivation with $1 fallback, concurrent on-chain state fetch from PHLIMBO contract, USDC-based APY from reward emission and depletionDuration, phUSD-based APY from desiredAPYBps, and pool result export.

🎯 2 (Simple) | ⏱️ ~12 minutes

🐰 A phoenix rises from the staking pool,
With Balancer prices and PHLIMBO rule,
phUSD rewards bloom, APY takes flight,
Dual yields dance in the DeFi light! ✨

🚥 Pre-merge checks | ✅ 5
✅ Passed checks (5 passed)
Check name Status Explanation
Description Check ✅ Passed Check skipped - CodeRabbit’s high-level summary is enabled.
Title check ✅ Passed The title 'Add phoenix-protocol (phUSD staking)' clearly and concisely summarizes the main change: introducing a new yield adapter for the Phoenix Protocol's phUSD staking pool.
Docstring Coverage ✅ Passed No functions found in the changed files to evaluate docstring coverage. Skipping docstring coverage check.
Linked Issues check ✅ Passed Check skipped because no linked issues were found for this pull request.
Out of Scope Changes check ✅ Passed Check skipped because no linked issues were found for this pull request.

✏️ Tip: You can configure your own custom pre-merge checks in the settings.

✨ Finishing Touches
🧪 Generate unit tests (beta)
  • Create PR with unit tests

Thanks for using CodeRabbit! It's free for OSS, and your support helps us grow. If you like it, consider giving us a shout-out.

❤️ Share

Comment @coderabbitai help to get the list of available commands and usage tips.

@github-actions
Copy link
Copy Markdown

The phoenix-protocol adapter exports pools:

Test Suites: 1 passed, 1 total
Tests: 11 passed, 11 total
Snapshots: 0 total
Time: 0.284 s
Ran all test suites.

Nb of pools: 1
 

Sample pools:
┌─────────┬───────────────────────────────────────────────────────┬────────────┬────────────────────┬─────────┬───────────────────┬─────────┬───────────────────┬────────────────────────────────────────────────────────────────────────────────────────────────┬──────────────────────────────────────────────────┬───────────┬─────────────────────────────────────┐
│ (index) │ pool                                                  │ chain      │ project            │ symbol  │ tvlUsd            │ apyBase │ apyReward         │ rewardTokens                                                                                   │ underlyingTokens                                 │ poolMeta  │ url                                 │
├─────────┼───────────────────────────────────────────────────────┼────────────┼────────────────────┼─────────┼───────────────────┼─────────┼───────────────────┼────────────────────────────────────────────────────────────────────────────────────────────────┼──────────────────────────────────────────────────┼───────────┼─────────────────────────────────────┤
│ 0       │ '0x3984ebc84d45a889ddac595d13dc0ac2e54819f4-ethereum' │ 'Ethereum' │ 'phoenix-protocol' │ 'phUSD' │ 11537.63055818622 │ null    │ 6.308491807129091 │ [ '0xA0b86991c6218b36c1d19D4a2e9Eb0cE3606eB48', '0xf3B5B661b92B75C71fA5Aba8Fd95D7514A9CD605' ] │ [ '0xf3B5B661b92B75C71fA5Aba8Fd95D7514A9CD605' ] │ 'Staking' │ 'https://phusd.behodler.io/staking' │
└─────────┴───────────────────────────────────────────────────────┴────────────┴────────────────────┴─────────┴───────────────────┴─────────┴───────────────────┴────────────────────────────────────────────────────────────────────────────────────────────────┴──────────────────────────────────────────────────┴───────────┴─────────────────────────────────────┘

Copy link
Copy Markdown
Contributor

@coderabbitai coderabbitai Bot left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Actionable comments posted: 1

🧹 Nitpick comments (1)
src/adaptors/phoenix-protocol/index.js (1)

51-59: ⚖️ Poor tradeoff

Consider BigInt arithmetic for precision.

Converting balances to Number (lines 51-52) may lose precision for very large pool balances. JavaScript Number has ~15-17 significant decimal digits, which could introduce small rounding errors for 18-decimal tokens with large supplies. For typical pool sizes this is acceptable, but using BigInt arithmetic would be more robust.

🤖 Prompt for AI Agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.

In `@src/adaptors/phoenix-protocol/index.js` around lines 51 - 59, The code
currently converts balances and sharesToAssets to Number which can lose
precision; instead parse balances (balances[idxSusds], balances[idxPhusd]) and
sharesToAssets as BigInt, perform fixed-point arithmetic using a chosen SCALE
(e.g., BigInt(1e18)) to preserve 18-decimal precision: compute phUsdPriceInSUsds
= (sUsdsBalance * SCALE) / phUsdBalance and compute usdsPerSUsds =
(sharesToAssets * SCALE) / BigInt(1e18) (or equivalently keep shares scaled),
then multiply and rescale to produce the final result; update the expressions
that reference sUsdsBalance, phUsdBalance, sharesToAssets, phUsdPriceInSUsds,
and usdsPerSUsds to use BigInt arithmetic and convert the final value to Number
or string only at the return boundary.
🤖 Prompt for all review comments with AI agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.

Inline comments:
In `@src/adaptors/phoenix-protocol/index.js`:
- Around line 37-38: The calls to callView using getPoolTokensAbi and
getCurrentLiveBalancesAbi pass BALANCER_POOL as a bare value; update these
invocations so the third argument is an array containing BALANCER_POOL (e.g.,
callView(BALANCER_VAULT, getPoolTokensAbi, [BALANCER_POOL]) and similarly for
getCurrentLiveBalancesAbi) to match the ABI parameter format used elsewhere and
avoid SDK runtime errors.

---

Nitpick comments:
In `@src/adaptors/phoenix-protocol/index.js`:
- Around line 51-59: The code currently converts balances and sharesToAssets to
Number which can lose precision; instead parse balances (balances[idxSusds],
balances[idxPhusd]) and sharesToAssets as BigInt, perform fixed-point arithmetic
using a chosen SCALE (e.g., BigInt(1e18)) to preserve 18-decimal precision:
compute phUsdPriceInSUsds = (sUsdsBalance * SCALE) / phUsdBalance and compute
usdsPerSUsds = (sharesToAssets * SCALE) / BigInt(1e18) (or equivalently keep
shares scaled), then multiply and rescale to produce the final result; update
the expressions that reference sUsdsBalance, phUsdBalance, sharesToAssets,
phUsdPriceInSUsds, and usdsPerSUsds to use BigInt arithmetic and convert the
final value to Number or string only at the return boundary.
🪄 Autofix (Beta)

Fix all unresolved CodeRabbit comments on this PR:

  • Push a commit to this branch (recommended)
  • Create a new PR with the fixes

ℹ️ Review info
⚙️ Run configuration

Configuration used: defaults

Review profile: CHILL

Plan: Pro

Run ID: 8c4801dc-2662-4d40-9e9d-072218b0caac

📥 Commits

Reviewing files that changed from the base of the PR and between b218cde and eba9023.

📒 Files selected for processing (2)
  • src/adaptors/phoenix-protocol/README.md
  • src/adaptors/phoenix-protocol/index.js

Comment thread src/adaptors/phoenix-protocol/index.js Outdated
Match the form already used by the convertToAssets call in the same
function. The SDK accepts both bare and array forms, but mixing them is
noisy.

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
@github-actions
Copy link
Copy Markdown

The phoenix-protocol adapter exports pools:

Test Suites: 1 passed, 1 total
Tests: 11 passed, 11 total
Snapshots: 0 total
Time: 0.246 s
Ran all test suites.

Nb of pools: 1
 

Sample pools:
┌─────────┬───────────────────────────────────────────────────────┬────────────┬────────────────────┬─────────┬───────────────────┬─────────┬───────────────────┬────────────────────────────────────────────────────────────────────────────────────────────────┬──────────────────────────────────────────────────┬───────────┬─────────────────────────────────────┐
│ (index) │ pool                                                  │ chain      │ project            │ symbol  │ tvlUsd            │ apyBase │ apyReward         │ rewardTokens                                                                                   │ underlyingTokens                                 │ poolMeta  │ url                                 │
├─────────┼───────────────────────────────────────────────────────┼────────────┼────────────────────┼─────────┼───────────────────┼─────────┼───────────────────┼────────────────────────────────────────────────────────────────────────────────────────────────┼──────────────────────────────────────────────────┼───────────┼─────────────────────────────────────┤
│ 0       │ '0x3984ebc84d45a889ddac595d13dc0ac2e54819f4-ethereum' │ 'Ethereum' │ 'phoenix-protocol' │ 'phUSD' │ 11537.63512248753 │ null    │ 6.308489311482701 │ [ '0xA0b86991c6218b36c1d19D4a2e9Eb0cE3606eB48', '0xf3B5B661b92B75C71fA5Aba8Fd95D7514A9CD605' ] │ [ '0xf3B5B661b92B75C71fA5Aba8Fd95D7514A9CD605' ] │ 'Staking' │ 'https://phusd.behodler.io/staking' │
└─────────┴───────────────────────────────────────────────────────┴────────────┴────────────────────┴─────────┴───────────────────┴─────────┴───────────────────┴────────────────────────────────────────────────────────────────────────────────────────────────┴──────────────────────────────────────────────────┴───────────┴─────────────────────────────────────┘

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant