Advertisement
Guest User

composing queryables

a guest
Apr 9th, 2020
265
0
Never
Not a member of Pastebin yet? Sign Up, it unlocks many cool features!
C# 2.59 KB | None | 0 0
  1. using System;
  2. using System.Collections.Specialized;
  3. using System.Linq;
  4. using System.Web;
  5.  
  6. namespace demo
  7. {
  8.     class Program
  9.     {
  10.         static void Main(string[] args)
  11.         {
  12.             // create a PagingOptions object from URL
  13.             var parser = new PagingQueryOptionsParser();
  14.             var options = parser.Parse(new Uri("https://localhost/foo?$top=5&$skip=5"));
  15.  
  16.             // retrieve data as a queryable
  17.             var items = Enumerable.Range(0, 100).AsQueryable();
  18.  
  19.             // apply paging query options
  20.             var result = options.Apply(items);
  21.  
  22.             // print result
  23.             System.Console.WriteLine("{0}", string.Join(", ", result));
  24.         }
  25.     }
  26.  
  27.  
  28.     public class PagingQueryOptions
  29.     {
  30.         public PagingQueryOptions(int? take, int? skip)
  31.         {
  32.             Take = take;
  33.             Skip = skip;
  34.         }
  35.  
  36.         public int? Take { get; }
  37.         public int? Skip { get; }
  38.  
  39.         public IQueryable<T> Apply<T>(IQueryable<T> items)
  40.         {
  41.             // n.b. order of skip and take is important
  42.             if (Skip.HasValue)
  43.             {
  44.                 items = items.Skip(Skip.Value);
  45.             }
  46.             if (Take.HasValue)
  47.             {
  48.                 items = items.Take(Take.Value);
  49.             }
  50.             return items;
  51.         }
  52.     }
  53.  
  54.     public class PagingQueryOptionsParser
  55.     {
  56.         public PagingQueryOptions Parse(Uri url)
  57.         {
  58.             var query = HttpUtility.ParseQueryString(url.Query);
  59.             var take = GetSingleIntQueryOption("$top", query);
  60.             var skip = GetSingleIntQueryOption("$skip", query);
  61.             return new PagingQueryOptions(take, skip);
  62.         }
  63.  
  64.         // get the value of the query option with name <name> and return it as int?
  65.         // return null if the name is not present,
  66.         // throw ArgumentException if value is not a number or the name is given more than once
  67.         // return the value as an Int otherwise
  68.         private static int? GetSingleIntQueryOption(string name, NameValueCollection query)
  69.         {
  70.             var values = query.GetValues(name);
  71.             if (values == null)
  72.             {
  73.                 return null;
  74.             }
  75.             if (values.Length > 1)
  76.             {
  77.                 throw new ArgumentException($"Invalid query parameter, query option {name} must not appear more than once");
  78.             }
  79.  
  80.             return Int32.TryParse(values.Single(), out var val) ? val :
  81.                 throw new ArgumentException($"Query Option {name}'s value is not a number");
  82.         }
  83.     }
  84. }
Advertisement
Add Comment
Please, Sign In to add comment
Advertisement