{"id":15002606,"url":"https://github.com/jihadkhawaja/egroo","last_synced_at":"2026-03-14T23:03:20.086Z","repository":{"id":40594744,"uuid":"376017572","full_name":"jihadkhawaja/Egroo","owner":"jihadkhawaja","description":"Cross-platform chat app created with MAUI (Hybrid), Blazor Auto and ASP.NET (SignalR) ","archived":false,"fork":false,"pushed_at":"2024-11-15T20:36:52.000Z","size":3936,"stargazers_count":165,"open_issues_count":15,"forks_count":29,"subscribers_count":8,"default_branch":"main","last_synced_at":"2024-12-17T15:19:39.138Z","etag":null,"topics":["asp-net","blazor","blazor-webassembly","chat-application","csharp","docker","dotnet","maui","mssql","mudblazor","postgresql","signalr","wasm"],"latest_commit_sha":null,"homepage":"https://egroo.org","language":"C#","has_issues":true,"has_wiki":null,"has_pages":null,"mirror_url":null,"source_name":null,"license":"mit","status":null,"scm":"git","pull_requests_enabled":true,"icon_url":"https://github.com/jihadkhawaja.png","metadata":{"files":{"readme":"README.md","changelog":null,"contributing":"docs/CONTRIBUTING.md","funding":null,"license":"LICENSE","code_of_conduct":"docs/CODE_OF_CONDUCT.md","threat_model":null,"audit":null,"citation":null,"codeowners":null,"security":null,"support":null,"governance":null,"roadmap":null,"authors":null,"dei":null,"publiccode":null,"codemeta":null},"funding":{"github":null,"patreon":null,"open_collective":null,"ko_fi":null,"tidelift":null,"community_bridge":null,"liberapay":null,"issuehunt":null,"otechie":null,"lfx_crowdfunding":null,"custom":["buymeacoffee.com/jihadkhawaja"]}},"created_at":"2021-06-11T12:26:45.000Z","updated_at":"2024-12-14T16:47:18.000Z","dependencies_parsed_at":"2023-08-13T14:39:16.155Z","dependency_job_id":"39e3604b-2044-45c3-9fac-8eb36f3ecf06","html_url":"https://github.com/jihadkhawaja/Egroo","commit_stats":{"total_commits":595,"total_committers":4,"mean_commits":148.75,"dds":0.5294117647058824,"last_synced_commit":"e6d5f6203fec7ec7d84e49c816f9a6fc60a5d495"},"previous_names":["jihadkhawaja/egroo","jihadkhawaja/mobilechat"],"tags_count":42,"template":false,"template_full_name":null,"repository_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/jihadkhawaja%2FEgroo","tags_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/jihadkhawaja%2FEgroo/tags","releases_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/jihadkhawaja%2FEgroo/releases","manifests_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/jihadkhawaja%2FEgroo/manifests","owner_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners/jihadkhawaja","download_url":"https://codeload.github.com/jihadkhawaja/Egroo/tar.gz/refs/heads/main","host":{"name":"GitHub","url":"https://github.com","kind":"github","repositories_count":247801169,"owners_count":20998339,"icon_url":"https://github.com/github.png","version":null,"created_at":"2022-05-30T11:31:42.601Z","updated_at":"2022-07-04T15:15:14.044Z","host_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub","repositories_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories","repository_names_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repository_names","owners_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners"}},"keywords":["asp-net","blazor","blazor-webassembly","chat-application","csharp","docker","dotnet","maui","mssql","mudblazor","postgresql","signalr","wasm"],"created_at":"2024-09-24T18:51:27.192Z","updated_at":"2026-03-14T23:03:20.080Z","avatar_url":"https://github.com/jihadkhawaja.png","language":"C#","funding_links":["buymeacoffee.com/jihadkhawaja"],"categories":[],"sub_categories":[],"readme":"﻿# [Egroo](https://www.egroo.org/)\n\n\u003cimg src=\"https://raw.githubusercontent.com/jihadkhawaja/Egroo/refs/heads/main/docs/icon.png\" alt=\"Egroo Icon\" width=\"128\"/\u003e\n\nEgroo is a self-hosted real-time chat platform built with Blazor, ASP.NET Core, SignalR, and PostgreSQL. It is designed for teams that want modern chat, voice, end-to-end encrypted messaging, and AI-assisted collaboration without giving up control of their infrastructure or data.\n\nIt combines a Blazor web experience, a SignalR-first real-time backend, per-recipient end-to-end encrypted messaging with ephemeral delivery, channel voice calls over WebRTC, and optional AI agents that can participate in conversations when mentioned.\n\n## Build Status\n\n[![NuGets Push](https://github.com/jihadkhawaja/Egroo/actions/workflows/Nuget.yml/badge.svg)](https://github.com/jihadkhawaja/Egroo/actions/workflows/Nuget.yml)\n[![Coverage %](https://raw.githubusercontent.com/jihadkhawaja/Egroo/main/docs/badges/coverage.svg)](https://github.com/jihadkhawaja/Egroo/actions/workflows/MSTest.yml)\n[![Egroo Deploy](https://github.com/jihadkhawaja/Egroo/actions/workflows/deploy-egroo.yml/badge.svg)](https://github.com/jihadkhawaja/Egroo/actions/workflows/deploy-egroo.yml)\n[![CodeQL](https://github.com/jihadkhawaja/Egroo/actions/workflows/github-code-scanning/codeql/badge.svg)](https://github.com/jihadkhawaja/Egroo/actions/workflows/github-code-scanning/codeql)\n\n## Why Egroo\n\n- Self-hosted architecture with PostgreSQL storage and no third-party message relay.\n- Blazor Auto rendering for fast first load with WebAssembly after hydration.\n- SignalR-based real-time messaging and presence.\n- End-to-end encrypted messaging with per-recipient payloads.\n- Ephemeral encrypted message delivery for stronger privacy.\n- WebRTC channel voice calls.\n- AI agents that can be created, published, added to channels, and triggered with mentions.\n\n## Core Capabilities\n\n| Capability | What it means |\n|---|---|\n| Real-time chat | Fast message delivery over SignalR WebSockets |\n| End-to-end encrypted messaging | Per-recipient payloads are encrypted with recipient public keys and decrypted on the receiving device |\n| Privacy-first delivery | Message metadata is stored separately and encrypted pending content is removed after recipients acknowledge delivery |\n| Voice channels | Peer-to-peer channel audio using WebRTC signaling through the hub |\n| Blazor UI | Shared Razor components across server and WebAssembly experiences |\n| AI agents | User-owned agents powered by OpenAI, Azure OpenAI, Anthropic, or Ollama |\n| Self-hosting | Full control over deployment, configuration, and data |\n\n## System Overview\n\nAt a high level, Egroo separates the web host, the API server, shared UI libraries, chat libraries, and database storage.\n\n```mermaid\nflowchart TD\n  Browser[\"Browser / PWA\"]\n  Db[(\"PostgreSQL\")]\n\n  subgraph PresentationLayer[\"Presentation Layer\"]\n    direction TB\n    Host[\"Egroo Host\"]\n    UI[\"Egroo.UI\"]\n    Client[\"Egroo.Client\"]\n  end\n\n  subgraph ClientServicesLayer[\"Client Services Layer\"]\n    direction TB\n    ChatClient[\"jihadkhawaja.chat.client\"]\n  end\n\n  subgraph ServerLayer[\"Server Layer\"]\n    direction TB\n    Api[\"Egroo.Server\"]\n    ChatServer[\"jihadkhawaja.chat.server\"]\n  end\n\n  subgraph SharedLayer[\"Shared Contracts Layer\"]\n    direction TB\n    Shared[\"jihadkhawaja.chat.shared\"]\n  end\n\n  Browser --\u003e PresentationLayer\n  Browser --\u003e ServerLayer\n  PresentationLayer --\u003e ClientServicesLayer\n  ClientServicesLayer --\u003e SharedLayer\n  ServerLayer --\u003e SharedLayer\n  ServerLayer --\u003e Db\n```\n\n## Solution Structure\n\nThe solution in `src/` is split by responsibility so the UI, transport layer, shared contracts, and server implementation remain independent.\n\n```mermaid\nflowchart LR\n  subgraph AppLayer[\"App Layer\"]\n    direction TB\n    EgrooHost[\"Egroo/Egroo\"]\n    EgrooClient[\"Egroo.Client\"]\n  end\n\n  subgraph UiLayer[\"UI Layer\"]\n    direction TB\n    UiProject[\"Egroo.UI\"]\n  end\n\n  subgraph ClientLayer[\"Client Transport Layer\"]\n    direction TB\n    ClientProject[\"jihadkhawaja.chat.client\"]\n  end\n\n  subgraph SharedLayer[\"Shared Contracts Layer\"]\n    direction TB\n    SharedProject[\"jihadkhawaja.chat.shared\"]\n  end\n\n  subgraph ServerLayer[\"Server Layer\"]\n    direction TB\n    ServerProject[\"Egroo.Server\"]\n    ChatServerProject[\"jihadkhawaja.chat.server\"]\n  end\n\n  subgraph TestLayer[\"Test Layer\"]\n    direction TB\n    TestProject[\"Egroo.Server.Test\"]\n  end\n\n  AppLayer --\u003e UiLayer\n  UiLayer --\u003e ClientLayer\n  ClientLayer --\u003e SharedLayer\n  ServerLayer --\u003e SharedLayer\n  TestLayer --\u003e ServerLayer\n```\n\n| Project | Purpose |\n|---|---|\n| `src/Egroo/Egroo` | Blazor host application that serves the web app and coordinates SSR to WASM rendering |\n| `src/Egroo/Egroo.Client` | Client-side WebAssembly project |\n| `src/Egroo.UI` | Shared Razor component library used by both hosting modes |\n| `src/Egroo.Server` | ASP.NET Core backend with Minimal APIs, SignalR, repositories, EF Core, and PostgreSQL |\n| `src/jihadkhawaja.chat.client` | Client services that wrap auth, channel, message, and call interactions |\n| `src/jihadkhawaja.chat.server` | SignalR hub implementation and connection tracking |\n| `src/jihadkhawaja.chat.shared` | Shared DTOs, models, and interfaces |\n| `src/Egroo.Server.Test` | MSTest coverage for server behavior |\n\n## How Messaging Works\n\nOne of Egroo's core design choices is that message content is not kept permanently in the main message record. The server stores metadata, carries per-recipient encrypted payloads, and removes pending encrypted content after acknowledgment.\n\n```mermaid\nsequenceDiagram\n  actor User\n  participant UI as Egroo.UI\n  participant Client as chat.client\n  participant Hub as ChatHub\n  participant Repo as Server Repository\n  participant Recipient as Recipient Client\n\n  User-\u003e\u003eUI: Send message\n  UI-\u003e\u003eClient: SendMessage(message)\n  Client-\u003e\u003eHub: SignalR invocation\n  Hub-\u003e\u003eRepo: Save metadata\n  Hub-\u003e\u003eRepo: Encrypt and store pending content\n  Hub--\u003e\u003eRecipient: ReceiveMessage(message)\n  Recipient--\u003e\u003eHub: UpdatePendingMessage(messageId)\n  Hub-\u003e\u003eRepo: Delete pending content\n```\n\n## How End-To-End Encryption Works\n\nEgroo encrypts message payloads for each recipient using published public keys. The server relays and temporarily stores ciphertext, while recipients decrypt on their own device with the matching private key.\n\n```mermaid\nsequenceDiagram\n  actor Sender as Sender Device\n  participant UI as Egroo.UI\n  participant Hub as ChatHub\n  participant Store as Pending Storage\n  actor Recipient as Recipient Device\n\n  Sender-\u003e\u003eUI: Load recipient public keys\n  UI-\u003e\u003eUI: Encrypt payload for each recipient\n  UI-\u003e\u003eHub: Send metadata + encrypted payloads\n  Hub-\u003e\u003eStore: Store ciphertext until delivery\n  Hub--\u003e\u003eRecipient: Relay encrypted payload\n  Recipient-\u003e\u003eRecipient: Decrypt with local private key\n\n  Note over Hub,Store: Server handles ciphertext and delivery state\n```\n\n## How Voice Channel Calls Work\n\nVoice calls in channels use a WebRTC mesh network. SignalR manages membership and relays WebRTC signaling, while the audio stream stays peer-to-peer between participants.\n\n```mermaid\nsequenceDiagram\n  actor A as Participant A\n  participant Hub as SignalR Hub\n  actor B as Participant B\n\n  A-\u003e\u003eHub: JoinChannelCall(channelId)\n  Hub--\u003e\u003eA: ChannelCallParticipantsChanged([A])\n\n  B-\u003e\u003eHub: JoinChannelCall(channelId)\n  Hub--\u003e\u003eA: ChannelCallParticipantsChanged([A, B])\n  Hub--\u003e\u003eB: ChannelCallParticipantsChanged([A, B])\n\n  Note over B: New participant creates WebRTC offers for existing members\n  B-\u003e\u003eHub: SendOfferToUser(A, offerSdp)\n  Hub--\u003e\u003eA: ReceiveOffer(B, offerSdp)\n\n  A-\u003e\u003eHub: SendAnswerToUser(B, answerSdp)\n  Hub--\u003e\u003eB: ReceiveAnswer(A, answerSdp)\n\n  Note over A,B: ICE candidates are exchanged through the hub\n  B-\u003e\u003eHub: SendIceCandidateToUser(A, candidate)\n  Hub--\u003e\u003eA: ReceiveIceCandidate(B, candidate)\n\n  Note over A,B: Peer-to-peer encrypted audio stream established\n```\n\n## AI Agents in Channels\n\nEgroo supports personal AI agents that can be attached to channels and respond when mentioned. Agents can use supported LLM providers and participate as first-class actors in the chat experience.\n\n```mermaid\nsequenceDiagram\n  actor User\n  participant Hub as ChatHub\n  participant AgentService as AgentChannelService\n  participant LLM as LLM Provider\n  participant Channel as Channel Members\n\n  User-\u003e\u003eHub: Send @AgentName message\n  Hub-\u003e\u003eAgentService: Detect mention and load context\n  AgentService-\u003e\u003eLLM: Generate reply\n  LLM--\u003e\u003eAgentService: Response text\n  AgentService--\u003e\u003eChannel: Broadcast agent reply\n```\n\n## Where To Start\n\nThe README is the entry point. The wiki is where installation, deployment, and deeper technical details live.\n\n| If you want to... | Go here |\n|---|---|\n| Get the app running quickly | [Getting Started](https://github.com/jihadkhawaja/Egroo/wiki/Getting-Started) |\n| Install with more detail | [Installation Guide](https://github.com/jihadkhawaja/Egroo/wiki/Installation) |\n| Configure database, JWT, encryption, and CORS | [Configuration](https://github.com/jihadkhawaja/Egroo/wiki/Configuration) |\n| Set up a contributor workstation | [Development Setup](https://github.com/jihadkhawaja/Egroo/wiki/Development-Setup) |\n| Deploy to production | [Deployment Guide](https://github.com/jihadkhawaja/Egroo/wiki/Deployment) |\n| Understand the backend and runtime design | [Architecture Overview](https://github.com/jihadkhawaja/Egroo/wiki/Architecture) |\n| Explore API and SignalR surface area | [API Documentation](https://github.com/jihadkhawaja/Egroo/wiki/API-Documentation) |\n| Debug common setup issues | [Troubleshooting](https://github.com/jihadkhawaja/Egroo/wiki/Troubleshooting) |\n\n## Local Development At A Glance\n\nFor contributors, the normal loop is:\n\n1. Install .NET 10 and PostgreSQL.\n2. Configure `src/Egroo.Server/appsettings.Development.json` with your database, JWT secret, and encryption values.\n3. Start the API from `src/Egroo.Server`.\n4. Start the web host from `src/Egroo/Egroo`.\n5. Run tests from `src/Egroo.Server.Test` or the solution root.\n\nCommon commands:\n\n```bash\ndotnet build src/Egroo.slnx --configuration Debug\ndotnet test src/Egroo.Server.Test/Egroo.Server.Test.csproj --verbosity normal\ndotnet watch --project src/Egroo.Server/Egroo.Server.csproj\ndotnet watch --project src/Egroo/Egroo/Egroo.csproj\n```\n\nFor full environment setup, use the [Development Setup](https://github.com/jihadkhawaja/Egroo/wiki/Development-Setup) guide.\n\n## Contributing\n\nContributions should be small, reviewable, and aligned with the existing architecture.\n\nBefore opening a pull request:\n\n1. Read the [Contributing Guide](https://github.com/jihadkhawaja/Egroo/blob/main/docs/CONTRIBUTING.md).\n2. Check the [Code of Conduct](https://github.com/jihadkhawaja/Egroo/blob/main/docs/CODE_OF_CONDUCT.md).\n3. Discuss larger changes through an issue first.\n4. Keep documentation updated when behavior or setup changes.\n5. Run tests before submitting your branch.\n\n## Community\n\n- GitHub issues: [Report bugs or request features](https://github.com/jihadkhawaja/Egroo/issues)\n- Discord: [Join the community server](https://discord.gg/9KMAM2RKVC)\n\n## License\n\nEgroo is licensed under the [Apache License 2.0](https://github.com/jihadkhawaja/Egroo/blob/main/LICENSE).\n","project_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Fjihadkhawaja%2Fegroo","html_url":"https://awesome.ecosyste.ms/projects/github.com%2Fjihadkhawaja%2Fegroo","lists_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Fjihadkhawaja%2Fegroo/lists"}