---
# System prepended metadata

title: LedgerVest System Architecture

---

[C4 Model](https://c4model.com/) for visualising software architecture:


1. System Context Diagram

```mermaid
flowchart TD
    User([Investor / Fundseeker])
    Admin([Admin])
    Google([Google OAuth Provider])
    LedgerVest["LedgerVest Investment Platform"]
    Ethereum([Ethereum Blockchain])

    User -->|"Initiates login through Google OAuth"| Google
    Google -->|"Returns token; "Users creates & invests in campaigns""| LedgerVest

    Admin -->|"Monitors platform and manages system"| LedgerVest

    LedgerVest -->|"Deploys/interacts with smart contracts"| Ethereum

    class LedgerVest system
    class User,Admin,Google,Ethereum external
```

2. Container Diagram

```mermaid
flowchart TD
  User([Investor, Fundseeker])
  Admin([Admin])
  Google([Google OAuth Provider])
  Ethereum([Ethereum Blockchain])

  subgraph LedgerVest["LedgerVest Platform"]
    WebApp["Web Application [Next.js + React]"]
    APIService["API Service [Next.js API Routes]"]
    LoggingService["Logging Service [Node.js]"]
    BlockchainService["Blockchain Service [ethers.js]"]
    AdminDashboard["Admin Dashboard [Next.js + React]"]

    WebApp -->|API calls| APIService
    APIService -->|Logging events for security & moitoring i.e. what actually happened| LoggingService
    APIService -->|Blockchain operations| BlockchainService
    WebApp -->|Frontend logs i.e. what the user tried to do| LoggingService
    AdminDashboard -->|API calls| APIService
    AdminDashboard -->|View logs| LoggingService
  end

  Database[(PostgreSQL Database)]
  SmartContracts["Smart Contracts [Solidity]"]

  User -->|Redirect to| Google
  Google -->|Redirect back with token| WebApp
  Admin -->|Access| AdminDashboard
  
  BlockchainService -->|Deploy/interact| SmartContracts
  SmartContracts -->|Deployed on| Ethereum
  APIService -->|Store/retrieve data i.e. main data storage| Database
  LoggingService -->|Store logs| Database
```

3. Component Diagram

```mermaid
flowchart TD
 subgraph FrontendContainer["Frontend Container"]
        NextApp["Next.js Application"]
        ReactComponents["React Components"]
        WalletContext["Wallet Context"]
  end
 subgraph APIContainer["API Container"]
        APIRoutes["Next.js API Routes"]
  end
 subgraph LoggingContainer["Logging Container"]
        LoggerService["Logger Service"]
        LogAPI["Logging API"]
  end
 subgraph BlockchainContainer["Blockchain Container"]
        EthersService["ethers.js Service"]
        ContractAPI["Smart Contract API"]
  end
 subgraph AdminContainer["Admin Container"]
        AdminDashboard["Admin Dashboard"]
        LogViewer["Log Viewer"]
  end
 subgraph LedgerVest["LedgerVest Platform"]
        FrontendContainer
        APIContainer
        LoggingContainer
        BlockchainContainer
        AdminContainer
  end
 subgraph SmartContractsContainer["Smart Contracts"]
        CampaignFactory["Campaign Factory Contract"]
        Campaign["Campaign Contract"]
  end
    NextApp -- Renders --> ReactComponents
    ReactComponents -- Uses --> WalletContext
    LoggerService -- Stores to --> LogAPI
    EthersService -- Interacts with --> ContractAPI
    ContractAPI -- Forwards events to --> LoggerService
    AdminDashboard -- Displays --> LogViewer
    FrontendContainer -- Makes requests to --> APIContainer
    APIContainer -- Logs events to --> LoggingContainer
    APIContainer -- Uses --> BlockchainContainer
    AdminContainer -- Accesses --> APIContainer
    AdminContainer -- Views logs from --> LoggingContainer
    CampaignFactory -- Creates --> Campaign
    User(["Investor, Fundseeker"]) -- Interacts with --> FrontendContainer
    User <-- Authenticates via --> OAuth(["OAuth Provider"])
    OAuth -- Provides token to --> FrontendContainer
    Admin(["Admin"]) -- Manages via --> AdminContainer
    APIContainer -- Stores/retrieves data --> PostgreSQL[("PostgreSQL Database")]
    LoggingContainer -- Stores logs --> PostgreSQL
    BlockchainContainer -- Deploys/interacts --> SmartContractsContainer
    SmartContractsContainer -- Deployed on --> Ethereum(["Ethereum Blockchain"])
    APIContainer --> LedgerVest
```

4. Code Diagram:

    i. Dual Login (Metamask + Google)
    
```mermaid
flowchart TD
  User([User: Investor / Fundseeker])
  Wallet[MetaMask Wallet]
  OAuthBtn["OAuthLoginButton.tsx"]
  GoogleOAuth["Google Auth Page"]
  OAuthAPI["/api/oauth/google"]
  OAuthCallback["/api/oauth/callback"]
  GoogleOAuthHandler["GoogleOAuthHandler.ts"]
  PrismaUser["prisma.user.upsert()"]
  LinkWallet["/api/oauth/link-wallet"]
  Logger["Logger (logAuth)"]
  DB[(PostgreSQL)]

  %% Flow: Google OAuth
  User -->|Click Sign in with Google| OAuthBtn
  OAuthBtn --> OAuthAPI
  OAuthAPI -->|Generate URL + Log| GoogleOAuthHandler
  OAuthAPI --> GoogleOAuth
  GoogleOAuth --> OAuthCallback
  OAuthCallback -->|Get Token + User Info| GoogleOAuthHandler
  OAuthCallback --> Logger
  PrismaUser --> DB
  Logger --> DB

  %% Flow: Wallet Connect
  User -->|Connect Wallet| Wallet
  Wallet -->|Returns Address| LinkWallet
  LinkWallet -->|Link to User| GoogleOAuthHandler
  LinkWallet --> Logger
  GoogleOAuthHandler --> PrismaUser
```    

ii) Campaigns

```mermaid
flowchart TD
  %% Users and Wallet
  User(["User (Authenticated via Google + MetaMask)"])
  Wallet[MetaMask Wallet]
  Ethereum["Ethereum Blockchain (Sepolia)"]
  DB[(PostgreSQL)]

  %% Contract Interfaces
  Ethers["ethers.js"]
  ABIs["Campaign.json ABI"]
  ContractAddr["contract-address.json"]

  %% Campaign Creation
  CreateCampaign["CreateCampaignForm.tsx"]
  CampaignFactory["CampaignFactory.createCampaign()"]
  CampaignAPI["/api/campaigns"]
  
  %% Invest in Campaign
  CampaignPage["CampaignDetailsPage.tsx"]
  ContributeBtn["ContributeButton.tsx"]
  CampaignContribute["Campaign.contribute()"]
  ContributionAPI["/api/contributions"]

  %% Create Spending Request (Campaign Owner)
  CreateRequestBtn["CreateRequestButton.tsx"]
  CampaignCreateReq["Campaign.createRequest()"]
  RequestAPI["/api/requests"]

  %% Vote on Request (Investor)
  ApproveBtn["ApproveButton.tsx"]
  CampaignVote["Campaign.approveRequest()"]
  VoteAPI["/api/votes"]

  %% Finalize Request (Campaign Owner)
  FinalizeBtn["FinalizeButton.tsx"]
  CampaignFinalize["Campaign.finalizeRequest()"]
  FinalizationAPI["/api/finalizations"]

  %% Logging
  Logger["Logger (logEvent)"]

  %% Campaign Creation Flow
  User -->|Fills & submits| CreateCampaign
  CreateCampaign -->|Send tx via ethers.js| Wallet
  Wallet --> Ethers
  Ethers --> ABIs
  Ethers --> ContractAddr
  Ethers --> CampaignFactory
  CampaignFactory --> Ethereum
  CreateCampaign --> CampaignAPI
  CampaignAPI --> DB
  CampaignAPI --> Logger

  %% Contribution Flow
  User -->|Browse & select| CampaignPage
  CampaignPage --> ContributeBtn
  ContributeBtn -->|"Send ETH via contribute()"| CampaignContribute
  CampaignContribute --> Ethereum
  ContributeBtn --> ContributionAPI
  ContributionAPI --> DB
  ContributionAPI --> Logger

  %% Create Request Flow (Only Owner)
  User --> CreateRequestBtn
  CreateRequestBtn -->|Create request on-chain| CampaignCreateReq
  CampaignCreateReq --> Ethereum
  CreateRequestBtn --> RequestAPI
  RequestAPI --> DB
  RequestAPI --> Logger

  %% Vote on Request (Investor)
  User --> ApproveBtn
  ApproveBtn -->|"vote via approveRequest()"| CampaignVote
  CampaignVote --> Ethereum
  ApproveBtn --> VoteAPI
  VoteAPI --> DB
  VoteAPI --> Logger

  %% Finalize Request (Owner)
  User --> FinalizeBtn
  FinalizeBtn -->|"execute finalizeRequest()"| CampaignFinalize
  CampaignFinalize --> Ethereum
  FinalizeBtn --> FinalizationAPI
  FinalizationAPI --> DB
  FinalizationAPI --> Logger
```


iii) Finalize Request 

```mermaid
flowchart TD
  User([User])
  FinalizeBtn["FinalizeButton.tsx"]
  CampaignSC["Campaign.finalizeRequest()"]
  Ethereum["Ethereum (Sepolia Testnet)"]
  FinalizationAPI["/api/finalizations"]
  PrismaFinalize["prisma.finalization.create()"]
  Logger["Logger (logEvent)"]
  DB[(PostgreSQL)]

  User -->|Clicks Finalize| FinalizeBtn
  FinalizeBtn -->|Smart Contract Call| CampaignSC
  CampaignSC --> Ethereum
  FinalizeBtn --> FinalizationAPI
  FinalizationAPI --> PrismaFinalize
  FinalizationAPI --> Logger
  PrismaFinalize --> DB
  Logger --> DB
```