{"id":19009029,"url":"https://github.com/d-edge/diffract","last_synced_at":"2025-08-20T16:32:44.230Z","repository":{"id":44316287,"uuid":"397995866","full_name":"d-edge/Diffract","owner":"d-edge","description":"A .NET library to perform structural diff between two objects","archived":false,"fork":false,"pushed_at":"2024-04-13T16:09:56.000Z","size":68,"stargazers_count":48,"open_issues_count":6,"forks_count":5,"subscribers_count":7,"default_branch":"main","last_synced_at":"2024-04-27T04:34:38.976Z","etag":null,"topics":["diff","dotnet","fsharp","hacktoberfest","hacktoberfest2021","testing","unit-testing"],"latest_commit_sha":null,"homepage":"","language":"F#","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/d-edge.png","metadata":{"files":{"readme":"README.md","changelog":null,"contributing":null,"funding":null,"license":"LICENSE","code_of_conduct":".github/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}},"created_at":"2021-08-19T15:48:15.000Z","updated_at":"2024-04-26T12:07:15.000Z","dependencies_parsed_at":"2024-02-08T15:26:54.170Z","dependency_job_id":"9aeccad2-2cbe-46c7-b301-9c1ac3774c78","html_url":"https://github.com/d-edge/Diffract","commit_stats":null,"previous_names":[],"tags_count":5,"template":false,"template_full_name":null,"repository_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/d-edge%2FDiffract","tags_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/d-edge%2FDiffract/tags","releases_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/d-edge%2FDiffract/releases","manifests_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/d-edge%2FDiffract/manifests","owner_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners/d-edge","download_url":"https://codeload.github.com/d-edge/Diffract/tar.gz/refs/heads/main","host":{"name":"GitHub","url":"https://github.com","kind":"github","repositories_count":230438185,"owners_count":18225870,"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":["diff","dotnet","fsharp","hacktoberfest","hacktoberfest2021","testing","unit-testing"],"created_at":"2024-11-08T19:06:17.030Z","updated_at":"2024-12-19T13:08:23.369Z","avatar_url":"https://github.com/d-edge.png","language":"F#","funding_links":[],"categories":[],"sub_categories":[],"readme":"\u003cbr /\u003e\n\n\u003cp align=\"center\"\u003e\n    \u003cimg src=\"https://raw.githubusercontent.com/d-edge/diffract/main/diffract.png\" alt=\"diffract logo\" height=\"140\"\u003e\n\u003c/p\u003e\n\n\u003cp align=\"center\"\u003e\n        \u003ca href=\"https://github.com/d-edge/diffract/actions\" title=\"actions\"\u003e\u003cimg src=\"https://github.com/d-edge/diffract/actions/workflows/build.yml/badge.svg?branch=main\" alt=\"actions build\" /\u003e\u003c/a\u003e\n    \u003ca href=\"https://www.nuget.org/packages/dedge.diffract/\" title=\"nuget\"\u003e\u003cimg src=\"https://img.shields.io/nuget/vpre/dedge.diffract\" alt=\"version\" /\u003e\u003c/a\u003e\n    \u003ca href=\"https://www.nuget.org/stats/packages/dedge.diffract?groupby=Version\" title=\"stats\"\u003e\u003cimg src=\"https://img.shields.io/nuget/dt/dedge.diffract\" alt=\"download\" /\u003e\u003c/a\u003e \n    \u003ca href=\"https://raw.githubusercontent.com/d-edge/diffract/main/LICENSE\" title=\"license\"\u003e\u003cimg src=\"https://img.shields.io/github/license/d-edge/diffract\" alt=\"license\" /\u003e\u003c/a\u003e\n\u003c/p\u003e\n\n\u003cbr /\u003e\n\nDiffract is a .NET library that displays a readable diff between two objects. It is particularly useful for unit testing complex objects. Diffract is maintained by folks at [D-EDGE](https://www.d-edge.com/).\n\nHere is an example:\n\n```csharp\nusing DEdge.Diffract;\n\nrecord User(string Name, int Age, string[] Pets);\n\nvar expected = new User(\"Emma\", 42, new[] { \"Oscar\", \"Fluffy\", \"Tibbles\" });\nvar actual = new User(\"Andy\", 42, new[] { \"Oscar\", \"Sparky\" });\n\nDiffer.Assert(expected, actual);\n```\n\nThe above throws an `AssertionFailedException` with the following message:\n\n```\nValue differs by 2 fields:\n  Name Expect = \"Emma\"\n       Actual = \"Andy\"\n  Pets collection differs:\n    Pets.Count Expect = 3\n               Actual = 2\n    Pets[1] Expect = \"Fluffy\"\n            Actual = \"Sparky\"\n```\n\nDiffract can drill down many composite types:\n* POCOs;\n* C# records;\n* F# records and anonymous records;\n* F# unions;\n* enumerables (`IEnumerable\u003cT\u003e`);\n* dictionaries (`IDictionary\u003cK, V\u003e`, `IReadOnlyDictionary\u003cK, V\u003e`);\n* value and reference tuples.\n\nValues of any other equatable type (like `string` and `int` in the above example) are treated as leaves that can be tested for equality.\n\n## Example outputs\n\nPOCO or record with multiple field differences:\n\n```csharp\nrecord User(string Name, int Age, bool IsActive);\n\nvar expected = new User(\"Emma\", 42, true);\nvar actual = new User(\"Andy\", 35, true);\n```\n\n```\nValue differs by 2 fields:\n  Name Expect = \"Emma\"\n       Actual = \"Andy\"\n  Age Expect = 42\n      Actual = 35\n```\n\nF# union where the case is different:\n\n```fsharp\ntype Contact =\n  | Email of address: string\n  | Phone of number: string\n  \nlet expected = Email \"user@example.com\"\nlet actual = Phone \"555-123-456\"\n```\n\n```\nValue differs by union case:\n  Expect is Email\n  Actual is Phone\n```\n\nF# union where the case is the same and the value is different:\n\n```fsharp\ntype Contact =\n  | Email of address: string\n  | Phone of number: string\n  \nlet expected = Email \"user@example.com\"\nlet actual = Email \"someone@example.com\"\n```\n\n```\nValue differs by union case Email fields:\n  address Expect = \"user@example.com\"\n          Actual = \"someone@example.com\"\n```\n\nEnumerables show the counts if they differ, followed by the diffs per item:\n\n```csharp\nvar expected = new string[] { \"first\", \"second\" };\nvar actual = new string[] { \"first\", \"2nd\", \"third\" };\n```\n\n```\nValue collection differs:\n  Count Expect = 2\n        Actual = 3\n  [1] Expect = \"second\"\n      Actual = \"2nd\"\n```\n\nDictionaries show the keys missing on either side, followed by the diffs per item that exists in both:\n\n```csharp\nvar expected = new Dictionary\u003cstring, int\u003e\n{\n    { \"first\", 1 },\n    { \"second\", 2 },\n    { \"third\", 3 },\n};\nvar actual = new Dictionary\u003cstring, int\u003e\n{\n    { \"first\", 1 },\n    { \"third\", 2 },\n    { \"fourth\", 4 },\n};\n```\n\n```\nValue dictionary differs:\n  [\"second\"] Actual is missing\n  [\"fourth\"] Expect is missing\n  [\"third\"] Expect = 3\n            Actual = 2\n```\n\n## API\n\nDiffract lives in the namespace `DEdge.Diffract`. Its main API is the class `Differ`, which provides the following methods:\n\n```csharp\nvoid Assert\u003cT\u003e(T expected, T actual, IDiffer\u003cT\u003e differ = null, PrintParams param = null)\n```\n\nComputes the diff between two objects and, if it is not empty, throws an `AssertionFailedException` with the diff as message.\n\n```csharp\nstring ToString\u003cT\u003e(T expected, T actual, IDiffer\u003cT\u003e differ = null, PrintParams param = null)\n```\n\nPrints the diff between two objects to a string.\n\n```csharp\nvoid Write\u003cT\u003e(T expected, T actual, TextWriter writer = null, IDiffer\u003cT\u003e differ = null, PrintParams param = null)\n```\n\nPrints the diff between two objects to the given TextWriter (or to standard output if not provided).\n\n```csharp\nFSharpOption\u003cDiff\u003e Diff\u003cT\u003e(T expected, T actual, IDiffer\u003cT\u003e differ = null)\n```\n\nComputes the diff between two objects. Returns `None` if the objects are found to be equal.\n","project_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Fd-edge%2Fdiffract","html_url":"https://awesome.ecosyste.ms/projects/github.com%2Fd-edge%2Fdiffract","lists_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Fd-edge%2Fdiffract/lists"}