private async Task CreateQueryTest <MovieType, TExpectedException>( string name, Expression <Func <MovieType, bool> > whereClause, int?top = null, int?skip = null, OrderByClause[] orderBy = null, Expression <Func <MovieType, string> > selectExpression = null, bool?includeTotalCount = null, string odataExpression = null, bool useStringIdTable = false, Func <MovieType, bool> whereLambda = null) where MovieType : class, IMovie where TExpectedException : Exception { Log("### Executing {0}.", name); if (whereClause == null && whereLambda != null) { Assert.Fail("The argument 'whereLambda' is optional and can only be specified if 'whereClause' is also specified."); } try { var table = this.GetClient().GetTable <MovieType>(); IEnumerable <MovieType> readMovies = null; IEnumerable <string> readProjectedMovies = null; if (odataExpression == null) { IMobileServiceTableQuery <MovieType> query = null; IMobileServiceTableQuery <string> selectedQuery = null; if (whereClause != null) { query = table.Where(whereClause); } if (orderBy != null) { if (query == null) { query = table.Where(m => m.Duration == m.Duration); } query = ApplyOrdering(query, orderBy); } if (top.HasValue) { query = query == null?table.Take(top.Value) : query.Take(top.Value); } if (skip.HasValue) { query = query == null?table.Skip(skip.Value) : query.Skip(skip.Value); } if (selectExpression != null) { selectedQuery = query == null?table.Select(selectExpression) : query.Select(selectExpression); } if (includeTotalCount.HasValue) { query = query.IncludeTotalCount(); } if (selectedQuery == null) { // Both ways of querying should be equivalent, so using both with equal probability here. // TODO: Make it deterministic var tickCount = Environment.TickCount; if ((tickCount % 2) == 0) { Log("Querying using MobileServiceTableQuery<T>.ToEnumerableAsync"); readMovies = await query.ToEnumerableAsync(); } else { Log("Querying using IMobileServiceTable<T>.ReadAsync(MobileServiceTableQuery<U>)"); readMovies = await table.ReadAsync(query); } } else { readProjectedMovies = await selectedQuery.ToEnumerableAsync(); } } else { Log("Using the OData query directly"); JToken result = await table.ReadAsync(odataExpression); readMovies = result.ToObject <IEnumerable <MovieType> >(); } long actualTotalCount = -1; ITotalCountProvider totalCountProvider = (readMovies as ITotalCountProvider) ?? (readProjectedMovies as ITotalCountProvider); if (totalCountProvider != null) { actualTotalCount = totalCountProvider.TotalCount; } IEnumerable <MovieType> expectedData; if (useStringIdTable) { var movies = QueryTestData.TestMovies(); expectedData = new MovieType[movies.Length]; for (var i = 0; i < movies.Length; i++) { ((MovieType[])expectedData)[i] = (MovieType)(IMovie)movies[i]; } } else { expectedData = QueryTestData.TestIntIdMovies.Select(s => (MovieType)(IMovie)s); } // Due to a Xamarin.iOS bug, Expression.Compile() does not work for some expression trees, // in which case we allow the caller to provide a lambda directly and we use it instead of // compiling the expression tree. if (whereLambda != null) { expectedData = expectedData.Where(whereLambda); } else if (whereClause != null) { expectedData = expectedData.Where(whereClause.Compile()); } long expectedTotalCount = -1; if (includeTotalCount.HasValue && includeTotalCount.Value) { expectedTotalCount = expectedData.Count(); } if (orderBy != null) { expectedData = ApplyOrdering(expectedData, orderBy); } if (skip.HasValue) { expectedData = expectedData.Skip(skip.Value); } if (top.HasValue) { expectedData = expectedData.Take(top.Value); } if (includeTotalCount.HasValue) { if (expectedTotalCount != actualTotalCount) { Log("Total count was requested, but the returned value is incorrect: expected={0}, actual={1}", expectedTotalCount, actualTotalCount); Assert.Fail(""); return; } } List <string> errors = new List <string>(); bool expectedDataIsSameAsReadData; if (selectExpression != null) { string[] expectedProjectedData = expectedData.Select(selectExpression.Compile()).ToArray(); expectedDataIsSameAsReadData = Utilities.CompareArrays(expectedProjectedData, readProjectedMovies.ToArray(), errors); } else { expectedDataIsSameAsReadData = Utilities.CompareArrays(expectedData.ToArray(), readMovies.ToArray(), errors); } if (!expectedDataIsSameAsReadData) { foreach (var error in errors) { Log(error); } Log("Expected data is different"); Assert.Fail(""); return; } else { if (typeof(TExpectedException) == typeof(ExceptionTypeWhichWillNeverBeThrown)) { return; } else { Log("Error, test should have failed with {0}, but succeeded.", typeof(TExpectedException).FullName); Assert.Fail(""); return; } } } catch (TExpectedException ex) { Log("Caught expected exception - {0}: {1}", ex.GetType().FullName, ex.Message); return; } }
private async Task CreateQueryTest <MovieType, TExpectedException>( string name, Expression <Func <MovieType, bool> > whereClause, int?top = null, int?skip = null, OrderByClause[] orderBy = null, Expression <Func <MovieType, string> > selectExpression = null, bool?includeTotalCount = null, string odataExpression = null, bool useStringIdTable = false, Func <MovieType, bool> whereLambda = null) where MovieType : class, IMovie where TExpectedException : Exception { Assert.False(whereClause == null && whereLambda != null); try { var table = this.GetClient().GetTable <MovieType>(); IEnumerable <MovieType> readMovies = null; IEnumerable <string> readProjectedMovies = null; if (odataExpression == null) { IMobileServiceTableQuery <MovieType> query = null; IMobileServiceTableQuery <string> selectedQuery = null; if (whereClause != null) { query = table.Where(whereClause); } if (orderBy != null) { if (query == null) { query = table.Where(m => m.Duration == m.Duration); } query = ApplyOrdering(query, orderBy); } if (top.HasValue) { query = query == null?table.Take(top.Value) : query.Take(top.Value); } if (skip.HasValue) { query = query == null?table.Skip(skip.Value) : query.Skip(skip.Value); } if (selectExpression != null) { selectedQuery = query == null?table.Select(selectExpression) : query.Select(selectExpression); } if (includeTotalCount.HasValue) { query = query.IncludeTotalCount(); } if (selectedQuery == null) { // Both ways of querying should be equivalent, so using both with equal probability here. // TODO: Make it deterministic var tickCount = Environment.TickCount; if ((tickCount % 2) == 0) { readMovies = await query.ToEnumerableAsync(); } else { readMovies = await table.ReadAsync(query); } } else { readProjectedMovies = await selectedQuery.ToEnumerableAsync(); } } else { JToken result = await table.ReadAsync(odataExpression); readMovies = result.ToObject <IEnumerable <MovieType> >(); } long actualTotalCount = -1; #pragma warning disable CS0618 // Type or member is obsolete ITotalCountProvider totalCountProvider = (readMovies as ITotalCountProvider) ?? (readProjectedMovies as ITotalCountProvider); #pragma warning restore CS0618 // Type or member is obsolete if (totalCountProvider != null) { actualTotalCount = totalCountProvider.TotalCount; } IEnumerable <MovieType> expectedData; if (useStringIdTable) { var movies = QueryTestData.TestMovies(); expectedData = new MovieType[movies.Length]; for (var i = 0; i < movies.Length; i++) { ((MovieType[])expectedData)[i] = (MovieType)(IMovie)movies[i]; } } else { expectedData = QueryTestData.TestIntIdMovies.Select(s => (MovieType)(IMovie)s); } // Due to a Xamarin.iOS bug, Expression.Compile() does not work for some expression trees, // in which case we allow the caller to provide a lambda directly and we use it instead of // compiling the expression tree. if (whereLambda != null) { expectedData = expectedData.Where(whereLambda); } else if (whereClause != null) { expectedData = expectedData.Where(whereClause.Compile()); } long expectedTotalCount = -1; if (includeTotalCount.HasValue && includeTotalCount.Value) { expectedTotalCount = expectedData.Count(); } if (orderBy != null) { expectedData = ApplyOrdering(expectedData, orderBy); } if (skip.HasValue) { expectedData = expectedData.Skip(skip.Value); } if (top.HasValue) { expectedData = expectedData.Take(top.Value); } if (includeTotalCount.HasValue) { Assert.Equal(expectedTotalCount, actualTotalCount); } List <string> errors = new List <string>(); bool expectedDataIsSameAsReadData; if (selectExpression != null) { string[] expectedProjectedData = expectedData.Select(selectExpression.Compile()).ToArray(); expectedDataIsSameAsReadData = Utilities.CompareArrays(expectedProjectedData, readProjectedMovies.ToArray(), errors); } else { expectedDataIsSameAsReadData = Utilities.CompareArrays(expectedData.ToArray(), readMovies.ToArray(), errors); } Assert.True(expectedDataIsSameAsReadData); if (typeof(TExpectedException) != typeof(ExceptionTypeWhichWillNeverBeThrown)) { Assert.True(false, "Test should have failed"); return; } } catch (TExpectedException) { return; } }
private static ZumoTest CreateQueryTest <TExpectedException>( string name, Expression <Func <Movie, bool> > whereClause, int?top = null, int?skip = null, OrderByClause[] orderBy = null, Expression <Func <Movie, string> > selectExpression = null, bool?includeTotalCount = null, string odataExpression = null) where TExpectedException : Exception { return(new ZumoTest(name, async delegate(ZumoTest test) { try { var table = ZumoTestGlobals.Instance.Client.GetTable <Movie>(); IEnumerable <Movie> readMovies = null; IEnumerable <string> readProjectedMovies = null; if (odataExpression == null) { IMobileServiceTableQuery <Movie> query = null; IMobileServiceTableQuery <string> selectedQuery = null; if (whereClause != null) { query = table.Where(whereClause); } if (orderBy != null) { if (query == null) { query = table.Where(m => m.Duration == m.Duration); } query = ApplyOrdering(query, orderBy); } if (top.HasValue) { query = query == null ? table.Take(top.Value) : query.Take(top.Value); } if (skip.HasValue) { query = query == null ? table.Skip(skip.Value) : query.Skip(skip.Value); } if (selectExpression != null) { selectedQuery = query == null ? table.Select(selectExpression) : query.Select(selectExpression); } if (includeTotalCount.HasValue) { query = query.IncludeTotalCount(); } if (selectedQuery == null) { // Both ways of querying should be equivalent, so using both with equal probability here. var tickCount = Environment.TickCount; if ((tickCount % 2) == 0) { test.AddLog("Querying using MobileServiceTableQuery<T>.ToEnumerableAsync"); readMovies = await query.ToEnumerableAsync(); } else { test.AddLog("Querying using IMobileServiceTable<T>.ReadAsync(MobileServiceTableQuery<U>)"); readMovies = await table.ReadAsync(query); } } else { readProjectedMovies = await selectedQuery.ToEnumerableAsync(); } } else { test.AddLog("Using the OData query directly"); JToken result = await table.ReadAsync(odataExpression); readMovies = result.ToObject <IEnumerable <Movie> >(); } long actualTotalCount = -1; ITotalCountProvider totalCountProvider = (readMovies as ITotalCountProvider) ?? (readProjectedMovies as ITotalCountProvider); if (totalCountProvider != null) { actualTotalCount = totalCountProvider.TotalCount; } IEnumerable <Movie> expectedData = ZumoQueryTestData.AllMovies; if (whereClause != null) { expectedData = expectedData.Where(whereClause.Compile()); } long expectedTotalCount = -1; if (includeTotalCount.HasValue && includeTotalCount.Value) { expectedTotalCount = expectedData.Count(); } if (orderBy != null) { expectedData = ApplyOrdering(expectedData, orderBy); } if (skip.HasValue) { expectedData = expectedData.Skip(skip.Value); } if (top.HasValue) { expectedData = expectedData.Take(top.Value); } if (includeTotalCount.HasValue) { if (expectedTotalCount != actualTotalCount) { test.AddLog("Total count was requested, but the returned value is incorrect: expected={0}, actual={1}", expectedTotalCount, actualTotalCount); return false; } } List <string> errors = new List <string>(); bool expectedDataIsSameAsReadData; if (selectExpression != null) { string[] expectedProjectedData = expectedData.Select(selectExpression.Compile()).ToArray(); expectedDataIsSameAsReadData = Util.CompareArrays(expectedProjectedData, readProjectedMovies.ToArray(), errors); } else { expectedDataIsSameAsReadData = Util.CompareArrays(expectedData.ToArray(), readMovies.ToArray(), errors); } if (!expectedDataIsSameAsReadData) { foreach (var error in errors) { test.AddLog(error); } test.AddLog("Expected data is different"); return false; } else { if (typeof(TExpectedException) == typeof(ExceptionTypeWhichWillNeverBeThrown)) { return true; } else { test.AddLog("Error, test should have failed with {0}, but succeeded.", typeof(TExpectedException).FullName); return false; } } } catch (TExpectedException ex) { test.AddLog("Caught expected exception - {0}: {1}", ex.GetType().FullName, ex.Message); return true; } })); }
public IAsyncQuery <T> Take(int count) { return(new AsyncQuery <T>(from.Take(count))); }