Staking Module

Fixed-period staking with admin-configured APYs, three penalty modes and a custom WordPress post type

What the Staking Module Is

The Staking Module lets your users lock a portion of their balance for a fixed period and earn a configurable APY. Each "staking page" is a custom WordPress post (post type wpcrypto_stake_page) with its own coin, periods, rates and penalty rules. Stakes are entirely internal accounting — no smart contract is deployed, no on-chain transaction is made, and your platform's balance ledger is the source of truth.

📋 Quick facts

  • Post type: wpcrypto_stake_page
  • Shortcode: [wpcrypto_stake page_id="X"]
  • Six fixed periods: 10 days, 20 days, 30 days, 3 months, 6 months, 1 year
  • Per-period APY set by the admin (no dynamic / market-driven adjustments)
  • Three penalty modes for early unstake (see below)
  • Default penalty rate: 10% with type reward_only

Where to Find It

Open WP Crypto → Staking Pools in the WordPress admin sidebar. The list mirrors the standard WordPress post list, scoped to the wpcrypto_stake_page post type. From there you can Add New to create a new staking page or open an existing one to edit its periods and rates.

Creating a Staking Page

  1. Add New. WP Crypto → Staking Pools → Add New opens the staking editor.
  2. Set the title and description. These render on the public stake page.
  3. Pick the staked coin. Choose from any coin you have configured in Coins Manager.
  4. Set APY per period. The form gives you one APY input per lock period (10d / 20d / 30d / 3m / 6m / 1y). Empty periods are hidden on the public page.
  5. Configure the early-unstake penalty. Pick a penalty rate (default 10%) and one of the three penalty modes described below.
  6. Publish. The plugin can also auto-create a public WordPress page that embeds the shortcode, or you can paste [wpcrypto_stake page_id="X"] on any page you already have.

Lock Periods and APY

The plugin offers six fixed lock periods. For each period you set the APY independently — there is no global rate, no dynamic adjustment, no market-driven recalculation. The APY you save is the APY users see and earn.

Period key Length Use case
10_days10 daysShort-term liquidity-friendly stake
20_days20 daysSlightly higher APY than 10-day
30_days30 daysMonthly cadence — often the marketing default
3_months3 monthsQuarter-long lock
6_months6 monthsMid-term retention
1_year1 yearLong-term commitment with the highest APY

Rewards are computed pro-rata between the stake start and the unlock time using the saved APY. The runtime helper wpcrypto_stake_pages_calculate_precise_reward() does the math so partial-period figures are accurate to the second.

Penalty Modes

If a user unstakes before the lock period ends, the plugin applies a penalty using one of three modes. The rate (default 10%) is applied to whichever base the mode targets.

Mode Penalty target Best for
reward_only (default)Penalty deducts only from the accrued reward; the principal is returned in fullUser-friendly — penalises only the rewards earned so far
principal_onlyPenalty is applied to the principal; rewards are forfeited entirelyStronger lock — discourages early exit even when no reward has accrued yet
total_amountPenalty is applied to (principal + accrued reward)Maximum deterrent — useful on premium-APY long-term pools

The user-facing stake page renders the chosen mode and the penalty rate so users see exactly what happens before they confirm.

The Shortcode

Embed the public stake page anywhere with:

[wpcrypto_stake page_id="123"]

The page_id attribute references the post id of the staking page you created. The renderer loads the periods, APYs and penalty configuration for that page and displays:

  • The available lock periods with their APYs
  • A live reward calculator
  • The penalty warning
  • A stake-now button (which prompts unauthenticated visitors to log in)
  • The user's own active stakes on this page, if they have any

When the admin publishes a staking page, the plugin can also auto-create a sibling WordPress page that already embeds the shortcode — useful if you do not want to copy-paste the shortcode yourself.

How the Balance Math Works

Stakes are pure ledger operations:

  1. Stake start. The plugin moves the staked amount from the user's available balance to a locked-stake state.
  2. While locked. The reward accrues on read (it is not periodically materialised); the UI shows the precise reward at any point in time.
  3. Unlock at maturity. Principal + accrued reward are credited back to the user's available balance.
  4. Early unstake. The penalty is computed based on the configured mode, the remaining principal/reward is credited back, and the penalty stays with the platform.

No on-chain transaction is made; everything happens in the WordPress database against the user's internal balance.

Operator Notes

⚠️ Things to know before launch

  • Pick APYs you can sustain. The platform pays rewards out of the same balance pool; there is no external yield source.
  • Decide your penalty stance up front. Switching from reward_only to total_amount after users have already staked changes their terms mid-flight — communicate before changing.
  • One stake page per token is usually enough. Create more pages only when you want different penalty rules or different coin pools on the same page.
  • The 10-day period is the shortest. The plugin does not support arbitrary "flexible" periods (e.g. 7 days, 14 days) — the periods are fixed.

Troubleshooting

The stake page renders an empty period grid

None of the six periods has an APY saved. Re-open the staking page in the admin and enter at least one APY before publishing.

Reward calculator shows zero

The APY for the selected period is 0. Pick a period with a non-zero APY, or set one in the admin.

Users can't stake — "balance too low"

The user does not have enough of the staked coin in their available balance. Top them up via the user-management screens or instruct them to deposit / buy the coin first.

Penalty is applied at unlock when it should not be

The unstake button is firing the early-exit branch because the lock period has not technically elapsed yet. Confirm the user opened the stake at the time they think they did — there is no grace period in the calculator.