Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
15 changes: 15 additions & 0 deletions CONTRIBUTING.md
Original file line number Diff line number Diff line change
Expand Up @@ -26,6 +26,21 @@ Welcome, and thanks for your interest in contributing. This document is your sta
- [`docs/API_ERROR_REFERENCE.md`](docs/API_ERROR_REFERENCE.md) — every error response the listener API returns
- [`docs/adr/README.md`](docs/adr/README.md) — Architecture Decision Records

## Documentation conventions

Use these names consistently in docs and PRs:

| Concept | Standard form |
|---------|----------------|
| Product name (prose/titles) | **NotifyChain** |
| GitHub repository / clone directory | **Notify-Chain** (`Core-Foundry/Notify-Chain`) |
| Off-chain service | **Listener** (`listener/`) |
| React + Vite UI | **Dashboard** (`dashboard/`) |
| Legacy analytics app | **Frontend** (`frontend/`) |
| On-chain code | **Smart contracts** (`contract/`, `Documents/Task Bounty/`) |

Canonical setup path: workflow guide → [`LOCAL_DEVELOPMENT.md`](LOCAL_DEVELOPMENT.md) (quick) → [`CONTRIBUTOR_SETUP.md`](CONTRIBUTOR_SETUP.md) (detailed).

## Code of Conduct

- Be respectful and inclusive
Expand Down
40 changes: 20 additions & 20 deletions CONTRIBUTOR_ARCHITECTURE_DEEP_DIVE.md
Original file line number Diff line number Diff line change
Expand Up @@ -52,9 +52,9 @@ NotifyChain is split into three decoupled components, separated by network and t
└────────────────────────────────────────────────────────────────────────┘
```

1. **Smart Contracts (On-Chain)**: Written in Rust for the Soroban smart contract platform. They run in a WebAssembly (WASM) sandbox, mutate ledger state, and emit structured events. Located in [contract/contracts/hello-world](file:///workspaces/Notify-Chain/contract/contracts/hello-world) and [Documents/Task Bounty](file:///workspaces/Notify-Chain/Documents/Task%20Bounty).
2. **Listener Service (Off-Chain Engine)**: Written in Node.js and TypeScript. It polls the Stellar RPC, parses, deduplicates, and stores events in SQLite, and dispatches real-time alerts. Located in [listener](file:///workspaces/Notify-Chain/listener).
3. **React Dashboard (Frontend)**: A standard Vite + React SPA that consumes the REST API exposed by the listener service to display events and schedule performance statistics. Located in [dashboard](file:///workspaces/Notify-Chain/dashboard).
1. **Smart Contracts (On-Chain)**: Written in Rust for the Soroban smart contract platform. They run in a WebAssembly (WASM) sandbox, mutate ledger state, and emit structured events. Located in [contract/contracts/hello-world](contract/contracts/hello-world) and [Documents/Task Bounty](Documents/Task%20Bounty).
2. **Listener Service (Off-Chain Engine)**: Written in Node.js and TypeScript. It polls the Stellar RPC, parses, deduplicates, and stores events in SQLite, and dispatches real-time alerts. Located in [listener](listener).
3. **React Dashboard (Frontend)**: A standard Vite + React SPA that consumes the REST API exposed by the listener service to display events and schedule performance statistics. Located in [dashboard](dashboard).

---

Expand All @@ -63,14 +63,14 @@ NotifyChain is split into three decoupled components, separated by network and t
NotifyChain supports two smart contract interaction patterns with different design structures:

### 2.1 Struct Event Pattern (AutoShare)
Implemented in [base/events.rs](file:///workspaces/Notify-Chain/contract/contracts/hello-world/src/base/events.rs). The contract defines dedicated struct types decorated with `#[contractevent]`. Each event carries standard routing topics:
Implemented in [base/events.rs](contract/contracts/hello-world/src/base/events.rs). The contract defines dedicated struct types decorated with `#[contractevent]`. Each event carries standard routing topics:
- **`NotificationCategory`**: A 4-variant enum mapping events to functional domains (`Group`, `Admin`, `Financial`, `Notification`).
- **`NotificationPriority`**: A 4-variant enum detailing severity (`Low`, `Medium`, `High`, `Critical`).

These are appended as the last two indexed topics to ensure backward compatibility for simpler indexers.

### 2.2 Subject-Action Event Pattern (TaskBounty)
Implemented in [src/events.rs](file:///workspaces/Notify-Chain/Documents/Task%20Bounty/src/events.rs). The contract does not use routing metadata structures. Instead, it emits events as tuples of short symbols matching the `(Subject, Action)` schema:
Implemented in [src/events.rs](Documents/Task%20Bounty/src/events.rs). The contract does not use routing metadata structures. Instead, it emits events as tuples of short symbols matching the `(Subject, Action)` schema:
- E.g., `(symbol_short!("task"), symbol_short!("created"))` or `(symbol_short!("sub"), symbol_short!("approved"))`.
- Payload arguments (like task ID, amount, and creator) are passed as tuples in the event data field.

Expand Down Expand Up @@ -116,15 +116,15 @@ sequenceDiagram
```

### 3.1 Step-by-Step Processing Pipeline:
1. **Polling**: The [EventSubscriber](file:///workspaces/Notify-Chain/listener/src/services/event-subscriber.ts) wakes up at configured intervals (default: 30 seconds) and invokes `getEvents` on the Stellar RPC using the last persisted ledger sequence.
2. **Persistent Deduplication**: The [EventDeduplicationService](file:///workspaces/Notify-Chain/listener/src/services/event-deduplication-service.ts) checks each incoming event. It references the `processed_events` SQLite table to see if the event ID has already been indexed.
1. **Polling**: The [EventSubscriber](listener/src/services/event-subscriber.ts) wakes up at configured intervals (default: 30 seconds) and invokes `getEvents` on the Stellar RPC using the last persisted ledger sequence.
2. **Persistent Deduplication**: The [EventDeduplicationService](listener/src/services/event-deduplication-service.ts) checks each incoming event. It references the `processed_events` SQLite table to see if the event ID has already been indexed.
3. **Reorg Handling**:
- If the RPC returns an event with a ledger number *lower* than the last processed ledger cursor, the system flags a blockchain reorganization.
- It sets `is_reorg_duplicate = true` on the event.
- The event is stored in SQLite for integrity, but the pipeline **skips sending Discord alerts or notifications** to prevent duplicate spam.
4. **In-Memory Cache (LRU)**: A secondary fast-path `NotificationDeduplicator` stores the last 60 seconds of event hashes in memory to prevent database roundtrips for duplicate frames.
5. **Persistence**: The event is formatted and saved to the `events` table. The `polling_cursors` table is updated with the new ledger index.
6. **Dispatch**: The [NotificationDispatcher](file:///workspaces/Notify-Chain/listener/src/services/notification-dispatcher.ts) formats the event and pushes it to active channels (e.g. Discord webhook).
6. **Dispatch**: The [NotificationDispatcher](listener/src/services/notification-dispatcher.ts) formats the event and pushes it to active channels (e.g. Discord webhook).

---

Expand Down Expand Up @@ -206,19 +206,19 @@ Because SQLite executes writes sequentially and locks the database, only one wor
Here are the critical paths and files that implement the core functionality of NotifyChain:

### 5.1 Smart Contracts
- [contract/contracts/hello-world/src/lib.rs](file:///workspaces/Notify-Chain/contract/contracts/hello-world/src/lib.rs): Entry point for the AutoShare contract. Declares the functions and maps calls to the logic module.
- [autoshare_logic.rs](file:///workspaces/Notify-Chain/contract/contracts/hello-world/src/autoshare_logic.rs): Core business logic for AutoShare groups, members, subscriptions, withdrawals, and scheduled notification parameters.
- [base/events.rs](file:///workspaces/Notify-Chain/contract/contracts/hello-world/src/base/events.rs): Structure definitions for category-priority routed events.
- [Documents/Task Bounty/src/lib.rs](file:///workspaces/Notify-Chain/Documents/Task%20Bounty/src/lib.rs): Entry point for the TaskBounty contract.
- [Documents/Task Bounty/src/events.rs](file:///workspaces/Notify-Chain/Documents/Task%20Bounty/src/events.rs): Emits the unstructured subject-action events for tasks, submissions, and disputes.
- [contract/contracts/hello-world/src/lib.rs](contract/contracts/hello-world/src/lib.rs): Entry point for the AutoShare contract. Declares the functions and maps calls to the logic module.
- [autoshare_logic.rs](contract/contracts/hello-world/src/autoshare_logic.rs): Core business logic for AutoShare groups, members, subscriptions, withdrawals, and scheduled notification parameters.
- [base/events.rs](contract/contracts/hello-world/src/base/events.rs): Structure definitions for category-priority routed events.
- [Documents/Task Bounty/src/lib.rs](Documents/Task%20Bounty/src/lib.rs): Entry point for the TaskBounty contract.
- [Documents/Task Bounty/src/events.rs](Documents/Task%20Bounty/src/events.rs): Emits the unstructured subject-action events for tasks, submissions, and disputes.

### 5.2 Off-Chain Listener Service
- [listener/src/index.ts](file:///workspaces/Notify-Chain/listener/src/index.ts): Initializer script. Bootstraps the HTTP API server, SQLite store, subscriber, and scheduler loops.
- [listener/src/services/event-subscriber.ts](file:///workspaces/Notify-Chain/listener/src/services/event-subscriber.ts): Polls Stellar RPC logs and drives the ingestion loop.
- [listener/src/services/event-deduplication-service.ts](file:///workspaces/Notify-Chain/listener/src/services/event-deduplication-service.ts): SQLite-backed deduplication layer; houses reorg-detection safeguards.
- [listener/src/services/notification-scheduler.ts](file:///workspaces/Notify-Chain/listener/src/services/notification-scheduler.ts): Periodically queries SQLite for due scheduled notifications, acquires locks, dispatches alerts, and performs recovery.
- [listener/src/store/](file:///workspaces/Notify-Chain/listener/src/store/): Holds the repositories (`EventRepository`, `ScheduleRepository`) managing queries to SQLite.
- [listener/src/index.ts](listener/src/index.ts): Initializer script. Bootstraps the HTTP API server, SQLite store, subscriber, and scheduler loops.
- [listener/src/services/event-subscriber.ts](listener/src/services/event-subscriber.ts): Polls Stellar RPC logs and drives the ingestion loop.
- [listener/src/services/event-deduplication-service.ts](listener/src/services/event-deduplication-service.ts): SQLite-backed deduplication layer; houses reorg-detection safeguards.
- [listener/src/services/notification-scheduler.ts](listener/src/services/notification-scheduler.ts): Periodically queries SQLite for due scheduled notifications, acquires locks, dispatches alerts, and performs recovery.
- [listener/src/store/](listener/src/store/): Holds the repositories (`EventRepository`, `ScheduleRepository`) managing queries to SQLite.

### 5.3 Frontend Dashboard
- [dashboard/src/pages/](file:///workspaces/Notify-Chain/dashboard/src/pages/): Contains top-level dashboard pages: `Events` (real-time stream), `Schedules` (notification queue stats), and `Stats` (overview charts).
- [dashboard/src/hooks/](file:///workspaces/Notify-Chain/dashboard/src/hooks/): React hooks for fetching event feeds, managing poll intervals, and querying status counts from the listener.
- [dashboard/src/pages/](dashboard/src/pages/): Contains top-level dashboard pages: `Events` (real-time stream), `Schedules` (notification queue stats), and `Stats` (overview charts).
- [dashboard/src/hooks/](dashboard/src/hooks/): React hooks for fetching event feeds, managing poll intervals, and querying status counts from the listener.
2 changes: 1 addition & 1 deletion CONTRIBUTOR_DEVELOPMENT_WORKFLOW_GUIDE.md
Original file line number Diff line number Diff line change
Expand Up @@ -21,7 +21,7 @@ A single, end-to-end workflow for local setup, branching, testing, and submittin
- Rust (stable) with WebAssembly target:
- `rustup target add wasm32-unknown-unknown`
- Stellar CLI:
- `cargo install stellar-cli`
- `cargo install --locked stellar-cli --features opt`
- Node.js:
- Listener uses **Node 20**
- Dashboard uses **Node 18**
Expand Down
33 changes: 33 additions & 0 deletions CONTRIBUTOR_SETUP.md
Original file line number Diff line number Diff line change
Expand Up @@ -2,6 +2,14 @@

> **Canonical setup guide:** [`docs/ENVIRONMENT_SETUP.md`](docs/ENVIRONMENT_SETUP.md)

This guide walks you through setting up a local development environment for
NotifyChain. By the end, you will have the listener service, the dashboard,
the frontend analytics app, and the smart contracts building and running on
your machine.

For the canonical contribution workflow, start with
[`CONTRIBUTOR_DEVELOPMENT_WORKFLOW_GUIDE.md`](CONTRIBUTOR_DEVELOPMENT_WORKFLOW_GUIDE.md).
For a shorter setup path, see [`LOCAL_DEVELOPMENT.md`](LOCAL_DEVELOPMENT.md).
That document contains step-by-step instructions to install required tools,
clone the repository, configure the listener and dashboard, build contracts, and
verify your installation (including CI-parity checks).
Expand All @@ -19,6 +27,13 @@ For Git workflow (fork, branch, PR), see
2. [Clone the Repository](#2-clone-the-repository)
3. [Listener Service Setup](#3-listener-service-setup)
4. [Dashboard Setup](#4-dashboard-setup)
5. [Frontend (Next.js Analytics) Setup](#5-frontend-nextjs-analytics-setup)
6. [Smart Contracts Setup](#6-smart-contracts-setup)
7. [Environment Variables Reference](#7-environment-variables-reference)
8. [Full-Stack Verification Checklist](#8-full-stack-verification-checklist)
9. [Running Tests](#9-running-tests)
10. [VS Code Setup (Recommended)](#10-vs-code-setup-recommended)
11. [Troubleshooting & FAQ](#11-troubleshooting--faq)
5. [Smart Contracts Setup](#5-smart-contracts-setup)
6. [Environment Variables Reference](#6-environment-variables-reference)
7. [Running Tests](#7-running-tests)
Expand All @@ -37,6 +52,14 @@ For Git workflow (fork, branch, PR), see
| Node.js | **22** | [nodejs.org](https://nodejs.org) or `nvm` | Listener, Dashboard |
| Git | — | your package manager | Version control |

| Dependency | Minimum Version | Install Method | Used By |
|----------------|-----------------|-----------------------------------------|--------------------|
| Rust | stable | [rustup.rs](https://rustup.rs) | Smart contracts |
| `wasm32-unknown-unknown` | — | `rustup target add wasm32-unknown-unknown` | Soroban contracts |
| Stellar CLI | latest | `cargo install --locked stellar-cli --features opt` | Contract build/deploy |
| Node.js | **18** (dashboard), **20** (listener) | [nodejs.org](https://nodejs.org) or `nvm` | Listener, Dashboard |
| npm | comes with Node | — | Package management |
| Git | — | Your package manager or [git-scm.com](https://git-scm.com) | Version control |
### Platform notes

- **macOS**: Install Xcode Command Line Tools first: `xcode-select --install`
Expand Down Expand Up @@ -98,6 +121,8 @@ docker compose restart listener # restart one service after env change
Edit `.env` at the repo root, then:

```bash
git clone https://github.com/Core-Foundry/Notify-Chain.git
cd Notify-Chain
docker compose restart listener # for most listener settings
docker compose up --build dashboard # required if VITE_* vars changed (baked in at build time)
```
Expand Down Expand Up @@ -544,6 +569,14 @@ docker compose up --build # fresh start, migrations run automatically

### Still stuck?

1. Search [open issues](https://github.com/Core-Foundry/Notify-Chain/issues) — your problem may already be reported.
1. Search [open issues](https://github.com/Core-Foundry/Notify-Chain/issues) — your problem may already be reported.
2. Read the detailed [Troubleshooting Guide](TROUBLESHOOTING.md).
3. Open a new issue with:
- Your OS and version
- Output of `rustc --version`, `node --version`, `stellar --version`
- The full error message and stack trace
- Steps you have already tried
1. Search [open issues](https://github.com/Core-Foundry/Notify-Chain/issues).
2. Open a new issue with: your OS, output of `rustc --version && node --version && stellar --version`, the full error and stack trace, and steps already tried.

Expand Down
12 changes: 6 additions & 6 deletions CREATE_PR_INSTRUCTIONS.md
Original file line number Diff line number Diff line change
Expand Up @@ -21,7 +21,7 @@ You now have a complete, working notification template preview feature ready to

1. **Go to your fork on GitHub:**
```
https://github.com/coderolisa/Notify-Chain
https://github.com/Core-Foundry/Notify-Chain
```

2. **You should see a yellow banner** saying:
Expand Down Expand Up @@ -122,7 +122,7 @@ gh pr create \

Click this link (replace YOUR_USERNAME):
```
https://github.com/coderolisa/Notify-Chain/pull/new/feature/notification-template-preview
https://github.com/Core-Foundry/Notify-Chain/pull/new/feature/notification-template-preview
```

## 📝 PR Checklist
Expand Down Expand Up @@ -279,15 +279,15 @@ If you encounter any issues:

### Branch Info
```
Repository: https://github.com/coderolisa/Notify-Chain
Repository: https://github.com/Core-Foundry/Notify-Chain
Branch: feature/notification-template-preview
Status: ✅ Ready for PR
```

### Key URLs
- Your Fork: `https://github.com/coderolisa/Notify-Chain`
- Create PR: `https://github.com/coderolisa/Notify-Chain/pull/new/feature/notification-template-preview`
- Branch: `https://github.com/coderolisa/Notify-Chain/tree/feature/notification-template-preview`
- Your Fork: `https://github.com/Core-Foundry/Notify-Chain`
- Create PR: `https://github.com/Core-Foundry/Notify-Chain/pull/new/feature/notification-template-preview`
- Branch: `https://github.com/Core-Foundry/Notify-Chain/tree/feature/notification-template-preview`

## ✨ You're All Set!

Expand Down
Loading
Loading