{"id":19971159,"url":"https://github.com/ignatandrei/rscg_queryables","last_synced_at":"2026-01-27T14:01:49.131Z","repository":{"id":261915414,"uuid":"885675611","full_name":"ignatandrei/rscg_queryables","owner":"ignatandrei","description":null,"archived":false,"fork":false,"pushed_at":"2024-11-11T17:11:41.000Z","size":63,"stargazers_count":0,"open_issues_count":0,"forks_count":0,"subscribers_count":1,"default_branch":"main","last_synced_at":"2025-12-01T16:30:33.269Z","etag":null,"topics":[],"latest_commit_sha":null,"homepage":null,"language":"HTML","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/ignatandrei.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":"2024-11-09T05:01:18.000Z","updated_at":"2024-11-11T17:11:45.000Z","dependencies_parsed_at":"2024-11-09T08:26:18.474Z","dependency_job_id":"70f2113e-17cd-4e93-9ec2-2c979940de8f","html_url":"https://github.com/ignatandrei/rscg_queryables","commit_stats":null,"previous_names":["ignatandrei/rscg_queryables"],"tags_count":2,"template":false,"template_full_name":null,"purl":"pkg:github/ignatandrei/rscg_queryables","repository_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/ignatandrei%2Frscg_queryables","tags_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/ignatandrei%2Frscg_queryables/tags","releases_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/ignatandrei%2Frscg_queryables/releases","manifests_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/ignatandrei%2Frscg_queryables/manifests","owner_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners/ignatandrei","download_url":"https://codeload.github.com/ignatandrei/rscg_queryables/tar.gz/refs/heads/main","sbom_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/ignatandrei%2Frscg_queryables/sbom","scorecard":null,"host":{"name":"GitHub","url":"https://github.com","kind":"github","repositories_count":286080680,"owners_count":28814289,"icon_url":"https://github.com/github.png","version":null,"created_at":"2022-05-30T11:31:42.601Z","updated_at":"2026-01-27T12:25:15.069Z","status":"ssl_error","status_checked_at":"2026-01-27T12:25:05.297Z","response_time":168,"last_error":"SSL_read: unexpected eof while reading","robots_txt_status":"success","robots_txt_updated_at":"2025-07-24T06:49:26.215Z","robots_txt_url":"https://github.com/robots.txt","online":false,"can_crawl_api":true,"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":[],"created_at":"2024-11-13T03:01:34.508Z","updated_at":"2026-01-27T14:01:49.109Z","avatar_url":"https://github.com/ignatandrei.png","language":"HTML","funding_links":[],"categories":["Content"],"sub_categories":["165. [rscg_queryables](https://ignatandrei.github.io/RSCG_Examples/v2/docs/rscg_queryables) , in the [FunctionalProgramming](https://ignatandrei.github.io/RSCG_Examples/v2/docs/rscg-examples#functionalprogramming) category"],"readme":"\n# rscg_queryables\n\n\n[![NuGet](https://img.shields.io/nuget/v/rscg_queryables.svg)](https://www.nuget.org/packages/rscg_queryables)\n[![NuGet](https://img.shields.io/nuget/v/rscg_queryablesCommon.svg)](https://www.nuget.org/packages/rscg_queryablesCommon)\n[![GitHub Actions](https://github.com/ignatandrei/rscg_queryables/actions/workflows/dotnet.yml/badge.svg)](https://github.com/ignatandrei/rscg_queryables/actions/workflows/dotnet.yml)\n\n\n`rscg_queryables` is a Roslyn Code Generator designed to generate extension methods for sorting and filtering `IEnumerable` and `IQueryable` collections based on a given class.\n\n\n\n## Sorting how the user wants in frontend  - description\n\nConsider a scenario where we need to display a list of `Person` objects and allow the user to sort them by various properties. The user should have the ability to select the property and the sorting order.\n\n```csharp\npublic class Person\n{\n    public string FirstName { get; set; } = string.Empty;\n    public string LastName { get; set; } = string.Empty;\n\n    public int Age { get; set; }\n    public string FullName\n    {\n        get\n        {\n            return $\"{FirstName} {LastName}\";\n        }\n    }\n}\n```\n\nWhen data is transmitted over HTTP, it is often in the form of a string object. To sort by first name in descending order, the query string should look like this:\n\n```json\norderBy=FirstName\u0026Asc=false\n```\n\nThen in the backend code we should parse the query string and apply the sorting logic.\n\n```csharp\nif(queryString.ContainsKey(\"orderBy\"))\n{\n    string orderBy = queryString[\"orderBy\"];\n    bool asc = queryString[\"asc\"] == \"false\" ? false: true;//default is true\n    if(orderBy == \"FirstName\")\n    {\n        if(asc)\n        {\n            persons = persons.OrderBy(p =\u003e p.FirstName);\n        }\n        else\n        {\n            persons = persons.OrderByDescending(p =\u003e p.FirstName);\n        }\n    }\n    //do the same for other properties : LastName, Age, FullName\n\n}\n```\n\n## The solution\n\nWith rscg_queryables, you can do this in a more elegant way.\n\n```csharp\nif(queryString.ContainsKey(\"orderBy\"))\n{\n    string orderBy = queryString[\"orderBy\"];\n    bool asc = queryString[\"asc\"] == \"false\" ? false: true;//default is true\n    persons = persons.OrderByAscDesc(orderBy, asc);\n    //or you can do this, if you want to control \n    //if(asc)\n    //{\n    //    persons = persons.OrderBy(orderBy);\n    //}\n    //else\n    //{\n    //    persons = persons.OrderByDescending(orderBy);\n    //}\n}\n```\n\nThis should be done for everything that implements IEnumerable or IQueryable.\n\n\n\n## Filtering Based on User Preferences - Description\n\nConsider a scenario where we need to display a list of `Person` objects and allow the user to filter them by various properties. The user should have the ability to select the property, the filter criteria, and the filter operator (equal or different).\n\nWhen data is transmitted over HTTP, it is often in the form of a string object. To filter by first name where the value is \"John\", the query string should look like this:\n\n```json\nfilterBy=FirstName\u0026filterOperator=equal\u0026filterValue=John\n```\n\nIn the backend code, we need to parse the query string and apply the appropriate filtering logic.\n\n```csharp\nif (queryString.ContainsKey(\"filterBy\") \u0026\u0026 queryString.ContainsKey(\"filterOperator\") \u0026\u0026 queryString.ContainsKey(\"filterValue\"))\n{\n    string filterBy = queryString[\"filterBy\"];\n    string filterOperator = queryString[\"filterOperator\"];\n    string filterValue = queryString[\"filterValue\"];\n    if (filterBy == \"FirstName\")\n    {\n        if (filterOperator == \"equal\")\n        {\n            persons = persons.Where(p =\u003e p.FirstName == filterValue);\n        }\n        else if (filterOperator == \"different\")\n        {\n            persons = persons.Where(p =\u003e p.FirstName != filterValue);\n        }\n    }\n    // Do the same for other properties: LastName, Age, FullName\n}\n```\n\n## The Solution\n\nWith `rscg_queryables`, you can achieve this in a more elegant and efficient manner.\n\n1. add the  nugets to your project\n\n```xml\n\t\u003cItemGroup\u003e\n\t\t\u003cPackageReference  Include=\"rscg_queryablesCommon\" Version=\"2024.1111.1910\" /\u003e\n\t\t\u003cPackageReference Include=\"rscg_queryables\" Version=\"2024.1111.1910\"  OutputItemType=\"Analyzer\" ReferenceOutputAssembly=\"false\" /\u003e\n\t\u003c/ItemGroup\u003e\n```\n\nOptional see the code generated\n```xml\n\t\u003cPropertyGroup\u003e\n\t\t\u003cEmitCompilerGeneratedFiles\u003etrue\u003c/EmitCompilerGeneratedFiles\u003e\n\t\t\u003cCompilerGeneratedFilesOutputPath\u003e$(BaseIntermediateOutputPath)\\GX\u003c/CompilerGeneratedFilesOutputPath\u003e\n\t\u003c/PropertyGroup\u003e\n```\n\n2. Modify the `Person` class to add the `rscg_queryables` attribute.\n\n```csharp\n[MakeSortable]\n[MakeWhere]\npublic class Person\n{\n    //same code as above, omitted for brevity\n}\n```\n\n3. Use the overloaded `Where` method to filter the collection based on the query string.\n\n```csharp\nif (queryString.ContainsKey(\"filterBy\") \u0026\u0026 queryString.ContainsKey(\"filterOperator\") \u0026\u0026 queryString.ContainsKey(\"filterValue\"))\n{\n    string filterBy = queryString[\"filterBy\"];\n    string filterOperator = queryString[\"filterOperator\"] == \"equal\"?WhereOperator.Equal:WhereOperator.Different;\n    string filterValue = queryString[\"filterValue\"];\n    persons = persons.Where(filterBy, filterOperator, filterValue);\n    \n}\n```\n\nThis approach can be applied to any collection that implements `IEnumerable` or `IQueryable`.\n\n## Other Roslyn Code Generators\n\nFor more Roslyn Source Code Generators, visit [RSCG Examples https://ignatandrei.github.io/RSCG_Examples/v2/docs/rscg-examples](https://ignatandrei.github.io/RSCG_Examples/v2/docs/rscg-examples).\n\n\n\n","project_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Fignatandrei%2Frscg_queryables","html_url":"https://awesome.ecosyste.ms/projects/github.com%2Fignatandrei%2Frscg_queryables","lists_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Fignatandrei%2Frscg_queryables/lists"}