> For the complete documentation index, see [llms.txt](https://docs.plugin.global/llms.txt). Markdown versions of documentation pages are available by appending `.md` to page URLs; this page is available as [Markdown](https://docs.plugin.global/plugin-automation/plugin-automation-upkeep-registration-ui-developer-guide.md).

# Plugin Automation - Upkeep Registration UI: Developer Guide

*Developer Guide (Registry 2.3 / OCR3)*

## Purpose of this document

This document is for the developer building the **front-end / user interface** that lets external DApp teams register their own Upkeep contract with Plugin Automation on XDC.

**In scope:** everything needed to build the UI — wallet connection, the registration form, the on-chain calls the UI makes, the events it listens to, and what to display back to the user.

**Out of scope:** how to *write, deploy, or configure* an Automation-compatible smart contract. The DApp team brings their own already-deployed Upkeep contract; we are not teaching them (or building) that part.

## Background — what is “Automation”, in plain terms?

> Read this section fully before the rest of the doc. It has no jargon assumed.

### The problem it solves

Smart contracts can't act on their own — nothing on a blockchain runs automatically. A contract only does something when **someone** sends a transaction that calls it.

So if a DApp needs some function on their contract to run periodically (for example, “check every hour if a loan is undercollateralized and liquidate it if so”) or in response to a condition (for example, “as soon as price crosses $X, do Y”), somebody has to keep watching and keep sending those transactions manually, forever.

That's tedious, easy to forget, and doesn't scale.

### What Plugin Automation does

It's a service, run by us using a network of off-chain nodes, that watches contracts on behalf of DApp teams and automatically sends the transaction that triggers their contract's logic whenever the conditions are met.

The DApp team never has to babysit it themselves.

### Key terms

* **Upkeep contract** — the DApp team's own smart contract that needs to be triggered automatically. It's not written by us and not written by our UI; the DApp team writes and deploys it themselves, *before* they ever come to our site. It just needs two specific functions in it: a “can this run now?” check function and a “do the thing” function, so our system knows how to talk to it.
* **Registering an upkeep** — the one-time action of telling our system “here's my contract's address, please start watching/triggering it.” This is the whole purpose of the UI we're building: it's the front door where a DApp team registers their contract with us.
* **The Registry** — our core on-chain contract that keeps the official list of every registered upkeep, their funding balance, and their settings. Think of it like a database, except it lives on-chain and our automation nodes read from it to know what to check and run.
* **Funding an upkeep** — running an upkeep costs gas (transaction fees) every time it's triggered. The DApp team deposits tokens up front into the Registry as a balance for their upkeep, and that balance is drawn down each time it runs. If the balance runs out, the upkeep stops being triggered.
* **The automation node network** — the off-chain software, run by our infrastructure and invisible to the DApp team, that continuously checks all registered upkeeps and submits the trigger transaction when needed. This part already exists and works; it's not something the UI or the DApp team touches at all.

### What the UI we're building actually is, in one sentence

It's a web page where a DApp developer connects their wallet, tells us the address of a contract they already deployed, puts some funding behind it, and clicks “Register” — and from that point on, our node network takes over and keeps calling that contract automatically.

Everything after registration — checking, funding, pausing — is just reading and writing values on the Registry contract; there is no custom logic to build beyond calling its functions.

## Actors and contracts involved

| Actor / Contract                        | Role                                                                                                                                                                                                                                                                                                           |
| --------------------------------------- | -------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------- |
| **DApp developer (end user of our UI)** | Owns/admins an already-deployed Upkeep contract. Brings the address, doesn't write any code on our site.                                                                                                                                                                                                       |
| **Upkeep contract**                     | Provided by the DApp developer. Must implement `checkUpkeep(bytes)` and `performUpkeep(bytes)`. Our UI never generates or edits this.                                                                                                                                                                          |
| **Registry contract (OCR3 / 2.3)**      | Plugin's core contract. Holds registered upkeeps, their balances, and triggers `performUpkeep` calls via the keeper/OCR3 node network.                                                                                                                                                                         |
| **Registrar contract (if used)**        | Optional front door that validates registration params and forwards to the Registry — used so registration can be a single approve + register call rather than requiring Registry admin whitelisting. Confirm with Karthick whether our deployment registers directly against the Registry or via a Registrar. |
| **PLI token (or native funding token)** | Used to fund the upkeep so the keeper network gets paid for performing it.                                                                                                                                                                                                                                     |

## UI flow, step by step

{% stepper %}
{% step %}

## Connect wallet

Connect the DApp developer's wallet. This wallet will become the upkeep's admin.
{% endstep %}

{% step %}

## Input form

Collect the following values:

* Upkeep contract address — the contract the DApp team already deployed
* Upkeep name/label — display only, stored off-chain or in registry metadata
* Gas limit — maximum gas to reserve for `performUpkeep`
* Admin address — defaults to the connected wallet, editable
* Initial funding amount
* Optional `checkData` / trigger config bytes, if the upkeep needs custom check parameters
  {% endstep %}

{% step %}

## Validate contract

Before submitting, optionally call `checkUpkeep` as a view/simulated call against the pasted address to confirm it responds like a valid Automation-compatible contract.

This catches a wrong address early instead of failing on-chain.
{% endstep %}

{% step %}

## Approve token spend

Call the standard ERC-20 `approve()` on the PLI token, or other funding token, for the Registry or Registrar contract.

Approve at least the initial funding amount.
{% endstep %}

{% step %}

## Submit registration

Call `registerUpkeep(...)` on the Registrar, or the equivalent Registry function, passing the form values.
{% endstep %}

{% step %}

## Capture the Upkeep ID

The registration transaction emits an event, such as `UpkeepRegistered`, containing the new `upkeepId`.

Parse the ID from the transaction receipt logs. This ID is how the upkeep is referenced everywhere after this point.
{% endstep %}

{% step %}

## Show confirmation

Show:

* Upkeep ID
* Funded balance
* Status: active
  {% endstep %}
  {% endstepper %}

## Post-registration dashboard

Once registered, the DApp developer should be able to return and view or manage their upkeep(s).

| Action              | Contract call                             | Notes                                                                                        |
| ------------------- | ----------------------------------------- | -------------------------------------------------------------------------------------------- |
| View upkeep details | `getUpkeep(upkeepId)` (view)              | Returns target contract, balance, admin, gas limit, paused state                             |
| Add funds           | `addFunds(upkeepId, amount)`              | Requires prior `approve()`                                                                   |
| Withdraw funds      | `withdrawFunds(upkeepId, amount)`         | Only callable by admin; typically only after cancellation delay, depending on registry rules |
| Pause               | `pauseUpkeep(upkeepId)`                   | Stops performs without removing registration                                                 |
| Unpause             | `unpauseUpkeep(upkeepId)`                 | Resumes                                                                                      |
| Cancel              | `cancelUpkeep(upkeepId)`                  | Starts/executes cancellation; remaining balance becomes withdrawable                         |
| Change admin        | `transferUpkeepAdmin(upkeepId, newAdmin)` | Two-step in most Registry versions: propose + accept                                         |

### Events to listen for

Reflect the following events in the UI:

* `UpkeepRegistered`
* `UpkeepPerformed`
* `UpkeepPaused`
* `UpkeepUnpaused`
* `UpkeepCanceled`
* `FundsAdded`
* `FundsWithdrawn`

{% hint style="warning" %}
Exact function signatures and the deployed Registry/Registrar addresses on XDC mainnet should be pulled from the actual OCR3 (2.3) contract ABI/artifacts we're running. Plug those in before the developer starts building against a testnet, rather than relying on generic Chainlink 2.3 signatures.
{% endhint %}

## What the UI should show per upkeep

* Upkeep ID
* Target contract address
* Status: Active / Paused / Canceled
* Current balance + low-balance warning threshold
* Last performed (block/time), if available from `UpkeepPerformed` event history
* Admin address

## Explicitly not part of this UI

* No code editor or contract deployment for the Upkeep contract itself
* No guidance/help for writing `checkUpkeep` / `performUpkeep` logic
* No OCR3 node configuration — that's our infrastructure, invisible to the DApp developer

## Open items for the requirements doc author

* [ ] Confirm: direct Registry registration vs. Registrar-mediated registration on our deployment
* [ ] Deployed contract addresses (Registry, Registrar, PLI/funding token) — mainnet + any testnet
* [ ] Exact `registerUpkeep` parameter list/order for our Registry 2.3 deployment
* [ ] Minimum funding amount / gas price buffer rules, if enforced
* [ ] Whether `checkData`/trigger config is required for our supported trigger types (custom logic vs. log trigger, etc.)
