{"id":25831432,"url":"https://github.com/sfmohassel/libc.eventbus","last_synced_at":"2026-03-08T19:36:43.393Z","repository":{"id":55151083,"uuid":"238201522","full_name":"sfmohassel/libc.eventbus","owner":"sfmohassel","description":"An in-memory event bus without any dependency in C#","archived":false,"fork":false,"pushed_at":"2024-12-03T08:49:55.000Z","size":90,"stargazers_count":10,"open_issues_count":0,"forks_count":7,"subscribers_count":2,"default_branch":"master","last_synced_at":"2024-12-03T09:35:26.805Z","etag":null,"topics":["csharp","domain-driven-design","domain-event","domain-events","event-bus","eventbus","in-memory","net-standard"],"latest_commit_sha":null,"homepage":"https://sfmohassel.medium.com/event-aggregator-an-implementation-in-c-17fad5e6ed28","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/sfmohassel.png","metadata":{"files":{"readme":"README.md","changelog":null,"contributing":null,"funding":null,"license":"LICENSE","code_of_conduct":null,"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}},"created_at":"2020-02-04T12:33:03.000Z","updated_at":"2024-12-03T08:49:59.000Z","dependencies_parsed_at":"2024-12-03T09:42:44.988Z","dependency_job_id":null,"html_url":"https://github.com/sfmohassel/libc.eventbus","commit_stats":null,"previous_names":["sfmohassel/libc.eventbus"],"tags_count":0,"template":false,"template_full_name":null,"repository_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/sfmohassel%2Flibc.eventbus","tags_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/sfmohassel%2Flibc.eventbus/tags","releases_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/sfmohassel%2Flibc.eventbus/releases","manifests_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/sfmohassel%2Flibc.eventbus/manifests","owner_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners/sfmohassel","download_url":"https://codeload.github.com/sfmohassel/libc.eventbus/tar.gz/refs/heads/master","host":{"name":"GitHub","url":"https://github.com","kind":"github","repositories_count":241226941,"owners_count":19930489,"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":["csharp","domain-driven-design","domain-event","domain-events","event-bus","eventbus","in-memory","net-standard"],"created_at":"2025-02-28T20:33:53.197Z","updated_at":"2026-03-08T19:36:43.351Z","avatar_url":"https://github.com/sfmohassel.png","language":"C#","funding_links":[],"categories":[],"sub_categories":[],"readme":"# An in-memory event aggregator without any dependency\n\n## Why bother?\n\nIn Domain-Driven Design (DDD) pattern, there are times when we want to inform other parts of application about occurrence of an event. This is the primary goal of [DOMAIN EVENTS](https://docs.microsoft.com/en-us/dotnet/architecture/microservices/microservice-ddd-cqrs-patterns/domain-events-design-implementation#:~:text=A%20domain%20event%20is%2C%20something,effects%20can%20be%20expressed%20explicitly.)\n\n## Read More\n\nYou can checkout my article on EventAggregator [HERE](https://sfmohassel.medium.com/event-aggregator-an-implementation-in-c-17fad5e6ed28)\n\n# Installation\n\nThe package is available on nuget.org:\n\n```powershell\nPM\u003e Install-Package libc.eventbus\n```\n\n# Simple Usage\n\nLet's say we have a simple message event that has a text:\n\n```csharp\npublic class SimpleMessage : IEvent {\n    public string Text { get; private set; }\n\n    public SimpleMessage(string text) {\n        Text = text;\n    }\n}\n```\n\nNow we want that when a `SimpleMessage` is raised, print it in two distinct ways:\n\n```csharp\npublic class PrintMessageRaw : IEventHandler\u003cSimpleMessage\u003e {\n    public Task Handle(SimpleMessage ev) {\n        // print message\n        Console.WriteLine($\"Raw: {ev.Text}\");\n        return Task.CompletedTask;\n    }\n}\n\npublic class PrintMessagePretty : IEventHandler\u003cSimpleMessage\u003e {\n    public Task Handle(SimpleMessage ev) {\n        // print message\n        Console.WriteLine($\"Pretty: {ev.Text}\");\n        return Task.CompletedTask;\n    }\n}\n```\n\nAs you can see both `PrintMessageRaw` and `PrintMessagePretty` implement __`IEventHandler\u003cSimpleMessage\u003e`__.\n\n## Put it together\n\n_Read the comments please_\n\n```csharp\npublic void Showcase_WithoutCatchAll() {\n    // 1- create an event bus\n    var bus = new DefaultEventBus();\n\n    // 2- subscribe to SimpleMessage event via PrintMessageRaw event handler\n    bus.Subscribe\u003cSimpleMessage, PrintMessageRaw\u003e(new PrintMessageRaw());\n\n    // 3- subscribe to SimpleMessage event via PrintMessagePretty event handler\n    var x = new PrintMessagePretty();\n    bus.Subscribe\u003cSimpleMessage, PrintMessagePretty\u003e(x);\n\n    // 4- remember subscribing to a message with the same handler instance, has no effect!\n    bus.Subscribe\u003cSimpleMessage, PrintMessagePretty\u003e(x);\n\n    // 5- create the event\n    var message = new SimpleMessage(\"a simple message\");\n\n    // 6- publish the event\n    bus.Publish(message);\n}\n```\n\nThe console will show:\n\n```text\nRaw: a simple message\nPretty: a simple message\n```\n\n# Usage 2\n\nThere are times that we need to catch all the event (for example for logging purposes). There's a `ICatchAllEventHandler` interface that you can\nregister in the bus. To test it, first add a new event:\n\n```csharp\npublic class PrivateMessage : IEvent {\n    public string Secret { get; private set; }\n\n    public PrivateMessage(string secret) {\n        Secret = secret;\n    }\n}\n```\n\nthen an implementation of `ICatchAllEventHandler`:\n\n```csharp\npublic class CatchAllMessages : ICatchAllEventHandler {\n    public Task Handle(IEvent ev) {\n        if (ev is SimpleMessage) {\n            Console.WriteLine($\"Caught SimpleMessage: {(ev as SimpleMessage).Text}\");\n        } else if (ev is PrivateMessage) {\n            Console.WriteLine($\"Caught PrivateMessage: {(ev as PrivateMessage).Secret}\");\n        }\n        return Task.CompletedTask;\n    }\n}\n```\n\n## Put it together\n\n_Read the comments please_\n\n```csharp\npublic void Showcase_WithCatchAll() {\n    // 1- create an event bus\n    var bus = new DefaultEventBus();\n\n    // 2- subscribe to SimpleMessage event via PrintMessageRaw event handler\n    bus.Subscribe\u003cSimpleMessage, PrintMessageRaw\u003e(new PrintMessageRaw());\n\n    // 3- subscribe to SimpleMessage event via PrintMessagePretty event handler\n    bus.Subscribe\u003cSimpleMessage, PrintMessagePretty\u003e(new PrintMessagePretty());\n\n    // 4- register a catch-all event handler\n    bus.RegisterCatchAllHandler(new CatchAllMessages());\n\n    // 5- create the event\n    var message = new SimpleMessage(\"a simple message\");\n\n    // 6- publish the event\n    bus.Publish(message);\n}\n```\n\nThe console will show:\n\n```text\nRaw: a simple message\nPretty: a simple message\nCaught SimpleMessage: a simple message\n```\n\nTo see the full showcase __[click here](./libc.eventbus.tests/ShowCase.cs)__\n\n## Contributions are welcome\n","project_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Fsfmohassel%2Flibc.eventbus","html_url":"https://awesome.ecosyste.ms/projects/github.com%2Fsfmohassel%2Flibc.eventbus","lists_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Fsfmohassel%2Flibc.eventbus/lists"}