From 13b3aed088ba10113c29274bdade5de01f39316c Mon Sep 17 00:00:00 2001 From: John Cardinal Date: Tue, 24 Feb 2026 07:05:56 -0800 Subject: [PATCH] 4648 --- ApiResponse.cs | 38 +- ApiRoot/ApiRoute.cs | 62 +- ApiTextResponse.cs | 24 +- Attachments/AttachmentTest.cs | 408 +- Authentication/Auth.cs | 274 +- DataList/DataListFiltering.cs | 7998 +++++++++++------------ DataList/DataListReturnFormat.cs | 230 +- DataList/DataListRights.cs | 60 +- DataList/DataListSorting.cs | 826 +-- DataList/DataListViewCrud.cs | 404 +- Docs/Docs.cs | 62 +- Enum/EnumListOps.cs | 90 +- EventLog/EventLog.cs | 442 +- FormCustom/FormCustom.cs | 482 +- Global/GlobalAll.cs | 58 +- LogFiles/LogFiles.cs | 56 +- Metrics/Metrics.cs | 126 +- PickList/PickListAllTests.cs | 932 +-- Privacy/Privacy.cs | 56 +- Search/SearchOps.cs | 1408 ++-- ServerJob/JobOperations.cs | 118 +- ServerState/ServerStateTest.cs | 50 +- Tags/TagOps.cs | 330 +- Translation/RequestedTranslationKeys.cs | 134 +- Translation/Translation.cs | 376 +- User/UserCrud.cs | 526 +- User/UserInactive.cs | 58 +- User/UserOptions.cs | 244 +- Widget/WidgetCrud.cs | 398 +- Widget/WidgetRights.cs | 162 +- Widget/WidgetValidationTests.cs | 478 +- WorkOrder/WorkOrderCrud.cs | 1380 ++-- raven-integration.csproj | 13 +- util.cs | 1308 ++-- 34 files changed, 9807 insertions(+), 9804 deletions(-) diff --git a/ApiResponse.cs b/ApiResponse.cs index df76a38..ecf351a 100644 --- a/ApiResponse.cs +++ b/ApiResponse.cs @@ -1,20 +1,20 @@ -using System.Net.Http; -using Newtonsoft.Json.Linq; - -namespace raven_integration -{ - public class ApiResponse - { - public HttpResponseMessage HttpResponse { get; set; } - public JObject ObjectResponse { get; set; } - public string CompactResponse - { - get - { - return ObjectResponse.ToString(Newtonsoft.Json.Formatting.None); - } - } - - - }//eoc +using System.Net.Http; +using Newtonsoft.Json.Linq; + +namespace raven_integration +{ + public class ApiResponse + { + public HttpResponseMessage HttpResponse { get; set; } + public JObject ObjectResponse { get; set; } + public string CompactResponse + { + get + { + return ObjectResponse.ToString(Newtonsoft.Json.Formatting.None); + } + } + + + }//eoc }//eons \ No newline at end of file diff --git a/ApiRoot/ApiRoute.cs b/ApiRoot/ApiRoute.cs index aa10b65..43fa823 100644 --- a/ApiRoot/ApiRoute.cs +++ b/ApiRoot/ApiRoute.cs @@ -1,31 +1,31 @@ -using System; -using Xunit; -using Newtonsoft.Json.Linq; -using FluentAssertions; -using System.Collections.Generic; -using System.Collections.Concurrent; - -namespace raven_integration -{ - - public class ApiRoute - { - - - - /// - /// - /// - [Fact] - public async void ServerApiRootPageShouldFetch() - { - ApiTextResponse t = await Util.GetNonApiPageAsync("/api/v8/"); - Util.ValidateHTTPStatusCode(t, 200); - t.TextResponse.Should().Contain("AyaNova server"); - - } - - //================================================== - - }//eoc -}//eons +using System; +using Xunit; +using Newtonsoft.Json.Linq; +using FluentAssertions; +using System.Collections.Generic; +using System.Collections.Concurrent; + +namespace raven_integration +{ + + public class ApiRoute + { + + + + /// + /// + /// + [Fact] + public async Task ServerApiRootPageShouldFetch() + { + ApiTextResponse t = await Util.GetNonApiPageAsync("/api/v8/"); + Util.ValidateHTTPStatusCode(t, 200); + t.TextResponse.Should().Contain("AyaNova server"); + + } + + //================================================== + + }//eoc +}//eons diff --git a/ApiTextResponse.cs b/ApiTextResponse.cs index 6cad35a..5b52014 100644 --- a/ApiTextResponse.cs +++ b/ApiTextResponse.cs @@ -1,13 +1,13 @@ -using System.Net.Http; -using Newtonsoft.Json.Linq; - -namespace raven_integration -{ - public class ApiTextResponse - { - public HttpResponseMessage HttpResponse {get;set;} - public string TextResponse {get;set;} - - - }//eoc +using System.Net.Http; +using Newtonsoft.Json.Linq; + +namespace raven_integration +{ + public class ApiTextResponse + { + public HttpResponseMessage HttpResponse {get;set;} + public string TextResponse {get;set;} + + + }//eoc }//eons \ No newline at end of file diff --git a/Attachments/AttachmentTest.cs b/Attachments/AttachmentTest.cs index ffbc01e..f6f9900 100644 --- a/Attachments/AttachmentTest.cs +++ b/Attachments/AttachmentTest.cs @@ -1,204 +1,204 @@ -using System; -using Xunit; -using Newtonsoft.Json.Linq; -using FluentAssertions; -using System.Collections.Generic; -using System.Collections.Concurrent; -using System.Net.Http; -using System.Net.Http.Headers; -using System.IO; - -namespace raven_integration -{ - //https://stackoverflow.com/questions/17725882/testing-asp-net-web-api-multipart-form-data-file-upload - public class AttachmentTest - { - /// - /// test attach CRUD - /// - [Fact] - public async void AttachmentUploadDownloadDeleteShouldWork() - { - - //Make a user just for this test so can deal with dl token properly - var UniqueName = Util.Uniquify("AttachmentUploadDownloadDeleteShouldWork"); - //CREATE - dynamic d = new JObject(); - d.name = UniqueName; - - d.active = true; - d.login = UniqueName; - d.password = UniqueName; - d.roles = 2;//bizadminfull needs widget rights - d.userType = 3;//non scheduleable - - //Required by form custom rules - d.notes = "notes"; - d.customFields = Util.UserRequiredCustomFieldsJsonString(); - - ApiResponse a = await Util.PostAsync("User", await Util.GetTokenAsync("superuser", "l3tm3in"), d.ToString()); - Util.ValidateDataReturnResponseOk(a); - long TestUserId=a.ObjectResponse["data"]["id"].Value(); - - d = new JObject(); - d.login = UniqueName; - d.password = UniqueName; - a = await Util.PostAsync("auth", null, d.ToString()); - string downloadToken = a.ObjectResponse["data"]["dlt"].Value(); - - ////////////////////////////////////////// - //// Upload the files - MultipartFormDataContent formDataContent = new MultipartFormDataContent(); - - //Form data like the bizobject type and id - formDataContent.Add(new StringContent("3"), name: "AttachToObjectType"); - formDataContent.Add(new StringContent(TestUserId.ToString()), name: "AttachToObjectId"); - formDataContent.Add(new StringContent("Test:AttachmentUploadDownloadDeleteShouldWork"), name: "Notes"); - formDataContent.Add(new StringContent("[{\"name\":\"test.zip\",\"lastModified\":1582822079618},{\"name\":\"test.png\",\"lastModified\":1586900220990}]"), name: "FileData"); - - //fileData in JSON stringify format which contains the actual last modified dates etc - //"[{\"name\":\"Client.csv\",\"lastModified\":1582822079618},{\"name\":\"wmi4fu06nrs41.jpg\",\"lastModified\":1586900220990}]" - //or if testing non-existant this is probably safe: long.MaxValue - - - StreamContent file1 = new StreamContent(File.OpenRead($"{Util.TEST_DATA_FOLDER}\\test.png")); - file1.Headers.ContentType = new MediaTypeHeaderValue("image/png"); - file1.Headers.ContentDisposition = new ContentDispositionHeaderValue("form-data"); - file1.Headers.ContentDisposition.FileName = "test.png"; - formDataContent.Add(file1); - StreamContent file2 = new StreamContent(File.OpenRead($"{Util.TEST_DATA_FOLDER}\\test.zip")); - file2.Headers.ContentType = new MediaTypeHeaderValue("application/zip"); - file2.Headers.ContentDisposition = new ContentDispositionHeaderValue("form-data"); - file2.Headers.ContentDisposition.FileName = "test.zip"; - formDataContent.Add(file2); - - //create via inventory full test user as attachments use the role of the object attaching to - a = await Util.PostFormDataAsync("attachment", formDataContent, await Util.GetTokenAsync("superuser", "l3tm3in")); - - - Util.ValidateDataReturnResponseOk(a); - - long lTestPngAttachmentId = a.ObjectResponse["data"][0]["id"].Value(); - long lTestZipAttachmentId = a.ObjectResponse["data"][1]["id"].Value(); - - //saw negative values on a db issue that I corrected (I think) - //Keeping these in case it arises again, if it does, see log, it's a db error with async issue of some kind - lTestPngAttachmentId.Should().BePositive(); - lTestZipAttachmentId.Should().BePositive(); - - ////////////////////////////////////////// - //// DOWNLOAD: Get the file attachment - - //now get the file https://rockfish.ayanova.com/api/rfcaseblob/download/248?t=9O2eDAAlZ0Wknj19SBK2iA - var dlresponse = await Util.DownloadFileAsync("attachment/Download/" + lTestZipAttachmentId.ToString() + "?t=" + downloadToken, null); - - //ensure it's the zip file we expected - dlresponse.Content.Headers.ContentDisposition.FileName.Should().Be("test.zip"); - dlresponse.Content.Headers.ContentLength.Should().BeGreaterThan(2000); - - - ////////////////////////////////////////// - //// DELETE: Delete the file attachments - a = await Util.DeleteAsync("attachment/" + lTestPngAttachmentId.ToString(), await Util.GetTokenAsync("superuser", "l3tm3in")); - Util.ValidateHTTPStatusCode(a, 204); - - a = await Util.DeleteAsync("attachment/" + lTestZipAttachmentId.ToString(), await Util.GetTokenAsync("superuser", "l3tm3in")); - Util.ValidateHTTPStatusCode(a, 204); - - - } - - - - /// - /// test no rights - /// - [Fact] - public async void NoRightsTest() - { - - MultipartFormDataContent formDataContent = new MultipartFormDataContent(); - - formDataContent.Add(new StringContent("2"), name: "AttachToObjectType"); - formDataContent.Add(new StringContent("1"), name: "AttachToObjectId"); - formDataContent.Add(new StringContent("Test:AttachmentUploadDownloadDeleteShouldWork"), name: "Notes"); - formDataContent.Add(new StringContent("[{\"name\":\"test.png\",\"lastModified\":1586900220990}]"), name: "FileData"); - - - StreamContent file1 = new StreamContent(File.OpenRead($"{Util.TEST_DATA_FOLDER}\\test.png")); - file1.Headers.ContentType = new MediaTypeHeaderValue("image/png"); - file1.Headers.ContentDisposition = new ContentDispositionHeaderValue("form-data"); - file1.Headers.ContentDisposition.FileName = "test.png"; - formDataContent.Add(file1); - - //ERROR CONDITION: BizAdminLimited user should not be able to attach a file to a widget - ApiResponse a = await Util.PostFormDataAsync("attachment", formDataContent, await Util.GetTokenAsync("BizAdminLimited")); - - //2004 unauthorized - Util.ValidateErrorCodeResponse(a, 2004, 403); - - } - - - /// - /// test not attachable - /// - [Fact] - public async void UnattachableTest() - { - MultipartFormDataContent formDataContent = new MultipartFormDataContent(); - - //Form data bizobject type and id - - //HERE IS THE ERROR CONDITION: LICENSE TYPE OBJECT WHICH IS UNATTACHABLE - formDataContent.Add(new StringContent("5"), name: "AttachToObjectType"); - formDataContent.Add(new StringContent("1"), name: "AttachToObjectId"); - - StreamContent file1 = new StreamContent(File.OpenRead($"{Util.TEST_DATA_FOLDER}\\test.png")); - file1.Headers.ContentType = new MediaTypeHeaderValue("image/png"); - file1.Headers.ContentDisposition = new ContentDispositionHeaderValue("form-data"); - file1.Headers.ContentDisposition.FileName = "test.png"; - formDataContent.Add(file1); - ApiResponse a = await Util.PostFormDataAsync("attachment", formDataContent, await Util.GetTokenAsync("InventoryFull")); - - //2203 unattachable object - Util.ValidateErrorCodeResponse(a, 2203, 400); - - } - - - /// - /// test bad object values - /// - [Fact] - public async void BadObject() - { - MultipartFormDataContent formDataContent = new MultipartFormDataContent(); - - //Form data like the bizobject type and id - formDataContent.Add(new StringContent("2"), name: "AttachToObjectType"); - - //HERE IS THE ERROR CONDITION, A NON EXISTENT ID VALUE FOR THE WIDGET - formDataContent.Add(new StringContent(long.MaxValue.ToString()), name: "AttachToObjectId");//non-existent widget - - StreamContent file1 = new StreamContent(File.OpenRead($"{Util.TEST_DATA_FOLDER}\\test.png")); - file1.Headers.ContentType = new MediaTypeHeaderValue("image/png"); - file1.Headers.ContentDisposition = new ContentDispositionHeaderValue("form-data"); - file1.Headers.ContentDisposition.FileName = "test.png"; - formDataContent.Add(file1); - ApiResponse a = await Util.PostFormDataAsync("attachment", formDataContent, await Util.GetTokenAsync("InventoryFull")); - - //2203 invalid attachment object - Util.ValidateErrorCodeResponse(a, 2203, 400); - - } - - - - - - - //================================================== - - }//eoc -}//eons +using System; +using Xunit; +using Newtonsoft.Json.Linq; +using FluentAssertions; +using System.Collections.Generic; +using System.Collections.Concurrent; +using System.Net.Http; +using System.Net.Http.Headers; +using System.IO; + +namespace raven_integration +{ + //https://stackoverflow.com/questions/17725882/testing-asp-net-web-api-multipart-form-data-file-upload + public class AttachmentTest + { + /// + /// test attach CRUD + /// + [Fact] + public async Task AttachmentUploadDownloadDeleteShouldWork() + { + + //Make a user just for this test so can deal with dl token properly + var UniqueName = Util.Uniquify("AttachmentUploadDownloadDeleteShouldWork"); + //CREATE + dynamic d = new JObject(); + d.name = UniqueName; + + d.active = true; + d.login = UniqueName; + d.password = UniqueName; + d.roles = 2;//bizadminfull needs widget rights + d.userType = 3;//non scheduleable + + //Required by form custom rules + d.notes = "notes"; + d.customFields = Util.UserRequiredCustomFieldsJsonString(); + + ApiResponse a = await Util.PostAsync("User", await Util.GetTokenAsync("superuser", "l3tm3in"), d.ToString()); + Util.ValidateDataReturnResponseOk(a); + long TestUserId=a.ObjectResponse["data"]["id"].Value(); + + d = new JObject(); + d.login = UniqueName; + d.password = UniqueName; + a = await Util.PostAsync("auth", null, d.ToString()); + string downloadToken = a.ObjectResponse["data"]["dlt"].Value(); + + ////////////////////////////////////////// + //// Upload the files + MultipartFormDataContent formDataContent = new MultipartFormDataContent(); + + //Form data like the bizobject type and id + formDataContent.Add(new StringContent("3"), name: "AttachToObjectType"); + formDataContent.Add(new StringContent(TestUserId.ToString()), name: "AttachToObjectId"); + formDataContent.Add(new StringContent("Test:AttachmentUploadDownloadDeleteShouldWork"), name: "Notes"); + formDataContent.Add(new StringContent("[{\"name\":\"test.zip\",\"lastModified\":1582822079618},{\"name\":\"test.png\",\"lastModified\":1586900220990}]"), name: "FileData"); + + //fileData in JSON stringify format which contains the actual last modified dates etc + //"[{\"name\":\"Client.csv\",\"lastModified\":1582822079618},{\"name\":\"wmi4fu06nrs41.jpg\",\"lastModified\":1586900220990}]" + //or if testing non-existant this is probably safe: long.MaxValue + + + StreamContent file1 = new StreamContent(File.OpenRead($"{Util.TEST_DATA_FOLDER}\\test.png")); + file1.Headers.ContentType = new MediaTypeHeaderValue("image/png"); + file1.Headers.ContentDisposition = new ContentDispositionHeaderValue("form-data"); + file1.Headers.ContentDisposition.FileName = "test.png"; + formDataContent.Add(file1); + StreamContent file2 = new StreamContent(File.OpenRead($"{Util.TEST_DATA_FOLDER}\\test.zip")); + file2.Headers.ContentType = new MediaTypeHeaderValue("application/zip"); + file2.Headers.ContentDisposition = new ContentDispositionHeaderValue("form-data"); + file2.Headers.ContentDisposition.FileName = "test.zip"; + formDataContent.Add(file2); + + //create via inventory full test user as attachments use the role of the object attaching to + a = await Util.PostFormDataAsync("attachment", formDataContent, await Util.GetTokenAsync("superuser", "l3tm3in")); + + + Util.ValidateDataReturnResponseOk(a); + + long lTestPngAttachmentId = a.ObjectResponse["data"][0]["id"].Value(); + long lTestZipAttachmentId = a.ObjectResponse["data"][1]["id"].Value(); + + //saw negative values on a db issue that I corrected (I think) + //Keeping these in case it arises again, if it does, see log, it's a db error with async issue of some kind + lTestPngAttachmentId.Should().BePositive(); + lTestZipAttachmentId.Should().BePositive(); + + ////////////////////////////////////////// + //// DOWNLOAD: Get the file attachment + + //now get the file https://rockfish.ayanova.com/api/rfcaseblob/download/248?t=9O2eDAAlZ0Wknj19SBK2iA + var dlresponse = await Util.DownloadFileAsync("attachment/Download/" + lTestZipAttachmentId.ToString() + "?t=" + downloadToken, null); + + //ensure it's the zip file we expected + dlresponse.Content.Headers.ContentDisposition.FileName.Should().Be("test.zip"); + dlresponse.Content.Headers.ContentLength.Should().BeGreaterThan(2000); + + + ////////////////////////////////////////// + //// DELETE: Delete the file attachments + a = await Util.DeleteAsync("attachment/" + lTestPngAttachmentId.ToString(), await Util.GetTokenAsync("superuser", "l3tm3in")); + Util.ValidateHTTPStatusCode(a, 204); + + a = await Util.DeleteAsync("attachment/" + lTestZipAttachmentId.ToString(), await Util.GetTokenAsync("superuser", "l3tm3in")); + Util.ValidateHTTPStatusCode(a, 204); + + + } + + + + /// + /// test no rights + /// + [Fact] + public async Task NoRightsTest() + { + + MultipartFormDataContent formDataContent = new MultipartFormDataContent(); + + formDataContent.Add(new StringContent("2"), name: "AttachToObjectType"); + formDataContent.Add(new StringContent("1"), name: "AttachToObjectId"); + formDataContent.Add(new StringContent("Test:AttachmentUploadDownloadDeleteShouldWork"), name: "Notes"); + formDataContent.Add(new StringContent("[{\"name\":\"test.png\",\"lastModified\":1586900220990}]"), name: "FileData"); + + + StreamContent file1 = new StreamContent(File.OpenRead($"{Util.TEST_DATA_FOLDER}\\test.png")); + file1.Headers.ContentType = new MediaTypeHeaderValue("image/png"); + file1.Headers.ContentDisposition = new ContentDispositionHeaderValue("form-data"); + file1.Headers.ContentDisposition.FileName = "test.png"; + formDataContent.Add(file1); + + //ERROR CONDITION: BizAdminLimited user should not be able to attach a file to a widget + ApiResponse a = await Util.PostFormDataAsync("attachment", formDataContent, await Util.GetTokenAsync("BizAdminLimited")); + + //2004 unauthorized + Util.ValidateErrorCodeResponse(a, 2004, 403); + + } + + + /// + /// test not attachable + /// + [Fact] + public async Task UnattachableTest() + { + MultipartFormDataContent formDataContent = new MultipartFormDataContent(); + + //Form data bizobject type and id + + //HERE IS THE ERROR CONDITION: LICENSE TYPE OBJECT WHICH IS UNATTACHABLE + formDataContent.Add(new StringContent("5"), name: "AttachToObjectType"); + formDataContent.Add(new StringContent("1"), name: "AttachToObjectId"); + + StreamContent file1 = new StreamContent(File.OpenRead($"{Util.TEST_DATA_FOLDER}\\test.png")); + file1.Headers.ContentType = new MediaTypeHeaderValue("image/png"); + file1.Headers.ContentDisposition = new ContentDispositionHeaderValue("form-data"); + file1.Headers.ContentDisposition.FileName = "test.png"; + formDataContent.Add(file1); + ApiResponse a = await Util.PostFormDataAsync("attachment", formDataContent, await Util.GetTokenAsync("InventoryFull")); + + //2203 unattachable object + Util.ValidateErrorCodeResponse(a, 2203, 400); + + } + + + /// + /// test bad object values + /// + [Fact] + public async Task BadObject() + { + MultipartFormDataContent formDataContent = new MultipartFormDataContent(); + + //Form data like the bizobject type and id + formDataContent.Add(new StringContent("2"), name: "AttachToObjectType"); + + //HERE IS THE ERROR CONDITION, A NON EXISTENT ID VALUE FOR THE WIDGET + formDataContent.Add(new StringContent(long.MaxValue.ToString()), name: "AttachToObjectId");//non-existent widget + + StreamContent file1 = new StreamContent(File.OpenRead($"{Util.TEST_DATA_FOLDER}\\test.png")); + file1.Headers.ContentType = new MediaTypeHeaderValue("image/png"); + file1.Headers.ContentDisposition = new ContentDispositionHeaderValue("form-data"); + file1.Headers.ContentDisposition.FileName = "test.png"; + formDataContent.Add(file1); + ApiResponse a = await Util.PostFormDataAsync("attachment", formDataContent, await Util.GetTokenAsync("InventoryFull")); + + //2203 invalid attachment object + Util.ValidateErrorCodeResponse(a, 2203, 400); + + } + + + + + + + //================================================== + + }//eoc +}//eons diff --git a/Authentication/Auth.cs b/Authentication/Auth.cs index b6e85ef..fe7180f 100644 --- a/Authentication/Auth.cs +++ b/Authentication/Auth.cs @@ -1,137 +1,137 @@ -using System; -using Xunit; -using Newtonsoft.Json.Linq; -using FluentAssertions; - -namespace raven_integration -{ - - public class auth - { - /// - /// - /// - [Fact] - public async void BadLoginShouldNotWork() - { - //Expect status code 401 and result: - // {{ - // "error": { - // "code": "2003", - // "message": "Authentication failed" - // } - // }} - - dynamic d = new JObject(); - d.login = "BOGUS"; - d.password = "ACCOUNT"; - ApiResponse a = await Util.PostAsync("auth", null, d.ToString()); - Util.ValidateErrorCodeResponse(a, 2003, 401); - } - - - - //NOTE: These tests are for Debug builds, they should still pass in a release build because none of the creds will work and it checks for 401 only - //but a true test of these JWT tokens is only in server debug mode - - /// - /// - /// - [Fact] - public async void JWTExpiredTokenShouldFail() - { - - ApiResponse a = await Util.GetAsync("build-mode", await Util.GetTokenAsync("superuser", "l3tm3in")); - var BuildMode = a.ObjectResponse["data"]["buildMode"].Value(); - if (BuildMode == "DEBUG") - { - a = await Util.GetAsync("translation/list", await Util.GetTokenAsync("INTEGRATION_TEST", "EXPIRED"));//lowest level test user because there are no limits on this route except to be authenticated - Util.ValidateHTTPStatusCode(a, 401); - } - } - - /// - /// - /// - [Fact] - public async void JWTWrongIssuerShouldFail() - { - ApiResponse a = await Util.GetAsync("build-mode", await Util.GetTokenAsync("superuser", "l3tm3in")); - var BuildMode = a.ObjectResponse["data"]["buildMode"].Value(); - if (BuildMode == "DEBUG") - { - a = await Util.GetAsync("translation/list", await Util.GetTokenAsync("INTEGRATION_TEST", "WRONG_ISSUER"));//lowest level test user because there are no limits on this route except to be authenticated - Util.ValidateHTTPStatusCode(a, 401); - } - } - - /// - /// - /// - [Fact] - public async void JWTNoAlgorithmShouldFail() - { - ApiResponse a = await Util.GetAsync("build-mode", await Util.GetTokenAsync("superuser", "l3tm3in")); - var BuildMode = a.ObjectResponse["data"]["buildMode"].Value(); - if (BuildMode == "DEBUG") - { - a = await Util.GetAsync("translation/list", await Util.GetTokenAsync("INTEGRATION_TEST", "NO_ALGORITHM")); - Util.ValidateHTTPStatusCode(a, 401); - } - } - - /// - /// - /// - [Fact] - public async void JWTBadSecretShouldFail() - { - ApiResponse a = await Util.GetAsync("build-mode", await Util.GetTokenAsync("superuser", "l3tm3in")); - var BuildMode = a.ObjectResponse["data"]["buildMode"].Value(); - if (BuildMode == "DEBUG") - { - a = await Util.GetAsync("translation/list", await Util.GetTokenAsync("INTEGRATION_TEST", "WRONG_SECRET")); - Util.ValidateHTTPStatusCode(a, 401); - } - } - - - /// - /// - /// - [Fact] - public async void JWTTruncatedSignatureShouldFail() - { - ApiResponse a = await Util.GetAsync("build-mode", await Util.GetTokenAsync("superuser", "l3tm3in")); - var BuildMode = a.ObjectResponse["data"]["buildMode"].Value(); - if (BuildMode == "DEBUG") - { - a = await Util.GetAsync("translation/list", await Util.GetTokenAsync("INTEGRATION_TEST", "TRUNCATED_SIGNATURE")); - Util.ValidateHTTPStatusCode(a, 401); - } - } - - - /// - /// - /// - [Fact] - public async void JWTTransposedSignatureShouldFail() - { - ApiResponse a = await Util.GetAsync("build-mode", await Util.GetTokenAsync("superuser", "l3tm3in")); - var BuildMode = a.ObjectResponse["data"]["buildMode"].Value(); - if (BuildMode == "DEBUG") - { - a = await Util.GetAsync("translation/list", await Util.GetTokenAsync("INTEGRATION_TEST", "TRANSPOSE_SIGNATURE")); - Util.ValidateHTTPStatusCode(a, 401); - } - } - - - - - //================================================== - - }//eoc -}//eons - +using System; +using Xunit; +using Newtonsoft.Json.Linq; +using FluentAssertions; + +namespace raven_integration +{ + + public class Auth + { + /// + /// + /// + [Fact] + public async Task BadLoginShouldNotWork() + { + //Expect status code 401 and result: + // {{ + // "error": { + // "code": "2003", + // "message": "Authentication failed" + // } + // }} + + dynamic d = new JObject(); + d.login = "BOGUS"; + d.password = "ACCOUNT"; + ApiResponse a = await Util.PostAsync("auth", null, d.ToString()); + Util.ValidateErrorCodeResponse(a, 2003, 401); + } + + + + //NOTE: These tests are for Debug builds, they should still pass in a release build because none of the creds will work and it checks for 401 only + //but a true test of these JWT tokens is only in server debug mode + + /// + /// + /// + [Fact] + public async Task JWTExpiredTokenShouldFail() + { + + ApiResponse a = await Util.GetAsync("build-mode", await Util.GetTokenAsync("superuser", "l3tm3in")); + var BuildMode = a.ObjectResponse["data"]["buildMode"].Value(); + if (BuildMode == "DEBUG") + { + a = await Util.GetAsync("translation/list", await Util.GetTokenAsync("INTEGRATION_TEST", "EXPIRED"));//lowest level test user because there are no limits on this route except to be authenticated + Util.ValidateHTTPStatusCode(a, 401); + } + } + + /// + /// + /// + [Fact] + public async Task JWTWrongIssuerShouldFail() + { + ApiResponse a = await Util.GetAsync("build-mode", await Util.GetTokenAsync("superuser", "l3tm3in")); + var BuildMode = a.ObjectResponse["data"]["buildMode"].Value(); + if (BuildMode == "DEBUG") + { + a = await Util.GetAsync("translation/list", await Util.GetTokenAsync("INTEGRATION_TEST", "WRONG_ISSUER"));//lowest level test user because there are no limits on this route except to be authenticated + Util.ValidateHTTPStatusCode(a, 401); + } + } + + /// + /// + /// + [Fact] + public async Task JWTNoAlgorithmShouldFail() + { + ApiResponse a = await Util.GetAsync("build-mode", await Util.GetTokenAsync("superuser", "l3tm3in")); + var BuildMode = a.ObjectResponse["data"]["buildMode"].Value(); + if (BuildMode == "DEBUG") + { + a = await Util.GetAsync("translation/list", await Util.GetTokenAsync("INTEGRATION_TEST", "NO_ALGORITHM")); + Util.ValidateHTTPStatusCode(a, 401); + } + } + + /// + /// + /// + [Fact] + public async Task JWTBadSecretShouldFail() + { + ApiResponse a = await Util.GetAsync("build-mode", await Util.GetTokenAsync("superuser", "l3tm3in")); + var BuildMode = a.ObjectResponse["data"]["buildMode"].Value(); + if (BuildMode == "DEBUG") + { + a = await Util.GetAsync("translation/list", await Util.GetTokenAsync("INTEGRATION_TEST", "WRONG_SECRET")); + Util.ValidateHTTPStatusCode(a, 401); + } + } + + + /// + /// + /// + [Fact] + public async Task JWTTruncatedSignatureShouldFail() + { + ApiResponse a = await Util.GetAsync("build-mode", await Util.GetTokenAsync("superuser", "l3tm3in")); + var BuildMode = a.ObjectResponse["data"]["buildMode"].Value(); + if (BuildMode == "DEBUG") + { + a = await Util.GetAsync("translation/list", await Util.GetTokenAsync("INTEGRATION_TEST", "TRUNCATED_SIGNATURE")); + Util.ValidateHTTPStatusCode(a, 401); + } + } + + + /// + /// + /// + [Fact] + public async Task JWTTransposedSignatureShouldFail() + { + ApiResponse a = await Util.GetAsync("build-mode", await Util.GetTokenAsync("superuser", "l3tm3in")); + var BuildMode = a.ObjectResponse["data"]["buildMode"].Value(); + if (BuildMode == "DEBUG") + { + a = await Util.GetAsync("translation/list", await Util.GetTokenAsync("INTEGRATION_TEST", "TRANSPOSE_SIGNATURE")); + Util.ValidateHTTPStatusCode(a, 401); + } + } + + + + + //================================================== + + }//eoc +}//eons + diff --git a/DataList/DataListFiltering.cs b/DataList/DataListFiltering.cs index ad394c6..a37194c 100644 --- a/DataList/DataListFiltering.cs +++ b/DataList/DataListFiltering.cs @@ -1,3999 +1,3999 @@ -using System; -using Xunit; -using Newtonsoft.Json.Linq; -using FluentAssertions; -using System.Collections.Generic; -using System.Collections.Concurrent; - -namespace raven_integration -{ - - - /* - - EVERY TYPE, EVERY OP - - Using the widget object test all filtering options - for all data types, all operation types - - This is the supertest to always confirm the filtering code is working as expected. - - -BUGBUG: Server takes into account user's time zone offset when filtering lists by date range but here the local test runner just uses the windows system offset instead of the defined offset in the User account at the server -Fix: Since seeder uses same time zone for all users it generates then can simply fetch one single users' tz offset and use that centerally to calculate a relative now and relative today -same as the server does but in a central location here for all tests to use. - - */ - - public class DataListFiltering - { - - - - - - - /////////////////////////////////////////////////////////////////////////////// - //DATE - // - - #region DATE FILTER TESTS - - // public const string TokenYesterday = "{[yesterday]}"; - // public const string TokenToday = "{[today]}"; - // public const string TokenTomorrow = "{[tomorrow]}"; - // public const string TokenLastWeek = "{[lastweek]}"; - // public const string TokenThisWeek = "{[thisweek]}"; - // public const string TokenNextWeek = "{[nextweek]}"; - // public const string TokenLastMonth = "{[lastmonth]}"; - // public const string TokenThisMonth = "{[thismonth]}"; - // public const string TokenNextMonth = "{[nextmonth]}"; - // public const string TokenFourteenDayWindow = "{[14daywindow]}"; - // public const string TokenPast = "{[past]}"; - // public const string TokenFuture = "{[future]}"; - // public const string TokenLastYear = "{[lastyear]}"; - // public const string TokenThisYear = "{[thisyear]}"; - // public const string TokenInTheLast3Months = "{[last3months]}"; - // public const string TokenInTheLast6Months = "{[last6months]}"; - // public const string TokenInTheLastYear = "{[lastcalendaryear]}"; - - // //More business time frames - - // public const string TokenYearToDate = "{[yeartodate]}"; - - // public const string TokenPast90Days = "{[past90days]}"; - // public const string TokenPast30Days = "{[past30days]}"; - // public const string TokenPast24Hours = "{[past24hours]}"; - - // //Months THIS year - // public const string TokenJanuary = "{[january]}"; - // public const string TokenFebruary = "{[february]}"; - // public const string TokenMarch = "{[march]}"; - // public const string TokenApril = "{[april]}"; - // public const string TokenMay = "{[may]}"; - // public const string TokenJune = "{[june]}"; - // public const string TokenJuly = "{[july]}"; - // public const string TokenAugust = "{[august]}"; - // public const string TokenSeptember = "{[september]}"; - // public const string TokenOctober = "{[october]}"; - // public const string TokenNovember = "{[november]}"; - // public const string TokenDecember = "{[december]}"; - - - #region DATE REGULAR FILTERS - - /// - /// - /// - [Fact] - public async void DateOpEqualityFilterWorks() - { - - var WidgetNameStart = "DateOpEqualityFilterWorks"; - - long IncludedWidgetId = 0; - long ExcludedWidgetId = 0; - - //CREATE TEST WIDGETS - - //included widget - dynamic w = new JObject(); - w.name = Util.Uniquify(WidgetNameStart); - w.notes = "blah"; - w.customFields = Util.WidgetRequiredCustomFieldsJsonString(); - w.startDate = new DateTime(1968, 3, 12, 10, 0, 0).ToOffsetAdjustedUniversalTime(); - w.endDate = new DateTime(1968, 3, 12, 11, 0, 0).ToOffsetAdjustedUniversalTime(); - w.usertype = 1; - - ApiResponse a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w.ToString()); - Util.ValidateDataReturnResponseOk(a); - IncludedWidgetId = a.ObjectResponse["data"]["id"].Value(); - - //Excluded widget - w.name = Util.Uniquify(WidgetNameStart); - w.startDate = new DateTime(1968, 3, 10, 10, 0, 0).ToOffsetAdjustedUniversalTime(); - w.endDate = new DateTime(1968, 3, 10, 11, 0, 0).ToOffsetAdjustedUniversalTime(); - - a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w.ToString()); - Util.ValidateDataReturnResponseOk(a); - ExcludedWidgetId = a.ObjectResponse["data"]["id"].Value(); - - //CREATE LISTVIEW - - dynamic dListView = new JArray(); - - - //name starts with filter to constrict to widgets that this test block created only - - dListView.Add(Util.BuildSimpleFilterDataListViewColumn("widgetname", Util.OpStartsWith, WidgetNameStart)); - - //## INCLUSIVE FILTER - // dynamic FilterItem = new JObject(); - // FilterItem.fld = "widgetstartdate"; - // FilterItem.op = Util.OpEquality; - // FilterItem.value = new DateTime(1968, 3, 12, 10, 0, 0).ToOffsetAdjustedUniversalTime(); - // dListView.Add(Util.BuildSimpleFilterDataListViewColumn("XXXX", Util.XXXX, XXXX)); - dListView.Add(Util.BuildSimpleFilterDataListViewColumn("widgetstartdate", Util.OpEquality, new DateTime(1968, 3, 12, 10, 0, 0).ToOffsetAdjustedUniversalTime())); - - - //FETCH DATALIST - a = await Util.PostAsync($"data-list", await Util.GetTokenAsync("superuser", "l3tm3in"), Util.BuildDataListRequestEx(dListView)); - Util.ValidateDataReturnResponseOk(a); - Util.ValidateHTTPStatusCode(a, 200); - - //assert contains at least this test record - ((JArray)a.ObjectResponse["data"]).Count.Should().BeGreaterThan(0); - var v = ((JArray)a.ObjectResponse["data"]); - List IDInResultList = new List(); - int InclusiveMatchCount = 0; - int ExclusiveMatchCount = 0; - - foreach (JArray ja in v) - { - JObject o = ja[0] as JObject; - - if (IncludedWidgetId == o["i"].Value()) - InclusiveMatchCount++; - if (ExcludedWidgetId == o["i"].Value()) - ExclusiveMatchCount++; - } - - InclusiveMatchCount.Should().BeGreaterOrEqualTo(1); - ExclusiveMatchCount.Should().Be(0); - - //DELETE WIDGETS - a = await Util.DeleteAsync("widget/" + IncludedWidgetId.ToString(), await Util.GetTokenAsync("BizAdminFull")); - Util.ValidateHTTPStatusCode(a, 204); - - a = await Util.DeleteAsync("widget/" + ExcludedWidgetId.ToString(), await Util.GetTokenAsync("BizAdminFull")); - Util.ValidateHTTPStatusCode(a, 204); - - - } - - - /// - /// - /// - [Fact] - public async void DateOpGreaterThanFilterWorks() - { - - var WidgetNameStart = "DateOpGreaterThanFilterWorks"; - - long IncludedWidgetId = 0; - long ExcludedWidgetId = 0; - - //CREATE TEST WIDGETS - - //included widget - dynamic w = new JObject(); - w.name = Util.Uniquify(WidgetNameStart); - w.notes = "blah"; - w.customFields = Util.WidgetRequiredCustomFieldsJsonString(); - w.startDate = new DateTime(1970, 3, 12, 10, 0, 0).ToOffsetAdjustedUniversalTime(); - w.endDate = new DateTime(1970, 3, 12, 11, 0, 0).ToOffsetAdjustedUniversalTime(); - w.usertype = 1; - - ApiResponse a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w.ToString()); - Util.ValidateDataReturnResponseOk(a); - IncludedWidgetId = a.ObjectResponse["data"]["id"].Value(); - - //Excluded widget - w.name = Util.Uniquify(WidgetNameStart); - w.startDate = new DateTime(1968, 3, 10, 10, 0, 0).ToOffsetAdjustedUniversalTime(); - w.endDate = new DateTime(1968, 3, 10, 11, 0, 0).ToOffsetAdjustedUniversalTime(); - - a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w.ToString()); - Util.ValidateDataReturnResponseOk(a); - ExcludedWidgetId = a.ObjectResponse["data"]["id"].Value(); - - //CREATE LISTVIEW - dynamic dListView = new JArray(); - - //name starts with filter to constrict to widgets that this test block created only - - dListView.Add(Util.BuildSimpleFilterDataListViewColumn("widgetname", Util.OpStartsWith, WidgetNameStart)); - - //## INCLUSIVE FILTER - // dynamic FilterItem = new JObject(); - // FilterItem.fld = "widgetstartdate"; - // FilterItem.op = Util.OpGreaterThan; - // FilterItem.value = new DateTime(1970, 3, 12, 9, 0, 0).ToOffsetAdjustedUniversalTime(); - // dListView.Add(Util.BuildSimpleFilterDataListViewColumn("XXXX", Util.XXXX, XXXX)); - dListView.Add(Util.BuildSimpleFilterDataListViewColumn("widgetstartdate", Util.OpGreaterThan, new DateTime(1970, 3, 12, 9, 0, 0).ToOffsetAdjustedUniversalTime())); - - - //FETCH DATALIST - a = await Util.PostAsync($"data-list", await Util.GetTokenAsync("superuser", "l3tm3in"), Util.BuildDataListRequestEx(dListView)); - Util.ValidateDataReturnResponseOk(a); - Util.ValidateHTTPStatusCode(a, 200); - - //assert contains at least this test record - ((JArray)a.ObjectResponse["data"]).Count.Should().BeGreaterThan(0); - var v = ((JArray)a.ObjectResponse["data"]); - List IDInResultList = new List(); - int InclusiveMatchCount = 0; - int ExclusiveMatchCount = 0; - - foreach (JArray ja in v) - { - JObject o = ja[0] as JObject; - - if (IncludedWidgetId == o["i"].Value()) - InclusiveMatchCount++; - if (ExcludedWidgetId == o["i"].Value()) - ExclusiveMatchCount++; - } - - InclusiveMatchCount.Should().BeGreaterOrEqualTo(1); - ExclusiveMatchCount.Should().Be(0); - - //DELETE WIDGETS - a = await Util.DeleteAsync("widget/" + IncludedWidgetId.ToString(), await Util.GetTokenAsync("BizAdminFull")); - Util.ValidateHTTPStatusCode(a, 204); - - a = await Util.DeleteAsync("widget/" + ExcludedWidgetId.ToString(), await Util.GetTokenAsync("BizAdminFull")); - Util.ValidateHTTPStatusCode(a, 204); - } - - - - /// - /// - /// - [Fact] - public async void DateOpGreaterThanOrEqualToFilterWorks() - { - - var WidgetNameStart = "DateOpGreaterThanOrEqualToFilterWorks"; - - long IncludedWidgetId = 0; - long ExcludedWidgetId = 0; - - //CREATE TEST WIDGETS - - //included widget - dynamic w = new JObject(); - w.name = Util.Uniquify(WidgetNameStart); - w.notes = "blah"; - w.customFields = Util.WidgetRequiredCustomFieldsJsonString(); - w.startDate = new DateTime(1970, 3, 12, 10, 0, 0).ToOffsetAdjustedUniversalTime(); - w.endDate = new DateTime(1970, 3, 12, 11, 0, 0).ToOffsetAdjustedUniversalTime(); - w.usertype = 1; - - ApiResponse a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w.ToString()); - Util.ValidateDataReturnResponseOk(a); - IncludedWidgetId = a.ObjectResponse["data"]["id"].Value(); - - //Excluded widget - w.name = Util.Uniquify(WidgetNameStart); - w.startDate = new DateTime(1968, 3, 10, 10, 0, 0).ToOffsetAdjustedUniversalTime(); - w.endDate = new DateTime(1968, 3, 10, 11, 0, 0).ToOffsetAdjustedUniversalTime(); - - a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w.ToString()); - Util.ValidateDataReturnResponseOk(a); - ExcludedWidgetId = a.ObjectResponse["data"]["id"].Value(); - - //CREATE LISTVIEW - - dynamic dListView = new JArray(); - - //name starts with filter to constrict to widgets that this test block created only - - dListView.Add(Util.BuildSimpleFilterDataListViewColumn("widgetname", Util.OpStartsWith, WidgetNameStart)); - - //## INCLUSIVE FILTER - // dynamic FilterItem = new JObject(); - // FilterItem.fld = "widgetstartdate"; - // FilterItem.op = Util.OpGreaterThanOrEqualTo; - // FilterItem.value = new DateTime(1970, 3, 12, 10, 0, 0).ToOffsetAdjustedUniversalTime(); - // dListView.Add(Util.BuildSimpleFilterDataListViewColumn("XXXX", Util.XXXX, XXXX)); - dListView.Add(Util.BuildSimpleFilterDataListViewColumn("widgetstartdate", Util.OpGreaterThanOrEqualTo, new DateTime(1970, 3, 12, 10, 0, 0).ToOffsetAdjustedUniversalTime())); - - - - //FETCH DATALIST - a = await Util.PostAsync($"data-list", await Util.GetTokenAsync("superuser", "l3tm3in"), Util.BuildDataListRequestEx(dListView)); - Util.ValidateDataReturnResponseOk(a); - Util.ValidateHTTPStatusCode(a, 200); - - //assert contains at least this test record - ((JArray)a.ObjectResponse["data"]).Count.Should().BeGreaterThan(0); - var v = ((JArray)a.ObjectResponse["data"]); - List IDInResultList = new List(); - int InclusiveMatchCount = 0; - int ExclusiveMatchCount = 0; - - foreach (JArray ja in v) - { - JObject o = ja[0] as JObject; - - if (IncludedWidgetId == o["i"].Value()) - InclusiveMatchCount++; - if (ExcludedWidgetId == o["i"].Value()) - ExclusiveMatchCount++; - } - - InclusiveMatchCount.Should().BeGreaterOrEqualTo(1); - ExclusiveMatchCount.Should().Be(0); - - //DELETE WIDGETS - a = await Util.DeleteAsync("widget/" + IncludedWidgetId.ToString(), await Util.GetTokenAsync("BizAdminFull")); - Util.ValidateHTTPStatusCode(a, 204); - - a = await Util.DeleteAsync("widget/" + ExcludedWidgetId.ToString(), await Util.GetTokenAsync("BizAdminFull")); - Util.ValidateHTTPStatusCode(a, 204); - } - - - /// - /// - /// - [Fact] - public async void DateOpLessThanFilterWorks() - { - - var WidgetNameStart = "DateOpLessThanFilterWorks"; - - long IncludedWidgetId = 0; - long ExcludedWidgetId = 0; - - //CREATE TEST WIDGETS - - //included widget - dynamic w = new JObject(); - w.name = Util.Uniquify(WidgetNameStart); - w.notes = "blah"; - w.customFields = Util.WidgetRequiredCustomFieldsJsonString(); - w.startDate = new DateTime(1970, 3, 12, 10, 0, 0).ToOffsetAdjustedUniversalTime(); - w.endDate = new DateTime(1970, 3, 12, 11, 0, 0).ToOffsetAdjustedUniversalTime(); - w.usertype = 1; - - ApiResponse a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w.ToString()); - Util.ValidateDataReturnResponseOk(a); - IncludedWidgetId = a.ObjectResponse["data"]["id"].Value(); - - //Excluded widget - w.name = Util.Uniquify(WidgetNameStart); - w.startDate = new DateTime(1970, 4, 10, 10, 0, 0).ToOffsetAdjustedUniversalTime(); - w.endDate = new DateTime(1970, 4, 10, 11, 0, 0).ToOffsetAdjustedUniversalTime(); - - a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w.ToString()); - Util.ValidateDataReturnResponseOk(a); - ExcludedWidgetId = a.ObjectResponse["data"]["id"].Value(); - - //CREATE LISTVIEW - dynamic dListView = new JArray(); - - //name starts with filter to constrict to widgets that this test block created only - dListView.Add(Util.BuildSimpleFilterDataListViewColumn("widgetname", Util.OpStartsWith, WidgetNameStart)); - - //## INCLUSIVE FILTER - // dynamic FilterItem = new JObject(); - // FilterItem.fld = "widgetstartdate"; - // FilterItem.op = Util.OpLessThan; - // FilterItem.value = new DateTime(1970, 3, 12, 11, 0, 0).ToOffsetAdjustedUniversalTime(); - dListView.Add(Util.BuildSimpleFilterDataListViewColumn("widgetstartdate", Util.OpLessThan, new DateTime(1970, 3, 12, 11, 0, 0).ToOffsetAdjustedUniversalTime())); - - - //FETCH DATALIST - a = await Util.PostAsync($"data-list", await Util.GetTokenAsync("superuser", "l3tm3in"), Util.BuildDataListRequestEx(dListView)); - Util.ValidateDataReturnResponseOk(a); - Util.ValidateHTTPStatusCode(a, 200); - - //assert contains at least this test record - ((JArray)a.ObjectResponse["data"]).Count.Should().BeGreaterThan(0); - var v = ((JArray)a.ObjectResponse["data"]); - List IDInResultList = new List(); - int InclusiveMatchCount = 0; - int ExclusiveMatchCount = 0; - foreach (JArray ja in v) - { - JObject o = ja[0] as JObject; - - if (IncludedWidgetId == o["i"].Value()) - InclusiveMatchCount++; - if (ExcludedWidgetId == o["i"].Value()) - ExclusiveMatchCount++; - } - - InclusiveMatchCount.Should().BeGreaterOrEqualTo(1); - ExclusiveMatchCount.Should().Be(0); - - //DELETE WIDGETS - a = await Util.DeleteAsync("widget/" + IncludedWidgetId.ToString(), await Util.GetTokenAsync("BizAdminFull")); - Util.ValidateHTTPStatusCode(a, 204); - - a = await Util.DeleteAsync("widget/" + ExcludedWidgetId.ToString(), await Util.GetTokenAsync("BizAdminFull")); - Util.ValidateHTTPStatusCode(a, 204); - } - - - - /// - /// - /// - [Fact] - public async void DateOpLessThanOrEqualToFilterWorks() - { - - var WidgetNameStart = "DateOpLessThanOrEqualToFilterWorks"; - - long IncludedWidgetId = 0; - long ExcludedWidgetId = 0; - - //CREATE TEST WIDGETS - - //included widget - dynamic w = new JObject(); - w.name = Util.Uniquify(WidgetNameStart); - w.notes = "blah"; - w.customFields = Util.WidgetRequiredCustomFieldsJsonString(); - w.startDate = new DateTime(1970, 3, 12, 10, 0, 0).ToOffsetAdjustedUniversalTime(); - w.endDate = new DateTime(1970, 3, 12, 11, 0, 0).ToOffsetAdjustedUniversalTime(); - w.usertype = 1; - - ApiResponse a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w.ToString()); - Util.ValidateDataReturnResponseOk(a); - IncludedWidgetId = a.ObjectResponse["data"]["id"].Value(); - - //Excluded widget - w.name = Util.Uniquify(WidgetNameStart); - w.startDate = new DateTime(1970, 4, 10, 10, 0, 0).ToOffsetAdjustedUniversalTime(); - w.endDate = new DateTime(1970, 4, 10, 11, 0, 0).ToOffsetAdjustedUniversalTime(); - - a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w.ToString()); - Util.ValidateDataReturnResponseOk(a); - ExcludedWidgetId = a.ObjectResponse["data"]["id"].Value(); - - //CREATE LISTVIEW - dynamic dListView = new JArray(); - - //name starts with filter to constrict to widgets that this test block created only - dListView.Add(Util.BuildSimpleFilterDataListViewColumn("widgetname", Util.OpStartsWith, WidgetNameStart)); - - //## INCLUSIVE FILTER - // dynamic FilterItem = new JObject(); - // FilterItem.fld = "widgetstartdate"; - // FilterItem.op = Util.OpLessThanOrEqualTo; - // FilterItem.value = new DateTime(1970, 3, 12, 10, 0, 0).ToOffsetAdjustedUniversalTime(); - dListView.Add(Util.BuildSimpleFilterDataListViewColumn("widgetstartdate", Util.OpLessThanOrEqualTo, new DateTime(1970, 3, 12, 10, 0, 0).ToOffsetAdjustedUniversalTime())); - //FETCH DATALIST - a = await Util.PostAsync($"data-list", await Util.GetTokenAsync("superuser", "l3tm3in"), Util.BuildDataListRequestEx(dListView)); - Util.ValidateDataReturnResponseOk(a); - Util.ValidateHTTPStatusCode(a, 200); - - //assert contains at least this test record - ((JArray)a.ObjectResponse["data"]).Count.Should().BeGreaterThan(0); - var v = ((JArray)a.ObjectResponse["data"]); - List IDInResultList = new List(); - int InclusiveMatchCount = 0; - int ExclusiveMatchCount = 0; - foreach (JArray ja in v) - { - JObject o = ja[0] as JObject; - - if (IncludedWidgetId == o["i"].Value()) - InclusiveMatchCount++; - if (ExcludedWidgetId == o["i"].Value()) - ExclusiveMatchCount++; - } - - InclusiveMatchCount.Should().BeGreaterOrEqualTo(1); - ExclusiveMatchCount.Should().Be(0); - - //DELETE WIDGETS - a = await Util.DeleteAsync("widget/" + IncludedWidgetId.ToString(), await Util.GetTokenAsync("BizAdminFull")); - Util.ValidateHTTPStatusCode(a, 204); - - a = await Util.DeleteAsync("widget/" + ExcludedWidgetId.ToString(), await Util.GetTokenAsync("BizAdminFull")); - Util.ValidateHTTPStatusCode(a, 204); - } - - - - /// - /// - /// - [Fact] - public async void DateOpNotEqualToFilterWorks() - { - - var WidgetNameStart = "DateOpNotEqualToFilterWorks"; - - long IncludedWidgetId = 0; - long ExcludedWidgetId = 0; - - //CREATE TEST WIDGETS - - //included widget - dynamic w = new JObject(); - w.name = Util.Uniquify(WidgetNameStart); - w.notes = "blah"; - w.customFields = Util.WidgetRequiredCustomFieldsJsonString(); - w.startDate = new DateTime(1970, 3, 12, 10, 0, 0).ToOffsetAdjustedUniversalTime(); - w.endDate = new DateTime(1970, 3, 12, 11, 0, 0).ToOffsetAdjustedUniversalTime(); - w.usertype = 1; - - ApiResponse a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w.ToString()); - Util.ValidateDataReturnResponseOk(a); - IncludedWidgetId = a.ObjectResponse["data"]["id"].Value(); - - //Excluded widget - w.name = Util.Uniquify(WidgetNameStart); - w.startDate = new DateTime(1970, 4, 10, 10, 0, 0).ToOffsetAdjustedUniversalTime(); - w.endDate = new DateTime(1970, 4, 10, 11, 0, 0).ToOffsetAdjustedUniversalTime(); - - a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w.ToString()); - Util.ValidateDataReturnResponseOk(a); - ExcludedWidgetId = a.ObjectResponse["data"]["id"].Value(); - - //CREATE LISTVIEW - dynamic dListView = new JArray(); - - //name starts with filter to constrict to widgets that this test block created only - dListView.Add(Util.BuildSimpleFilterDataListViewColumn("widgetname", Util.OpStartsWith, WidgetNameStart)); - - //## INCLUSIVE FILTER - // dynamic FilterItem = new JObject(); - // FilterItem.fld = "widgetstartdate"; - // FilterItem.op = Util.OpNotEqual; - // FilterItem.value = new DateTime(1970, 4, 10, 10, 0, 0).ToOffsetAdjustedUniversalTime(); - dListView.Add(Util.BuildSimpleFilterDataListViewColumn("widgetstartdate", Util.OpNotEqual, new DateTime(1970, 4, 10, 10, 0, 0).ToOffsetAdjustedUniversalTime())); - //FETCH DATALIST - a = await Util.PostAsync($"data-list", await Util.GetTokenAsync("superuser", "l3tm3in"), Util.BuildDataListRequestEx(dListView)); - Util.ValidateDataReturnResponseOk(a); - Util.ValidateHTTPStatusCode(a, 200); - - //assert contains at least this test record - ((JArray)a.ObjectResponse["data"]).Count.Should().BeGreaterThan(0); - var v = ((JArray)a.ObjectResponse["data"]); - List IDInResultList = new List(); - int InclusiveMatchCount = 0; - int ExclusiveMatchCount = 0; - foreach (JArray ja in v) - { - JObject o = ja[0] as JObject; - - if (IncludedWidgetId == o["i"].Value()) - InclusiveMatchCount++; - if (ExcludedWidgetId == o["i"].Value()) - ExclusiveMatchCount++; - } - - InclusiveMatchCount.Should().BeGreaterOrEqualTo(1); - ExclusiveMatchCount.Should().Be(0); - - //DELETE WIDGETS - a = await Util.DeleteAsync("widget/" + IncludedWidgetId.ToString(), await Util.GetTokenAsync("BizAdminFull")); - Util.ValidateHTTPStatusCode(a, 204); - - a = await Util.DeleteAsync("widget/" + ExcludedWidgetId.ToString(), await Util.GetTokenAsync("BizAdminFull")); - Util.ValidateHTTPStatusCode(a, 204); - } - - - - /// - /// - /// - [Fact] - public async void DateOpBetweenFilterWorks() - { - - var WidgetNameStart = "DateOpBetweenFilterWorks"; - - long IncludedWidgetId = 0; - long ExcludedWidgetId = 0; - - //CREATE TEST WIDGETS - - //included widget - dynamic w = new JObject(); - w.name = Util.Uniquify(WidgetNameStart); - w.notes = "blah"; - w.customFields = Util.WidgetRequiredCustomFieldsJsonString(); - w.startDate = new DateTime(2019, 3, 12, 10, 0, 0).ToOffsetAdjustedUniversalTime(); - w.endDate = new DateTime(2019, 3, 12, 11, 0, 0).ToOffsetAdjustedUniversalTime(); - w.usertype = 1; - - ApiResponse a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w.ToString()); - Util.ValidateDataReturnResponseOk(a); - IncludedWidgetId = a.ObjectResponse["data"]["id"].Value(); - - //Excluded widget - w.name = Util.Uniquify(WidgetNameStart); - w.startDate = new DateTime(2019, 3, 12, 8, 0, 0).ToOffsetAdjustedUniversalTime(); - w.endDate = new DateTime(2019, 3, 12, 9, 0, 0).ToOffsetAdjustedUniversalTime(); - - a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w.ToString()); - Util.ValidateDataReturnResponseOk(a); - ExcludedWidgetId = a.ObjectResponse["data"]["id"].Value(); - - //CREATE LISTVIEW - - dynamic dListView = new JArray(); - - //name starts with filter to constrict to widgets that this test block created only - dListView.Add(Util.BuildSimpleFilterDataListViewColumn("widgetname", Util.OpStartsWith, WidgetNameStart)); - - //## INCLUSIVE FILTER - // dynamic FilterItem = new JObject(); - // FilterItem.fld = "widgetstartdate"; - // FilterItem.op = Util.OpGreaterThanOrEqualTo; - // FilterItem.value = new DateTime(2019, 3, 12, 10, 0, 0).ToOffsetAdjustedUniversalTime(); - // dListView.Add(Util.BuildSimpleFilterDataListViewColumn("widgetstartdate", Util.OpGreaterThanOrEqualTo, new DateTime(2019, 3, 12, 10, 0, 0).ToOffsetAdjustedUniversalTime())); - - - // dynamic FilterItem2 = new JObject(); - // FilterItem2.fld = "widgetstartdate"; - // FilterItem2.op = Util.OpLessThanOrEqualTo; - // FilterItem2.value = new DateTime(2019, 3, 12, 11, 0, 0).ToOffsetAdjustedUniversalTime(); - // dListView.Add(FilterItem2); - - //Build multiple condition filter (not handled by util method) - dynamic d = new JObject(); - d.fld = "widgetstartdate"; - - - dynamic filter = new JObject(); - dynamic items = new JArray(); - - dynamic fitem = new JObject(); - fitem.op = Util.OpGreaterThanOrEqualTo; - fitem.value = new DateTime(2019, 3, 12, 10, 0, 0).ToOffsetAdjustedUniversalTime(); - items.Add(fitem); - - fitem = new JObject(); - fitem.op = Util.OpLessThanOrEqualTo; - fitem.value = new DateTime(2019, 3, 12, 11, 0, 0).ToOffsetAdjustedUniversalTime(); - items.Add(fitem); - - - filter.items = items; - d.filter = filter; - - dListView.Add(d); - - - //FETCH DATALIST - a = await Util.PostAsync($"data-list", await Util.GetTokenAsync("superuser", "l3tm3in"), Util.BuildDataListRequestEx(dListView)); - Util.ValidateDataReturnResponseOk(a); - Util.ValidateHTTPStatusCode(a, 200); - - //assert contains at least this test record - ((JArray)a.ObjectResponse["data"]).Count.Should().BeGreaterThan(0); - var v = ((JArray)a.ObjectResponse["data"]); - List IDInResultList = new List(); - int InclusiveMatchCount = 0; - int ExclusiveMatchCount = 0; - - foreach (JArray ja in v) - { - JObject o = ja[0] as JObject; - - if (IncludedWidgetId == o["i"].Value()) - InclusiveMatchCount++; - if (ExcludedWidgetId == o["i"].Value()) - ExclusiveMatchCount++; - } - - InclusiveMatchCount.Should().BeGreaterOrEqualTo(1); - ExclusiveMatchCount.Should().Be(0); - - //DELETE WIDGETS - a = await Util.DeleteAsync("widget/" + IncludedWidgetId.ToString(), await Util.GetTokenAsync("BizAdminFull")); - Util.ValidateHTTPStatusCode(a, 204); - - a = await Util.DeleteAsync("widget/" + ExcludedWidgetId.ToString(), await Util.GetTokenAsync("BizAdminFull")); - Util.ValidateHTTPStatusCode(a, 204); - - } - - /* - RELATIVE TOKEN EXAMPLE: - - public const string TokenYesterday = "{[yesterday]}"; - public const string TokenToday = "{[today]}"; - public const string TokenTomorrow = "{[tomorrow]}"; - public const string TokenLastWeek = "{[lastweek]}"; - public const string TokenThisWeek = "{[thisweek]}"; - public const string TokenNextWeek = "{[nextweek]}"; - public const string TokenLastMonth = "{[lastmonth]}"; - public const string TokenThisMonth = "{[thismonth]}"; - public const string TokenNextMonth = "{[nextmonth]}"; - public const string TokenFourteenDayWindow = "{[14daywindow]}"; - public const string TokenPast = "{[past]}"; - public const string TokenFuture = "{[future]}"; - public const string TokenLastYear = "{[lastyear]}"; - public const string TokenThisYear = "{[thisyear]}"; - public const string TokenInTheLast3Months = "{[last3months]}"; - public const string TokenInTheLast6Months = "{[last6months]}"; - public const string TokenInTheLastYear = "{[lastcalendaryear]}"; - - //More business time frames - - public const string TokenYearToDate = "{[yeartodate]}"; - - public const string TokenPast90Days = "{[past90days]}"; - public const string TokenPast30Days = "{[past30days]}"; - public const string TokenPast24Hours = "{[past24hours]}"; - - //Months THIS year - public const string TokenJanuary = "{[january]}"; - public const string TokenFebruary = "{[february]}"; - public const string TokenMarch = "{[march]}"; - public const string TokenApril = "{[april]}"; - public const string TokenMay = "{[may]}"; - public const string TokenJune = "{[june]}"; - public const string TokenJuly = "{[july]}"; - public const string TokenAugust = "{[august]}"; - public const string TokenSeptember = "{[september]}"; - public const string TokenOctober = "{[october]}"; - public const string TokenNovember = "{[november]}"; - public const string TokenDecember = "{[december]}"; - - /// - /// - /// - [Fact] - public async void DateTokenYesterdayFilterWorks() - { - - var WidgetNameStart = "DateTokenYesterdayFilterWorks"; - - long IncludedWidgetId = 0; - long ExcludedWidgetId = 0; - - //CREATE TEST WIDGETS - - //included widget - dynamic w = new JObject(); - w.name = Util.Uniquify(WidgetNameStart); - w.notes = "blah"; - w.customFields = Util.WidgetRequiredCustomFieldsJsonString(); - w.startDate = DateTime.UtcNow.AddDays(-1); - w.endDate = DateTime.UtcNow.AddHours(1).AddDays(-1); - - ApiResponse a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w.ToString()); - Util.ValidateDataReturnResponseOk(a); - IncludedWidgetId = a.ObjectResponse["data"]["id"].Value(); - - //Excluded widget - w.name = Util.Uniquify(WidgetNameStart); - w.startDate = DateTime.UtcNow; - w.endDate = DateTime.UtcNow.AddHours(1); - - a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w.ToString()); - Util.ValidateDataReturnResponseOk(a); - ExcludedWidgetId = a.ObjectResponse["data"]["id"].Value(); - - //CREATE LISTVIEW - dynamic d = new JObject(); - d.name = Util.Uniquify(WidgetNameStart); - - d["public"] = true; - d.listKey = "TestWidgetDataList"; - - dynamic dListView = new JArray(); - - //name starts with filter to constrict to widgets that this test block created only - dListView.Add(Util.BuildSimpleFilterDataListViewColumn("widgetname", Util.OpStartsWith, WidgetNameStart)); - - //## INCLUSIVE FILTER - dynamic FilterItem = new JObject(); - FilterItem.fld = "widgetstartdate"; - FilterItem.op = Util.OpEquality; - FilterItem.value = TokenYesterday; - dListView.Add(Util.BuildSimpleFilterDataListViewColumn("XXXX", Util.XXXX, XXXX)); - - - - a = await Util, await Util.GetTokenAsync("BizAdminFull"), d.ToString()); - Util.ValidateDataReturnResponseOk(a); - - long DataFilterId = a.ObjectResponse["data"]["id"].Value(); - - //FETCH DATALIST - a = await Util.PostAsync($"data-list", await Util.GetTokenAsync("superuser", "l3tm3in"), Util.BuildDataListRequestEx(dListView)); - Util.ValidateDataReturnResponseOk(a); - Util.ValidateHTTPStatusCode(a, 200); - - //assert contains at least this test record - ((JArray)a.ObjectResponse["data"]).Count.Should().BeGreaterThan(0); - var v = ((JArray)a.ObjectResponse["data"]); - List IDInResultList = new List(); - int InclusiveMatchCount = 0; - int ExclusiveMatchCount = 0; - foreach (JArray ja in v) - { - JObject o = ja[0] as JObject; - if (IncludedWidgetId == o["i"].Value()) - InclusiveMatchCount++; - if (ExcludedWidgetId == o["i"].Value()) - ExclusiveMatchCount++; - } - - InclusiveMatchCount.Should().BeGreaterOrEqualTo(1); - ExclusiveMatchCount.Should().Be(0); - - //DELETE WIDGETS - a = await Util.DeleteAsync("widget/" + IncludedWidgetId.ToString(), await Util.GetTokenAsync("BizAdminFull")); - Util.ValidateHTTPStatusCode(a, 204); - - a = await Util.DeleteAsync("widget/" + ExcludedWidgetId.ToString(), await Util.GetTokenAsync("BizAdminFull")); - Util.ValidateHTTPStatusCode(a, 204); - - - //DELETE DATAFILTER - a = await Util.DeleteAsync("DataListFilter/" + DataFilterId.ToString(), await Util.GetTokenAsync("BizAdminFull")); - Util.ValidateHTTPStatusCode(a, 204); - } - - - - */ - - #endregion DATE REGULAR FILTERS - //======== - - #endregion date filter tests - - - - /////////////////////////////////////////////////////////////////////////////// - //TEXT - // - - #region STRING FILTER TESTS - - /// - /// - /// - [Fact] - public async void TextOpEqualityFilterWorks() - { - - var TestName = "TextOpEqualityFilterWorks"; - var WidgetNameStart = Util.Uniquify(TestName); - - List InclusiveWidgetIdList = new List(); - List ExclusiveWidgetIdList = new List(); - - //CREATE 4 TEST WIDGETS - //two inclusive and two not inclusive - - //first inclusive widget - dynamic w = new JObject(); - w.name = Util.Uniquify(WidgetNameStart); - w.customFields = Util.WidgetRequiredCustomFieldsJsonString(); - w.notes = "aardvark"; - w.usertype = 1; - - ApiResponse a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w.ToString()); - Util.ValidateDataReturnResponseOk(a); - InclusiveWidgetIdList.Add(a.ObjectResponse["data"]["id"].Value()); - - //second inclusive widget - w.name = Util.Uniquify(WidgetNameStart); - - a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w.ToString()); - Util.ValidateDataReturnResponseOk(a); - InclusiveWidgetIdList.Add(a.ObjectResponse["data"]["id"].Value()); - - //first exclusive widget - w.name = Util.Uniquify(WidgetNameStart); - w.notes = "zebra"; - w.active = false; - - a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w.ToString()); - Util.ValidateDataReturnResponseOk(a); - ExclusiveWidgetIdList.Add(a.ObjectResponse["data"]["id"].Value()); - - //second exclusive widget - w.name = Util.Uniquify(WidgetNameStart); - w.active = false; - - a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w.ToString()); - Util.ValidateDataReturnResponseOk(a); - ExclusiveWidgetIdList.Add(a.ObjectResponse["data"]["id"].Value()); - - - //CREATE LISTVIEW - dynamic dListView = new JArray(); - - //name starts with filter to constrict to widgets that this test block created only - dListView.Add(Util.BuildSimpleFilterDataListViewColumn("widgetname", Util.OpStartsWith, WidgetNameStart)); - - //FILTER - // dynamic DataFilterActive = new JObject(); - // DataFilterActive.fld = "widgetnotes"; - // DataFilterActive.op = Util.OpEquality; - // DataFilterActive.value = "aardvark"; - dListView.Add(Util.BuildSimpleFilterDataListViewColumn("widgetnotes", Util.OpEquality, "aardvark")); - - - - //FETCH DATALIST - a = await Util.PostAsync($"data-list", await Util.GetTokenAsync("superuser", "l3tm3in"), Util.BuildDataListRequestEx(dListView)); - Util.ValidateDataReturnResponseOk(a); - Util.ValidateHTTPStatusCode(a, 200); - - //assert contains at least two records - ((JArray)a.ObjectResponse["data"]).Count.Should().BeGreaterThan(1); - var v = ((JArray)a.ObjectResponse["data"]); - List IDInResultList = new List(); - int InclusiveMatchCount = 0; - int ExclusiveMatchCount = 0; - foreach (JArray ja in v) - { - JObject o = ja[0] as JObject; - if (InclusiveWidgetIdList.Contains(o["i"].Value())) - InclusiveMatchCount++; - if (ExclusiveWidgetIdList.Contains(o["i"].Value())) - ExclusiveMatchCount++; - } - - InclusiveMatchCount.Should().Be(InclusiveWidgetIdList.Count); - ExclusiveMatchCount.Should().Be(0); - - //DELETE WIDGETS - foreach (long l in InclusiveWidgetIdList) - { - a = await Util.DeleteAsync("widget/" + l.ToString(), await Util.GetTokenAsync("BizAdminFull")); - Util.ValidateHTTPStatusCode(a, 204); - } - - foreach (long l in ExclusiveWidgetIdList) - { - a = await Util.DeleteAsync("widget/" + l.ToString(), await Util.GetTokenAsync("BizAdminFull")); - Util.ValidateHTTPStatusCode(a, 204); - } - } - - - - - /// - /// Specifically test a string with an apostrophe in it (for inclusive) - /// - [Fact] - public async void TextApostropheOpEqualityFilterWorks() - { - - var TestName = "TextApostropheOpEqualityFilterWorks"; - var WidgetNameStart = Util.Uniquify(TestName); - - List InclusiveWidgetIdList = new List(); - List ExclusiveWidgetIdList = new List(); - - //CREATE 4 TEST WIDGETS - //two inclusive and two not inclusive - - //first inclusive widget - dynamic w = new JObject(); - w.name = Util.Uniquify(WidgetNameStart); - w.customFields = Util.WidgetRequiredCustomFieldsJsonString(); - w.notes = "O'Flaherty's pub"; - w.usertype = 1; - - ApiResponse a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w.ToString()); - Util.ValidateDataReturnResponseOk(a); - InclusiveWidgetIdList.Add(a.ObjectResponse["data"]["id"].Value()); - - //second inclusive widget - w.name = Util.Uniquify(WidgetNameStart); - - a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w.ToString()); - Util.ValidateDataReturnResponseOk(a); - InclusiveWidgetIdList.Add(a.ObjectResponse["data"]["id"].Value()); - - //first exclusive widget - w.name = Util.Uniquify(WidgetNameStart); - w.notes = "Outback steak house"; - w.active = false; - - a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w.ToString()); - Util.ValidateDataReturnResponseOk(a); - ExclusiveWidgetIdList.Add(a.ObjectResponse["data"]["id"].Value()); - - //second exclusive widget - w.name = Util.Uniquify(WidgetNameStart); - w.active = false; - - a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w.ToString()); - Util.ValidateDataReturnResponseOk(a); - ExclusiveWidgetIdList.Add(a.ObjectResponse["data"]["id"].Value()); - - - //CREATE LISTVIEW - dynamic dListView = new JArray(); - - //name starts with filter to constrict to widgets that this test block created only - dListView.Add(Util.BuildSimpleFilterDataListViewColumn("widgetname", Util.OpStartsWith, WidgetNameStart)); - //FILTER - // dynamic DataFilterActive = new JObject(); - // DataFilterActive.fld = "widgetnotes"; - // DataFilterActive.op = Util.OpEquality; - // DataFilterActive.value = "O'Flaherty's pub"; - dListView.Add(Util.BuildSimpleFilterDataListViewColumn("widgetnotes", Util.OpEquality, "O'Flaherty's pub")); - - - //FETCH DATALIST - a = await Util.PostAsync($"data-list", await Util.GetTokenAsync("superuser", "l3tm3in"), Util.BuildDataListRequestEx(dListView)); - Util.ValidateDataReturnResponseOk(a); - Util.ValidateHTTPStatusCode(a, 200); - - //assert contains at least two records - ((JArray)a.ObjectResponse["data"]).Count.Should().BeGreaterThan(1); - var v = ((JArray)a.ObjectResponse["data"]); - List IDInResultList = new List(); - int InclusiveMatchCount = 0; - int ExclusiveMatchCount = 0; - foreach (JArray ja in v) - { - JObject o = ja[0] as JObject; - if (InclusiveWidgetIdList.Contains(o["i"].Value())) - InclusiveMatchCount++; - if (ExclusiveWidgetIdList.Contains(o["i"].Value())) - ExclusiveMatchCount++; - } - - InclusiveMatchCount.Should().Be(InclusiveWidgetIdList.Count); - ExclusiveMatchCount.Should().Be(0); - - //DELETE WIDGETS - foreach (long l in InclusiveWidgetIdList) - { - a = await Util.DeleteAsync("widget/" + l.ToString(), await Util.GetTokenAsync("BizAdminFull")); - Util.ValidateHTTPStatusCode(a, 204); - } - - foreach (long l in ExclusiveWidgetIdList) - { - a = await Util.DeleteAsync("widget/" + l.ToString(), await Util.GetTokenAsync("BizAdminFull")); - Util.ValidateHTTPStatusCode(a, 204); - } - } - - /// - /// specifically test a string with an ampersand character in it for inclusive (finding it) - /// - [Fact] - public async void TextAmpersandOpEqualityFilterWorks() - { - - var TestName = "TextAmpersandOpEqualityFilterWorks"; - var WidgetNameStart = Util.Uniquify(TestName); - - List InclusiveWidgetIdList = new List(); - List ExclusiveWidgetIdList = new List(); - - //CREATE 4 TEST WIDGETS - //two inclusive and two not inclusive - - //first inclusive widget - dynamic w = new JObject(); - w.name = Util.Uniquify(WidgetNameStart); - w.customFields = Util.WidgetRequiredCustomFieldsJsonString(); - w.notes = "Bill & Ted's excellent adventure"; - w.usertype = 1; - - ApiResponse a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w.ToString()); - Util.ValidateDataReturnResponseOk(a); - InclusiveWidgetIdList.Add(a.ObjectResponse["data"]["id"].Value()); - - //second inclusive widget - w.name = Util.Uniquify(WidgetNameStart); - - a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w.ToString()); - Util.ValidateDataReturnResponseOk(a); - InclusiveWidgetIdList.Add(a.ObjectResponse["data"]["id"].Value()); - - //first exclusive widget - w.name = Util.Uniquify(WidgetNameStart); - w.notes = "Strange things are afoot at the Circle-K"; - w.active = false; - - a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w.ToString()); - Util.ValidateDataReturnResponseOk(a); - ExclusiveWidgetIdList.Add(a.ObjectResponse["data"]["id"].Value()); - - //second exclusive widget - w.name = Util.Uniquify(WidgetNameStart); - w.active = false; - - a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w.ToString()); - Util.ValidateDataReturnResponseOk(a); - ExclusiveWidgetIdList.Add(a.ObjectResponse["data"]["id"].Value()); - - - //CREATE LISTVIEW - dynamic dListView = new JArray(); - - //name starts with filter to constrict to widgets that this test block created only - dListView.Add(Util.BuildSimpleFilterDataListViewColumn("widgetname", Util.OpStartsWith, WidgetNameStart)); - - //FILTER - // dynamic DataFilterActive = new JObject(); - // DataFilterActive.fld = "widgetnotes"; - // DataFilterActive.op = Util.OpEquality; - // DataFilterActive.value = "Bill & Ted's excellent adventure"; - dListView.Add(Util.BuildSimpleFilterDataListViewColumn("widgetnotes", Util.OpEquality, "Bill & Ted's excellent adventure")); - //FETCH DATALIST - a = await Util.PostAsync($"data-list", await Util.GetTokenAsync("superuser", "l3tm3in"), Util.BuildDataListRequestEx(dListView)); - Util.ValidateDataReturnResponseOk(a); - Util.ValidateHTTPStatusCode(a, 200); - - //assert contains at least two records - ((JArray)a.ObjectResponse["data"]).Count.Should().BeGreaterThan(1); - var v = ((JArray)a.ObjectResponse["data"]); - List IDInResultList = new List(); - int InclusiveMatchCount = 0; - int ExclusiveMatchCount = 0; - - - foreach (JArray ja in v) - { - JObject o = ja[0] as JObject; - - if (InclusiveWidgetIdList.Contains(o["i"].Value())) - InclusiveMatchCount++; - if (ExclusiveWidgetIdList.Contains(o["i"].Value())) - ExclusiveMatchCount++; - } - - InclusiveMatchCount.Should().Be(InclusiveWidgetIdList.Count); - ExclusiveMatchCount.Should().Be(0); - - //DELETE WIDGETS - foreach (long l in InclusiveWidgetIdList) - { - a = await Util.DeleteAsync("widget/" + l.ToString(), await Util.GetTokenAsync("BizAdminFull")); - Util.ValidateHTTPStatusCode(a, 204); - } - - foreach (long l in ExclusiveWidgetIdList) - { - a = await Util.DeleteAsync("widget/" + l.ToString(), await Util.GetTokenAsync("BizAdminFull")); - Util.ValidateHTTPStatusCode(a, 204); - } - } - - /// - /// specifically test a non english unicode string - /// - [Fact] - public async void TextUnicodeOpEqualityFilterWorks() - { - - var TestName = "TextUnicodeOpEqualityFilterWorks"; - var WidgetNameStart = Util.Uniquify(TestName); - - List InclusiveWidgetIdList = new List(); - List ExclusiveWidgetIdList = new List(); - - //CREATE 4 TEST WIDGETS - //two inclusive and two not inclusive - - //first inclusive widget - var InclusiveTestString = "Ādam Iñtërnâtiônàližætiøn"; - dynamic w = new JObject(); - w.name = Util.Uniquify(WidgetNameStart); - w.customFields = Util.WidgetRequiredCustomFieldsJsonString(); - w.notes = InclusiveTestString; - w.usertype = 1; - - ApiResponse a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w.ToString()); - Util.ValidateDataReturnResponseOk(a); - InclusiveWidgetIdList.Add(a.ObjectResponse["data"]["id"].Value()); - - //second inclusive widget - w.name = Util.Uniquify(WidgetNameStart); - - a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w.ToString()); - Util.ValidateDataReturnResponseOk(a); - InclusiveWidgetIdList.Add(a.ObjectResponse["data"]["id"].Value()); - - //first exclusive widget - w.name = Util.Uniquify(WidgetNameStart); - w.notes = "Adam Internationalization"; - w.active = false; - - a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w.ToString()); - Util.ValidateDataReturnResponseOk(a); - ExclusiveWidgetIdList.Add(a.ObjectResponse["data"]["id"].Value()); - - //second exclusive widget - w.name = Util.Uniquify(WidgetNameStart); - w.active = false; - - a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w.ToString()); - Util.ValidateDataReturnResponseOk(a); - ExclusiveWidgetIdList.Add(a.ObjectResponse["data"]["id"].Value()); - - - //CREATE LISTVIEW - dynamic dListView = new JArray(); - - //name starts with filter to constrict to widgets that this test block created only - dListView.Add(Util.BuildSimpleFilterDataListViewColumn("widgetname", Util.OpStartsWith, WidgetNameStart)); - - //FILTER - // dynamic DataFilterActive = new JObject(); - // DataFilterActive.fld = "widgetnotes"; - // DataFilterActive.op = Util.OpEquality; - // DataFilterActive.value = InclusiveTestString; - dListView.Add(Util.BuildSimpleFilterDataListViewColumn("widgetnotes", Util.OpEquality, InclusiveTestString)); - - //FETCH DATALIST - a = await Util.PostAsync($"data-list", await Util.GetTokenAsync("superuser", "l3tm3in"), Util.BuildDataListRequestEx(dListView)); - Util.ValidateDataReturnResponseOk(a); - Util.ValidateHTTPStatusCode(a, 200); - - //assert contains at least two records - ((JArray)a.ObjectResponse["data"]).Count.Should().BeGreaterThan(1); - var v = ((JArray)a.ObjectResponse["data"]); - List IDInResultList = new List(); - int InclusiveMatchCount = 0; - int ExclusiveMatchCount = 0; - foreach (JArray ja in v) - { - JObject o = ja[0] as JObject; - if (InclusiveWidgetIdList.Contains(o["i"].Value())) - InclusiveMatchCount++; - if (ExclusiveWidgetIdList.Contains(o["i"].Value())) - ExclusiveMatchCount++; - } - - InclusiveMatchCount.Should().Be(InclusiveWidgetIdList.Count); - ExclusiveMatchCount.Should().Be(0); - - //DELETE WIDGETS - foreach (long l in InclusiveWidgetIdList) - { - a = await Util.DeleteAsync("widget/" + l.ToString(), await Util.GetTokenAsync("BizAdminFull")); - Util.ValidateHTTPStatusCode(a, 204); - } - - foreach (long l in ExclusiveWidgetIdList) - { - a = await Util.DeleteAsync("widget/" + l.ToString(), await Util.GetTokenAsync("BizAdminFull")); - Util.ValidateHTTPStatusCode(a, 204); - } - } - - - /// - /// - /// - [Fact] - public async void TextOpGreaterThanFilterWorks() - { - - var TestName = "TextOpGreaterThanFilterWorks"; - var WidgetNameStart = Util.Uniquify(TestName); - - List InclusiveWidgetIdList = new List(); - List ExclusiveWidgetIdList = new List(); - - //CREATE 4 TEST WIDGETS - //two inclusive and two not inclusive - - //first inclusive widget - dynamic w = new JObject(); - w.name = Util.Uniquify(WidgetNameStart); - w.customFields = Util.WidgetRequiredCustomFieldsJsonString(); - w.notes = "Alabama"; - w.usertype = 1; - - ApiResponse a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w.ToString()); - Util.ValidateDataReturnResponseOk(a); - InclusiveWidgetIdList.Add(a.ObjectResponse["data"]["id"].Value()); - - //second inclusive widget - w.name = Util.Uniquify(WidgetNameStart); - - a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w.ToString()); - Util.ValidateDataReturnResponseOk(a); - InclusiveWidgetIdList.Add(a.ObjectResponse["data"]["id"].Value()); - - //first exclusive widget - w.name = Util.Uniquify(WidgetNameStart); - w.notes = "Aardvark"; - w.active = false; - - a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w.ToString()); - Util.ValidateDataReturnResponseOk(a); - ExclusiveWidgetIdList.Add(a.ObjectResponse["data"]["id"].Value()); - - //second exclusive widget - w.name = Util.Uniquify(WidgetNameStart); - w.active = false; - - a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w.ToString()); - Util.ValidateDataReturnResponseOk(a); - ExclusiveWidgetIdList.Add(a.ObjectResponse["data"]["id"].Value()); - - - //CREATE LISTVIEW - dynamic dListView = new JArray(); - - //name starts with filter to constrict to widgets that this test block created only - dListView.Add(Util.BuildSimpleFilterDataListViewColumn("widgetname", Util.OpStartsWith, WidgetNameStart)); - - //FILTER - // dynamic DataFilterActive = new JObject(); - // DataFilterActive.fld = "widgetnotes"; - // DataFilterActive.op = Util.OpGreaterThan; - // DataFilterActive.value = "Aardvark"; - dListView.Add(Util.BuildSimpleFilterDataListViewColumn("widgetnotes", Util.OpGreaterThan, "Aardvark")); - - - //FETCH DATALIST - a = await Util.PostAsync($"data-list", await Util.GetTokenAsync("superuser", "l3tm3in"), Util.BuildDataListRequestEx(dListView)); - Util.ValidateDataReturnResponseOk(a); - Util.ValidateHTTPStatusCode(a, 200); - - //assert contains at least two records - ((JArray)a.ObjectResponse["data"]).Count.Should().BeGreaterThan(1); - var v = ((JArray)a.ObjectResponse["data"]); - List IDInResultList = new List(); - int InclusiveMatchCount = 0; - int ExclusiveMatchCount = 0; - foreach (JArray ja in v) - { - JObject o = ja[0] as JObject; - if (InclusiveWidgetIdList.Contains(o["i"].Value())) - InclusiveMatchCount++; - if (ExclusiveWidgetIdList.Contains(o["i"].Value())) - ExclusiveMatchCount++; - } - - InclusiveMatchCount.Should().Be(InclusiveWidgetIdList.Count); - ExclusiveMatchCount.Should().Be(0); - - //DELETE WIDGETS - foreach (long l in InclusiveWidgetIdList) - { - a = await Util.DeleteAsync("widget/" + l.ToString(), await Util.GetTokenAsync("BizAdminFull")); - Util.ValidateHTTPStatusCode(a, 204); - } - - foreach (long l in ExclusiveWidgetIdList) - { - a = await Util.DeleteAsync("widget/" + l.ToString(), await Util.GetTokenAsync("BizAdminFull")); - Util.ValidateHTTPStatusCode(a, 204); - } - } - - - /// - /// - /// - [Fact] - public async void TextOpGreaterThanOrEqualToFilterWorks() - { - - var TestName = "TextOpGreaterThanOrEqualToFilterWorks"; - var WidgetNameStart = Util.Uniquify(TestName); - - List InclusiveWidgetIdList = new List(); - List ExclusiveWidgetIdList = new List(); - - //CREATE 4 TEST WIDGETS - //two inclusive and two not inclusive - - //first inclusive widget - dynamic w = new JObject(); - w.name = Util.Uniquify(WidgetNameStart); - w.customFields = Util.WidgetRequiredCustomFieldsJsonString(); - w.notes = "Bjorn"; - w.usertype = 1; - - ApiResponse a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w.ToString()); - Util.ValidateDataReturnResponseOk(a); - InclusiveWidgetIdList.Add(a.ObjectResponse["data"]["id"].Value()); - - //second inclusive widget - w.name = Util.Uniquify(WidgetNameStart); - - a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w.ToString()); - Util.ValidateDataReturnResponseOk(a); - InclusiveWidgetIdList.Add(a.ObjectResponse["data"]["id"].Value()); - - //first exclusive widget - w.name = Util.Uniquify(WidgetNameStart); - w.notes = "Bing"; - w.active = false; - - a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w.ToString()); - Util.ValidateDataReturnResponseOk(a); - ExclusiveWidgetIdList.Add(a.ObjectResponse["data"]["id"].Value()); - - //second exclusive widget - w.name = Util.Uniquify(WidgetNameStart); - w.active = false; - - a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w.ToString()); - Util.ValidateDataReturnResponseOk(a); - ExclusiveWidgetIdList.Add(a.ObjectResponse["data"]["id"].Value()); - - - //CREATE LISTVIEW - dynamic dListView = new JArray(); - - //name starts with filter to constrict to widgets that this test block created only - dListView.Add(Util.BuildSimpleFilterDataListViewColumn("widgetname", Util.OpStartsWith, WidgetNameStart)); - - //FILTER - // dynamic DataFilterActive = new JObject(); - // DataFilterActive.fld = "widgetnotes"; - // DataFilterActive.op = Util.OpGreaterThanOrEqualTo; - // DataFilterActive.value = "Bjarn"; - dListView.Add(Util.BuildSimpleFilterDataListViewColumn("widgetnotes", Util.OpGreaterThanOrEqualTo, "Bjarn")); - - //FETCH DATALIST - a = await Util.PostAsync($"data-list", await Util.GetTokenAsync("superuser", "l3tm3in"), Util.BuildDataListRequestEx(dListView)); - Util.ValidateDataReturnResponseOk(a); - Util.ValidateHTTPStatusCode(a, 200); - - //assert contains at least two records - ((JArray)a.ObjectResponse["data"]).Count.Should().BeGreaterThan(1); - var v = ((JArray)a.ObjectResponse["data"]); - List IDInResultList = new List(); - int InclusiveMatchCount = 0; - int ExclusiveMatchCount = 0; - foreach (JArray ja in v) - { - JObject o = ja[0] as JObject; - if (InclusiveWidgetIdList.Contains(o["i"].Value())) - InclusiveMatchCount++; - if (ExclusiveWidgetIdList.Contains(o["i"].Value())) - ExclusiveMatchCount++; - } - - InclusiveMatchCount.Should().Be(InclusiveWidgetIdList.Count); - ExclusiveMatchCount.Should().Be(0); - - //DELETE WIDGETS - foreach (long l in InclusiveWidgetIdList) - { - a = await Util.DeleteAsync("widget/" + l.ToString(), await Util.GetTokenAsync("BizAdminFull")); - Util.ValidateHTTPStatusCode(a, 204); - } - - foreach (long l in ExclusiveWidgetIdList) - { - a = await Util.DeleteAsync("widget/" + l.ToString(), await Util.GetTokenAsync("BizAdminFull")); - Util.ValidateHTTPStatusCode(a, 204); - } - } - - - /// - /// - /// - [Fact] - public async void TextOpLessThanFilterWorks() - { - - var TestName = "TextOpLessThanFilterWorks"; - var WidgetNameStart = Util.Uniquify(TestName); - - List InclusiveWidgetIdList = new List(); - List ExclusiveWidgetIdList = new List(); - - //CREATE 4 TEST WIDGETS - //two inclusive and two not inclusive - - //first inclusive widget - dynamic w = new JObject(); - w.name = Util.Uniquify(WidgetNameStart); - w.customFields = Util.WidgetRequiredCustomFieldsJsonString(); - w.notes = "California"; - w.usertype = 1; - - ApiResponse a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w.ToString()); - Util.ValidateDataReturnResponseOk(a); - InclusiveWidgetIdList.Add(a.ObjectResponse["data"]["id"].Value()); - - //second inclusive widget - w.name = Util.Uniquify(WidgetNameStart); - - a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w.ToString()); - Util.ValidateDataReturnResponseOk(a); - InclusiveWidgetIdList.Add(a.ObjectResponse["data"]["id"].Value()); - - //first exclusive widget - w.name = Util.Uniquify(WidgetNameStart); - w.notes = "Cthulu"; - w.active = false; - - a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w.ToString()); - Util.ValidateDataReturnResponseOk(a); - ExclusiveWidgetIdList.Add(a.ObjectResponse["data"]["id"].Value()); - - //second exclusive widget - w.name = Util.Uniquify(WidgetNameStart); - w.active = false; - - a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w.ToString()); - Util.ValidateDataReturnResponseOk(a); - ExclusiveWidgetIdList.Add(a.ObjectResponse["data"]["id"].Value()); - - - //CREATE LISTVIEW - dynamic dListView = new JArray(); - - //name starts with filter to constrict to widgets that this test block created only - dListView.Add(Util.BuildSimpleFilterDataListViewColumn("widgetname", Util.OpStartsWith, WidgetNameStart)); - - //FILTER - // dynamic DataFilterActive = new JObject(); - // DataFilterActive.fld = "widgetnotes"; - // DataFilterActive.op = Util.OpLessThan; - // DataFilterActive.value = "Celery"; - dListView.Add(Util.BuildSimpleFilterDataListViewColumn("widgetnotes", Util.OpLessThan, "Celery")); - - //FETCH DATALIST - a = await Util.PostAsync($"data-list", await Util.GetTokenAsync("superuser", "l3tm3in"), Util.BuildDataListRequestEx(dListView)); - Util.ValidateDataReturnResponseOk(a); - Util.ValidateHTTPStatusCode(a, 200); - - //assert contains at least two records - ((JArray)a.ObjectResponse["data"]).Count.Should().BeGreaterThan(1); - var v = ((JArray)a.ObjectResponse["data"]); - List IDInResultList = new List(); - int InclusiveMatchCount = 0; - int ExclusiveMatchCount = 0; - foreach (JArray ja in v) - { - JObject o = ja[0] as JObject; - if (InclusiveWidgetIdList.Contains(o["i"].Value())) - InclusiveMatchCount++; - if (ExclusiveWidgetIdList.Contains(o["i"].Value())) - ExclusiveMatchCount++; - } - - InclusiveMatchCount.Should().Be(InclusiveWidgetIdList.Count); - ExclusiveMatchCount.Should().Be(0); - - //DELETE WIDGETS - foreach (long l in InclusiveWidgetIdList) - { - a = await Util.DeleteAsync("widget/" + l.ToString(), await Util.GetTokenAsync("BizAdminFull")); - Util.ValidateHTTPStatusCode(a, 204); - } - - foreach (long l in ExclusiveWidgetIdList) - { - a = await Util.DeleteAsync("widget/" + l.ToString(), await Util.GetTokenAsync("BizAdminFull")); - Util.ValidateHTTPStatusCode(a, 204); - } - } - - - /// - /// - /// - [Fact] - public async void TextOpLessThanOrEqualToFilterWorks() - { - - var TestName = "TextOpLessThanOrEqualToFilterWorks"; - var WidgetNameStart = Util.Uniquify(TestName); - - List InclusiveWidgetIdList = new List(); - List ExclusiveWidgetIdList = new List(); - - //CREATE 4 TEST WIDGETS - //two inclusive and two not inclusive - - //first inclusive widget - dynamic w = new JObject(); - w.name = Util.Uniquify(WidgetNameStart); - w.customFields = Util.WidgetRequiredCustomFieldsJsonString(); - w.notes = "Donut"; - w.usertype = 1; - - ApiResponse a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w.ToString()); - Util.ValidateDataReturnResponseOk(a); - InclusiveWidgetIdList.Add(a.ObjectResponse["data"]["id"].Value()); - - //second inclusive widget - w.name = Util.Uniquify(WidgetNameStart); - - a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w.ToString()); - Util.ValidateDataReturnResponseOk(a); - InclusiveWidgetIdList.Add(a.ObjectResponse["data"]["id"].Value()); - - //first exclusive widget - w.name = Util.Uniquify(WidgetNameStart); - w.notes = "Duvet"; - w.active = false; - - a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w.ToString()); - Util.ValidateDataReturnResponseOk(a); - ExclusiveWidgetIdList.Add(a.ObjectResponse["data"]["id"].Value()); - - //second exclusive widget - w.name = Util.Uniquify(WidgetNameStart); - w.active = false; - - a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w.ToString()); - Util.ValidateDataReturnResponseOk(a); - ExclusiveWidgetIdList.Add(a.ObjectResponse["data"]["id"].Value()); - - - //CREATE LISTVIEW - dynamic dListView = new JArray(); - - //name starts with filter to constrict to widgets that this test block created only - dListView.Add(Util.BuildSimpleFilterDataListViewColumn("widgetname", Util.OpStartsWith, WidgetNameStart)); - - //FILTER - // dynamic DataFilterActive = new JObject(); - // DataFilterActive.fld = "widgetnotes"; - // DataFilterActive.op = Util.OpLessThanOrEqualTo; - // DataFilterActive.value = "Dusseldorf"; - dListView.Add(Util.BuildSimpleFilterDataListViewColumn("widgetnotes", Util.OpLessThanOrEqualTo, "Dusseldorf")); - - - //FETCH DATALIST - a = await Util.PostAsync($"data-list", await Util.GetTokenAsync("superuser", "l3tm3in"), Util.BuildDataListRequestEx(dListView)); - Util.ValidateDataReturnResponseOk(a); - Util.ValidateHTTPStatusCode(a, 200); - - //assert contains at least two records - ((JArray)a.ObjectResponse["data"]).Count.Should().BeGreaterThan(1); - var v = ((JArray)a.ObjectResponse["data"]); - List IDInResultList = new List(); - int InclusiveMatchCount = 0; - int ExclusiveMatchCount = 0; - foreach (JArray ja in v) - { - JObject o = ja[0] as JObject; - if (InclusiveWidgetIdList.Contains(o["i"].Value())) - InclusiveMatchCount++; - if (ExclusiveWidgetIdList.Contains(o["i"].Value())) - ExclusiveMatchCount++; - } - - InclusiveMatchCount.Should().Be(InclusiveWidgetIdList.Count); - ExclusiveMatchCount.Should().Be(0); - - //DELETE WIDGETS - foreach (long l in InclusiveWidgetIdList) - { - a = await Util.DeleteAsync("widget/" + l.ToString(), await Util.GetTokenAsync("BizAdminFull")); - Util.ValidateHTTPStatusCode(a, 204); - } - - foreach (long l in ExclusiveWidgetIdList) - { - a = await Util.DeleteAsync("widget/" + l.ToString(), await Util.GetTokenAsync("BizAdminFull")); - Util.ValidateHTTPStatusCode(a, 204); - } - } - - /// - /// - /// - [Fact] - public async void TextOpNotEqualFilterWorks() - { - - var TestName = "TextOpNotEqualFilterWorks"; - var WidgetNameStart = Util.Uniquify(TestName); - - List InclusiveWidgetIdList = new List(); - List ExclusiveWidgetIdList = new List(); - - //CREATE 4 TEST WIDGETS - //two inclusive and two not inclusive - - //first inclusive widget - dynamic w = new JObject(); - w.name = Util.Uniquify(WidgetNameStart); - w.customFields = Util.WidgetRequiredCustomFieldsJsonString(); - w.notes = "Egg Salad Sandwich"; - w.usertype = 1; - - ApiResponse a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w.ToString()); - Util.ValidateDataReturnResponseOk(a); - InclusiveWidgetIdList.Add(a.ObjectResponse["data"]["id"].Value()); - - //second inclusive widget - w.name = Util.Uniquify(WidgetNameStart); - - a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w.ToString()); - Util.ValidateDataReturnResponseOk(a); - InclusiveWidgetIdList.Add(a.ObjectResponse["data"]["id"].Value()); - - //first exclusive widget - w.name = Util.Uniquify(WidgetNameStart); - w.notes = "Elephant"; - w.active = false; - - a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w.ToString()); - Util.ValidateDataReturnResponseOk(a); - ExclusiveWidgetIdList.Add(a.ObjectResponse["data"]["id"].Value()); - - //second exclusive widget - w.name = Util.Uniquify(WidgetNameStart); - w.active = false; - - a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w.ToString()); - Util.ValidateDataReturnResponseOk(a); - ExclusiveWidgetIdList.Add(a.ObjectResponse["data"]["id"].Value()); - - - //CREATE LISTVIEW - dynamic dListView = new JArray(); - - //name starts with filter to constrict to widgets that this test block created only - dListView.Add(Util.BuildSimpleFilterDataListViewColumn("widgetname", Util.OpStartsWith, WidgetNameStart)); - - //FILTER - // dynamic DataFilterActive = new JObject(); - // DataFilterActive.fld = "widgetnotes"; - // DataFilterActive.op = Util.OpNotEqual; - // DataFilterActive.value = "Elephant"; - dListView.Add(Util.BuildSimpleFilterDataListViewColumn("widgetnotes", Util.OpNotEqual, "Elephant")); - - //FETCH DATALIST - a = await Util.PostAsync($"data-list", await Util.GetTokenAsync("superuser", "l3tm3in"), Util.BuildDataListRequestEx(dListView)); - Util.ValidateDataReturnResponseOk(a); - Util.ValidateHTTPStatusCode(a, 200); - - //assert contains at least two records - ((JArray)a.ObjectResponse["data"]).Count.Should().BeGreaterThan(1); - var v = ((JArray)a.ObjectResponse["data"]); - List IDInResultList = new List(); - int InclusiveMatchCount = 0; - int ExclusiveMatchCount = 0; - foreach (JArray ja in v) - { - JObject o = ja[0] as JObject; - if (InclusiveWidgetIdList.Contains(o["i"].Value())) - InclusiveMatchCount++; - if (ExclusiveWidgetIdList.Contains(o["i"].Value())) - ExclusiveMatchCount++; - } - - InclusiveMatchCount.Should().Be(InclusiveWidgetIdList.Count); - ExclusiveMatchCount.Should().Be(0); - - //DELETE WIDGETS - foreach (long l in InclusiveWidgetIdList) - { - a = await Util.DeleteAsync("widget/" + l.ToString(), await Util.GetTokenAsync("BizAdminFull")); - Util.ValidateHTTPStatusCode(a, 204); - } - - foreach (long l in ExclusiveWidgetIdList) - { - a = await Util.DeleteAsync("widget/" + l.ToString(), await Util.GetTokenAsync("BizAdminFull")); - Util.ValidateHTTPStatusCode(a, 204); - } - } - - - /// - /// - /// - [Fact] - public async void TextOpNotContainsFilterWorks() - { - var TestName = "TextOpNotContainsFilterWorks"; - var WidgetNameStart = Util.Uniquify(TestName); - - List InclusiveWidgetIdList = new List(); - List ExclusiveWidgetIdList = new List(); - - //CREATE 4 TEST WIDGETS - //two inclusive and two not inclusive - - //first inclusive widget - dynamic w = new JObject(); - w.name = Util.Uniquify(WidgetNameStart); - w.customFields = Util.WidgetRequiredCustomFieldsJsonString(); - w.notes = "Gray poupon"; - w.usertype = 1; - - ApiResponse a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w.ToString()); - Util.ValidateDataReturnResponseOk(a); - InclusiveWidgetIdList.Add(a.ObjectResponse["data"]["id"].Value()); - - //second inclusive widget - w.name = Util.Uniquify(WidgetNameStart); - - a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w.ToString()); - Util.ValidateDataReturnResponseOk(a); - InclusiveWidgetIdList.Add(a.ObjectResponse["data"]["id"].Value()); - - //first exclusive widget - w.name = Util.Uniquify(WidgetNameStart); - w.notes = "Get shorty"; - w.active = false; - - a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w.ToString()); - Util.ValidateDataReturnResponseOk(a); - ExclusiveWidgetIdList.Add(a.ObjectResponse["data"]["id"].Value()); - - //second exclusive widget - w.name = Util.Uniquify(WidgetNameStart); - w.active = false; - - a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w.ToString()); - Util.ValidateDataReturnResponseOk(a); - ExclusiveWidgetIdList.Add(a.ObjectResponse["data"]["id"].Value()); - - - //CREATE LISTVIEW - dynamic dListView = new JArray(); - - //name starts with filter to constrict to widgets that this test block created only - dListView.Add(Util.BuildSimpleFilterDataListViewColumn("widgetname", Util.OpStartsWith, WidgetNameStart)); - - //FILTER - // dynamic DataFilterActive = new JObject(); - // DataFilterActive.fld = "widgetnotes"; - // DataFilterActive.op = Util.OpNotContains; - // DataFilterActive.value = "short"; - dListView.Add(Util.BuildSimpleFilterDataListViewColumn("widgetnotes", Util.OpNotContains, "short")); - - //FETCH DATALIST - a = await Util.PostAsync($"data-list", await Util.GetTokenAsync("superuser", "l3tm3in"), Util.BuildDataListRequestEx(dListView)); - Util.ValidateDataReturnResponseOk(a); - Util.ValidateHTTPStatusCode(a, 200); - - //assert contains at least two records - ((JArray)a.ObjectResponse["data"]).Count.Should().BeGreaterThan(1); - var v = ((JArray)a.ObjectResponse["data"]); - List IDInResultList = new List(); - int InclusiveMatchCount = 0; - int ExclusiveMatchCount = 0; - foreach (JArray ja in v) - { - JObject o = ja[0] as JObject; - if (InclusiveWidgetIdList.Contains(o["i"].Value())) - InclusiveMatchCount++; - if (ExclusiveWidgetIdList.Contains(o["i"].Value())) - ExclusiveMatchCount++; - } - - InclusiveMatchCount.Should().Be(InclusiveWidgetIdList.Count); - ExclusiveMatchCount.Should().Be(0); - - //DELETE WIDGETS - foreach (long l in InclusiveWidgetIdList) - { - a = await Util.DeleteAsync("widget/" + l.ToString(), await Util.GetTokenAsync("BizAdminFull")); - Util.ValidateHTTPStatusCode(a, 204); - } - - foreach (long l in ExclusiveWidgetIdList) - { - a = await Util.DeleteAsync("widget/" + l.ToString(), await Util.GetTokenAsync("BizAdminFull")); - Util.ValidateHTTPStatusCode(a, 204); - } - } - - - /// - /// - /// - [Fact] - public async void TextOpContainsFilterWorks() - { - var TestName = "TextOpContainsFilterWorks"; - var WidgetNameStart = Util.Uniquify(TestName); - - List InclusiveWidgetIdList = new List(); - List ExclusiveWidgetIdList = new List(); - - //CREATE 4 TEST WIDGETS - //two inclusive and two not inclusive - - //first inclusive widget - dynamic w = new JObject(); - w.name = Util.Uniquify(WidgetNameStart); - w.customFields = Util.WidgetRequiredCustomFieldsJsonString(); - w.notes = "Fast Freddy Freak"; - w.usertype = 1; - - ApiResponse a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w.ToString()); - Util.ValidateDataReturnResponseOk(a); - InclusiveWidgetIdList.Add(a.ObjectResponse["data"]["id"].Value()); - - //second inclusive widget - w.name = Util.Uniquify(WidgetNameStart); - - a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w.ToString()); - Util.ValidateDataReturnResponseOk(a); - InclusiveWidgetIdList.Add(a.ObjectResponse["data"]["id"].Value()); - - //first exclusive widget - w.name = Util.Uniquify(WidgetNameStart); - w.notes = "Phineas Freak"; - w.active = false; - - a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w.ToString()); - Util.ValidateDataReturnResponseOk(a); - ExclusiveWidgetIdList.Add(a.ObjectResponse["data"]["id"].Value()); - - //second exclusive widget - w.name = Util.Uniquify(WidgetNameStart); - w.active = false; - - a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w.ToString()); - Util.ValidateDataReturnResponseOk(a); - ExclusiveWidgetIdList.Add(a.ObjectResponse["data"]["id"].Value()); - - - //CREATE LISTVIEW - dynamic dListView = new JArray(); - - //name starts with filter to constrict to widgets that this test block created only - dListView.Add(Util.BuildSimpleFilterDataListViewColumn("widgetname", Util.OpStartsWith, WidgetNameStart)); - - //FILTER - // dynamic DataFilterActive = new JObject(); - // DataFilterActive.fld = "widgetnotes"; - // DataFilterActive.op = Util.OpContains; - // DataFilterActive.value = "red"; - dListView.Add(Util.BuildSimpleFilterDataListViewColumn("widgetnotes", Util.OpContains, "red")); - //FETCH DATALIST - a = await Util.PostAsync($"data-list", await Util.GetTokenAsync("superuser", "l3tm3in"), Util.BuildDataListRequestEx(dListView)); - Util.ValidateDataReturnResponseOk(a); - Util.ValidateHTTPStatusCode(a, 200); - - //assert contains at least two records - ((JArray)a.ObjectResponse["data"]).Count.Should().BeGreaterThan(1); - var v = ((JArray)a.ObjectResponse["data"]); - List IDInResultList = new List(); - int InclusiveMatchCount = 0; - int ExclusiveMatchCount = 0; - foreach (JArray ja in v) - { - JObject o = ja[0] as JObject; - if (InclusiveWidgetIdList.Contains(o["i"].Value())) - InclusiveMatchCount++; - if (ExclusiveWidgetIdList.Contains(o["i"].Value())) - ExclusiveMatchCount++; - } - - InclusiveMatchCount.Should().Be(InclusiveWidgetIdList.Count); - ExclusiveMatchCount.Should().Be(0); - - //DELETE WIDGETS - foreach (long l in InclusiveWidgetIdList) - { - a = await Util.DeleteAsync("widget/" + l.ToString(), await Util.GetTokenAsync("BizAdminFull")); - Util.ValidateHTTPStatusCode(a, 204); - } - - foreach (long l in ExclusiveWidgetIdList) - { - a = await Util.DeleteAsync("widget/" + l.ToString(), await Util.GetTokenAsync("BizAdminFull")); - Util.ValidateHTTPStatusCode(a, 204); - } - } - - - /// - /// - /// - [Fact] - public async void TextOpStartsWithFilterWorks() - { - var TestName = "TextOpStartsWithFilterWorks"; - var WidgetNameStart = Util.Uniquify(TestName); - - List InclusiveWidgetIdList = new List(); - List ExclusiveWidgetIdList = new List(); - - //CREATE 4 TEST WIDGETS - //two inclusive and two not inclusive - - //first inclusive widget - dynamic w = new JObject(); - w.name = Util.Uniquify(WidgetNameStart); - w.customFields = Util.WidgetRequiredCustomFieldsJsonString(); - w.notes = "Granular"; - w.usertype = 1; - - ApiResponse a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w.ToString()); - Util.ValidateDataReturnResponseOk(a); - InclusiveWidgetIdList.Add(a.ObjectResponse["data"]["id"].Value()); - - //second inclusive widget - w.name = Util.Uniquify(WidgetNameStart); - - a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w.ToString()); - Util.ValidateDataReturnResponseOk(a); - InclusiveWidgetIdList.Add(a.ObjectResponse["data"]["id"].Value()); - - //first exclusive widget - w.name = Util.Uniquify(WidgetNameStart); - w.notes = "Gus Grifferson"; - w.active = false; - - a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w.ToString()); - Util.ValidateDataReturnResponseOk(a); - ExclusiveWidgetIdList.Add(a.ObjectResponse["data"]["id"].Value()); - - //second exclusive widget - w.name = Util.Uniquify(WidgetNameStart); - w.active = false; - - a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w.ToString()); - Util.ValidateDataReturnResponseOk(a); - ExclusiveWidgetIdList.Add(a.ObjectResponse["data"]["id"].Value()); - - - //CREATE LISTVIEW - dynamic dListView = new JArray(); - - //name starts with filter to constrict to widgets that this test block created only - dListView.Add(Util.BuildSimpleFilterDataListViewColumn("widgetname", Util.OpStartsWith, WidgetNameStart)); - - //FILTER - // dynamic DataFilterActive = new JObject(); - // DataFilterActive.fld = "widgetnotes"; - // DataFilterActive.op = Util.OpStartsWith; - // DataFilterActive.value = "Gra"; - dListView.Add(Util.BuildSimpleFilterDataListViewColumn("widgetnotes", Util.OpStartsWith, "Gra")); - - - //FETCH DATALIST - a = await Util.PostAsync($"data-list", await Util.GetTokenAsync("superuser", "l3tm3in"), Util.BuildDataListRequestEx(dListView)); - Util.ValidateDataReturnResponseOk(a); - Util.ValidateHTTPStatusCode(a, 200); - - //assert contains at least two records - ((JArray)a.ObjectResponse["data"]).Count.Should().BeGreaterThan(1); - var v = ((JArray)a.ObjectResponse["data"]); - List IDInResultList = new List(); - int InclusiveMatchCount = 0; - int ExclusiveMatchCount = 0; - foreach (JArray ja in v) - { - JObject o = ja[0] as JObject; - if (InclusiveWidgetIdList.Contains(o["i"].Value())) - InclusiveMatchCount++; - if (ExclusiveWidgetIdList.Contains(o["i"].Value())) - ExclusiveMatchCount++; - } - - InclusiveMatchCount.Should().Be(InclusiveWidgetIdList.Count); - ExclusiveMatchCount.Should().Be(0); - - //DELETE WIDGETS - foreach (long l in InclusiveWidgetIdList) - { - a = await Util.DeleteAsync("widget/" + l.ToString(), await Util.GetTokenAsync("BizAdminFull")); - Util.ValidateHTTPStatusCode(a, 204); - } - - foreach (long l in ExclusiveWidgetIdList) - { - a = await Util.DeleteAsync("widget/" + l.ToString(), await Util.GetTokenAsync("BizAdminFull")); - Util.ValidateHTTPStatusCode(a, 204); - } - - } - - - /// - /// - /// - [Fact] - public async void TextOpEndsWithFilterWorks() - { - var TestName = "TextOpEndsWithFilterWorks"; - var WidgetNameStart = Util.Uniquify(TestName); - - List InclusiveWidgetIdList = new List(); - List ExclusiveWidgetIdList = new List(); - - //CREATE 4 TEST WIDGETS - //two inclusive and two not inclusive - - //first inclusive widget - dynamic w = new JObject(); - w.name = Util.Uniquify(WidgetNameStart); - w.customFields = Util.WidgetRequiredCustomFieldsJsonString(); - w.notes = "Bo Horvat"; - w.usertype = 1; - - ApiResponse a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w.ToString()); - Util.ValidateDataReturnResponseOk(a); - InclusiveWidgetIdList.Add(a.ObjectResponse["data"]["id"].Value()); - - //second inclusive widget - w.name = Util.Uniquify(WidgetNameStart); - - a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w.ToString()); - Util.ValidateDataReturnResponseOk(a); - InclusiveWidgetIdList.Add(a.ObjectResponse["data"]["id"].Value()); - - //first exclusive widget - w.name = Util.Uniquify(WidgetNameStart); - w.notes = "Bo Duke"; - w.active = false; - - a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w.ToString()); - Util.ValidateDataReturnResponseOk(a); - ExclusiveWidgetIdList.Add(a.ObjectResponse["data"]["id"].Value()); - - //second exclusive widget - w.name = Util.Uniquify(WidgetNameStart); - w.active = false; - - a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w.ToString()); - Util.ValidateDataReturnResponseOk(a); - ExclusiveWidgetIdList.Add(a.ObjectResponse["data"]["id"].Value()); - - - //CREATE LISTVIEW - dynamic dListView = new JArray(); - - //name starts with filter to constrict to widgets that this test block created only - dListView.Add(Util.BuildSimpleFilterDataListViewColumn("widgetname", Util.OpStartsWith, WidgetNameStart)); - - //FILTER - // dynamic DataFilterActive = new JObject(); - // DataFilterActive.fld = "widgetnotes"; - // DataFilterActive.op = Util.OpEndsWith; - // DataFilterActive.value = "vat"; - dListView.Add(Util.BuildSimpleFilterDataListViewColumn("widgetnotes", Util.OpEndsWith, "vat")); - - - - //FETCH DATALIST - a = await Util.PostAsync($"data-list", await Util.GetTokenAsync("superuser", "l3tm3in"), Util.BuildDataListRequestEx(dListView)); - Util.ValidateDataReturnResponseOk(a); - Util.ValidateHTTPStatusCode(a, 200); - - //assert contains at least two records - ((JArray)a.ObjectResponse["data"]).Count.Should().BeGreaterThan(1); - var v = ((JArray)a.ObjectResponse["data"]); - List IDInResultList = new List(); - int InclusiveMatchCount = 0; - int ExclusiveMatchCount = 0; - foreach (JArray ja in v) - { - JObject o = ja[0] as JObject; - if (InclusiveWidgetIdList.Contains(o["i"].Value())) - InclusiveMatchCount++; - if (ExclusiveWidgetIdList.Contains(o["i"].Value())) - ExclusiveMatchCount++; - } - - InclusiveMatchCount.Should().Be(InclusiveWidgetIdList.Count); - ExclusiveMatchCount.Should().Be(0); - - //DELETE WIDGETS - foreach (long l in InclusiveWidgetIdList) - { - a = await Util.DeleteAsync("widget/" + l.ToString(), await Util.GetTokenAsync("BizAdminFull")); - Util.ValidateHTTPStatusCode(a, 204); - } - - foreach (long l in ExclusiveWidgetIdList) - { - a = await Util.DeleteAsync("widget/" + l.ToString(), await Util.GetTokenAsync("BizAdminFull")); - Util.ValidateHTTPStatusCode(a, 204); - } - - } - - - //====================== - - #endregion string filter tests - - - - - /////////////////////////////////////////////////////////////////////////////// - //INT - // - #region INTEGER TESTS - - /// - /// - /// - [Fact] - public async void IntegerOpEqualityFilterWorks() - { - - var WidgetNameStart = "IntegerDataFilterTest"; - - long IncludedWidgetId = 0; - long ExcludedWidgetId = 0; - - //CREATE TEST WIDGETS - - - //included widget - dynamic w = new JObject(); - w.name = Util.Uniquify(WidgetNameStart); - w.customFields = Util.WidgetRequiredCustomFieldsJsonString(); - w.active = true; - w.usertype = 1; - w.count = 5; - w.notes = "blah"; - w.customFields = Util.WidgetRequiredCustomFieldsJsonString(); - - ApiResponse a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w.ToString()); - Util.ValidateDataReturnResponseOk(a); - IncludedWidgetId = a.ObjectResponse["data"]["id"].Value(); - - //Excluded widget - w.name = Util.Uniquify(WidgetNameStart); - w.count = 3; - a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w.ToString()); - Util.ValidateDataReturnResponseOk(a); - ExcludedWidgetId = a.ObjectResponse["data"]["id"].Value(); - - //CREATE LISTVIEW - dynamic dListView = new JArray(); - - //name starts with filter to constrict to widgets that this test block created only - dListView.Add(Util.BuildSimpleFilterDataListViewColumn("widgetname", Util.OpStartsWith, WidgetNameStart)); - - //inclusive test filter - - // dynamic FilterItem = new JObject(); - // FilterItem.fld = "widgetcount"; - // FilterItem.op = Util.OpEquality; - // FilterItem.value = 5; - dListView.Add(Util.BuildSimpleFilterDataListViewColumn("widgetcount", Util.OpEquality, 5)); - - //FETCH DATALIST - a = await Util.PostAsync($"data-list", await Util.GetTokenAsync("superuser", "l3tm3in"), Util.BuildDataListRequestEx(dListView)); - Util.ValidateDataReturnResponseOk(a); - Util.ValidateHTTPStatusCode(a, 200); - - //assert contains at least this test record - ((JArray)a.ObjectResponse["data"]).Count.Should().BeGreaterThan(0); - var v = ((JArray)a.ObjectResponse["data"]); - List IDInResultList = new List(); - int InclusiveMatchCount = 0; - int ExclusiveMatchCount = 0; - foreach (JArray ja in v) - { - JObject o = ja[0] as JObject; - if (IncludedWidgetId == o["i"].Value()) - InclusiveMatchCount++; - if (ExcludedWidgetId == o["i"].Value()) - ExclusiveMatchCount++; - } - - InclusiveMatchCount.Should().BeGreaterOrEqualTo(1); - ExclusiveMatchCount.Should().Be(0); - - //DELETE WIDGETS - a = await Util.DeleteAsync("widget/" + IncludedWidgetId.ToString(), await Util.GetTokenAsync("BizAdminFull")); - Util.ValidateHTTPStatusCode(a, 204); - - a = await Util.DeleteAsync("widget/" + ExcludedWidgetId.ToString(), await Util.GetTokenAsync("BizAdminFull")); - Util.ValidateHTTPStatusCode(a, 204); - - } - - /// - /// - /// - [Fact] - public async void IntegerOpGreaterThanFilterWorks() - { - - var WidgetNameStart = "IntegerOpGreaterThanFilterWorks"; - - long IncludedWidgetId = 0; - long ExcludedWidgetId = 0; - - //CREATE TEST WIDGETS - - //included widget - dynamic w = new JObject(); - w.name = Util.Uniquify(WidgetNameStart); - w.customFields = Util.WidgetRequiredCustomFieldsJsonString(); - w.notes = "blah"; - w.active = true; - w.usertype = 1; - w.count = 55; - - ApiResponse a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w.ToString()); - Util.ValidateDataReturnResponseOk(a); - IncludedWidgetId = a.ObjectResponse["data"]["id"].Value(); - - //Excluded widget - w.name = Util.Uniquify(WidgetNameStart); - w.count = -55; - a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w.ToString()); - Util.ValidateDataReturnResponseOk(a); - ExcludedWidgetId = a.ObjectResponse["data"]["id"].Value(); - - - //CREATE LISTVIEW - dynamic dListView = new JArray(); - - //name starts with filter to constrict to widgets that this test block created only - dListView.Add(Util.BuildSimpleFilterDataListViewColumn("widgetname", Util.OpStartsWith, WidgetNameStart)); - - //inclusive test filter - - // dynamic FilterItem = new JObject(); - // FilterItem.fld = "widgetcount"; - // FilterItem.op = Util.OpGreaterThan; - // FilterItem.value = 54; - dListView.Add(Util.BuildSimpleFilterDataListViewColumn("widgetcount", Util.OpGreaterThan, 54)); - //FETCH DATALIST - a = await Util.PostAsync($"data-list", await Util.GetTokenAsync("superuser", "l3tm3in"), Util.BuildDataListRequestEx(dListView)); - Util.ValidateDataReturnResponseOk(a); - Util.ValidateHTTPStatusCode(a, 200); - - //assert contains at least this test record - ((JArray)a.ObjectResponse["data"]).Count.Should().BeGreaterThan(0); - var v = ((JArray)a.ObjectResponse["data"]); - List IDInResultList = new List(); - int InclusiveMatchCount = 0; - int ExclusiveMatchCount = 0; - foreach (JArray ja in v) - { - JObject o = ja[0] as JObject; - if (IncludedWidgetId == o["i"].Value()) - InclusiveMatchCount++; - if (ExcludedWidgetId == o["i"].Value()) - ExclusiveMatchCount++; - } - - InclusiveMatchCount.Should().BeGreaterOrEqualTo(1); - ExclusiveMatchCount.Should().Be(0); - - //DELETE WIDGETS - a = await Util.DeleteAsync("widget/" + IncludedWidgetId.ToString(), await Util.GetTokenAsync("BizAdminFull")); - Util.ValidateHTTPStatusCode(a, 204); - - a = await Util.DeleteAsync("widget/" + ExcludedWidgetId.ToString(), await Util.GetTokenAsync("BizAdminFull")); - Util.ValidateHTTPStatusCode(a, 204); - - } - - /// - /// - /// - [Fact] - public async void IntegerOpGreaterThanOrEqualToFilterWorks() - { - - var WidgetNameStart = "IntegerOpGreaterThanOrEqualToFilterWorks"; - - long IncludedWidgetId = 0; - long ExcludedWidgetId = 0; - - //CREATE TEST WIDGETS - - //included widget - dynamic w = new JObject(); - w.name = Util.Uniquify(WidgetNameStart); - w.customFields = Util.WidgetRequiredCustomFieldsJsonString(); - w.notes = "blah"; - w.active = true; - w.usertype = 1; - w.count = 555; - - ApiResponse a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w.ToString()); - Util.ValidateDataReturnResponseOk(a); - IncludedWidgetId = a.ObjectResponse["data"]["id"].Value(); - - //Excluded widget - w.name = Util.Uniquify(WidgetNameStart); - w.count = 554; - a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w.ToString()); - Util.ValidateDataReturnResponseOk(a); - ExcludedWidgetId = a.ObjectResponse["data"]["id"].Value(); - - - //CREATE LISTVIEW - dynamic dListView = new JArray(); - - //name starts with filter to constrict to widgets that this test block created only - dListView.Add(Util.BuildSimpleFilterDataListViewColumn("widgetname", Util.OpStartsWith, WidgetNameStart)); - - //inclusive test filter - - // dynamic FilterItem = new JObject(); - // FilterItem.fld = "widgetcount"; - // FilterItem.op = Util.OpGreaterThanOrEqualTo; - // FilterItem.value = 555; - dListView.Add(Util.BuildSimpleFilterDataListViewColumn("widgetcount", Util.OpGreaterThanOrEqualTo, 555)); - //FETCH DATALIST - a = await Util.PostAsync($"data-list", await Util.GetTokenAsync("superuser", "l3tm3in"), Util.BuildDataListRequestEx(dListView)); - Util.ValidateDataReturnResponseOk(a); - Util.ValidateHTTPStatusCode(a, 200); - - //assert contains at least this test record - ((JArray)a.ObjectResponse["data"]).Count.Should().BeGreaterThan(0); - var v = ((JArray)a.ObjectResponse["data"]); - List IDInResultList = new List(); - int InclusiveMatchCount = 0; - int ExclusiveMatchCount = 0; - foreach (JArray ja in v) - { - JObject o = ja[0] as JObject; - if (IncludedWidgetId == o["i"].Value()) - InclusiveMatchCount++; - if (ExcludedWidgetId == o["i"].Value()) - ExclusiveMatchCount++; - } - - InclusiveMatchCount.Should().BeGreaterOrEqualTo(1); - ExclusiveMatchCount.Should().Be(0); - - //DELETE WIDGETS - a = await Util.DeleteAsync("widget/" + IncludedWidgetId.ToString(), await Util.GetTokenAsync("BizAdminFull")); - Util.ValidateHTTPStatusCode(a, 204); - - a = await Util.DeleteAsync("widget/" + ExcludedWidgetId.ToString(), await Util.GetTokenAsync("BizAdminFull")); - Util.ValidateHTTPStatusCode(a, 204); - - } - - - - /// - /// - /// - [Fact] - public async void IntegerOpLessThanFilterWorks() - { - - var WidgetNameStart = "IntegerOpLessThanFilterWorks"; - - long IncludedWidgetId = 0; - long ExcludedWidgetId = 0; - - //CREATE TEST WIDGETS - - //included widget - dynamic w = new JObject(); - w.name = Util.Uniquify(WidgetNameStart); - w.customFields = Util.WidgetRequiredCustomFieldsJsonString(); - w.notes = "blah"; - w.active = true; - w.usertype = 1; - w.count = -5555; - - ApiResponse a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w.ToString()); - Util.ValidateDataReturnResponseOk(a); - IncludedWidgetId = a.ObjectResponse["data"]["id"].Value(); - - //Excluded widget - w.name = Util.Uniquify(WidgetNameStart); - w.count = 5555; - a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w.ToString()); - Util.ValidateDataReturnResponseOk(a); - ExcludedWidgetId = a.ObjectResponse["data"]["id"].Value(); - - - //CREATE LISTVIEW - dynamic dListView = new JArray(); - - //name starts with filter to constrict to widgets that this test block created only - dListView.Add(Util.BuildSimpleFilterDataListViewColumn("widgetname", Util.OpStartsWith, WidgetNameStart)); - - //inclusive test filter - - // dynamic FilterItem = new JObject(); - // FilterItem.fld = "widgetcount"; - // FilterItem.op = Util.OpLessThan; - // FilterItem.value = 5555; - dListView.Add(Util.BuildSimpleFilterDataListViewColumn("widgetcount", Util.OpLessThan, 5555)); - //FETCH DATALIST - a = await Util.PostAsync($"data-list", await Util.GetTokenAsync("superuser", "l3tm3in"), Util.BuildDataListRequestEx(dListView)); - Util.ValidateDataReturnResponseOk(a); - Util.ValidateHTTPStatusCode(a, 200); - - //assert contains at least this test record - ((JArray)a.ObjectResponse["data"]).Count.Should().BeGreaterThan(0); - var v = ((JArray)a.ObjectResponse["data"]); - List IDInResultList = new List(); - int InclusiveMatchCount = 0; - int ExclusiveMatchCount = 0; - foreach (JArray ja in v) - { - JObject o = ja[0] as JObject; - if (IncludedWidgetId == o["i"].Value()) - InclusiveMatchCount++; - if (ExcludedWidgetId == o["i"].Value()) - ExclusiveMatchCount++; - } - - InclusiveMatchCount.Should().BeGreaterOrEqualTo(1); - ExclusiveMatchCount.Should().Be(0); - - //DELETE WIDGETS - a = await Util.DeleteAsync("widget/" + IncludedWidgetId.ToString(), await Util.GetTokenAsync("BizAdminFull")); - Util.ValidateHTTPStatusCode(a, 204); - - a = await Util.DeleteAsync("widget/" + ExcludedWidgetId.ToString(), await Util.GetTokenAsync("BizAdminFull")); - Util.ValidateHTTPStatusCode(a, 204); - - } - - - /// - /// - /// - [Fact] - public async void IntegerOpLessThanOrEqualToFilterWorks() - { - - var WidgetNameStart = "IntegerOpLessThanOrEqualToFilterWorks"; - - long IncludedWidgetId = 0; - long ExcludedWidgetId = 0; - - //CREATE TEST WIDGETS - - //included widget - dynamic w = new JObject(); - w.name = Util.Uniquify(WidgetNameStart); - w.customFields = Util.WidgetRequiredCustomFieldsJsonString(); - w.notes = "blah"; - w.active = true; - w.usertype = 1; - w.count = -444; - - ApiResponse a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w.ToString()); - Util.ValidateDataReturnResponseOk(a); - IncludedWidgetId = a.ObjectResponse["data"]["id"].Value(); - - //Excluded widget - w.name = Util.Uniquify(WidgetNameStart); - w.count = -443; - a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w.ToString()); - Util.ValidateDataReturnResponseOk(a); - ExcludedWidgetId = a.ObjectResponse["data"]["id"].Value(); - - - //CREATE LISTVIEW - dynamic dListView = new JArray(); - - //name starts with filter to constrict to widgets that this test block created only - dListView.Add(Util.BuildSimpleFilterDataListViewColumn("widgetname", Util.OpStartsWith, WidgetNameStart)); - - //inclusive test filter - - // dynamic FilterItem = new JObject(); - // FilterItem.fld = "widgetcount"; - // FilterItem.op = Util.OpLessThanOrEqualTo; - // FilterItem.value = -444; - dListView.Add(Util.BuildSimpleFilterDataListViewColumn("widgetcount", Util.OpLessThanOrEqualTo, -444)); - //FETCH DATALIST - a = await Util.PostAsync($"data-list", await Util.GetTokenAsync("superuser", "l3tm3in"), Util.BuildDataListRequestEx(dListView)); - Util.ValidateDataReturnResponseOk(a); - Util.ValidateHTTPStatusCode(a, 200); - - //assert contains at least this test record - ((JArray)a.ObjectResponse["data"]).Count.Should().BeGreaterThan(0); - var v = ((JArray)a.ObjectResponse["data"]); - List IDInResultList = new List(); - int InclusiveMatchCount = 0; - int ExclusiveMatchCount = 0; - foreach (JArray ja in v) - { - JObject o = ja[0] as JObject; - if (IncludedWidgetId == o["i"].Value()) - InclusiveMatchCount++; - if (ExcludedWidgetId == o["i"].Value()) - ExclusiveMatchCount++; - } - - InclusiveMatchCount.Should().BeGreaterOrEqualTo(1); - ExclusiveMatchCount.Should().Be(0); - - //DELETE WIDGETS - a = await Util.DeleteAsync("widget/" + IncludedWidgetId.ToString(), await Util.GetTokenAsync("BizAdminFull")); - Util.ValidateHTTPStatusCode(a, 204); - - a = await Util.DeleteAsync("widget/" + ExcludedWidgetId.ToString(), await Util.GetTokenAsync("BizAdminFull")); - Util.ValidateHTTPStatusCode(a, 204); - } - - - - /// - /// - /// - [Fact] - public async void IntegerNotEqualToFilterWorks() - { - - var WidgetNameStart = "IntegerNotEqualToFilterWorks"; - - long IncludedWidgetId = 0; - long ExcludedWidgetId = 0; - - //CREATE TEST WIDGETS - - //included widget - dynamic w = new JObject(); - w.name = Util.Uniquify(WidgetNameStart); - w.customFields = Util.WidgetRequiredCustomFieldsJsonString(); - w.notes = "blah"; - w.active = true; - w.usertype = 1; - w.count = 222; - - ApiResponse a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w.ToString()); - Util.ValidateDataReturnResponseOk(a); - IncludedWidgetId = a.ObjectResponse["data"]["id"].Value(); - - //Excluded widget - w.name = Util.Uniquify(WidgetNameStart); - w.count = 223; - a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w.ToString()); - Util.ValidateDataReturnResponseOk(a); - ExcludedWidgetId = a.ObjectResponse["data"]["id"].Value(); - - - //CREATE LISTVIEW - dynamic dListView = new JArray(); - - //name starts with filter to constrict to widgets that this test block created only - dListView.Add(Util.BuildSimpleFilterDataListViewColumn("widgetname", Util.OpStartsWith, WidgetNameStart)); - - //inclusive test filter - - // dynamic FilterItem = new JObject(); - // FilterItem.fld = "widgetcount"; - // FilterItem.op = Util.OpNotEqual; - // FilterItem.value = 223; - dListView.Add(Util.BuildSimpleFilterDataListViewColumn("widgetcount", Util.OpNotEqual, 223)); - //FETCH DATALIST - a = await Util.PostAsync($"data-list", await Util.GetTokenAsync("superuser", "l3tm3in"), Util.BuildDataListRequestEx(dListView)); - Util.ValidateDataReturnResponseOk(a); - Util.ValidateHTTPStatusCode(a, 200); - - //assert contains at least this test record - ((JArray)a.ObjectResponse["data"]).Count.Should().BeGreaterThan(0); - var v = ((JArray)a.ObjectResponse["data"]); - List IDInResultList = new List(); - int InclusiveMatchCount = 0; - int ExclusiveMatchCount = 0; - foreach (JArray ja in v) - { - JObject o = ja[0] as JObject; - if (IncludedWidgetId == o["i"].Value()) - InclusiveMatchCount++; - if (ExcludedWidgetId == o["i"].Value()) - ExclusiveMatchCount++; - } - - InclusiveMatchCount.Should().BeGreaterOrEqualTo(1); - ExclusiveMatchCount.Should().Be(0); - - //DELETE WIDGETS - a = await Util.DeleteAsync("widget/" + IncludedWidgetId.ToString(), await Util.GetTokenAsync("BizAdminFull")); - Util.ValidateHTTPStatusCode(a, 204); - - a = await Util.DeleteAsync("widget/" + ExcludedWidgetId.ToString(), await Util.GetTokenAsync("BizAdminFull")); - Util.ValidateHTTPStatusCode(a, 204); - - } - #endregion integer tests - - - /////////////////////////////////////////////////////////////////////////////// - //BOOL - // - - #region BOOLEAN TESTS - - /// - /// - /// - [Fact] - public async void BoolOpEqualityFilterWorks() - { - //OPS: equal to, not equal to - //values: true, false - - var WidgetNameStart = "BoolDataFilterTest"; - - List ActiveWidgetIdList = new List(); - List NotActiveWidgetIdList = new List(); - - //CREATE 4 TEST WIDGETS - //two active and two non active - - //first active widget - dynamic w = new JObject(); - w.name = Util.Uniquify(WidgetNameStart); - w.customFields = Util.WidgetRequiredCustomFieldsJsonString(); - w.notes = "blah"; - w.active = true; - w.usertype = 1; - - ApiResponse a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w.ToString()); - Util.ValidateDataReturnResponseOk(a); - ActiveWidgetIdList.Add(a.ObjectResponse["data"]["id"].Value()); - - //second active widget - w.name = Util.Uniquify(WidgetNameStart); - - a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w.ToString()); - Util.ValidateDataReturnResponseOk(a); - ActiveWidgetIdList.Add(a.ObjectResponse["data"]["id"].Value()); - - - //first NON active widget - w.name = Util.Uniquify(WidgetNameStart); - w.active = false; - - a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w.ToString()); - Util.ValidateDataReturnResponseOk(a); - NotActiveWidgetIdList.Add(a.ObjectResponse["data"]["id"].Value()); - - //second NON active widget - w.name = Util.Uniquify(WidgetNameStart); - w.active = false; - - a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w.ToString()); - Util.ValidateDataReturnResponseOk(a); - NotActiveWidgetIdList.Add(a.ObjectResponse["data"]["id"].Value()); - - - //CREATE LISTVIEW - dynamic dListView = new JArray(); - - //name starts with filter to constrict to widgets that this test block created only - dListView.Add(Util.BuildSimpleFilterDataListViewColumn("widgetname", Util.OpStartsWith, WidgetNameStart)); - - //FILTER - // dynamic DataFilterActive = new JObject(); - // DataFilterActive.fld = "widgetactive"; - // DataFilterActive.op = Util.OpEquality; - // DataFilterActive.value = true; - dListView.Add(Util.BuildSimpleFilterDataListViewColumn("widgetactive", Util.OpEquality, true)); - - - //FETCH DATALIST - a = await Util.PostAsync($"data-list", await Util.GetTokenAsync("superuser", "l3tm3in"), Util.BuildDataListRequestEx(dListView)); - Util.ValidateDataReturnResponseOk(a); - Util.ValidateHTTPStatusCode(a, 200); - - //assert contains at least two records - ((JArray)a.ObjectResponse["data"]).Count.Should().BeGreaterThan(1); - var v = ((JArray)a.ObjectResponse["data"]); - // List IDInResultList = new List(); - int nActiveMatches = 0; - int nInactiveMatches = 0; - - foreach (JArray ja in v) - { - JObject o = ja[0] as JObject; - - - if (ActiveWidgetIdList.Contains(o["i"].Value())) - nActiveMatches++; - //if (NotActiveWidgetIdList.Contains(o["i"].Value())) - if (NotActiveWidgetIdList.Contains(o["i"].Value())) - nInactiveMatches++; - } - - nActiveMatches.Should().Be(ActiveWidgetIdList.Count); - nInactiveMatches.Should().Be(0); - - //DELETE WIDGETS - foreach (long l in ActiveWidgetIdList) - { - a = await Util.DeleteAsync("widget/" + l.ToString(), await Util.GetTokenAsync("BizAdminFull")); - Util.ValidateHTTPStatusCode(a, 204); - } - - foreach (long l in NotActiveWidgetIdList) - { - a = await Util.DeleteAsync("widget/" + l.ToString(), await Util.GetTokenAsync("BizAdminFull")); - Util.ValidateHTTPStatusCode(a, 204); - } - } - - - - /// - /// - /// - [Fact] - public async void BoolOpNotEqualFilterWorks() - { - - //OPS: equal to, not equal to - //values: true, false - - var WidgetNameStart = "BoolDataFilterTest"; - - List ActiveWidgetIdList = new List(); - List NotActiveWidgetIdList = new List(); - - //CREATE 4 TEST WIDGETS - //two active and two non active - - //first active widget - dynamic w = new JObject(); - w.name = Util.Uniquify(WidgetNameStart); - w.customFields = Util.WidgetRequiredCustomFieldsJsonString(); - w.notes = "blah"; - w.active = true; - w.usertype = 1; - - ApiResponse a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w.ToString()); - Util.ValidateDataReturnResponseOk(a); - ActiveWidgetIdList.Add(a.ObjectResponse["data"]["id"].Value()); - - //second active widget - w.name = Util.Uniquify(WidgetNameStart); - - a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w.ToString()); - Util.ValidateDataReturnResponseOk(a); - ActiveWidgetIdList.Add(a.ObjectResponse["data"]["id"].Value()); - - - //first NON active widget - w.name = Util.Uniquify(WidgetNameStart); - w.active = false; - - a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w.ToString()); - Util.ValidateDataReturnResponseOk(a); - NotActiveWidgetIdList.Add(a.ObjectResponse["data"]["id"].Value()); - - //second NON active widget - w.name = Util.Uniquify(WidgetNameStart); - w.active = false; - - a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w.ToString()); - Util.ValidateDataReturnResponseOk(a); - NotActiveWidgetIdList.Add(a.ObjectResponse["data"]["id"].Value()); - - - //CREATE LISTVIEW - dynamic dListView = new JArray(); - - //name starts with filter to constrict to widgets that this test block created only - dListView.Add(Util.BuildSimpleFilterDataListViewColumn("widgetname", Util.OpStartsWith, WidgetNameStart)); - - //FILTER - // dynamic DataFilterActive = new JObject(); - // DataFilterActive.fld = "widgetactive"; - // DataFilterActive.op = Util.OpNotEqual; - // DataFilterActive.value = true; - dListView.Add(Util.BuildSimpleFilterDataListViewColumn("widgetactive", Util.OpNotEqual, true)); - - - - //FETCH DATALIST - a = await Util.PostAsync($"data-list", await Util.GetTokenAsync("superuser", "l3tm3in"), Util.BuildDataListRequestEx(dListView)); - Util.ValidateDataReturnResponseOk(a); - Util.ValidateHTTPStatusCode(a, 200); - - //assert contains at least two records - ((JArray)a.ObjectResponse["data"]).Count.Should().BeGreaterThan(1); - var v = ((JArray)a.ObjectResponse["data"]); - List IDInResultList = new List(); - int nActiveMatches = 0; - int nInactiveMatches = 0; - - foreach (JArray ja in v) - { - JObject o = ja[0] as JObject; - - if (ActiveWidgetIdList.Contains(o["i"].Value())) - nActiveMatches++; - if (NotActiveWidgetIdList.Contains(o["i"].Value())) - nInactiveMatches++; - } - - nInactiveMatches.Should().Be(NotActiveWidgetIdList.Count); - nActiveMatches.Should().Be(0); - - //DELETE WIDGETS - foreach (long l in ActiveWidgetIdList) - { - a = await Util.DeleteAsync("widget/" + l.ToString(), await Util.GetTokenAsync("BizAdminFull")); - Util.ValidateHTTPStatusCode(a, 204); - } - - foreach (long l in NotActiveWidgetIdList) - { - a = await Util.DeleteAsync("widget/" + l.ToString(), await Util.GetTokenAsync("BizAdminFull")); - Util.ValidateHTTPStatusCode(a, 204); - } - - - } - - #endregion boolean tests - - - /////////////////////////////////////////////////////////////////////////////// - //DECIMAL - // - #region DECIMAL TESTS - - /// - /// - /// - [Fact] - public async void DecimalOpEqualityFilterWorks() - { - - var WidgetNameStart = "DecimalOpEqualityFilterWorks"; - - long IncludedWidgetId = 0; - long ExcludedWidgetId = 0; - - //CREATE TEST WIDGETS - - - //included widget - dynamic w = new JObject(); - w.name = Util.Uniquify(WidgetNameStart); - w.customFields = Util.WidgetRequiredCustomFieldsJsonString(); - w.notes = "blah"; - w.active = true; - w.usertype = 1; - w.dollarAmount = 5.55; - - ApiResponse a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w.ToString()); - Util.ValidateDataReturnResponseOk(a); - IncludedWidgetId = a.ObjectResponse["data"]["id"].Value(); - - //Excluded widget - w.name = Util.Uniquify(WidgetNameStart); - w.dollarAmount = 3.33; - a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w.ToString()); - Util.ValidateDataReturnResponseOk(a); - ExcludedWidgetId = a.ObjectResponse["data"]["id"].Value(); - - //CREATE LISTVIEW - dynamic dListView = new JArray(); - - //name starts with filter to constrict to widgets that this test block created only - dListView.Add(Util.BuildSimpleFilterDataListViewColumn("widgetname", Util.OpStartsWith, WidgetNameStart)); - - //inclusive test filter - - // dynamic FilterItem = new JObject(); - // FilterItem.fld = "widgetdollaramount"; - // FilterItem.op = Util.OpEquality; - // FilterItem.value = 5.55; - dListView.Add(Util.BuildSimpleFilterDataListViewColumn("widgetdollaramount", Util.OpEquality, 5.55)); - //FETCH DATALIST - a = await Util.PostAsync($"data-list", await Util.GetTokenAsync("superuser", "l3tm3in"), Util.BuildDataListRequestEx(dListView)); - Util.ValidateDataReturnResponseOk(a); - Util.ValidateHTTPStatusCode(a, 200); - - //assert contains at least this test record - ((JArray)a.ObjectResponse["data"]).Count.Should().BeGreaterThan(0); - var v = ((JArray)a.ObjectResponse["data"]); - List IDInResultList = new List(); - int InclusiveMatchCount = 0; - int ExclusiveMatchCount = 0; - foreach (JArray ja in v) - { - JObject o = ja[0] as JObject; - if (IncludedWidgetId == o["i"].Value()) - InclusiveMatchCount++; - if (ExcludedWidgetId == o["i"].Value()) - ExclusiveMatchCount++; - } - - InclusiveMatchCount.Should().BeGreaterOrEqualTo(1); - ExclusiveMatchCount.Should().Be(0); - - //DELETE WIDGETS - a = await Util.DeleteAsync("widget/" + IncludedWidgetId.ToString(), await Util.GetTokenAsync("BizAdminFull")); - Util.ValidateHTTPStatusCode(a, 204); - - a = await Util.DeleteAsync("widget/" + ExcludedWidgetId.ToString(), await Util.GetTokenAsync("BizAdminFull")); - Util.ValidateHTTPStatusCode(a, 204); - - } - - /// - /// - /// - [Fact] - public async void DecimalOpGreaterThanFilterWorks() - { - - var WidgetNameStart = "DecimalOpGreaterThanFilterWorks"; - - long IncludedWidgetId = 0; - long ExcludedWidgetId = 0; - - //CREATE TEST WIDGETS - - //included widget - dynamic w = new JObject(); - w.name = Util.Uniquify(WidgetNameStart); - w.customFields = Util.WidgetRequiredCustomFieldsJsonString(); - w.notes = "blah"; - w.active = true; - w.usertype = 1; - w.dollarAmount = 55.55; - - ApiResponse a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w.ToString()); - Util.ValidateDataReturnResponseOk(a); - IncludedWidgetId = a.ObjectResponse["data"]["id"].Value(); - - //Excluded widget - w.name = Util.Uniquify(WidgetNameStart); - w.dollarAmount = -55.55; - a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w.ToString()); - Util.ValidateDataReturnResponseOk(a); - ExcludedWidgetId = a.ObjectResponse["data"]["id"].Value(); - - - //CREATE LISTVIEW - dynamic dListView = new JArray(); - - //name starts with filter to constrict to widgets that this test block created only - dListView.Add(Util.BuildSimpleFilterDataListViewColumn("widgetname", Util.OpStartsWith, WidgetNameStart)); - - //inclusive test filter - - // dynamic FilterItem = new JObject(); - // FilterItem.fld = "widgetdollaramount"; - // FilterItem.op = Util.OpGreaterThan; - // FilterItem.value = 54.44; - dListView.Add(Util.BuildSimpleFilterDataListViewColumn("widgetdollaramount", Util.OpGreaterThan, 54.44)); - - //FETCH DATALIST - a = await Util.PostAsync($"data-list", await Util.GetTokenAsync("superuser", "l3tm3in"), Util.BuildDataListRequestEx(dListView)); - Util.ValidateDataReturnResponseOk(a); - Util.ValidateHTTPStatusCode(a, 200); - - //assert contains at least this test record - ((JArray)a.ObjectResponse["data"]).Count.Should().BeGreaterThan(0); - var v = ((JArray)a.ObjectResponse["data"]); - List IDInResultList = new List(); - int InclusiveMatchCount = 0; - int ExclusiveMatchCount = 0; - foreach (JArray ja in v) - { - JObject o = ja[0] as JObject; - if (IncludedWidgetId == o["i"].Value()) - InclusiveMatchCount++; - if (ExcludedWidgetId == o["i"].Value()) - ExclusiveMatchCount++; - } - - InclusiveMatchCount.Should().BeGreaterOrEqualTo(1); - ExclusiveMatchCount.Should().Be(0); - - //DELETE WIDGETS - a = await Util.DeleteAsync("widget/" + IncludedWidgetId.ToString(), await Util.GetTokenAsync("BizAdminFull")); - Util.ValidateHTTPStatusCode(a, 204); - - a = await Util.DeleteAsync("widget/" + ExcludedWidgetId.ToString(), await Util.GetTokenAsync("BizAdminFull")); - Util.ValidateHTTPStatusCode(a, 204); - - } - - /// - /// - /// - [Fact] - public async void DecimalOpGreaterThanOrEqualToFilterWorks() - { - - var WidgetNameStart = "DecimalOpGreaterThanOrEqualToFilterWorks"; - - long IncludedWidgetId = 0; - long ExcludedWidgetId = 0; - - //CREATE TEST WIDGETS - - //included widget - dynamic w = new JObject(); - w.name = Util.Uniquify(WidgetNameStart); - w.customFields = Util.WidgetRequiredCustomFieldsJsonString(); - w.notes = "blah"; - w.active = true; - w.usertype = 1; - w.dollarAmount = 555.55; - - ApiResponse a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w.ToString()); - Util.ValidateDataReturnResponseOk(a); - IncludedWidgetId = a.ObjectResponse["data"]["id"].Value(); - - //Excluded widget - w.name = Util.Uniquify(WidgetNameStart); - w.dollarAmount = 554.54; - a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w.ToString()); - Util.ValidateDataReturnResponseOk(a); - ExcludedWidgetId = a.ObjectResponse["data"]["id"].Value(); - - - //CREATE LISTVIEW - dynamic dListView = new JArray(); - - //name starts with filter to constrict to widgets that this test block created only - dListView.Add(Util.BuildSimpleFilterDataListViewColumn("widgetname", Util.OpStartsWith, WidgetNameStart)); - - //inclusive test filter - - // dynamic FilterItem = new JObject(); - // FilterItem.fld = "widgetdollaramount"; - // FilterItem.op = Util.OpGreaterThanOrEqualTo; - // FilterItem.value = 555.55; - dListView.Add(Util.BuildSimpleFilterDataListViewColumn("widgetdollaramount", Util.OpGreaterThanOrEqualTo, 555.55)); - - //FETCH DATALIST - a = await Util.PostAsync($"data-list", await Util.GetTokenAsync("superuser", "l3tm3in"), Util.BuildDataListRequestEx(dListView)); - Util.ValidateDataReturnResponseOk(a); - Util.ValidateHTTPStatusCode(a, 200); - - //assert contains at least this test record - ((JArray)a.ObjectResponse["data"]).Count.Should().BeGreaterThan(0); - var v = ((JArray)a.ObjectResponse["data"]); - List IDInResultList = new List(); - int InclusiveMatchCount = 0; - int ExclusiveMatchCount = 0; - foreach (JArray ja in v) - { - JObject o = ja[0] as JObject; - if (IncludedWidgetId == o["i"].Value()) - InclusiveMatchCount++; - if (ExcludedWidgetId == o["i"].Value()) - ExclusiveMatchCount++; - } - - InclusiveMatchCount.Should().BeGreaterOrEqualTo(1); - ExclusiveMatchCount.Should().Be(0); - - //DELETE WIDGETS - a = await Util.DeleteAsync("widget/" + IncludedWidgetId.ToString(), await Util.GetTokenAsync("BizAdminFull")); - Util.ValidateHTTPStatusCode(a, 204); - - a = await Util.DeleteAsync("widget/" + ExcludedWidgetId.ToString(), await Util.GetTokenAsync("BizAdminFull")); - Util.ValidateHTTPStatusCode(a, 204); - - } - - - - /// - /// - /// - [Fact] - public async void DecimalOpLessThanFilterWorks() - { - - var WidgetNameStart = "DecimalOpLessThanFilterWorks"; - - long IncludedWidgetId = 0; - long ExcludedWidgetId = 0; - - //CREATE TEST WIDGETS - - //included widget - dynamic w = new JObject(); - w.name = Util.Uniquify(WidgetNameStart); - w.customFields = Util.WidgetRequiredCustomFieldsJsonString(); - w.notes = "blah"; - w.active = true; - w.usertype = 1; - w.dollarAmount = -5555.55; - - ApiResponse a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w.ToString()); - Util.ValidateDataReturnResponseOk(a); - IncludedWidgetId = a.ObjectResponse["data"]["id"].Value(); - - //Excluded widget - w.name = Util.Uniquify(WidgetNameStart); - w.dollarAmount = 5555.55; - a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w.ToString()); - Util.ValidateDataReturnResponseOk(a); - ExcludedWidgetId = a.ObjectResponse["data"]["id"].Value(); - - - //CREATE LISTVIEW - dynamic dListView = new JArray(); - - //name starts with filter to constrict to widgets that this test block created only - dListView.Add(Util.BuildSimpleFilterDataListViewColumn("widgetname", Util.OpStartsWith, WidgetNameStart)); - - //inclusive test filter - - // dynamic FilterItem = new JObject(); - // FilterItem.fld = "widgetdollaramount"; - // FilterItem.op = Util.OpLessThan; - // FilterItem.value = 5555.55; - dListView.Add(Util.BuildSimpleFilterDataListViewColumn("widgetdollaramount", Util.OpLessThan, 5555.55)); - - //FETCH DATALIST - a = await Util.PostAsync($"data-list", await Util.GetTokenAsync("superuser", "l3tm3in"), Util.BuildDataListRequestEx(dListView)); - Util.ValidateDataReturnResponseOk(a); - Util.ValidateHTTPStatusCode(a, 200); - - //assert contains at least this test record - ((JArray)a.ObjectResponse["data"]).Count.Should().BeGreaterThan(0); - var v = ((JArray)a.ObjectResponse["data"]); - List IDInResultList = new List(); - int InclusiveMatchCount = 0; - int ExclusiveMatchCount = 0; - foreach (JArray ja in v) - { - JObject o = ja[0] as JObject; - if (IncludedWidgetId == o["i"].Value()) - InclusiveMatchCount++; - if (ExcludedWidgetId == o["i"].Value()) - ExclusiveMatchCount++; - } - - InclusiveMatchCount.Should().BeGreaterOrEqualTo(1); - ExclusiveMatchCount.Should().Be(0); - - //DELETE WIDGETS - a = await Util.DeleteAsync("widget/" + IncludedWidgetId.ToString(), await Util.GetTokenAsync("BizAdminFull")); - Util.ValidateHTTPStatusCode(a, 204); - - a = await Util.DeleteAsync("widget/" + ExcludedWidgetId.ToString(), await Util.GetTokenAsync("BizAdminFull")); - Util.ValidateHTTPStatusCode(a, 204); - - } - - - /// - /// - /// - [Fact] - public async void DecimalOpLessThanOrEqualToFilterWorks() - { - - var WidgetNameStart = "DecimalOpLessThanOrEqualToFilterWorks"; - - long IncludedWidgetId = 0; - long ExcludedWidgetId = 0; - - //CREATE TEST WIDGETS - - //included widget - dynamic w = new JObject(); - w.name = Util.Uniquify(WidgetNameStart); - w.customFields = Util.WidgetRequiredCustomFieldsJsonString(); - w.notes = "blah"; - w.active = true; - w.usertype = 1; - w.dollarAmount = -444.44; - - ApiResponse a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w.ToString()); - Util.ValidateDataReturnResponseOk(a); - IncludedWidgetId = a.ObjectResponse["data"]["id"].Value(); - - //Excluded widget - w.name = Util.Uniquify(WidgetNameStart); - w.dollarAmount = -443.43; - a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w.ToString()); - Util.ValidateDataReturnResponseOk(a); - ExcludedWidgetId = a.ObjectResponse["data"]["id"].Value(); - - - //CREATE LISTVIEW - dynamic dListView = new JArray(); - - //name starts with filter to constrict to widgets that this test block created only - dListView.Add(Util.BuildSimpleFilterDataListViewColumn("widgetname", Util.OpStartsWith, WidgetNameStart)); - - //inclusive test filter - - // dynamic FilterItem = new JObject(); - // FilterItem.fld = "widgetdollaramount"; - // FilterItem.op = Util.OpLessThanOrEqualTo; - // FilterItem.value = -444.44; - dListView.Add(Util.BuildSimpleFilterDataListViewColumn("widgetdollaramount", Util.OpLessThanOrEqualTo, -444.44)); - - //FETCH DATALIST - a = await Util.PostAsync($"data-list", await Util.GetTokenAsync("superuser", "l3tm3in"), Util.BuildDataListRequestEx(dListView)); - Util.ValidateDataReturnResponseOk(a); - Util.ValidateHTTPStatusCode(a, 200); - - //assert contains at least this test record - ((JArray)a.ObjectResponse["data"]).Count.Should().BeGreaterThan(0); - var v = ((JArray)a.ObjectResponse["data"]); - List IDInResultList = new List(); - int InclusiveMatchCount = 0; - int ExclusiveMatchCount = 0; - foreach (JArray ja in v) - { - JObject o = ja[0] as JObject; - if (IncludedWidgetId == o["i"].Value()) - InclusiveMatchCount++; - if (ExcludedWidgetId == o["i"].Value()) - ExclusiveMatchCount++; - } - - InclusiveMatchCount.Should().BeGreaterOrEqualTo(1); - ExclusiveMatchCount.Should().Be(0); - - //DELETE WIDGETS - a = await Util.DeleteAsync("widget/" + IncludedWidgetId.ToString(), await Util.GetTokenAsync("BizAdminFull")); - Util.ValidateHTTPStatusCode(a, 204); - - a = await Util.DeleteAsync("widget/" + ExcludedWidgetId.ToString(), await Util.GetTokenAsync("BizAdminFull")); - Util.ValidateHTTPStatusCode(a, 204); - - } - - - - /// - /// - /// - [Fact] - public async void DecimalNotEqualToFilterWorks() - { - - var WidgetNameStart = "DecimalNotEqualToFilterWorks"; - - long IncludedWidgetId = 0; - long ExcludedWidgetId = 0; - - //CREATE TEST WIDGETS - - //included widget - dynamic w = new JObject(); - w.name = Util.Uniquify(WidgetNameStart); - w.customFields = Util.WidgetRequiredCustomFieldsJsonString(); - w.notes = "blah"; - w.active = true; - w.usertype = 1; - w.dollarAmount = 222.22; - - ApiResponse a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w.ToString()); - Util.ValidateDataReturnResponseOk(a); - IncludedWidgetId = a.ObjectResponse["data"]["id"].Value(); - - //Excluded widget - w.name = Util.Uniquify(WidgetNameStart); - w.dollarAmount = 223.23; - a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w.ToString()); - Util.ValidateDataReturnResponseOk(a); - ExcludedWidgetId = a.ObjectResponse["data"]["id"].Value(); - - - //CREATE LISTVIEW - dynamic dListView = new JArray(); - - //name starts with filter to constrict to widgets that this test block created only - dListView.Add(Util.BuildSimpleFilterDataListViewColumn("widgetname", Util.OpStartsWith, WidgetNameStart)); - - //inclusive test filter - - // dynamic FilterItem = new JObject(); - // FilterItem.fld = "widgetdollaramount"; - // FilterItem.op = Util.OpNotEqual; - // FilterItem.value = 223.23; - dListView.Add(Util.BuildSimpleFilterDataListViewColumn("widgetdollaramount", Util.OpNotEqual, 223.23)); - - //FETCH DATALIST - a = await Util.PostAsync($"data-list", await Util.GetTokenAsync("superuser", "l3tm3in"), Util.BuildDataListRequestEx(dListView)); - Util.ValidateDataReturnResponseOk(a); - Util.ValidateHTTPStatusCode(a, 200); - - //assert contains at least this test record - ((JArray)a.ObjectResponse["data"]).Count.Should().BeGreaterThan(0); - var v = ((JArray)a.ObjectResponse["data"]); - List IDInResultList = new List(); - int InclusiveMatchCount = 0; - int ExclusiveMatchCount = 0; - foreach (JArray ja in v) - { - JObject o = ja[0] as JObject; - if (IncludedWidgetId == o["i"].Value()) - InclusiveMatchCount++; - if (ExcludedWidgetId == o["i"].Value()) - ExclusiveMatchCount++; - } - - InclusiveMatchCount.Should().BeGreaterOrEqualTo(1); - ExclusiveMatchCount.Should().Be(0); - - //DELETE WIDGETS - a = await Util.DeleteAsync("widget/" + IncludedWidgetId.ToString(), await Util.GetTokenAsync("BizAdminFull")); - Util.ValidateHTTPStatusCode(a, 204); - - a = await Util.DeleteAsync("widget/" + ExcludedWidgetId.ToString(), await Util.GetTokenAsync("BizAdminFull")); - Util.ValidateHTTPStatusCode(a, 204); - - } - #endregion decimal tests - - /////////////////////////////////////////////////////////////////////////////// - //TAGS - // - #region TAG TESTS - - /// - /// - /// - [Fact] - public async void TagFilterWorks() - { - - var TestName = "TagFilterWorks"; - var WidgetNameStart = Util.Uniquify(TestName); - - List InclusiveWidgetIdList = new List(); - List ExclusiveWidgetIdList = new List(); - - //CREATE 4 TEST WIDGETS - //two inclusive and two not inclusive - - //first inclusive widget - dynamic w = new JObject(); - w.name = Util.Uniquify(WidgetNameStart); - w.customFields = Util.WidgetRequiredCustomFieldsJsonString(); - w.notes = "blah"; - w.usertype = 1; - //Tags - dynamic InclusiveTagsArray = new JArray(); - InclusiveTagsArray.Add("red-tag-test"); - InclusiveTagsArray.Add("orange-tag-test"); - InclusiveTagsArray.Add("yellow-tag-test"); - InclusiveTagsArray.Add("green-tag-test"); - InclusiveTagsArray.Add("blue-tag-test"); - InclusiveTagsArray.Add("indigo-tag-test"); - InclusiveTagsArray.Add("violet-tag-test"); - w.tags = InclusiveTagsArray; - - ApiResponse a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w.ToString()); - Util.ValidateDataReturnResponseOk(a); - InclusiveWidgetIdList.Add(a.ObjectResponse["data"]["id"].Value()); - - //second inclusive widget - w.name = Util.Uniquify(WidgetNameStart); - - a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w.ToString()); - Util.ValidateDataReturnResponseOk(a); - InclusiveWidgetIdList.Add(a.ObjectResponse["data"]["id"].Value()); - - //first exclusive widget - w.name = Util.Uniquify(WidgetNameStart); - //Tags - dynamic ExclusiveTagsArray = new JArray(); - ExclusiveTagsArray.Add("crimson-tag-test"); - ExclusiveTagsArray.Add("amber-tag-test"); - ExclusiveTagsArray.Add("saffron-tag-test"); - ExclusiveTagsArray.Add("emerald-tag-test"); - ExclusiveTagsArray.Add("azure-tag-test"); - ExclusiveTagsArray.Add("red-tag-test"); - ExclusiveTagsArray.Add("blue-tag-test"); - ExclusiveTagsArray.Add("cobalt-tag-test"); - ExclusiveTagsArray.Add("magenta-tag-test"); - w.tags = ExclusiveTagsArray;//Missing green - - a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w.ToString()); - Util.ValidateDataReturnResponseOk(a); - ExclusiveWidgetIdList.Add(a.ObjectResponse["data"]["id"].Value()); - - //second exclusive widget - w.name = Util.Uniquify(WidgetNameStart); - w.active = false; - - a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w.ToString()); - Util.ValidateDataReturnResponseOk(a); - ExclusiveWidgetIdList.Add(a.ObjectResponse["data"]["id"].Value()); - - - //CREATE LISTVIEW - dynamic dListView = new JArray(); - - //name starts with filter to constrict to widgets that this test block created only - dListView.Add(Util.BuildSimpleFilterDataListViewColumn("widgetname", Util.OpStartsWith, WidgetNameStart)); - - //active test filter - // dynamic DataFilterActive = new JObject(); - // DataFilterActive.fld = "widgettags"; - // DataFilterActive.op = Util.OpEquality; - dynamic FilterTagsArray = new JArray(); - FilterTagsArray.Add("red-tag-test"); - FilterTagsArray.Add("green-tag-test");//green is the only one missing from the exclusive widget - FilterTagsArray.Add("blue-tag-test"); - // DataFilterActive.value = FilterTagsArray; - dListView.Add(Util.BuildSimpleFilterDataListViewColumn("widgettags", Util.OpEquality, FilterTagsArray)); - - - //FETCH DATALIST - a = await Util.PostAsync($"data-list", await Util.GetTokenAsync("superuser", "l3tm3in"), Util.BuildDataListRequestEx(dListView)); - Util.ValidateDataReturnResponseOk(a); - Util.ValidateHTTPStatusCode(a, 200); - - //assert contains at least two records - ((JArray)a.ObjectResponse["data"]).Count.Should().BeGreaterThan(1); - var v = ((JArray)a.ObjectResponse["data"]); - List IDInResultList = new List(); - int InclusiveMatchCount = 0; - int ExclusiveMatchCount = 0; - - - foreach (JArray ja in v) - { - JObject o = ja[0] as JObject; - - if (InclusiveWidgetIdList.Contains(o["i"].Value())) - InclusiveMatchCount++; - if (ExclusiveWidgetIdList.Contains(o["i"].Value())) - ExclusiveMatchCount++; - } - - - - InclusiveMatchCount.Should().Be(InclusiveWidgetIdList.Count); - ExclusiveMatchCount.Should().Be(0); - - //DELETE WIDGETS - foreach (long l in InclusiveWidgetIdList) - { - a = await Util.DeleteAsync("widget/" + l.ToString(), await Util.GetTokenAsync("BizAdminFull")); - Util.ValidateHTTPStatusCode(a, 204); - } - - foreach (long l in ExclusiveWidgetIdList) - { - a = await Util.DeleteAsync("widget/" + l.ToString(), await Util.GetTokenAsync("BizAdminFull")); - Util.ValidateHTTPStatusCode(a, 204); - } - } - - - /// - /// - /// - [Fact] - public async void UnicodeTagFilterWorks() - { - - var TestName = "UnicodeTagFilterWorks"; - var WidgetNameStart = Util.Uniquify(TestName); - - List InclusiveWidgetIdList = new List(); - List ExclusiveWidgetIdList = new List(); - - //CREATE 4 TEST WIDGETS - //two inclusive and two not inclusive - - //first inclusive widget - dynamic w = new JObject(); - w.name = Util.Uniquify(WidgetNameStart); - w.customFields = Util.WidgetRequiredCustomFieldsJsonString(); - w.notes = "blah"; - w.usertype = 1; - //Tags - dynamic InclusiveTagsArray = new JArray(); - InclusiveTagsArray.Add("red-tag-test"); - InclusiveTagsArray.Add("orange-tag-test"); - InclusiveTagsArray.Add("Ādam Iñtërnâtiônàližætiøn"); - w.tags = InclusiveTagsArray; - - ApiResponse a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w.ToString()); - Util.ValidateDataReturnResponseOk(a); - InclusiveWidgetIdList.Add(a.ObjectResponse["data"]["id"].Value()); - - //second inclusive widget - w.name = Util.Uniquify(WidgetNameStart); - - a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w.ToString()); - Util.ValidateDataReturnResponseOk(a); - InclusiveWidgetIdList.Add(a.ObjectResponse["data"]["id"].Value()); - - //first exclusive widget - w.name = Util.Uniquify(WidgetNameStart); - //Tags - dynamic ExclusiveTagsArray = new JArray(); - ExclusiveTagsArray.Add("crimson-tag-test"); - ExclusiveTagsArray.Add("amber-tag-test"); - ExclusiveTagsArray.Add("saffron-tag-test"); - ExclusiveTagsArray.Add("emerald-tag-test"); - ExclusiveTagsArray.Add("azure-tag-test"); - ExclusiveTagsArray.Add("red-tag-test"); - ExclusiveTagsArray.Add("blue-tag-test"); - ExclusiveTagsArray.Add("cobalt-tag-test"); - ExclusiveTagsArray.Add("magenta-tag-test"); - w.tags = ExclusiveTagsArray;//Missing green - - a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w.ToString()); - Util.ValidateDataReturnResponseOk(a); - ExclusiveWidgetIdList.Add(a.ObjectResponse["data"]["id"].Value()); - - //second exclusive widget - w.name = Util.Uniquify(WidgetNameStart); - w.active = false; - - a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w.ToString()); - Util.ValidateDataReturnResponseOk(a); - ExclusiveWidgetIdList.Add(a.ObjectResponse["data"]["id"].Value()); - - - //CREATE LISTVIEW - dynamic dListView = new JArray(); - - //name starts with filter to constrict to widgets that this test block created only - dListView.Add(Util.BuildSimpleFilterDataListViewColumn("widgetname", Util.OpStartsWith, WidgetNameStart)); - - //active test filter - // dynamic DataFilterActive = new JObject(); - // DataFilterActive.fld = "widgettags"; - // DataFilterActive.op = Util.OpEquality; - dynamic FilterTagsArray = new JArray(); - FilterTagsArray.Add("red-tag-test"); - FilterTagsArray.Add("Ādam Iñtërnâtiônàližætiøn"); - // DataFilterActive.value = FilterTagsArray; - dListView.Add(Util.BuildSimpleFilterDataListViewColumn("widgettags", Util.OpEquality, FilterTagsArray)); - - //FETCH DATALIST - a = await Util.PostAsync($"data-list", await Util.GetTokenAsync("superuser", "l3tm3in"), Util.BuildDataListRequestEx(dListView)); - Util.ValidateDataReturnResponseOk(a); - Util.ValidateHTTPStatusCode(a, 200); - - //assert contains at least two records - ((JArray)a.ObjectResponse["data"]).Count.Should().BeGreaterThan(1); - var v = ((JArray)a.ObjectResponse["data"]); - List IDInResultList = new List(); - int InclusiveMatchCount = 0; - int ExclusiveMatchCount = 0; - foreach (JArray ja in v) - { - JObject o = ja[0] as JObject; - if (InclusiveWidgetIdList.Contains(o["i"].Value())) - InclusiveMatchCount++; - if (ExclusiveWidgetIdList.Contains(o["i"].Value())) - ExclusiveMatchCount++; - } - - InclusiveMatchCount.Should().Be(InclusiveWidgetIdList.Count); - ExclusiveMatchCount.Should().Be(0); - - //DELETE WIDGETS - foreach (long l in InclusiveWidgetIdList) - { - a = await Util.DeleteAsync("widget/" + l.ToString(), await Util.GetTokenAsync("BizAdminFull")); - Util.ValidateHTTPStatusCode(a, 204); - } - - foreach (long l in ExclusiveWidgetIdList) - { - a = await Util.DeleteAsync("widget/" + l.ToString(), await Util.GetTokenAsync("BizAdminFull")); - Util.ValidateHTTPStatusCode(a, 204); - } - } - - - #endregion tag tests - //================================================== - - /////////////////////////////////////////////////////////////////////////////// - //FILTER BY ID VALUE - // - #region ID FILTER TESTS - - /// - /// - /// - [Fact] - public async void IdFilterWorks() - { - - var TestName = "IdFilterWorks"; - var WidgetNameStart = Util.Uniquify(TestName); - - //CREATE WIDGET - dynamic w = new JObject(); - w.name = Util.Uniquify(WidgetNameStart); - w.customFields = Util.WidgetRequiredCustomFieldsJsonString(); - w.notes = "ID FILTER NOTES"; - w.usertype = 1; - - ApiResponse a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w.ToString()); - Util.ValidateDataReturnResponseOk(a); - long Id = a.ObjectResponse["data"]["id"].Value(); - - - //CREATE LISTVIEW - dynamic dListView = new JArray(); - //FILTER - dListView.Add(Util.BuildSimpleFilterDataListViewColumn("widgetname", Util.OpEquality, Id)); - //FETCH DATALIST - a = await Util.PostAsync($"data-list", await Util.GetTokenAsync("superuser", "l3tm3in"), Util.BuildDataListRequestEx(dListView)); - - Util.ValidateDataReturnResponseOk(a); - Util.ValidateHTTPStatusCode(a, 200); - - //assert contains ONE record ONLY - ((JArray)a.ObjectResponse["data"]).Count.Should().Be(1); - //assert it's ours - ((JArray)a.ObjectResponse["data"])[0][0]["i"].Value().Should().Be(Id); - // v[0]["v"].Value() - - //DELETE WIDGET - a = await Util.DeleteAsync("widget/" + Id.ToString(), await Util.GetTokenAsync("BizAdminFull")); - Util.ValidateHTTPStatusCode(a, 204); - - - - } - - - - - - #endregion ID filter tests - - - - /////////////////////////////////////////////////////////////////////////////// - //*NULL* TESTS - // - - #region *NULL* TESTS - - /// - /// - /// - [Fact] - public async void NullEqualityFilterWorks() - { - //OPS: equal to, not equal to - //values: null - - var WidgetNameStart = "NullEqualityFilterWorks"; - - List NullInCountWidgetIdList = new List(); - List NotNullInCountWidgetIdList = new List(); - - //CREATE 4 TEST WIDGETS - //two null count and two non null count - - //first null count widget - dynamic w = new JObject(); - w.name = Util.Uniquify(WidgetNameStart); - w.customFields = Util.WidgetRequiredCustomFieldsJsonString(); - w.notes = "blah"; - w.active = true; - w.usertype = 1; - - ApiResponse a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w.ToString()); - Util.ValidateDataReturnResponseOk(a); - NullInCountWidgetIdList.Add(a.ObjectResponse["data"]["id"].Value()); - - //second null count widget - w.name = Util.Uniquify(WidgetNameStart); - - a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w.ToString()); - Util.ValidateDataReturnResponseOk(a); - NullInCountWidgetIdList.Add(a.ObjectResponse["data"]["id"].Value()); - - - //first NON null in count widget - w.name = Util.Uniquify(WidgetNameStart); - w.count = 22; - - a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w.ToString()); - Util.ValidateDataReturnResponseOk(a); - NotNullInCountWidgetIdList.Add(a.ObjectResponse["data"]["id"].Value()); - - //second NON null in count field widget - w.name = Util.Uniquify(WidgetNameStart); - w.count = 33; - - a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w.ToString()); - Util.ValidateDataReturnResponseOk(a); - NotNullInCountWidgetIdList.Add(a.ObjectResponse["data"]["id"].Value()); - - - //CREATE LISTVIEW - dynamic dListView = new JArray(); - - //name starts with filter to constrict to widgets that this test block created only - dListView.Add(Util.BuildSimpleFilterDataListViewColumn("widgetname", Util.OpStartsWith, WidgetNameStart)); - - //FILTER - // dynamic DataFilterActive = new JObject(); - // DataFilterActive.fld = "widgetactive"; - // DataFilterActive.op = Util.OpEquality; - // DataFilterActive.value = true; - dListView.Add(Util.BuildSimpleFilterDataListViewColumn("widgetcount", Util.OpEquality, "*NULL*")); - - - //FETCH DATALIST - a = await Util.PostAsync($"data-list", await Util.GetTokenAsync("superuser", "l3tm3in"), Util.BuildDataListRequestEx(dListView)); - Util.ValidateDataReturnResponseOk(a); - Util.ValidateHTTPStatusCode(a, 200); - - //assert contains at least two records - ((JArray)a.ObjectResponse["data"]).Count.Should().BeGreaterThan(1); - var v = ((JArray)a.ObjectResponse["data"]); - List IDInResultList = new List(); - int nNullCountMatches = 0; - int nNotNullCountMatches = 0; - - foreach (JArray ja in v) - { - JObject o = ja[0] as JObject; - - - if (NullInCountWidgetIdList.Contains(o["i"].Value())) - nNullCountMatches++; - //if (NotActiveWidgetIdList.Contains(o["i"].Value())) - if (NotNullInCountWidgetIdList.Contains(o["i"].Value())) - nNotNullCountMatches++; - } - - nNullCountMatches.Should().Be(NullInCountWidgetIdList.Count); - nNotNullCountMatches.Should().Be(0); - - //DELETE WIDGETS - foreach (long l in NullInCountWidgetIdList) - { - a = await Util.DeleteAsync("widget/" + l.ToString(), await Util.GetTokenAsync("BizAdminFull")); - Util.ValidateHTTPStatusCode(a, 204); - } - - foreach (long l in NotNullInCountWidgetIdList) - { - a = await Util.DeleteAsync("widget/" + l.ToString(), await Util.GetTokenAsync("BizAdminFull")); - Util.ValidateHTTPStatusCode(a, 204); - } - } - - /// - /// - /// - [Fact] - public async void NullNotEqualFilterWorks() - { - //OPS: equal to, not equal to - //values: null - - var WidgetNameStart = "NullNotEqualFilterWorks"; - - List NullInCountWidgetIdList = new List(); - List NotNullInCountWidgetIdList = new List(); - - //CREATE 4 TEST WIDGETS - //two null count and two non null count - - //first null count widget - dynamic w = new JObject(); - w.name = Util.Uniquify(WidgetNameStart); - w.customFields = Util.WidgetRequiredCustomFieldsJsonString(); - w.notes = "blah"; - w.active = true; - w.usertype = 1; - - ApiResponse a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w.ToString()); - Util.ValidateDataReturnResponseOk(a); - NullInCountWidgetIdList.Add(a.ObjectResponse["data"]["id"].Value()); - - //second null count widget - w.name = Util.Uniquify(WidgetNameStart); - - a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w.ToString()); - Util.ValidateDataReturnResponseOk(a); - NullInCountWidgetIdList.Add(a.ObjectResponse["data"]["id"].Value()); - - - //first NON null in count widget - w.name = Util.Uniquify(WidgetNameStart); - w.count = 22; - - a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w.ToString()); - Util.ValidateDataReturnResponseOk(a); - NotNullInCountWidgetIdList.Add(a.ObjectResponse["data"]["id"].Value()); - - //second NON null in count field widget - w.name = Util.Uniquify(WidgetNameStart); - w.count = 33; - - a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w.ToString()); - Util.ValidateDataReturnResponseOk(a); - NotNullInCountWidgetIdList.Add(a.ObjectResponse["data"]["id"].Value()); - - - //CREATE LISTVIEW - dynamic dListView = new JArray(); - - //name starts with filter to constrict to widgets that this test block created only - dListView.Add(Util.BuildSimpleFilterDataListViewColumn("widgetname", Util.OpStartsWith, WidgetNameStart)); - - //FILTER - // dynamic DataFilterActive = new JObject(); - // DataFilterActive.fld = "widgetactive"; - // DataFilterActive.op = Util.OpEquality; - // DataFilterActive.value = true; - dListView.Add(Util.BuildSimpleFilterDataListViewColumn("widgetcount", Util.OpNotEqual, "*NULL*")); - - - //FETCH DATALIST - a = await Util.PostAsync($"data-list", await Util.GetTokenAsync("superuser", "l3tm3in"), Util.BuildDataListRequestEx(dListView)); - Util.ValidateDataReturnResponseOk(a); - Util.ValidateHTTPStatusCode(a, 200); - - //assert contains at least two records - ((JArray)a.ObjectResponse["data"]).Count.Should().BeGreaterThan(1); - var v = ((JArray)a.ObjectResponse["data"]); - List IDInResultList = new List(); - int nNullCountMatches = 0; - int nNotNullCountMatches = 0; - - foreach (JArray ja in v) - { - JObject o = ja[0] as JObject; - - - if (NullInCountWidgetIdList.Contains(o["i"].Value())) - nNullCountMatches++; - //if (NotActiveWidgetIdList.Contains(o["i"].Value())) - if (NotNullInCountWidgetIdList.Contains(o["i"].Value())) - nNotNullCountMatches++; - } - - nNotNullCountMatches.Should().Be(NullInCountWidgetIdList.Count); - nNullCountMatches.Should().Be(0); - - //DELETE WIDGETS - foreach (long l in NullInCountWidgetIdList) - { - a = await Util.DeleteAsync("widget/" + l.ToString(), await Util.GetTokenAsync("BizAdminFull")); - Util.ValidateHTTPStatusCode(a, 204); - } - - foreach (long l in NotNullInCountWidgetIdList) - { - a = await Util.DeleteAsync("widget/" + l.ToString(), await Util.GetTokenAsync("BizAdminFull")); - Util.ValidateHTTPStatusCode(a, 204); - } - } - - - #endregion *NULL* tests - - - - - - //================================================== - - }//eoc -}//eons +using System; +using Xunit; +using Newtonsoft.Json.Linq; +using FluentAssertions; +using System.Collections.Generic; +using System.Collections.Concurrent; + +namespace raven_integration +{ + + + /* + + EVERY TYPE, EVERY OP + + Using the widget object test all filtering options + for all data types, all operation types + + This is the supertest to always confirm the filtering code is working as expected. + + +BUGBUG: Server takes into account user's time zone offset when filtering lists by date range but here the local test runner just uses the windows system offset instead of the defined offset in the User account at the server +Fix: Since seeder uses same time zone for all users it generates then can simply fetch one single users' tz offset and use that centerally to calculate a relative now and relative today +same as the server does but in a central location here for all tests to use. + + */ + + public class DataListFiltering + { + + + + + + + /////////////////////////////////////////////////////////////////////////////// + //DATE + // + + #region DATE FILTER TESTS + + // public const string TokenYesterday = "{[yesterday]}"; + // public const string TokenToday = "{[today]}"; + // public const string TokenTomorrow = "{[tomorrow]}"; + // public const string TokenLastWeek = "{[lastweek]}"; + // public const string TokenThisWeek = "{[thisweek]}"; + // public const string TokenNextWeek = "{[nextweek]}"; + // public const string TokenLastMonth = "{[lastmonth]}"; + // public const string TokenThisMonth = "{[thismonth]}"; + // public const string TokenNextMonth = "{[nextmonth]}"; + // public const string TokenFourteenDayWindow = "{[14daywindow]}"; + // public const string TokenPast = "{[past]}"; + // public const string TokenFuture = "{[future]}"; + // public const string TokenLastYear = "{[lastyear]}"; + // public const string TokenThisYear = "{[thisyear]}"; + // public const string TokenInTheLast3Months = "{[last3months]}"; + // public const string TokenInTheLast6Months = "{[last6months]}"; + // public const string TokenInTheLastYear = "{[lastcalendaryear]}"; + + // //More business time frames + + // public const string TokenYearToDate = "{[yeartodate]}"; + + // public const string TokenPast90Days = "{[past90days]}"; + // public const string TokenPast30Days = "{[past30days]}"; + // public const string TokenPast24Hours = "{[past24hours]}"; + + // //Months THIS year + // public const string TokenJanuary = "{[january]}"; + // public const string TokenFebruary = "{[february]}"; + // public const string TokenMarch = "{[march]}"; + // public const string TokenApril = "{[april]}"; + // public const string TokenMay = "{[may]}"; + // public const string TokenJune = "{[june]}"; + // public const string TokenJuly = "{[july]}"; + // public const string TokenAugust = "{[august]}"; + // public const string TokenSeptember = "{[september]}"; + // public const string TokenOctober = "{[october]}"; + // public const string TokenNovember = "{[november]}"; + // public const string TokenDecember = "{[december]}"; + + + #region DATE REGULAR FILTERS + + /// + /// + /// + [Fact] + public async Task DateOpEqualityFilterWorks() + { + + var WidgetNameStart = "DateOpEqualityFilterWorks"; + + long IncludedWidgetId = 0; + long ExcludedWidgetId = 0; + + //CREATE TEST WIDGETS + + //included widget + dynamic w = new JObject(); + w.name = Util.Uniquify(WidgetNameStart); + w.notes = "blah"; + w.customFields = Util.WidgetRequiredCustomFieldsJsonString(); + w.startDate = new DateTime(1968, 3, 12, 10, 0, 0).ToOffsetAdjustedUniversalTime(); + w.endDate = new DateTime(1968, 3, 12, 11, 0, 0).ToOffsetAdjustedUniversalTime(); + w.usertype = 1; + + ApiResponse a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w.ToString()); + Util.ValidateDataReturnResponseOk(a); + IncludedWidgetId = a.ObjectResponse["data"]["id"].Value(); + + //Excluded widget + w.name = Util.Uniquify(WidgetNameStart); + w.startDate = new DateTime(1968, 3, 10, 10, 0, 0).ToOffsetAdjustedUniversalTime(); + w.endDate = new DateTime(1968, 3, 10, 11, 0, 0).ToOffsetAdjustedUniversalTime(); + + a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w.ToString()); + Util.ValidateDataReturnResponseOk(a); + ExcludedWidgetId = a.ObjectResponse["data"]["id"].Value(); + + //CREATE LISTVIEW + + dynamic dListView = new JArray(); + + + //name starts with filter to constrict to widgets that this test block created only + + dListView.Add(Util.BuildSimpleFilterDataListViewColumn("widgetname", Util.OpStartsWith, WidgetNameStart)); + + //## INCLUSIVE FILTER + // dynamic FilterItem = new JObject(); + // FilterItem.fld = "widgetstartdate"; + // FilterItem.op = Util.OpEquality; + // FilterItem.value = new DateTime(1968, 3, 12, 10, 0, 0).ToOffsetAdjustedUniversalTime(); + // dListView.Add(Util.BuildSimpleFilterDataListViewColumn("XXXX", Util.XXXX, XXXX)); + dListView.Add(Util.BuildSimpleFilterDataListViewColumn("widgetstartdate", Util.OpEquality, new DateTime(1968, 3, 12, 10, 0, 0).ToOffsetAdjustedUniversalTime())); + + + //FETCH DATALIST + a = await Util.PostAsync($"data-list", await Util.GetTokenAsync("superuser", "l3tm3in"), Util.BuildDataListRequestEx(dListView)); + Util.ValidateDataReturnResponseOk(a); + Util.ValidateHTTPStatusCode(a, 200); + + //assert contains at least this test record + ((JArray)a.ObjectResponse["data"]).Count.Should().BeGreaterThan(0); + var v = ((JArray)a.ObjectResponse["data"]); + List IDInResultList = new List(); + int InclusiveMatchCount = 0; + int ExclusiveMatchCount = 0; + + foreach (JArray ja in v) + { + JObject o = ja[0] as JObject; + + if (IncludedWidgetId == o["i"].Value()) + InclusiveMatchCount++; + if (ExcludedWidgetId == o["i"].Value()) + ExclusiveMatchCount++; + } + + InclusiveMatchCount.Should().BeGreaterOrEqualTo(1); + ExclusiveMatchCount.Should().Be(0); + + //DELETE WIDGETS + a = await Util.DeleteAsync("widget/" + IncludedWidgetId.ToString(), await Util.GetTokenAsync("BizAdminFull")); + Util.ValidateHTTPStatusCode(a, 204); + + a = await Util.DeleteAsync("widget/" + ExcludedWidgetId.ToString(), await Util.GetTokenAsync("BizAdminFull")); + Util.ValidateHTTPStatusCode(a, 204); + + + } + + + /// + /// + /// + [Fact] + public async Task DateOpGreaterThanFilterWorks() + { + + var WidgetNameStart = "DateOpGreaterThanFilterWorks"; + + long IncludedWidgetId = 0; + long ExcludedWidgetId = 0; + + //CREATE TEST WIDGETS + + //included widget + dynamic w = new JObject(); + w.name = Util.Uniquify(WidgetNameStart); + w.notes = "blah"; + w.customFields = Util.WidgetRequiredCustomFieldsJsonString(); + w.startDate = new DateTime(1970, 3, 12, 10, 0, 0).ToOffsetAdjustedUniversalTime(); + w.endDate = new DateTime(1970, 3, 12, 11, 0, 0).ToOffsetAdjustedUniversalTime(); + w.usertype = 1; + + ApiResponse a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w.ToString()); + Util.ValidateDataReturnResponseOk(a); + IncludedWidgetId = a.ObjectResponse["data"]["id"].Value(); + + //Excluded widget + w.name = Util.Uniquify(WidgetNameStart); + w.startDate = new DateTime(1968, 3, 10, 10, 0, 0).ToOffsetAdjustedUniversalTime(); + w.endDate = new DateTime(1968, 3, 10, 11, 0, 0).ToOffsetAdjustedUniversalTime(); + + a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w.ToString()); + Util.ValidateDataReturnResponseOk(a); + ExcludedWidgetId = a.ObjectResponse["data"]["id"].Value(); + + //CREATE LISTVIEW + dynamic dListView = new JArray(); + + //name starts with filter to constrict to widgets that this test block created only + + dListView.Add(Util.BuildSimpleFilterDataListViewColumn("widgetname", Util.OpStartsWith, WidgetNameStart)); + + //## INCLUSIVE FILTER + // dynamic FilterItem = new JObject(); + // FilterItem.fld = "widgetstartdate"; + // FilterItem.op = Util.OpGreaterThan; + // FilterItem.value = new DateTime(1970, 3, 12, 9, 0, 0).ToOffsetAdjustedUniversalTime(); + // dListView.Add(Util.BuildSimpleFilterDataListViewColumn("XXXX", Util.XXXX, XXXX)); + dListView.Add(Util.BuildSimpleFilterDataListViewColumn("widgetstartdate", Util.OpGreaterThan, new DateTime(1970, 3, 12, 9, 0, 0).ToOffsetAdjustedUniversalTime())); + + + //FETCH DATALIST + a = await Util.PostAsync($"data-list", await Util.GetTokenAsync("superuser", "l3tm3in"), Util.BuildDataListRequestEx(dListView)); + Util.ValidateDataReturnResponseOk(a); + Util.ValidateHTTPStatusCode(a, 200); + + //assert contains at least this test record + ((JArray)a.ObjectResponse["data"]).Count.Should().BeGreaterThan(0); + var v = ((JArray)a.ObjectResponse["data"]); + List IDInResultList = new List(); + int InclusiveMatchCount = 0; + int ExclusiveMatchCount = 0; + + foreach (JArray ja in v) + { + JObject o = ja[0] as JObject; + + if (IncludedWidgetId == o["i"].Value()) + InclusiveMatchCount++; + if (ExcludedWidgetId == o["i"].Value()) + ExclusiveMatchCount++; + } + + InclusiveMatchCount.Should().BeGreaterOrEqualTo(1); + ExclusiveMatchCount.Should().Be(0); + + //DELETE WIDGETS + a = await Util.DeleteAsync("widget/" + IncludedWidgetId.ToString(), await Util.GetTokenAsync("BizAdminFull")); + Util.ValidateHTTPStatusCode(a, 204); + + a = await Util.DeleteAsync("widget/" + ExcludedWidgetId.ToString(), await Util.GetTokenAsync("BizAdminFull")); + Util.ValidateHTTPStatusCode(a, 204); + } + + + + /// + /// + /// + [Fact] + public async Task DateOpGreaterThanOrEqualToFilterWorks() + { + + var WidgetNameStart = "DateOpGreaterThanOrEqualToFilterWorks"; + + long IncludedWidgetId = 0; + long ExcludedWidgetId = 0; + + //CREATE TEST WIDGETS + + //included widget + dynamic w = new JObject(); + w.name = Util.Uniquify(WidgetNameStart); + w.notes = "blah"; + w.customFields = Util.WidgetRequiredCustomFieldsJsonString(); + w.startDate = new DateTime(1970, 3, 12, 10, 0, 0).ToOffsetAdjustedUniversalTime(); + w.endDate = new DateTime(1970, 3, 12, 11, 0, 0).ToOffsetAdjustedUniversalTime(); + w.usertype = 1; + + ApiResponse a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w.ToString()); + Util.ValidateDataReturnResponseOk(a); + IncludedWidgetId = a.ObjectResponse["data"]["id"].Value(); + + //Excluded widget + w.name = Util.Uniquify(WidgetNameStart); + w.startDate = new DateTime(1968, 3, 10, 10, 0, 0).ToOffsetAdjustedUniversalTime(); + w.endDate = new DateTime(1968, 3, 10, 11, 0, 0).ToOffsetAdjustedUniversalTime(); + + a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w.ToString()); + Util.ValidateDataReturnResponseOk(a); + ExcludedWidgetId = a.ObjectResponse["data"]["id"].Value(); + + //CREATE LISTVIEW + + dynamic dListView = new JArray(); + + //name starts with filter to constrict to widgets that this test block created only + + dListView.Add(Util.BuildSimpleFilterDataListViewColumn("widgetname", Util.OpStartsWith, WidgetNameStart)); + + //## INCLUSIVE FILTER + // dynamic FilterItem = new JObject(); + // FilterItem.fld = "widgetstartdate"; + // FilterItem.op = Util.OpGreaterThanOrEqualTo; + // FilterItem.value = new DateTime(1970, 3, 12, 10, 0, 0).ToOffsetAdjustedUniversalTime(); + // dListView.Add(Util.BuildSimpleFilterDataListViewColumn("XXXX", Util.XXXX, XXXX)); + dListView.Add(Util.BuildSimpleFilterDataListViewColumn("widgetstartdate", Util.OpGreaterThanOrEqualTo, new DateTime(1970, 3, 12, 10, 0, 0).ToOffsetAdjustedUniversalTime())); + + + + //FETCH DATALIST + a = await Util.PostAsync($"data-list", await Util.GetTokenAsync("superuser", "l3tm3in"), Util.BuildDataListRequestEx(dListView)); + Util.ValidateDataReturnResponseOk(a); + Util.ValidateHTTPStatusCode(a, 200); + + //assert contains at least this test record + ((JArray)a.ObjectResponse["data"]).Count.Should().BeGreaterThan(0); + var v = ((JArray)a.ObjectResponse["data"]); + List IDInResultList = new List(); + int InclusiveMatchCount = 0; + int ExclusiveMatchCount = 0; + + foreach (JArray ja in v) + { + JObject o = ja[0] as JObject; + + if (IncludedWidgetId == o["i"].Value()) + InclusiveMatchCount++; + if (ExcludedWidgetId == o["i"].Value()) + ExclusiveMatchCount++; + } + + InclusiveMatchCount.Should().BeGreaterOrEqualTo(1); + ExclusiveMatchCount.Should().Be(0); + + //DELETE WIDGETS + a = await Util.DeleteAsync("widget/" + IncludedWidgetId.ToString(), await Util.GetTokenAsync("BizAdminFull")); + Util.ValidateHTTPStatusCode(a, 204); + + a = await Util.DeleteAsync("widget/" + ExcludedWidgetId.ToString(), await Util.GetTokenAsync("BizAdminFull")); + Util.ValidateHTTPStatusCode(a, 204); + } + + + /// + /// + /// + [Fact] + public async Task DateOpLessThanFilterWorks() + { + + var WidgetNameStart = "DateOpLessThanFilterWorks"; + + long IncludedWidgetId = 0; + long ExcludedWidgetId = 0; + + //CREATE TEST WIDGETS + + //included widget + dynamic w = new JObject(); + w.name = Util.Uniquify(WidgetNameStart); + w.notes = "blah"; + w.customFields = Util.WidgetRequiredCustomFieldsJsonString(); + w.startDate = new DateTime(1970, 3, 12, 10, 0, 0).ToOffsetAdjustedUniversalTime(); + w.endDate = new DateTime(1970, 3, 12, 11, 0, 0).ToOffsetAdjustedUniversalTime(); + w.usertype = 1; + + ApiResponse a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w.ToString()); + Util.ValidateDataReturnResponseOk(a); + IncludedWidgetId = a.ObjectResponse["data"]["id"].Value(); + + //Excluded widget + w.name = Util.Uniquify(WidgetNameStart); + w.startDate = new DateTime(1970, 4, 10, 10, 0, 0).ToOffsetAdjustedUniversalTime(); + w.endDate = new DateTime(1970, 4, 10, 11, 0, 0).ToOffsetAdjustedUniversalTime(); + + a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w.ToString()); + Util.ValidateDataReturnResponseOk(a); + ExcludedWidgetId = a.ObjectResponse["data"]["id"].Value(); + + //CREATE LISTVIEW + dynamic dListView = new JArray(); + + //name starts with filter to constrict to widgets that this test block created only + dListView.Add(Util.BuildSimpleFilterDataListViewColumn("widgetname", Util.OpStartsWith, WidgetNameStart)); + + //## INCLUSIVE FILTER + // dynamic FilterItem = new JObject(); + // FilterItem.fld = "widgetstartdate"; + // FilterItem.op = Util.OpLessThan; + // FilterItem.value = new DateTime(1970, 3, 12, 11, 0, 0).ToOffsetAdjustedUniversalTime(); + dListView.Add(Util.BuildSimpleFilterDataListViewColumn("widgetstartdate", Util.OpLessThan, new DateTime(1970, 3, 12, 11, 0, 0).ToOffsetAdjustedUniversalTime())); + + + //FETCH DATALIST + a = await Util.PostAsync($"data-list", await Util.GetTokenAsync("superuser", "l3tm3in"), Util.BuildDataListRequestEx(dListView)); + Util.ValidateDataReturnResponseOk(a); + Util.ValidateHTTPStatusCode(a, 200); + + //assert contains at least this test record + ((JArray)a.ObjectResponse["data"]).Count.Should().BeGreaterThan(0); + var v = ((JArray)a.ObjectResponse["data"]); + List IDInResultList = new List(); + int InclusiveMatchCount = 0; + int ExclusiveMatchCount = 0; + foreach (JArray ja in v) + { + JObject o = ja[0] as JObject; + + if (IncludedWidgetId == o["i"].Value()) + InclusiveMatchCount++; + if (ExcludedWidgetId == o["i"].Value()) + ExclusiveMatchCount++; + } + + InclusiveMatchCount.Should().BeGreaterOrEqualTo(1); + ExclusiveMatchCount.Should().Be(0); + + //DELETE WIDGETS + a = await Util.DeleteAsync("widget/" + IncludedWidgetId.ToString(), await Util.GetTokenAsync("BizAdminFull")); + Util.ValidateHTTPStatusCode(a, 204); + + a = await Util.DeleteAsync("widget/" + ExcludedWidgetId.ToString(), await Util.GetTokenAsync("BizAdminFull")); + Util.ValidateHTTPStatusCode(a, 204); + } + + + + /// + /// + /// + [Fact] + public async Task DateOpLessThanOrEqualToFilterWorks() + { + + var WidgetNameStart = "DateOpLessThanOrEqualToFilterWorks"; + + long IncludedWidgetId = 0; + long ExcludedWidgetId = 0; + + //CREATE TEST WIDGETS + + //included widget + dynamic w = new JObject(); + w.name = Util.Uniquify(WidgetNameStart); + w.notes = "blah"; + w.customFields = Util.WidgetRequiredCustomFieldsJsonString(); + w.startDate = new DateTime(1970, 3, 12, 10, 0, 0).ToOffsetAdjustedUniversalTime(); + w.endDate = new DateTime(1970, 3, 12, 11, 0, 0).ToOffsetAdjustedUniversalTime(); + w.usertype = 1; + + ApiResponse a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w.ToString()); + Util.ValidateDataReturnResponseOk(a); + IncludedWidgetId = a.ObjectResponse["data"]["id"].Value(); + + //Excluded widget + w.name = Util.Uniquify(WidgetNameStart); + w.startDate = new DateTime(1970, 4, 10, 10, 0, 0).ToOffsetAdjustedUniversalTime(); + w.endDate = new DateTime(1970, 4, 10, 11, 0, 0).ToOffsetAdjustedUniversalTime(); + + a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w.ToString()); + Util.ValidateDataReturnResponseOk(a); + ExcludedWidgetId = a.ObjectResponse["data"]["id"].Value(); + + //CREATE LISTVIEW + dynamic dListView = new JArray(); + + //name starts with filter to constrict to widgets that this test block created only + dListView.Add(Util.BuildSimpleFilterDataListViewColumn("widgetname", Util.OpStartsWith, WidgetNameStart)); + + //## INCLUSIVE FILTER + // dynamic FilterItem = new JObject(); + // FilterItem.fld = "widgetstartdate"; + // FilterItem.op = Util.OpLessThanOrEqualTo; + // FilterItem.value = new DateTime(1970, 3, 12, 10, 0, 0).ToOffsetAdjustedUniversalTime(); + dListView.Add(Util.BuildSimpleFilterDataListViewColumn("widgetstartdate", Util.OpLessThanOrEqualTo, new DateTime(1970, 3, 12, 10, 0, 0).ToOffsetAdjustedUniversalTime())); + //FETCH DATALIST + a = await Util.PostAsync($"data-list", await Util.GetTokenAsync("superuser", "l3tm3in"), Util.BuildDataListRequestEx(dListView)); + Util.ValidateDataReturnResponseOk(a); + Util.ValidateHTTPStatusCode(a, 200); + + //assert contains at least this test record + ((JArray)a.ObjectResponse["data"]).Count.Should().BeGreaterThan(0); + var v = ((JArray)a.ObjectResponse["data"]); + List IDInResultList = new List(); + int InclusiveMatchCount = 0; + int ExclusiveMatchCount = 0; + foreach (JArray ja in v) + { + JObject o = ja[0] as JObject; + + if (IncludedWidgetId == o["i"].Value()) + InclusiveMatchCount++; + if (ExcludedWidgetId == o["i"].Value()) + ExclusiveMatchCount++; + } + + InclusiveMatchCount.Should().BeGreaterOrEqualTo(1); + ExclusiveMatchCount.Should().Be(0); + + //DELETE WIDGETS + a = await Util.DeleteAsync("widget/" + IncludedWidgetId.ToString(), await Util.GetTokenAsync("BizAdminFull")); + Util.ValidateHTTPStatusCode(a, 204); + + a = await Util.DeleteAsync("widget/" + ExcludedWidgetId.ToString(), await Util.GetTokenAsync("BizAdminFull")); + Util.ValidateHTTPStatusCode(a, 204); + } + + + + /// + /// + /// + [Fact] + public async Task DateOpNotEqualToFilterWorks() + { + + var WidgetNameStart = "DateOpNotEqualToFilterWorks"; + + long IncludedWidgetId = 0; + long ExcludedWidgetId = 0; + + //CREATE TEST WIDGETS + + //included widget + dynamic w = new JObject(); + w.name = Util.Uniquify(WidgetNameStart); + w.notes = "blah"; + w.customFields = Util.WidgetRequiredCustomFieldsJsonString(); + w.startDate = new DateTime(1970, 3, 12, 10, 0, 0).ToOffsetAdjustedUniversalTime(); + w.endDate = new DateTime(1970, 3, 12, 11, 0, 0).ToOffsetAdjustedUniversalTime(); + w.usertype = 1; + + ApiResponse a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w.ToString()); + Util.ValidateDataReturnResponseOk(a); + IncludedWidgetId = a.ObjectResponse["data"]["id"].Value(); + + //Excluded widget + w.name = Util.Uniquify(WidgetNameStart); + w.startDate = new DateTime(1970, 4, 10, 10, 0, 0).ToOffsetAdjustedUniversalTime(); + w.endDate = new DateTime(1970, 4, 10, 11, 0, 0).ToOffsetAdjustedUniversalTime(); + + a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w.ToString()); + Util.ValidateDataReturnResponseOk(a); + ExcludedWidgetId = a.ObjectResponse["data"]["id"].Value(); + + //CREATE LISTVIEW + dynamic dListView = new JArray(); + + //name starts with filter to constrict to widgets that this test block created only + dListView.Add(Util.BuildSimpleFilterDataListViewColumn("widgetname", Util.OpStartsWith, WidgetNameStart)); + + //## INCLUSIVE FILTER + // dynamic FilterItem = new JObject(); + // FilterItem.fld = "widgetstartdate"; + // FilterItem.op = Util.OpNotEqual; + // FilterItem.value = new DateTime(1970, 4, 10, 10, 0, 0).ToOffsetAdjustedUniversalTime(); + dListView.Add(Util.BuildSimpleFilterDataListViewColumn("widgetstartdate", Util.OpNotEqual, new DateTime(1970, 4, 10, 10, 0, 0).ToOffsetAdjustedUniversalTime())); + //FETCH DATALIST + a = await Util.PostAsync($"data-list", await Util.GetTokenAsync("superuser", "l3tm3in"), Util.BuildDataListRequestEx(dListView)); + Util.ValidateDataReturnResponseOk(a); + Util.ValidateHTTPStatusCode(a, 200); + + //assert contains at least this test record + ((JArray)a.ObjectResponse["data"]).Count.Should().BeGreaterThan(0); + var v = ((JArray)a.ObjectResponse["data"]); + List IDInResultList = new List(); + int InclusiveMatchCount = 0; + int ExclusiveMatchCount = 0; + foreach (JArray ja in v) + { + JObject o = ja[0] as JObject; + + if (IncludedWidgetId == o["i"].Value()) + InclusiveMatchCount++; + if (ExcludedWidgetId == o["i"].Value()) + ExclusiveMatchCount++; + } + + InclusiveMatchCount.Should().BeGreaterOrEqualTo(1); + ExclusiveMatchCount.Should().Be(0); + + //DELETE WIDGETS + a = await Util.DeleteAsync("widget/" + IncludedWidgetId.ToString(), await Util.GetTokenAsync("BizAdminFull")); + Util.ValidateHTTPStatusCode(a, 204); + + a = await Util.DeleteAsync("widget/" + ExcludedWidgetId.ToString(), await Util.GetTokenAsync("BizAdminFull")); + Util.ValidateHTTPStatusCode(a, 204); + } + + + + /// + /// + /// + [Fact] + public async Task DateOpBetweenFilterWorks() + { + + var WidgetNameStart = "DateOpBetweenFilterWorks"; + + long IncludedWidgetId = 0; + long ExcludedWidgetId = 0; + + //CREATE TEST WIDGETS + + //included widget + dynamic w = new JObject(); + w.name = Util.Uniquify(WidgetNameStart); + w.notes = "blah"; + w.customFields = Util.WidgetRequiredCustomFieldsJsonString(); + w.startDate = new DateTime(2019, 3, 12, 10, 0, 0).ToOffsetAdjustedUniversalTime(); + w.endDate = new DateTime(2019, 3, 12, 11, 0, 0).ToOffsetAdjustedUniversalTime(); + w.usertype = 1; + + ApiResponse a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w.ToString()); + Util.ValidateDataReturnResponseOk(a); + IncludedWidgetId = a.ObjectResponse["data"]["id"].Value(); + + //Excluded widget + w.name = Util.Uniquify(WidgetNameStart); + w.startDate = new DateTime(2019, 3, 12, 8, 0, 0).ToOffsetAdjustedUniversalTime(); + w.endDate = new DateTime(2019, 3, 12, 9, 0, 0).ToOffsetAdjustedUniversalTime(); + + a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w.ToString()); + Util.ValidateDataReturnResponseOk(a); + ExcludedWidgetId = a.ObjectResponse["data"]["id"].Value(); + + //CREATE LISTVIEW + + dynamic dListView = new JArray(); + + //name starts with filter to constrict to widgets that this test block created only + dListView.Add(Util.BuildSimpleFilterDataListViewColumn("widgetname", Util.OpStartsWith, WidgetNameStart)); + + //## INCLUSIVE FILTER + // dynamic FilterItem = new JObject(); + // FilterItem.fld = "widgetstartdate"; + // FilterItem.op = Util.OpGreaterThanOrEqualTo; + // FilterItem.value = new DateTime(2019, 3, 12, 10, 0, 0).ToOffsetAdjustedUniversalTime(); + // dListView.Add(Util.BuildSimpleFilterDataListViewColumn("widgetstartdate", Util.OpGreaterThanOrEqualTo, new DateTime(2019, 3, 12, 10, 0, 0).ToOffsetAdjustedUniversalTime())); + + + // dynamic FilterItem2 = new JObject(); + // FilterItem2.fld = "widgetstartdate"; + // FilterItem2.op = Util.OpLessThanOrEqualTo; + // FilterItem2.value = new DateTime(2019, 3, 12, 11, 0, 0).ToOffsetAdjustedUniversalTime(); + // dListView.Add(FilterItem2); + + //Build multiple condition filter (not handled by util method) + dynamic d = new JObject(); + d.fld = "widgetstartdate"; + + + dynamic filter = new JObject(); + dynamic items = new JArray(); + + dynamic fitem = new JObject(); + fitem.op = Util.OpGreaterThanOrEqualTo; + fitem.value = new DateTime(2019, 3, 12, 10, 0, 0).ToOffsetAdjustedUniversalTime(); + items.Add(fitem); + + fitem = new JObject(); + fitem.op = Util.OpLessThanOrEqualTo; + fitem.value = new DateTime(2019, 3, 12, 11, 0, 0).ToOffsetAdjustedUniversalTime(); + items.Add(fitem); + + + filter.items = items; + d.filter = filter; + + dListView.Add(d); + + + //FETCH DATALIST + a = await Util.PostAsync($"data-list", await Util.GetTokenAsync("superuser", "l3tm3in"), Util.BuildDataListRequestEx(dListView)); + Util.ValidateDataReturnResponseOk(a); + Util.ValidateHTTPStatusCode(a, 200); + + //assert contains at least this test record + ((JArray)a.ObjectResponse["data"]).Count.Should().BeGreaterThan(0); + var v = ((JArray)a.ObjectResponse["data"]); + List IDInResultList = new List(); + int InclusiveMatchCount = 0; + int ExclusiveMatchCount = 0; + + foreach (JArray ja in v) + { + JObject o = ja[0] as JObject; + + if (IncludedWidgetId == o["i"].Value()) + InclusiveMatchCount++; + if (ExcludedWidgetId == o["i"].Value()) + ExclusiveMatchCount++; + } + + InclusiveMatchCount.Should().BeGreaterOrEqualTo(1); + ExclusiveMatchCount.Should().Be(0); + + //DELETE WIDGETS + a = await Util.DeleteAsync("widget/" + IncludedWidgetId.ToString(), await Util.GetTokenAsync("BizAdminFull")); + Util.ValidateHTTPStatusCode(a, 204); + + a = await Util.DeleteAsync("widget/" + ExcludedWidgetId.ToString(), await Util.GetTokenAsync("BizAdminFull")); + Util.ValidateHTTPStatusCode(a, 204); + + } + + /* + RELATIVE TOKEN EXAMPLE: + + public const string TokenYesterday = "{[yesterday]}"; + public const string TokenToday = "{[today]}"; + public const string TokenTomorrow = "{[tomorrow]}"; + public const string TokenLastWeek = "{[lastweek]}"; + public const string TokenThisWeek = "{[thisweek]}"; + public const string TokenNextWeek = "{[nextweek]}"; + public const string TokenLastMonth = "{[lastmonth]}"; + public const string TokenThisMonth = "{[thismonth]}"; + public const string TokenNextMonth = "{[nextmonth]}"; + public const string TokenFourteenDayWindow = "{[14daywindow]}"; + public const string TokenPast = "{[past]}"; + public const string TokenFuture = "{[future]}"; + public const string TokenLastYear = "{[lastyear]}"; + public const string TokenThisYear = "{[thisyear]}"; + public const string TokenInTheLast3Months = "{[last3months]}"; + public const string TokenInTheLast6Months = "{[last6months]}"; + public const string TokenInTheLastYear = "{[lastcalendaryear]}"; + + //More business time frames + + public const string TokenYearToDate = "{[yeartodate]}"; + + public const string TokenPast90Days = "{[past90days]}"; + public const string TokenPast30Days = "{[past30days]}"; + public const string TokenPast24Hours = "{[past24hours]}"; + + //Months THIS year + public const string TokenJanuary = "{[january]}"; + public const string TokenFebruary = "{[february]}"; + public const string TokenMarch = "{[march]}"; + public const string TokenApril = "{[april]}"; + public const string TokenMay = "{[may]}"; + public const string TokenJune = "{[june]}"; + public const string TokenJuly = "{[july]}"; + public const string TokenAugust = "{[august]}"; + public const string TokenSeptember = "{[september]}"; + public const string TokenOctober = "{[october]}"; + public const string TokenNovember = "{[november]}"; + public const string TokenDecember = "{[december]}"; + + /// + /// + /// + [Fact] + public async Task DateTokenYesterdayFilterWorks() + { + + var WidgetNameStart = "DateTokenYesterdayFilterWorks"; + + long IncludedWidgetId = 0; + long ExcludedWidgetId = 0; + + //CREATE TEST WIDGETS + + //included widget + dynamic w = new JObject(); + w.name = Util.Uniquify(WidgetNameStart); + w.notes = "blah"; + w.customFields = Util.WidgetRequiredCustomFieldsJsonString(); + w.startDate = DateTime.UtcNow.AddDays(-1); + w.endDate = DateTime.UtcNow.AddHours(1).AddDays(-1); + + ApiResponse a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w.ToString()); + Util.ValidateDataReturnResponseOk(a); + IncludedWidgetId = a.ObjectResponse["data"]["id"].Value(); + + //Excluded widget + w.name = Util.Uniquify(WidgetNameStart); + w.startDate = DateTime.UtcNow; + w.endDate = DateTime.UtcNow.AddHours(1); + + a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w.ToString()); + Util.ValidateDataReturnResponseOk(a); + ExcludedWidgetId = a.ObjectResponse["data"]["id"].Value(); + + //CREATE LISTVIEW + dynamic d = new JObject(); + d.name = Util.Uniquify(WidgetNameStart); + + d["public"] = true; + d.listKey = "TestWidgetDataList"; + + dynamic dListView = new JArray(); + + //name starts with filter to constrict to widgets that this test block created only + dListView.Add(Util.BuildSimpleFilterDataListViewColumn("widgetname", Util.OpStartsWith, WidgetNameStart)); + + //## INCLUSIVE FILTER + dynamic FilterItem = new JObject(); + FilterItem.fld = "widgetstartdate"; + FilterItem.op = Util.OpEquality; + FilterItem.value = TokenYesterday; + dListView.Add(Util.BuildSimpleFilterDataListViewColumn("XXXX", Util.XXXX, XXXX)); + + + + a = await Util, await Util.GetTokenAsync("BizAdminFull"), d.ToString()); + Util.ValidateDataReturnResponseOk(a); + + long DataFilterId = a.ObjectResponse["data"]["id"].Value(); + + //FETCH DATALIST + a = await Util.PostAsync($"data-list", await Util.GetTokenAsync("superuser", "l3tm3in"), Util.BuildDataListRequestEx(dListView)); + Util.ValidateDataReturnResponseOk(a); + Util.ValidateHTTPStatusCode(a, 200); + + //assert contains at least this test record + ((JArray)a.ObjectResponse["data"]).Count.Should().BeGreaterThan(0); + var v = ((JArray)a.ObjectResponse["data"]); + List IDInResultList = new List(); + int InclusiveMatchCount = 0; + int ExclusiveMatchCount = 0; + foreach (JArray ja in v) + { + JObject o = ja[0] as JObject; + if (IncludedWidgetId == o["i"].Value()) + InclusiveMatchCount++; + if (ExcludedWidgetId == o["i"].Value()) + ExclusiveMatchCount++; + } + + InclusiveMatchCount.Should().BeGreaterOrEqualTo(1); + ExclusiveMatchCount.Should().Be(0); + + //DELETE WIDGETS + a = await Util.DeleteAsync("widget/" + IncludedWidgetId.ToString(), await Util.GetTokenAsync("BizAdminFull")); + Util.ValidateHTTPStatusCode(a, 204); + + a = await Util.DeleteAsync("widget/" + ExcludedWidgetId.ToString(), await Util.GetTokenAsync("BizAdminFull")); + Util.ValidateHTTPStatusCode(a, 204); + + + //DELETE DATAFILTER + a = await Util.DeleteAsync("DataListFilter/" + DataFilterId.ToString(), await Util.GetTokenAsync("BizAdminFull")); + Util.ValidateHTTPStatusCode(a, 204); + } + + + + */ + + #endregion DATE REGULAR FILTERS + //======== + + #endregion date filter tests + + + + /////////////////////////////////////////////////////////////////////////////// + //TEXT + // + + #region STRING FILTER TESTS + + /// + /// + /// + [Fact] + public async Task TextOpEqualityFilterWorks() + { + + var TestName = "TextOpEqualityFilterWorks"; + var WidgetNameStart = Util.Uniquify(TestName); + + List InclusiveWidgetIdList = new List(); + List ExclusiveWidgetIdList = new List(); + + //CREATE 4 TEST WIDGETS + //two inclusive and two not inclusive + + //first inclusive widget + dynamic w = new JObject(); + w.name = Util.Uniquify(WidgetNameStart); + w.customFields = Util.WidgetRequiredCustomFieldsJsonString(); + w.notes = "aardvark"; + w.usertype = 1; + + ApiResponse a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w.ToString()); + Util.ValidateDataReturnResponseOk(a); + InclusiveWidgetIdList.Add(a.ObjectResponse["data"]["id"].Value()); + + //second inclusive widget + w.name = Util.Uniquify(WidgetNameStart); + + a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w.ToString()); + Util.ValidateDataReturnResponseOk(a); + InclusiveWidgetIdList.Add(a.ObjectResponse["data"]["id"].Value()); + + //first exclusive widget + w.name = Util.Uniquify(WidgetNameStart); + w.notes = "zebra"; + w.active = false; + + a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w.ToString()); + Util.ValidateDataReturnResponseOk(a); + ExclusiveWidgetIdList.Add(a.ObjectResponse["data"]["id"].Value()); + + //second exclusive widget + w.name = Util.Uniquify(WidgetNameStart); + w.active = false; + + a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w.ToString()); + Util.ValidateDataReturnResponseOk(a); + ExclusiveWidgetIdList.Add(a.ObjectResponse["data"]["id"].Value()); + + + //CREATE LISTVIEW + dynamic dListView = new JArray(); + + //name starts with filter to constrict to widgets that this test block created only + dListView.Add(Util.BuildSimpleFilterDataListViewColumn("widgetname", Util.OpStartsWith, WidgetNameStart)); + + //FILTER + // dynamic DataFilterActive = new JObject(); + // DataFilterActive.fld = "widgetnotes"; + // DataFilterActive.op = Util.OpEquality; + // DataFilterActive.value = "aardvark"; + dListView.Add(Util.BuildSimpleFilterDataListViewColumn("widgetnotes", Util.OpEquality, "aardvark")); + + + + //FETCH DATALIST + a = await Util.PostAsync($"data-list", await Util.GetTokenAsync("superuser", "l3tm3in"), Util.BuildDataListRequestEx(dListView)); + Util.ValidateDataReturnResponseOk(a); + Util.ValidateHTTPStatusCode(a, 200); + + //assert contains at least two records + ((JArray)a.ObjectResponse["data"]).Count.Should().BeGreaterThan(1); + var v = ((JArray)a.ObjectResponse["data"]); + List IDInResultList = new List(); + int InclusiveMatchCount = 0; + int ExclusiveMatchCount = 0; + foreach (JArray ja in v) + { + JObject o = ja[0] as JObject; + if (InclusiveWidgetIdList.Contains(o["i"].Value())) + InclusiveMatchCount++; + if (ExclusiveWidgetIdList.Contains(o["i"].Value())) + ExclusiveMatchCount++; + } + + InclusiveMatchCount.Should().Be(InclusiveWidgetIdList.Count); + ExclusiveMatchCount.Should().Be(0); + + //DELETE WIDGETS + foreach (long l in InclusiveWidgetIdList) + { + a = await Util.DeleteAsync("widget/" + l.ToString(), await Util.GetTokenAsync("BizAdminFull")); + Util.ValidateHTTPStatusCode(a, 204); + } + + foreach (long l in ExclusiveWidgetIdList) + { + a = await Util.DeleteAsync("widget/" + l.ToString(), await Util.GetTokenAsync("BizAdminFull")); + Util.ValidateHTTPStatusCode(a, 204); + } + } + + + + + /// + /// Specifically test a string with an apostrophe in it (for inclusive) + /// + [Fact] + public async Task TextApostropheOpEqualityFilterWorks() + { + + var TestName = "TextApostropheOpEqualityFilterWorks"; + var WidgetNameStart = Util.Uniquify(TestName); + + List InclusiveWidgetIdList = new List(); + List ExclusiveWidgetIdList = new List(); + + //CREATE 4 TEST WIDGETS + //two inclusive and two not inclusive + + //first inclusive widget + dynamic w = new JObject(); + w.name = Util.Uniquify(WidgetNameStart); + w.customFields = Util.WidgetRequiredCustomFieldsJsonString(); + w.notes = "O'Flaherty's pub"; + w.usertype = 1; + + ApiResponse a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w.ToString()); + Util.ValidateDataReturnResponseOk(a); + InclusiveWidgetIdList.Add(a.ObjectResponse["data"]["id"].Value()); + + //second inclusive widget + w.name = Util.Uniquify(WidgetNameStart); + + a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w.ToString()); + Util.ValidateDataReturnResponseOk(a); + InclusiveWidgetIdList.Add(a.ObjectResponse["data"]["id"].Value()); + + //first exclusive widget + w.name = Util.Uniquify(WidgetNameStart); + w.notes = "Outback steak house"; + w.active = false; + + a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w.ToString()); + Util.ValidateDataReturnResponseOk(a); + ExclusiveWidgetIdList.Add(a.ObjectResponse["data"]["id"].Value()); + + //second exclusive widget + w.name = Util.Uniquify(WidgetNameStart); + w.active = false; + + a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w.ToString()); + Util.ValidateDataReturnResponseOk(a); + ExclusiveWidgetIdList.Add(a.ObjectResponse["data"]["id"].Value()); + + + //CREATE LISTVIEW + dynamic dListView = new JArray(); + + //name starts with filter to constrict to widgets that this test block created only + dListView.Add(Util.BuildSimpleFilterDataListViewColumn("widgetname", Util.OpStartsWith, WidgetNameStart)); + //FILTER + // dynamic DataFilterActive = new JObject(); + // DataFilterActive.fld = "widgetnotes"; + // DataFilterActive.op = Util.OpEquality; + // DataFilterActive.value = "O'Flaherty's pub"; + dListView.Add(Util.BuildSimpleFilterDataListViewColumn("widgetnotes", Util.OpEquality, "O'Flaherty's pub")); + + + //FETCH DATALIST + a = await Util.PostAsync($"data-list", await Util.GetTokenAsync("superuser", "l3tm3in"), Util.BuildDataListRequestEx(dListView)); + Util.ValidateDataReturnResponseOk(a); + Util.ValidateHTTPStatusCode(a, 200); + + //assert contains at least two records + ((JArray)a.ObjectResponse["data"]).Count.Should().BeGreaterThan(1); + var v = ((JArray)a.ObjectResponse["data"]); + List IDInResultList = new List(); + int InclusiveMatchCount = 0; + int ExclusiveMatchCount = 0; + foreach (JArray ja in v) + { + JObject o = ja[0] as JObject; + if (InclusiveWidgetIdList.Contains(o["i"].Value())) + InclusiveMatchCount++; + if (ExclusiveWidgetIdList.Contains(o["i"].Value())) + ExclusiveMatchCount++; + } + + InclusiveMatchCount.Should().Be(InclusiveWidgetIdList.Count); + ExclusiveMatchCount.Should().Be(0); + + //DELETE WIDGETS + foreach (long l in InclusiveWidgetIdList) + { + a = await Util.DeleteAsync("widget/" + l.ToString(), await Util.GetTokenAsync("BizAdminFull")); + Util.ValidateHTTPStatusCode(a, 204); + } + + foreach (long l in ExclusiveWidgetIdList) + { + a = await Util.DeleteAsync("widget/" + l.ToString(), await Util.GetTokenAsync("BizAdminFull")); + Util.ValidateHTTPStatusCode(a, 204); + } + } + + /// + /// specifically test a string with an ampersand character in it for inclusive (finding it) + /// + [Fact] + public async Task TextAmpersandOpEqualityFilterWorks() + { + + var TestName = "TextAmpersandOpEqualityFilterWorks"; + var WidgetNameStart = Util.Uniquify(TestName); + + List InclusiveWidgetIdList = new List(); + List ExclusiveWidgetIdList = new List(); + + //CREATE 4 TEST WIDGETS + //two inclusive and two not inclusive + + //first inclusive widget + dynamic w = new JObject(); + w.name = Util.Uniquify(WidgetNameStart); + w.customFields = Util.WidgetRequiredCustomFieldsJsonString(); + w.notes = "Bill & Ted's excellent adventure"; + w.usertype = 1; + + ApiResponse a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w.ToString()); + Util.ValidateDataReturnResponseOk(a); + InclusiveWidgetIdList.Add(a.ObjectResponse["data"]["id"].Value()); + + //second inclusive widget + w.name = Util.Uniquify(WidgetNameStart); + + a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w.ToString()); + Util.ValidateDataReturnResponseOk(a); + InclusiveWidgetIdList.Add(a.ObjectResponse["data"]["id"].Value()); + + //first exclusive widget + w.name = Util.Uniquify(WidgetNameStart); + w.notes = "Strange things are afoot at the Circle-K"; + w.active = false; + + a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w.ToString()); + Util.ValidateDataReturnResponseOk(a); + ExclusiveWidgetIdList.Add(a.ObjectResponse["data"]["id"].Value()); + + //second exclusive widget + w.name = Util.Uniquify(WidgetNameStart); + w.active = false; + + a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w.ToString()); + Util.ValidateDataReturnResponseOk(a); + ExclusiveWidgetIdList.Add(a.ObjectResponse["data"]["id"].Value()); + + + //CREATE LISTVIEW + dynamic dListView = new JArray(); + + //name starts with filter to constrict to widgets that this test block created only + dListView.Add(Util.BuildSimpleFilterDataListViewColumn("widgetname", Util.OpStartsWith, WidgetNameStart)); + + //FILTER + // dynamic DataFilterActive = new JObject(); + // DataFilterActive.fld = "widgetnotes"; + // DataFilterActive.op = Util.OpEquality; + // DataFilterActive.value = "Bill & Ted's excellent adventure"; + dListView.Add(Util.BuildSimpleFilterDataListViewColumn("widgetnotes", Util.OpEquality, "Bill & Ted's excellent adventure")); + //FETCH DATALIST + a = await Util.PostAsync($"data-list", await Util.GetTokenAsync("superuser", "l3tm3in"), Util.BuildDataListRequestEx(dListView)); + Util.ValidateDataReturnResponseOk(a); + Util.ValidateHTTPStatusCode(a, 200); + + //assert contains at least two records + ((JArray)a.ObjectResponse["data"]).Count.Should().BeGreaterThan(1); + var v = ((JArray)a.ObjectResponse["data"]); + List IDInResultList = new List(); + int InclusiveMatchCount = 0; + int ExclusiveMatchCount = 0; + + + foreach (JArray ja in v) + { + JObject o = ja[0] as JObject; + + if (InclusiveWidgetIdList.Contains(o["i"].Value())) + InclusiveMatchCount++; + if (ExclusiveWidgetIdList.Contains(o["i"].Value())) + ExclusiveMatchCount++; + } + + InclusiveMatchCount.Should().Be(InclusiveWidgetIdList.Count); + ExclusiveMatchCount.Should().Be(0); + + //DELETE WIDGETS + foreach (long l in InclusiveWidgetIdList) + { + a = await Util.DeleteAsync("widget/" + l.ToString(), await Util.GetTokenAsync("BizAdminFull")); + Util.ValidateHTTPStatusCode(a, 204); + } + + foreach (long l in ExclusiveWidgetIdList) + { + a = await Util.DeleteAsync("widget/" + l.ToString(), await Util.GetTokenAsync("BizAdminFull")); + Util.ValidateHTTPStatusCode(a, 204); + } + } + + /// + /// specifically test a non english unicode string + /// + [Fact] + public async Task TextUnicodeOpEqualityFilterWorks() + { + + var TestName = "TextUnicodeOpEqualityFilterWorks"; + var WidgetNameStart = Util.Uniquify(TestName); + + List InclusiveWidgetIdList = new List(); + List ExclusiveWidgetIdList = new List(); + + //CREATE 4 TEST WIDGETS + //two inclusive and two not inclusive + + //first inclusive widget + var InclusiveTestString = "Ādam Iñtërnâtiônàližætiøn"; + dynamic w = new JObject(); + w.name = Util.Uniquify(WidgetNameStart); + w.customFields = Util.WidgetRequiredCustomFieldsJsonString(); + w.notes = InclusiveTestString; + w.usertype = 1; + + ApiResponse a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w.ToString()); + Util.ValidateDataReturnResponseOk(a); + InclusiveWidgetIdList.Add(a.ObjectResponse["data"]["id"].Value()); + + //second inclusive widget + w.name = Util.Uniquify(WidgetNameStart); + + a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w.ToString()); + Util.ValidateDataReturnResponseOk(a); + InclusiveWidgetIdList.Add(a.ObjectResponse["data"]["id"].Value()); + + //first exclusive widget + w.name = Util.Uniquify(WidgetNameStart); + w.notes = "Adam Internationalization"; + w.active = false; + + a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w.ToString()); + Util.ValidateDataReturnResponseOk(a); + ExclusiveWidgetIdList.Add(a.ObjectResponse["data"]["id"].Value()); + + //second exclusive widget + w.name = Util.Uniquify(WidgetNameStart); + w.active = false; + + a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w.ToString()); + Util.ValidateDataReturnResponseOk(a); + ExclusiveWidgetIdList.Add(a.ObjectResponse["data"]["id"].Value()); + + + //CREATE LISTVIEW + dynamic dListView = new JArray(); + + //name starts with filter to constrict to widgets that this test block created only + dListView.Add(Util.BuildSimpleFilterDataListViewColumn("widgetname", Util.OpStartsWith, WidgetNameStart)); + + //FILTER + // dynamic DataFilterActive = new JObject(); + // DataFilterActive.fld = "widgetnotes"; + // DataFilterActive.op = Util.OpEquality; + // DataFilterActive.value = InclusiveTestString; + dListView.Add(Util.BuildSimpleFilterDataListViewColumn("widgetnotes", Util.OpEquality, InclusiveTestString)); + + //FETCH DATALIST + a = await Util.PostAsync($"data-list", await Util.GetTokenAsync("superuser", "l3tm3in"), Util.BuildDataListRequestEx(dListView)); + Util.ValidateDataReturnResponseOk(a); + Util.ValidateHTTPStatusCode(a, 200); + + //assert contains at least two records + ((JArray)a.ObjectResponse["data"]).Count.Should().BeGreaterThan(1); + var v = ((JArray)a.ObjectResponse["data"]); + List IDInResultList = new List(); + int InclusiveMatchCount = 0; + int ExclusiveMatchCount = 0; + foreach (JArray ja in v) + { + JObject o = ja[0] as JObject; + if (InclusiveWidgetIdList.Contains(o["i"].Value())) + InclusiveMatchCount++; + if (ExclusiveWidgetIdList.Contains(o["i"].Value())) + ExclusiveMatchCount++; + } + + InclusiveMatchCount.Should().Be(InclusiveWidgetIdList.Count); + ExclusiveMatchCount.Should().Be(0); + + //DELETE WIDGETS + foreach (long l in InclusiveWidgetIdList) + { + a = await Util.DeleteAsync("widget/" + l.ToString(), await Util.GetTokenAsync("BizAdminFull")); + Util.ValidateHTTPStatusCode(a, 204); + } + + foreach (long l in ExclusiveWidgetIdList) + { + a = await Util.DeleteAsync("widget/" + l.ToString(), await Util.GetTokenAsync("BizAdminFull")); + Util.ValidateHTTPStatusCode(a, 204); + } + } + + + /// + /// + /// + [Fact] + public async Task TextOpGreaterThanFilterWorks() + { + + var TestName = "TextOpGreaterThanFilterWorks"; + var WidgetNameStart = Util.Uniquify(TestName); + + List InclusiveWidgetIdList = new List(); + List ExclusiveWidgetIdList = new List(); + + //CREATE 4 TEST WIDGETS + //two inclusive and two not inclusive + + //first inclusive widget + dynamic w = new JObject(); + w.name = Util.Uniquify(WidgetNameStart); + w.customFields = Util.WidgetRequiredCustomFieldsJsonString(); + w.notes = "Alabama"; + w.usertype = 1; + + ApiResponse a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w.ToString()); + Util.ValidateDataReturnResponseOk(a); + InclusiveWidgetIdList.Add(a.ObjectResponse["data"]["id"].Value()); + + //second inclusive widget + w.name = Util.Uniquify(WidgetNameStart); + + a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w.ToString()); + Util.ValidateDataReturnResponseOk(a); + InclusiveWidgetIdList.Add(a.ObjectResponse["data"]["id"].Value()); + + //first exclusive widget + w.name = Util.Uniquify(WidgetNameStart); + w.notes = "Aardvark"; + w.active = false; + + a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w.ToString()); + Util.ValidateDataReturnResponseOk(a); + ExclusiveWidgetIdList.Add(a.ObjectResponse["data"]["id"].Value()); + + //second exclusive widget + w.name = Util.Uniquify(WidgetNameStart); + w.active = false; + + a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w.ToString()); + Util.ValidateDataReturnResponseOk(a); + ExclusiveWidgetIdList.Add(a.ObjectResponse["data"]["id"].Value()); + + + //CREATE LISTVIEW + dynamic dListView = new JArray(); + + //name starts with filter to constrict to widgets that this test block created only + dListView.Add(Util.BuildSimpleFilterDataListViewColumn("widgetname", Util.OpStartsWith, WidgetNameStart)); + + //FILTER + // dynamic DataFilterActive = new JObject(); + // DataFilterActive.fld = "widgetnotes"; + // DataFilterActive.op = Util.OpGreaterThan; + // DataFilterActive.value = "Aardvark"; + dListView.Add(Util.BuildSimpleFilterDataListViewColumn("widgetnotes", Util.OpGreaterThan, "Aardvark")); + + + //FETCH DATALIST + a = await Util.PostAsync($"data-list", await Util.GetTokenAsync("superuser", "l3tm3in"), Util.BuildDataListRequestEx(dListView)); + Util.ValidateDataReturnResponseOk(a); + Util.ValidateHTTPStatusCode(a, 200); + + //assert contains at least two records + ((JArray)a.ObjectResponse["data"]).Count.Should().BeGreaterThan(1); + var v = ((JArray)a.ObjectResponse["data"]); + List IDInResultList = new List(); + int InclusiveMatchCount = 0; + int ExclusiveMatchCount = 0; + foreach (JArray ja in v) + { + JObject o = ja[0] as JObject; + if (InclusiveWidgetIdList.Contains(o["i"].Value())) + InclusiveMatchCount++; + if (ExclusiveWidgetIdList.Contains(o["i"].Value())) + ExclusiveMatchCount++; + } + + InclusiveMatchCount.Should().Be(InclusiveWidgetIdList.Count); + ExclusiveMatchCount.Should().Be(0); + + //DELETE WIDGETS + foreach (long l in InclusiveWidgetIdList) + { + a = await Util.DeleteAsync("widget/" + l.ToString(), await Util.GetTokenAsync("BizAdminFull")); + Util.ValidateHTTPStatusCode(a, 204); + } + + foreach (long l in ExclusiveWidgetIdList) + { + a = await Util.DeleteAsync("widget/" + l.ToString(), await Util.GetTokenAsync("BizAdminFull")); + Util.ValidateHTTPStatusCode(a, 204); + } + } + + + /// + /// + /// + [Fact] + public async Task TextOpGreaterThanOrEqualToFilterWorks() + { + + var TestName = "TextOpGreaterThanOrEqualToFilterWorks"; + var WidgetNameStart = Util.Uniquify(TestName); + + List InclusiveWidgetIdList = new List(); + List ExclusiveWidgetIdList = new List(); + + //CREATE 4 TEST WIDGETS + //two inclusive and two not inclusive + + //first inclusive widget + dynamic w = new JObject(); + w.name = Util.Uniquify(WidgetNameStart); + w.customFields = Util.WidgetRequiredCustomFieldsJsonString(); + w.notes = "Bjorn"; + w.usertype = 1; + + ApiResponse a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w.ToString()); + Util.ValidateDataReturnResponseOk(a); + InclusiveWidgetIdList.Add(a.ObjectResponse["data"]["id"].Value()); + + //second inclusive widget + w.name = Util.Uniquify(WidgetNameStart); + + a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w.ToString()); + Util.ValidateDataReturnResponseOk(a); + InclusiveWidgetIdList.Add(a.ObjectResponse["data"]["id"].Value()); + + //first exclusive widget + w.name = Util.Uniquify(WidgetNameStart); + w.notes = "Bing"; + w.active = false; + + a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w.ToString()); + Util.ValidateDataReturnResponseOk(a); + ExclusiveWidgetIdList.Add(a.ObjectResponse["data"]["id"].Value()); + + //second exclusive widget + w.name = Util.Uniquify(WidgetNameStart); + w.active = false; + + a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w.ToString()); + Util.ValidateDataReturnResponseOk(a); + ExclusiveWidgetIdList.Add(a.ObjectResponse["data"]["id"].Value()); + + + //CREATE LISTVIEW + dynamic dListView = new JArray(); + + //name starts with filter to constrict to widgets that this test block created only + dListView.Add(Util.BuildSimpleFilterDataListViewColumn("widgetname", Util.OpStartsWith, WidgetNameStart)); + + //FILTER + // dynamic DataFilterActive = new JObject(); + // DataFilterActive.fld = "widgetnotes"; + // DataFilterActive.op = Util.OpGreaterThanOrEqualTo; + // DataFilterActive.value = "Bjarn"; + dListView.Add(Util.BuildSimpleFilterDataListViewColumn("widgetnotes", Util.OpGreaterThanOrEqualTo, "Bjarn")); + + //FETCH DATALIST + a = await Util.PostAsync($"data-list", await Util.GetTokenAsync("superuser", "l3tm3in"), Util.BuildDataListRequestEx(dListView)); + Util.ValidateDataReturnResponseOk(a); + Util.ValidateHTTPStatusCode(a, 200); + + //assert contains at least two records + ((JArray)a.ObjectResponse["data"]).Count.Should().BeGreaterThan(1); + var v = ((JArray)a.ObjectResponse["data"]); + List IDInResultList = new List(); + int InclusiveMatchCount = 0; + int ExclusiveMatchCount = 0; + foreach (JArray ja in v) + { + JObject o = ja[0] as JObject; + if (InclusiveWidgetIdList.Contains(o["i"].Value())) + InclusiveMatchCount++; + if (ExclusiveWidgetIdList.Contains(o["i"].Value())) + ExclusiveMatchCount++; + } + + InclusiveMatchCount.Should().Be(InclusiveWidgetIdList.Count); + ExclusiveMatchCount.Should().Be(0); + + //DELETE WIDGETS + foreach (long l in InclusiveWidgetIdList) + { + a = await Util.DeleteAsync("widget/" + l.ToString(), await Util.GetTokenAsync("BizAdminFull")); + Util.ValidateHTTPStatusCode(a, 204); + } + + foreach (long l in ExclusiveWidgetIdList) + { + a = await Util.DeleteAsync("widget/" + l.ToString(), await Util.GetTokenAsync("BizAdminFull")); + Util.ValidateHTTPStatusCode(a, 204); + } + } + + + /// + /// + /// + [Fact] + public async Task TextOpLessThanFilterWorks() + { + + var TestName = "TextOpLessThanFilterWorks"; + var WidgetNameStart = Util.Uniquify(TestName); + + List InclusiveWidgetIdList = new List(); + List ExclusiveWidgetIdList = new List(); + + //CREATE 4 TEST WIDGETS + //two inclusive and two not inclusive + + //first inclusive widget + dynamic w = new JObject(); + w.name = Util.Uniquify(WidgetNameStart); + w.customFields = Util.WidgetRequiredCustomFieldsJsonString(); + w.notes = "California"; + w.usertype = 1; + + ApiResponse a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w.ToString()); + Util.ValidateDataReturnResponseOk(a); + InclusiveWidgetIdList.Add(a.ObjectResponse["data"]["id"].Value()); + + //second inclusive widget + w.name = Util.Uniquify(WidgetNameStart); + + a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w.ToString()); + Util.ValidateDataReturnResponseOk(a); + InclusiveWidgetIdList.Add(a.ObjectResponse["data"]["id"].Value()); + + //first exclusive widget + w.name = Util.Uniquify(WidgetNameStart); + w.notes = "Cthulu"; + w.active = false; + + a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w.ToString()); + Util.ValidateDataReturnResponseOk(a); + ExclusiveWidgetIdList.Add(a.ObjectResponse["data"]["id"].Value()); + + //second exclusive widget + w.name = Util.Uniquify(WidgetNameStart); + w.active = false; + + a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w.ToString()); + Util.ValidateDataReturnResponseOk(a); + ExclusiveWidgetIdList.Add(a.ObjectResponse["data"]["id"].Value()); + + + //CREATE LISTVIEW + dynamic dListView = new JArray(); + + //name starts with filter to constrict to widgets that this test block created only + dListView.Add(Util.BuildSimpleFilterDataListViewColumn("widgetname", Util.OpStartsWith, WidgetNameStart)); + + //FILTER + // dynamic DataFilterActive = new JObject(); + // DataFilterActive.fld = "widgetnotes"; + // DataFilterActive.op = Util.OpLessThan; + // DataFilterActive.value = "Celery"; + dListView.Add(Util.BuildSimpleFilterDataListViewColumn("widgetnotes", Util.OpLessThan, "Celery")); + + //FETCH DATALIST + a = await Util.PostAsync($"data-list", await Util.GetTokenAsync("superuser", "l3tm3in"), Util.BuildDataListRequestEx(dListView)); + Util.ValidateDataReturnResponseOk(a); + Util.ValidateHTTPStatusCode(a, 200); + + //assert contains at least two records + ((JArray)a.ObjectResponse["data"]).Count.Should().BeGreaterThan(1); + var v = ((JArray)a.ObjectResponse["data"]); + List IDInResultList = new List(); + int InclusiveMatchCount = 0; + int ExclusiveMatchCount = 0; + foreach (JArray ja in v) + { + JObject o = ja[0] as JObject; + if (InclusiveWidgetIdList.Contains(o["i"].Value())) + InclusiveMatchCount++; + if (ExclusiveWidgetIdList.Contains(o["i"].Value())) + ExclusiveMatchCount++; + } + + InclusiveMatchCount.Should().Be(InclusiveWidgetIdList.Count); + ExclusiveMatchCount.Should().Be(0); + + //DELETE WIDGETS + foreach (long l in InclusiveWidgetIdList) + { + a = await Util.DeleteAsync("widget/" + l.ToString(), await Util.GetTokenAsync("BizAdminFull")); + Util.ValidateHTTPStatusCode(a, 204); + } + + foreach (long l in ExclusiveWidgetIdList) + { + a = await Util.DeleteAsync("widget/" + l.ToString(), await Util.GetTokenAsync("BizAdminFull")); + Util.ValidateHTTPStatusCode(a, 204); + } + } + + + /// + /// + /// + [Fact] + public async Task TextOpLessThanOrEqualToFilterWorks() + { + + var TestName = "TextOpLessThanOrEqualToFilterWorks"; + var WidgetNameStart = Util.Uniquify(TestName); + + List InclusiveWidgetIdList = new List(); + List ExclusiveWidgetIdList = new List(); + + //CREATE 4 TEST WIDGETS + //two inclusive and two not inclusive + + //first inclusive widget + dynamic w = new JObject(); + w.name = Util.Uniquify(WidgetNameStart); + w.customFields = Util.WidgetRequiredCustomFieldsJsonString(); + w.notes = "Donut"; + w.usertype = 1; + + ApiResponse a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w.ToString()); + Util.ValidateDataReturnResponseOk(a); + InclusiveWidgetIdList.Add(a.ObjectResponse["data"]["id"].Value()); + + //second inclusive widget + w.name = Util.Uniquify(WidgetNameStart); + + a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w.ToString()); + Util.ValidateDataReturnResponseOk(a); + InclusiveWidgetIdList.Add(a.ObjectResponse["data"]["id"].Value()); + + //first exclusive widget + w.name = Util.Uniquify(WidgetNameStart); + w.notes = "Duvet"; + w.active = false; + + a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w.ToString()); + Util.ValidateDataReturnResponseOk(a); + ExclusiveWidgetIdList.Add(a.ObjectResponse["data"]["id"].Value()); + + //second exclusive widget + w.name = Util.Uniquify(WidgetNameStart); + w.active = false; + + a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w.ToString()); + Util.ValidateDataReturnResponseOk(a); + ExclusiveWidgetIdList.Add(a.ObjectResponse["data"]["id"].Value()); + + + //CREATE LISTVIEW + dynamic dListView = new JArray(); + + //name starts with filter to constrict to widgets that this test block created only + dListView.Add(Util.BuildSimpleFilterDataListViewColumn("widgetname", Util.OpStartsWith, WidgetNameStart)); + + //FILTER + // dynamic DataFilterActive = new JObject(); + // DataFilterActive.fld = "widgetnotes"; + // DataFilterActive.op = Util.OpLessThanOrEqualTo; + // DataFilterActive.value = "Dusseldorf"; + dListView.Add(Util.BuildSimpleFilterDataListViewColumn("widgetnotes", Util.OpLessThanOrEqualTo, "Dusseldorf")); + + + //FETCH DATALIST + a = await Util.PostAsync($"data-list", await Util.GetTokenAsync("superuser", "l3tm3in"), Util.BuildDataListRequestEx(dListView)); + Util.ValidateDataReturnResponseOk(a); + Util.ValidateHTTPStatusCode(a, 200); + + //assert contains at least two records + ((JArray)a.ObjectResponse["data"]).Count.Should().BeGreaterThan(1); + var v = ((JArray)a.ObjectResponse["data"]); + List IDInResultList = new List(); + int InclusiveMatchCount = 0; + int ExclusiveMatchCount = 0; + foreach (JArray ja in v) + { + JObject o = ja[0] as JObject; + if (InclusiveWidgetIdList.Contains(o["i"].Value())) + InclusiveMatchCount++; + if (ExclusiveWidgetIdList.Contains(o["i"].Value())) + ExclusiveMatchCount++; + } + + InclusiveMatchCount.Should().Be(InclusiveWidgetIdList.Count); + ExclusiveMatchCount.Should().Be(0); + + //DELETE WIDGETS + foreach (long l in InclusiveWidgetIdList) + { + a = await Util.DeleteAsync("widget/" + l.ToString(), await Util.GetTokenAsync("BizAdminFull")); + Util.ValidateHTTPStatusCode(a, 204); + } + + foreach (long l in ExclusiveWidgetIdList) + { + a = await Util.DeleteAsync("widget/" + l.ToString(), await Util.GetTokenAsync("BizAdminFull")); + Util.ValidateHTTPStatusCode(a, 204); + } + } + + /// + /// + /// + [Fact] + public async Task TextOpNotEqualFilterWorks() + { + + var TestName = "TextOpNotEqualFilterWorks"; + var WidgetNameStart = Util.Uniquify(TestName); + + List InclusiveWidgetIdList = new List(); + List ExclusiveWidgetIdList = new List(); + + //CREATE 4 TEST WIDGETS + //two inclusive and two not inclusive + + //first inclusive widget + dynamic w = new JObject(); + w.name = Util.Uniquify(WidgetNameStart); + w.customFields = Util.WidgetRequiredCustomFieldsJsonString(); + w.notes = "Egg Salad Sandwich"; + w.usertype = 1; + + ApiResponse a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w.ToString()); + Util.ValidateDataReturnResponseOk(a); + InclusiveWidgetIdList.Add(a.ObjectResponse["data"]["id"].Value()); + + //second inclusive widget + w.name = Util.Uniquify(WidgetNameStart); + + a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w.ToString()); + Util.ValidateDataReturnResponseOk(a); + InclusiveWidgetIdList.Add(a.ObjectResponse["data"]["id"].Value()); + + //first exclusive widget + w.name = Util.Uniquify(WidgetNameStart); + w.notes = "Elephant"; + w.active = false; + + a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w.ToString()); + Util.ValidateDataReturnResponseOk(a); + ExclusiveWidgetIdList.Add(a.ObjectResponse["data"]["id"].Value()); + + //second exclusive widget + w.name = Util.Uniquify(WidgetNameStart); + w.active = false; + + a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w.ToString()); + Util.ValidateDataReturnResponseOk(a); + ExclusiveWidgetIdList.Add(a.ObjectResponse["data"]["id"].Value()); + + + //CREATE LISTVIEW + dynamic dListView = new JArray(); + + //name starts with filter to constrict to widgets that this test block created only + dListView.Add(Util.BuildSimpleFilterDataListViewColumn("widgetname", Util.OpStartsWith, WidgetNameStart)); + + //FILTER + // dynamic DataFilterActive = new JObject(); + // DataFilterActive.fld = "widgetnotes"; + // DataFilterActive.op = Util.OpNotEqual; + // DataFilterActive.value = "Elephant"; + dListView.Add(Util.BuildSimpleFilterDataListViewColumn("widgetnotes", Util.OpNotEqual, "Elephant")); + + //FETCH DATALIST + a = await Util.PostAsync($"data-list", await Util.GetTokenAsync("superuser", "l3tm3in"), Util.BuildDataListRequestEx(dListView)); + Util.ValidateDataReturnResponseOk(a); + Util.ValidateHTTPStatusCode(a, 200); + + //assert contains at least two records + ((JArray)a.ObjectResponse["data"]).Count.Should().BeGreaterThan(1); + var v = ((JArray)a.ObjectResponse["data"]); + List IDInResultList = new List(); + int InclusiveMatchCount = 0; + int ExclusiveMatchCount = 0; + foreach (JArray ja in v) + { + JObject o = ja[0] as JObject; + if (InclusiveWidgetIdList.Contains(o["i"].Value())) + InclusiveMatchCount++; + if (ExclusiveWidgetIdList.Contains(o["i"].Value())) + ExclusiveMatchCount++; + } + + InclusiveMatchCount.Should().Be(InclusiveWidgetIdList.Count); + ExclusiveMatchCount.Should().Be(0); + + //DELETE WIDGETS + foreach (long l in InclusiveWidgetIdList) + { + a = await Util.DeleteAsync("widget/" + l.ToString(), await Util.GetTokenAsync("BizAdminFull")); + Util.ValidateHTTPStatusCode(a, 204); + } + + foreach (long l in ExclusiveWidgetIdList) + { + a = await Util.DeleteAsync("widget/" + l.ToString(), await Util.GetTokenAsync("BizAdminFull")); + Util.ValidateHTTPStatusCode(a, 204); + } + } + + + /// + /// + /// + [Fact] + public async Task TextOpNotContainsFilterWorks() + { + var TestName = "TextOpNotContainsFilterWorks"; + var WidgetNameStart = Util.Uniquify(TestName); + + List InclusiveWidgetIdList = new List(); + List ExclusiveWidgetIdList = new List(); + + //CREATE 4 TEST WIDGETS + //two inclusive and two not inclusive + + //first inclusive widget + dynamic w = new JObject(); + w.name = Util.Uniquify(WidgetNameStart); + w.customFields = Util.WidgetRequiredCustomFieldsJsonString(); + w.notes = "Gray poupon"; + w.usertype = 1; + + ApiResponse a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w.ToString()); + Util.ValidateDataReturnResponseOk(a); + InclusiveWidgetIdList.Add(a.ObjectResponse["data"]["id"].Value()); + + //second inclusive widget + w.name = Util.Uniquify(WidgetNameStart); + + a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w.ToString()); + Util.ValidateDataReturnResponseOk(a); + InclusiveWidgetIdList.Add(a.ObjectResponse["data"]["id"].Value()); + + //first exclusive widget + w.name = Util.Uniquify(WidgetNameStart); + w.notes = "Get shorty"; + w.active = false; + + a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w.ToString()); + Util.ValidateDataReturnResponseOk(a); + ExclusiveWidgetIdList.Add(a.ObjectResponse["data"]["id"].Value()); + + //second exclusive widget + w.name = Util.Uniquify(WidgetNameStart); + w.active = false; + + a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w.ToString()); + Util.ValidateDataReturnResponseOk(a); + ExclusiveWidgetIdList.Add(a.ObjectResponse["data"]["id"].Value()); + + + //CREATE LISTVIEW + dynamic dListView = new JArray(); + + //name starts with filter to constrict to widgets that this test block created only + dListView.Add(Util.BuildSimpleFilterDataListViewColumn("widgetname", Util.OpStartsWith, WidgetNameStart)); + + //FILTER + // dynamic DataFilterActive = new JObject(); + // DataFilterActive.fld = "widgetnotes"; + // DataFilterActive.op = Util.OpNotContains; + // DataFilterActive.value = "short"; + dListView.Add(Util.BuildSimpleFilterDataListViewColumn("widgetnotes", Util.OpNotContains, "short")); + + //FETCH DATALIST + a = await Util.PostAsync($"data-list", await Util.GetTokenAsync("superuser", "l3tm3in"), Util.BuildDataListRequestEx(dListView)); + Util.ValidateDataReturnResponseOk(a); + Util.ValidateHTTPStatusCode(a, 200); + + //assert contains at least two records + ((JArray)a.ObjectResponse["data"]).Count.Should().BeGreaterThan(1); + var v = ((JArray)a.ObjectResponse["data"]); + List IDInResultList = new List(); + int InclusiveMatchCount = 0; + int ExclusiveMatchCount = 0; + foreach (JArray ja in v) + { + JObject o = ja[0] as JObject; + if (InclusiveWidgetIdList.Contains(o["i"].Value())) + InclusiveMatchCount++; + if (ExclusiveWidgetIdList.Contains(o["i"].Value())) + ExclusiveMatchCount++; + } + + InclusiveMatchCount.Should().Be(InclusiveWidgetIdList.Count); + ExclusiveMatchCount.Should().Be(0); + + //DELETE WIDGETS + foreach (long l in InclusiveWidgetIdList) + { + a = await Util.DeleteAsync("widget/" + l.ToString(), await Util.GetTokenAsync("BizAdminFull")); + Util.ValidateHTTPStatusCode(a, 204); + } + + foreach (long l in ExclusiveWidgetIdList) + { + a = await Util.DeleteAsync("widget/" + l.ToString(), await Util.GetTokenAsync("BizAdminFull")); + Util.ValidateHTTPStatusCode(a, 204); + } + } + + + /// + /// + /// + [Fact] + public async Task TextOpContainsFilterWorks() + { + var TestName = "TextOpContainsFilterWorks"; + var WidgetNameStart = Util.Uniquify(TestName); + + List InclusiveWidgetIdList = new List(); + List ExclusiveWidgetIdList = new List(); + + //CREATE 4 TEST WIDGETS + //two inclusive and two not inclusive + + //first inclusive widget + dynamic w = new JObject(); + w.name = Util.Uniquify(WidgetNameStart); + w.customFields = Util.WidgetRequiredCustomFieldsJsonString(); + w.notes = "Fast Freddy Freak"; + w.usertype = 1; + + ApiResponse a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w.ToString()); + Util.ValidateDataReturnResponseOk(a); + InclusiveWidgetIdList.Add(a.ObjectResponse["data"]["id"].Value()); + + //second inclusive widget + w.name = Util.Uniquify(WidgetNameStart); + + a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w.ToString()); + Util.ValidateDataReturnResponseOk(a); + InclusiveWidgetIdList.Add(a.ObjectResponse["data"]["id"].Value()); + + //first exclusive widget + w.name = Util.Uniquify(WidgetNameStart); + w.notes = "Phineas Freak"; + w.active = false; + + a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w.ToString()); + Util.ValidateDataReturnResponseOk(a); + ExclusiveWidgetIdList.Add(a.ObjectResponse["data"]["id"].Value()); + + //second exclusive widget + w.name = Util.Uniquify(WidgetNameStart); + w.active = false; + + a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w.ToString()); + Util.ValidateDataReturnResponseOk(a); + ExclusiveWidgetIdList.Add(a.ObjectResponse["data"]["id"].Value()); + + + //CREATE LISTVIEW + dynamic dListView = new JArray(); + + //name starts with filter to constrict to widgets that this test block created only + dListView.Add(Util.BuildSimpleFilterDataListViewColumn("widgetname", Util.OpStartsWith, WidgetNameStart)); + + //FILTER + // dynamic DataFilterActive = new JObject(); + // DataFilterActive.fld = "widgetnotes"; + // DataFilterActive.op = Util.OpContains; + // DataFilterActive.value = "red"; + dListView.Add(Util.BuildSimpleFilterDataListViewColumn("widgetnotes", Util.OpContains, "red")); + //FETCH DATALIST + a = await Util.PostAsync($"data-list", await Util.GetTokenAsync("superuser", "l3tm3in"), Util.BuildDataListRequestEx(dListView)); + Util.ValidateDataReturnResponseOk(a); + Util.ValidateHTTPStatusCode(a, 200); + + //assert contains at least two records + ((JArray)a.ObjectResponse["data"]).Count.Should().BeGreaterThan(1); + var v = ((JArray)a.ObjectResponse["data"]); + List IDInResultList = new List(); + int InclusiveMatchCount = 0; + int ExclusiveMatchCount = 0; + foreach (JArray ja in v) + { + JObject o = ja[0] as JObject; + if (InclusiveWidgetIdList.Contains(o["i"].Value())) + InclusiveMatchCount++; + if (ExclusiveWidgetIdList.Contains(o["i"].Value())) + ExclusiveMatchCount++; + } + + InclusiveMatchCount.Should().Be(InclusiveWidgetIdList.Count); + ExclusiveMatchCount.Should().Be(0); + + //DELETE WIDGETS + foreach (long l in InclusiveWidgetIdList) + { + a = await Util.DeleteAsync("widget/" + l.ToString(), await Util.GetTokenAsync("BizAdminFull")); + Util.ValidateHTTPStatusCode(a, 204); + } + + foreach (long l in ExclusiveWidgetIdList) + { + a = await Util.DeleteAsync("widget/" + l.ToString(), await Util.GetTokenAsync("BizAdminFull")); + Util.ValidateHTTPStatusCode(a, 204); + } + } + + + /// + /// + /// + [Fact] + public async Task TextOpStartsWithFilterWorks() + { + var TestName = "TextOpStartsWithFilterWorks"; + var WidgetNameStart = Util.Uniquify(TestName); + + List InclusiveWidgetIdList = new List(); + List ExclusiveWidgetIdList = new List(); + + //CREATE 4 TEST WIDGETS + //two inclusive and two not inclusive + + //first inclusive widget + dynamic w = new JObject(); + w.name = Util.Uniquify(WidgetNameStart); + w.customFields = Util.WidgetRequiredCustomFieldsJsonString(); + w.notes = "Granular"; + w.usertype = 1; + + ApiResponse a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w.ToString()); + Util.ValidateDataReturnResponseOk(a); + InclusiveWidgetIdList.Add(a.ObjectResponse["data"]["id"].Value()); + + //second inclusive widget + w.name = Util.Uniquify(WidgetNameStart); + + a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w.ToString()); + Util.ValidateDataReturnResponseOk(a); + InclusiveWidgetIdList.Add(a.ObjectResponse["data"]["id"].Value()); + + //first exclusive widget + w.name = Util.Uniquify(WidgetNameStart); + w.notes = "Gus Grifferson"; + w.active = false; + + a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w.ToString()); + Util.ValidateDataReturnResponseOk(a); + ExclusiveWidgetIdList.Add(a.ObjectResponse["data"]["id"].Value()); + + //second exclusive widget + w.name = Util.Uniquify(WidgetNameStart); + w.active = false; + + a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w.ToString()); + Util.ValidateDataReturnResponseOk(a); + ExclusiveWidgetIdList.Add(a.ObjectResponse["data"]["id"].Value()); + + + //CREATE LISTVIEW + dynamic dListView = new JArray(); + + //name starts with filter to constrict to widgets that this test block created only + dListView.Add(Util.BuildSimpleFilterDataListViewColumn("widgetname", Util.OpStartsWith, WidgetNameStart)); + + //FILTER + // dynamic DataFilterActive = new JObject(); + // DataFilterActive.fld = "widgetnotes"; + // DataFilterActive.op = Util.OpStartsWith; + // DataFilterActive.value = "Gra"; + dListView.Add(Util.BuildSimpleFilterDataListViewColumn("widgetnotes", Util.OpStartsWith, "Gra")); + + + //FETCH DATALIST + a = await Util.PostAsync($"data-list", await Util.GetTokenAsync("superuser", "l3tm3in"), Util.BuildDataListRequestEx(dListView)); + Util.ValidateDataReturnResponseOk(a); + Util.ValidateHTTPStatusCode(a, 200); + + //assert contains at least two records + ((JArray)a.ObjectResponse["data"]).Count.Should().BeGreaterThan(1); + var v = ((JArray)a.ObjectResponse["data"]); + List IDInResultList = new List(); + int InclusiveMatchCount = 0; + int ExclusiveMatchCount = 0; + foreach (JArray ja in v) + { + JObject o = ja[0] as JObject; + if (InclusiveWidgetIdList.Contains(o["i"].Value())) + InclusiveMatchCount++; + if (ExclusiveWidgetIdList.Contains(o["i"].Value())) + ExclusiveMatchCount++; + } + + InclusiveMatchCount.Should().Be(InclusiveWidgetIdList.Count); + ExclusiveMatchCount.Should().Be(0); + + //DELETE WIDGETS + foreach (long l in InclusiveWidgetIdList) + { + a = await Util.DeleteAsync("widget/" + l.ToString(), await Util.GetTokenAsync("BizAdminFull")); + Util.ValidateHTTPStatusCode(a, 204); + } + + foreach (long l in ExclusiveWidgetIdList) + { + a = await Util.DeleteAsync("widget/" + l.ToString(), await Util.GetTokenAsync("BizAdminFull")); + Util.ValidateHTTPStatusCode(a, 204); + } + + } + + + /// + /// + /// + [Fact] + public async Task TextOpEndsWithFilterWorks() + { + var TestName = "TextOpEndsWithFilterWorks"; + var WidgetNameStart = Util.Uniquify(TestName); + + List InclusiveWidgetIdList = new List(); + List ExclusiveWidgetIdList = new List(); + + //CREATE 4 TEST WIDGETS + //two inclusive and two not inclusive + + //first inclusive widget + dynamic w = new JObject(); + w.name = Util.Uniquify(WidgetNameStart); + w.customFields = Util.WidgetRequiredCustomFieldsJsonString(); + w.notes = "Bo Horvat"; + w.usertype = 1; + + ApiResponse a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w.ToString()); + Util.ValidateDataReturnResponseOk(a); + InclusiveWidgetIdList.Add(a.ObjectResponse["data"]["id"].Value()); + + //second inclusive widget + w.name = Util.Uniquify(WidgetNameStart); + + a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w.ToString()); + Util.ValidateDataReturnResponseOk(a); + InclusiveWidgetIdList.Add(a.ObjectResponse["data"]["id"].Value()); + + //first exclusive widget + w.name = Util.Uniquify(WidgetNameStart); + w.notes = "Bo Duke"; + w.active = false; + + a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w.ToString()); + Util.ValidateDataReturnResponseOk(a); + ExclusiveWidgetIdList.Add(a.ObjectResponse["data"]["id"].Value()); + + //second exclusive widget + w.name = Util.Uniquify(WidgetNameStart); + w.active = false; + + a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w.ToString()); + Util.ValidateDataReturnResponseOk(a); + ExclusiveWidgetIdList.Add(a.ObjectResponse["data"]["id"].Value()); + + + //CREATE LISTVIEW + dynamic dListView = new JArray(); + + //name starts with filter to constrict to widgets that this test block created only + dListView.Add(Util.BuildSimpleFilterDataListViewColumn("widgetname", Util.OpStartsWith, WidgetNameStart)); + + //FILTER + // dynamic DataFilterActive = new JObject(); + // DataFilterActive.fld = "widgetnotes"; + // DataFilterActive.op = Util.OpEndsWith; + // DataFilterActive.value = "vat"; + dListView.Add(Util.BuildSimpleFilterDataListViewColumn("widgetnotes", Util.OpEndsWith, "vat")); + + + + //FETCH DATALIST + a = await Util.PostAsync($"data-list", await Util.GetTokenAsync("superuser", "l3tm3in"), Util.BuildDataListRequestEx(dListView)); + Util.ValidateDataReturnResponseOk(a); + Util.ValidateHTTPStatusCode(a, 200); + + //assert contains at least two records + ((JArray)a.ObjectResponse["data"]).Count.Should().BeGreaterThan(1); + var v = ((JArray)a.ObjectResponse["data"]); + List IDInResultList = new List(); + int InclusiveMatchCount = 0; + int ExclusiveMatchCount = 0; + foreach (JArray ja in v) + { + JObject o = ja[0] as JObject; + if (InclusiveWidgetIdList.Contains(o["i"].Value())) + InclusiveMatchCount++; + if (ExclusiveWidgetIdList.Contains(o["i"].Value())) + ExclusiveMatchCount++; + } + + InclusiveMatchCount.Should().Be(InclusiveWidgetIdList.Count); + ExclusiveMatchCount.Should().Be(0); + + //DELETE WIDGETS + foreach (long l in InclusiveWidgetIdList) + { + a = await Util.DeleteAsync("widget/" + l.ToString(), await Util.GetTokenAsync("BizAdminFull")); + Util.ValidateHTTPStatusCode(a, 204); + } + + foreach (long l in ExclusiveWidgetIdList) + { + a = await Util.DeleteAsync("widget/" + l.ToString(), await Util.GetTokenAsync("BizAdminFull")); + Util.ValidateHTTPStatusCode(a, 204); + } + + } + + + //====================== + + #endregion string filter tests + + + + + /////////////////////////////////////////////////////////////////////////////// + //INT + // + #region INTEGER TESTS + + /// + /// + /// + [Fact] + public async Task IntegerOpEqualityFilterWorks() + { + + var WidgetNameStart = "IntegerDataFilterTest"; + + long IncludedWidgetId = 0; + long ExcludedWidgetId = 0; + + //CREATE TEST WIDGETS + + + //included widget + dynamic w = new JObject(); + w.name = Util.Uniquify(WidgetNameStart); + w.customFields = Util.WidgetRequiredCustomFieldsJsonString(); + w.active = true; + w.usertype = 1; + w.count = 5; + w.notes = "blah"; + w.customFields = Util.WidgetRequiredCustomFieldsJsonString(); + + ApiResponse a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w.ToString()); + Util.ValidateDataReturnResponseOk(a); + IncludedWidgetId = a.ObjectResponse["data"]["id"].Value(); + + //Excluded widget + w.name = Util.Uniquify(WidgetNameStart); + w.count = 3; + a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w.ToString()); + Util.ValidateDataReturnResponseOk(a); + ExcludedWidgetId = a.ObjectResponse["data"]["id"].Value(); + + //CREATE LISTVIEW + dynamic dListView = new JArray(); + + //name starts with filter to constrict to widgets that this test block created only + dListView.Add(Util.BuildSimpleFilterDataListViewColumn("widgetname", Util.OpStartsWith, WidgetNameStart)); + + //inclusive test filter + + // dynamic FilterItem = new JObject(); + // FilterItem.fld = "widgetcount"; + // FilterItem.op = Util.OpEquality; + // FilterItem.value = 5; + dListView.Add(Util.BuildSimpleFilterDataListViewColumn("widgetcount", Util.OpEquality, 5)); + + //FETCH DATALIST + a = await Util.PostAsync($"data-list", await Util.GetTokenAsync("superuser", "l3tm3in"), Util.BuildDataListRequestEx(dListView)); + Util.ValidateDataReturnResponseOk(a); + Util.ValidateHTTPStatusCode(a, 200); + + //assert contains at least this test record + ((JArray)a.ObjectResponse["data"]).Count.Should().BeGreaterThan(0); + var v = ((JArray)a.ObjectResponse["data"]); + List IDInResultList = new List(); + int InclusiveMatchCount = 0; + int ExclusiveMatchCount = 0; + foreach (JArray ja in v) + { + JObject o = ja[0] as JObject; + if (IncludedWidgetId == o["i"].Value()) + InclusiveMatchCount++; + if (ExcludedWidgetId == o["i"].Value()) + ExclusiveMatchCount++; + } + + InclusiveMatchCount.Should().BeGreaterOrEqualTo(1); + ExclusiveMatchCount.Should().Be(0); + + //DELETE WIDGETS + a = await Util.DeleteAsync("widget/" + IncludedWidgetId.ToString(), await Util.GetTokenAsync("BizAdminFull")); + Util.ValidateHTTPStatusCode(a, 204); + + a = await Util.DeleteAsync("widget/" + ExcludedWidgetId.ToString(), await Util.GetTokenAsync("BizAdminFull")); + Util.ValidateHTTPStatusCode(a, 204); + + } + + /// + /// + /// + [Fact] + public async Task IntegerOpGreaterThanFilterWorks() + { + + var WidgetNameStart = "IntegerOpGreaterThanFilterWorks"; + + long IncludedWidgetId = 0; + long ExcludedWidgetId = 0; + + //CREATE TEST WIDGETS + + //included widget + dynamic w = new JObject(); + w.name = Util.Uniquify(WidgetNameStart); + w.customFields = Util.WidgetRequiredCustomFieldsJsonString(); + w.notes = "blah"; + w.active = true; + w.usertype = 1; + w.count = 55; + + ApiResponse a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w.ToString()); + Util.ValidateDataReturnResponseOk(a); + IncludedWidgetId = a.ObjectResponse["data"]["id"].Value(); + + //Excluded widget + w.name = Util.Uniquify(WidgetNameStart); + w.count = -55; + a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w.ToString()); + Util.ValidateDataReturnResponseOk(a); + ExcludedWidgetId = a.ObjectResponse["data"]["id"].Value(); + + + //CREATE LISTVIEW + dynamic dListView = new JArray(); + + //name starts with filter to constrict to widgets that this test block created only + dListView.Add(Util.BuildSimpleFilterDataListViewColumn("widgetname", Util.OpStartsWith, WidgetNameStart)); + + //inclusive test filter + + // dynamic FilterItem = new JObject(); + // FilterItem.fld = "widgetcount"; + // FilterItem.op = Util.OpGreaterThan; + // FilterItem.value = 54; + dListView.Add(Util.BuildSimpleFilterDataListViewColumn("widgetcount", Util.OpGreaterThan, 54)); + //FETCH DATALIST + a = await Util.PostAsync($"data-list", await Util.GetTokenAsync("superuser", "l3tm3in"), Util.BuildDataListRequestEx(dListView)); + Util.ValidateDataReturnResponseOk(a); + Util.ValidateHTTPStatusCode(a, 200); + + //assert contains at least this test record + ((JArray)a.ObjectResponse["data"]).Count.Should().BeGreaterThan(0); + var v = ((JArray)a.ObjectResponse["data"]); + List IDInResultList = new List(); + int InclusiveMatchCount = 0; + int ExclusiveMatchCount = 0; + foreach (JArray ja in v) + { + JObject o = ja[0] as JObject; + if (IncludedWidgetId == o["i"].Value()) + InclusiveMatchCount++; + if (ExcludedWidgetId == o["i"].Value()) + ExclusiveMatchCount++; + } + + InclusiveMatchCount.Should().BeGreaterOrEqualTo(1); + ExclusiveMatchCount.Should().Be(0); + + //DELETE WIDGETS + a = await Util.DeleteAsync("widget/" + IncludedWidgetId.ToString(), await Util.GetTokenAsync("BizAdminFull")); + Util.ValidateHTTPStatusCode(a, 204); + + a = await Util.DeleteAsync("widget/" + ExcludedWidgetId.ToString(), await Util.GetTokenAsync("BizAdminFull")); + Util.ValidateHTTPStatusCode(a, 204); + + } + + /// + /// + /// + [Fact] + public async Task IntegerOpGreaterThanOrEqualToFilterWorks() + { + + var WidgetNameStart = "IntegerOpGreaterThanOrEqualToFilterWorks"; + + long IncludedWidgetId = 0; + long ExcludedWidgetId = 0; + + //CREATE TEST WIDGETS + + //included widget + dynamic w = new JObject(); + w.name = Util.Uniquify(WidgetNameStart); + w.customFields = Util.WidgetRequiredCustomFieldsJsonString(); + w.notes = "blah"; + w.active = true; + w.usertype = 1; + w.count = 555; + + ApiResponse a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w.ToString()); + Util.ValidateDataReturnResponseOk(a); + IncludedWidgetId = a.ObjectResponse["data"]["id"].Value(); + + //Excluded widget + w.name = Util.Uniquify(WidgetNameStart); + w.count = 554; + a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w.ToString()); + Util.ValidateDataReturnResponseOk(a); + ExcludedWidgetId = a.ObjectResponse["data"]["id"].Value(); + + + //CREATE LISTVIEW + dynamic dListView = new JArray(); + + //name starts with filter to constrict to widgets that this test block created only + dListView.Add(Util.BuildSimpleFilterDataListViewColumn("widgetname", Util.OpStartsWith, WidgetNameStart)); + + //inclusive test filter + + // dynamic FilterItem = new JObject(); + // FilterItem.fld = "widgetcount"; + // FilterItem.op = Util.OpGreaterThanOrEqualTo; + // FilterItem.value = 555; + dListView.Add(Util.BuildSimpleFilterDataListViewColumn("widgetcount", Util.OpGreaterThanOrEqualTo, 555)); + //FETCH DATALIST + a = await Util.PostAsync($"data-list", await Util.GetTokenAsync("superuser", "l3tm3in"), Util.BuildDataListRequestEx(dListView)); + Util.ValidateDataReturnResponseOk(a); + Util.ValidateHTTPStatusCode(a, 200); + + //assert contains at least this test record + ((JArray)a.ObjectResponse["data"]).Count.Should().BeGreaterThan(0); + var v = ((JArray)a.ObjectResponse["data"]); + List IDInResultList = new List(); + int InclusiveMatchCount = 0; + int ExclusiveMatchCount = 0; + foreach (JArray ja in v) + { + JObject o = ja[0] as JObject; + if (IncludedWidgetId == o["i"].Value()) + InclusiveMatchCount++; + if (ExcludedWidgetId == o["i"].Value()) + ExclusiveMatchCount++; + } + + InclusiveMatchCount.Should().BeGreaterOrEqualTo(1); + ExclusiveMatchCount.Should().Be(0); + + //DELETE WIDGETS + a = await Util.DeleteAsync("widget/" + IncludedWidgetId.ToString(), await Util.GetTokenAsync("BizAdminFull")); + Util.ValidateHTTPStatusCode(a, 204); + + a = await Util.DeleteAsync("widget/" + ExcludedWidgetId.ToString(), await Util.GetTokenAsync("BizAdminFull")); + Util.ValidateHTTPStatusCode(a, 204); + + } + + + + /// + /// + /// + [Fact] + public async Task IntegerOpLessThanFilterWorks() + { + + var WidgetNameStart = "IntegerOpLessThanFilterWorks"; + + long IncludedWidgetId = 0; + long ExcludedWidgetId = 0; + + //CREATE TEST WIDGETS + + //included widget + dynamic w = new JObject(); + w.name = Util.Uniquify(WidgetNameStart); + w.customFields = Util.WidgetRequiredCustomFieldsJsonString(); + w.notes = "blah"; + w.active = true; + w.usertype = 1; + w.count = -5555; + + ApiResponse a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w.ToString()); + Util.ValidateDataReturnResponseOk(a); + IncludedWidgetId = a.ObjectResponse["data"]["id"].Value(); + + //Excluded widget + w.name = Util.Uniquify(WidgetNameStart); + w.count = 5555; + a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w.ToString()); + Util.ValidateDataReturnResponseOk(a); + ExcludedWidgetId = a.ObjectResponse["data"]["id"].Value(); + + + //CREATE LISTVIEW + dynamic dListView = new JArray(); + + //name starts with filter to constrict to widgets that this test block created only + dListView.Add(Util.BuildSimpleFilterDataListViewColumn("widgetname", Util.OpStartsWith, WidgetNameStart)); + + //inclusive test filter + + // dynamic FilterItem = new JObject(); + // FilterItem.fld = "widgetcount"; + // FilterItem.op = Util.OpLessThan; + // FilterItem.value = 5555; + dListView.Add(Util.BuildSimpleFilterDataListViewColumn("widgetcount", Util.OpLessThan, 5555)); + //FETCH DATALIST + a = await Util.PostAsync($"data-list", await Util.GetTokenAsync("superuser", "l3tm3in"), Util.BuildDataListRequestEx(dListView)); + Util.ValidateDataReturnResponseOk(a); + Util.ValidateHTTPStatusCode(a, 200); + + //assert contains at least this test record + ((JArray)a.ObjectResponse["data"]).Count.Should().BeGreaterThan(0); + var v = ((JArray)a.ObjectResponse["data"]); + List IDInResultList = new List(); + int InclusiveMatchCount = 0; + int ExclusiveMatchCount = 0; + foreach (JArray ja in v) + { + JObject o = ja[0] as JObject; + if (IncludedWidgetId == o["i"].Value()) + InclusiveMatchCount++; + if (ExcludedWidgetId == o["i"].Value()) + ExclusiveMatchCount++; + } + + InclusiveMatchCount.Should().BeGreaterOrEqualTo(1); + ExclusiveMatchCount.Should().Be(0); + + //DELETE WIDGETS + a = await Util.DeleteAsync("widget/" + IncludedWidgetId.ToString(), await Util.GetTokenAsync("BizAdminFull")); + Util.ValidateHTTPStatusCode(a, 204); + + a = await Util.DeleteAsync("widget/" + ExcludedWidgetId.ToString(), await Util.GetTokenAsync("BizAdminFull")); + Util.ValidateHTTPStatusCode(a, 204); + + } + + + /// + /// + /// + [Fact] + public async Task IntegerOpLessThanOrEqualToFilterWorks() + { + + var WidgetNameStart = "IntegerOpLessThanOrEqualToFilterWorks"; + + long IncludedWidgetId = 0; + long ExcludedWidgetId = 0; + + //CREATE TEST WIDGETS + + //included widget + dynamic w = new JObject(); + w.name = Util.Uniquify(WidgetNameStart); + w.customFields = Util.WidgetRequiredCustomFieldsJsonString(); + w.notes = "blah"; + w.active = true; + w.usertype = 1; + w.count = -444; + + ApiResponse a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w.ToString()); + Util.ValidateDataReturnResponseOk(a); + IncludedWidgetId = a.ObjectResponse["data"]["id"].Value(); + + //Excluded widget + w.name = Util.Uniquify(WidgetNameStart); + w.count = -443; + a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w.ToString()); + Util.ValidateDataReturnResponseOk(a); + ExcludedWidgetId = a.ObjectResponse["data"]["id"].Value(); + + + //CREATE LISTVIEW + dynamic dListView = new JArray(); + + //name starts with filter to constrict to widgets that this test block created only + dListView.Add(Util.BuildSimpleFilterDataListViewColumn("widgetname", Util.OpStartsWith, WidgetNameStart)); + + //inclusive test filter + + // dynamic FilterItem = new JObject(); + // FilterItem.fld = "widgetcount"; + // FilterItem.op = Util.OpLessThanOrEqualTo; + // FilterItem.value = -444; + dListView.Add(Util.BuildSimpleFilterDataListViewColumn("widgetcount", Util.OpLessThanOrEqualTo, -444)); + //FETCH DATALIST + a = await Util.PostAsync($"data-list", await Util.GetTokenAsync("superuser", "l3tm3in"), Util.BuildDataListRequestEx(dListView)); + Util.ValidateDataReturnResponseOk(a); + Util.ValidateHTTPStatusCode(a, 200); + + //assert contains at least this test record + ((JArray)a.ObjectResponse["data"]).Count.Should().BeGreaterThan(0); + var v = ((JArray)a.ObjectResponse["data"]); + List IDInResultList = new List(); + int InclusiveMatchCount = 0; + int ExclusiveMatchCount = 0; + foreach (JArray ja in v) + { + JObject o = ja[0] as JObject; + if (IncludedWidgetId == o["i"].Value()) + InclusiveMatchCount++; + if (ExcludedWidgetId == o["i"].Value()) + ExclusiveMatchCount++; + } + + InclusiveMatchCount.Should().BeGreaterOrEqualTo(1); + ExclusiveMatchCount.Should().Be(0); + + //DELETE WIDGETS + a = await Util.DeleteAsync("widget/" + IncludedWidgetId.ToString(), await Util.GetTokenAsync("BizAdminFull")); + Util.ValidateHTTPStatusCode(a, 204); + + a = await Util.DeleteAsync("widget/" + ExcludedWidgetId.ToString(), await Util.GetTokenAsync("BizAdminFull")); + Util.ValidateHTTPStatusCode(a, 204); + } + + + + /// + /// + /// + [Fact] + public async Task IntegerNotEqualToFilterWorks() + { + + var WidgetNameStart = "IntegerNotEqualToFilterWorks"; + + long IncludedWidgetId = 0; + long ExcludedWidgetId = 0; + + //CREATE TEST WIDGETS + + //included widget + dynamic w = new JObject(); + w.name = Util.Uniquify(WidgetNameStart); + w.customFields = Util.WidgetRequiredCustomFieldsJsonString(); + w.notes = "blah"; + w.active = true; + w.usertype = 1; + w.count = 222; + + ApiResponse a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w.ToString()); + Util.ValidateDataReturnResponseOk(a); + IncludedWidgetId = a.ObjectResponse["data"]["id"].Value(); + + //Excluded widget + w.name = Util.Uniquify(WidgetNameStart); + w.count = 223; + a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w.ToString()); + Util.ValidateDataReturnResponseOk(a); + ExcludedWidgetId = a.ObjectResponse["data"]["id"].Value(); + + + //CREATE LISTVIEW + dynamic dListView = new JArray(); + + //name starts with filter to constrict to widgets that this test block created only + dListView.Add(Util.BuildSimpleFilterDataListViewColumn("widgetname", Util.OpStartsWith, WidgetNameStart)); + + //inclusive test filter + + // dynamic FilterItem = new JObject(); + // FilterItem.fld = "widgetcount"; + // FilterItem.op = Util.OpNotEqual; + // FilterItem.value = 223; + dListView.Add(Util.BuildSimpleFilterDataListViewColumn("widgetcount", Util.OpNotEqual, 223)); + //FETCH DATALIST + a = await Util.PostAsync($"data-list", await Util.GetTokenAsync("superuser", "l3tm3in"), Util.BuildDataListRequestEx(dListView)); + Util.ValidateDataReturnResponseOk(a); + Util.ValidateHTTPStatusCode(a, 200); + + //assert contains at least this test record + ((JArray)a.ObjectResponse["data"]).Count.Should().BeGreaterThan(0); + var v = ((JArray)a.ObjectResponse["data"]); + List IDInResultList = new List(); + int InclusiveMatchCount = 0; + int ExclusiveMatchCount = 0; + foreach (JArray ja in v) + { + JObject o = ja[0] as JObject; + if (IncludedWidgetId == o["i"].Value()) + InclusiveMatchCount++; + if (ExcludedWidgetId == o["i"].Value()) + ExclusiveMatchCount++; + } + + InclusiveMatchCount.Should().BeGreaterOrEqualTo(1); + ExclusiveMatchCount.Should().Be(0); + + //DELETE WIDGETS + a = await Util.DeleteAsync("widget/" + IncludedWidgetId.ToString(), await Util.GetTokenAsync("BizAdminFull")); + Util.ValidateHTTPStatusCode(a, 204); + + a = await Util.DeleteAsync("widget/" + ExcludedWidgetId.ToString(), await Util.GetTokenAsync("BizAdminFull")); + Util.ValidateHTTPStatusCode(a, 204); + + } + #endregion integer tests + + + /////////////////////////////////////////////////////////////////////////////// + //BOOL + // + + #region BOOLEAN TESTS + + /// + /// + /// + [Fact] + public async Task BoolOpEqualityFilterWorks() + { + //OPS: equal to, not equal to + //values: true, false + + var WidgetNameStart = "BoolDataFilterTest"; + + List ActiveWidgetIdList = new List(); + List NotActiveWidgetIdList = new List(); + + //CREATE 4 TEST WIDGETS + //two active and two non active + + //first active widget + dynamic w = new JObject(); + w.name = Util.Uniquify(WidgetNameStart); + w.customFields = Util.WidgetRequiredCustomFieldsJsonString(); + w.notes = "blah"; + w.active = true; + w.usertype = 1; + + ApiResponse a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w.ToString()); + Util.ValidateDataReturnResponseOk(a); + ActiveWidgetIdList.Add(a.ObjectResponse["data"]["id"].Value()); + + //second active widget + w.name = Util.Uniquify(WidgetNameStart); + + a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w.ToString()); + Util.ValidateDataReturnResponseOk(a); + ActiveWidgetIdList.Add(a.ObjectResponse["data"]["id"].Value()); + + + //first NON active widget + w.name = Util.Uniquify(WidgetNameStart); + w.active = false; + + a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w.ToString()); + Util.ValidateDataReturnResponseOk(a); + NotActiveWidgetIdList.Add(a.ObjectResponse["data"]["id"].Value()); + + //second NON active widget + w.name = Util.Uniquify(WidgetNameStart); + w.active = false; + + a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w.ToString()); + Util.ValidateDataReturnResponseOk(a); + NotActiveWidgetIdList.Add(a.ObjectResponse["data"]["id"].Value()); + + + //CREATE LISTVIEW + dynamic dListView = new JArray(); + + //name starts with filter to constrict to widgets that this test block created only + dListView.Add(Util.BuildSimpleFilterDataListViewColumn("widgetname", Util.OpStartsWith, WidgetNameStart)); + + //FILTER + // dynamic DataFilterActive = new JObject(); + // DataFilterActive.fld = "widgetactive"; + // DataFilterActive.op = Util.OpEquality; + // DataFilterActive.value = true; + dListView.Add(Util.BuildSimpleFilterDataListViewColumn("widgetactive", Util.OpEquality, true)); + + + //FETCH DATALIST + a = await Util.PostAsync($"data-list", await Util.GetTokenAsync("superuser", "l3tm3in"), Util.BuildDataListRequestEx(dListView)); + Util.ValidateDataReturnResponseOk(a); + Util.ValidateHTTPStatusCode(a, 200); + + //assert contains at least two records + ((JArray)a.ObjectResponse["data"]).Count.Should().BeGreaterThan(1); + var v = ((JArray)a.ObjectResponse["data"]); + // List IDInResultList = new List(); + int nActiveMatches = 0; + int nInactiveMatches = 0; + + foreach (JArray ja in v) + { + JObject o = ja[0] as JObject; + + + if (ActiveWidgetIdList.Contains(o["i"].Value())) + nActiveMatches++; + //if (NotActiveWidgetIdList.Contains(o["i"].Value())) + if (NotActiveWidgetIdList.Contains(o["i"].Value())) + nInactiveMatches++; + } + + nActiveMatches.Should().Be(ActiveWidgetIdList.Count); + nInactiveMatches.Should().Be(0); + + //DELETE WIDGETS + foreach (long l in ActiveWidgetIdList) + { + a = await Util.DeleteAsync("widget/" + l.ToString(), await Util.GetTokenAsync("BizAdminFull")); + Util.ValidateHTTPStatusCode(a, 204); + } + + foreach (long l in NotActiveWidgetIdList) + { + a = await Util.DeleteAsync("widget/" + l.ToString(), await Util.GetTokenAsync("BizAdminFull")); + Util.ValidateHTTPStatusCode(a, 204); + } + } + + + + /// + /// + /// + [Fact] + public async Task BoolOpNotEqualFilterWorks() + { + + //OPS: equal to, not equal to + //values: true, false + + var WidgetNameStart = "BoolDataFilterTest"; + + List ActiveWidgetIdList = new List(); + List NotActiveWidgetIdList = new List(); + + //CREATE 4 TEST WIDGETS + //two active and two non active + + //first active widget + dynamic w = new JObject(); + w.name = Util.Uniquify(WidgetNameStart); + w.customFields = Util.WidgetRequiredCustomFieldsJsonString(); + w.notes = "blah"; + w.active = true; + w.usertype = 1; + + ApiResponse a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w.ToString()); + Util.ValidateDataReturnResponseOk(a); + ActiveWidgetIdList.Add(a.ObjectResponse["data"]["id"].Value()); + + //second active widget + w.name = Util.Uniquify(WidgetNameStart); + + a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w.ToString()); + Util.ValidateDataReturnResponseOk(a); + ActiveWidgetIdList.Add(a.ObjectResponse["data"]["id"].Value()); + + + //first NON active widget + w.name = Util.Uniquify(WidgetNameStart); + w.active = false; + + a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w.ToString()); + Util.ValidateDataReturnResponseOk(a); + NotActiveWidgetIdList.Add(a.ObjectResponse["data"]["id"].Value()); + + //second NON active widget + w.name = Util.Uniquify(WidgetNameStart); + w.active = false; + + a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w.ToString()); + Util.ValidateDataReturnResponseOk(a); + NotActiveWidgetIdList.Add(a.ObjectResponse["data"]["id"].Value()); + + + //CREATE LISTVIEW + dynamic dListView = new JArray(); + + //name starts with filter to constrict to widgets that this test block created only + dListView.Add(Util.BuildSimpleFilterDataListViewColumn("widgetname", Util.OpStartsWith, WidgetNameStart)); + + //FILTER + // dynamic DataFilterActive = new JObject(); + // DataFilterActive.fld = "widgetactive"; + // DataFilterActive.op = Util.OpNotEqual; + // DataFilterActive.value = true; + dListView.Add(Util.BuildSimpleFilterDataListViewColumn("widgetactive", Util.OpNotEqual, true)); + + + + //FETCH DATALIST + a = await Util.PostAsync($"data-list", await Util.GetTokenAsync("superuser", "l3tm3in"), Util.BuildDataListRequestEx(dListView)); + Util.ValidateDataReturnResponseOk(a); + Util.ValidateHTTPStatusCode(a, 200); + + //assert contains at least two records + ((JArray)a.ObjectResponse["data"]).Count.Should().BeGreaterThan(1); + var v = ((JArray)a.ObjectResponse["data"]); + List IDInResultList = new List(); + int nActiveMatches = 0; + int nInactiveMatches = 0; + + foreach (JArray ja in v) + { + JObject o = ja[0] as JObject; + + if (ActiveWidgetIdList.Contains(o["i"].Value())) + nActiveMatches++; + if (NotActiveWidgetIdList.Contains(o["i"].Value())) + nInactiveMatches++; + } + + nInactiveMatches.Should().Be(NotActiveWidgetIdList.Count); + nActiveMatches.Should().Be(0); + + //DELETE WIDGETS + foreach (long l in ActiveWidgetIdList) + { + a = await Util.DeleteAsync("widget/" + l.ToString(), await Util.GetTokenAsync("BizAdminFull")); + Util.ValidateHTTPStatusCode(a, 204); + } + + foreach (long l in NotActiveWidgetIdList) + { + a = await Util.DeleteAsync("widget/" + l.ToString(), await Util.GetTokenAsync("BizAdminFull")); + Util.ValidateHTTPStatusCode(a, 204); + } + + + } + + #endregion boolean tests + + + /////////////////////////////////////////////////////////////////////////////// + //DECIMAL + // + #region DECIMAL TESTS + + /// + /// + /// + [Fact] + public async Task DecimalOpEqualityFilterWorks() + { + + var WidgetNameStart = "DecimalOpEqualityFilterWorks"; + + long IncludedWidgetId = 0; + long ExcludedWidgetId = 0; + + //CREATE TEST WIDGETS + + + //included widget + dynamic w = new JObject(); + w.name = Util.Uniquify(WidgetNameStart); + w.customFields = Util.WidgetRequiredCustomFieldsJsonString(); + w.notes = "blah"; + w.active = true; + w.usertype = 1; + w.dollarAmount = 5.55; + + ApiResponse a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w.ToString()); + Util.ValidateDataReturnResponseOk(a); + IncludedWidgetId = a.ObjectResponse["data"]["id"].Value(); + + //Excluded widget + w.name = Util.Uniquify(WidgetNameStart); + w.dollarAmount = 3.33; + a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w.ToString()); + Util.ValidateDataReturnResponseOk(a); + ExcludedWidgetId = a.ObjectResponse["data"]["id"].Value(); + + //CREATE LISTVIEW + dynamic dListView = new JArray(); + + //name starts with filter to constrict to widgets that this test block created only + dListView.Add(Util.BuildSimpleFilterDataListViewColumn("widgetname", Util.OpStartsWith, WidgetNameStart)); + + //inclusive test filter + + // dynamic FilterItem = new JObject(); + // FilterItem.fld = "widgetdollaramount"; + // FilterItem.op = Util.OpEquality; + // FilterItem.value = 5.55; + dListView.Add(Util.BuildSimpleFilterDataListViewColumn("widgetdollaramount", Util.OpEquality, 5.55)); + //FETCH DATALIST + a = await Util.PostAsync($"data-list", await Util.GetTokenAsync("superuser", "l3tm3in"), Util.BuildDataListRequestEx(dListView)); + Util.ValidateDataReturnResponseOk(a); + Util.ValidateHTTPStatusCode(a, 200); + + //assert contains at least this test record + ((JArray)a.ObjectResponse["data"]).Count.Should().BeGreaterThan(0); + var v = ((JArray)a.ObjectResponse["data"]); + List IDInResultList = new List(); + int InclusiveMatchCount = 0; + int ExclusiveMatchCount = 0; + foreach (JArray ja in v) + { + JObject o = ja[0] as JObject; + if (IncludedWidgetId == o["i"].Value()) + InclusiveMatchCount++; + if (ExcludedWidgetId == o["i"].Value()) + ExclusiveMatchCount++; + } + + InclusiveMatchCount.Should().BeGreaterOrEqualTo(1); + ExclusiveMatchCount.Should().Be(0); + + //DELETE WIDGETS + a = await Util.DeleteAsync("widget/" + IncludedWidgetId.ToString(), await Util.GetTokenAsync("BizAdminFull")); + Util.ValidateHTTPStatusCode(a, 204); + + a = await Util.DeleteAsync("widget/" + ExcludedWidgetId.ToString(), await Util.GetTokenAsync("BizAdminFull")); + Util.ValidateHTTPStatusCode(a, 204); + + } + + /// + /// + /// + [Fact] + public async Task DecimalOpGreaterThanFilterWorks() + { + + var WidgetNameStart = "DecimalOpGreaterThanFilterWorks"; + + long IncludedWidgetId = 0; + long ExcludedWidgetId = 0; + + //CREATE TEST WIDGETS + + //included widget + dynamic w = new JObject(); + w.name = Util.Uniquify(WidgetNameStart); + w.customFields = Util.WidgetRequiredCustomFieldsJsonString(); + w.notes = "blah"; + w.active = true; + w.usertype = 1; + w.dollarAmount = 55.55; + + ApiResponse a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w.ToString()); + Util.ValidateDataReturnResponseOk(a); + IncludedWidgetId = a.ObjectResponse["data"]["id"].Value(); + + //Excluded widget + w.name = Util.Uniquify(WidgetNameStart); + w.dollarAmount = -55.55; + a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w.ToString()); + Util.ValidateDataReturnResponseOk(a); + ExcludedWidgetId = a.ObjectResponse["data"]["id"].Value(); + + + //CREATE LISTVIEW + dynamic dListView = new JArray(); + + //name starts with filter to constrict to widgets that this test block created only + dListView.Add(Util.BuildSimpleFilterDataListViewColumn("widgetname", Util.OpStartsWith, WidgetNameStart)); + + //inclusive test filter + + // dynamic FilterItem = new JObject(); + // FilterItem.fld = "widgetdollaramount"; + // FilterItem.op = Util.OpGreaterThan; + // FilterItem.value = 54.44; + dListView.Add(Util.BuildSimpleFilterDataListViewColumn("widgetdollaramount", Util.OpGreaterThan, 54.44)); + + //FETCH DATALIST + a = await Util.PostAsync($"data-list", await Util.GetTokenAsync("superuser", "l3tm3in"), Util.BuildDataListRequestEx(dListView)); + Util.ValidateDataReturnResponseOk(a); + Util.ValidateHTTPStatusCode(a, 200); + + //assert contains at least this test record + ((JArray)a.ObjectResponse["data"]).Count.Should().BeGreaterThan(0); + var v = ((JArray)a.ObjectResponse["data"]); + List IDInResultList = new List(); + int InclusiveMatchCount = 0; + int ExclusiveMatchCount = 0; + foreach (JArray ja in v) + { + JObject o = ja[0] as JObject; + if (IncludedWidgetId == o["i"].Value()) + InclusiveMatchCount++; + if (ExcludedWidgetId == o["i"].Value()) + ExclusiveMatchCount++; + } + + InclusiveMatchCount.Should().BeGreaterOrEqualTo(1); + ExclusiveMatchCount.Should().Be(0); + + //DELETE WIDGETS + a = await Util.DeleteAsync("widget/" + IncludedWidgetId.ToString(), await Util.GetTokenAsync("BizAdminFull")); + Util.ValidateHTTPStatusCode(a, 204); + + a = await Util.DeleteAsync("widget/" + ExcludedWidgetId.ToString(), await Util.GetTokenAsync("BizAdminFull")); + Util.ValidateHTTPStatusCode(a, 204); + + } + + /// + /// + /// + [Fact] + public async Task DecimalOpGreaterThanOrEqualToFilterWorks() + { + + var WidgetNameStart = "DecimalOpGreaterThanOrEqualToFilterWorks"; + + long IncludedWidgetId = 0; + long ExcludedWidgetId = 0; + + //CREATE TEST WIDGETS + + //included widget + dynamic w = new JObject(); + w.name = Util.Uniquify(WidgetNameStart); + w.customFields = Util.WidgetRequiredCustomFieldsJsonString(); + w.notes = "blah"; + w.active = true; + w.usertype = 1; + w.dollarAmount = 555.55; + + ApiResponse a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w.ToString()); + Util.ValidateDataReturnResponseOk(a); + IncludedWidgetId = a.ObjectResponse["data"]["id"].Value(); + + //Excluded widget + w.name = Util.Uniquify(WidgetNameStart); + w.dollarAmount = 554.54; + a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w.ToString()); + Util.ValidateDataReturnResponseOk(a); + ExcludedWidgetId = a.ObjectResponse["data"]["id"].Value(); + + + //CREATE LISTVIEW + dynamic dListView = new JArray(); + + //name starts with filter to constrict to widgets that this test block created only + dListView.Add(Util.BuildSimpleFilterDataListViewColumn("widgetname", Util.OpStartsWith, WidgetNameStart)); + + //inclusive test filter + + // dynamic FilterItem = new JObject(); + // FilterItem.fld = "widgetdollaramount"; + // FilterItem.op = Util.OpGreaterThanOrEqualTo; + // FilterItem.value = 555.55; + dListView.Add(Util.BuildSimpleFilterDataListViewColumn("widgetdollaramount", Util.OpGreaterThanOrEqualTo, 555.55)); + + //FETCH DATALIST + a = await Util.PostAsync($"data-list", await Util.GetTokenAsync("superuser", "l3tm3in"), Util.BuildDataListRequestEx(dListView)); + Util.ValidateDataReturnResponseOk(a); + Util.ValidateHTTPStatusCode(a, 200); + + //assert contains at least this test record + ((JArray)a.ObjectResponse["data"]).Count.Should().BeGreaterThan(0); + var v = ((JArray)a.ObjectResponse["data"]); + List IDInResultList = new List(); + int InclusiveMatchCount = 0; + int ExclusiveMatchCount = 0; + foreach (JArray ja in v) + { + JObject o = ja[0] as JObject; + if (IncludedWidgetId == o["i"].Value()) + InclusiveMatchCount++; + if (ExcludedWidgetId == o["i"].Value()) + ExclusiveMatchCount++; + } + + InclusiveMatchCount.Should().BeGreaterOrEqualTo(1); + ExclusiveMatchCount.Should().Be(0); + + //DELETE WIDGETS + a = await Util.DeleteAsync("widget/" + IncludedWidgetId.ToString(), await Util.GetTokenAsync("BizAdminFull")); + Util.ValidateHTTPStatusCode(a, 204); + + a = await Util.DeleteAsync("widget/" + ExcludedWidgetId.ToString(), await Util.GetTokenAsync("BizAdminFull")); + Util.ValidateHTTPStatusCode(a, 204); + + } + + + + /// + /// + /// + [Fact] + public async Task DecimalOpLessThanFilterWorks() + { + + var WidgetNameStart = "DecimalOpLessThanFilterWorks"; + + long IncludedWidgetId = 0; + long ExcludedWidgetId = 0; + + //CREATE TEST WIDGETS + + //included widget + dynamic w = new JObject(); + w.name = Util.Uniquify(WidgetNameStart); + w.customFields = Util.WidgetRequiredCustomFieldsJsonString(); + w.notes = "blah"; + w.active = true; + w.usertype = 1; + w.dollarAmount = -5555.55; + + ApiResponse a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w.ToString()); + Util.ValidateDataReturnResponseOk(a); + IncludedWidgetId = a.ObjectResponse["data"]["id"].Value(); + + //Excluded widget + w.name = Util.Uniquify(WidgetNameStart); + w.dollarAmount = 5555.55; + a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w.ToString()); + Util.ValidateDataReturnResponseOk(a); + ExcludedWidgetId = a.ObjectResponse["data"]["id"].Value(); + + + //CREATE LISTVIEW + dynamic dListView = new JArray(); + + //name starts with filter to constrict to widgets that this test block created only + dListView.Add(Util.BuildSimpleFilterDataListViewColumn("widgetname", Util.OpStartsWith, WidgetNameStart)); + + //inclusive test filter + + // dynamic FilterItem = new JObject(); + // FilterItem.fld = "widgetdollaramount"; + // FilterItem.op = Util.OpLessThan; + // FilterItem.value = 5555.55; + dListView.Add(Util.BuildSimpleFilterDataListViewColumn("widgetdollaramount", Util.OpLessThan, 5555.55)); + + //FETCH DATALIST + a = await Util.PostAsync($"data-list", await Util.GetTokenAsync("superuser", "l3tm3in"), Util.BuildDataListRequestEx(dListView)); + Util.ValidateDataReturnResponseOk(a); + Util.ValidateHTTPStatusCode(a, 200); + + //assert contains at least this test record + ((JArray)a.ObjectResponse["data"]).Count.Should().BeGreaterThan(0); + var v = ((JArray)a.ObjectResponse["data"]); + List IDInResultList = new List(); + int InclusiveMatchCount = 0; + int ExclusiveMatchCount = 0; + foreach (JArray ja in v) + { + JObject o = ja[0] as JObject; + if (IncludedWidgetId == o["i"].Value()) + InclusiveMatchCount++; + if (ExcludedWidgetId == o["i"].Value()) + ExclusiveMatchCount++; + } + + InclusiveMatchCount.Should().BeGreaterOrEqualTo(1); + ExclusiveMatchCount.Should().Be(0); + + //DELETE WIDGETS + a = await Util.DeleteAsync("widget/" + IncludedWidgetId.ToString(), await Util.GetTokenAsync("BizAdminFull")); + Util.ValidateHTTPStatusCode(a, 204); + + a = await Util.DeleteAsync("widget/" + ExcludedWidgetId.ToString(), await Util.GetTokenAsync("BizAdminFull")); + Util.ValidateHTTPStatusCode(a, 204); + + } + + + /// + /// + /// + [Fact] + public async Task DecimalOpLessThanOrEqualToFilterWorks() + { + + var WidgetNameStart = "DecimalOpLessThanOrEqualToFilterWorks"; + + long IncludedWidgetId = 0; + long ExcludedWidgetId = 0; + + //CREATE TEST WIDGETS + + //included widget + dynamic w = new JObject(); + w.name = Util.Uniquify(WidgetNameStart); + w.customFields = Util.WidgetRequiredCustomFieldsJsonString(); + w.notes = "blah"; + w.active = true; + w.usertype = 1; + w.dollarAmount = -444.44; + + ApiResponse a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w.ToString()); + Util.ValidateDataReturnResponseOk(a); + IncludedWidgetId = a.ObjectResponse["data"]["id"].Value(); + + //Excluded widget + w.name = Util.Uniquify(WidgetNameStart); + w.dollarAmount = -443.43; + a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w.ToString()); + Util.ValidateDataReturnResponseOk(a); + ExcludedWidgetId = a.ObjectResponse["data"]["id"].Value(); + + + //CREATE LISTVIEW + dynamic dListView = new JArray(); + + //name starts with filter to constrict to widgets that this test block created only + dListView.Add(Util.BuildSimpleFilterDataListViewColumn("widgetname", Util.OpStartsWith, WidgetNameStart)); + + //inclusive test filter + + // dynamic FilterItem = new JObject(); + // FilterItem.fld = "widgetdollaramount"; + // FilterItem.op = Util.OpLessThanOrEqualTo; + // FilterItem.value = -444.44; + dListView.Add(Util.BuildSimpleFilterDataListViewColumn("widgetdollaramount", Util.OpLessThanOrEqualTo, -444.44)); + + //FETCH DATALIST + a = await Util.PostAsync($"data-list", await Util.GetTokenAsync("superuser", "l3tm3in"), Util.BuildDataListRequestEx(dListView)); + Util.ValidateDataReturnResponseOk(a); + Util.ValidateHTTPStatusCode(a, 200); + + //assert contains at least this test record + ((JArray)a.ObjectResponse["data"]).Count.Should().BeGreaterThan(0); + var v = ((JArray)a.ObjectResponse["data"]); + List IDInResultList = new List(); + int InclusiveMatchCount = 0; + int ExclusiveMatchCount = 0; + foreach (JArray ja in v) + { + JObject o = ja[0] as JObject; + if (IncludedWidgetId == o["i"].Value()) + InclusiveMatchCount++; + if (ExcludedWidgetId == o["i"].Value()) + ExclusiveMatchCount++; + } + + InclusiveMatchCount.Should().BeGreaterOrEqualTo(1); + ExclusiveMatchCount.Should().Be(0); + + //DELETE WIDGETS + a = await Util.DeleteAsync("widget/" + IncludedWidgetId.ToString(), await Util.GetTokenAsync("BizAdminFull")); + Util.ValidateHTTPStatusCode(a, 204); + + a = await Util.DeleteAsync("widget/" + ExcludedWidgetId.ToString(), await Util.GetTokenAsync("BizAdminFull")); + Util.ValidateHTTPStatusCode(a, 204); + + } + + + + /// + /// + /// + [Fact] + public async Task DecimalNotEqualToFilterWorks() + { + + var WidgetNameStart = "DecimalNotEqualToFilterWorks"; + + long IncludedWidgetId = 0; + long ExcludedWidgetId = 0; + + //CREATE TEST WIDGETS + + //included widget + dynamic w = new JObject(); + w.name = Util.Uniquify(WidgetNameStart); + w.customFields = Util.WidgetRequiredCustomFieldsJsonString(); + w.notes = "blah"; + w.active = true; + w.usertype = 1; + w.dollarAmount = 222.22; + + ApiResponse a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w.ToString()); + Util.ValidateDataReturnResponseOk(a); + IncludedWidgetId = a.ObjectResponse["data"]["id"].Value(); + + //Excluded widget + w.name = Util.Uniquify(WidgetNameStart); + w.dollarAmount = 223.23; + a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w.ToString()); + Util.ValidateDataReturnResponseOk(a); + ExcludedWidgetId = a.ObjectResponse["data"]["id"].Value(); + + + //CREATE LISTVIEW + dynamic dListView = new JArray(); + + //name starts with filter to constrict to widgets that this test block created only + dListView.Add(Util.BuildSimpleFilterDataListViewColumn("widgetname", Util.OpStartsWith, WidgetNameStart)); + + //inclusive test filter + + // dynamic FilterItem = new JObject(); + // FilterItem.fld = "widgetdollaramount"; + // FilterItem.op = Util.OpNotEqual; + // FilterItem.value = 223.23; + dListView.Add(Util.BuildSimpleFilterDataListViewColumn("widgetdollaramount", Util.OpNotEqual, 223.23)); + + //FETCH DATALIST + a = await Util.PostAsync($"data-list", await Util.GetTokenAsync("superuser", "l3tm3in"), Util.BuildDataListRequestEx(dListView)); + Util.ValidateDataReturnResponseOk(a); + Util.ValidateHTTPStatusCode(a, 200); + + //assert contains at least this test record + ((JArray)a.ObjectResponse["data"]).Count.Should().BeGreaterThan(0); + var v = ((JArray)a.ObjectResponse["data"]); + List IDInResultList = new List(); + int InclusiveMatchCount = 0; + int ExclusiveMatchCount = 0; + foreach (JArray ja in v) + { + JObject o = ja[0] as JObject; + if (IncludedWidgetId == o["i"].Value()) + InclusiveMatchCount++; + if (ExcludedWidgetId == o["i"].Value()) + ExclusiveMatchCount++; + } + + InclusiveMatchCount.Should().BeGreaterOrEqualTo(1); + ExclusiveMatchCount.Should().Be(0); + + //DELETE WIDGETS + a = await Util.DeleteAsync("widget/" + IncludedWidgetId.ToString(), await Util.GetTokenAsync("BizAdminFull")); + Util.ValidateHTTPStatusCode(a, 204); + + a = await Util.DeleteAsync("widget/" + ExcludedWidgetId.ToString(), await Util.GetTokenAsync("BizAdminFull")); + Util.ValidateHTTPStatusCode(a, 204); + + } + #endregion decimal tests + + /////////////////////////////////////////////////////////////////////////////// + //TAGS + // + #region TAG TESTS + + /// + /// + /// + [Fact] + public async Task TagFilterWorks() + { + + var TestName = "TagFilterWorks"; + var WidgetNameStart = Util.Uniquify(TestName); + + List InclusiveWidgetIdList = new List(); + List ExclusiveWidgetIdList = new List(); + + //CREATE 4 TEST WIDGETS + //two inclusive and two not inclusive + + //first inclusive widget + dynamic w = new JObject(); + w.name = Util.Uniquify(WidgetNameStart); + w.customFields = Util.WidgetRequiredCustomFieldsJsonString(); + w.notes = "blah"; + w.usertype = 1; + //Tags + dynamic InclusiveTagsArray = new JArray(); + InclusiveTagsArray.Add("red-tag-test"); + InclusiveTagsArray.Add("orange-tag-test"); + InclusiveTagsArray.Add("yellow-tag-test"); + InclusiveTagsArray.Add("green-tag-test"); + InclusiveTagsArray.Add("blue-tag-test"); + InclusiveTagsArray.Add("indigo-tag-test"); + InclusiveTagsArray.Add("violet-tag-test"); + w.tags = InclusiveTagsArray; + + ApiResponse a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w.ToString()); + Util.ValidateDataReturnResponseOk(a); + InclusiveWidgetIdList.Add(a.ObjectResponse["data"]["id"].Value()); + + //second inclusive widget + w.name = Util.Uniquify(WidgetNameStart); + + a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w.ToString()); + Util.ValidateDataReturnResponseOk(a); + InclusiveWidgetIdList.Add(a.ObjectResponse["data"]["id"].Value()); + + //first exclusive widget + w.name = Util.Uniquify(WidgetNameStart); + //Tags + dynamic ExclusiveTagsArray = new JArray(); + ExclusiveTagsArray.Add("crimson-tag-test"); + ExclusiveTagsArray.Add("amber-tag-test"); + ExclusiveTagsArray.Add("saffron-tag-test"); + ExclusiveTagsArray.Add("emerald-tag-test"); + ExclusiveTagsArray.Add("azure-tag-test"); + ExclusiveTagsArray.Add("red-tag-test"); + ExclusiveTagsArray.Add("blue-tag-test"); + ExclusiveTagsArray.Add("cobalt-tag-test"); + ExclusiveTagsArray.Add("magenta-tag-test"); + w.tags = ExclusiveTagsArray;//Missing green + + a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w.ToString()); + Util.ValidateDataReturnResponseOk(a); + ExclusiveWidgetIdList.Add(a.ObjectResponse["data"]["id"].Value()); + + //second exclusive widget + w.name = Util.Uniquify(WidgetNameStart); + w.active = false; + + a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w.ToString()); + Util.ValidateDataReturnResponseOk(a); + ExclusiveWidgetIdList.Add(a.ObjectResponse["data"]["id"].Value()); + + + //CREATE LISTVIEW + dynamic dListView = new JArray(); + + //name starts with filter to constrict to widgets that this test block created only + dListView.Add(Util.BuildSimpleFilterDataListViewColumn("widgetname", Util.OpStartsWith, WidgetNameStart)); + + //active test filter + // dynamic DataFilterActive = new JObject(); + // DataFilterActive.fld = "widgettags"; + // DataFilterActive.op = Util.OpEquality; + dynamic FilterTagsArray = new JArray(); + FilterTagsArray.Add("red-tag-test"); + FilterTagsArray.Add("green-tag-test");//green is the only one missing from the exclusive widget + FilterTagsArray.Add("blue-tag-test"); + // DataFilterActive.value = FilterTagsArray; + dListView.Add(Util.BuildSimpleFilterDataListViewColumn("widgettags", Util.OpEquality, FilterTagsArray)); + + + //FETCH DATALIST + a = await Util.PostAsync($"data-list", await Util.GetTokenAsync("superuser", "l3tm3in"), Util.BuildDataListRequestEx(dListView)); + Util.ValidateDataReturnResponseOk(a); + Util.ValidateHTTPStatusCode(a, 200); + + //assert contains at least two records + ((JArray)a.ObjectResponse["data"]).Count.Should().BeGreaterThan(1); + var v = ((JArray)a.ObjectResponse["data"]); + List IDInResultList = new List(); + int InclusiveMatchCount = 0; + int ExclusiveMatchCount = 0; + + + foreach (JArray ja in v) + { + JObject o = ja[0] as JObject; + + if (InclusiveWidgetIdList.Contains(o["i"].Value())) + InclusiveMatchCount++; + if (ExclusiveWidgetIdList.Contains(o["i"].Value())) + ExclusiveMatchCount++; + } + + + + InclusiveMatchCount.Should().Be(InclusiveWidgetIdList.Count); + ExclusiveMatchCount.Should().Be(0); + + //DELETE WIDGETS + foreach (long l in InclusiveWidgetIdList) + { + a = await Util.DeleteAsync("widget/" + l.ToString(), await Util.GetTokenAsync("BizAdminFull")); + Util.ValidateHTTPStatusCode(a, 204); + } + + foreach (long l in ExclusiveWidgetIdList) + { + a = await Util.DeleteAsync("widget/" + l.ToString(), await Util.GetTokenAsync("BizAdminFull")); + Util.ValidateHTTPStatusCode(a, 204); + } + } + + + /// + /// + /// + [Fact] + public async Task UnicodeTagFilterWorks() + { + + var TestName = "UnicodeTagFilterWorks"; + var WidgetNameStart = Util.Uniquify(TestName); + + List InclusiveWidgetIdList = new List(); + List ExclusiveWidgetIdList = new List(); + + //CREATE 4 TEST WIDGETS + //two inclusive and two not inclusive + + //first inclusive widget + dynamic w = new JObject(); + w.name = Util.Uniquify(WidgetNameStart); + w.customFields = Util.WidgetRequiredCustomFieldsJsonString(); + w.notes = "blah"; + w.usertype = 1; + //Tags + dynamic InclusiveTagsArray = new JArray(); + InclusiveTagsArray.Add("red-tag-test"); + InclusiveTagsArray.Add("orange-tag-test"); + InclusiveTagsArray.Add("Ādam Iñtërnâtiônàližætiøn"); + w.tags = InclusiveTagsArray; + + ApiResponse a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w.ToString()); + Util.ValidateDataReturnResponseOk(a); + InclusiveWidgetIdList.Add(a.ObjectResponse["data"]["id"].Value()); + + //second inclusive widget + w.name = Util.Uniquify(WidgetNameStart); + + a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w.ToString()); + Util.ValidateDataReturnResponseOk(a); + InclusiveWidgetIdList.Add(a.ObjectResponse["data"]["id"].Value()); + + //first exclusive widget + w.name = Util.Uniquify(WidgetNameStart); + //Tags + dynamic ExclusiveTagsArray = new JArray(); + ExclusiveTagsArray.Add("crimson-tag-test"); + ExclusiveTagsArray.Add("amber-tag-test"); + ExclusiveTagsArray.Add("saffron-tag-test"); + ExclusiveTagsArray.Add("emerald-tag-test"); + ExclusiveTagsArray.Add("azure-tag-test"); + ExclusiveTagsArray.Add("red-tag-test"); + ExclusiveTagsArray.Add("blue-tag-test"); + ExclusiveTagsArray.Add("cobalt-tag-test"); + ExclusiveTagsArray.Add("magenta-tag-test"); + w.tags = ExclusiveTagsArray;//Missing green + + a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w.ToString()); + Util.ValidateDataReturnResponseOk(a); + ExclusiveWidgetIdList.Add(a.ObjectResponse["data"]["id"].Value()); + + //second exclusive widget + w.name = Util.Uniquify(WidgetNameStart); + w.active = false; + + a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w.ToString()); + Util.ValidateDataReturnResponseOk(a); + ExclusiveWidgetIdList.Add(a.ObjectResponse["data"]["id"].Value()); + + + //CREATE LISTVIEW + dynamic dListView = new JArray(); + + //name starts with filter to constrict to widgets that this test block created only + dListView.Add(Util.BuildSimpleFilterDataListViewColumn("widgetname", Util.OpStartsWith, WidgetNameStart)); + + //active test filter + // dynamic DataFilterActive = new JObject(); + // DataFilterActive.fld = "widgettags"; + // DataFilterActive.op = Util.OpEquality; + dynamic FilterTagsArray = new JArray(); + FilterTagsArray.Add("red-tag-test"); + FilterTagsArray.Add("Ādam Iñtërnâtiônàližætiøn"); + // DataFilterActive.value = FilterTagsArray; + dListView.Add(Util.BuildSimpleFilterDataListViewColumn("widgettags", Util.OpEquality, FilterTagsArray)); + + //FETCH DATALIST + a = await Util.PostAsync($"data-list", await Util.GetTokenAsync("superuser", "l3tm3in"), Util.BuildDataListRequestEx(dListView)); + Util.ValidateDataReturnResponseOk(a); + Util.ValidateHTTPStatusCode(a, 200); + + //assert contains at least two records + ((JArray)a.ObjectResponse["data"]).Count.Should().BeGreaterThan(1); + var v = ((JArray)a.ObjectResponse["data"]); + List IDInResultList = new List(); + int InclusiveMatchCount = 0; + int ExclusiveMatchCount = 0; + foreach (JArray ja in v) + { + JObject o = ja[0] as JObject; + if (InclusiveWidgetIdList.Contains(o["i"].Value())) + InclusiveMatchCount++; + if (ExclusiveWidgetIdList.Contains(o["i"].Value())) + ExclusiveMatchCount++; + } + + InclusiveMatchCount.Should().Be(InclusiveWidgetIdList.Count); + ExclusiveMatchCount.Should().Be(0); + + //DELETE WIDGETS + foreach (long l in InclusiveWidgetIdList) + { + a = await Util.DeleteAsync("widget/" + l.ToString(), await Util.GetTokenAsync("BizAdminFull")); + Util.ValidateHTTPStatusCode(a, 204); + } + + foreach (long l in ExclusiveWidgetIdList) + { + a = await Util.DeleteAsync("widget/" + l.ToString(), await Util.GetTokenAsync("BizAdminFull")); + Util.ValidateHTTPStatusCode(a, 204); + } + } + + + #endregion tag tests + //================================================== + + /////////////////////////////////////////////////////////////////////////////// + //FILTER BY ID VALUE + // + #region ID FILTER TESTS + + /// + /// + /// + [Fact] + public async Task IdFilterWorks() + { + + var TestName = "IdFilterWorks"; + var WidgetNameStart = Util.Uniquify(TestName); + + //CREATE WIDGET + dynamic w = new JObject(); + w.name = Util.Uniquify(WidgetNameStart); + w.customFields = Util.WidgetRequiredCustomFieldsJsonString(); + w.notes = "ID FILTER NOTES"; + w.usertype = 1; + + ApiResponse a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w.ToString()); + Util.ValidateDataReturnResponseOk(a); + long Id = a.ObjectResponse["data"]["id"].Value(); + + + //CREATE LISTVIEW + dynamic dListView = new JArray(); + //FILTER + dListView.Add(Util.BuildSimpleFilterDataListViewColumn("widgetname", Util.OpEquality, Id)); + //FETCH DATALIST + a = await Util.PostAsync($"data-list", await Util.GetTokenAsync("superuser", "l3tm3in"), Util.BuildDataListRequestEx(dListView)); + + Util.ValidateDataReturnResponseOk(a); + Util.ValidateHTTPStatusCode(a, 200); + + //assert contains ONE record ONLY + ((JArray)a.ObjectResponse["data"]).Count.Should().Be(1); + //assert it's ours + ((JArray)a.ObjectResponse["data"])[0][0]["i"].Value().Should().Be(Id); + // v[0]["v"].Value() + + //DELETE WIDGET + a = await Util.DeleteAsync("widget/" + Id.ToString(), await Util.GetTokenAsync("BizAdminFull")); + Util.ValidateHTTPStatusCode(a, 204); + + + + } + + + + + + #endregion ID filter tests + + + + /////////////////////////////////////////////////////////////////////////////// + //*NULL* TESTS + // + + #region *NULL* TESTS + + /// + /// + /// + [Fact] + public async Task NullEqualityFilterWorks() + { + //OPS: equal to, not equal to + //values: null + + var WidgetNameStart = "NullEqualityFilterWorks"; + + List NullInCountWidgetIdList = new List(); + List NotNullInCountWidgetIdList = new List(); + + //CREATE 4 TEST WIDGETS + //two null count and two non null count + + //first null count widget + dynamic w = new JObject(); + w.name = Util.Uniquify(WidgetNameStart); + w.customFields = Util.WidgetRequiredCustomFieldsJsonString(); + w.notes = "blah"; + w.active = true; + w.usertype = 1; + + ApiResponse a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w.ToString()); + Util.ValidateDataReturnResponseOk(a); + NullInCountWidgetIdList.Add(a.ObjectResponse["data"]["id"].Value()); + + //second null count widget + w.name = Util.Uniquify(WidgetNameStart); + + a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w.ToString()); + Util.ValidateDataReturnResponseOk(a); + NullInCountWidgetIdList.Add(a.ObjectResponse["data"]["id"].Value()); + + + //first NON null in count widget + w.name = Util.Uniquify(WidgetNameStart); + w.count = 22; + + a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w.ToString()); + Util.ValidateDataReturnResponseOk(a); + NotNullInCountWidgetIdList.Add(a.ObjectResponse["data"]["id"].Value()); + + //second NON null in count field widget + w.name = Util.Uniquify(WidgetNameStart); + w.count = 33; + + a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w.ToString()); + Util.ValidateDataReturnResponseOk(a); + NotNullInCountWidgetIdList.Add(a.ObjectResponse["data"]["id"].Value()); + + + //CREATE LISTVIEW + dynamic dListView = new JArray(); + + //name starts with filter to constrict to widgets that this test block created only + dListView.Add(Util.BuildSimpleFilterDataListViewColumn("widgetname", Util.OpStartsWith, WidgetNameStart)); + + //FILTER + // dynamic DataFilterActive = new JObject(); + // DataFilterActive.fld = "widgetactive"; + // DataFilterActive.op = Util.OpEquality; + // DataFilterActive.value = true; + dListView.Add(Util.BuildSimpleFilterDataListViewColumn("widgetcount", Util.OpEquality, "*NULL*")); + + + //FETCH DATALIST + a = await Util.PostAsync($"data-list", await Util.GetTokenAsync("superuser", "l3tm3in"), Util.BuildDataListRequestEx(dListView)); + Util.ValidateDataReturnResponseOk(a); + Util.ValidateHTTPStatusCode(a, 200); + + //assert contains at least two records + ((JArray)a.ObjectResponse["data"]).Count.Should().BeGreaterThan(1); + var v = ((JArray)a.ObjectResponse["data"]); + List IDInResultList = new List(); + int nNullCountMatches = 0; + int nNotNullCountMatches = 0; + + foreach (JArray ja in v) + { + JObject o = ja[0] as JObject; + + + if (NullInCountWidgetIdList.Contains(o["i"].Value())) + nNullCountMatches++; + //if (NotActiveWidgetIdList.Contains(o["i"].Value())) + if (NotNullInCountWidgetIdList.Contains(o["i"].Value())) + nNotNullCountMatches++; + } + + nNullCountMatches.Should().Be(NullInCountWidgetIdList.Count); + nNotNullCountMatches.Should().Be(0); + + //DELETE WIDGETS + foreach (long l in NullInCountWidgetIdList) + { + a = await Util.DeleteAsync("widget/" + l.ToString(), await Util.GetTokenAsync("BizAdminFull")); + Util.ValidateHTTPStatusCode(a, 204); + } + + foreach (long l in NotNullInCountWidgetIdList) + { + a = await Util.DeleteAsync("widget/" + l.ToString(), await Util.GetTokenAsync("BizAdminFull")); + Util.ValidateHTTPStatusCode(a, 204); + } + } + + /// + /// + /// + [Fact] + public async Task NullNotEqualFilterWorks() + { + //OPS: equal to, not equal to + //values: null + + var WidgetNameStart = "NullNotEqualFilterWorks"; + + List NullInCountWidgetIdList = new List(); + List NotNullInCountWidgetIdList = new List(); + + //CREATE 4 TEST WIDGETS + //two null count and two non null count + + //first null count widget + dynamic w = new JObject(); + w.name = Util.Uniquify(WidgetNameStart); + w.customFields = Util.WidgetRequiredCustomFieldsJsonString(); + w.notes = "blah"; + w.active = true; + w.usertype = 1; + + ApiResponse a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w.ToString()); + Util.ValidateDataReturnResponseOk(a); + NullInCountWidgetIdList.Add(a.ObjectResponse["data"]["id"].Value()); + + //second null count widget + w.name = Util.Uniquify(WidgetNameStart); + + a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w.ToString()); + Util.ValidateDataReturnResponseOk(a); + NullInCountWidgetIdList.Add(a.ObjectResponse["data"]["id"].Value()); + + + //first NON null in count widget + w.name = Util.Uniquify(WidgetNameStart); + w.count = 22; + + a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w.ToString()); + Util.ValidateDataReturnResponseOk(a); + NotNullInCountWidgetIdList.Add(a.ObjectResponse["data"]["id"].Value()); + + //second NON null in count field widget + w.name = Util.Uniquify(WidgetNameStart); + w.count = 33; + + a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w.ToString()); + Util.ValidateDataReturnResponseOk(a); + NotNullInCountWidgetIdList.Add(a.ObjectResponse["data"]["id"].Value()); + + + //CREATE LISTVIEW + dynamic dListView = new JArray(); + + //name starts with filter to constrict to widgets that this test block created only + dListView.Add(Util.BuildSimpleFilterDataListViewColumn("widgetname", Util.OpStartsWith, WidgetNameStart)); + + //FILTER + // dynamic DataFilterActive = new JObject(); + // DataFilterActive.fld = "widgetactive"; + // DataFilterActive.op = Util.OpEquality; + // DataFilterActive.value = true; + dListView.Add(Util.BuildSimpleFilterDataListViewColumn("widgetcount", Util.OpNotEqual, "*NULL*")); + + + //FETCH DATALIST + a = await Util.PostAsync($"data-list", await Util.GetTokenAsync("superuser", "l3tm3in"), Util.BuildDataListRequestEx(dListView)); + Util.ValidateDataReturnResponseOk(a); + Util.ValidateHTTPStatusCode(a, 200); + + //assert contains at least two records + ((JArray)a.ObjectResponse["data"]).Count.Should().BeGreaterThan(1); + var v = ((JArray)a.ObjectResponse["data"]); + List IDInResultList = new List(); + int nNullCountMatches = 0; + int nNotNullCountMatches = 0; + + foreach (JArray ja in v) + { + JObject o = ja[0] as JObject; + + + if (NullInCountWidgetIdList.Contains(o["i"].Value())) + nNullCountMatches++; + //if (NotActiveWidgetIdList.Contains(o["i"].Value())) + if (NotNullInCountWidgetIdList.Contains(o["i"].Value())) + nNotNullCountMatches++; + } + + nNotNullCountMatches.Should().Be(NullInCountWidgetIdList.Count); + nNullCountMatches.Should().Be(0); + + //DELETE WIDGETS + foreach (long l in NullInCountWidgetIdList) + { + a = await Util.DeleteAsync("widget/" + l.ToString(), await Util.GetTokenAsync("BizAdminFull")); + Util.ValidateHTTPStatusCode(a, 204); + } + + foreach (long l in NotNullInCountWidgetIdList) + { + a = await Util.DeleteAsync("widget/" + l.ToString(), await Util.GetTokenAsync("BizAdminFull")); + Util.ValidateHTTPStatusCode(a, 204); + } + } + + + #endregion *NULL* tests + + + + + + //================================================== + + }//eoc +}//eons diff --git a/DataList/DataListReturnFormat.cs b/DataList/DataListReturnFormat.cs index f0b8b1a..946fcb3 100644 --- a/DataList/DataListReturnFormat.cs +++ b/DataList/DataListReturnFormat.cs @@ -1,115 +1,115 @@ -using System; -using Xunit; -using Newtonsoft.Json.Linq; -using FluentAssertions; -using System.Collections.Generic; -using System.Threading.Tasks; -using System.Collections.Concurrent; - -namespace raven_integration -{ - - public class DataListPaging - { - - - /// - /// Return format test - /// - [Fact] - public async void DataListReturnFormatShouldWorkAsExpected() - { - - ApiResponse a = await Util.PostAsync($"data-list", await Util.GetTokenAsync("superuser", "l3tm3in"), Util.BuildDataListRequestEx(null, 3, 2)); - Util.ValidateDataReturnResponseOk(a); - Util.ValidateHTTPStatusCode(a, 200); - - //assert aAll contains at least three records - ((JArray)a.ObjectResponse["data"]).Count.Should().Be(3); - //sb a total record count greater than 3 - ((JValue)a.ObjectResponse["totalRecordCount"]).Value().Should().BeGreaterThan(3); - //sb a column header collection greater than 3 - ((JArray)a.ObjectResponse["columns"]).Count.Should().BeGreaterThan(3); - - } - - /// - /// Return un - filtered/sorted fields and custom fields test - /// - [Fact] - public async void DataListShouldReturnAllFieldsSpecifiedEvenIfUnsortedOrFilteredAndCustomToo() - { - - dynamic dListView = new JArray(); - - dynamic d = new JObject(); - d.fld = "widgetserial"; - dListView.Add(d); - - d = new JObject(); - d.fld = "widgetdollaramount"; - dListView.Add(d); - - d = new JObject(); - d.fld = "widgetcount"; - dListView.Add(d); - - d = new JObject(); - d.fld = "widgetusertype"; - dListView.Add(d); - - d = new JObject(); - d.fld = "widgetcustom2"; - dListView.Add(d); - - d = new JObject(); - d.fld = "widgetcustom1"; - dListView.Add(d); - - d = new JObject(); - d.fld = "widgetcustom3"; - dListView.Add(d); - - d = new JObject(); - d.fld = "widgetcustom4"; - dListView.Add(d); - - d = new JObject(); - d.fld = "widgetcustom5"; - dListView.Add(d); - - /* - //RANDOM CUSTOM FIELD DATA - var c1 = DateUtil.UniversalISO8661Format(f.Date.Between(DateTime.Now.AddYears(-1), DateTime.Now.AddYears(1))); - var c2 = f.Lorem.Sentence(); - var c3 = f.Random.Int(1, 99999999); - var c4 = f.Random.Bool().ToString().ToLowerInvariant(); - var c5 = f.Random.Decimal(); - */ - - //FETCH DATALIST - ApiResponse a = await Util.PostAsync($"data-list", await Util.GetTokenAsync("superuser", "l3tm3in"), Util.BuildDataListRequestEx(dListView)); - - Util.ValidateDataReturnResponseOk(a); - Util.ValidateHTTPStatusCode(a, 200); - - //assert aAll contains at least three records - ((JArray)a.ObjectResponse["data"]).Count.Should().BeGreaterThan(0); - - //ensure first row contains all columns requested in listview - ((JArray)a.ObjectResponse["data"][0]).Count.Should().Be(9); - - //sb a total record count greater than 3 - ((JValue)a.ObjectResponse["totalRecordCount"]).Value().Should().BeGreaterThan(3); - //sb a column header collection greater than 3 - ((JArray)a.ObjectResponse["columns"]).Count.Should().BeGreaterThan(3); - - } - - /* - "{\"data\":[[{\"v\":276},{\"v\":276},{\"v\":2.22},{\"v\":null},{\"v\":1}],[{\"v\":272},{\"v\":272},{\"v\":1.11},{\"v\":null},{\"v\":1}],[{\"v\":270},{\"v\":270},{\"v\":1.11},{\"v\":null},{\"v\":1}],[{\"v\":265},{\"v\":265},{\"v\":1.11},{\"v\":null},{\"v\":1}],[{\"v\":263},{\"v\":263},{\"v\":1.11},{\"v\":null},{\"v\":1}],[{\"v\":259},{\"v\":259},{\"v\":1.11},{\"v\":null},{\"v\":1}],[{\"v\":252},{\"v\":252},{\"v\":1.11},{\"v\":null},{\"v\":1}],[{\"v\":249},{\"v\":249},{\"v\":1.11},{\"v\":null},{\"v\":1}],[{\"v\":248},{\"v\":248},{\"v\":1.11},{\"v\":null},{\"v\":1}],[{\"v\":247},{\"v\":247},{\"v\":1.11},{\"v\":null},{\"v\":1}],[{\"v\":246},{\"v\":246},{\"v\":1.11},{\"v\":null},{\"v\":1}],[{\"v\":242},{\"v\":242},{\"v\":2.22},{\"v\":null},{\"v\":1}],[{\"v\":238},{\"v\":238},{\"v\":1.11},{\"v\":null},{\"v\":1}],[{\"v\":147},{\"v\":147},{\"v\":1.11},{\"v\":null},{\"v\":1}],[{\"v\":144},{\"v\":144},{\"v\":1.11},{\"v\":null},{\"v\":1}],[{\"v\":135},{\"v\":135},{\"v\":1.11},{\"v\":null},{\"v\":1}],[{\"v\":134},{\"v\":134},{\"v\":1.11},{\"v\":null},{\"v\":1}],[{\"v\":133},{\"v\":133},{\"v\":2.22},{\"v\":null},{\"v\":1}],[{\"v\":129},{\"v\":130},{\"v\":1.11},{\"v\":null},{\"v\":1}],[{\"v\":122},{\"v\":122},{\"v\":1.11},{\"v\":null},{\"v\":1}],[{\"v\":120},{\"v\":121},{\"v\":1.11},{\"v\":null},{\"v\":1}],[{\"v\":119},{\"v\":119},{\"v\":1.11},{\"v\":null},{\"v\":1}],[{\"v\":113},{\"v\":113},{\"v\":1.11},{\"v\":null},{\"v\":1}],[{\"v\":108},{\"v\":108},{\"v\":1.11},{\"v\":null},{\"v\":1}],[{\"v\":105},{\"v\":105},{\"v\":1.11},{\"v\":null},{\"v\":1}],[{\"v\":103},{\"v\":103},{\"v\":2.22},{\"v\":null},{\"v\":1}],[{\"v\":100},{\"v\":100},{\"v\":618.17},{\"v\":null},{\"v\":1}],[{\"v\":99},{\"v\":99},{\"v\":885.48},{\"v\":null},{\"v\":6}],[{\"v\":98},{\"v\":98},{\"v\":794.97},{\"v\":null},{\"v\":5}],[{\"v\":97},{\"v\":97},{\"v\":999.02},{\"v\":null},{\"v\":5}],[{\"v\":96},{\"v\":96},{\"v\":958.63},{\"v\":null},{\"v\":1}],[{\"v\":95},{\"v\":95},{\"v\":270.99},{\"v\":null},{\"v\":7}],[{\"v\":94},{\"v\":94},{\"v\":505.75},{\"v\":null},{\"v\":2}],[{\"v\":93},{\"v\":93},{\"v\":704.93},{\"v\":null},{\"v\":7}],[{\"v\":92},{\"v\":92},{\"v\":637.32},{\"v\":null},{\"v\":2}],[{\"v\":91},{\"v\":91},{\"v\":780.54},{\"v\":null},{\"v\":4}],[{\"v\":90},{\"v\":90},{\"v\":834.7},{\"v\":null},{\"v\":3}],[{\"v\":89},{\"v\":89},{\"v\":663.87},{\"v\":null},{\"v\":5}],[{\"v\":88},{\"v\":88},{\"v\":104.97},{\"v\":null},{\"v\":1}],[{\"v\":87},{\"v\":87},{\"v\":519.91},{\"v\":null},{\"v\":3}],[{\"v\":86},{\"v\":86},{\"v\":725.35},{\"v\":null},{\"v\":1}],[{\"v\":85},{\"v\":85},{\"v\":346.63},{\"v\":null},{\"v\":4}],[{\"v\":84},{\"v\":84},{\"v\":750.63},{\"v\":null},{\"v\":3}],[{\"v\":83},{\"v\":83},{\"v\":69.88},{\"v\":null},{\"v\":1}],[{\"v\":82},{\"v\":82},{\"v\":723.35},{\"v\":null},{\"v\":2}],[{\"v\":81},{\"v\":81},{\"v\":643.24},{\"v\":null},{\"v\":2}],[{\"v\":80},{\"v\":80},{\"v\":482.79},{\"v\":null},{\"v\":2}],[{\"v\":79},{\"v\":79},{\"v\":37.92},{\"v\":null},{\"v\":5}],[{\"v\":78},{\"v\":78},{\"v\":423.83},{\"v\":null},{\"v\":6}],[{\"v\":77},{\"v\":77},{\"v\":37.08},{\"v\":null},{\"v\":4}],[{\"v\":76},{\"v\":76},{\"v\":226.49},{\"v\":null},{\"v\":4}],[{\"v\":75},{\"v\":75},{\"v\":523.93},{\"v\":null},{\"v\":5}],[{\"v\":74},{\"v\":74},{\"v\":899.03},{\"v\":null},{\"v\":7}],[{\"v\":73},{\"v\":73},{\"v\":222.86},{\"v\":null},{\"v\":3}],[{\"v\":72},{\"v\":72},{\"v\":881.09},{\"v\":null},{\"v\":3}],[{\"v\":71},{\"v\":71},{\"v\":75.91},{\"v\":null},{\"v\":3}],[{\"v\":70},{\"v\":70},{\"v\":592.48},{\"v\":null},{\"v\":7}],[{\"v\":69},{\"v\":69},{\"v\":723.12},{\"v\":null},{\"v\":7}],[{\"v\":68},{\"v\":68},{\"v\":912.26},{\"v\":null},{\"v\":7}],[{\"v\":67},{\"v\":67},{\"v\":93.87},{\"v\":null},{\"v\":6}],[{\"v\":66},{\"v\":66},{\"v\":613.15},{\"v\":null},{\"v\":5}],[{\"v\":65},{\"v\":65},{\"v\":713.82},{\"v\":null},{\"v\":7}],[{\"v\":64},{\"v\":64},{\"v\":526.5},{\"v\":null},{\"v\":1}],[{\"v\":63},{\"v\":63},{\"v\":585.31},{\"v\":null},{\"v\":4}],[{\"v\":62},{\"v\":62},{\"v\":441.5},{\"v\":null},{\"v\":2}],[{\"v\":61},{\"v\":61},{\"v\":717.32},{\"v\":null},{\"v\":1}],[{\"v\":60},{\"v\":60},{\"v\":558.3},{\"v\":null},{\"v\":6}],[{\"v\":59},{\"v\":59},{\"v\":65.28},{\"v\":null},{\"v\":5}],[{\"v\":58},{\"v\":58},{\"v\":707.71},{\"v\":null},{\"v\":5}],[{\"v\":57},{\"v\":57},{\"v\":963.73},{\"v\":null},{\"v\":7}],[{\"v\":56},{\"v\":56},{\"v\":591.21},{\"v\":null},{\"v\":2}],[{\"v\":55},{\"v\":55},{\"v\":551.17},{\"v\":null},{\"v\":3}],[{\"v\":54},{\"v\":54},{\"v\":146.21},{\"v\":null},{\"v\":1}],[{\"v\":53},{\"v\":53},{\"v\":258.66},{\"v\":null},{\"v\":5}],[{\"v\":52},{\"v\":52},{\"v\":623.71},{\"v\":null},{\"v\":3}],[{\"v\":51},{\"v\":51},{\"v\":352.75},{\"v\":null},{\"v\":2}],[{\"v\":50},{\"v\":50},{\"v\":224.18},{\"v\":null},{\"v\":5}],[{\"v\":49},{\"v\":49},{\"v\":667.09},{\"v\":null},{\"v\":7}],[{\"v\":48},{\"v\":48},{\"v\":676.25},{\"v\":null},{\"v\":6}],[{\"v\":47},{\"v\":47},{\"v\":498.2},{\"v\":null},{\"v\":2}],[{\"v\":46},{\"v\":46},{\"v\":999.28},{\"v\":null},{\"v\":3}],[{\"v\":45},{\"v\":45},{\"v\":262.86},{\"v\":null},{\"v\":5}],[{\"v\":44},{\"v\":44},{\"v\":556.43},{\"v\":null},{\"v\":5}],[{\"v\":43},{\"v\":43},{\"v\":768.96},{\"v\":null},{\"v\":6}],[{\"v\":42},{\"v\":42},{\"v\":427.17},{\"v\":null},{\"v\":1}],[{\"v\":41},{\"v\":41},{\"v\":118.47},{\"v\":null},{\"v\":3}],[{\"v\":40},{\"v\":40},{\"v\":539.87},{\"v\":null},{\"v\":7}],[{\"v\":39},{\"v\":39},{\"v\":37.45},{\"v\":null},{\"v\":7}],[{\"v\":38},{\"v\":38},{\"v\":967.69},{\"v\":null},{\"v\":5}],[{\"v\":37},{\"v\":37},{\"v\":3.46},{\"v\":null},{\"v\":7}],[{\"v\":36},{\"v\":36},{\"v\":483.42},{\"v\":null},{\"v\":3}],[{\"v\":35},{\"v\":35},{\"v\":548.64},{\"v\":null},{\"v\":5}],[{\"v\":34},{\"v\":34},{\"v\":74.34},{\"v\":null},{\"v\":7}],[{\"v\":33},{\"v\":33},{\"v\":506.67},{\"v\":null},{\"v\":2}],[{\"v\":32},{\"v\":32},{\"v\":823.07},{\"v\":null},{\"v\":1}],[{\"v\":31},{\"v\":31},{\"v\":983.09},{\"v\":null},{\"v\":4}],[{\"v\":30},{\"v\":30},{\"v\":25.46},{\"v\":null},{\"v\":5}],[{\"v\":29},{\"v\":29},{\"v\":717.39},{\"v\":null},{\"v\":7}],[{\"v\":28},{\"v\":28},{\"v\":874.1},{\"v\":null},{\"v\":1}],[{\"v\":27},{\"v\":27},{\"v\":529.19},{\"v\":null},{\"v\":1}],[{\"v\":26},{\"v\":26},{\"v\":851.66},{\"v\":null},{\"v\":3}],[{\"v\":25},{\"v\":25},{\"v\":127.14},{\"v\":null},{\"v\":5}],[{\"v\":24},{\"v\":24},{\"v\":985.65},{\"v\":null},{\"v\":2}],[{\"v\":23},{\"v\":23},{\"v\":507.75},{\"v\":null},{\"v\":4}],[{\"v\":22},{\"v\":22},{\"v\":949.86},{\"v\":null},{\"v\":2}],[{\"v\":21},{\"v\":21},{\"v\":862.96},{\"v\":null},{\"v\":4}],[{\"v\":20},{\"v\":20},{\"v\":189.26},{\"v\":null},{\"v\":7}],[{\"v\":19},{\"v\":19},{\"v\":489.77},{\"v\":null},{\"v\":6}],[{\"v\":18},{\"v\":18},{\"v\":233.59},{\"v\":null},{\"v\":3}],[{\"v\":17},{\"v\":17},{\"v\":260.98},{\"v\":null},{\"v\":7}],[{\"v\":16},{\"v\":16},{\"v\":478.33},{\"v\":null},{\"v\":2}],[{\"v\":15},{\"v\":15},{\"v\":87.56},{\"v\":null},{\"v\":3}],[{\"v\":14},{\"v\":14},{\"v\":86.51},{\"v\":null},{\"v\":4}],[{\"v\":13},{\"v\":13},{\"v\":702.71},{\"v\":null},{\"v\":7}],[{\"v\":12},{\"v\":12},{\"v\":635.24},{\"v\":null},{\"v\":7}],[{\"v\":11},{\"v\":11},{\"v\":84.4},{\"v\":null},{\"v\":5}],[{\"v\":10},{\"v\":10},{\"v\":213.61},{\"v\":null},{\"v\":3}],[{\"v\":9},{\"v\":9},{\"v\":745.44},{\"v\":null},{\"v\":6}],[{\"v\":8},{\"v\":8},{\"v\":796.05},{\"v\":null},{\"v\":3}],[{\"v\":7},{\"v\":7},{\"v\":341.13},{\"v\":null},{\"v\":2}],[{\"v\":6},{\"v\":6},{\"v\":252.86},{\"v\":null},{\"v\":1}],[{\"v\":5},{\"v\":5},{\"v\":40.62},{\"v\":null},{\"v\":1}],[{\"v\":4},{\"v\":4},{\"v\":86.94},{\"v\":null},{\"v\":3}],[{\"v\":3},{\"v\":3},{\"v\":551.06},{\"v\":null},{\"v\":6}],[{\"v\":2},{\"v\":2},{\"v\":137.74},{\"v\":null},{\"v\":3}],[{\"v\":1},{\"v\":1},{\"v\":870.43},{\"v\":null},{\"v\":4}]],\"totalRecordCount\":126,\"columns\":[{\"cm\":\"df\",\"dt\":0,\"ay\":2},{\"cm\":\"WidgetSerial\",\"dt\":5},{\"cm\":\"WidgetDollarAmount\",\"dt\":8},{\"cm\":\"WidgetCount\",\"dt\":5},{\"cm\":\"WidgetUserType\",\"dt\":10,\"et\":\"UserType\"}]}" - */ - //================================================== - - }//eoc -}//eons +using System; +using Xunit; +using Newtonsoft.Json.Linq; +using FluentAssertions; +using System.Collections.Generic; +using System.Threading.Tasks; +using System.Collections.Concurrent; + +namespace raven_integration +{ + + public class DataListPaging + { + + + /// + /// Return format test + /// + [Fact] + public async Task DataListReturnFormatShouldWorkAsExpected() + { + + ApiResponse a = await Util.PostAsync($"data-list", await Util.GetTokenAsync("superuser", "l3tm3in"), Util.BuildDataListRequestEx(null, 3, 2)); + Util.ValidateDataReturnResponseOk(a); + Util.ValidateHTTPStatusCode(a, 200); + + //assert aAll contains at least three records + ((JArray)a.ObjectResponse["data"]).Count.Should().Be(3); + //sb a total record count greater than 3 + ((JValue)a.ObjectResponse["totalRecordCount"]).Value().Should().BeGreaterThan(3); + //sb a column header collection greater than 3 + ((JArray)a.ObjectResponse["columns"]).Count.Should().BeGreaterThan(3); + + } + + /// + /// Return un - filtered/sorted fields and custom fields test + /// + [Fact] + public async Task DataListShouldReturnAllFieldsSpecifiedEvenIfUnsortedOrFilteredAndCustomToo() + { + + dynamic dListView = new JArray(); + + dynamic d = new JObject(); + d.fld = "widgetserial"; + dListView.Add(d); + + d = new JObject(); + d.fld = "widgetdollaramount"; + dListView.Add(d); + + d = new JObject(); + d.fld = "widgetcount"; + dListView.Add(d); + + d = new JObject(); + d.fld = "widgetusertype"; + dListView.Add(d); + + d = new JObject(); + d.fld = "widgetcustom2"; + dListView.Add(d); + + d = new JObject(); + d.fld = "widgetcustom1"; + dListView.Add(d); + + d = new JObject(); + d.fld = "widgetcustom3"; + dListView.Add(d); + + d = new JObject(); + d.fld = "widgetcustom4"; + dListView.Add(d); + + d = new JObject(); + d.fld = "widgetcustom5"; + dListView.Add(d); + + /* + //RANDOM CUSTOM FIELD DATA + var c1 = DateUtil.UniversalISO8661Format(f.Date.Between(DateTime.Now.AddYears(-1), DateTime.Now.AddYears(1))); + var c2 = f.Lorem.Sentence(); + var c3 = f.Random.Int(1, 99999999); + var c4 = f.Random.Bool().ToString().ToLowerInvariant(); + var c5 = f.Random.Decimal(); + */ + + //FETCH DATALIST + ApiResponse a = await Util.PostAsync($"data-list", await Util.GetTokenAsync("superuser", "l3tm3in"), Util.BuildDataListRequestEx(dListView)); + + Util.ValidateDataReturnResponseOk(a); + Util.ValidateHTTPStatusCode(a, 200); + + //assert aAll contains at least three records + ((JArray)a.ObjectResponse["data"]).Count.Should().BeGreaterThan(0); + + //ensure first row contains all columns requested in listview + ((JArray)a.ObjectResponse["data"][0]).Count.Should().Be(9); + + //sb a total record count greater than 3 + ((JValue)a.ObjectResponse["totalRecordCount"]).Value().Should().BeGreaterThan(3); + //sb a column header collection greater than 3 + ((JArray)a.ObjectResponse["columns"]).Count.Should().BeGreaterThan(3); + + } + + /* + "{\"data\":[[{\"v\":276},{\"v\":276},{\"v\":2.22},{\"v\":null},{\"v\":1}],[{\"v\":272},{\"v\":272},{\"v\":1.11},{\"v\":null},{\"v\":1}],[{\"v\":270},{\"v\":270},{\"v\":1.11},{\"v\":null},{\"v\":1}],[{\"v\":265},{\"v\":265},{\"v\":1.11},{\"v\":null},{\"v\":1}],[{\"v\":263},{\"v\":263},{\"v\":1.11},{\"v\":null},{\"v\":1}],[{\"v\":259},{\"v\":259},{\"v\":1.11},{\"v\":null},{\"v\":1}],[{\"v\":252},{\"v\":252},{\"v\":1.11},{\"v\":null},{\"v\":1}],[{\"v\":249},{\"v\":249},{\"v\":1.11},{\"v\":null},{\"v\":1}],[{\"v\":248},{\"v\":248},{\"v\":1.11},{\"v\":null},{\"v\":1}],[{\"v\":247},{\"v\":247},{\"v\":1.11},{\"v\":null},{\"v\":1}],[{\"v\":246},{\"v\":246},{\"v\":1.11},{\"v\":null},{\"v\":1}],[{\"v\":242},{\"v\":242},{\"v\":2.22},{\"v\":null},{\"v\":1}],[{\"v\":238},{\"v\":238},{\"v\":1.11},{\"v\":null},{\"v\":1}],[{\"v\":147},{\"v\":147},{\"v\":1.11},{\"v\":null},{\"v\":1}],[{\"v\":144},{\"v\":144},{\"v\":1.11},{\"v\":null},{\"v\":1}],[{\"v\":135},{\"v\":135},{\"v\":1.11},{\"v\":null},{\"v\":1}],[{\"v\":134},{\"v\":134},{\"v\":1.11},{\"v\":null},{\"v\":1}],[{\"v\":133},{\"v\":133},{\"v\":2.22},{\"v\":null},{\"v\":1}],[{\"v\":129},{\"v\":130},{\"v\":1.11},{\"v\":null},{\"v\":1}],[{\"v\":122},{\"v\":122},{\"v\":1.11},{\"v\":null},{\"v\":1}],[{\"v\":120},{\"v\":121},{\"v\":1.11},{\"v\":null},{\"v\":1}],[{\"v\":119},{\"v\":119},{\"v\":1.11},{\"v\":null},{\"v\":1}],[{\"v\":113},{\"v\":113},{\"v\":1.11},{\"v\":null},{\"v\":1}],[{\"v\":108},{\"v\":108},{\"v\":1.11},{\"v\":null},{\"v\":1}],[{\"v\":105},{\"v\":105},{\"v\":1.11},{\"v\":null},{\"v\":1}],[{\"v\":103},{\"v\":103},{\"v\":2.22},{\"v\":null},{\"v\":1}],[{\"v\":100},{\"v\":100},{\"v\":618.17},{\"v\":null},{\"v\":1}],[{\"v\":99},{\"v\":99},{\"v\":885.48},{\"v\":null},{\"v\":6}],[{\"v\":98},{\"v\":98},{\"v\":794.97},{\"v\":null},{\"v\":5}],[{\"v\":97},{\"v\":97},{\"v\":999.02},{\"v\":null},{\"v\":5}],[{\"v\":96},{\"v\":96},{\"v\":958.63},{\"v\":null},{\"v\":1}],[{\"v\":95},{\"v\":95},{\"v\":270.99},{\"v\":null},{\"v\":7}],[{\"v\":94},{\"v\":94},{\"v\":505.75},{\"v\":null},{\"v\":2}],[{\"v\":93},{\"v\":93},{\"v\":704.93},{\"v\":null},{\"v\":7}],[{\"v\":92},{\"v\":92},{\"v\":637.32},{\"v\":null},{\"v\":2}],[{\"v\":91},{\"v\":91},{\"v\":780.54},{\"v\":null},{\"v\":4}],[{\"v\":90},{\"v\":90},{\"v\":834.7},{\"v\":null},{\"v\":3}],[{\"v\":89},{\"v\":89},{\"v\":663.87},{\"v\":null},{\"v\":5}],[{\"v\":88},{\"v\":88},{\"v\":104.97},{\"v\":null},{\"v\":1}],[{\"v\":87},{\"v\":87},{\"v\":519.91},{\"v\":null},{\"v\":3}],[{\"v\":86},{\"v\":86},{\"v\":725.35},{\"v\":null},{\"v\":1}],[{\"v\":85},{\"v\":85},{\"v\":346.63},{\"v\":null},{\"v\":4}],[{\"v\":84},{\"v\":84},{\"v\":750.63},{\"v\":null},{\"v\":3}],[{\"v\":83},{\"v\":83},{\"v\":69.88},{\"v\":null},{\"v\":1}],[{\"v\":82},{\"v\":82},{\"v\":723.35},{\"v\":null},{\"v\":2}],[{\"v\":81},{\"v\":81},{\"v\":643.24},{\"v\":null},{\"v\":2}],[{\"v\":80},{\"v\":80},{\"v\":482.79},{\"v\":null},{\"v\":2}],[{\"v\":79},{\"v\":79},{\"v\":37.92},{\"v\":null},{\"v\":5}],[{\"v\":78},{\"v\":78},{\"v\":423.83},{\"v\":null},{\"v\":6}],[{\"v\":77},{\"v\":77},{\"v\":37.08},{\"v\":null},{\"v\":4}],[{\"v\":76},{\"v\":76},{\"v\":226.49},{\"v\":null},{\"v\":4}],[{\"v\":75},{\"v\":75},{\"v\":523.93},{\"v\":null},{\"v\":5}],[{\"v\":74},{\"v\":74},{\"v\":899.03},{\"v\":null},{\"v\":7}],[{\"v\":73},{\"v\":73},{\"v\":222.86},{\"v\":null},{\"v\":3}],[{\"v\":72},{\"v\":72},{\"v\":881.09},{\"v\":null},{\"v\":3}],[{\"v\":71},{\"v\":71},{\"v\":75.91},{\"v\":null},{\"v\":3}],[{\"v\":70},{\"v\":70},{\"v\":592.48},{\"v\":null},{\"v\":7}],[{\"v\":69},{\"v\":69},{\"v\":723.12},{\"v\":null},{\"v\":7}],[{\"v\":68},{\"v\":68},{\"v\":912.26},{\"v\":null},{\"v\":7}],[{\"v\":67},{\"v\":67},{\"v\":93.87},{\"v\":null},{\"v\":6}],[{\"v\":66},{\"v\":66},{\"v\":613.15},{\"v\":null},{\"v\":5}],[{\"v\":65},{\"v\":65},{\"v\":713.82},{\"v\":null},{\"v\":7}],[{\"v\":64},{\"v\":64},{\"v\":526.5},{\"v\":null},{\"v\":1}],[{\"v\":63},{\"v\":63},{\"v\":585.31},{\"v\":null},{\"v\":4}],[{\"v\":62},{\"v\":62},{\"v\":441.5},{\"v\":null},{\"v\":2}],[{\"v\":61},{\"v\":61},{\"v\":717.32},{\"v\":null},{\"v\":1}],[{\"v\":60},{\"v\":60},{\"v\":558.3},{\"v\":null},{\"v\":6}],[{\"v\":59},{\"v\":59},{\"v\":65.28},{\"v\":null},{\"v\":5}],[{\"v\":58},{\"v\":58},{\"v\":707.71},{\"v\":null},{\"v\":5}],[{\"v\":57},{\"v\":57},{\"v\":963.73},{\"v\":null},{\"v\":7}],[{\"v\":56},{\"v\":56},{\"v\":591.21},{\"v\":null},{\"v\":2}],[{\"v\":55},{\"v\":55},{\"v\":551.17},{\"v\":null},{\"v\":3}],[{\"v\":54},{\"v\":54},{\"v\":146.21},{\"v\":null},{\"v\":1}],[{\"v\":53},{\"v\":53},{\"v\":258.66},{\"v\":null},{\"v\":5}],[{\"v\":52},{\"v\":52},{\"v\":623.71},{\"v\":null},{\"v\":3}],[{\"v\":51},{\"v\":51},{\"v\":352.75},{\"v\":null},{\"v\":2}],[{\"v\":50},{\"v\":50},{\"v\":224.18},{\"v\":null},{\"v\":5}],[{\"v\":49},{\"v\":49},{\"v\":667.09},{\"v\":null},{\"v\":7}],[{\"v\":48},{\"v\":48},{\"v\":676.25},{\"v\":null},{\"v\":6}],[{\"v\":47},{\"v\":47},{\"v\":498.2},{\"v\":null},{\"v\":2}],[{\"v\":46},{\"v\":46},{\"v\":999.28},{\"v\":null},{\"v\":3}],[{\"v\":45},{\"v\":45},{\"v\":262.86},{\"v\":null},{\"v\":5}],[{\"v\":44},{\"v\":44},{\"v\":556.43},{\"v\":null},{\"v\":5}],[{\"v\":43},{\"v\":43},{\"v\":768.96},{\"v\":null},{\"v\":6}],[{\"v\":42},{\"v\":42},{\"v\":427.17},{\"v\":null},{\"v\":1}],[{\"v\":41},{\"v\":41},{\"v\":118.47},{\"v\":null},{\"v\":3}],[{\"v\":40},{\"v\":40},{\"v\":539.87},{\"v\":null},{\"v\":7}],[{\"v\":39},{\"v\":39},{\"v\":37.45},{\"v\":null},{\"v\":7}],[{\"v\":38},{\"v\":38},{\"v\":967.69},{\"v\":null},{\"v\":5}],[{\"v\":37},{\"v\":37},{\"v\":3.46},{\"v\":null},{\"v\":7}],[{\"v\":36},{\"v\":36},{\"v\":483.42},{\"v\":null},{\"v\":3}],[{\"v\":35},{\"v\":35},{\"v\":548.64},{\"v\":null},{\"v\":5}],[{\"v\":34},{\"v\":34},{\"v\":74.34},{\"v\":null},{\"v\":7}],[{\"v\":33},{\"v\":33},{\"v\":506.67},{\"v\":null},{\"v\":2}],[{\"v\":32},{\"v\":32},{\"v\":823.07},{\"v\":null},{\"v\":1}],[{\"v\":31},{\"v\":31},{\"v\":983.09},{\"v\":null},{\"v\":4}],[{\"v\":30},{\"v\":30},{\"v\":25.46},{\"v\":null},{\"v\":5}],[{\"v\":29},{\"v\":29},{\"v\":717.39},{\"v\":null},{\"v\":7}],[{\"v\":28},{\"v\":28},{\"v\":874.1},{\"v\":null},{\"v\":1}],[{\"v\":27},{\"v\":27},{\"v\":529.19},{\"v\":null},{\"v\":1}],[{\"v\":26},{\"v\":26},{\"v\":851.66},{\"v\":null},{\"v\":3}],[{\"v\":25},{\"v\":25},{\"v\":127.14},{\"v\":null},{\"v\":5}],[{\"v\":24},{\"v\":24},{\"v\":985.65},{\"v\":null},{\"v\":2}],[{\"v\":23},{\"v\":23},{\"v\":507.75},{\"v\":null},{\"v\":4}],[{\"v\":22},{\"v\":22},{\"v\":949.86},{\"v\":null},{\"v\":2}],[{\"v\":21},{\"v\":21},{\"v\":862.96},{\"v\":null},{\"v\":4}],[{\"v\":20},{\"v\":20},{\"v\":189.26},{\"v\":null},{\"v\":7}],[{\"v\":19},{\"v\":19},{\"v\":489.77},{\"v\":null},{\"v\":6}],[{\"v\":18},{\"v\":18},{\"v\":233.59},{\"v\":null},{\"v\":3}],[{\"v\":17},{\"v\":17},{\"v\":260.98},{\"v\":null},{\"v\":7}],[{\"v\":16},{\"v\":16},{\"v\":478.33},{\"v\":null},{\"v\":2}],[{\"v\":15},{\"v\":15},{\"v\":87.56},{\"v\":null},{\"v\":3}],[{\"v\":14},{\"v\":14},{\"v\":86.51},{\"v\":null},{\"v\":4}],[{\"v\":13},{\"v\":13},{\"v\":702.71},{\"v\":null},{\"v\":7}],[{\"v\":12},{\"v\":12},{\"v\":635.24},{\"v\":null},{\"v\":7}],[{\"v\":11},{\"v\":11},{\"v\":84.4},{\"v\":null},{\"v\":5}],[{\"v\":10},{\"v\":10},{\"v\":213.61},{\"v\":null},{\"v\":3}],[{\"v\":9},{\"v\":9},{\"v\":745.44},{\"v\":null},{\"v\":6}],[{\"v\":8},{\"v\":8},{\"v\":796.05},{\"v\":null},{\"v\":3}],[{\"v\":7},{\"v\":7},{\"v\":341.13},{\"v\":null},{\"v\":2}],[{\"v\":6},{\"v\":6},{\"v\":252.86},{\"v\":null},{\"v\":1}],[{\"v\":5},{\"v\":5},{\"v\":40.62},{\"v\":null},{\"v\":1}],[{\"v\":4},{\"v\":4},{\"v\":86.94},{\"v\":null},{\"v\":3}],[{\"v\":3},{\"v\":3},{\"v\":551.06},{\"v\":null},{\"v\":6}],[{\"v\":2},{\"v\":2},{\"v\":137.74},{\"v\":null},{\"v\":3}],[{\"v\":1},{\"v\":1},{\"v\":870.43},{\"v\":null},{\"v\":4}]],\"totalRecordCount\":126,\"columns\":[{\"cm\":\"df\",\"dt\":0,\"ay\":2},{\"cm\":\"WidgetSerial\",\"dt\":5},{\"cm\":\"WidgetDollarAmount\",\"dt\":8},{\"cm\":\"WidgetCount\",\"dt\":5},{\"cm\":\"WidgetUserType\",\"dt\":10,\"et\":\"UserType\"}]}" + */ + //================================================== + + }//eoc +}//eons diff --git a/DataList/DataListRights.cs b/DataList/DataListRights.cs index bf8053b..5918275 100644 --- a/DataList/DataListRights.cs +++ b/DataList/DataListRights.cs @@ -1,30 +1,30 @@ -using Xunit; -using Newtonsoft.Json.Linq; -using FluentAssertions; - -namespace raven_integration -{ - - public class DataListRights - { - - - /// - /// - /// - [Fact] - public async void InsufficentRightsShouldNotRetrieve() - { - //Get without rights - /* - "{\"error\":{\"code\":\"2004\",\"message\":\"User not authorized for this resource operation (insufficient rights)\"}}" - */ - //ApiResponse a = await Util.GetAsync("data-list/list?DataListKey=TestWidgetDataList&Offset=0&Limit=3", await Util.GetTokenAsync("CustomerLimited")); - ApiResponse a = await Util.PostAsync($"data-list", await Util.GetTokenAsync("CustomerLimited"), Util.BuildDataListRequestEx()); - Util.ValidateErrorCodeResponse(a, 2004, 403); - } - - //================================================== - - }//eoc -}//eons +using Xunit; +using Newtonsoft.Json.Linq; +using FluentAssertions; + +namespace raven_integration +{ + + public class DataListRights + { + + + /// + /// + /// + [Fact] + public async Task InsufficentRightsShouldNotRetrieve() + { + //Get without rights + /* + "{\"error\":{\"code\":\"2004\",\"message\":\"User not authorized for this resource operation (insufficient rights)\"}}" + */ + //ApiResponse a = await Util.GetAsync("data-list/list?DataListKey=TestWidgetDataList&Offset=0&Limit=3", await Util.GetTokenAsync("CustomerLimited")); + ApiResponse a = await Util.PostAsync($"data-list", await Util.GetTokenAsync("CustomerLimited"), Util.BuildDataListRequestEx()); + Util.ValidateErrorCodeResponse(a, 2004, 403); + } + + //================================================== + + }//eoc +}//eons diff --git a/DataList/DataListSorting.cs b/DataList/DataListSorting.cs index e8c556c..b0d8f27 100644 --- a/DataList/DataListSorting.cs +++ b/DataList/DataListSorting.cs @@ -1,413 +1,413 @@ -using System; -using Xunit; -using Newtonsoft.Json.Linq; -using FluentAssertions; -using System.Collections.Generic; -using System.Collections.Concurrent; - -namespace raven_integration -{ - - - public class DataListSorting - { - - /// - /// - /// - [Fact] - public async void DefaultSortByIdWorks() - { - - var WidgetNameStart = Util.Uniquify("DefaultSortByIdWorks"); - - //CREATE 3 TEST WIDGETS TO TEST ORDER - long FirstInOrderWidgetId = 0; - long SecondInOrderWidgetId = 0; - long ThirdInOrderWidgetId = 0; - - dynamic w = new JObject(); - w.name = Util.Uniquify(WidgetNameStart); - w.customFields = Util.WidgetRequiredCustomFieldsJsonString(); - w.notes = "blah"; - w.usertype = 1; - ApiResponse a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w.ToString()); - Util.ValidateDataReturnResponseOk(a); - ThirdInOrderWidgetId = a.ObjectResponse["data"]["id"].Value(); - - w = new JObject(); - w.name = Util.Uniquify(WidgetNameStart); - w.customFields = Util.WidgetRequiredCustomFieldsJsonString(); - w.notes = "blah"; - w.usertype = 1; - a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w.ToString()); - Util.ValidateDataReturnResponseOk(a); - SecondInOrderWidgetId = a.ObjectResponse["data"]["id"].Value(); - - w = new JObject(); - w.name = Util.Uniquify(WidgetNameStart); - w.customFields = Util.WidgetRequiredCustomFieldsJsonString(); - w.notes = "blah"; - w.usertype = 1; - a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w.ToString()); - Util.ValidateDataReturnResponseOk(a); - FirstInOrderWidgetId = a.ObjectResponse["data"]["id"].Value(); - - - //CREATE FILTER - - dynamic dListView = new JArray(); - - - //name starts with filter to constrict to widgets that this test block created only - - dListView.Add(Util.BuildSimpleFilterDataListViewColumn("widgetname", Util.OpStartsWith, WidgetNameStart)); - - //NOW FETCH WIDGET LIST WITH FILTER - // a = await Util.GetAsync($"data-list/list?DataListKey=TestWidgetDataList&Offset=0&Limit=999&DataFilterId={DataFilterId.ToString()}", await Util.GetTokenAsync("superuser", "l3tm3in")); - a = await Util.PostAsync($"data-list", await Util.GetTokenAsync("superuser", "l3tm3in"), Util.BuildDataListRequestEx(dListView)); - Util.ValidateDataReturnResponseOk(a); - Util.ValidateHTTPStatusCode(a, 200); - - //assert contains exactly 3 records - ((JArray)a.ObjectResponse["data"]).Count.Should().Be(3); - - //assert the order returned - a.ObjectResponse["data"][0][0]["i"].Value().Should().Be(FirstInOrderWidgetId); - a.ObjectResponse["data"][1][0]["i"].Value().Should().Be(SecondInOrderWidgetId); - a.ObjectResponse["data"][2][0]["i"].Value().Should().Be(ThirdInOrderWidgetId); - - - a = await Util.DeleteAsync("widget/" + FirstInOrderWidgetId.ToString(), await Util.GetTokenAsync("superuser", "l3tm3in")); - Util.ValidateHTTPStatusCode(a, 204); - - a = await Util.DeleteAsync("widget/" + SecondInOrderWidgetId.ToString(), await Util.GetTokenAsync("superuser", "l3tm3in")); - Util.ValidateHTTPStatusCode(a, 204); - - a = await Util.DeleteAsync("widget/" + ThirdInOrderWidgetId.ToString(), await Util.GetTokenAsync("superuser", "l3tm3in")); - Util.ValidateHTTPStatusCode(a, 204); - } - - - - /// - /// - /// - [Fact] - public async void SortByFieldAscendingWorks() - { - - var WidgetNameStart = Util.Uniquify("SortByFieldAscendingWorks"); - - //CREATE 3 TEST WIDGETS TO TEST ORDER - long FirstInOrderWidgetId = 0; - long SecondInOrderWidgetId = 0; - long ThirdInOrderWidgetId = 0; - - dynamic w = new JObject(); - w.name = Util.Uniquify(WidgetNameStart); - w.customFields = Util.WidgetRequiredCustomFieldsJsonString(); - w.notes = "blah"; - w.startDate = DateTime.Now; - w.endDate = DateTime.Now.AddHours(1); - w.usertype = 1; - - ApiResponse a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w.ToString()); - Util.ValidateDataReturnResponseOk(a); - FirstInOrderWidgetId = a.ObjectResponse["data"]["id"].Value(); - - w = new JObject(); - w.name = Util.Uniquify(WidgetNameStart); - w.customFields = Util.WidgetRequiredCustomFieldsJsonString(); - w.notes = "blah"; - w.startDate = DateTime.Now.AddHours(1); - w.endDate = DateTime.Now.AddHours(2); - w.usertype = 1; - a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w.ToString()); - Util.ValidateDataReturnResponseOk(a); - SecondInOrderWidgetId = a.ObjectResponse["data"]["id"].Value(); - - w = new JObject(); - w.name = Util.Uniquify(WidgetNameStart); - w.customFields = Util.WidgetRequiredCustomFieldsJsonString(); - w.notes = "blah"; - w.startDate = DateTime.Now.AddHours(2); - w.endDate = DateTime.Now.AddHours(3); - w.usertype = 1; - a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w.ToString()); - Util.ValidateDataReturnResponseOk(a); - ThirdInOrderWidgetId = a.ObjectResponse["data"]["id"].Value(); - - - //CREATE FILTER - //FILTER IN BY NAME FOR TESTING THIS RUN ONLY - dynamic dListView = new JArray(); - //name starts with filter to constrict to widgets that this test block created only - - - //SORT ORDER ################### - // dynamic dsortarray = new JArray(); - // dynamic dsort = new JObject(); - // dsort.fld = "widgetstartdate"; - // dsort.dir = "+"; - // dsortarray.Add(dsort); - - //both conditions filter and sort here - dListView.Add(Util.BuildSimpleFilterDataListViewColumn("widgetname", Util.OpStartsWith, WidgetNameStart, "+")); - - - - //NOW FETCH WIDGET LIST WITH FILTER - a = await Util.PostAsync($"data-list", await Util.GetTokenAsync("superuser", "l3tm3in"), Util.BuildDataListRequestEx(dListView)); - Util.ValidateDataReturnResponseOk(a); - Util.ValidateHTTPStatusCode(a, 200); - - //assert contains exactly 3 records - ((JArray)a.ObjectResponse["data"]).Count.Should().Be(3); - - //assert the order returned - a.ObjectResponse["data"][0][0]["i"].Value().Should().Be(FirstInOrderWidgetId); - a.ObjectResponse["data"][1][0]["i"].Value().Should().Be(SecondInOrderWidgetId); - a.ObjectResponse["data"][2][0]["i"].Value().Should().Be(ThirdInOrderWidgetId); - - - a = await Util.DeleteAsync("widget/" + FirstInOrderWidgetId.ToString(), await Util.GetTokenAsync("superuser", "l3tm3in")); - Util.ValidateHTTPStatusCode(a, 204); - - a = await Util.DeleteAsync("widget/" + SecondInOrderWidgetId.ToString(), await Util.GetTokenAsync("superuser", "l3tm3in")); - Util.ValidateHTTPStatusCode(a, 204); - - a = await Util.DeleteAsync("widget/" + ThirdInOrderWidgetId.ToString(), await Util.GetTokenAsync("superuser", "l3tm3in")); - Util.ValidateHTTPStatusCode(a, 204); - - } - - - - /// - /// - /// - [Fact] - public async void SortByFieldDescendingWorks() - { - - var WidgetNameStart = Util.Uniquify("SortByFieldDescendingWorks"); - - //CREATE 3 TEST WIDGETS TO TEST ORDER - long FirstInOrderWidgetId = 0; - long SecondInOrderWidgetId = 0; - long ThirdInOrderWidgetId = 0; - - dynamic w = new JObject(); - w.name = Util.Uniquify(WidgetNameStart); - w.customFields = Util.WidgetRequiredCustomFieldsJsonString(); - w.notes = "blah"; - w.count = 999; - w.usertype = 1; - - ApiResponse a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w.ToString()); - Util.ValidateDataReturnResponseOk(a); - FirstInOrderWidgetId = a.ObjectResponse["data"]["id"].Value(); - - w = new JObject(); - w.name = Util.Uniquify(WidgetNameStart); - w.customFields = Util.WidgetRequiredCustomFieldsJsonString(); - w.notes = "blah"; - w.count = 665; - w.usertype = 1; - a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w.ToString()); - Util.ValidateDataReturnResponseOk(a); - SecondInOrderWidgetId = a.ObjectResponse["data"]["id"].Value(); - - w = new JObject(); - w.name = Util.Uniquify(WidgetNameStart); - w.customFields = Util.WidgetRequiredCustomFieldsJsonString(); - w.notes = "blah"; - w.count = 333; - w.usertype = 1; - a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w.ToString()); - Util.ValidateDataReturnResponseOk(a); - ThirdInOrderWidgetId = a.ObjectResponse["data"]["id"].Value(); - - - //CREATE FILTER - - //FILTER IN BY NAME FOR TESTING THIS RUN ONLY - dynamic dListView = new JArray(); - //name starts with filter to constrict to widgets that this test block created only - - dListView.Add(Util.BuildSimpleFilterDataListViewColumn("widgetname", Util.OpStartsWith, WidgetNameStart)); - - - //SORT ORDER ################### - // dynamic dsortarray = new JArray(); - // dynamic dsort = new JObject(); - // dsort.fld = "widgetcount"; - // dsort.dir = "-"; - dListView.Add(Util.BuildSimpleSortDataListViewColumn("widgetcount", "-")); - - //NOW FETCH WIDGET LIST WITH FILTER - a = await Util.PostAsync($"data-list", await Util.GetTokenAsync("superuser", "l3tm3in"), Util.BuildDataListRequestEx(dListView)); - Util.ValidateDataReturnResponseOk(a); - Util.ValidateHTTPStatusCode(a, 200); - - //assert contains exactly 3 records - ((JArray)a.ObjectResponse["data"]).Count.Should().Be(3); - - //assert the order returned - a.ObjectResponse["data"][0][0]["i"].Value().Should().Be(FirstInOrderWidgetId); - a.ObjectResponse["data"][1][0]["i"].Value().Should().Be(SecondInOrderWidgetId); - a.ObjectResponse["data"][2][0]["i"].Value().Should().Be(ThirdInOrderWidgetId); - - - a = await Util.DeleteAsync("widget/" + FirstInOrderWidgetId.ToString(), await Util.GetTokenAsync("superuser", "l3tm3in")); - Util.ValidateHTTPStatusCode(a, 204); - - a = await Util.DeleteAsync("widget/" + SecondInOrderWidgetId.ToString(), await Util.GetTokenAsync("superuser", "l3tm3in")); - Util.ValidateHTTPStatusCode(a, 204); - - a = await Util.DeleteAsync("widget/" + ThirdInOrderWidgetId.ToString(), await Util.GetTokenAsync("superuser", "l3tm3in")); - Util.ValidateHTTPStatusCode(a, 204); - - } - - - - - - /// - /// - /// - [Fact] - public async void SortByMultipleFieldsWorks() - { - /* - - Created order: - dollaramount, count - 2,1 - 1,2 - 2,2 - 1,1 - - - sorted order: - dollar asc, count desc - 1,2 - 1,1 - 2,2 - 2,1 - - */ - var WidgetNameStart = Util.Uniquify("SortByMultipleFieldsWorks"); - - //CREATE 4 TEST WIDGETS TO TEST ORDER - long FirstInOrderWidgetId = 0; - long SecondInOrderWidgetId = 0; - long ThirdInOrderWidgetId = 0; - long FourthInOrderWidgetId = 0; - - dynamic w = new JObject(); - w.name = Util.Uniquify(WidgetNameStart); - w.customFields = Util.WidgetRequiredCustomFieldsJsonString(); - w.notes = "blah"; - w.dollaramount = 2.22; - w.count = 1; - w.usertype = 1; - - ApiResponse a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w.ToString()); - Util.ValidateDataReturnResponseOk(a); - FourthInOrderWidgetId = a.ObjectResponse["data"]["id"].Value(); - - w = new JObject(); - w.name = Util.Uniquify(WidgetNameStart); - w.customFields = Util.WidgetRequiredCustomFieldsJsonString(); - w.notes = "blah"; - w.dollaramount = 1.11; - w.count = 2; - w.usertype = 1; - a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w.ToString()); - Util.ValidateDataReturnResponseOk(a); - FirstInOrderWidgetId = a.ObjectResponse["data"]["id"].Value(); - - w = new JObject(); - w.name = Util.Uniquify(WidgetNameStart); - w.customFields = Util.WidgetRequiredCustomFieldsJsonString(); - w.notes = "blah"; - w.dollaramount = 1.11; - w.count = 1; - w.usertype = 1; - a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w.ToString()); - Util.ValidateDataReturnResponseOk(a); - SecondInOrderWidgetId = a.ObjectResponse["data"]["id"].Value(); - - w = new JObject(); - w.name = Util.Uniquify(WidgetNameStart); - w.customFields = Util.WidgetRequiredCustomFieldsJsonString(); - w.notes = "blah"; - w.dollaramount = 2.22; - w.count = 2; - w.usertype = 1; - a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w.ToString()); - Util.ValidateDataReturnResponseOk(a); - ThirdInOrderWidgetId = a.ObjectResponse["data"]["id"].Value(); - - - //CREATE FILTER - - //FILTER IN BY NAME FOR TESTING THIS RUN ONLY - dynamic dListView = new JArray(); - //name starts with filter to constrict to widgets that this test block created only - dListView.Add(Util.BuildSimpleFilterDataListViewColumn("widgetname", Util.OpStartsWith, WidgetNameStart)); - - //SORT ORDER ################### - // dynamic dsortarray = new JArray(); - - //First column - // dynamic dsort1 = new JObject(); - // dsort1.fld = "widgetdollaramount"; - // dsort1.dir = "+"; - // dsortarray.Add(dsort1); - dListView.Add(Util.BuildSimpleSortDataListViewColumn("widgetdollaramount", "+")); - - //Second column - // dynamic dsort2 = new JObject(); - // dsort2.fld = "widgetcount"; - // dsort2.dir = "-"; - // dsortarray.Add(dsort2); - dListView.Add(Util.BuildSimpleSortDataListViewColumn("widgetcount", "-")); - - - //NOW FETCH WIDGET LIST WITH FILTER - a = await Util.PostAsync($"data-list", await Util.GetTokenAsync("superuser", "l3tm3in"), Util.BuildDataListRequestEx(dListView)); - Util.ValidateDataReturnResponseOk(a); - Util.ValidateHTTPStatusCode(a, 200); - - //assert contains exactly 3 records - ((JArray)a.ObjectResponse["data"]).Count.Should().Be(4); - - //assert the order returned - a.ObjectResponse["data"][0][0]["i"].Value().Should().Be(FirstInOrderWidgetId); - a.ObjectResponse["data"][1][0]["i"].Value().Should().Be(SecondInOrderWidgetId); - a.ObjectResponse["data"][2][0]["i"].Value().Should().Be(ThirdInOrderWidgetId); - a.ObjectResponse["data"][3][0]["i"].Value().Should().Be(FourthInOrderWidgetId); - - - a = await Util.DeleteAsync("widget/" + FirstInOrderWidgetId.ToString(), await Util.GetTokenAsync("superuser", "l3tm3in")); - Util.ValidateHTTPStatusCode(a, 204); - - a = await Util.DeleteAsync("widget/" + SecondInOrderWidgetId.ToString(), await Util.GetTokenAsync("superuser", "l3tm3in")); - Util.ValidateHTTPStatusCode(a, 204); - - a = await Util.DeleteAsync("widget/" + ThirdInOrderWidgetId.ToString(), await Util.GetTokenAsync("superuser", "l3tm3in")); - Util.ValidateHTTPStatusCode(a, 204); - - a = await Util.DeleteAsync("widget/" + FourthInOrderWidgetId.ToString(), await Util.GetTokenAsync("superuser", "l3tm3in")); - Util.ValidateHTTPStatusCode(a, 204); - - } - - //======================================================================== - - }//eoc -}//eons +using System; +using Xunit; +using Newtonsoft.Json.Linq; +using FluentAssertions; +using System.Collections.Generic; +using System.Collections.Concurrent; + +namespace raven_integration +{ + + + public class DataListSorting + { + + /// + /// + /// + [Fact] + public async Task DefaultSortByIdWorks() + { + + var WidgetNameStart = Util.Uniquify("DefaultSortByIdWorks"); + + //CREATE 3 TEST WIDGETS TO TEST ORDER + long FirstInOrderWidgetId = 0; + long SecondInOrderWidgetId = 0; + long ThirdInOrderWidgetId = 0; + + dynamic w = new JObject(); + w.name = Util.Uniquify(WidgetNameStart); + w.customFields = Util.WidgetRequiredCustomFieldsJsonString(); + w.notes = "blah"; + w.usertype = 1; + ApiResponse a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w.ToString()); + Util.ValidateDataReturnResponseOk(a); + ThirdInOrderWidgetId = a.ObjectResponse["data"]["id"].Value(); + + w = new JObject(); + w.name = Util.Uniquify(WidgetNameStart); + w.customFields = Util.WidgetRequiredCustomFieldsJsonString(); + w.notes = "blah"; + w.usertype = 1; + a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w.ToString()); + Util.ValidateDataReturnResponseOk(a); + SecondInOrderWidgetId = a.ObjectResponse["data"]["id"].Value(); + + w = new JObject(); + w.name = Util.Uniquify(WidgetNameStart); + w.customFields = Util.WidgetRequiredCustomFieldsJsonString(); + w.notes = "blah"; + w.usertype = 1; + a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w.ToString()); + Util.ValidateDataReturnResponseOk(a); + FirstInOrderWidgetId = a.ObjectResponse["data"]["id"].Value(); + + + //CREATE FILTER + + dynamic dListView = new JArray(); + + + //name starts with filter to constrict to widgets that this test block created only + + dListView.Add(Util.BuildSimpleFilterDataListViewColumn("widgetname", Util.OpStartsWith, WidgetNameStart)); + + //NOW FETCH WIDGET LIST WITH FILTER + // a = await Util.GetAsync($"data-list/list?DataListKey=TestWidgetDataList&Offset=0&Limit=999&DataFilterId={DataFilterId.ToString()}", await Util.GetTokenAsync("superuser", "l3tm3in")); + a = await Util.PostAsync($"data-list", await Util.GetTokenAsync("superuser", "l3tm3in"), Util.BuildDataListRequestEx(dListView)); + Util.ValidateDataReturnResponseOk(a); + Util.ValidateHTTPStatusCode(a, 200); + + //assert contains exactly 3 records + ((JArray)a.ObjectResponse["data"]).Count.Should().Be(3); + + //assert the order returned + a.ObjectResponse["data"][0][0]["i"].Value().Should().Be(FirstInOrderWidgetId); + a.ObjectResponse["data"][1][0]["i"].Value().Should().Be(SecondInOrderWidgetId); + a.ObjectResponse["data"][2][0]["i"].Value().Should().Be(ThirdInOrderWidgetId); + + + a = await Util.DeleteAsync("widget/" + FirstInOrderWidgetId.ToString(), await Util.GetTokenAsync("superuser", "l3tm3in")); + Util.ValidateHTTPStatusCode(a, 204); + + a = await Util.DeleteAsync("widget/" + SecondInOrderWidgetId.ToString(), await Util.GetTokenAsync("superuser", "l3tm3in")); + Util.ValidateHTTPStatusCode(a, 204); + + a = await Util.DeleteAsync("widget/" + ThirdInOrderWidgetId.ToString(), await Util.GetTokenAsync("superuser", "l3tm3in")); + Util.ValidateHTTPStatusCode(a, 204); + } + + + + /// + /// + /// + [Fact] + public async Task SortByFieldAscendingWorks() + { + + var WidgetNameStart = Util.Uniquify("SortByFieldAscendingWorks"); + + //CREATE 3 TEST WIDGETS TO TEST ORDER + long FirstInOrderWidgetId = 0; + long SecondInOrderWidgetId = 0; + long ThirdInOrderWidgetId = 0; + + dynamic w = new JObject(); + w.name = Util.Uniquify(WidgetNameStart); + w.customFields = Util.WidgetRequiredCustomFieldsJsonString(); + w.notes = "blah"; + w.startDate = DateTime.Now; + w.endDate = DateTime.Now.AddHours(1); + w.usertype = 1; + + ApiResponse a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w.ToString()); + Util.ValidateDataReturnResponseOk(a); + FirstInOrderWidgetId = a.ObjectResponse["data"]["id"].Value(); + + w = new JObject(); + w.name = Util.Uniquify(WidgetNameStart); + w.customFields = Util.WidgetRequiredCustomFieldsJsonString(); + w.notes = "blah"; + w.startDate = DateTime.Now.AddHours(1); + w.endDate = DateTime.Now.AddHours(2); + w.usertype = 1; + a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w.ToString()); + Util.ValidateDataReturnResponseOk(a); + SecondInOrderWidgetId = a.ObjectResponse["data"]["id"].Value(); + + w = new JObject(); + w.name = Util.Uniquify(WidgetNameStart); + w.customFields = Util.WidgetRequiredCustomFieldsJsonString(); + w.notes = "blah"; + w.startDate = DateTime.Now.AddHours(2); + w.endDate = DateTime.Now.AddHours(3); + w.usertype = 1; + a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w.ToString()); + Util.ValidateDataReturnResponseOk(a); + ThirdInOrderWidgetId = a.ObjectResponse["data"]["id"].Value(); + + + //CREATE FILTER + //FILTER IN BY NAME FOR TESTING THIS RUN ONLY + dynamic dListView = new JArray(); + //name starts with filter to constrict to widgets that this test block created only + + + //SORT ORDER ################### + // dynamic dsortarray = new JArray(); + // dynamic dsort = new JObject(); + // dsort.fld = "widgetstartdate"; + // dsort.dir = "+"; + // dsortarray.Add(dsort); + + //both conditions filter and sort here + dListView.Add(Util.BuildSimpleFilterDataListViewColumn("widgetname", Util.OpStartsWith, WidgetNameStart, "+")); + + + + //NOW FETCH WIDGET LIST WITH FILTER + a = await Util.PostAsync($"data-list", await Util.GetTokenAsync("superuser", "l3tm3in"), Util.BuildDataListRequestEx(dListView)); + Util.ValidateDataReturnResponseOk(a); + Util.ValidateHTTPStatusCode(a, 200); + + //assert contains exactly 3 records + ((JArray)a.ObjectResponse["data"]).Count.Should().Be(3); + + //assert the order returned + a.ObjectResponse["data"][0][0]["i"].Value().Should().Be(FirstInOrderWidgetId); + a.ObjectResponse["data"][1][0]["i"].Value().Should().Be(SecondInOrderWidgetId); + a.ObjectResponse["data"][2][0]["i"].Value().Should().Be(ThirdInOrderWidgetId); + + + a = await Util.DeleteAsync("widget/" + FirstInOrderWidgetId.ToString(), await Util.GetTokenAsync("superuser", "l3tm3in")); + Util.ValidateHTTPStatusCode(a, 204); + + a = await Util.DeleteAsync("widget/" + SecondInOrderWidgetId.ToString(), await Util.GetTokenAsync("superuser", "l3tm3in")); + Util.ValidateHTTPStatusCode(a, 204); + + a = await Util.DeleteAsync("widget/" + ThirdInOrderWidgetId.ToString(), await Util.GetTokenAsync("superuser", "l3tm3in")); + Util.ValidateHTTPStatusCode(a, 204); + + } + + + + /// + /// + /// + [Fact] + public async Task SortByFieldDescendingWorks() + { + + var WidgetNameStart = Util.Uniquify("SortByFieldDescendingWorks"); + + //CREATE 3 TEST WIDGETS TO TEST ORDER + long FirstInOrderWidgetId = 0; + long SecondInOrderWidgetId = 0; + long ThirdInOrderWidgetId = 0; + + dynamic w = new JObject(); + w.name = Util.Uniquify(WidgetNameStart); + w.customFields = Util.WidgetRequiredCustomFieldsJsonString(); + w.notes = "blah"; + w.count = 999; + w.usertype = 1; + + ApiResponse a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w.ToString()); + Util.ValidateDataReturnResponseOk(a); + FirstInOrderWidgetId = a.ObjectResponse["data"]["id"].Value(); + + w = new JObject(); + w.name = Util.Uniquify(WidgetNameStart); + w.customFields = Util.WidgetRequiredCustomFieldsJsonString(); + w.notes = "blah"; + w.count = 665; + w.usertype = 1; + a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w.ToString()); + Util.ValidateDataReturnResponseOk(a); + SecondInOrderWidgetId = a.ObjectResponse["data"]["id"].Value(); + + w = new JObject(); + w.name = Util.Uniquify(WidgetNameStart); + w.customFields = Util.WidgetRequiredCustomFieldsJsonString(); + w.notes = "blah"; + w.count = 333; + w.usertype = 1; + a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w.ToString()); + Util.ValidateDataReturnResponseOk(a); + ThirdInOrderWidgetId = a.ObjectResponse["data"]["id"].Value(); + + + //CREATE FILTER + + //FILTER IN BY NAME FOR TESTING THIS RUN ONLY + dynamic dListView = new JArray(); + //name starts with filter to constrict to widgets that this test block created only + + dListView.Add(Util.BuildSimpleFilterDataListViewColumn("widgetname", Util.OpStartsWith, WidgetNameStart)); + + + //SORT ORDER ################### + // dynamic dsortarray = new JArray(); + // dynamic dsort = new JObject(); + // dsort.fld = "widgetcount"; + // dsort.dir = "-"; + dListView.Add(Util.BuildSimpleSortDataListViewColumn("widgetcount", "-")); + + //NOW FETCH WIDGET LIST WITH FILTER + a = await Util.PostAsync($"data-list", await Util.GetTokenAsync("superuser", "l3tm3in"), Util.BuildDataListRequestEx(dListView)); + Util.ValidateDataReturnResponseOk(a); + Util.ValidateHTTPStatusCode(a, 200); + + //assert contains exactly 3 records + ((JArray)a.ObjectResponse["data"]).Count.Should().Be(3); + + //assert the order returned + a.ObjectResponse["data"][0][0]["i"].Value().Should().Be(FirstInOrderWidgetId); + a.ObjectResponse["data"][1][0]["i"].Value().Should().Be(SecondInOrderWidgetId); + a.ObjectResponse["data"][2][0]["i"].Value().Should().Be(ThirdInOrderWidgetId); + + + a = await Util.DeleteAsync("widget/" + FirstInOrderWidgetId.ToString(), await Util.GetTokenAsync("superuser", "l3tm3in")); + Util.ValidateHTTPStatusCode(a, 204); + + a = await Util.DeleteAsync("widget/" + SecondInOrderWidgetId.ToString(), await Util.GetTokenAsync("superuser", "l3tm3in")); + Util.ValidateHTTPStatusCode(a, 204); + + a = await Util.DeleteAsync("widget/" + ThirdInOrderWidgetId.ToString(), await Util.GetTokenAsync("superuser", "l3tm3in")); + Util.ValidateHTTPStatusCode(a, 204); + + } + + + + + + /// + /// + /// + [Fact] + public async Task SortByMultipleFieldsWorks() + { + /* + + Created order: + dollaramount, count + 2,1 + 1,2 + 2,2 + 1,1 + + + sorted order: + dollar asc, count desc + 1,2 + 1,1 + 2,2 + 2,1 + + */ + var WidgetNameStart = Util.Uniquify("SortByMultipleFieldsWorks"); + + //CREATE 4 TEST WIDGETS TO TEST ORDER + long FirstInOrderWidgetId = 0; + long SecondInOrderWidgetId = 0; + long ThirdInOrderWidgetId = 0; + long FourthInOrderWidgetId = 0; + + dynamic w = new JObject(); + w.name = Util.Uniquify(WidgetNameStart); + w.customFields = Util.WidgetRequiredCustomFieldsJsonString(); + w.notes = "blah"; + w.dollaramount = 2.22; + w.count = 1; + w.usertype = 1; + + ApiResponse a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w.ToString()); + Util.ValidateDataReturnResponseOk(a); + FourthInOrderWidgetId = a.ObjectResponse["data"]["id"].Value(); + + w = new JObject(); + w.name = Util.Uniquify(WidgetNameStart); + w.customFields = Util.WidgetRequiredCustomFieldsJsonString(); + w.notes = "blah"; + w.dollaramount = 1.11; + w.count = 2; + w.usertype = 1; + a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w.ToString()); + Util.ValidateDataReturnResponseOk(a); + FirstInOrderWidgetId = a.ObjectResponse["data"]["id"].Value(); + + w = new JObject(); + w.name = Util.Uniquify(WidgetNameStart); + w.customFields = Util.WidgetRequiredCustomFieldsJsonString(); + w.notes = "blah"; + w.dollaramount = 1.11; + w.count = 1; + w.usertype = 1; + a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w.ToString()); + Util.ValidateDataReturnResponseOk(a); + SecondInOrderWidgetId = a.ObjectResponse["data"]["id"].Value(); + + w = new JObject(); + w.name = Util.Uniquify(WidgetNameStart); + w.customFields = Util.WidgetRequiredCustomFieldsJsonString(); + w.notes = "blah"; + w.dollaramount = 2.22; + w.count = 2; + w.usertype = 1; + a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w.ToString()); + Util.ValidateDataReturnResponseOk(a); + ThirdInOrderWidgetId = a.ObjectResponse["data"]["id"].Value(); + + + //CREATE FILTER + + //FILTER IN BY NAME FOR TESTING THIS RUN ONLY + dynamic dListView = new JArray(); + //name starts with filter to constrict to widgets that this test block created only + dListView.Add(Util.BuildSimpleFilterDataListViewColumn("widgetname", Util.OpStartsWith, WidgetNameStart)); + + //SORT ORDER ################### + // dynamic dsortarray = new JArray(); + + //First column + // dynamic dsort1 = new JObject(); + // dsort1.fld = "widgetdollaramount"; + // dsort1.dir = "+"; + // dsortarray.Add(dsort1); + dListView.Add(Util.BuildSimpleSortDataListViewColumn("widgetdollaramount", "+")); + + //Second column + // dynamic dsort2 = new JObject(); + // dsort2.fld = "widgetcount"; + // dsort2.dir = "-"; + // dsortarray.Add(dsort2); + dListView.Add(Util.BuildSimpleSortDataListViewColumn("widgetcount", "-")); + + + //NOW FETCH WIDGET LIST WITH FILTER + a = await Util.PostAsync($"data-list", await Util.GetTokenAsync("superuser", "l3tm3in"), Util.BuildDataListRequestEx(dListView)); + Util.ValidateDataReturnResponseOk(a); + Util.ValidateHTTPStatusCode(a, 200); + + //assert contains exactly 3 records + ((JArray)a.ObjectResponse["data"]).Count.Should().Be(4); + + //assert the order returned + a.ObjectResponse["data"][0][0]["i"].Value().Should().Be(FirstInOrderWidgetId); + a.ObjectResponse["data"][1][0]["i"].Value().Should().Be(SecondInOrderWidgetId); + a.ObjectResponse["data"][2][0]["i"].Value().Should().Be(ThirdInOrderWidgetId); + a.ObjectResponse["data"][3][0]["i"].Value().Should().Be(FourthInOrderWidgetId); + + + a = await Util.DeleteAsync("widget/" + FirstInOrderWidgetId.ToString(), await Util.GetTokenAsync("superuser", "l3tm3in")); + Util.ValidateHTTPStatusCode(a, 204); + + a = await Util.DeleteAsync("widget/" + SecondInOrderWidgetId.ToString(), await Util.GetTokenAsync("superuser", "l3tm3in")); + Util.ValidateHTTPStatusCode(a, 204); + + a = await Util.DeleteAsync("widget/" + ThirdInOrderWidgetId.ToString(), await Util.GetTokenAsync("superuser", "l3tm3in")); + Util.ValidateHTTPStatusCode(a, 204); + + a = await Util.DeleteAsync("widget/" + FourthInOrderWidgetId.ToString(), await Util.GetTokenAsync("superuser", "l3tm3in")); + Util.ValidateHTTPStatusCode(a, 204); + + } + + //======================================================================== + + }//eoc +}//eons diff --git a/DataList/DataListViewCrud.cs b/DataList/DataListViewCrud.cs index 6e41efd..86d5fa5 100644 --- a/DataList/DataListViewCrud.cs +++ b/DataList/DataListViewCrud.cs @@ -1,202 +1,202 @@ -using System; -using Xunit; -using Newtonsoft.Json.Linq; -using FluentAssertions; -using System.Collections.Generic; -using System.Collections.Concurrent; - -namespace raven_integration -{ - - public class DataListFilterCrud - { - - /// - /// Test all CRUD routes - /// - [Fact] - public async void CRUD() - { - //CREATE - dynamic d = new JObject(); - d.name = Util.Uniquify("Test DataListView"); - - d["public"] = true; - d.listKey="TestWidgetDataList"; - - //"[{fld:"name",op:"!=",value:"Notequaltothis"},{fld:"tags",op:"Eq",value:"[23,456,54]"}] - dynamic dListView = new JArray(); - // dynamic df = new JObject(); - // df.fld = "widgetname"; - // df.op = "%-"; - // df.value = "Generic";//lots of seed widgets start with Generic - // dListView.Add(df); - // d.filter = dListView.ToString();//it expects it to be a json string, not actual json - dListView.Add(Util.BuildSimpleFilterDataListViewColumn("widgetname", Util.OpStartsWith, "Generic")); - d.listView=dListView.ToString(Newtonsoft.Json.Formatting.None); - - ApiResponse a = await Util.PostAsync("data-list-view", await Util.GetTokenAsync("BizAdminFull"), d.ToString(Newtonsoft.Json.Formatting.None)); - Util.ValidateDataReturnResponseOk(a); - - long Id = a.ObjectResponse["data"]["id"].Value(); - - - //RETRIEVE - //Get one - a = await Util.GetAsync("data-list-view/" + Id.ToString(), await Util.GetTokenAsync("BizAdminFull")); - Util.ValidateDataReturnResponseOk(a); - a.ObjectResponse["data"]["name"].Value().Should().StartWith("Test DataListView"); - - //Get as alternate user should work for public filter - a = await Util.GetAsync("data-list-view/" + Id.ToString(), await Util.GetTokenAsync("SubContractorLimited")); - Util.ValidateDataReturnResponseOk(a); - a.ObjectResponse["data"]["name"].Value().Should().StartWith("Test DataListView"); - - - //UPDATE - - //PUT, make private - d["public"] = false; - d.name = Util.Uniquify("Put - Test DataListView (privatized)"); - d.concurrency = a.ObjectResponse["data"]["concurrency"].Value(); - a = await Util.PutAsync("data-list-view/" + Id.ToString(), await Util.GetTokenAsync("BizAdminFull"), d.ToString()); - Util.ValidateHTTPStatusCode(a, 200); - - //check PUT worked - a = await Util.GetAsync("data-list-view/" + Id.ToString(), await Util.GetTokenAsync("BizAdminFull")); - Util.ValidateNoErrorInResponse(a); - a.ObjectResponse["data"]["name"].Value().Should().Be(d.name.ToString()); - - - //FETCH DISALLOWED - //Get as alternate user should fail for private filter - a = await Util.GetAsync("data-list-view/" + Id.ToString(), await Util.GetTokenAsync("SubContractorLimited")); - Util.ValidateResponseNotFound(a); - - // //DELETE - ApiResponse DELETETestResponse = await Util.DeleteAsync("data-list-view/" + Id.ToString(), await Util.GetTokenAsync("BizAdminFull")); - Util.ValidateHTTPStatusCode(DELETETestResponse, 204); - - } - - /// - /// - /// - [Fact] - public async void InvalidListKeyShouldFail() - { - //CREATE - dynamic d = new JObject(); - d.name = Util.Uniquify("Test DataListView"); - - d["public"] = true; - d.listKey = "nonexistant"; - - //"[{fld:"name",op:"!=",value:"Notequaltothis"},{fld:"tags",op:"Eq",value:"[23,456,54]"}] - // dynamic dfilter = new JArray(); - // dynamic df = new JObject(); - // df.fld = "name"; - // df.op = "%-"; - // df.value = "Generic";//lots of seed widgets start with Generic - // dfilter.Add(df); - - // d.filter = dfilter.ToString();//it expects it to be a json string, not actual json - - // ApiResponse a = await Util.PostAsync("data-list-view", await Util.GetTokenAsync("BizAdminFull"), d.ToString()); - - dynamic dListView = new JArray(); - // dynamic df = new JObject(); - // df.fld = "widgetname"; - // df.op = "%-"; - // df.value = "Generic";//lots of seed widgets start with Generic - // dListView.Add(df); - // d.filter = dListView.ToString();//it expects it to be a json string, not actual json - dListView.Add(Util.BuildSimpleFilterDataListViewColumn("widgetname", Util.OpStartsWith, "Generic")); - d.listView=dListView.ToString(Newtonsoft.Json.Formatting.None); - - ApiResponse a = await Util.PostAsync("data-list-view", await Util.GetTokenAsync("BizAdminFull"), d.ToString(Newtonsoft.Json.Formatting.None)); - Util.ValidateErrorCodeResponse(a, 2200, 400); - Util.ShouldContainValidationError(a, "ListKey", "2203"); - - } - - - /// - /// - /// - [Fact] - public async void InvalidFieldNameShouldFail() - { - //CREATE - dynamic d = new JObject(); - d.name = Util.Uniquify("Test DataListView"); - - d["public"] = true; - d.listKey="TestWidgetDataList"; - - //"[{fld:"name",op:"!=",value:"Notequaltothis"},{fld:"tags",op:"Eq",value:"[23,456,54]"}] - // dynamic dfilter = new JArray(); - // dynamic df = new JObject(); - // df.fld = "doesntexist"; - // df.op = "%-"; - // df.value = "Generic";//lots of seed widgets start with Generic - // dfilter.Add(df); - - // d.filter = dfilter.ToString();//it expects it to be a json string, not actual json - - // ApiResponse a = await Util.PostAsync("data-list-view", await Util.GetTokenAsync("BizAdminFull"), d.ToString()); - dynamic dListView = new JArray(); - // dynamic df = new JObject(); - // df.fld = "widgetname"; - // df.op = "%-"; - // df.value = "Generic";//lots of seed widgets start with Generic - // dListView.Add(df); - // d.filter = dListView.ToString();//it expects it to be a json string, not actual json - dListView.Add(Util.BuildSimpleFilterDataListViewColumn("doesntexist", Util.OpStartsWith, "Generic")); - d.listView=dListView.ToString(Newtonsoft.Json.Formatting.None); - - ApiResponse a = await Util.PostAsync("data-list-view", await Util.GetTokenAsync("BizAdminFull"), d.ToString(Newtonsoft.Json.Formatting.None)); - Util.ValidateErrorCodeResponse(a, 2200, 400); - Util.ShouldContainValidationError(a, "ListView", "2203"); - - } - - - -//REMOVED THIS VALIDATION TEST AS SWITCH TO DATALISTVIEW NO LONGER VALIDATES FILTER ANYWAY -//ONLY COLUMN NAMES AND LIST NAME - // /// - // /// - // /// - // [Fact] - // public async void InvalidOperatorShouldFail() - // { - // //CREATE - // dynamic d = new JObject(); - // d.name = Util.Uniquify("Test DataListView"); - - // d["public"] = true; - // d.listKey="TestWidgetDataList"; - - // //"[{fld:"name",op:"!=",value:"Notequaltothis"},{fld:"tags",op:"Eq",value:"[23,456,54]"}] - // dynamic dfilter = new JArray(); - // dynamic df = new JObject(); - // df.fld = "name"; - // df.op = "wtf"; - // df.value = "Generic";//lots of seed widgets start with Generic - // dfilter.Add(df); - - // d.filter = dfilter.ToString();//it expects it to be a json string, not actual json - - // ApiResponse a = await Util.PostAsync("data-list-view", await Util.GetTokenAsync("BizAdminFull"), d.ToString()); - // Util.ValidateErrorCodeResponse(a, 2200, 400); - // Util.ShouldContainValidationError(a, "Filter", "2203"); - - // } - - - - //================================================== - - }//eoc -}//eons +using System; +using Xunit; +using Newtonsoft.Json.Linq; +using FluentAssertions; +using System.Collections.Generic; +using System.Collections.Concurrent; + +namespace raven_integration +{ + + public class DataListFilterCrud + { + + /// + /// Test all CRUD routes + /// + [Fact] + public async Task CRUD() + { + //CREATE + dynamic d = new JObject(); + d.name = Util.Uniquify("Test DataListView"); + + d["public"] = true; + d.listKey="TestWidgetDataList"; + + //"[{fld:"name",op:"!=",value:"Notequaltothis"},{fld:"tags",op:"Eq",value:"[23,456,54]"}] + dynamic dListView = new JArray(); + // dynamic df = new JObject(); + // df.fld = "widgetname"; + // df.op = "%-"; + // df.value = "Generic";//lots of seed widgets start with Generic + // dListView.Add(df); + // d.filter = dListView.ToString();//it expects it to be a json string, not actual json + dListView.Add(Util.BuildSimpleFilterDataListViewColumn("widgetname", Util.OpStartsWith, "Generic")); + d.listView=dListView.ToString(Newtonsoft.Json.Formatting.None); + + ApiResponse a = await Util.PostAsync("data-list-view", await Util.GetTokenAsync("BizAdminFull"), d.ToString(Newtonsoft.Json.Formatting.None)); + Util.ValidateDataReturnResponseOk(a); + + long Id = a.ObjectResponse["data"]["id"].Value(); + + + //RETRIEVE + //Get one + a = await Util.GetAsync("data-list-view/" + Id.ToString(), await Util.GetTokenAsync("BizAdminFull")); + Util.ValidateDataReturnResponseOk(a); + a.ObjectResponse["data"]["name"].Value().Should().StartWith("Test DataListView"); + + //Get as alternate user should work for public filter + a = await Util.GetAsync("data-list-view/" + Id.ToString(), await Util.GetTokenAsync("SubContractorLimited")); + Util.ValidateDataReturnResponseOk(a); + a.ObjectResponse["data"]["name"].Value().Should().StartWith("Test DataListView"); + + + //UPDATE + + //PUT, make private + d["public"] = false; + d.name = Util.Uniquify("Put - Test DataListView (privatized)"); + d.concurrency = a.ObjectResponse["data"]["concurrency"].Value(); + a = await Util.PutAsync("data-list-view/" + Id.ToString(), await Util.GetTokenAsync("BizAdminFull"), d.ToString()); + Util.ValidateHTTPStatusCode(a, 200); + + //check PUT worked + a = await Util.GetAsync("data-list-view/" + Id.ToString(), await Util.GetTokenAsync("BizAdminFull")); + Util.ValidateNoErrorInResponse(a); + a.ObjectResponse["data"]["name"].Value().Should().Be(d.name.ToString()); + + + //FETCH DISALLOWED + //Get as alternate user should fail for private filter + a = await Util.GetAsync("data-list-view/" + Id.ToString(), await Util.GetTokenAsync("SubContractorLimited")); + Util.ValidateResponseNotFound(a); + + // //DELETE + ApiResponse DELETETestResponse = await Util.DeleteAsync("data-list-view/" + Id.ToString(), await Util.GetTokenAsync("BizAdminFull")); + Util.ValidateHTTPStatusCode(DELETETestResponse, 204); + + } + + /// + /// + /// + [Fact] + public async Task InvalidListKeyShouldFail() + { + //CREATE + dynamic d = new JObject(); + d.name = Util.Uniquify("Test DataListView"); + + d["public"] = true; + d.listKey = "nonexistant"; + + //"[{fld:"name",op:"!=",value:"Notequaltothis"},{fld:"tags",op:"Eq",value:"[23,456,54]"}] + // dynamic dfilter = new JArray(); + // dynamic df = new JObject(); + // df.fld = "name"; + // df.op = "%-"; + // df.value = "Generic";//lots of seed widgets start with Generic + // dfilter.Add(df); + + // d.filter = dfilter.ToString();//it expects it to be a json string, not actual json + + // ApiResponse a = await Util.PostAsync("data-list-view", await Util.GetTokenAsync("BizAdminFull"), d.ToString()); + + dynamic dListView = new JArray(); + // dynamic df = new JObject(); + // df.fld = "widgetname"; + // df.op = "%-"; + // df.value = "Generic";//lots of seed widgets start with Generic + // dListView.Add(df); + // d.filter = dListView.ToString();//it expects it to be a json string, not actual json + dListView.Add(Util.BuildSimpleFilterDataListViewColumn("widgetname", Util.OpStartsWith, "Generic")); + d.listView=dListView.ToString(Newtonsoft.Json.Formatting.None); + + ApiResponse a = await Util.PostAsync("data-list-view", await Util.GetTokenAsync("BizAdminFull"), d.ToString(Newtonsoft.Json.Formatting.None)); + Util.ValidateErrorCodeResponse(a, 2200, 400); + Util.ShouldContainValidationError(a, "ListKey", "2203"); + + } + + + /// + /// + /// + [Fact] + public async Task InvalidFieldNameShouldFail() + { + //CREATE + dynamic d = new JObject(); + d.name = Util.Uniquify("Test DataListView"); + + d["public"] = true; + d.listKey="TestWidgetDataList"; + + //"[{fld:"name",op:"!=",value:"Notequaltothis"},{fld:"tags",op:"Eq",value:"[23,456,54]"}] + // dynamic dfilter = new JArray(); + // dynamic df = new JObject(); + // df.fld = "doesntexist"; + // df.op = "%-"; + // df.value = "Generic";//lots of seed widgets start with Generic + // dfilter.Add(df); + + // d.filter = dfilter.ToString();//it expects it to be a json string, not actual json + + // ApiResponse a = await Util.PostAsync("data-list-view", await Util.GetTokenAsync("BizAdminFull"), d.ToString()); + dynamic dListView = new JArray(); + // dynamic df = new JObject(); + // df.fld = "widgetname"; + // df.op = "%-"; + // df.value = "Generic";//lots of seed widgets start with Generic + // dListView.Add(df); + // d.filter = dListView.ToString();//it expects it to be a json string, not actual json + dListView.Add(Util.BuildSimpleFilterDataListViewColumn("doesntexist", Util.OpStartsWith, "Generic")); + d.listView=dListView.ToString(Newtonsoft.Json.Formatting.None); + + ApiResponse a = await Util.PostAsync("data-list-view", await Util.GetTokenAsync("BizAdminFull"), d.ToString(Newtonsoft.Json.Formatting.None)); + Util.ValidateErrorCodeResponse(a, 2200, 400); + Util.ShouldContainValidationError(a, "ListView", "2203"); + + } + + + +//REMOVED THIS VALIDATION TEST AS SWITCH TO DATALISTVIEW NO LONGER VALIDATES FILTER ANYWAY +//ONLY COLUMN NAMES AND LIST NAME + // /// + // /// + // /// + // [Fact] + // public async Task InvalidOperatorShouldFail() + // { + // //CREATE + // dynamic d = new JObject(); + // d.name = Util.Uniquify("Test DataListView"); + + // d["public"] = true; + // d.listKey="TestWidgetDataList"; + + // //"[{fld:"name",op:"!=",value:"Notequaltothis"},{fld:"tags",op:"Eq",value:"[23,456,54]"}] + // dynamic dfilter = new JArray(); + // dynamic df = new JObject(); + // df.fld = "name"; + // df.op = "wtf"; + // df.value = "Generic";//lots of seed widgets start with Generic + // dfilter.Add(df); + + // d.filter = dfilter.ToString();//it expects it to be a json string, not actual json + + // ApiResponse a = await Util.PostAsync("data-list-view", await Util.GetTokenAsync("BizAdminFull"), d.ToString()); + // Util.ValidateErrorCodeResponse(a, 2200, 400); + // Util.ShouldContainValidationError(a, "Filter", "2203"); + + // } + + + + //================================================== + + }//eoc +}//eons diff --git a/Docs/Docs.cs b/Docs/Docs.cs index 4d47e96..64ac326 100644 --- a/Docs/Docs.cs +++ b/Docs/Docs.cs @@ -1,31 +1,31 @@ -using System; -using Xunit; -using Newtonsoft.Json.Linq; -using FluentAssertions; -using System.Collections.Generic; -using System.Collections.Concurrent; - -namespace raven_integration -{ - - public class Docs - { - - - - /// - /// - /// - [Fact] - public async void UserManualShouldFetch() - { - ApiTextResponse t = await Util.GetNonApiPageAsync("docs/"); - Util.ValidateHTTPStatusCode(t, 200); - t.TextResponse.Should().Contain("AyaNova manual"); - - } - - //================================================== - - }//eoc -}//eons +using System; +using Xunit; +using Newtonsoft.Json.Linq; +using FluentAssertions; +using System.Collections.Generic; +using System.Collections.Concurrent; + +namespace raven_integration +{ + + public class Docs + { + + + + /// + /// + /// + [Fact] + public async Task UserManualShouldFetch() + { + ApiTextResponse t = await Util.GetNonApiPageAsync("docs/"); + Util.ValidateHTTPStatusCode(t, 200); + t.TextResponse.Should().Contain("AyaNova manual"); + + } + + //================================================== + + }//eoc +}//eons diff --git a/Enum/EnumListOps.cs b/Enum/EnumListOps.cs index afbc02f..f176d3f 100644 --- a/Enum/EnumListOps.cs +++ b/Enum/EnumListOps.cs @@ -1,45 +1,45 @@ -using System; -using Xunit; -using Newtonsoft.Json.Linq; -using FluentAssertions; - -namespace raven_integration -{ - - public class EnumListOps - { - - - /// - /// - /// - [Fact] - public async void GetListOfEnumListsAndGetAllEnumListsWorks() - { - ApiResponse a = await Util.GetAsync("enum-list/listkeys", await Util.GetTokenAsync("superuser", "l3tm3in")); - Util.ValidateDataReturnResponseOk(a); - Util.ValidateHTTPStatusCode(a, 200); - ((JArray)a.ObjectResponse["data"]).Count.Should().BeGreaterThan(2); - - //iterate all the list names and fetch each one in turn and see that it fetches ok and has at least 2 list items in it - foreach (JObject jListName in a.ObjectResponse["data"]) - { - - ApiResponse b = await Util.GetAsync($"enum-list/list/{jListName["key"].Value()}", await Util.GetTokenAsync("superuser", "l3tm3in")); - Util.ValidateDataReturnResponseOk(b); - Util.ValidateHTTPStatusCode(b, 200); - ((JArray)b.ObjectResponse["data"]).Count.Should().BeGreaterThan(1); - - } - - } - - - - - - - //================================================== - - }//eoc -}//eons +using System; +using Xunit; +using Newtonsoft.Json.Linq; +using FluentAssertions; + +namespace raven_integration +{ + + public class EnumListOps + { + + + /// + /// + /// + [Fact] + public async Task GetListOfEnumListsAndGetAllEnumListsWorks() + { + ApiResponse a = await Util.GetAsync("enum-list/listkeys", await Util.GetTokenAsync("superuser", "l3tm3in")); + Util.ValidateDataReturnResponseOk(a); + Util.ValidateHTTPStatusCode(a, 200); + ((JArray)a.ObjectResponse["data"]).Count.Should().BeGreaterThan(2); + + //iterate all the list names and fetch each one in turn and see that it fetches ok and has at least 2 list items in it + foreach (JObject jListName in a.ObjectResponse["data"]) + { + + ApiResponse b = await Util.GetAsync($"enum-list/list/{jListName["key"].Value()}", await Util.GetTokenAsync("superuser", "l3tm3in")); + Util.ValidateDataReturnResponseOk(b); + Util.ValidateHTTPStatusCode(b, 200); + ((JArray)b.ObjectResponse["data"]).Count.Should().BeGreaterThan(1); + + } + + } + + + + + + + //================================================== + + }//eoc +}//eons diff --git a/EventLog/EventLog.cs b/EventLog/EventLog.cs index ec9cb78..f991ff2 100644 --- a/EventLog/EventLog.cs +++ b/EventLog/EventLog.cs @@ -1,221 +1,221 @@ -using System; -using Xunit; -using Newtonsoft.Json.Linq; -using FluentAssertions; -using System.Collections.Generic; -using System.Collections.Concurrent; - -namespace raven_integration -{ - - public class EventLog - { - - - - /// - /// - /// - [Fact] - public async void ObjectLogWorks() - { - //CRUD a widget and confirm it logs properly - //http://localhost:7575/api/v8.0/event-log/userlog?AyType=3&AyId=1 - //http://localhost:7575/api/v8.0/event-log/objectlog?AyType=2&AyId=242 - //http://localhost:7575/api/v8.0/event-log/userlog?AyType=3&AyId=1&StartDate=2018-08-23&EndDate=2018-08-24 - - dynamic w = new JObject(); - w.name = Util.Uniquify("EventLog Test WIDGET"); - w.customFields = Util.WidgetRequiredCustomFieldsJsonString(); - w.notes = "blah"; - w.created = DateTime.Now.ToString(); - w.dollarAmount = 2.22m; - w.active = true; - w.usertype = 1; - - //*** CREATED - ApiResponse r2 = await Util.PostAsync("widget", await Util.GetTokenAsync("InventoryFull"), w.ToString()); - Util.ValidateDataReturnResponseOk(r2); - long w2Id = r2.ObjectResponse["data"]["id"].Value(); - - ApiResponse EventLogResponse = await Util.GetAsync($"event-log/objectlog?AyaType=2&AyId={w2Id}", await Util.GetTokenAsync("BizAdminFull")); - Util.ValidateHTTPStatusCode(EventLogResponse, 200); - - ((JArray)EventLogResponse.ObjectResponse["data"]["events"]).Count.Should().Be(1);//only one event so far - EventLogResponse.ObjectResponse["data"]["events"][0]["date"].Value().Should().BeLessThan(new TimeSpan(1, 0, 0)).Before(DateTime.UtcNow);//should be less than one hour before now - EventLogResponse.ObjectResponse["data"]["events"][0]["userId"].Should().NotBeNull(); - EventLogResponse.ObjectResponse["data"]["events"][0]["event"].Value().Should().Be(1);//AyEvent 1 = created - EventLogResponse.ObjectResponse["data"]["events"][0]["textra"].Should().BeNullOrEmpty(); - - //Get current user doing modifications ID - long CurrentUserId = EventLogResponse.ObjectResponse["data"]["events"][0]["userId"].Value(); - - //*** RETRIEVED - //Get one - ApiResponse r3 = await Util.GetAsync("widget/" + w2Id.ToString(), await Util.GetTokenAsync("InventoryFull")); - Util.ValidateDataReturnResponseOk(r3); - r3.ObjectResponse["data"]["name"].Value().Should().Be(w.name.ToString()); - w = r3.ObjectResponse["data"]; - - - EventLogResponse = await Util.GetAsync($"event-log/objectlog?AyaType=2&AyId={w2Id}", await Util.GetTokenAsync("BizAdminFull")); - Util.ValidateHTTPStatusCode(EventLogResponse, 200); - //confirm event count, type and sort order (descending by date most recent first) - ((JArray)EventLogResponse.ObjectResponse["data"]["events"]).Count.Should().Be(2); - EventLogResponse.ObjectResponse["data"]["events"][0]["date"].Value().Should().BeLessThan(new TimeSpan(1, 0, 0)).Before(DateTime.UtcNow);//should be less than one hour before now - EventLogResponse.ObjectResponse["data"]["events"][0]["userId"].Should().NotBeNull(); - EventLogResponse.ObjectResponse["data"]["events"][0]["event"].Value().Should().Be(2);//AyEvent 2 = retrieved - EventLogResponse.ObjectResponse["data"]["events"][0]["textra"].Should().BeNullOrEmpty(); - - //*** MODIFIED - //PUT - //update w2id - w.name = Util.Uniquify("UPDATED VIA PUT EVENTLOG TEST WIDGET"); - w.UserId = 1; - w.concurrency = r2.ObjectResponse["data"]["concurrency"].Value(); - ApiResponse PUTTestResponse = await Util.PutAsync("widget", await Util.GetTokenAsync("InventoryFull"), w.ToString()); - Util.ValidateHTTPStatusCode(PUTTestResponse, 200); - - //*** RETRIEVED - //check PUT worked - ApiResponse checkPUTWorked = await Util.GetAsync("widget/" + w2Id.ToString(), await Util.GetTokenAsync("InventoryFull")); - Util.ValidateNoErrorInResponse(checkPUTWorked); - checkPUTWorked.ObjectResponse["data"]["name"].Value().Should().Be(w.name.ToString()); - uint concurrency = PUTTestResponse.ObjectResponse["data"]["concurrency"].Value(); - - EventLogResponse = await Util.GetAsync($"event-log/objectlog?AyaType=2&AyId={w2Id}", await Util.GetTokenAsync("BizAdminFull")); - Util.ValidateHTTPStatusCode(EventLogResponse, 200); - ((JArray)EventLogResponse.ObjectResponse["data"]["events"]).Count.Should().Be(4); - //put op is the second item in the list, top item is the recent fetch - EventLogResponse.ObjectResponse["data"]["events"][1]["date"].Value().Should().BeLessThan(new TimeSpan(1, 0, 0)).Before(DateTime.UtcNow);//should be less than one hour before now - EventLogResponse.ObjectResponse["data"]["events"][1]["userId"].Should().NotBeNull(); - EventLogResponse.ObjectResponse["data"]["events"][1]["event"].Value().Should().Be(3);//AyEvent 3 = Modified - EventLogResponse.ObjectResponse["data"]["events"][1]["textra"].Should().BeNullOrEmpty(); - - - //Check user log for basic accessibility userlog?UserId=7 - EventLogResponse = await Util.GetAsync($"event-log/userlog?UserId={CurrentUserId}", await Util.GetTokenAsync("BizAdminFull")); - Util.ValidateHTTPStatusCode(EventLogResponse, 200); - ((JArray)EventLogResponse.ObjectResponse["data"]["events"]).Count.Should().BeGreaterOrEqualTo(4);//just one run of the above will be 4 events plus any others from other tests - //Not sure of any easy way to assert the User log is correct other than the count as other tests running concurrently could easily skew this - - - //DELETE - ApiResponse DELETETestResponse = await Util.DeleteAsync("widget/" + w2Id.ToString(), await Util.GetTokenAsync("InventoryFull")); - Util.ValidateHTTPStatusCode(DELETETestResponse, 204); - - //All events should be cleared up on deletion with the sole exception of the deleted event - EventLogResponse = await Util.GetAsync($"event-log/objectlog?AyaType=2&AyId={w2Id}", await Util.GetTokenAsync("BizAdminFull")); - Util.ValidateHTTPStatusCode(EventLogResponse, 200); - ((JArray)EventLogResponse.ObjectResponse["data"]["events"]).Count.Should().Be(1); - EventLogResponse.ObjectResponse["data"]["events"][0]["date"].Value().Should().BeLessThan(new TimeSpan(1, 0, 0)).Before(DateTime.UtcNow);//should be less than one hour before now - EventLogResponse.ObjectResponse["data"]["events"][0]["userId"].Should().NotBeNull(); - EventLogResponse.ObjectResponse["data"]["events"][0]["event"].Value().Should().Be(0);//AyEvent 0 = deleted - EventLogResponse.ObjectResponse["data"]["events"][0]["textra"].Value().Should().Be(w.name.ToString()); - - - } - - /// - /// - /// - [Fact] - public async void UserLogWorks() - { - //get admin log, sb lots of shit - ApiResponse a = await Util.GetAsync($"event-log/userlog?UserId=1&Offset=0&Limit=999", await Util.GetTokenAsync("BizAdminFull")); - Util.ValidateDataReturnResponseOk(a); - ((JArray)a.ObjectResponse["data"]["events"]).Count.Should().BeGreaterThan(90); - } - - - - /// - /// - /// - [Fact] - public async void EventLogLimitOffSetWorks() - { - - var UniqueName = Util.Uniquify("EventLogLimitOffSetWorks"); - //CREATE - dynamic d = new JObject(); - d.name = UniqueName; - - d.active = true; - d.login = UniqueName; - d.password = UniqueName; - d.roles = 2;//bizadminfull needs widget rights - d.userType = 3;//non scheduleable - - //Required by form custom rules - d.notes = "notes"; - d.customFields = Util.UserRequiredCustomFieldsJsonString(); - - ApiResponse a = await Util.PostAsync("User", await Util.GetTokenAsync("superuser", "l3tm3in"), d.ToString()); - Util.ValidateDataReturnResponseOk(a); - long UserId = a.ObjectResponse["data"]["id"].Value(); - - - //Loop and make 10 widgets - for (int i = 0; i < 10; i++) - { - d = new JObject(); - d.name = Util.Uniquify("EventLogLimitOffSetWorks"); - d.customFields = Util.WidgetRequiredCustomFieldsJsonString(); - d.dollarAmount = 1.11m; - d.active = true; - d.usertype = 1; - d.notes = "note here"; - a = await Util.PostAsync("widget", await Util.GetTokenAsync(UniqueName, UniqueName), d.ToString()); - Util.ValidateDataReturnResponseOk(a); - } - - a = await Util.GetAsync($"event-log/userlog?UserId={UserId}&Offset=0&Limit=9", await Util.GetTokenAsync("BizAdminFull")); - ((JArray)a.ObjectResponse["data"]["events"]).Count.Should().Be(9); - //capture events, then compare to paged ones - var eventList = ((JArray)a.ObjectResponse["data"]["events"]); - List allEvents = new List(9); - foreach (JObject o in eventList) - { - allEvents.Add(o["date"].Value() + o["objectType"].Value() - + o["objectId"].Value() + o["name"].Value() + o["event"].Value() - ); - } - - a = await Util.GetAsync($"event-log/userlog?UserId={UserId}&Offset=0&Limit=3", await Util.GetTokenAsync("BizAdminFull")); - ((JArray)a.ObjectResponse["data"]["events"]).Count.Should().Be(3); - var pageEventList = ((JArray)a.ObjectResponse["data"]["events"]); - foreach (JObject o in pageEventList) - { - allEvents.Should().Contain(o["date"].Value() + o["objectType"].Value() - + o["objectId"].Value() + o["name"].Value() + o["event"].Value() - ); - } - - a = await Util.GetAsync($"event-log/userlog?UserId={UserId}&Offset=1&Limit=3", await Util.GetTokenAsync("BizAdminFull")); - ((JArray)a.ObjectResponse["data"]["events"]).Count.Should().Be(3); - pageEventList = ((JArray)a.ObjectResponse["data"]["events"]); - foreach (JObject o in pageEventList) - { - allEvents.Should().Contain(o["date"].Value() + o["objectType"].Value() - + o["objectId"].Value() + o["name"].Value() + o["event"].Value() - ); - } - - - a = await Util.GetAsync($"event-log/userlog?UserId={UserId}&Offset=2&Limit=3", await Util.GetTokenAsync("BizAdminFull")); - ((JArray)a.ObjectResponse["data"]["events"]).Count.Should().Be(3); - pageEventList = ((JArray)a.ObjectResponse["data"]["events"]); - foreach (JObject o in pageEventList) - { - allEvents.Should().Contain(o["date"].Value() + o["objectType"].Value() - + o["objectId"].Value() + o["name"].Value() + o["event"].Value() - ); - } - } - - //================================================== - - }//eoc -}//eons +using System; +using Xunit; +using Newtonsoft.Json.Linq; +using FluentAssertions; +using System.Collections.Generic; +using System.Collections.Concurrent; + +namespace raven_integration +{ + + public class EventLog + { + + + + /// + /// + /// + [Fact] + public async Task ObjectLogWorks() + { + //CRUD a widget and confirm it logs properly + //http://localhost:7575/api/v8.0/event-log/userlog?AyType=3&AyId=1 + //http://localhost:7575/api/v8.0/event-log/objectlog?AyType=2&AyId=242 + //http://localhost:7575/api/v8.0/event-log/userlog?AyType=3&AyId=1&StartDate=2018-08-23&EndDate=2018-08-24 + + dynamic w = new JObject(); + w.name = Util.Uniquify("EventLog Test WIDGET"); + w.customFields = Util.WidgetRequiredCustomFieldsJsonString(); + w.notes = "blah"; + w.created = DateTime.Now.ToString(); + w.dollarAmount = 2.22m; + w.active = true; + w.usertype = 1; + + //*** CREATED + ApiResponse r2 = await Util.PostAsync("widget", await Util.GetTokenAsync("InventoryFull"), w.ToString()); + Util.ValidateDataReturnResponseOk(r2); + long w2Id = r2.ObjectResponse["data"]["id"].Value(); + + ApiResponse EventLogResponse = await Util.GetAsync($"event-log/objectlog?AyaType=2&AyId={w2Id}", await Util.GetTokenAsync("BizAdminFull")); + Util.ValidateHTTPStatusCode(EventLogResponse, 200); + + ((JArray)EventLogResponse.ObjectResponse["data"]["events"]).Count.Should().Be(1);//only one event so far + EventLogResponse.ObjectResponse["data"]["events"][0]["date"].Value().Should().BeLessThan(new TimeSpan(1, 0, 0)).Before(DateTime.UtcNow);//should be less than one hour before now + EventLogResponse.ObjectResponse["data"]["events"][0]["userId"].Should().NotBeNull(); + EventLogResponse.ObjectResponse["data"]["events"][0]["event"].Value().Should().Be(1);//AyEvent 1 = created + EventLogResponse.ObjectResponse["data"]["events"][0]["textra"].Should().BeNullOrEmpty(); + + //Get current user doing modifications ID + long CurrentUserId = EventLogResponse.ObjectResponse["data"]["events"][0]["userId"].Value(); + + //*** RETRIEVED + //Get one + ApiResponse r3 = await Util.GetAsync("widget/" + w2Id.ToString(), await Util.GetTokenAsync("InventoryFull")); + Util.ValidateDataReturnResponseOk(r3); + r3.ObjectResponse["data"]["name"].Value().Should().Be(w.name.ToString()); + w = r3.ObjectResponse["data"]; + + + EventLogResponse = await Util.GetAsync($"event-log/objectlog?AyaType=2&AyId={w2Id}", await Util.GetTokenAsync("BizAdminFull")); + Util.ValidateHTTPStatusCode(EventLogResponse, 200); + //confirm event count, type and sort order (descending by date most recent first) + ((JArray)EventLogResponse.ObjectResponse["data"]["events"]).Count.Should().Be(2); + EventLogResponse.ObjectResponse["data"]["events"][0]["date"].Value().Should().BeLessThan(new TimeSpan(1, 0, 0)).Before(DateTime.UtcNow);//should be less than one hour before now + EventLogResponse.ObjectResponse["data"]["events"][0]["userId"].Should().NotBeNull(); + EventLogResponse.ObjectResponse["data"]["events"][0]["event"].Value().Should().Be(2);//AyEvent 2 = retrieved + EventLogResponse.ObjectResponse["data"]["events"][0]["textra"].Should().BeNullOrEmpty(); + + //*** MODIFIED + //PUT + //update w2id + w.name = Util.Uniquify("UPDATED VIA PUT EVENTLOG TEST WIDGET"); + w.UserId = 1; + w.concurrency = r2.ObjectResponse["data"]["concurrency"].Value(); + ApiResponse PUTTestResponse = await Util.PutAsync("widget", await Util.GetTokenAsync("InventoryFull"), w.ToString()); + Util.ValidateHTTPStatusCode(PUTTestResponse, 200); + + //*** RETRIEVED + //check PUT worked + ApiResponse checkPUTWorked = await Util.GetAsync("widget/" + w2Id.ToString(), await Util.GetTokenAsync("InventoryFull")); + Util.ValidateNoErrorInResponse(checkPUTWorked); + checkPUTWorked.ObjectResponse["data"]["name"].Value().Should().Be(w.name.ToString()); + uint concurrency = PUTTestResponse.ObjectResponse["data"]["concurrency"].Value(); + + EventLogResponse = await Util.GetAsync($"event-log/objectlog?AyaType=2&AyId={w2Id}", await Util.GetTokenAsync("BizAdminFull")); + Util.ValidateHTTPStatusCode(EventLogResponse, 200); + ((JArray)EventLogResponse.ObjectResponse["data"]["events"]).Count.Should().Be(4); + //put op is the second item in the list, top item is the recent fetch + EventLogResponse.ObjectResponse["data"]["events"][1]["date"].Value().Should().BeLessThan(new TimeSpan(1, 0, 0)).Before(DateTime.UtcNow);//should be less than one hour before now + EventLogResponse.ObjectResponse["data"]["events"][1]["userId"].Should().NotBeNull(); + EventLogResponse.ObjectResponse["data"]["events"][1]["event"].Value().Should().Be(3);//AyEvent 3 = Modified + EventLogResponse.ObjectResponse["data"]["events"][1]["textra"].Should().BeNullOrEmpty(); + + + //Check user log for basic accessibility userlog?UserId=7 + EventLogResponse = await Util.GetAsync($"event-log/userlog?UserId={CurrentUserId}", await Util.GetTokenAsync("BizAdminFull")); + Util.ValidateHTTPStatusCode(EventLogResponse, 200); + ((JArray)EventLogResponse.ObjectResponse["data"]["events"]).Count.Should().BeGreaterOrEqualTo(4);//just one run of the above will be 4 events plus any others from other tests + //Not sure of any easy way to assert the User log is correct other than the count as other tests running concurrently could easily skew this + + + //DELETE + ApiResponse DELETETestResponse = await Util.DeleteAsync("widget/" + w2Id.ToString(), await Util.GetTokenAsync("InventoryFull")); + Util.ValidateHTTPStatusCode(DELETETestResponse, 204); + + //All events should be cleared up on deletion with the sole exception of the deleted event + EventLogResponse = await Util.GetAsync($"event-log/objectlog?AyaType=2&AyId={w2Id}", await Util.GetTokenAsync("BizAdminFull")); + Util.ValidateHTTPStatusCode(EventLogResponse, 200); + ((JArray)EventLogResponse.ObjectResponse["data"]["events"]).Count.Should().Be(1); + EventLogResponse.ObjectResponse["data"]["events"][0]["date"].Value().Should().BeLessThan(new TimeSpan(1, 0, 0)).Before(DateTime.UtcNow);//should be less than one hour before now + EventLogResponse.ObjectResponse["data"]["events"][0]["userId"].Should().NotBeNull(); + EventLogResponse.ObjectResponse["data"]["events"][0]["event"].Value().Should().Be(0);//AyEvent 0 = deleted + EventLogResponse.ObjectResponse["data"]["events"][0]["textra"].Value().Should().Be(w.name.ToString()); + + + } + + /// + /// + /// + [Fact] + public async Task UserLogWorks() + { + //get admin log, sb lots of shit + ApiResponse a = await Util.GetAsync($"event-log/userlog?UserId=1&Offset=0&Limit=999", await Util.GetTokenAsync("BizAdminFull")); + Util.ValidateDataReturnResponseOk(a); + ((JArray)a.ObjectResponse["data"]["events"]).Count.Should().BeGreaterThan(90); + } + + + + /// + /// + /// + [Fact] + public async Task EventLogLimitOffSetWorks() + { + + var UniqueName = Util.Uniquify("EventLogLimitOffSetWorks"); + //CREATE + dynamic d = new JObject(); + d.name = UniqueName; + + d.active = true; + d.login = UniqueName; + d.password = UniqueName; + d.roles = 2;//bizadminfull needs widget rights + d.userType = 3;//non scheduleable + + //Required by form custom rules + d.notes = "notes"; + d.customFields = Util.UserRequiredCustomFieldsJsonString(); + + ApiResponse a = await Util.PostAsync("User", await Util.GetTokenAsync("superuser", "l3tm3in"), d.ToString()); + Util.ValidateDataReturnResponseOk(a); + long UserId = a.ObjectResponse["data"]["id"].Value(); + + + //Loop and make 10 widgets + for (int i = 0; i < 10; i++) + { + d = new JObject(); + d.name = Util.Uniquify("EventLogLimitOffSetWorks"); + d.customFields = Util.WidgetRequiredCustomFieldsJsonString(); + d.dollarAmount = 1.11m; + d.active = true; + d.usertype = 1; + d.notes = "note here"; + a = await Util.PostAsync("widget", await Util.GetTokenAsync(UniqueName, UniqueName), d.ToString()); + Util.ValidateDataReturnResponseOk(a); + } + + a = await Util.GetAsync($"event-log/userlog?UserId={UserId}&Offset=0&Limit=9", await Util.GetTokenAsync("BizAdminFull")); + ((JArray)a.ObjectResponse["data"]["events"]).Count.Should().Be(9); + //capture events, then compare to paged ones + var eventList = ((JArray)a.ObjectResponse["data"]["events"]); + List allEvents = new List(9); + foreach (JObject o in eventList) + { + allEvents.Add(o["date"].Value() + o["objectType"].Value() + + o["objectId"].Value() + o["name"].Value() + o["event"].Value() + ); + } + + a = await Util.GetAsync($"event-log/userlog?UserId={UserId}&Offset=0&Limit=3", await Util.GetTokenAsync("BizAdminFull")); + ((JArray)a.ObjectResponse["data"]["events"]).Count.Should().Be(3); + var pageEventList = ((JArray)a.ObjectResponse["data"]["events"]); + foreach (JObject o in pageEventList) + { + allEvents.Should().Contain(o["date"].Value() + o["objectType"].Value() + + o["objectId"].Value() + o["name"].Value() + o["event"].Value() + ); + } + + a = await Util.GetAsync($"event-log/userlog?UserId={UserId}&Offset=1&Limit=3", await Util.GetTokenAsync("BizAdminFull")); + ((JArray)a.ObjectResponse["data"]["events"]).Count.Should().Be(3); + pageEventList = ((JArray)a.ObjectResponse["data"]["events"]); + foreach (JObject o in pageEventList) + { + allEvents.Should().Contain(o["date"].Value() + o["objectType"].Value() + + o["objectId"].Value() + o["name"].Value() + o["event"].Value() + ); + } + + + a = await Util.GetAsync($"event-log/userlog?UserId={UserId}&Offset=2&Limit=3", await Util.GetTokenAsync("BizAdminFull")); + ((JArray)a.ObjectResponse["data"]["events"]).Count.Should().Be(3); + pageEventList = ((JArray)a.ObjectResponse["data"]["events"]); + foreach (JObject o in pageEventList) + { + allEvents.Should().Contain(o["date"].Value() + o["objectType"].Value() + + o["objectId"].Value() + o["name"].Value() + o["event"].Value() + ); + } + } + + //================================================== + + }//eoc +}//eons diff --git a/FormCustom/FormCustom.cs b/FormCustom/FormCustom.cs index d67d1a2..5029227 100644 --- a/FormCustom/FormCustom.cs +++ b/FormCustom/FormCustom.cs @@ -1,241 +1,241 @@ -using System; -using Xunit; -using Newtonsoft.Json.Linq; -using FluentAssertions; -using System.Collections.Generic; -using System.Collections.Concurrent; - -namespace raven_integration -{ - - public class FormCustom - { - public enum AyaUiFieldDataType : int - { - NoType = 0, - DateTime = 1, - Date = 2, - Time = 3, - Text = 4, - Integer = 5, - Bool = 6, - Decimal = 7, - Currency = 8, - Tags = 9, - Enum = 10, - EmailAddress = 11 - - } - - /// - /// Test create or update - /// - [Fact] - public async void FormCustomUpdate() - { - - //This is a special case, you can PUT a formcustom, but you can't delete one and you can't create one - /* - - */ - - dynamic d = new JObject(); - d.formkey = "User"; - - dynamic dtemplate = new JArray(); - - dynamic dt = new JObject(); - dt.fld = "UserCustom1"; - dt.hide = false; - dt.required = true; - dt.type = AyaUiFieldDataType.Text; - dtemplate.Add(dt); - - - dt = new JObject(); - dt.fld = "Notes"; - dt.required = true; - dtemplate.Add(dt); - - dt = new JObject(); - dt.fld = "UserCustom2"; - dt.hide = true; - dt.required = false; - dt.type = AyaUiFieldDataType.Bool; - dtemplate.Add(dt); - - d.template = dtemplate.ToString();//it expects it to be a json string, not actual json - - - //RETRIEVE - //Get the current one (server will create if non-existent) - ApiResponse a = await Util.GetAsync("form-custom/User", await Util.GetTokenAsync("BizAdminFull")); - - //Update - d.concurrency = a.ObjectResponse["data"]["concurrency"].Value(); - a = await Util.PutAsync("form-custom/User", await Util.GetTokenAsync("BizAdminFull"), d.ToString()); - Util.ValidateHTTPStatusCode(a, 200); - - //check the concurrency token cache scheme - uint token = a.ObjectResponse["data"]["concurrency"].Value(); - //This should return a 304 not modified - a = await Util.GetAsync($"form-custom/User?concurrency={token}", await Util.GetTokenAsync("BizAdminFull")); - Util.ValidateHTTPStatusCode(a, 304); - - //and this should return the whole object - token--;//make the token not match - //This should return a 200 and the whole object - a = await Util.GetAsync($"form-custom/User?concurrency={token}", await Util.GetTokenAsync("BizAdminFull")); - Util.ValidateDataReturnResponseOk(a); - } - - - - - /// - /// Ensure validation works in FormCustombiz - /// - [Fact] - public async void ValidatesProperly() - { - - dynamic d = new JObject(); - d.formkey = "User"; - - dynamic dtemplate = new JArray(); - - dynamic dt = new JObject(); - dt.fld = string.Empty;//expected ApiErrorCode.VALIDATION_REQUIRED Missing key 2 errors 2201 and 2203 - dt.hide = false; - dt.required = true; - dtemplate.Add(dt); - - - dt = new JObject(); - dt.fld = "ThisFieldKeyDoesNotExist";//expected ApiErrorCode.VALIDATION_INVALID_VALUE Bad key - dt.required = true; - dtemplate.Add(dt); - - dt = new JObject(); - dt.fld = "Name";//expect ApiErrorCode.VALIDATION_INVALID_VALUE required field not hideable - dt.hide = true; - dt.required = true; - dtemplate.Add(dt); - - dt = new JObject(); - dt.fld = "UserCustom1";//expected ApiErrorCode.VALIDATION_INVALID_VALUE type missing for custom field - dt.hide = false; - dt.required = false; - dtemplate.Add(dt); - - dt = new JObject(); - dt.fld = "EmployeeNumber";//expect ApiErrorCode.VALIDATION_INVALID_VALUE not custom field but type specified anyway - dt.hide = true; - dt.required = false; - dt.type = AyaUiFieldDataType.EmailAddress;//type specified (doesn't matter what type) - dtemplate.Add(dt); - - dt = new JObject(); - dt.fld = "UserCustom2";//expected ApiErrorCode.VALIDATION_INVALID_VALUE type missing for custom field - dt.hide = false; - dt.required = false; - dtemplate.Add(dt); - dt.type = 999;//not a valid type - - dt = new JObject(); - dt.fld = "Notes";//expect ApiErrorCode.VALIDATION_REQUIRED required property is always required (no idea why, just designed that way and that's the rule) - dt.hide = true; - // dt.required = false; Deliberately not set - dtemplate.Add(dt); - - d.template = dtemplate.ToString();//it expects it to be a json string, not actual json - - - //RETRIEVE - //Get the current one (server will create if non-existent) - ApiResponse a = await Util.GetAsync("form-custom/User", await Util.GetTokenAsync("BizAdminFull")); - - //Update - d.concurrency = a.ObjectResponse["data"]["concurrency"].Value(); - a = await Util.PutAsync("form-custom/User", await Util.GetTokenAsync("BizAdminFull"), d.ToString()); - Util.ValidateHTTPStatusCode(a, 400); - Util.ShouldContainValidationError(a, "Template", "2201", "Template array item 0, \"fld\" property exists but is empty, a value is required"); - Util.ShouldContainValidationError(a, "Template", "2203", "Template array item 0, fld property value \"\" is not a valid form field value for formKey specified"); - Util.ShouldContainValidationError(a, "Template", "2203", "Template array item 1, fld property value \"ThisFieldKeyDoesNotExist\" is not a valid form field value for formKey specified"); - Util.ShouldContainValidationError(a, "Template", "2203", "Template array item 2 (\"Name\"), \"hide\" property value of \"True\" is not valid, this field is core and cannot be hidden"); - Util.ShouldContainValidationError(a, "Template", "2203", "Template array item 3 (\"UserCustom1\"), \"type\" property value is MISSING for custom field, Custom fields MUST have types specified"); - Util.ShouldContainValidationError(a, "Template", "2203", "Template array item 4 (\"EmployeeNumber\"), \"type\" property value is not valid, only Custom fields can have types specified"); - Util.ShouldContainValidationError(a, "Template", "2203", "Template array item 5 (\"UserCustom2\"), \"type\" property value of \"999\" is not a valid custom field type"); - Util.ShouldContainValidationError(a, "Template", "2201", "Template array item 6, object is missing \"required\" property. All items must contain this property."); - - /* - "{\"error\":{\"code\":\"2200\",\"details\":[ - {\"message\":\"Template array item 0, \\\"fld\\\" property exists but is empty, a value is required\",\"target\":\"Template\",\"error\":\"2201\"}, - {\"message\":\"Template array item 0, fld property value \\\"\\\" is not a valid form field value for formKey specified\",\"target\":\"Template\",\"error\":\"2203\"}, - {\"message\":\"Template array item 1, fld property value \\\"ThisFieldKeyDoesNotExist\\\" is not a valid form field value for formKey specified\",\"target\":\"Template\",\"error\":\"2203\"}, - {\"message\":\"Template array item 2 (\\\"Name\\\"), \\\"hide\\\" property value of \\\"True\\\" is not valid, this field is core and cannot be hidden\",\"target\":\"Template\",\"error\":\"2203\"}, - {\"message\":\"Template array item 3 (\\\"UserCustom1\\\"), \\\"type\\\" property value is MISSING for custom filed, Custom fields MUST have types specified\",\"target\":\"Template\",\"error\":\"2203\"}, - {\"message\":\"Template array item 4 (\\\"EmployeeNumber\\\"), \\\"type\\\" property value is not valid, only Custom fields can have types specified\",\"target\":\"Template\",\"error\":\"2203\"}, - {\"message\":\"Template array item 5 (\\\"UserCustom2\\\"), \\\"type\\\" property value of \\\"999\\\" is not a valid custom field type\",\"target\":\"Template\",\"error\":\"2203\"}, - {\"message\":\"Template array item 6, object is missing \\\"required\\\" property. All items must contain this property. \",\"target\":\"Template\",\"error\":\"2201\"} - ],\"message\":\"Object did not pass validation\"}}" - */ - } - - - /// - /// - /// - [Fact] - public async void InvalidObjectFieldsFormKeyShouldFail() - { - ApiResponse a = await Util.GetAsync("form-field-definition/nonexistent", await Util.GetTokenAsync("BizAdminFull")); - Util.ValidateErrorCodeResponse(a, 2010, 404); - } - - - /// - /// - /// - [Fact] - public async void ObjectFieldsWorks() - { - ApiResponse a = await Util.GetAsync("form-field-definition/Widget", await Util.GetTokenAsync("BizAdminFull")); - Util.ValidateDataReturnResponseOk(a); - ((JArray)a.ObjectResponse["data"]).Count.Should().BeGreaterThan(25); - } - - - /// - /// - /// - [Fact] - public async void AvailableCustomizableFormKeysWorks() - { - ApiResponse a = await Util.GetAsync("form-custom/availablecustomizableformkeys", await Util.GetTokenAsync("BizAdminFull")); - Util.ValidateDataReturnResponseOk(a); - ((JArray)a.ObjectResponse["data"]).Count.Should().BeGreaterThan(1);//is 2 as of writing (widget,user) - } - - - - /// - /// - /// - [Fact] - public async void AvailableCustomTypesWorks() - { - ApiResponse a = await Util.GetAsync("form-custom/availablecustomtypes", await Util.GetTokenAsync("BizAdminFull")); - Util.ValidateDataReturnResponseOk(a); - ((JArray)a.ObjectResponse["data"]).Count.Should().BeGreaterThan(4); - } - - - - - - - //================================================== - - }//eoc -}//eons +using System; +using Xunit; +using Newtonsoft.Json.Linq; +using FluentAssertions; +using System.Collections.Generic; +using System.Collections.Concurrent; + +namespace raven_integration +{ + + public class FormCustom + { + public enum AyaUiFieldDataType : int + { + NoType = 0, + DateTime = 1, + Date = 2, + Time = 3, + Text = 4, + Integer = 5, + Bool = 6, + Decimal = 7, + Currency = 8, + Tags = 9, + Enum = 10, + EmailAddress = 11 + + } + + /// + /// Test create or update + /// + [Fact] + public async Task FormCustomUpdate() + { + + //This is a special case, you can PUT a formcustom, but you can't delete one and you can't create one + /* + + */ + + dynamic d = new JObject(); + d.formkey = "User"; + + dynamic dtemplate = new JArray(); + + dynamic dt = new JObject(); + dt.fld = "UserCustom1"; + dt.hide = false; + dt.required = true; + dt.type = AyaUiFieldDataType.Text; + dtemplate.Add(dt); + + + dt = new JObject(); + dt.fld = "Notes"; + dt.required = true; + dtemplate.Add(dt); + + dt = new JObject(); + dt.fld = "UserCustom2"; + dt.hide = true; + dt.required = false; + dt.type = AyaUiFieldDataType.Bool; + dtemplate.Add(dt); + + d.template = dtemplate.ToString();//it expects it to be a json string, not actual json + + + //RETRIEVE + //Get the current one (server will create if non-existent) + ApiResponse a = await Util.GetAsync("form-custom/User", await Util.GetTokenAsync("BizAdminFull")); + + //Update + d.concurrency = a.ObjectResponse["data"]["concurrency"].Value(); + a = await Util.PutAsync("form-custom/User", await Util.GetTokenAsync("BizAdminFull"), d.ToString()); + Util.ValidateHTTPStatusCode(a, 200); + + //check the concurrency token cache scheme + uint token = a.ObjectResponse["data"]["concurrency"].Value(); + //This should return a 304 not modified + a = await Util.GetAsync($"form-custom/User?concurrency={token}", await Util.GetTokenAsync("BizAdminFull")); + Util.ValidateHTTPStatusCode(a, 304); + + //and this should return the whole object + token--;//make the token not match + //This should return a 200 and the whole object + a = await Util.GetAsync($"form-custom/User?concurrency={token}", await Util.GetTokenAsync("BizAdminFull")); + Util.ValidateDataReturnResponseOk(a); + } + + + + + /// + /// Ensure validation works in FormCustombiz + /// + [Fact] + public async Task ValidatesProperly() + { + + dynamic d = new JObject(); + d.formkey = "User"; + + dynamic dtemplate = new JArray(); + + dynamic dt = new JObject(); + dt.fld = string.Empty;//expected ApiErrorCode.VALIDATION_REQUIRED Missing key 2 errors 2201 and 2203 + dt.hide = false; + dt.required = true; + dtemplate.Add(dt); + + + dt = new JObject(); + dt.fld = "ThisFieldKeyDoesNotExist";//expected ApiErrorCode.VALIDATION_INVALID_VALUE Bad key + dt.required = true; + dtemplate.Add(dt); + + dt = new JObject(); + dt.fld = "Name";//expect ApiErrorCode.VALIDATION_INVALID_VALUE required field not hideable + dt.hide = true; + dt.required = true; + dtemplate.Add(dt); + + dt = new JObject(); + dt.fld = "UserCustom1";//expected ApiErrorCode.VALIDATION_INVALID_VALUE type missing for custom field + dt.hide = false; + dt.required = false; + dtemplate.Add(dt); + + dt = new JObject(); + dt.fld = "EmployeeNumber";//expect ApiErrorCode.VALIDATION_INVALID_VALUE not custom field but type specified anyway + dt.hide = true; + dt.required = false; + dt.type = AyaUiFieldDataType.EmailAddress;//type specified (doesn't matter what type) + dtemplate.Add(dt); + + dt = new JObject(); + dt.fld = "UserCustom2";//expected ApiErrorCode.VALIDATION_INVALID_VALUE type missing for custom field + dt.hide = false; + dt.required = false; + dtemplate.Add(dt); + dt.type = 999;//not a valid type + + dt = new JObject(); + dt.fld = "Notes";//expect ApiErrorCode.VALIDATION_REQUIRED required property is always required (no idea why, just designed that way and that's the rule) + dt.hide = true; + // dt.required = false; Deliberately not set + dtemplate.Add(dt); + + d.template = dtemplate.ToString();//it expects it to be a json string, not actual json + + + //RETRIEVE + //Get the current one (server will create if non-existent) + ApiResponse a = await Util.GetAsync("form-custom/User", await Util.GetTokenAsync("BizAdminFull")); + + //Update + d.concurrency = a.ObjectResponse["data"]["concurrency"].Value(); + a = await Util.PutAsync("form-custom/User", await Util.GetTokenAsync("BizAdminFull"), d.ToString()); + Util.ValidateHTTPStatusCode(a, 400); + Util.ShouldContainValidationError(a, "Template", "2201", "Template array item 0, \"fld\" property exists but is empty, a value is required"); + Util.ShouldContainValidationError(a, "Template", "2203", "Template array item 0, fld property value \"\" is not a valid form field value for formKey specified"); + Util.ShouldContainValidationError(a, "Template", "2203", "Template array item 1, fld property value \"ThisFieldKeyDoesNotExist\" is not a valid form field value for formKey specified"); + Util.ShouldContainValidationError(a, "Template", "2203", "Template array item 2 (\"Name\"), \"hide\" property value of \"True\" is not valid, this field is core and cannot be hidden"); + Util.ShouldContainValidationError(a, "Template", "2203", "Template array item 3 (\"UserCustom1\"), \"type\" property value is MISSING for custom field, Custom fields MUST have types specified"); + Util.ShouldContainValidationError(a, "Template", "2203", "Template array item 4 (\"EmployeeNumber\"), \"type\" property value is not valid, only Custom fields can have types specified"); + Util.ShouldContainValidationError(a, "Template", "2203", "Template array item 5 (\"UserCustom2\"), \"type\" property value of \"999\" is not a valid custom field type"); + Util.ShouldContainValidationError(a, "Template", "2201", "Template array item 6, object is missing \"required\" property. All items must contain this property."); + + /* + "{\"error\":{\"code\":\"2200\",\"details\":[ + {\"message\":\"Template array item 0, \\\"fld\\\" property exists but is empty, a value is required\",\"target\":\"Template\",\"error\":\"2201\"}, + {\"message\":\"Template array item 0, fld property value \\\"\\\" is not a valid form field value for formKey specified\",\"target\":\"Template\",\"error\":\"2203\"}, + {\"message\":\"Template array item 1, fld property value \\\"ThisFieldKeyDoesNotExist\\\" is not a valid form field value for formKey specified\",\"target\":\"Template\",\"error\":\"2203\"}, + {\"message\":\"Template array item 2 (\\\"Name\\\"), \\\"hide\\\" property value of \\\"True\\\" is not valid, this field is core and cannot be hidden\",\"target\":\"Template\",\"error\":\"2203\"}, + {\"message\":\"Template array item 3 (\\\"UserCustom1\\\"), \\\"type\\\" property value is MISSING for custom filed, Custom fields MUST have types specified\",\"target\":\"Template\",\"error\":\"2203\"}, + {\"message\":\"Template array item 4 (\\\"EmployeeNumber\\\"), \\\"type\\\" property value is not valid, only Custom fields can have types specified\",\"target\":\"Template\",\"error\":\"2203\"}, + {\"message\":\"Template array item 5 (\\\"UserCustom2\\\"), \\\"type\\\" property value of \\\"999\\\" is not a valid custom field type\",\"target\":\"Template\",\"error\":\"2203\"}, + {\"message\":\"Template array item 6, object is missing \\\"required\\\" property. All items must contain this property. \",\"target\":\"Template\",\"error\":\"2201\"} + ],\"message\":\"Object did not pass validation\"}}" + */ + } + + + /// + /// + /// + [Fact] + public async Task InvalidObjectFieldsFormKeyShouldFail() + { + ApiResponse a = await Util.GetAsync("form-field-definition/nonexistent", await Util.GetTokenAsync("BizAdminFull")); + Util.ValidateErrorCodeResponse(a, 2010, 404); + } + + + /// + /// + /// + [Fact] + public async Task ObjectFieldsWorks() + { + ApiResponse a = await Util.GetAsync("form-field-definition/Widget", await Util.GetTokenAsync("BizAdminFull")); + Util.ValidateDataReturnResponseOk(a); + ((JArray)a.ObjectResponse["data"]).Count.Should().BeGreaterThan(25); + } + + + /// + /// + /// + [Fact] + public async Task AvailableCustomizableFormKeysWorks() + { + ApiResponse a = await Util.GetAsync("form-custom/availablecustomizableformkeys", await Util.GetTokenAsync("BizAdminFull")); + Util.ValidateDataReturnResponseOk(a); + ((JArray)a.ObjectResponse["data"]).Count.Should().BeGreaterThan(1);//is 2 as of writing (widget,user) + } + + + + /// + /// + /// + [Fact] + public async Task AvailableCustomTypesWorks() + { + ApiResponse a = await Util.GetAsync("form-custom/availablecustomtypes", await Util.GetTokenAsync("BizAdminFull")); + Util.ValidateDataReturnResponseOk(a); + ((JArray)a.ObjectResponse["data"]).Count.Should().BeGreaterThan(4); + } + + + + + + + //================================================== + + }//eoc +}//eons diff --git a/Global/GlobalAll.cs b/Global/GlobalAll.cs index fa40f07..fe50fd6 100644 --- a/Global/GlobalAll.cs +++ b/Global/GlobalAll.cs @@ -1,29 +1,29 @@ -using Xunit; -using FluentAssertions; - -namespace raven_integration -{ - public class GlobalAll - { - /// - /// Test Global routes - /// - [Fact] - public async void GlobalOps() - { - //excercise the fetch and update routes but no actual changes because making a change of any kind to global will likely break other tests - //and we just need to see the routes are active really - - ApiResponse a = await Util.GetAsync("global-biz-setting", await Util.GetTokenAsync("BizAdminFull")); - Util.ValidateDataReturnResponseOk(a); - a.ObjectResponse["data"]["searchCaseSensitiveOnly"].Should().NotBeNull(); - - var g = a.ObjectResponse["data"]; - a = await Util.PutAsync("global-biz-setting", await Util.GetTokenAsync("BizAdminFull"), g.ToString(Newtonsoft.Json.Formatting.None)); - Util.ValidateHTTPStatusCode(a, 200); - } - - //================================================== - - }//eoc -}//eons +using Xunit; +using FluentAssertions; + +namespace raven_integration +{ + public class GlobalAll + { + /// + /// Test Global routes + /// + [Fact] + public async Task GlobalOps() + { + //excercise the fetch and update routes but no actual changes because making a change of any kind to global will likely break other tests + //and we just need to see the routes are active really + + ApiResponse a = await Util.GetAsync("global-biz-setting", await Util.GetTokenAsync("BizAdminFull")); + Util.ValidateDataReturnResponseOk(a); + a.ObjectResponse["data"]["searchCaseSensitiveOnly"].Should().NotBeNull(); + + var g = a.ObjectResponse["data"]; + a = await Util.PutAsync("global-biz-setting", await Util.GetTokenAsync("BizAdminFull"), g.ToString(Newtonsoft.Json.Formatting.None)); + Util.ValidateHTTPStatusCode(a, 200); + } + + //================================================== + + }//eoc +}//eons diff --git a/LogFiles/LogFiles.cs b/LogFiles/LogFiles.cs index 06a13d5..0b6fccb 100644 --- a/LogFiles/LogFiles.cs +++ b/LogFiles/LogFiles.cs @@ -1,28 +1,28 @@ -using Xunit; -using FluentAssertions; - -namespace raven_integration -{ - - public class LogFiles - { - - - - /// - /// - /// - [Fact] - public async void MostRecentLogShouldFetch() - { - ApiTextResponse t = await Util.GetTextResultAsync("log-file/log-ayanova.txt", await Util.GetTokenAsync("OpsAdminFull")); - Util.ValidateHTTPStatusCode(t, 200); - string[] ExpectedLogItems = {"|INFO|","|ERROR|","|FATAL|", "|WARN|"};//assumes any log will have at least one of these items in it - t.TextResponse.Should().ContainAny(ExpectedLogItems); - - } - - //================================================== - - }//eoc -}//eons +using Xunit; +using FluentAssertions; + +namespace raven_integration +{ + + public class LogFiles + { + + + + /// + /// + /// + [Fact] + public async Task MostRecentLogShouldFetch() + { + ApiTextResponse t = await Util.GetTextResultAsync("log-file/log-ayanova.txt", await Util.GetTokenAsync("OpsAdminFull")); + Util.ValidateHTTPStatusCode(t, 200); + string[] ExpectedLogItems = {"|INFO|","|ERROR|","|FATAL|", "|WARN|"};//assumes any log will have at least one of these items in it + t.TextResponse.Should().ContainAny(ExpectedLogItems); + + } + + //================================================== + + }//eoc +}//eons diff --git a/Metrics/Metrics.cs b/Metrics/Metrics.cs index e6c0668..0e55f9b 100644 --- a/Metrics/Metrics.cs +++ b/Metrics/Metrics.cs @@ -1,63 +1,63 @@ -using System; -using Xunit; -using Newtonsoft.Json.Linq; -using FluentAssertions; -using System.Collections.Generic; -using System.Collections.Concurrent; - -namespace raven_integration -{ - - public class Metrics - { - - - - - - /// - /// - /// - [Fact] - public async void MetricsShouldFetch() - { - // DateTime tsEnd = DateTime.Now.ToOffsetAdjustedUniversalTime();//{2020-05-29 3:30:21 PM} - // DateTime tsStart = DateTime.Now.AddHours(-6).ToOffsetAdjustedUniversalTime();//{2020-05-29 9:30:21 AM} - - // DateTime tsEnd = DateTime.UtcNow;//{2020-05-29 3:32:54 PM} - // DateTime tsStart = DateTime.UtcNow.AddHours(-6); //{2020-05-29 9:32:54 AM} - - //weirdly, this is the only way to get the correct date range - //just as the html client does but from here - //in both cases the server shows parameters as local time to the server - //and in the route I have to adjust them back to universal time before sending them to the db query - //as the db data is in utc and the db server doesn't know what timezone it is - DateTime tsEnd = DateTime.Now;//{2020-05-29 8:36:48 AM} - DateTime tsStart = DateTime.Now.AddHours(-6); //{2020-05-29 2:36:48 AM} - - - - //http://localhost:7575/api/v8.0/server-metric/mm?maxRecords=200&tsStart=2020-05-29T09:23:18.114Z&tsEnd=2020-05-29T15:23:19.114Z - //from client at server route {2020-05-29 2:29:25 AM} {2020-05-29 8:29:26 AM} - - - - - - ApiResponse a = await Util.GetAsync($"server-metric/memcpu?tsStart={tsStart}&tsEnd={tsEnd}", await Util.GetTokenAsync("OpsAdminFull")); - Util.ValidateDataReturnResponseOk(a); - a.ObjectResponse["data"].Should().NotBeNull();//can't get more detailed as there might not be any data here to see - - a = await Util.GetAsync($"server-metric/storage?tsStart={tsStart}&tsEnd={tsEnd}", await Util.GetTokenAsync("OpsAdminFull")); - Util.ValidateDataReturnResponseOk(a); - a.ObjectResponse["data"].Should().NotBeNull();//can't get more detailed as there might not be any data here to see - - - - } - - - //================================================== - - }//eoc -}//eons +using System; +using Xunit; +using Newtonsoft.Json.Linq; +using FluentAssertions; +using System.Collections.Generic; +using System.Collections.Concurrent; + +namespace raven_integration +{ + + public class Metrics + { + + + + + + /// + /// + /// + [Fact] + public async Task MetricsShouldFetch() + { + // DateTime tsEnd = DateTime.Now.ToOffsetAdjustedUniversalTime();//{2020-05-29 3:30:21 PM} + // DateTime tsStart = DateTime.Now.AddHours(-6).ToOffsetAdjustedUniversalTime();//{2020-05-29 9:30:21 AM} + + // DateTime tsEnd = DateTime.UtcNow;//{2020-05-29 3:32:54 PM} + // DateTime tsStart = DateTime.UtcNow.AddHours(-6); //{2020-05-29 9:32:54 AM} + + //weirdly, this is the only way to get the correct date range + //just as the html client does but from here + //in both cases the server shows parameters as local time to the server + //and in the route I have to adjust them back to universal time before sending them to the db query + //as the db data is in utc and the db server doesn't know what timezone it is + DateTime tsEnd = DateTime.Now;//{2020-05-29 8:36:48 AM} + DateTime tsStart = DateTime.Now.AddHours(-6); //{2020-05-29 2:36:48 AM} + + + + //http://localhost:7575/api/v8.0/server-metric/mm?maxRecords=200&tsStart=2020-05-29T09:23:18.114Z&tsEnd=2020-05-29T15:23:19.114Z + //from client at server route {2020-05-29 2:29:25 AM} {2020-05-29 8:29:26 AM} + + + + + + ApiResponse a = await Util.GetAsync($"server-metric/memcpu?tsStart={tsStart}&tsEnd={tsEnd}", await Util.GetTokenAsync("OpsAdminFull")); + Util.ValidateDataReturnResponseOk(a); + a.ObjectResponse["data"].Should().NotBeNull();//can't get more detailed as there might not be any data here to see + + a = await Util.GetAsync($"server-metric/storage?tsStart={tsStart}&tsEnd={tsEnd}", await Util.GetTokenAsync("OpsAdminFull")); + Util.ValidateDataReturnResponseOk(a); + a.ObjectResponse["data"].Should().NotBeNull();//can't get more detailed as there might not be any data here to see + + + + } + + + //================================================== + + }//eoc +}//eons diff --git a/PickList/PickListAllTests.cs b/PickList/PickListAllTests.cs index 62783c5..303ac92 100644 --- a/PickList/PickListAllTests.cs +++ b/PickList/PickListAllTests.cs @@ -1,466 +1,466 @@ -using System; -using Xunit; -using Newtonsoft.Json.Linq; -using FluentAssertions; -using System.Collections.Generic; -using System.Collections.Concurrent; - -namespace raven_integration -{ - public class PickListAllTests - { - //NOTE: in order not to interfere in each other will use Widget picklist to test with standard unmodified picklist template - //and will use User pick-list to test the template functionality - - /// - /// Test all Template editing related routes - /// - [Fact] - public async void UserPickListTemplatesOps() - { - //NOTE: Due to there being only one possible template per type, this test will need to test ALL potential tests in one function - //and only for the User picklist in order to not step over other potential tests running in parallel - - //REPLACE USER TEMPLATE - dynamic d = new JObject(); - d.Id = 3;//User type - - //custom template, only one field employee number - dynamic dTemplateArray = new JArray(); - dynamic df = new JObject(); - df.fld = "useremployeenumber"; - dTemplateArray.Add(df); - d.Template = dTemplateArray.ToString(Newtonsoft.Json.Formatting.None); - - //replace the User template at the server - ApiResponse a = await Util.PostAsync("pick-list/template", await Util.GetTokenAsync("BizAdminFull"), d.ToString(Newtonsoft.Json.Formatting.None)); - Util.ValidateHTTPStatusCode(a, 204); - - - //RETRIEVE - //Get one - a = await Util.GetAsync("pick-list/template/3/", await Util.GetTokenAsync("BizAdminFull")); - Util.ValidateDataReturnResponseOk(a); - //assert contains ONE record ONLY and it's the one we set - var templateArray = JArray.Parse(a.ObjectResponse["data"]["template"].Value()); - templateArray.Count.Should().Be(1); - templateArray[0]["fld"].Value().Should().Be("useremployeenumber"); - - - //CONFIRM THE CUSTOM PICKLIST TEMPLATE WORKS PROPERLY - //MAKE THE TEST USERS - //First make a unique string for this iteration of this test only - var UniquePhrase = Util.Uniquify("pick").Replace(" ", ""); - d = new JObject(); - d.name = Util.Uniquify("UserPickListTemplatesOps") + UniquePhrase; - d.active = true; - d.login = Util.Uniquify("LOGIN"); - d.password = Util.Uniquify("PASSWORD"); - d.roles = 0;//norole - - d.userType = 3;//non scheduleable - //Required by form custom rules - d.notes = "notes"; - d.customFields = Util.UserRequiredCustomFieldsJsonString(); - - a = await Util.PostAsync("User", await Util.GetTokenAsync("superuser", "l3tm3in"), d.ToString()); - Util.ValidateDataReturnResponseOk(a); - long InNameId = a.ObjectResponse["data"]["id"].Value(); - - d = new JObject(); - d.name = Util.Uniquify("UserPickListTemplatesOps"); - d.employeeNumber = UniquePhrase; - d.login = Util.Uniquify("LOGIN"); - d.password = Util.Uniquify("PASSWORD"); - d.roles = 0;//norole - d.userType = 3;//non scheduleable - d.active = true; - //Required by form custom rules - d.notes = "notes"; - d.customFields = Util.UserRequiredCustomFieldsJsonString(); - - a = await Util.PostAsync("User", await Util.GetTokenAsync("superuser", "l3tm3in"), d.ToString()); - Util.ValidateDataReturnResponseOk(a); - long InEmployeeNumberId = a.ObjectResponse["data"]["id"].Value(); - - - //GET PICKLIST FOR unique phrase query sb only employee number due to custom template - a = await Util.GetAsync("pick-list/list?ayaType=3&query=" + UniquePhrase, await Util.GetTokenAsync("BizAdminFull")); - Util.ValidateDataReturnResponseOk(a); - var pickList = ((JArray)a.ObjectResponse["data"]); - pickList.Count.Should().Be(1); - pickList[0]["id"].Value().Should().Be(InEmployeeNumberId); - - //custom template, only one field user name - d = new JObject(); - d.Id = 3;//User type - dTemplateArray = new JArray(); - df = new JObject(); - df.fld = "username"; - dTemplateArray.Add(df); - d.Template = dTemplateArray.ToString(Newtonsoft.Json.Formatting.None); - - //replace the User template at the server - a = await Util.PostAsync("pick-list/template", await Util.GetTokenAsync("BizAdminFull"), d.ToString(Newtonsoft.Json.Formatting.None)); - Util.ValidateHTTPStatusCode(a, 204); - - //GET PICKLIST FOR unique phrase query sb only user name field due to custom template - a = await Util.GetAsync("pick-list/list?ayaType=3&query=" + UniquePhrase, await Util.GetTokenAsync("BizAdminFull")); - //"select auser.id as plId, auser.active as plActive, concat_ws(' ', auser.name) as plname from auser where auser.active = true and ((auser.name like '%pick1584556347748%')) order by auser.name limit 100" - Util.ValidateDataReturnResponseOk(a); - pickList = ((JArray)a.ObjectResponse["data"]); - pickList.Count.Should().Be(1); - pickList[0]["id"].Value().Should().Be(InNameId); - - //DELETE TEST USERS NO LONGER NEEDED - a = await Util.DeleteAsync("User/" + InNameId.ToString(), await Util.GetTokenAsync("superuser", "l3tm3in")); - Util.ValidateHTTPStatusCode(a, 204); - - a = await Util.DeleteAsync("User/" + InEmployeeNumberId.ToString(), await Util.GetTokenAsync("superuser", "l3tm3in")); - Util.ValidateHTTPStatusCode(a, 204); - - - // RESET TEMPLATE TO DEFAULT - a = await Util.DeleteAsync("pick-list/template/3/", await Util.GetTokenAsync("BizAdminFull")); - Util.ValidateHTTPStatusCode(a, 204); - - //RETRIEVE (Confirm it's back to default) - //Get one - a = await Util.GetAsync("pick-list/template/3/", await Util.GetTokenAsync("BizAdminFull")); - Util.ValidateDataReturnResponseOk(a); - //assert contains default template record ONLY and it's the one we set - templateArray = JArray.Parse(a.ObjectResponse["data"]["template"].Value()); - templateArray.Count.Should().Be(3); - templateArray[0]["fld"].Value().Should().Be("username"); - - - //Now test error conditions.... - //BAD FIELD NAME VALIDATION ERROR - d = new JObject(); - d.Id = 3;//User type - //template, simple test, nothing fancy - dTemplateArray = new JArray(); - df = new JObject(); - df.fld = "DOES_NOT_EXIST";//<-- ERROR BAD FIELD NAME - dTemplateArray.Add(df); - d.Template = dTemplateArray.ToString(Newtonsoft.Json.Formatting.None); - a = await Util.PostAsync("pick-list/template", await Util.GetTokenAsync("BizAdminFull"), d.ToString(Newtonsoft.Json.Formatting.None)); - //"{\"error\":{\"code\":\"2200\",\"details\":[{\"message\":\"Template array item 0, fld property value \\\"DOES_NOT_EXIST\\\" is not a valid value for AyaType specified\",\"target\":\"Template\",\"error\":\"2203\"}],\"message\":\"Object did not pass validation\"}}" - Util.ValidateErrorCodeResponse(a, 2200, 400); - Util.ShouldContainValidationError(a, "Template", "2203"); - - //BAD AYATYPE ERROR - d = new JObject(); - d.Id = 0;//<==ERROR NO_TYPE, INVALID - //template, simple test, nothing fancy - dTemplateArray = new JArray(); - df = new JObject(); - df.fld = "useremployeenumber"; - dTemplateArray.Add(df); - d.Template = dTemplateArray.ToString(Newtonsoft.Json.Formatting.None); - //replace the User template at the server - a = await Util.PostAsync("pick-list/template", await Util.GetTokenAsync("BizAdminFull"), d.ToString(Newtonsoft.Json.Formatting.None)); - //"{\"error\":{\"code\":\"2200\",\"details\":[{\"message\":\"Template array item 0, fld property value \\\"DOES_NOT_EXIST\\\" is not a valid value for AyaType specified\",\"target\":\"Template\",\"error\":\"2203\"}],\"message\":\"Object did not pass validation\"}}" - Util.ValidateErrorCodeResponse(a, 2200, 400); - Util.ShouldContainValidationError(a, "ayaType", "2203"); - - //RIGHTS ISSUE, - //currently only bizadminfull can change a picklist template - d = new JObject(); - d.Id = 3;//User - //template, simple test, nothing fancy - dTemplateArray = new JArray(); - df = new JObject(); - df.fld = "useremployeenumber"; - dTemplateArray.Add(df); - d.Template = dTemplateArray.ToString(Newtonsoft.Json.Formatting.None); - //ERROR NO RIGHTS USER - a = await Util.PostAsync("pick-list/template", await Util.GetTokenAsync("CustomerLimited"), d.ToString(Newtonsoft.Json.Formatting.None)); - //"{\"error\":{\"code\":\"2004\",\"message\":\"User not authorized for this resource operation (insufficient rights)\"}}" - Util.ValidateErrorCodeResponse(a, 2004, 403); - - //EMPTY TEMPLATE VALIDATION ERROR - d = new JObject(); - d.Id = 3;//User - d.Template = "";//<-- ERROR no template - a = await Util.PostAsync("pick-list/template", await Util.GetTokenAsync("BizAdminFull"), d.ToString(Newtonsoft.Json.Formatting.None)); - Util.ValidateErrorCodeResponse(a, 2200, 400); - Util.ShouldContainValidationError(a, "Template", "2201"); - - - //MALFORMED TEMPLATE JSON ERROR - d = new JObject(); - d.Id = 3;//User type - dTemplateArray = new JArray(); - df = new JObject(); - df.fld = "useremployeenumber"; - dTemplateArray.Add(df); - string sTemplate = dTemplateArray.ToString(Newtonsoft.Json.Formatting.None); - d.Template = sTemplate.Substring(2);//<-- ERROR missing first two characters of json template array - a = await Util.PostAsync("pick-list/template", await Util.GetTokenAsync("BizAdminFull"), d.ToString(Newtonsoft.Json.Formatting.None)); - //"{\"error\":{\"code\":\"2200\",\"details\":[{\"message\":\"Template is not valid JSON string: Error reading JArray from JsonReader. Current JsonReader item is not an array: String. Path '', line 1, position 5.\",\"target\":\"Template\",\"error\":\"2203\"}],\"message\":\"Object did not pass validation\"}}" - Util.ValidateErrorCodeResponse(a, 2200, 400); - Util.ShouldContainValidationError(a, "Template", "2203"); - - } - - /// - /// test get templates list - /// - [Fact] - public async void PickListTemplateList() - { - //RETRIEVE - ApiResponse a = await Util.GetAsync("pick-list/template/list", await Util.GetTokenAsync("BizAdminFull")); - Util.ValidateDataReturnResponseOk(a); - //assert contains at least two records (as we only have two at time of writing this test) - var templateList = ((JArray)a.ObjectResponse["data"]); - templateList.Count.Should().BeGreaterThan(1); - templateList[0]["id"].Value().Should().Be(2);//first one should be a widget - } - - - /// - /// test get picklist fields list for widget template - /// - [Fact] - public async void WidgetPickListTemplateFieldList() - { - //RETRIEVE WIDGET PICKLIST FIELDS - ApiResponse a = await Util.GetAsync("pick-list/template/ListFields/2", await Util.GetTokenAsync("BizAdminFull")); - Util.ValidateDataReturnResponseOk(a); - //assert contains at least two records (as we only have two at time of writing this test) - var templateList = ((JArray)a.ObjectResponse["data"]); - templateList.Count.Should().BeGreaterThan(4); - templateList[0]["fieldKey"].Value().Should().Be("widgetactive");//first one should be a widgetactive field - } - - - /// - /// test get picklist for widget without query - /// - [Fact] - public async void FetchWidgetPickListNoQuery() - { - //RETRIEVE WIDGET PICKLIST no filter - ApiResponse a = await Util.GetAsync("pick-list/list?ayaType=2", await Util.GetTokenAsync("BizAdminFull")); - Util.ValidateDataReturnResponseOk(a); - //assert contains 100 records (current picklist maximum count) - var pickList = ((JArray)a.ObjectResponse["data"]); - pickList.Count.Should().Be(100); - } - - - /// - /// test get picklist for single predefined value only - /// - [Fact] - public async void FetchWidgetPickListPreDefined() - { - //fetch the SuperUser account which always exists - ApiResponse a = await Util.GetAsync("pick-list/list?ayaType=3&preId=1", await Util.GetTokenAsync("BizAdminFull")); - Util.ValidateDataReturnResponseOk(a); - //assert contains 1 record - var pickList = ((JArray)a.ObjectResponse["data"]); - pickList.Count.Should().Be(1); - pickList[0]["id"].Value().Should().Be(1); - - } - - - /// - /// test get picklist for widget with basic autocomplete query only - /// - [Fact] - public async void FetchWidgetPickListAutoComplete() - { - - //make key widget - - var WidgetNameStart = "FetchWidgetPickListAutoComplete_a1b2c3"; - long IncludedWidgetId = 0; - //CREATE TEST WIDGETS - //included widget - dynamic w = new JObject(); - w.name = Util.Uniquify(WidgetNameStart); - w.customFields = Util.WidgetRequiredCustomFieldsJsonString(); - w.notes = "blah"; - w.active = true; - w.usertype = 1; - w.dollarAmount = 555.55; - - ApiResponse a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w.ToString()); - Util.ValidateDataReturnResponseOk(a); - IncludedWidgetId = a.ObjectResponse["data"]["id"].Value(); - - - //RETRIEVE WIDGET PICKLIST with name filter - a = await Util.GetAsync("pick-list/list?ayaType=2&query=a1b2c3", await Util.GetTokenAsync("BizAdminFull")); - Util.ValidateDataReturnResponseOk(a); - - var pickList = ((JArray)a.ObjectResponse["data"]); - pickList.Count.Should().BeGreaterThan(0); - pickList[0]["name"].Value().Should().Contain("_a1b2c3"); - - //DELETE WIDGETS - a = await Util.DeleteAsync("widget/" + IncludedWidgetId.ToString(), await Util.GetTokenAsync("BizAdminFull")); - Util.ValidateHTTPStatusCode(a, 204); - } - - - /// - /// - /// - [Fact] - public async void FetchWidgetPickListTags() - { - - //make key widget - var WidgetNameStart = "FetchWidgetPickListTags"; - long IncludedWidgetId = 0; - //CREATE TEST WIDGETS - //included widget - dynamic w = new JObject(); - w.name = Util.Uniquify(WidgetNameStart); - w.customFields = Util.WidgetRequiredCustomFieldsJsonString(); - w.notes = "blah"; - w.active = true; - w.usertype = 1; - w.dollarAmount = 555.55; - //Tags - dynamic InclusiveTagsArray = new JArray(); - InclusiveTagsArray.Add("plred"); - InclusiveTagsArray.Add("plblue"); - w.tags = InclusiveTagsArray; - - ApiResponse a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w.ToString()); - Util.ValidateDataReturnResponseOk(a); - IncludedWidgetId = a.ObjectResponse["data"]["id"].Value(); - - - //RETRIEVE WIDGET PICKLIST with name filter - a = await Util.GetAsync("pick-list/list?ayaType=2&query=..lblu", await Util.GetTokenAsync("BizAdminFull")); - Util.ValidateDataReturnResponseOk(a); - - var pickList = ((JArray)a.ObjectResponse["data"]); - pickList.Count.Should().Be(1); - pickList[0]["id"].Value().Should().Be(IncludedWidgetId); - - //DELETE WIDGETS - a = await Util.DeleteAsync("widget/" + IncludedWidgetId.ToString(), await Util.GetTokenAsync("BizAdminFull")); - Util.ValidateHTTPStatusCode(a, 204); - } - - - /// - /// test get picklist for widget with basic autocomplete query only - /// - [Fact] - public async void FetchWidgetPickListInactiveActive() - { - - //make key widget - - var WidgetNameStart = "FetchWidgetPickListInactiveActive"; - List ActiveWidgetIdList = new List(); - List NotActiveWidgetIdList = new List(); - - //CREATE 4 TEST WIDGETS - //two active and two non active - - //first active widget - dynamic w = new JObject(); - w.name = Util.Uniquify(WidgetNameStart); - w.customFields = Util.WidgetRequiredCustomFieldsJsonString(); - w.notes = "blah"; - w.active = true; - w.usertype = 1; - - ApiResponse a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w.ToString()); - Util.ValidateDataReturnResponseOk(a); - ActiveWidgetIdList.Add(a.ObjectResponse["data"]["id"].Value()); - - //second active widget - w.name = Util.Uniquify(WidgetNameStart); - - a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w.ToString()); - Util.ValidateDataReturnResponseOk(a); - ActiveWidgetIdList.Add(a.ObjectResponse["data"]["id"].Value()); - - - //first NON active widget - w.name = Util.Uniquify(WidgetNameStart); - w.active = false; - - a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w.ToString()); - Util.ValidateDataReturnResponseOk(a); - NotActiveWidgetIdList.Add(a.ObjectResponse["data"]["id"].Value()); - - //second NON active widget - w.name = Util.Uniquify(WidgetNameStart); - w.active = false; - - a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w.ToString()); - Util.ValidateDataReturnResponseOk(a); - NotActiveWidgetIdList.Add(a.ObjectResponse["data"]["id"].Value()); - - - //CONFIRM BOTH INACTIVE AND ACTIVE - a = await Util.GetAsync("pick-list/list?ayaType=2&query=ickListInactiveAct&inactive=true", await Util.GetTokenAsync("BizAdminFull")); - Util.ValidateDataReturnResponseOk(a); - var pickList = ((JArray)a.ObjectResponse["data"]); - //assert contains at least two records - pickList.Count.Should().BeGreaterThan(1); - int nActiveMatches = 0; - int nInactiveMatches = 0; - foreach (JObject o in pickList) - { - if (ActiveWidgetIdList.Contains(o["id"].Value())) - nActiveMatches++; - if (NotActiveWidgetIdList.Contains(o["id"].Value())) - nInactiveMatches++; - } - nActiveMatches.Should().Be(ActiveWidgetIdList.Count); - nInactiveMatches.Should().Be(NotActiveWidgetIdList.Count); - - - //CONFIRM ACTIVE ONLY - a = await Util.GetAsync("pick-list/list?ayaType=2&query=ickListInactiveAct", await Util.GetTokenAsync("BizAdminFull")); - Util.ValidateDataReturnResponseOk(a); - pickList = ((JArray)a.ObjectResponse["data"]); - //assert contains at least two records - pickList.Count.Should().BeGreaterThan(1); - nActiveMatches = 0; - nInactiveMatches = 0; - foreach (JObject o in pickList) - { - if (ActiveWidgetIdList.Contains(o["id"].Value())) - nActiveMatches++; - if (NotActiveWidgetIdList.Contains(o["id"].Value())) - nInactiveMatches++; - } - nActiveMatches.Should().Be(ActiveWidgetIdList.Count); - nInactiveMatches.Should().Be(0); - - //DELETE WIDGETS - foreach (long l in ActiveWidgetIdList) - { - a = await Util.DeleteAsync("widget/" + l.ToString(), await Util.GetTokenAsync("BizAdminFull")); - Util.ValidateHTTPStatusCode(a, 204); - } - - foreach (long l in NotActiveWidgetIdList) - { - a = await Util.DeleteAsync("widget/" + l.ToString(), await Util.GetTokenAsync("BizAdminFull")); - Util.ValidateHTTPStatusCode(a, 204); - } - } - - - - - - //================================================== - - }//eoc -}//eons +using System; +using Xunit; +using Newtonsoft.Json.Linq; +using FluentAssertions; +using System.Collections.Generic; +using System.Collections.Concurrent; + +namespace raven_integration +{ + public class PickListAllTests + { + //NOTE: in order not to interfere in each other will use Widget picklist to test with standard unmodified picklist template + //and will use User pick-list to test the template functionality + + /// + /// Test all Template editing related routes + /// + [Fact] + public async Task UserPickListTemplatesOps() + { + //NOTE: Due to there being only one possible template per type, this test will need to test ALL potential tests in one function + //and only for the User picklist in order to not step over other potential tests running in parallel + + //REPLACE USER TEMPLATE + dynamic d = new JObject(); + d.Id = 3;//User type + + //custom template, only one field employee number + dynamic dTemplateArray = new JArray(); + dynamic df = new JObject(); + df.fld = "useremployeenumber"; + dTemplateArray.Add(df); + d.Template = dTemplateArray.ToString(Newtonsoft.Json.Formatting.None); + + //replace the User template at the server + ApiResponse a = await Util.PostAsync("pick-list/template", await Util.GetTokenAsync("BizAdminFull"), d.ToString(Newtonsoft.Json.Formatting.None)); + Util.ValidateHTTPStatusCode(a, 204); + + + //RETRIEVE + //Get one + a = await Util.GetAsync("pick-list/template/3/", await Util.GetTokenAsync("BizAdminFull")); + Util.ValidateDataReturnResponseOk(a); + //assert contains ONE record ONLY and it's the one we set + var templateArray = JArray.Parse(a.ObjectResponse["data"]["template"].Value()); + templateArray.Count.Should().Be(1); + templateArray[0]["fld"].Value().Should().Be("useremployeenumber"); + + + //CONFIRM THE CUSTOM PICKLIST TEMPLATE WORKS PROPERLY + //MAKE THE TEST USERS + //First make a unique string for this iteration of this test only + var UniquePhrase = Util.Uniquify("pick").Replace(" ", ""); + d = new JObject(); + d.name = Util.Uniquify("UserPickListTemplatesOps") + UniquePhrase; + d.active = true; + d.login = Util.Uniquify("LOGIN"); + d.password = Util.Uniquify("PASSWORD"); + d.roles = 0;//norole + + d.userType = 3;//non scheduleable + //Required by form custom rules + d.notes = "notes"; + d.customFields = Util.UserRequiredCustomFieldsJsonString(); + + a = await Util.PostAsync("User", await Util.GetTokenAsync("superuser", "l3tm3in"), d.ToString()); + Util.ValidateDataReturnResponseOk(a); + long InNameId = a.ObjectResponse["data"]["id"].Value(); + + d = new JObject(); + d.name = Util.Uniquify("UserPickListTemplatesOps"); + d.employeeNumber = UniquePhrase; + d.login = Util.Uniquify("LOGIN"); + d.password = Util.Uniquify("PASSWORD"); + d.roles = 0;//norole + d.userType = 3;//non scheduleable + d.active = true; + //Required by form custom rules + d.notes = "notes"; + d.customFields = Util.UserRequiredCustomFieldsJsonString(); + + a = await Util.PostAsync("User", await Util.GetTokenAsync("superuser", "l3tm3in"), d.ToString()); + Util.ValidateDataReturnResponseOk(a); + long InEmployeeNumberId = a.ObjectResponse["data"]["id"].Value(); + + + //GET PICKLIST FOR unique phrase query sb only employee number due to custom template + a = await Util.GetAsync("pick-list/list?ayaType=3&query=" + UniquePhrase, await Util.GetTokenAsync("BizAdminFull")); + Util.ValidateDataReturnResponseOk(a); + var pickList = ((JArray)a.ObjectResponse["data"]); + pickList.Count.Should().Be(1); + pickList[0]["id"].Value().Should().Be(InEmployeeNumberId); + + //custom template, only one field user name + d = new JObject(); + d.Id = 3;//User type + dTemplateArray = new JArray(); + df = new JObject(); + df.fld = "username"; + dTemplateArray.Add(df); + d.Template = dTemplateArray.ToString(Newtonsoft.Json.Formatting.None); + + //replace the User template at the server + a = await Util.PostAsync("pick-list/template", await Util.GetTokenAsync("BizAdminFull"), d.ToString(Newtonsoft.Json.Formatting.None)); + Util.ValidateHTTPStatusCode(a, 204); + + //GET PICKLIST FOR unique phrase query sb only user name field due to custom template + a = await Util.GetAsync("pick-list/list?ayaType=3&query=" + UniquePhrase, await Util.GetTokenAsync("BizAdminFull")); + //"select auser.id as plId, auser.active as plActive, concat_ws(' ', auser.name) as plname from auser where auser.active = true and ((auser.name like '%pick1584556347748%')) order by auser.name limit 100" + Util.ValidateDataReturnResponseOk(a); + pickList = ((JArray)a.ObjectResponse["data"]); + pickList.Count.Should().Be(1); + pickList[0]["id"].Value().Should().Be(InNameId); + + //DELETE TEST USERS NO LONGER NEEDED + a = await Util.DeleteAsync("User/" + InNameId.ToString(), await Util.GetTokenAsync("superuser", "l3tm3in")); + Util.ValidateHTTPStatusCode(a, 204); + + a = await Util.DeleteAsync("User/" + InEmployeeNumberId.ToString(), await Util.GetTokenAsync("superuser", "l3tm3in")); + Util.ValidateHTTPStatusCode(a, 204); + + + // RESET TEMPLATE TO DEFAULT + a = await Util.DeleteAsync("pick-list/template/3/", await Util.GetTokenAsync("BizAdminFull")); + Util.ValidateHTTPStatusCode(a, 204); + + //RETRIEVE (Confirm it's back to default) + //Get one + a = await Util.GetAsync("pick-list/template/3/", await Util.GetTokenAsync("BizAdminFull")); + Util.ValidateDataReturnResponseOk(a); + //assert contains default template record ONLY and it's the one we set + templateArray = JArray.Parse(a.ObjectResponse["data"]["template"].Value()); + templateArray.Count.Should().Be(3); + templateArray[0]["fld"].Value().Should().Be("username"); + + + //Now test error conditions.... + //BAD FIELD NAME VALIDATION ERROR + d = new JObject(); + d.Id = 3;//User type + //template, simple test, nothing fancy + dTemplateArray = new JArray(); + df = new JObject(); + df.fld = "DOES_NOT_EXIST";//<-- ERROR BAD FIELD NAME + dTemplateArray.Add(df); + d.Template = dTemplateArray.ToString(Newtonsoft.Json.Formatting.None); + a = await Util.PostAsync("pick-list/template", await Util.GetTokenAsync("BizAdminFull"), d.ToString(Newtonsoft.Json.Formatting.None)); + //"{\"error\":{\"code\":\"2200\",\"details\":[{\"message\":\"Template array item 0, fld property value \\\"DOES_NOT_EXIST\\\" is not a valid value for AyaType specified\",\"target\":\"Template\",\"error\":\"2203\"}],\"message\":\"Object did not pass validation\"}}" + Util.ValidateErrorCodeResponse(a, 2200, 400); + Util.ShouldContainValidationError(a, "Template", "2203"); + + //BAD AYATYPE ERROR + d = new JObject(); + d.Id = 0;//<==ERROR NO_TYPE, INVALID + //template, simple test, nothing fancy + dTemplateArray = new JArray(); + df = new JObject(); + df.fld = "useremployeenumber"; + dTemplateArray.Add(df); + d.Template = dTemplateArray.ToString(Newtonsoft.Json.Formatting.None); + //replace the User template at the server + a = await Util.PostAsync("pick-list/template", await Util.GetTokenAsync("BizAdminFull"), d.ToString(Newtonsoft.Json.Formatting.None)); + //"{\"error\":{\"code\":\"2200\",\"details\":[{\"message\":\"Template array item 0, fld property value \\\"DOES_NOT_EXIST\\\" is not a valid value for AyaType specified\",\"target\":\"Template\",\"error\":\"2203\"}],\"message\":\"Object did not pass validation\"}}" + Util.ValidateErrorCodeResponse(a, 2200, 400); + Util.ShouldContainValidationError(a, "ayaType", "2203"); + + //RIGHTS ISSUE, + //currently only bizadminfull can change a picklist template + d = new JObject(); + d.Id = 3;//User + //template, simple test, nothing fancy + dTemplateArray = new JArray(); + df = new JObject(); + df.fld = "useremployeenumber"; + dTemplateArray.Add(df); + d.Template = dTemplateArray.ToString(Newtonsoft.Json.Formatting.None); + //ERROR NO RIGHTS USER + a = await Util.PostAsync("pick-list/template", await Util.GetTokenAsync("CustomerLimited"), d.ToString(Newtonsoft.Json.Formatting.None)); + //"{\"error\":{\"code\":\"2004\",\"message\":\"User not authorized for this resource operation (insufficient rights)\"}}" + Util.ValidateErrorCodeResponse(a, 2004, 403); + + //EMPTY TEMPLATE VALIDATION ERROR + d = new JObject(); + d.Id = 3;//User + d.Template = "";//<-- ERROR no template + a = await Util.PostAsync("pick-list/template", await Util.GetTokenAsync("BizAdminFull"), d.ToString(Newtonsoft.Json.Formatting.None)); + Util.ValidateErrorCodeResponse(a, 2200, 400); + Util.ShouldContainValidationError(a, "Template", "2201"); + + + //MALFORMED TEMPLATE JSON ERROR + d = new JObject(); + d.Id = 3;//User type + dTemplateArray = new JArray(); + df = new JObject(); + df.fld = "useremployeenumber"; + dTemplateArray.Add(df); + string sTemplate = dTemplateArray.ToString(Newtonsoft.Json.Formatting.None); + d.Template = sTemplate.Substring(2);//<-- ERROR missing first two characters of json template array + a = await Util.PostAsync("pick-list/template", await Util.GetTokenAsync("BizAdminFull"), d.ToString(Newtonsoft.Json.Formatting.None)); + //"{\"error\":{\"code\":\"2200\",\"details\":[{\"message\":\"Template is not valid JSON string: Error reading JArray from JsonReader. Current JsonReader item is not an array: String. Path '', line 1, position 5.\",\"target\":\"Template\",\"error\":\"2203\"}],\"message\":\"Object did not pass validation\"}}" + Util.ValidateErrorCodeResponse(a, 2200, 400); + Util.ShouldContainValidationError(a, "Template", "2203"); + + } + + /// + /// test get templates list + /// + [Fact] + public async Task PickListTemplateList() + { + //RETRIEVE + ApiResponse a = await Util.GetAsync("pick-list/template/list", await Util.GetTokenAsync("BizAdminFull")); + Util.ValidateDataReturnResponseOk(a); + //assert contains at least two records (as we only have two at time of writing this test) + var templateList = ((JArray)a.ObjectResponse["data"]); + templateList.Count.Should().BeGreaterThan(1); + templateList[0]["id"].Value().Should().Be(2);//first one should be a widget + } + + + /// + /// test get picklist fields list for widget template + /// + [Fact] + public async Task WidgetPickListTemplateFieldList() + { + //RETRIEVE WIDGET PICKLIST FIELDS + ApiResponse a = await Util.GetAsync("pick-list/template/ListFields/2", await Util.GetTokenAsync("BizAdminFull")); + Util.ValidateDataReturnResponseOk(a); + //assert contains at least two records (as we only have two at time of writing this test) + var templateList = ((JArray)a.ObjectResponse["data"]); + templateList.Count.Should().BeGreaterThan(4); + templateList[0]["fieldKey"].Value().Should().Be("widgetactive");//first one should be a widgetactive field + } + + + /// + /// test get picklist for widget without query + /// + [Fact] + public async Task FetchWidgetPickListNoQuery() + { + //RETRIEVE WIDGET PICKLIST no filter + ApiResponse a = await Util.GetAsync("pick-list/list?ayaType=2", await Util.GetTokenAsync("BizAdminFull")); + Util.ValidateDataReturnResponseOk(a); + //assert contains 100 records (current picklist maximum count) + var pickList = ((JArray)a.ObjectResponse["data"]); + pickList.Count.Should().Be(100); + } + + + /// + /// test get picklist for single predefined value only + /// + [Fact] + public async Task FetchWidgetPickListPreDefined() + { + //fetch the SuperUser account which always exists + ApiResponse a = await Util.GetAsync("pick-list/list?ayaType=3&preId=1", await Util.GetTokenAsync("BizAdminFull")); + Util.ValidateDataReturnResponseOk(a); + //assert contains 1 record + var pickList = ((JArray)a.ObjectResponse["data"]); + pickList.Count.Should().Be(1); + pickList[0]["id"].Value().Should().Be(1); + + } + + + /// + /// test get picklist for widget with basic autocomplete query only + /// + [Fact] + public async Task FetchWidgetPickListAutoComplete() + { + + //make key widget + + var WidgetNameStart = "FetchWidgetPickListAutoComplete_a1b2c3"; + long IncludedWidgetId = 0; + //CREATE TEST WIDGETS + //included widget + dynamic w = new JObject(); + w.name = Util.Uniquify(WidgetNameStart); + w.customFields = Util.WidgetRequiredCustomFieldsJsonString(); + w.notes = "blah"; + w.active = true; + w.usertype = 1; + w.dollarAmount = 555.55; + + ApiResponse a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w.ToString()); + Util.ValidateDataReturnResponseOk(a); + IncludedWidgetId = a.ObjectResponse["data"]["id"].Value(); + + + //RETRIEVE WIDGET PICKLIST with name filter + a = await Util.GetAsync("pick-list/list?ayaType=2&query=a1b2c3", await Util.GetTokenAsync("BizAdminFull")); + Util.ValidateDataReturnResponseOk(a); + + var pickList = ((JArray)a.ObjectResponse["data"]); + pickList.Count.Should().BeGreaterThan(0); + pickList[0]["name"].Value().Should().Contain("_a1b2c3"); + + //DELETE WIDGETS + a = await Util.DeleteAsync("widget/" + IncludedWidgetId.ToString(), await Util.GetTokenAsync("BizAdminFull")); + Util.ValidateHTTPStatusCode(a, 204); + } + + + /// + /// + /// + [Fact] + public async Task FetchWidgetPickListTags() + { + + //make key widget + var WidgetNameStart = "FetchWidgetPickListTags"; + long IncludedWidgetId = 0; + //CREATE TEST WIDGETS + //included widget + dynamic w = new JObject(); + w.name = Util.Uniquify(WidgetNameStart); + w.customFields = Util.WidgetRequiredCustomFieldsJsonString(); + w.notes = "blah"; + w.active = true; + w.usertype = 1; + w.dollarAmount = 555.55; + //Tags + dynamic InclusiveTagsArray = new JArray(); + InclusiveTagsArray.Add("plred"); + InclusiveTagsArray.Add("plblue"); + w.tags = InclusiveTagsArray; + + ApiResponse a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w.ToString()); + Util.ValidateDataReturnResponseOk(a); + IncludedWidgetId = a.ObjectResponse["data"]["id"].Value(); + + + //RETRIEVE WIDGET PICKLIST with name filter + a = await Util.GetAsync("pick-list/list?ayaType=2&query=..lblu", await Util.GetTokenAsync("BizAdminFull")); + Util.ValidateDataReturnResponseOk(a); + + var pickList = ((JArray)a.ObjectResponse["data"]); + pickList.Count.Should().Be(1); + pickList[0]["id"].Value().Should().Be(IncludedWidgetId); + + //DELETE WIDGETS + a = await Util.DeleteAsync("widget/" + IncludedWidgetId.ToString(), await Util.GetTokenAsync("BizAdminFull")); + Util.ValidateHTTPStatusCode(a, 204); + } + + + /// + /// test get picklist for widget with basic autocomplete query only + /// + [Fact] + public async Task FetchWidgetPickListInactiveActive() + { + + //make key widget + + var WidgetNameStart = "FetchWidgetPickListInactiveActive"; + List ActiveWidgetIdList = new List(); + List NotActiveWidgetIdList = new List(); + + //CREATE 4 TEST WIDGETS + //two active and two non active + + //first active widget + dynamic w = new JObject(); + w.name = Util.Uniquify(WidgetNameStart); + w.customFields = Util.WidgetRequiredCustomFieldsJsonString(); + w.notes = "blah"; + w.active = true; + w.usertype = 1; + + ApiResponse a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w.ToString()); + Util.ValidateDataReturnResponseOk(a); + ActiveWidgetIdList.Add(a.ObjectResponse["data"]["id"].Value()); + + //second active widget + w.name = Util.Uniquify(WidgetNameStart); + + a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w.ToString()); + Util.ValidateDataReturnResponseOk(a); + ActiveWidgetIdList.Add(a.ObjectResponse["data"]["id"].Value()); + + + //first NON active widget + w.name = Util.Uniquify(WidgetNameStart); + w.active = false; + + a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w.ToString()); + Util.ValidateDataReturnResponseOk(a); + NotActiveWidgetIdList.Add(a.ObjectResponse["data"]["id"].Value()); + + //second NON active widget + w.name = Util.Uniquify(WidgetNameStart); + w.active = false; + + a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w.ToString()); + Util.ValidateDataReturnResponseOk(a); + NotActiveWidgetIdList.Add(a.ObjectResponse["data"]["id"].Value()); + + + //CONFIRM BOTH INACTIVE AND ACTIVE + a = await Util.GetAsync("pick-list/list?ayaType=2&query=ickListInactiveAct&inactive=true", await Util.GetTokenAsync("BizAdminFull")); + Util.ValidateDataReturnResponseOk(a); + var pickList = ((JArray)a.ObjectResponse["data"]); + //assert contains at least two records + pickList.Count.Should().BeGreaterThan(1); + int nActiveMatches = 0; + int nInactiveMatches = 0; + foreach (JObject o in pickList) + { + if (ActiveWidgetIdList.Contains(o["id"].Value())) + nActiveMatches++; + if (NotActiveWidgetIdList.Contains(o["id"].Value())) + nInactiveMatches++; + } + nActiveMatches.Should().Be(ActiveWidgetIdList.Count); + nInactiveMatches.Should().Be(NotActiveWidgetIdList.Count); + + + //CONFIRM ACTIVE ONLY + a = await Util.GetAsync("pick-list/list?ayaType=2&query=ickListInactiveAct", await Util.GetTokenAsync("BizAdminFull")); + Util.ValidateDataReturnResponseOk(a); + pickList = ((JArray)a.ObjectResponse["data"]); + //assert contains at least two records + pickList.Count.Should().BeGreaterThan(1); + nActiveMatches = 0; + nInactiveMatches = 0; + foreach (JObject o in pickList) + { + if (ActiveWidgetIdList.Contains(o["id"].Value())) + nActiveMatches++; + if (NotActiveWidgetIdList.Contains(o["id"].Value())) + nInactiveMatches++; + } + nActiveMatches.Should().Be(ActiveWidgetIdList.Count); + nInactiveMatches.Should().Be(0); + + //DELETE WIDGETS + foreach (long l in ActiveWidgetIdList) + { + a = await Util.DeleteAsync("widget/" + l.ToString(), await Util.GetTokenAsync("BizAdminFull")); + Util.ValidateHTTPStatusCode(a, 204); + } + + foreach (long l in NotActiveWidgetIdList) + { + a = await Util.DeleteAsync("widget/" + l.ToString(), await Util.GetTokenAsync("BizAdminFull")); + Util.ValidateHTTPStatusCode(a, 204); + } + } + + + + + + //================================================== + + }//eoc +}//eons diff --git a/Privacy/Privacy.cs b/Privacy/Privacy.cs index 93adfe5..6fcad1b 100644 --- a/Privacy/Privacy.cs +++ b/Privacy/Privacy.cs @@ -1,28 +1,28 @@ -using Xunit; -using FluentAssertions; - -namespace raven_integration -{ - - public class Privacy - { - -//DEPRECATED, NOT USEFUL - - // /// - // /// - // /// - // [Fact] - // public async void LogShouldNotContainPrivateData() - // { - // ApiResponse a = await Util.GetAsync("AyaType", await Util.GetTokenAsync("TEST_PRIVACY_USER_ACCOUNT")); - // ApiTextResponse t = await Util.GetTextResultAsync("log-file/log-ayanova.txt", await Util.GetTokenAsync("TEST_PRIVACY_USER_ACCOUNT")); - // Util.ValidateHTTPStatusCode(t, 200); - // t.TextResponse.Should().NotContain("TEST_PRIVACY_USER_ACCOUNT"); - - // } - - // //================================================== - - }//eoc -}//eons +using Xunit; +using FluentAssertions; + +namespace raven_integration +{ + + public class Privacy + { + +//DEPRECATED, NOT USEFUL + + // /// + // /// + // /// + // [Fact] + // public async Task LogShouldNotContainPrivateData() + // { + // ApiResponse a = await Util.GetAsync("AyaType", await Util.GetTokenAsync("TEST_PRIVACY_USER_ACCOUNT")); + // ApiTextResponse t = await Util.GetTextResultAsync("log-file/log-ayanova.txt", await Util.GetTokenAsync("TEST_PRIVACY_USER_ACCOUNT")); + // Util.ValidateHTTPStatusCode(t, 200); + // t.TextResponse.Should().NotContain("TEST_PRIVACY_USER_ACCOUNT"); + + // } + + // //================================================== + + }//eoc +}//eons diff --git a/Search/SearchOps.cs b/Search/SearchOps.cs index 4b68af7..6aa8102 100644 --- a/Search/SearchOps.cs +++ b/Search/SearchOps.cs @@ -1,704 +1,704 @@ -using System; -using Xunit; -using Newtonsoft.Json.Linq; -using System.Linq; -using FluentAssertions; -using System.Collections.Generic; - -namespace raven_integration -{ - - public class SearchOps - { - - //NOTE: this test failed one time for no apparent reason but then was ok afterwards - [Fact] - public async void PhraseOnlySearchShouldReturnCorrectResultsInOrder() - { - const string TEST_SEARCH_PHRASE = "simple dogs"; - - //CREATE A WIDGET - dynamic D = new JObject(); - D.name = Util.Uniquify("search NOTES Test WIDGET"); - D.customFields = Util.WidgetRequiredCustomFieldsJsonString(); - D.dollarAmount = 1.11m; - D.active = true; - D.usertype = 1; - D.notes = "This record will match in notes: The quick brown and simple fox jumped over the six lazy dogs!"; - - ApiResponse a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), D.ToString()); - Util.ValidateDataReturnResponseOk(a); - long MatchWidgetInNotesId = a.ObjectResponse["data"]["id"].Value(); - - //CREATE FIRST TEST USER WITH PHRASE IN NAME - D = new JObject(); - D.name = Util.Uniquify("search NAME DOGS simple Test User"); - D.customFields = Util.WidgetRequiredCustomFieldsJsonString(); - D.notes = "This user has the match in it's name"; - - D.active = true; - D.login = Util.Uniquify("LOGIN"); - D.password = Util.Uniquify("PASSWORD"); - D.usertype = 1; - - D.userType = 3;//non scheduleable - - a = await Util.PostAsync("User", await Util.GetTokenAsync("superuser", "l3tm3in"), D.ToString()); - Util.ValidateDataReturnResponseOk(a); - long MatchUserInNameId = a.ObjectResponse["data"]["id"].Value(); - - //CREATE A SECOND TEST USER WITH PHRASE IN NOTES - D = new JObject(); - D.name = Util.Uniquify("search NOTES Test User"); - D.customFields = Util.WidgetRequiredCustomFieldsJsonString(); - D.notes = "This user has the match simple dogs in its notes"; - - D.active = true; - D.login = Util.Uniquify("LOGIN"); - D.password = Util.Uniquify("PASSWORD"); - D.usertype = 1; - - D.userType = 3;//non scheduleable - - a = await Util.PostAsync("User", await Util.GetTokenAsync("superuser", "l3tm3in"), D.ToString()); - Util.ValidateDataReturnResponseOk(a); - long MatchUserInNotesId = a.ObjectResponse["data"]["id"].Value(); - - //CREATE A SECOND WIDGET - D = new JObject(); - D.name = Util.Uniquify("search NAME simple as in dogs Test WIDGET"); - D.customFields = Util.WidgetRequiredCustomFieldsJsonString(); - D.dollarAmount = 1.11m; - D.active = true; - D.usertype = 1; - D.notes = "This Widget matches in name"; - - a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), D.ToString()); - Util.ValidateDataReturnResponseOk(a); - long MatchWidgetInNameId = a.ObjectResponse["data"]["id"].Value(); - - //CREATE A THIRD WIDGET - D = new JObject(); - D.name = Util.Uniquify("search NO-MATCH THIRD Test WIDGET"); - D.customFields = Util.WidgetRequiredCustomFieldsJsonString(); - D.dollarAmount = 1.11m; - D.active = true; - D.usertype = 1; - D.notes = "This Widget should not be returned in the search as it only contains a single keyword in the name not both"; - - a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), D.ToString()); - Util.ValidateDataReturnResponseOk(a); - long MatchNothingWidgetId = a.ObjectResponse["data"]["id"].Value(); - - - //Now see if can find those objects with a phrase search - dynamic SearchParameters = new JObject(); - - SearchParameters.phrase = TEST_SEARCH_PHRASE; - - SearchParameters.typeOnly = 0;//no type - SearchParameters.maxResults = 0; - a = await Util.PostAsync("search", await Util.GetTokenAsync("superuser", "l3tm3in"), SearchParameters.ToString()); - Util.ValidateDataReturnResponseOk(a); - - //Now validate the return list - ((JArray)a.ObjectResponse["data"]["searchResults"]).Count.Should().BeGreaterOrEqualTo(3); - - //Turn the list into an array of id's - var v = ((JArray)a.ObjectResponse["data"]["searchResults"]); - List MatchingIdList = new List(); - foreach (JObject j in v) - { - MatchingIdList.Add(j["id"].Value()); - } - - //Ensure the expected items are returned - MatchingIdList.Should().Contain(MatchWidgetInNotesId, "ShouldContainMatchWidgetInNotesId"); - MatchingIdList.Should().Contain(MatchWidgetInNameId, "ShouldContainMatchWidgetInNameId"); - MatchingIdList.Should().Contain(MatchUserInNotesId, "ShouldContainMatchUserInNotesId"); - MatchingIdList.Should().Contain(MatchUserInNameId, "ShouldContainMatchUserInNameId"); - MatchingIdList.Should().NotContain(MatchNothingWidgetId, "ShouldNotContainMatchNothingWidgetId"); - - //Assert the order (roughly, this is kind of a waste of time, either the code is sorting or not, it's not going to change) - //first item must be a widget - a.ObjectResponse["data"]["searchResults"][0]["type"].Value().Should().Be(2); - - //final item must be a user - a.ObjectResponse["data"]["searchResults"][MatchingIdList.Count - 1]["type"].Value().Should().Be(3); - - - //FULL BODY SEARCH RIGHTS - //First up test a full record search returns no results due to insufficient rights - //even though the record exists - //Just re-run the above search exactly but with a no rights to full User or Widget role instead - - //Only BizAdmin* roles can read a full user record - //This search should return zero items - a = await Util.PostAsync("search", await Util.GetTokenAsync("SubContractorLimited"), SearchParameters.ToString()); - Util.ValidateDataReturnResponseOk(a); - ((JArray)a.ObjectResponse["data"]["searchResults"]).Count.Should().Be(0, "User with no rights should not see any results in body search"); - - - - - }//eot - - - - [Fact] - public async void WildCardStartsWithSearchShouldWork() - { - const string TEST_SEARCH_PHRASE = "hap* goose"; - - //CREATE A WIDGET - dynamic D = new JObject(); - D.name = Util.Uniquify("Wildcard startswith search test WIDGET"); - D.customFields = Util.WidgetRequiredCustomFieldsJsonString(); - D.dollarAmount = 1.11m; - D.active = true; - D.usertype = 1; - D.notes = "This record will match in notes: The quick brown and hapless goose"; - - - ApiResponse a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), D.ToString()); - Util.ValidateDataReturnResponseOk(a); - long MatchWidgetInNotesId = a.ObjectResponse["data"]["id"].Value(); - - //CREATE FIRST TEST USER WITH PHRASE IN NAME - D = new JObject(); - D.name = Util.Uniquify("Wildcard startswith search NAME happy goose Test User"); - D.notes = "This user has the match in it's name"; - - D.active = true; - D.login = Util.Uniquify("LOGIN"); - D.password = Util.Uniquify("PASSWORD"); - D.usertype = 1; - - D.userType = 3;//non scheduleable - D.customFields = Util.UserRequiredCustomFieldsJsonString(); - - a = await Util.PostAsync("User", await Util.GetTokenAsync("superuser", "l3tm3in"), D.ToString()); - Util.ValidateDataReturnResponseOk(a); - long MatchUserInNameId = a.ObjectResponse["data"]["id"].Value(); - - - //Now see if can find those objects with a phrase search - dynamic SearchParameters = new JObject(); - - SearchParameters.phrase = TEST_SEARCH_PHRASE; - - SearchParameters.typeOnly = 0;//no type - SearchParameters.maxResults = 0; - a = await Util.PostAsync("search", await Util.GetTokenAsync("superuser", "l3tm3in"), SearchParameters.ToString()); - Util.ValidateDataReturnResponseOk(a); - - //Now validate the return list - ((JArray)a.ObjectResponse["data"]["searchResults"]).Count.Should().BeGreaterOrEqualTo(2); - - //Turn the list into an array of id's - var v = ((JArray)a.ObjectResponse["data"]["searchResults"]); - List MatchingIdList = new List(); - foreach (JObject j in v) - { - MatchingIdList.Add(j["id"].Value()); - } - - //Ensure the expected items are returned - MatchingIdList.Should().Contain(MatchWidgetInNotesId, "ShouldContainMatchWidgetInNotesId"); - MatchingIdList.Should().Contain(MatchUserInNameId, "ShouldContainMatchUserInNameId"); - - }//eot - - - [Fact] - public async void WildCardEndsWithSearchShouldWork() - { - const string TEST_SEARCH_PHRASE = "goose *act"; - - //CREATE A WIDGET - dynamic D = new JObject(); - D.name = Util.Uniquify("Wildcard endswith search test WIDGET"); - D.customFields = Util.WidgetRequiredCustomFieldsJsonString(); - D.dollarAmount = 1.11m; - D.active = true; - D.usertype = 1; - D.notes = "This record will match in notes: react to the goose"; - - ApiResponse a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), D.ToString()); - Util.ValidateDataReturnResponseOk(a); - long MatchWidgetInNotesId = a.ObjectResponse["data"]["id"].Value(); - - //CREATE FIRST TEST USER WITH PHRASE IN NAME - D = new JObject(); - D.name = Util.Uniquify("Wildcard endswith search NAME goose exact Test User"); - D.notes = "This user has the match in it's name"; - - D.active = true; - D.login = Util.Uniquify("LOGIN"); - D.password = Util.Uniquify("PASSWORD"); - D.usertype = 1; - - D.userType = 3;//non scheduleable - D.customFields = Util.UserRequiredCustomFieldsJsonString(); - - a = await Util.PostAsync("User", await Util.GetTokenAsync("superuser", "l3tm3in"), D.ToString()); - Util.ValidateDataReturnResponseOk(a); - long MatchUserInNameId = a.ObjectResponse["data"]["id"].Value(); - - - //Now see if can find those objects with a phrase search - dynamic SearchParameters = new JObject(); - - SearchParameters.phrase = TEST_SEARCH_PHRASE; - - SearchParameters.typeOnly = 0;//no type - SearchParameters.maxResults = 0; - a = await Util.PostAsync("search", await Util.GetTokenAsync("superuser", "l3tm3in"), SearchParameters.ToString()); - Util.ValidateDataReturnResponseOk(a); - - //Now validate the return list - ((JArray)a.ObjectResponse["data"]["searchResults"]).Count.Should().BeGreaterOrEqualTo(2); - - //Turn the list into an array of id's - var v = ((JArray)a.ObjectResponse["data"]["searchResults"]); - List MatchingIdList = new List(); - foreach (JObject j in v) - { - MatchingIdList.Add(j["id"].Value()); - } - - //Ensure the expected items are returned - MatchingIdList.Should().Contain(MatchWidgetInNotesId, "ShouldContainMatchWidgetInNotesId"); - MatchingIdList.Should().Contain(MatchUserInNameId, "ShouldContainMatchUserInNameId"); - - }//eot - - - - - [Fact] - public async void SearchAndExtractShouldWork() - { - const string TEST_SEARCH_PHRASE = "cast goose"; - - //CREATE A WIDGET - dynamic D = new JObject(); - D.name = Util.Uniquify("Wildcard contains search test WIDGET"); - D.customFields = Util.WidgetRequiredCustomFieldsJsonString(); - D.dollarAmount = 1.11m; - D.active = true; - D.usertype = 1; - D.notes = "This record will match in notes: broadcasting to the goose"; - - ApiResponse a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), D.ToString()); - Util.ValidateDataReturnResponseOk(a); - long MatchWidgetInNotesId = a.ObjectResponse["data"]["id"].Value(); - - //CREATE FIRST TEST USER WITH PHRASE IN NAME - D = new JObject(); - D.name = Util.Uniquify("Wildcard contains search NAME goose elcastro Test User"); - D.notes = "This user has the match in it's name"; - - D.active = true; - D.login = Util.Uniquify("LOGIN"); - D.password = Util.Uniquify("PASSWORD"); - D.usertype = 1; - - D.userType = 3;//non scheduleable - D.customFields = Util.UserRequiredCustomFieldsJsonString(); - - a = await Util.PostAsync("User", await Util.GetTokenAsync("superuser", "l3tm3in"), D.ToString()); - Util.ValidateDataReturnResponseOk(a); - long MatchUserInNameId = a.ObjectResponse["data"]["id"].Value(); - - - //Now see if can find those objects with a phrase search - dynamic SearchParameters = new JObject(); - - SearchParameters.phrase = TEST_SEARCH_PHRASE; - - SearchParameters.typeOnly = 0;//no type - SearchParameters.maxResults = 0; - a = await Util.PostAsync("search", await Util.GetTokenAsync("superuser", "l3tm3in"), SearchParameters.ToString()); - Util.ValidateDataReturnResponseOk(a); - - //Now validate the return list - ((JArray)a.ObjectResponse["data"]["searchResults"]).Count.Should().BeGreaterOrEqualTo(2); - - //Turn the list into an array of id's - var v = ((JArray)a.ObjectResponse["data"]["searchResults"]); - List MatchingIdList = new List(); - foreach (JObject j in v) - { - MatchingIdList.Add(j["id"].Value()); - } - - //Ensure the expected items are returned - MatchingIdList.Should().Contain(MatchWidgetInNotesId, "ShouldContainMatchWidgetInNotesId"); - MatchingIdList.Should().Contain(MatchUserInNameId, "ShouldContainMatchUserInNameId"); - - - //Ensure excerpt works and contains the search phrase - // /Search/Info/2/1?phrase=we&max=200 - a = await Util.GetAsync($"search/Info/2/{MatchWidgetInNotesId}?phrase={TEST_SEARCH_PHRASE}&max=200", await Util.GetTokenAsync("superuser", "l3tm3in")); - Util.ValidateDataReturnResponseOk(a); - a.ObjectResponse["data"].Value().Should().Contain(TEST_SEARCH_PHRASE.Split(" ")[0]); - a.ObjectResponse["data"].Value().Should().Contain(TEST_SEARCH_PHRASE.Split(" ")[1]); - - }//eot - - - [Fact] - public async void TagSearchShouldWork() - { - const string TEST_SEARCH_PHRASE = "element* aardvark"; - - // //CREATE A TAG - // dynamic D = new JObject(); - // D.name = Util.Uniquify("TAGSEARCH"); - // ApiResponse a = await Util.PostAsync("Tag", await Util.GetTokenAsync("superuser", "l3tm3in"), D.ToString()); - // Util.ValidateDataReturnResponseOk(a); - // long TagId = a.ObjectResponse["data"]["id"].Value(); - - - var SearchTagPhrase = Util.Uniquify("TAGSEARCH"); - //Tags - dynamic TagsArray = new JArray(); - TagsArray.Add(SearchTagPhrase); - - //w.tags = InclusiveTagsArray; - - //CREATE A WIDGET - dynamic D = new JObject(); - D.name = Util.Uniquify("TAG search test WIDGET TAG AND PHRASE"); - D.customFields = Util.WidgetRequiredCustomFieldsJsonString(); - D.dollarAmount = 1.11m; - D.active = true; - D.usertype = 1; - D.notes = "This record will match in notes and tag: elementary my dear aardvark"; - D.tags = TagsArray; - - ApiResponse a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), D.ToString()); - Util.ValidateDataReturnResponseOk(a); - long MatchWidgetInNotesId = a.ObjectResponse["data"]["id"].Value(); - - - - - //CREATE A WIDGET WITH TAG BUT NOT SEARCH PHRASE - D = new JObject(); - D.name = Util.Uniquify("TAG search test WIDGET TAG ONLY"); - D.customFields = Util.WidgetRequiredCustomFieldsJsonString(); - D.dollarAmount = 1.11m; - D.active = true; - D.usertype = 1; - D.notes = "This record will match in tag but no search phrase"; - D.tags = TagsArray; - - a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), D.ToString()); - Util.ValidateDataReturnResponseOk(a); - long NoPhraseMatchWidgetInTagId = a.ObjectResponse["data"]["id"].Value(); - - - - //CREATE FIRST TEST USER WITH PHRASE IN NAME BUT NO TAG - D = new JObject(); - D.name = Util.Uniquify("Wildcard contains search NAME elementary aardvark Test User"); - D.notes = "This user has the match in it's name but no tag match"; - - D.active = true; - D.login = Util.Uniquify("LOGIN"); - D.password = Util.Uniquify("PASSWORD"); - D.usertype = 1; - - D.userType = 3;//non scheduleable - D.customFields = Util.UserRequiredCustomFieldsJsonString(); - - a = await Util.PostAsync("User", await Util.GetTokenAsync("superuser", "l3tm3in"), D.ToString()); - Util.ValidateDataReturnResponseOk(a); - long MatchUserInNameId = a.ObjectResponse["data"]["id"].Value(); - - - //Now see if can find those objects with a phrase search - dynamic SearchParameters = new JObject(); - - SearchParameters.phrase = TEST_SEARCH_PHRASE + " " + SearchTagPhrase; - - SearchParameters.typeOnly = 0;//no type - - a = await Util.PostAsync("search", await Util.GetTokenAsync("superuser", "l3tm3in"), SearchParameters.ToString()); - Util.ValidateDataReturnResponseOk(a); - - //Now validate the return list - ((JArray)a.ObjectResponse["data"]["searchResults"]).Count.Should().BeGreaterOrEqualTo(1); - - //Turn the list into an array of id's - var v = ((JArray)a.ObjectResponse["data"]["searchResults"]); - List MatchingIdList = new List(); - foreach (JObject j in v) - { - MatchingIdList.Add(j["id"].Value()); - } - - //Ensure the expected items are returned - MatchingIdList.Should().Contain(MatchWidgetInNotesId, "ShouldContainMatchWidgetInNotesId"); - MatchingIdList.Should().NotContain(MatchUserInNameId, "ShouldNotContainMatchUserInNameId"); - MatchingIdList.Should().NotContain(NoPhraseMatchWidgetInTagId, "ShouldNotContainNoPhraseMatchWidgetInTagId"); - - }//eot - - - - [Fact] - public async void ConstrainedBigDataSearchShouldHonourMaxResultsAndBeRelativelyFast() - { - //THIS test is a bit different in that it relies partly on the big dataset for testing - //so it has different paths depending upon if it's testing against the big data or not - const string TEST_SEARCH_PHRASE = "et*"; - - //Now see if can find those objects with a phrase search - dynamic SearchParameters = new JObject(); - - SearchParameters.phrase = TEST_SEARCH_PHRASE; - - SearchParameters.typeOnly = 0;//no type - SearchParameters.maxResults = 1000;//default is 500 - - var watch = new System.Diagnostics.Stopwatch(); - watch.Start(); - ApiResponse a = await Util.PostAsync("search", await Util.GetTokenAsync("superuser", "l3tm3in"), SearchParameters.ToString()); - watch.Stop(); - - var TimeToSearch = watch.ElapsedMilliseconds; - - Util.ValidateDataReturnResponseOk(a); - - //Now validate the return list - var ResultCount = ((JArray)a.ObjectResponse["data"]["searchResults"]).Count; - //assert it's not unbounded - ResultCount.Should().BeLessOrEqualTo(1000); - - if (ResultCount > 999) - { - //assert the TotalResultsFound is greater than the results returned - var TotalResultsFound = a.ObjectResponse["data"]["totalResultsFound"].Value(); - //assert it's not unbounded - TotalResultsFound.Should().BeGreaterThan(ResultCount); - } - //5456 ms is the longest I've seen in initial testing with all 1000 results so setting 10% above - TimeToSearch.Should().BeLessThan(6000, "Constrained big data search should not be too slow"); - - }//eot - - - [Fact] - public async void UnboundBigDataSearchShouldBeRelativelyFast() - { - //THIS test is a bit different in that it relies partly on the big dataset for testing - //so it has different paths depending upon if it's testing against the big data or not - const string TEST_SEARCH_PHRASE = "et*"; - - //Now see if can find those objects with a phrase search - dynamic SearchParameters = new JObject(); - - SearchParameters.phrase = TEST_SEARCH_PHRASE; - - SearchParameters.typeOnly = 0;//no type - SearchParameters.maxResults = 0;//0=return all results - - var watch = new System.Diagnostics.Stopwatch(); - watch.Start(); - ApiResponse a = await Util.PostAsync("search", await Util.GetTokenAsync("superuser", "l3tm3in"), SearchParameters.ToString()); - watch.Stop(); - - var TimeToSearch = watch.ElapsedMilliseconds; - - Util.ValidateDataReturnResponseOk(a); - - //Now validate the return list - var ResultCount = ((JArray)a.ObjectResponse["data"]["searchResults"]).Count; - - - //Set this time based on testing. 52385 Slowest run plus 10% - TimeToSearch.Should().BeLessThan(57623, "Unconstrained big data search should not be too slow"); - - - }//eot - - - - [Fact] - public async void SearchForSerialFieldShouldWork() - { - //CREATE A WIDGET - dynamic D = new JObject(); - D.name = Util.Uniquify("Serial search test WIDGET"); - D.customFields = Util.WidgetRequiredCustomFieldsJsonString(); - D.dollarAmount = 1.11m; - D.active = true; - D.usertype = 1; - D.notes = "Test for serial number search"; - - ApiResponse a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), D.ToString()); - Util.ValidateDataReturnResponseOk(a); - long MatchWidgetInSerialId = a.ObjectResponse["data"]["id"].Value(); - var MatchWidgetSerial = a.ObjectResponse["data"]["serial"].Value(); - - //TODO: get this from the return object - string SerialSearch = MatchWidgetSerial.ToString(); ; - - - //Now see if can find those objects with a phrase search - dynamic SearchParameters = new JObject(); - SearchParameters.phrase = SerialSearch; - - SearchParameters.typeOnly = 0;//no type - SearchParameters.maxResults = 0; - a = await Util.PostAsync("search", await Util.GetTokenAsync("superuser", "l3tm3in"), SearchParameters.ToString()); - Util.ValidateDataReturnResponseOk(a); - - //Now validate the return list - ((JArray)a.ObjectResponse["data"]["searchResults"]).Count.Should().BeGreaterOrEqualTo(1); - - //Turn the list into an array of id's - var v = ((JArray)a.ObjectResponse["data"]["searchResults"]); - List MatchingIdList = new List(); - foreach (JObject j in v) - { - MatchingIdList.Add(j["id"].Value()); - } - - //Ensure the expected items are returned - MatchingIdList.Should().Contain(MatchWidgetInSerialId, "ShouldContainMatchWidgetInSerialId"); - - - - }//eot - - - - - - [Fact] - public async void CustomFieldSearchShouldWork() - { - /* - Failing on huge data test after many hours: - -[xUnit.net 00:00:21.49] raven_integration.SearchOps.CustomFieldSearchShouldWork [FAIL] - X raven_integration.SearchOps.CustomFieldSearchShouldWork [1s 84ms] - Error Message: - Expected MatchingIdList {109274L, 109095L, 108919L, 108740L, 108558L, 108382L, 108201L, 108021L, 107842L, 107663L, 107487L, 107305L, 107126L, 106947L, 106768L, 106589L, 106413L, 106233L, 106052L, 105873L, 105692L, 105510L, 105341L, 105157L, 104978L, 104799L, 104620L, 104441L, 104262L, 104084L, 103906L, 103725L, .468 more.} to contain 195378L because ShouldContainMatchingCustomFieldWidgetId. - Stack Trace: - at FluentAssertions.Execution.XUnit2TestFramework.Throw(String message) - at FluentAssertions.Execution.TestFrameworkProvider.Throw(String message) - at FluentAssertions.Execution.DefaultAssertionStrategy.HandleFailure(String message) - at FluentAssertions.Execution.AssertionScope.FailWith(Func`1 failReasonFunc) - at FluentAssertions.Collections.SelfReferencingCollectionAssertions`2.Contain(T expected, String because, Object[] becauseArgs) - at raven_integration.SearchOps.CustomFieldSearchShouldWork() in c:\data\code\raven-test-integration\Search\SearchOps.cs:line 644 - at System.Threading.Tasks.Task.<>c.b__139_0(Object state) - -Likely fix is to force order to most recent or simply to delete after test so they don't build up into a huge list - - */ - - //CREATE CUSTOM FIELD DATA TO SEARCH FOR (note must use already defined template so c2 is the text one) - dynamic dCustomField = new JObject(); - dCustomField.c1 = "2019-02-08T06:31:48.0019809Z"; - dCustomField.c2 = "pelican beak nozzle"; - dCustomField.c3 = "747"; - dCustomField.c4 = "true"; - dCustomField.c5 = "23.45"; - - //CREATE A WIDGET - dynamic D = new JObject(); - D.name = Util.Uniquify("CUSTOMFIELD search test WIDGET"); - D.customFields = dCustomField.ToString(); - D.dollarAmount = 1.11m; - D.active = true; - D.usertype = 1; - D.notes = "This record will match in custom field"; - - ApiResponse a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), D.ToString()); - Util.ValidateDataReturnResponseOk(a); - long MatchingWidgetId = a.ObjectResponse["data"]["id"].Value(); - - - //Now see if can find this object with a phrase search - dynamic SearchParameters = new JObject(); - - SearchParameters.phrase = "beak pelican"; - - SearchParameters.typeOnly = 0;//no type - - a = await Util.PostAsync("search", await Util.GetTokenAsync("superuser", "l3tm3in"), SearchParameters.ToString()); - Util.ValidateDataReturnResponseOk(a); - - //Now validate the return list - ((JArray)a.ObjectResponse["data"]["searchResults"]).Count.Should().BeGreaterOrEqualTo(1);//might be a successive run and still have some left so account for more than one return - - //Turn the list into an array of id's - var v = ((JArray)a.ObjectResponse["data"]["searchResults"]); - List MatchingIdList = new List(); - foreach (JObject j in v) - { - MatchingIdList.Add(j["id"].Value()); - } - - //Ensure the expected items are returned - MatchingIdList.Should().Contain(MatchingWidgetId, "ShouldContainMatchingCustomFieldWidgetId"); - - //Now delete the newly created one so the list doesn't build up and prevent this test from working in big runs... - //DELETE - ApiResponse DELETETestResponse = await Util.DeleteAsync("widget/" + MatchingWidgetId.ToString(), await Util.GetTokenAsync("superuser", "l3tm3in")); - Util.ValidateHTTPStatusCode(DELETETestResponse, 204); - - - }//eot - - - - - [Fact] - public async void DeletedObjectShouldRemoveKeywords() - { - string TEST_SEARCH_PHRASE = Util.Uniquify("qqwweerrttyy"); - - //CREATE A WIDGET - dynamic d = new JObject(); - d.name = Util.Uniquify("Wildcard endswith search test WIDGET"); - d.customFields = Util.WidgetRequiredCustomFieldsJsonString(); - d.dollarAmount = 1.11m; - d.active = true; - d.usertype = 1; - d.notes = $"This record will match in notes: {TEST_SEARCH_PHRASE} there"; - - ApiResponse a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), d.ToString()); - Util.ValidateDataReturnResponseOk(a); - long WidgetId = (long)a.ObjectResponse["data"]["id"]; - - //Now see if can find with a phrase search - dynamic SearchParameters = new JObject(); - SearchParameters.phrase = TEST_SEARCH_PHRASE; - SearchParameters.typeOnly = 0;//no type - SearchParameters.maxResults = 0; - a = await Util.PostAsync("search", await Util.GetTokenAsync("superuser", "l3tm3in"), SearchParameters.ToString()); - Util.ValidateDataReturnResponseOk(a); - //Now validate the return list (should be only one as it's super unique) - ((JArray)a.ObjectResponse["data"]["searchResults"]).Count.Should().Be(1); - - //Now delete the widget and re-run the search - a = await Util.DeleteAsync("widget/" + WidgetId.ToString(), await Util.GetTokenAsync("superuser", "l3tm3in")); - Util.ValidateHTTPStatusCode(a, 204); - - a = await Util.PostAsync("search", await Util.GetTokenAsync("superuser", "l3tm3in"), SearchParameters.ToString()); - Util.ValidateDataReturnResponseOk(a); - //Now validate the return list (should be only one as it's super unique) - ((JArray)a.ObjectResponse["data"]["searchResults"]).Count.Should().Be(0); - - - }//eot - //================================================== - - }//eoc -}//eons +using System; +using Xunit; +using Newtonsoft.Json.Linq; +using System.Linq; +using FluentAssertions; +using System.Collections.Generic; + +namespace raven_integration +{ + + public class SearchOps + { + + //NOTE: this test failed one time for no apparent reason but then was ok afterwards + [Fact] + public async Task PhraseOnlySearchShouldReturnCorrectResultsInOrder() + { + const string TEST_SEARCH_PHRASE = "simple dogs"; + + //CREATE A WIDGET + dynamic D = new JObject(); + D.name = Util.Uniquify("search NOTES Test WIDGET"); + D.customFields = Util.WidgetRequiredCustomFieldsJsonString(); + D.dollarAmount = 1.11m; + D.active = true; + D.usertype = 1; + D.notes = "This record will match in notes: The quick brown and simple fox jumped over the six lazy dogs!"; + + ApiResponse a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), D.ToString()); + Util.ValidateDataReturnResponseOk(a); + long MatchWidgetInNotesId = a.ObjectResponse["data"]["id"].Value(); + + //CREATE FIRST TEST USER WITH PHRASE IN NAME + D = new JObject(); + D.name = Util.Uniquify("search NAME DOGS simple Test User"); + D.customFields = Util.WidgetRequiredCustomFieldsJsonString(); + D.notes = "This user has the match in it's name"; + + D.active = true; + D.login = Util.Uniquify("LOGIN"); + D.password = Util.Uniquify("PASSWORD"); + D.usertype = 1; + + D.userType = 3;//non scheduleable + + a = await Util.PostAsync("User", await Util.GetTokenAsync("superuser", "l3tm3in"), D.ToString()); + Util.ValidateDataReturnResponseOk(a); + long MatchUserInNameId = a.ObjectResponse["data"]["id"].Value(); + + //CREATE A SECOND TEST USER WITH PHRASE IN NOTES + D = new JObject(); + D.name = Util.Uniquify("search NOTES Test User"); + D.customFields = Util.WidgetRequiredCustomFieldsJsonString(); + D.notes = "This user has the match simple dogs in its notes"; + + D.active = true; + D.login = Util.Uniquify("LOGIN"); + D.password = Util.Uniquify("PASSWORD"); + D.usertype = 1; + + D.userType = 3;//non scheduleable + + a = await Util.PostAsync("User", await Util.GetTokenAsync("superuser", "l3tm3in"), D.ToString()); + Util.ValidateDataReturnResponseOk(a); + long MatchUserInNotesId = a.ObjectResponse["data"]["id"].Value(); + + //CREATE A SECOND WIDGET + D = new JObject(); + D.name = Util.Uniquify("search NAME simple as in dogs Test WIDGET"); + D.customFields = Util.WidgetRequiredCustomFieldsJsonString(); + D.dollarAmount = 1.11m; + D.active = true; + D.usertype = 1; + D.notes = "This Widget matches in name"; + + a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), D.ToString()); + Util.ValidateDataReturnResponseOk(a); + long MatchWidgetInNameId = a.ObjectResponse["data"]["id"].Value(); + + //CREATE A THIRD WIDGET + D = new JObject(); + D.name = Util.Uniquify("search NO-MATCH THIRD Test WIDGET"); + D.customFields = Util.WidgetRequiredCustomFieldsJsonString(); + D.dollarAmount = 1.11m; + D.active = true; + D.usertype = 1; + D.notes = "This Widget should not be returned in the search as it only contains a single keyword in the name not both"; + + a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), D.ToString()); + Util.ValidateDataReturnResponseOk(a); + long MatchNothingWidgetId = a.ObjectResponse["data"]["id"].Value(); + + + //Now see if can find those objects with a phrase search + dynamic SearchParameters = new JObject(); + + SearchParameters.phrase = TEST_SEARCH_PHRASE; + + SearchParameters.typeOnly = 0;//no type + SearchParameters.maxResults = 0; + a = await Util.PostAsync("search", await Util.GetTokenAsync("superuser", "l3tm3in"), SearchParameters.ToString()); + Util.ValidateDataReturnResponseOk(a); + + //Now validate the return list + ((JArray)a.ObjectResponse["data"]["searchResults"]).Count.Should().BeGreaterOrEqualTo(3); + + //Turn the list into an array of id's + var v = ((JArray)a.ObjectResponse["data"]["searchResults"]); + List MatchingIdList = new List(); + foreach (JObject j in v) + { + MatchingIdList.Add(j["id"].Value()); + } + + //Ensure the expected items are returned + MatchingIdList.Should().Contain(MatchWidgetInNotesId, "ShouldContainMatchWidgetInNotesId"); + MatchingIdList.Should().Contain(MatchWidgetInNameId, "ShouldContainMatchWidgetInNameId"); + MatchingIdList.Should().Contain(MatchUserInNotesId, "ShouldContainMatchUserInNotesId"); + MatchingIdList.Should().Contain(MatchUserInNameId, "ShouldContainMatchUserInNameId"); + MatchingIdList.Should().NotContain(MatchNothingWidgetId, "ShouldNotContainMatchNothingWidgetId"); + + //Assert the order (roughly, this is kind of a waste of time, either the code is sorting or not, it's not going to change) + //first item must be a widget + a.ObjectResponse["data"]["searchResults"][0]["type"].Value().Should().Be(2); + + //final item must be a user + a.ObjectResponse["data"]["searchResults"][MatchingIdList.Count - 1]["type"].Value().Should().Be(3); + + + //FULL BODY SEARCH RIGHTS + //First up test a full record search returns no results due to insufficient rights + //even though the record exists + //Just re-run the above search exactly but with a no rights to full User or Widget role instead + + //Only BizAdmin* roles can read a full user record + //This search should return zero items + a = await Util.PostAsync("search", await Util.GetTokenAsync("SubContractorLimited"), SearchParameters.ToString()); + Util.ValidateDataReturnResponseOk(a); + ((JArray)a.ObjectResponse["data"]["searchResults"]).Count.Should().Be(0, "User with no rights should not see any results in body search"); + + + + + }//eot + + + + [Fact] + public async Task WildCardStartsWithSearchShouldWork() + { + const string TEST_SEARCH_PHRASE = "hap* goose"; + + //CREATE A WIDGET + dynamic D = new JObject(); + D.name = Util.Uniquify("Wildcard startswith search test WIDGET"); + D.customFields = Util.WidgetRequiredCustomFieldsJsonString(); + D.dollarAmount = 1.11m; + D.active = true; + D.usertype = 1; + D.notes = "This record will match in notes: The quick brown and hapless goose"; + + + ApiResponse a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), D.ToString()); + Util.ValidateDataReturnResponseOk(a); + long MatchWidgetInNotesId = a.ObjectResponse["data"]["id"].Value(); + + //CREATE FIRST TEST USER WITH PHRASE IN NAME + D = new JObject(); + D.name = Util.Uniquify("Wildcard startswith search NAME happy goose Test User"); + D.notes = "This user has the match in it's name"; + + D.active = true; + D.login = Util.Uniquify("LOGIN"); + D.password = Util.Uniquify("PASSWORD"); + D.usertype = 1; + + D.userType = 3;//non scheduleable + D.customFields = Util.UserRequiredCustomFieldsJsonString(); + + a = await Util.PostAsync("User", await Util.GetTokenAsync("superuser", "l3tm3in"), D.ToString()); + Util.ValidateDataReturnResponseOk(a); + long MatchUserInNameId = a.ObjectResponse["data"]["id"].Value(); + + + //Now see if can find those objects with a phrase search + dynamic SearchParameters = new JObject(); + + SearchParameters.phrase = TEST_SEARCH_PHRASE; + + SearchParameters.typeOnly = 0;//no type + SearchParameters.maxResults = 0; + a = await Util.PostAsync("search", await Util.GetTokenAsync("superuser", "l3tm3in"), SearchParameters.ToString()); + Util.ValidateDataReturnResponseOk(a); + + //Now validate the return list + ((JArray)a.ObjectResponse["data"]["searchResults"]).Count.Should().BeGreaterOrEqualTo(2); + + //Turn the list into an array of id's + var v = ((JArray)a.ObjectResponse["data"]["searchResults"]); + List MatchingIdList = new List(); + foreach (JObject j in v) + { + MatchingIdList.Add(j["id"].Value()); + } + + //Ensure the expected items are returned + MatchingIdList.Should().Contain(MatchWidgetInNotesId, "ShouldContainMatchWidgetInNotesId"); + MatchingIdList.Should().Contain(MatchUserInNameId, "ShouldContainMatchUserInNameId"); + + }//eot + + + [Fact] + public async Task WildCardEndsWithSearchShouldWork() + { + const string TEST_SEARCH_PHRASE = "goose *act"; + + //CREATE A WIDGET + dynamic D = new JObject(); + D.name = Util.Uniquify("Wildcard endswith search test WIDGET"); + D.customFields = Util.WidgetRequiredCustomFieldsJsonString(); + D.dollarAmount = 1.11m; + D.active = true; + D.usertype = 1; + D.notes = "This record will match in notes: react to the goose"; + + ApiResponse a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), D.ToString()); + Util.ValidateDataReturnResponseOk(a); + long MatchWidgetInNotesId = a.ObjectResponse["data"]["id"].Value(); + + //CREATE FIRST TEST USER WITH PHRASE IN NAME + D = new JObject(); + D.name = Util.Uniquify("Wildcard endswith search NAME goose exact Test User"); + D.notes = "This user has the match in it's name"; + + D.active = true; + D.login = Util.Uniquify("LOGIN"); + D.password = Util.Uniquify("PASSWORD"); + D.usertype = 1; + + D.userType = 3;//non scheduleable + D.customFields = Util.UserRequiredCustomFieldsJsonString(); + + a = await Util.PostAsync("User", await Util.GetTokenAsync("superuser", "l3tm3in"), D.ToString()); + Util.ValidateDataReturnResponseOk(a); + long MatchUserInNameId = a.ObjectResponse["data"]["id"].Value(); + + + //Now see if can find those objects with a phrase search + dynamic SearchParameters = new JObject(); + + SearchParameters.phrase = TEST_SEARCH_PHRASE; + + SearchParameters.typeOnly = 0;//no type + SearchParameters.maxResults = 0; + a = await Util.PostAsync("search", await Util.GetTokenAsync("superuser", "l3tm3in"), SearchParameters.ToString()); + Util.ValidateDataReturnResponseOk(a); + + //Now validate the return list + ((JArray)a.ObjectResponse["data"]["searchResults"]).Count.Should().BeGreaterOrEqualTo(2); + + //Turn the list into an array of id's + var v = ((JArray)a.ObjectResponse["data"]["searchResults"]); + List MatchingIdList = new List(); + foreach (JObject j in v) + { + MatchingIdList.Add(j["id"].Value()); + } + + //Ensure the expected items are returned + MatchingIdList.Should().Contain(MatchWidgetInNotesId, "ShouldContainMatchWidgetInNotesId"); + MatchingIdList.Should().Contain(MatchUserInNameId, "ShouldContainMatchUserInNameId"); + + }//eot + + + + + [Fact] + public async Task SearchAndExtractShouldWork() + { + const string TEST_SEARCH_PHRASE = "cast goose"; + + //CREATE A WIDGET + dynamic D = new JObject(); + D.name = Util.Uniquify("Wildcard contains search test WIDGET"); + D.customFields = Util.WidgetRequiredCustomFieldsJsonString(); + D.dollarAmount = 1.11m; + D.active = true; + D.usertype = 1; + D.notes = "This record will match in notes: broadcasting to the goose"; + + ApiResponse a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), D.ToString()); + Util.ValidateDataReturnResponseOk(a); + long MatchWidgetInNotesId = a.ObjectResponse["data"]["id"].Value(); + + //CREATE FIRST TEST USER WITH PHRASE IN NAME + D = new JObject(); + D.name = Util.Uniquify("Wildcard contains search NAME goose elcastro Test User"); + D.notes = "This user has the match in it's name"; + + D.active = true; + D.login = Util.Uniquify("LOGIN"); + D.password = Util.Uniquify("PASSWORD"); + D.usertype = 1; + + D.userType = 3;//non scheduleable + D.customFields = Util.UserRequiredCustomFieldsJsonString(); + + a = await Util.PostAsync("User", await Util.GetTokenAsync("superuser", "l3tm3in"), D.ToString()); + Util.ValidateDataReturnResponseOk(a); + long MatchUserInNameId = a.ObjectResponse["data"]["id"].Value(); + + + //Now see if can find those objects with a phrase search + dynamic SearchParameters = new JObject(); + + SearchParameters.phrase = TEST_SEARCH_PHRASE; + + SearchParameters.typeOnly = 0;//no type + SearchParameters.maxResults = 0; + a = await Util.PostAsync("search", await Util.GetTokenAsync("superuser", "l3tm3in"), SearchParameters.ToString()); + Util.ValidateDataReturnResponseOk(a); + + //Now validate the return list + ((JArray)a.ObjectResponse["data"]["searchResults"]).Count.Should().BeGreaterOrEqualTo(2); + + //Turn the list into an array of id's + var v = ((JArray)a.ObjectResponse["data"]["searchResults"]); + List MatchingIdList = new List(); + foreach (JObject j in v) + { + MatchingIdList.Add(j["id"].Value()); + } + + //Ensure the expected items are returned + MatchingIdList.Should().Contain(MatchWidgetInNotesId, "ShouldContainMatchWidgetInNotesId"); + MatchingIdList.Should().Contain(MatchUserInNameId, "ShouldContainMatchUserInNameId"); + + + //Ensure excerpt works and contains the search phrase + // /Search/Info/2/1?phrase=we&max=200 + a = await Util.GetAsync($"search/Info/2/{MatchWidgetInNotesId}?phrase={TEST_SEARCH_PHRASE}&max=200", await Util.GetTokenAsync("superuser", "l3tm3in")); + Util.ValidateDataReturnResponseOk(a); + a.ObjectResponse["data"].Value().Should().Contain(TEST_SEARCH_PHRASE.Split(" ")[0]); + a.ObjectResponse["data"].Value().Should().Contain(TEST_SEARCH_PHRASE.Split(" ")[1]); + + }//eot + + + [Fact] + public async Task TagSearchShouldWork() + { + const string TEST_SEARCH_PHRASE = "element* aardvark"; + + // //CREATE A TAG + // dynamic D = new JObject(); + // D.name = Util.Uniquify("TAGSEARCH"); + // ApiResponse a = await Util.PostAsync("Tag", await Util.GetTokenAsync("superuser", "l3tm3in"), D.ToString()); + // Util.ValidateDataReturnResponseOk(a); + // long TagId = a.ObjectResponse["data"]["id"].Value(); + + + var SearchTagPhrase = Util.Uniquify("TAGSEARCH"); + //Tags + dynamic TagsArray = new JArray(); + TagsArray.Add(SearchTagPhrase); + + //w.tags = InclusiveTagsArray; + + //CREATE A WIDGET + dynamic D = new JObject(); + D.name = Util.Uniquify("TAG search test WIDGET TAG AND PHRASE"); + D.customFields = Util.WidgetRequiredCustomFieldsJsonString(); + D.dollarAmount = 1.11m; + D.active = true; + D.usertype = 1; + D.notes = "This record will match in notes and tag: elementary my dear aardvark"; + D.tags = TagsArray; + + ApiResponse a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), D.ToString()); + Util.ValidateDataReturnResponseOk(a); + long MatchWidgetInNotesId = a.ObjectResponse["data"]["id"].Value(); + + + + + //CREATE A WIDGET WITH TAG BUT NOT SEARCH PHRASE + D = new JObject(); + D.name = Util.Uniquify("TAG search test WIDGET TAG ONLY"); + D.customFields = Util.WidgetRequiredCustomFieldsJsonString(); + D.dollarAmount = 1.11m; + D.active = true; + D.usertype = 1; + D.notes = "This record will match in tag but no search phrase"; + D.tags = TagsArray; + + a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), D.ToString()); + Util.ValidateDataReturnResponseOk(a); + long NoPhraseMatchWidgetInTagId = a.ObjectResponse["data"]["id"].Value(); + + + + //CREATE FIRST TEST USER WITH PHRASE IN NAME BUT NO TAG + D = new JObject(); + D.name = Util.Uniquify("Wildcard contains search NAME elementary aardvark Test User"); + D.notes = "This user has the match in it's name but no tag match"; + + D.active = true; + D.login = Util.Uniquify("LOGIN"); + D.password = Util.Uniquify("PASSWORD"); + D.usertype = 1; + + D.userType = 3;//non scheduleable + D.customFields = Util.UserRequiredCustomFieldsJsonString(); + + a = await Util.PostAsync("User", await Util.GetTokenAsync("superuser", "l3tm3in"), D.ToString()); + Util.ValidateDataReturnResponseOk(a); + long MatchUserInNameId = a.ObjectResponse["data"]["id"].Value(); + + + //Now see if can find those objects with a phrase search + dynamic SearchParameters = new JObject(); + + SearchParameters.phrase = TEST_SEARCH_PHRASE + " " + SearchTagPhrase; + + SearchParameters.typeOnly = 0;//no type + + a = await Util.PostAsync("search", await Util.GetTokenAsync("superuser", "l3tm3in"), SearchParameters.ToString()); + Util.ValidateDataReturnResponseOk(a); + + //Now validate the return list + ((JArray)a.ObjectResponse["data"]["searchResults"]).Count.Should().BeGreaterOrEqualTo(1); + + //Turn the list into an array of id's + var v = ((JArray)a.ObjectResponse["data"]["searchResults"]); + List MatchingIdList = new List(); + foreach (JObject j in v) + { + MatchingIdList.Add(j["id"].Value()); + } + + //Ensure the expected items are returned + MatchingIdList.Should().Contain(MatchWidgetInNotesId, "ShouldContainMatchWidgetInNotesId"); + MatchingIdList.Should().NotContain(MatchUserInNameId, "ShouldNotContainMatchUserInNameId"); + MatchingIdList.Should().NotContain(NoPhraseMatchWidgetInTagId, "ShouldNotContainNoPhraseMatchWidgetInTagId"); + + }//eot + + + + [Fact] + public async Task ConstrainedBigDataSearchShouldHonourMaxResultsAndBeRelativelyFast() + { + //THIS test is a bit different in that it relies partly on the big dataset for testing + //so it has different paths depending upon if it's testing against the big data or not + const string TEST_SEARCH_PHRASE = "et*"; + + //Now see if can find those objects with a phrase search + dynamic SearchParameters = new JObject(); + + SearchParameters.phrase = TEST_SEARCH_PHRASE; + + SearchParameters.typeOnly = 0;//no type + SearchParameters.maxResults = 1000;//default is 500 + + var watch = new System.Diagnostics.Stopwatch(); + watch.Start(); + ApiResponse a = await Util.PostAsync("search", await Util.GetTokenAsync("superuser", "l3tm3in"), SearchParameters.ToString()); + watch.Stop(); + + var TimeToSearch = watch.ElapsedMilliseconds; + + Util.ValidateDataReturnResponseOk(a); + + //Now validate the return list + var ResultCount = ((JArray)a.ObjectResponse["data"]["searchResults"]).Count; + //assert it's not unbounded + ResultCount.Should().BeLessOrEqualTo(1000); + + if (ResultCount > 999) + { + //assert the TotalResultsFound is greater than the results returned + var TotalResultsFound = a.ObjectResponse["data"]["totalResultsFound"].Value(); + //assert it's not unbounded + TotalResultsFound.Should().BeGreaterThan(ResultCount); + } + //5456 ms is the longest I've seen in initial testing with all 1000 results so setting 10% above + TimeToSearch.Should().BeLessThan(6000, "Constrained big data search should not be too slow"); + + }//eot + + + [Fact] + public async Task UnboundBigDataSearchShouldBeRelativelyFast() + { + //THIS test is a bit different in that it relies partly on the big dataset for testing + //so it has different paths depending upon if it's testing against the big data or not + const string TEST_SEARCH_PHRASE = "et*"; + + //Now see if can find those objects with a phrase search + dynamic SearchParameters = new JObject(); + + SearchParameters.phrase = TEST_SEARCH_PHRASE; + + SearchParameters.typeOnly = 0;//no type + SearchParameters.maxResults = 0;//0=return all results + + var watch = new System.Diagnostics.Stopwatch(); + watch.Start(); + ApiResponse a = await Util.PostAsync("search", await Util.GetTokenAsync("superuser", "l3tm3in"), SearchParameters.ToString()); + watch.Stop(); + + var TimeToSearch = watch.ElapsedMilliseconds; + + Util.ValidateDataReturnResponseOk(a); + + //Now validate the return list + var ResultCount = ((JArray)a.ObjectResponse["data"]["searchResults"]).Count; + + + //Set this time based on testing. 52385 Slowest run plus 10% + TimeToSearch.Should().BeLessThan(57623, "Unconstrained big data search should not be too slow"); + + + }//eot + + + + [Fact] + public async Task SearchForSerialFieldShouldWork() + { + //CREATE A WIDGET + dynamic D = new JObject(); + D.name = Util.Uniquify("Serial search test WIDGET"); + D.customFields = Util.WidgetRequiredCustomFieldsJsonString(); + D.dollarAmount = 1.11m; + D.active = true; + D.usertype = 1; + D.notes = "Test for serial number search"; + + ApiResponse a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), D.ToString()); + Util.ValidateDataReturnResponseOk(a); + long MatchWidgetInSerialId = a.ObjectResponse["data"]["id"].Value(); + var MatchWidgetSerial = a.ObjectResponse["data"]["serial"].Value(); + + //TODO: get this from the return object + string SerialSearch = MatchWidgetSerial.ToString(); ; + + + //Now see if can find those objects with a phrase search + dynamic SearchParameters = new JObject(); + SearchParameters.phrase = SerialSearch; + + SearchParameters.typeOnly = 0;//no type + SearchParameters.maxResults = 0; + a = await Util.PostAsync("search", await Util.GetTokenAsync("superuser", "l3tm3in"), SearchParameters.ToString()); + Util.ValidateDataReturnResponseOk(a); + + //Now validate the return list + ((JArray)a.ObjectResponse["data"]["searchResults"]).Count.Should().BeGreaterOrEqualTo(1); + + //Turn the list into an array of id's + var v = ((JArray)a.ObjectResponse["data"]["searchResults"]); + List MatchingIdList = new List(); + foreach (JObject j in v) + { + MatchingIdList.Add(j["id"].Value()); + } + + //Ensure the expected items are returned + MatchingIdList.Should().Contain(MatchWidgetInSerialId, "ShouldContainMatchWidgetInSerialId"); + + + + }//eot + + + + + + [Fact] + public async Task CustomFieldSearchShouldWork() + { + /* + Failing on huge data test after many hours: + +[xUnit.net 00:00:21.49] raven_integration.SearchOps.CustomFieldSearchShouldWork [FAIL] + X raven_integration.SearchOps.CustomFieldSearchShouldWork [1s 84ms] + Error Message: + Expected MatchingIdList {109274L, 109095L, 108919L, 108740L, 108558L, 108382L, 108201L, 108021L, 107842L, 107663L, 107487L, 107305L, 107126L, 106947L, 106768L, 106589L, 106413L, 106233L, 106052L, 105873L, 105692L, 105510L, 105341L, 105157L, 104978L, 104799L, 104620L, 104441L, 104262L, 104084L, 103906L, 103725L, .468 more.} to contain 195378L because ShouldContainMatchingCustomFieldWidgetId. + Stack Trace: + at FluentAssertions.Execution.XUnit2TestFramework.Throw(String message) + at FluentAssertions.Execution.TestFrameworkProvider.Throw(String message) + at FluentAssertions.Execution.DefaultAssertionStrategy.HandleFailure(String message) + at FluentAssertions.Execution.AssertionScope.FailWith(Func`1 failReasonFunc) + at FluentAssertions.Collections.SelfReferencingCollectionAssertions`2.Contain(T expected, String because, Object[] becauseArgs) + at raven_integration.SearchOps.CustomFieldSearchShouldWork() in c:\data\code\raven-test-integration\Search\SearchOps.cs:line 644 + at System.Threading.Tasks.Task.<>c.b__139_0(Object state) + +Likely fix is to force order to most recent or simply to delete after test so they don't build up into a huge list + + */ + + //CREATE CUSTOM FIELD DATA TO SEARCH FOR (note must use already defined template so c2 is the text one) + dynamic dCustomField = new JObject(); + dCustomField.c1 = "2019-02-08T06:31:48.0019809Z"; + dCustomField.c2 = "pelican beak nozzle"; + dCustomField.c3 = "747"; + dCustomField.c4 = "true"; + dCustomField.c5 = "23.45"; + + //CREATE A WIDGET + dynamic D = new JObject(); + D.name = Util.Uniquify("CUSTOMFIELD search test WIDGET"); + D.customFields = dCustomField.ToString(); + D.dollarAmount = 1.11m; + D.active = true; + D.usertype = 1; + D.notes = "This record will match in custom field"; + + ApiResponse a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), D.ToString()); + Util.ValidateDataReturnResponseOk(a); + long MatchingWidgetId = a.ObjectResponse["data"]["id"].Value(); + + + //Now see if can find this object with a phrase search + dynamic SearchParameters = new JObject(); + + SearchParameters.phrase = "beak pelican"; + + SearchParameters.typeOnly = 0;//no type + + a = await Util.PostAsync("search", await Util.GetTokenAsync("superuser", "l3tm3in"), SearchParameters.ToString()); + Util.ValidateDataReturnResponseOk(a); + + //Now validate the return list + ((JArray)a.ObjectResponse["data"]["searchResults"]).Count.Should().BeGreaterOrEqualTo(1);//might be a successive run and still have some left so account for more than one return + + //Turn the list into an array of id's + var v = ((JArray)a.ObjectResponse["data"]["searchResults"]); + List MatchingIdList = new List(); + foreach (JObject j in v) + { + MatchingIdList.Add(j["id"].Value()); + } + + //Ensure the expected items are returned + MatchingIdList.Should().Contain(MatchingWidgetId, "ShouldContainMatchingCustomFieldWidgetId"); + + //Now delete the newly created one so the list doesn't build up and prevent this test from working in big runs... + //DELETE + ApiResponse DELETETestResponse = await Util.DeleteAsync("widget/" + MatchingWidgetId.ToString(), await Util.GetTokenAsync("superuser", "l3tm3in")); + Util.ValidateHTTPStatusCode(DELETETestResponse, 204); + + + }//eot + + + + + [Fact] + public async Task DeletedObjectShouldRemoveKeywords() + { + string TEST_SEARCH_PHRASE = Util.Uniquify("qqwweerrttyy"); + + //CREATE A WIDGET + dynamic d = new JObject(); + d.name = Util.Uniquify("Wildcard endswith search test WIDGET"); + d.customFields = Util.WidgetRequiredCustomFieldsJsonString(); + d.dollarAmount = 1.11m; + d.active = true; + d.usertype = 1; + d.notes = $"This record will match in notes: {TEST_SEARCH_PHRASE} there"; + + ApiResponse a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), d.ToString()); + Util.ValidateDataReturnResponseOk(a); + long WidgetId = (long)a.ObjectResponse["data"]["id"]; + + //Now see if can find with a phrase search + dynamic SearchParameters = new JObject(); + SearchParameters.phrase = TEST_SEARCH_PHRASE; + SearchParameters.typeOnly = 0;//no type + SearchParameters.maxResults = 0; + a = await Util.PostAsync("search", await Util.GetTokenAsync("superuser", "l3tm3in"), SearchParameters.ToString()); + Util.ValidateDataReturnResponseOk(a); + //Now validate the return list (should be only one as it's super unique) + ((JArray)a.ObjectResponse["data"]["searchResults"]).Count.Should().Be(1); + + //Now delete the widget and re-run the search + a = await Util.DeleteAsync("widget/" + WidgetId.ToString(), await Util.GetTokenAsync("superuser", "l3tm3in")); + Util.ValidateHTTPStatusCode(a, 204); + + a = await Util.PostAsync("search", await Util.GetTokenAsync("superuser", "l3tm3in"), SearchParameters.ToString()); + Util.ValidateDataReturnResponseOk(a); + //Now validate the return list (should be only one as it's super unique) + ((JArray)a.ObjectResponse["data"]["searchResults"]).Count.Should().Be(0); + + + }//eot + //================================================== + + }//eoc +}//eons diff --git a/ServerJob/JobOperations.cs b/ServerJob/JobOperations.cs index c06c79b..3c8c479 100644 --- a/ServerJob/JobOperations.cs +++ b/ServerJob/JobOperations.cs @@ -1,59 +1,59 @@ -using System; -using Xunit; -using Newtonsoft.Json.Linq; -using FluentAssertions; -using System.Collections.Generic; -using System.Collections.Concurrent; - -namespace raven_integration -{ - - public class ServerJob - { - - /// - /// - /// - [Fact] - public async void TestJobShouldSubmit() - { - ApiResponse a = await Util.PostAsync("job-operations/test-job", await Util.GetTokenAsync("OpsAdminFull")); - //Util.ValidateDataReturnResponseOk(a); - Util.ValidateHTTPStatusCode(a, 202); - //should return something like this: - /* - { - "testJobId": 4 - } - */ - - String jobId = a.ObjectResponse["jobId"].Value(); - - //Get a list of operations - a = await Util.GetAsync("job-operations", await Util.GetTokenAsync("OpsAdminFull")); - Util.ValidateDataReturnResponseOk(a); - Util.ValidateHTTPStatusCode(a, 200); - - - - //there should be at least 1 - ((JArray)a.ObjectResponse["data"]).Count.Should().BeGreaterOrEqualTo(1); - - //See if our job is in there - bool bFound=false; - foreach(JToken t in a.ObjectResponse["data"]) - { - if(t["gId"].Value()==jobId) - bFound=true; - } - bFound.Should().BeTrue(); - - - - } - - - //================================================== - - }//eoc -}//eons +using System; +using Xunit; +using Newtonsoft.Json.Linq; +using FluentAssertions; +using System.Collections.Generic; +using System.Collections.Concurrent; + +namespace raven_integration +{ + + public class ServerJob + { + + /// + /// + /// + [Fact] + public async Task TestJobShouldSubmit() + { + ApiResponse a = await Util.PostAsync("job-operations/test-job", await Util.GetTokenAsync("OpsAdminFull")); + //Util.ValidateDataReturnResponseOk(a); + Util.ValidateHTTPStatusCode(a, 202); + //should return something like this: + /* + { + "testJobId": 4 + } + */ + + String jobId = a.ObjectResponse["jobId"].Value(); + + //Get a list of operations + a = await Util.GetAsync("job-operations", await Util.GetTokenAsync("OpsAdminFull")); + Util.ValidateDataReturnResponseOk(a); + Util.ValidateHTTPStatusCode(a, 200); + + + + //there should be at least 1 + ((JArray)a.ObjectResponse["data"]).Count.Should().BeGreaterOrEqualTo(1); + + //See if our job is in there + bool bFound=false; + foreach(JToken t in a.ObjectResponse["data"]) + { + if(t["gId"].Value()==jobId) + bFound=true; + } + bFound.Should().BeTrue(); + + + + } + + + //================================================== + + }//eoc +}//eons diff --git a/ServerState/ServerStateTest.cs b/ServerState/ServerStateTest.cs index 23309fe..0eec5a7 100644 --- a/ServerState/ServerStateTest.cs +++ b/ServerState/ServerStateTest.cs @@ -1,25 +1,25 @@ -using Xunit; - -namespace raven_integration -{ - - public class ServerStateTest - { - - /// - /// Test get state - /// - [Fact] - public async void ServerStateShouldReturnOk() - { - ApiResponse a = await Util.GetAsync("server-state"); - Util.ValidateDataReturnResponseOk(a); - } - - - //NOTE: can't test set because it would break the other tests - - //================================================== - - }//eoc -}//eons +using Xunit; + +namespace raven_integration +{ + + public class ServerStateTest + { + + /// + /// Test get state + /// + [Fact] + public async Task ServerStateShouldReturnOk() + { + ApiResponse a = await Util.GetAsync("server-state"); + Util.ValidateDataReturnResponseOk(a); + } + + + //NOTE: can't test set because it would break the other tests + + //================================================== + + }//eoc +}//eons diff --git a/Tags/TagOps.cs b/Tags/TagOps.cs index e97888f..e0adbc5 100644 --- a/Tags/TagOps.cs +++ b/Tags/TagOps.cs @@ -1,165 +1,165 @@ -using Xunit; -using Newtonsoft.Json.Linq; -using FluentAssertions; -using System.Collections.Generic; - - -namespace raven_integration -{ - - public class TagOps - { - - /// - /// - /// - [Fact] - public async void TagListsWork() - { - - var TestName = "TagListsWork"; - var WidgetRunNameStart = Util.Uniquify(TestName); - var TagNameStart = Util.Uniquify("crud-tag-test-") + "-";//ensure this run gets it's own unique tags - TagNameStart = TagNameStart.Replace(" ", ""); - - List InitialTagsList = new List(); - InitialTagsList.Add(TagNameStart + "red"); - InitialTagsList.Add(TagNameStart + "orange"); - InitialTagsList.Add(TagNameStart + "yellow"); - InitialTagsList.Add(TagNameStart + "green"); - InitialTagsList.Add(TagNameStart + "blue"); - InitialTagsList.Add(TagNameStart + "indigo"); - InitialTagsList.Add(TagNameStart + "violet"); - - List UpdateTagsList = new List(); - //Newly added tags - UpdateTagsList.Add(TagNameStart + "crimson"); - UpdateTagsList.Add(TagNameStart + "amber"); - UpdateTagsList.Add(TagNameStart + "saffron"); - UpdateTagsList.Add(TagNameStart + "emerald"); - UpdateTagsList.Add(TagNameStart + "azure"); - UpdateTagsList.Add(TagNameStart + "cobalt"); - UpdateTagsList.Add(TagNameStart + "magenta"); - - //maintains these tags - UpdateTagsList.Add(TagNameStart + "red"); - UpdateTagsList.Add(TagNameStart + "blue"); - - //Removes these tags by omission - //orange, yellow, green, indigo, violet - - - dynamic w = new JObject(); - w.name = Util.Uniquify(WidgetRunNameStart); - w.notes = "blah"; - w.customFields = Util.WidgetRequiredCustomFieldsJsonString(); - w.usertype = 1; - //Tags - dynamic InitialTags = new JArray(); - foreach (string s in InitialTagsList) - { - InitialTags.Add(s); - } - w.tags = InitialTags; - - ApiResponse a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w.ToString()); - Util.ValidateDataReturnResponseOk(a); - long WidgetId = a.ObjectResponse["data"]["id"].Value(); - uint Concurrency = a.ObjectResponse["data"]["concurrency"].Value(); - w = a.ObjectResponse["data"]; - - //validate the repository LIST ROUTE of tags contains the ones above - a = await Util.GetAsync($"tag-list/list?query={TagNameStart}", await Util.GetTokenAsync("superuser", "l3tm3in")); - Util.ValidateDataReturnResponseOk(a); - Util.ValidateHTTPStatusCode(a, 200); - ((JArray)a.ObjectResponse["data"]).Count.Should().Be(7); - - - //UPDATE Tags - dynamic UpdateTags = new JArray(); - - //Adds these tags - foreach (string s in UpdateTagsList) - { - UpdateTags.Add(s); - } - //update Widget and put to server - w.concurrency = Concurrency; - w.tags = UpdateTags; - ApiResponse PUTTestResponse = await Util.PutAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w.ToString()); - Util.ValidateHTTPStatusCode(PUTTestResponse, 200); - - - //Verify the tags collection remaining - a = await Util.GetAsync($"tag-list/list?query=" + TagNameStart, await Util.GetTokenAsync("superuser", "l3tm3in")); - Util.ValidateDataReturnResponseOk(a); - Util.ValidateHTTPStatusCode(a, 200); - ((JArray)a.ObjectResponse["data"]).Count.Should().Be(9); - - //Verify the CLOUD LIST AND REF COUNT of tags collection remaining - a = await Util.GetAsync($"tag-list/cloudlist?query=" + TagNameStart, await Util.GetTokenAsync("superuser", "l3tm3in")); - Util.ValidateDataReturnResponseOk(a); - Util.ValidateHTTPStatusCode(a, 200); - ((JArray)a.ObjectResponse["data"]).Count.Should().Be(9); - a.ObjectResponse["data"][0]["refCount"].Value().Should().Be(1); - - //DELETE - ApiResponse DELETETestResponse = await Util.DeleteAsync("widget/" + WidgetId.ToString(), await Util.GetTokenAsync("superuser", "l3tm3in")); - Util.ValidateHTTPStatusCode(DELETETestResponse, 204); - - //Verify the tags collection remaining - a = await Util.GetAsync($"tag-list/list?query=" + TagNameStart, await Util.GetTokenAsync("superuser", "l3tm3in")); - Util.ValidateDataReturnResponseOk(a); - Util.ValidateHTTPStatusCode(a, 200); - ((JArray)a.ObjectResponse["data"]).Count.Should().Be(0); - - } - - - - /// - /// Test bulk tag bad params - /// - [Fact] - public async void BulkBadParamsShouldFail() - { - - dynamic d = new JArray(); - // d.Add(1); - // d.Add(2); - // d.Add(3); - - ApiResponse a = await Util.PostAsync("tag-list/bulk-add/33/my new tag", await Util.GetTokenAsync("superuser", "l3tm3in"), d.ToString()); - ; - } - - - - - // /// - // /// Test bulk tag - // /// - // [Fact] - // public async void BulkTagDriver() - // { - - // dynamic d = new JArray(); - // d.Add(1); - // d.Add(2); - - - // ApiResponse a = await Util.PostAsync("tag-list/bulk-add/2/my new tag", await Util.GetTokenAsync("superuser", "l3tm3in"), d.ToString()); - // //http://localhost:7575/api/v8/tag-list/bulk-add-any/2/bulk-add-this-tag - // //http://localhost:7575/api/v8/tag-list/bulk-remove/2/happy%20new%20tag - // //http://localhost:7575/api/v8/tag-list/bulk-remove-any/2/red - // //http://localhost:7575/api/v8/tag-list/bulk-replace/2/bulk-add-this-tag?toTag=bulk-update-this-tag - // //http://localhost:7575/api/v8/tag-list/bulk-replace-any/2/bulk-update-this-tag?toTag=bulk-replace-this-tag-any - // ; - // } - - - - //================================================== - - }//eoc -}//eons +using Xunit; +using Newtonsoft.Json.Linq; +using FluentAssertions; +using System.Collections.Generic; + + +namespace raven_integration +{ + + public class TagOps + { + + /// + /// + /// + [Fact] + public async Task TagListsWork() + { + + var TestName = "TagListsWork"; + var WidgetRunNameStart = Util.Uniquify(TestName); + var TagNameStart = Util.Uniquify("crud-tag-test-") + "-";//ensure this run gets it's own unique tags + TagNameStart = TagNameStart.Replace(" ", ""); + + List InitialTagsList = new List(); + InitialTagsList.Add(TagNameStart + "red"); + InitialTagsList.Add(TagNameStart + "orange"); + InitialTagsList.Add(TagNameStart + "yellow"); + InitialTagsList.Add(TagNameStart + "green"); + InitialTagsList.Add(TagNameStart + "blue"); + InitialTagsList.Add(TagNameStart + "indigo"); + InitialTagsList.Add(TagNameStart + "violet"); + + List UpdateTagsList = new List(); + //Newly added tags + UpdateTagsList.Add(TagNameStart + "crimson"); + UpdateTagsList.Add(TagNameStart + "amber"); + UpdateTagsList.Add(TagNameStart + "saffron"); + UpdateTagsList.Add(TagNameStart + "emerald"); + UpdateTagsList.Add(TagNameStart + "azure"); + UpdateTagsList.Add(TagNameStart + "cobalt"); + UpdateTagsList.Add(TagNameStart + "magenta"); + + //maintains these tags + UpdateTagsList.Add(TagNameStart + "red"); + UpdateTagsList.Add(TagNameStart + "blue"); + + //Removes these tags by omission + //orange, yellow, green, indigo, violet + + + dynamic w = new JObject(); + w.name = Util.Uniquify(WidgetRunNameStart); + w.notes = "blah"; + w.customFields = Util.WidgetRequiredCustomFieldsJsonString(); + w.usertype = 1; + //Tags + dynamic InitialTags = new JArray(); + foreach (string s in InitialTagsList) + { + InitialTags.Add(s); + } + w.tags = InitialTags; + + ApiResponse a = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w.ToString()); + Util.ValidateDataReturnResponseOk(a); + long WidgetId = a.ObjectResponse["data"]["id"].Value(); + uint Concurrency = a.ObjectResponse["data"]["concurrency"].Value(); + w = a.ObjectResponse["data"]; + + //validate the repository LIST ROUTE of tags contains the ones above + a = await Util.GetAsync($"tag-list/list?query={TagNameStart}", await Util.GetTokenAsync("superuser", "l3tm3in")); + Util.ValidateDataReturnResponseOk(a); + Util.ValidateHTTPStatusCode(a, 200); + ((JArray)a.ObjectResponse["data"]).Count.Should().Be(7); + + + //UPDATE Tags + dynamic UpdateTags = new JArray(); + + //Adds these tags + foreach (string s in UpdateTagsList) + { + UpdateTags.Add(s); + } + //update Widget and put to server + w.concurrency = Concurrency; + w.tags = UpdateTags; + ApiResponse PUTTestResponse = await Util.PutAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w.ToString()); + Util.ValidateHTTPStatusCode(PUTTestResponse, 200); + + + //Verify the tags collection remaining + a = await Util.GetAsync($"tag-list/list?query=" + TagNameStart, await Util.GetTokenAsync("superuser", "l3tm3in")); + Util.ValidateDataReturnResponseOk(a); + Util.ValidateHTTPStatusCode(a, 200); + ((JArray)a.ObjectResponse["data"]).Count.Should().Be(9); + + //Verify the CLOUD LIST AND REF COUNT of tags collection remaining + a = await Util.GetAsync($"tag-list/cloudlist?query=" + TagNameStart, await Util.GetTokenAsync("superuser", "l3tm3in")); + Util.ValidateDataReturnResponseOk(a); + Util.ValidateHTTPStatusCode(a, 200); + ((JArray)a.ObjectResponse["data"]).Count.Should().Be(9); + a.ObjectResponse["data"][0]["refCount"].Value().Should().Be(1); + + //DELETE + ApiResponse DELETETestResponse = await Util.DeleteAsync("widget/" + WidgetId.ToString(), await Util.GetTokenAsync("superuser", "l3tm3in")); + Util.ValidateHTTPStatusCode(DELETETestResponse, 204); + + //Verify the tags collection remaining + a = await Util.GetAsync($"tag-list/list?query=" + TagNameStart, await Util.GetTokenAsync("superuser", "l3tm3in")); + Util.ValidateDataReturnResponseOk(a); + Util.ValidateHTTPStatusCode(a, 200); + ((JArray)a.ObjectResponse["data"]).Count.Should().Be(0); + + } + + + + /// + /// Test bulk tag bad params + /// + [Fact] + public async Task BulkBadParamsShouldFail() + { + + dynamic d = new JArray(); + // d.Add(1); + // d.Add(2); + // d.Add(3); + + ApiResponse a = await Util.PostAsync("tag-list/bulk-add/33/my new tag", await Util.GetTokenAsync("superuser", "l3tm3in"), d.ToString()); + ; + } + + + + + // /// + // /// Test bulk tag + // /// + // [Fact] + // public async Task BulkTagDriver() + // { + + // dynamic d = new JArray(); + // d.Add(1); + // d.Add(2); + + + // ApiResponse a = await Util.PostAsync("tag-list/bulk-add/2/my new tag", await Util.GetTokenAsync("superuser", "l3tm3in"), d.ToString()); + // //http://localhost:7575/api/v8/tag-list/bulk-add-any/2/bulk-add-this-tag + // //http://localhost:7575/api/v8/tag-list/bulk-remove/2/happy%20new%20tag + // //http://localhost:7575/api/v8/tag-list/bulk-remove-any/2/red + // //http://localhost:7575/api/v8/tag-list/bulk-replace/2/bulk-add-this-tag?toTag=bulk-update-this-tag + // //http://localhost:7575/api/v8/tag-list/bulk-replace-any/2/bulk-update-this-tag?toTag=bulk-replace-this-tag-any + // ; + // } + + + + //================================================== + + }//eoc +}//eons diff --git a/Translation/RequestedTranslationKeys.cs b/Translation/RequestedTranslationKeys.cs index c2b03c6..47ddabd 100644 --- a/Translation/RequestedTranslationKeys.cs +++ b/Translation/RequestedTranslationKeys.cs @@ -1,67 +1,67 @@ -using System; -using Xunit; -using Newtonsoft.Json.Linq; -using FluentAssertions; -using System.Collections.Generic; -using System.Threading.Tasks; -using System.Collections.Concurrent; -namespace raven_integration -{ - - public class RequestedLocaleKeys - { - - - - [Fact] - public async void RequestedLocaleKeysWorks() - { - //First determine if there is a requested key route because it's debug build dependent - //And doesn't exists if server was not debug built - ApiResponse a = await Util.GetAsync("build-mode", await Util.GetTokenAsync("CustomerLimited")); - Util.ValidateDataReturnResponseOk(a); - var BuildMode = a.ObjectResponse["data"]["buildMode"].Value(); - BuildMode.Should().BeOneOf((new string[] { "DEBUG", "RELEASE" })); - - if (BuildMode == "DEBUG") - { - - //Make a "list" of keys to fetch the values for - List keys = new List(); - keys.AddRange(new string[] { "HelpLicense", "CustomerName" }); - dynamic d = new JObject(); - - d = JToken.FromObject(keys); - - //Fetch the values to force RAVEN to track at least these two - a = await Util.PostAsync("translation/subset", await Util.GetTokenAsync("CustomerLimited"), d.ToString()); - Util.ValidateDataReturnResponseOk(a); - Util.ValidateHTTPStatusCode(a, 200); - //there should be dozens of keys but at times there might only be a few during development so at least verify there is more than one - ((JArray)a.ObjectResponse["data"]).Count.Should().Be(2); - - //Now ensure there are at least two keys in the fetched keys array - a = await Util.GetAsync("translation/TranslationKeyCoverage", await Util.GetTokenAsync("CustomerLimited")); - Util.ValidateDataReturnResponseOk(a); - Util.ValidateHTTPStatusCode(a, 200); - - var RequestedKeyCount = a.ObjectResponse["data"]["requestedKeyCount"].Value(); - RequestedKeyCount.Should().BeGreaterOrEqualTo(2); - var NotRequestedKeyCount = a.ObjectResponse["data"]["notRequestedKeyCount"].Value(); - NotRequestedKeyCount.Should().BeGreaterThan(1);//For now at least, once we have this dialed in it will be zero ultimately - - //there should be dozens of keys but at times there might only be a few during development so at least verify there is more than one - ((JArray)a.ObjectResponse["data"]["requestedKeys"]).Count.Should().Be(RequestedKeyCount); - ((JArray)a.ObjectResponse["data"]["notRequestedKeys"]).Count.Should().Be(NotRequestedKeyCount); - - } - } - - - - - - //================================================== - - }//eoc -}//eons +using System; +using Xunit; +using Newtonsoft.Json.Linq; +using FluentAssertions; +using System.Collections.Generic; +using System.Threading.Tasks; +using System.Collections.Concurrent; +namespace raven_integration +{ + + public class RequestedLocaleKeys + { + + + + [Fact] + public async Task RequestedLocaleKeysWorks() + { + //First determine if there is a requested key route because it's debug build dependent + //And doesn't exists if server was not debug built + ApiResponse a = await Util.GetAsync("build-mode", await Util.GetTokenAsync("CustomerLimited")); + Util.ValidateDataReturnResponseOk(a); + var BuildMode = a.ObjectResponse["data"]["buildMode"].Value(); + BuildMode.Should().BeOneOf((new string[] { "DEBUG", "RELEASE" })); + + if (BuildMode == "DEBUG") + { + + //Make a "list" of keys to fetch the values for + List keys = new List(); + keys.AddRange(new string[] { "HelpLicense", "CustomerName" }); + dynamic d = new JObject(); + + d = JToken.FromObject(keys); + + //Fetch the values to force RAVEN to track at least these two + a = await Util.PostAsync("translation/subset", await Util.GetTokenAsync("CustomerLimited"), d.ToString()); + Util.ValidateDataReturnResponseOk(a); + Util.ValidateHTTPStatusCode(a, 200); + //there should be dozens of keys but at times there might only be a few during development so at least verify there is more than one + ((JArray)a.ObjectResponse["data"]).Count.Should().Be(2); + + //Now ensure there are at least two keys in the fetched keys array + a = await Util.GetAsync("translation/TranslationKeyCoverage", await Util.GetTokenAsync("CustomerLimited")); + Util.ValidateDataReturnResponseOk(a); + Util.ValidateHTTPStatusCode(a, 200); + + var RequestedKeyCount = a.ObjectResponse["data"]["requestedKeyCount"].Value(); + RequestedKeyCount.Should().BeGreaterOrEqualTo(2); + var NotRequestedKeyCount = a.ObjectResponse["data"]["notRequestedKeyCount"].Value(); + NotRequestedKeyCount.Should().BeGreaterThan(1);//For now at least, once we have this dialed in it will be zero ultimately + + //there should be dozens of keys but at times there might only be a few during development so at least verify there is more than one + ((JArray)a.ObjectResponse["data"]["requestedKeys"]).Count.Should().Be(RequestedKeyCount); + ((JArray)a.ObjectResponse["data"]["notRequestedKeys"]).Count.Should().Be(NotRequestedKeyCount); + + } + } + + + + + + //================================================== + + }//eoc +}//eons diff --git a/Translation/Translation.cs b/Translation/Translation.cs index dc131f5..6b0ec9b 100644 --- a/Translation/Translation.cs +++ b/Translation/Translation.cs @@ -1,188 +1,188 @@ -using System; -using Xunit; -using Newtonsoft.Json.Linq; -using FluentAssertions; -using System.Collections.Generic; -using System.Threading.Tasks; -using System.Collections.Concurrent; -namespace raven_integration -{ - - public class Translation - { - - /* - - ImportTranslation(ct, ResourceFolderPath, "en"); - id 1 - ImportTranslation(ct, ResourceFolderPath, "es"); - id 2 - ImportTranslation(ct, ResourceFolderPath, "fr"); - id 3 - ImportTranslation(ct, ResourceFolderPath, "de"); - id 4 - */ - - [Fact] - public async void TranslationListWorks() - { - //Get all - ApiResponse a = await Util.GetAsync("translation/list", await Util.GetTokenAsync("CustomerLimited"));//lowest level test user because there are no limits on this route except to be authenticated - Util.ValidateDataReturnResponseOk(a); - Util.ValidateHTTPStatusCode(a, 200); - //there should be at least 4 of them as there are 4 stock translations - ((JArray)a.ObjectResponse["data"]).Count.Should().BeGreaterThan(3); - } - - - [Fact] - public async void GetFullTranslationWorks() - { - //Get all - ApiResponse a = await Util.GetAsync("translation/1", await Util.GetTokenAsync("CustomerLimited"));//lowest level test user because there are no limits on this route except to be authenticated - Util.ValidateDataReturnResponseOk(a); - Util.ValidateHTTPStatusCode(a, 200); - //there should be dozens of keys but at times there might only be a few during development so at least verify there is more than one - ((JArray)a.ObjectResponse["data"]["translationItems"]).Count.Should().BeGreaterThan(0); - } - - - [Fact] - public async void GetSubsetWorks() - { - - - List keys = new List(); - keys.AddRange(new string[] { "AddressType", "CustomerName", "RateName", "WorkOrder" }); - dynamic d = new JObject(); - - d = JToken.FromObject(keys); - - ApiResponse a = await Util.PostAsync("translation/subset", await Util.GetTokenAsync("CustomerLimited"), d.ToString()); - Util.ValidateDataReturnResponseOk(a); - Util.ValidateHTTPStatusCode(a, 200); - //there should be dozens of keys but at times there might only be a few during development so at least verify there is more than one - ((JArray)a.ObjectResponse["data"]).Count.Should().Be(4); - } - - - [Fact] - public async void DuplicateUpdateAndDeleteWorks() - { - - //DUPLICATE - dynamic d = new JObject(); - d.id = 1; - d.name = Util.Uniquify("INTEGRATION-TEST-LOCALE"); - - ApiResponse a = await Util.PostAsync("translation/Duplicate", await Util.GetTokenAsync("BizAdminFull"), d.ToString()); - Util.ValidateDataReturnResponseOk(a); - Util.ValidateHTTPStatusCode(a, 201); - //verify the object returned is as expected - a.ObjectResponse["data"]["name"].Value().Should().Be(d.name.ToString()); - a.ObjectResponse["data"]["stock"].Value().Should().Be(false); - a.ObjectResponse["data"]["id"].Value().Should().BeGreaterThan(4); - a.ObjectResponse["data"]["concurrency"].Value().Should().BeGreaterThan(0); - ((JArray)a.ObjectResponse["data"]["translationItems"]).Count.Should().BeGreaterThan(0); - - long NewId = a.ObjectResponse["data"]["id"].Value(); - - //UPDATE - //Update translation name - - dynamic d2 = new JObject(); - d2.id = NewId; - d2.newText = Util.Uniquify("INTEGRATION-TEST-LOCALE NAME UPDATE"); - d2.concurrency = a.ObjectResponse["data"]["concurrency"].Value(); - ApiResponse PUTTestResponse = await Util.PutAsync("translation/UpdateTranslationName", await Util.GetTokenAsync("BizAdminFull"), d2.ToString()); - Util.ValidateHTTPStatusCode(PUTTestResponse, 200); - - - ApiResponse checkPUTWorked = await Util.GetAsync("translation/" + NewId.ToString(), await Util.GetTokenAsync("BizAdminFull")); - Util.ValidateNoErrorInResponse(checkPUTWorked); - checkPUTWorked.ObjectResponse["data"]["name"].Value().Should().Be(d2.newText.ToString()); - //uint concurrency = PUTTestResponse.ObjectResponse["data"]["concurrency"].Value(); - - - //Update translation key - var FirstTranslationKey = ((JArray)a.ObjectResponse["data"]["translationItems"])[0]; - long UpdatedTranslationKeyId = FirstTranslationKey["id"].Value(); - d2.id = UpdatedTranslationKeyId; - d2.newText = Util.Uniquify("INTEGRATION-TEST-LOCALEITEM DISPLAY UPDATE"); - d2.concurrency = FirstTranslationKey["concurrency"].Value(); - - string UpdatedTranslationKey = FirstTranslationKey["key"].Value(); - - PUTTestResponse = await Util.PutAsync("translation/UpdateTranslationItemDisplayText", await Util.GetTokenAsync("BizAdminFull"), d2.ToString()); - Util.ValidateHTTPStatusCode(PUTTestResponse, 200); - - //create user that is set to new translation so can use getSubset - var Login = Util.Uniquify("LOGIN"); - var Password = Util.Uniquify("PASSWORD"); - dynamic DUSER = new JObject(); - DUSER.name = Util.Uniquify("TranslationUpdateSubsetTestUser"); - - DUSER.active = true; - DUSER.login = Login; - DUSER.password = Password; - DUSER.roles = 0;//norole (any role can get a subset of translation keys) - // DUSER.translationId = NewId; - DUSER.userType = 3;//non scheduleable - //Required by form custom rules - DUSER.notes = "notes"; - DUSER.customFields = Util.UserRequiredCustomFieldsJsonString(); - a = await Util.PostAsync("User", await Util.GetTokenAsync("superuser", "l3tm3in"), DUSER.ToString()); - Util.ValidateDataReturnResponseOk(a); - long DUSERID = a.ObjectResponse["data"]["id"].Value(); - - - //RETRIEVE companion USEROPTIONS object - ApiResponse R = await Util.GetAsync("user-option/" + DUSERID.ToString(), await Util.GetTokenAsync("superuser", "l3tm3in")); - Util.ValidateDataReturnResponseOk(R); - //ensure the default value is set - R.ObjectResponse["data"]["uiColor"].Value().Should().Be("#000000"); - uint concurrency = R.ObjectResponse["data"]["concurrency"].Value(); - - //UPDATE - - //PUT - dynamic D2 = new JObject(); - D2.translationId = NewId; - - D2.concurrency = concurrency; - PUTTestResponse = await Util.PutAsync("user-option/" + DUSERID.ToString(), await Util.GetTokenAsync("superuser", "l3tm3in"), D2.ToString()); - Util.ValidateHTTPStatusCode(PUTTestResponse, 200); - - //VALIDATE - R = await Util.GetAsync("user-option/" + DUSERID.ToString(), await Util.GetTokenAsync("superuser", "l3tm3in")); - Util.ValidateDataReturnResponseOk(R); - - - - List keys = new List(); - keys.AddRange(new string[] { UpdatedTranslationKey }); - dynamic d3 = new JObject(); - - d3 = JToken.FromObject(keys); - - checkPUTWorked = await Util.PostAsync("translation/subset", await Util.GetTokenAsync(Login, Password), d3.ToString()); - Util.ValidateDataReturnResponseOk(checkPUTWorked); - Util.ValidateHTTPStatusCode(checkPUTWorked, 200); - ((JArray)checkPUTWorked.ObjectResponse["data"]).Count.Should().Be(1); - var FirstTranslationKeyUpdated = ((JArray)checkPUTWorked.ObjectResponse["data"])[0]; - - FirstTranslationKeyUpdated["value"].Value().Should().Be(d2.newText.ToString()); - - //DELETE TEMPORARY USER SO CAN DELETE LOCALE - a = await Util.DeleteAsync("User/" + DUSERID.ToString(), await Util.GetTokenAsync("superuser", "l3tm3in")); - Util.ValidateHTTPStatusCode(a, 204); - - //DELETE TEMP LOCALE - a = await Util.DeleteAsync("translation/" + NewId.ToString(), await Util.GetTokenAsync("BizAdminFull")); - Util.ValidateHTTPStatusCode(a, 204); - - - } - - - - //================================================== - - }//eoc -}//eons +using System; +using Xunit; +using Newtonsoft.Json.Linq; +using FluentAssertions; +using System.Collections.Generic; +using System.Threading.Tasks; +using System.Collections.Concurrent; +namespace raven_integration +{ + + public class Translation + { + + /* + + ImportTranslation(ct, ResourceFolderPath, "en"); - id 1 + ImportTranslation(ct, ResourceFolderPath, "es"); - id 2 + ImportTranslation(ct, ResourceFolderPath, "fr"); - id 3 + ImportTranslation(ct, ResourceFolderPath, "de"); - id 4 + */ + + [Fact] + public async Task TranslationListWorks() + { + //Get all + ApiResponse a = await Util.GetAsync("translation/list", await Util.GetTokenAsync("CustomerLimited"));//lowest level test user because there are no limits on this route except to be authenticated + Util.ValidateDataReturnResponseOk(a); + Util.ValidateHTTPStatusCode(a, 200); + //there should be at least 4 of them as there are 4 stock translations + ((JArray)a.ObjectResponse["data"]).Count.Should().BeGreaterThan(3); + } + + + [Fact] + public async Task GetFullTranslationWorks() + { + //Get all + ApiResponse a = await Util.GetAsync("translation/1", await Util.GetTokenAsync("CustomerLimited"));//lowest level test user because there are no limits on this route except to be authenticated + Util.ValidateDataReturnResponseOk(a); + Util.ValidateHTTPStatusCode(a, 200); + //there should be dozens of keys but at times there might only be a few during development so at least verify there is more than one + ((JArray)a.ObjectResponse["data"]["translationItems"]).Count.Should().BeGreaterThan(0); + } + + + [Fact] + public async Task GetSubsetWorks() + { + + + List keys = new List(); + keys.AddRange(new string[] { "AddressType", "CustomerName", "RateName", "WorkOrder" }); + dynamic d = new JObject(); + + d = JToken.FromObject(keys); + + ApiResponse a = await Util.PostAsync("translation/subset", await Util.GetTokenAsync("CustomerLimited"), d.ToString()); + Util.ValidateDataReturnResponseOk(a); + Util.ValidateHTTPStatusCode(a, 200); + //there should be dozens of keys but at times there might only be a few during development so at least verify there is more than one + ((JArray)a.ObjectResponse["data"]).Count.Should().Be(4); + } + + + [Fact] + public async Task DuplicateUpdateAndDeleteWorks() + { + + //DUPLICATE + dynamic d = new JObject(); + d.id = 1; + d.name = Util.Uniquify("INTEGRATION-TEST-LOCALE"); + + ApiResponse a = await Util.PostAsync("translation/Duplicate", await Util.GetTokenAsync("BizAdminFull"), d.ToString()); + Util.ValidateDataReturnResponseOk(a); + Util.ValidateHTTPStatusCode(a, 201); + //verify the object returned is as expected + a.ObjectResponse["data"]["name"].Value().Should().Be(d.name.ToString()); + a.ObjectResponse["data"]["stock"].Value().Should().Be(false); + a.ObjectResponse["data"]["id"].Value().Should().BeGreaterThan(4); + a.ObjectResponse["data"]["concurrency"].Value().Should().BeGreaterThan(0); + ((JArray)a.ObjectResponse["data"]["translationItems"]).Count.Should().BeGreaterThan(0); + + long NewId = a.ObjectResponse["data"]["id"].Value(); + + //UPDATE + //Update translation name + + dynamic d2 = new JObject(); + d2.id = NewId; + d2.newText = Util.Uniquify("INTEGRATION-TEST-LOCALE NAME UPDATE"); + d2.concurrency = a.ObjectResponse["data"]["concurrency"].Value(); + ApiResponse PUTTestResponse = await Util.PutAsync("translation/UpdateTranslationName", await Util.GetTokenAsync("BizAdminFull"), d2.ToString()); + Util.ValidateHTTPStatusCode(PUTTestResponse, 200); + + + ApiResponse checkPUTWorked = await Util.GetAsync("translation/" + NewId.ToString(), await Util.GetTokenAsync("BizAdminFull")); + Util.ValidateNoErrorInResponse(checkPUTWorked); + checkPUTWorked.ObjectResponse["data"]["name"].Value().Should().Be(d2.newText.ToString()); + //uint concurrency = PUTTestResponse.ObjectResponse["data"]["concurrency"].Value(); + + + //Update translation key + var FirstTranslationKey = ((JArray)a.ObjectResponse["data"]["translationItems"])[0]; + long UpdatedTranslationKeyId = FirstTranslationKey["id"].Value(); + d2.id = UpdatedTranslationKeyId; + d2.newText = Util.Uniquify("INTEGRATION-TEST-LOCALEITEM DISPLAY UPDATE"); + d2.concurrency = FirstTranslationKey["concurrency"].Value(); + + string UpdatedTranslationKey = FirstTranslationKey["key"].Value(); + + PUTTestResponse = await Util.PutAsync("translation/UpdateTranslationItemDisplayText", await Util.GetTokenAsync("BizAdminFull"), d2.ToString()); + Util.ValidateHTTPStatusCode(PUTTestResponse, 200); + + //create user that is set to new translation so can use getSubset + var Login = Util.Uniquify("LOGIN"); + var Password = Util.Uniquify("PASSWORD"); + dynamic DUSER = new JObject(); + DUSER.name = Util.Uniquify("TranslationUpdateSubsetTestUser"); + + DUSER.active = true; + DUSER.login = Login; + DUSER.password = Password; + DUSER.roles = 0;//norole (any role can get a subset of translation keys) + // DUSER.translationId = NewId; + DUSER.userType = 3;//non scheduleable + //Required by form custom rules + DUSER.notes = "notes"; + DUSER.customFields = Util.UserRequiredCustomFieldsJsonString(); + a = await Util.PostAsync("User", await Util.GetTokenAsync("superuser", "l3tm3in"), DUSER.ToString()); + Util.ValidateDataReturnResponseOk(a); + long DUSERID = a.ObjectResponse["data"]["id"].Value(); + + + //RETRIEVE companion USEROPTIONS object + ApiResponse R = await Util.GetAsync("user-option/" + DUSERID.ToString(), await Util.GetTokenAsync("superuser", "l3tm3in")); + Util.ValidateDataReturnResponseOk(R); + //ensure the default value is set + R.ObjectResponse["data"]["uiColor"].Value().Should().Be("#000000"); + uint concurrency = R.ObjectResponse["data"]["concurrency"].Value(); + + //UPDATE + + //PUT + dynamic D2 = new JObject(); + D2.translationId = NewId; + + D2.concurrency = concurrency; + PUTTestResponse = await Util.PutAsync("user-option/" + DUSERID.ToString(), await Util.GetTokenAsync("superuser", "l3tm3in"), D2.ToString()); + Util.ValidateHTTPStatusCode(PUTTestResponse, 200); + + //VALIDATE + R = await Util.GetAsync("user-option/" + DUSERID.ToString(), await Util.GetTokenAsync("superuser", "l3tm3in")); + Util.ValidateDataReturnResponseOk(R); + + + + List keys = new List(); + keys.AddRange(new string[] { UpdatedTranslationKey }); + dynamic d3 = new JObject(); + + d3 = JToken.FromObject(keys); + + checkPUTWorked = await Util.PostAsync("translation/subset", await Util.GetTokenAsync(Login, Password), d3.ToString()); + Util.ValidateDataReturnResponseOk(checkPUTWorked); + Util.ValidateHTTPStatusCode(checkPUTWorked, 200); + ((JArray)checkPUTWorked.ObjectResponse["data"]).Count.Should().Be(1); + var FirstTranslationKeyUpdated = ((JArray)checkPUTWorked.ObjectResponse["data"])[0]; + + FirstTranslationKeyUpdated["value"].Value().Should().Be(d2.newText.ToString()); + + //DELETE TEMPORARY USER SO CAN DELETE LOCALE + a = await Util.DeleteAsync("User/" + DUSERID.ToString(), await Util.GetTokenAsync("superuser", "l3tm3in")); + Util.ValidateHTTPStatusCode(a, 204); + + //DELETE TEMP LOCALE + a = await Util.DeleteAsync("translation/" + NewId.ToString(), await Util.GetTokenAsync("BizAdminFull")); + Util.ValidateHTTPStatusCode(a, 204); + + + } + + + + //================================================== + + }//eoc +}//eons diff --git a/User/UserCrud.cs b/User/UserCrud.cs index 87f879b..22f39eb 100644 --- a/User/UserCrud.cs +++ b/User/UserCrud.cs @@ -1,263 +1,263 @@ -using System; -using Xunit; -using Newtonsoft.Json.Linq; -using FluentAssertions; - -namespace raven_integration -{ - - public class UserCrud - { - - /// - /// Test all CRUD routes for a User - /// - [Fact] - public async void CRUD() - { - - //CREATE - dynamic D1 = new JObject(); - D1.name = Util.Uniquify("First Test User"); - - D1.active = true; - D1.login = Util.Uniquify("LOGIN"); - D1.password = Util.Uniquify("PASSWORD"); - D1.roles = 0;//norole - - D1.userType = 3;//non scheduleable - - //Required by form custom rules - D1.notes = "notes"; - D1.customFields = Util.UserRequiredCustomFieldsJsonString(); - - ApiResponse R1 = await Util.PostAsync("User", await Util.GetTokenAsync("superuser", "l3tm3in"), D1.ToString()); - Util.ValidateDataReturnResponseOk(R1); - long d1Id = R1.ObjectResponse["data"]["id"].Value(); - - - dynamic D2 = new JObject(); - D2.name = Util.Uniquify("Second Test User"); - //Required by form custom rules - D2.notes = "notes"; - D2.customFields = Util.UserRequiredCustomFieldsJsonString(); - D2.active = true; - D2.login = Util.Uniquify("LOGIN"); - D2.password = Util.Uniquify("PASSWORD"); - D2.roles = 0;//norole - - D2.userType = 3;//non scheduleable - - ApiResponse R2 = await Util.PostAsync("User", await Util.GetTokenAsync("superuser", "l3tm3in"), D2.ToString()); - Util.ValidateDataReturnResponseOk(R2); - long d2Id = R2.ObjectResponse["data"]["id"].Value(); - - - //RETRIEVE - - //Get one - ApiResponse R3 = await Util.GetAsync("User/" + d2Id.ToString(), await Util.GetTokenAsync("superuser", "l3tm3in")); - Util.ValidateDataReturnResponseOk(R3); - R3.ObjectResponse["data"]["name"].Value().Should().Be(D2.name.ToString()); - - - - //UPDATE - //PUT - - //update w2id - D2.name = Util.Uniquify("UPDATED VIA PUT SECOND TEST User"); - D2.concurrency = R2.ObjectResponse["data"]["concurrency"].Value(); - D2.id=d2Id; - ApiResponse PUTTestResponse = await Util.PutAsync("User" , await Util.GetTokenAsync("superuser", "l3tm3in"), D2.ToString()); - Util.ValidateHTTPStatusCode(PUTTestResponse, 200); - - //check PUT worked - ApiResponse checkPUTWorked = await Util.GetAsync("User/" + d2Id.ToString(), await Util.GetTokenAsync("superuser", "l3tm3in")); - Util.ValidateNoErrorInResponse(checkPUTWorked); - checkPUTWorked.ObjectResponse["data"]["name"].Value().Should().Be(D2.name.ToString()); - uint concurrency = PUTTestResponse.ObjectResponse["data"]["concurrency"].Value(); - - //DELETE - ApiResponse DELETETestResponse = await Util.DeleteAsync("User/" + d2Id.ToString(), await Util.GetTokenAsync("superuser", "l3tm3in")); - Util.ValidateHTTPStatusCode(DELETETestResponse, 204); - } - - - /// - /// - /// - [Fact] - public async void UserWithActivityShouldNotBeDeleteable() - { - ApiResponse a = await Util.DeleteAsync("User/1", await Util.GetTokenAsync("superuser", "l3tm3in")); - Util.ValidateErrorCodeResponse(a, 2200, 400); - a.ObjectResponse["error"]["details"][0]["message"].Value().Should().Contain("LT:ErrorDBForeignKeyViolation"); - } - - - /// - /// Test not found - /// - [Fact] - public async void GetNonExistentItemShouldError() - { - //Get non existant - //Should return status code 404, api error code 2010 - ApiResponse R = await Util.GetAsync("User/999999", await Util.GetTokenAsync("superuser", "l3tm3in")); - Util.ValidateResponseNotFound(R); - } - - /// - /// Test bad modelstate - /// - [Fact] - public async void GetBadModelStateShouldError() - { - //Get non existant - //Should return status code 400, api error code 2200 and a first target in details of "id" - ApiResponse R = await Util.GetAsync("User/2q2", await Util.GetTokenAsync("superuser", "l3tm3in")); - Util.ValidateBadModelStateResponse(R, "id"); - } - - - /// - /// - /// - [Fact] - public async void PutConcurrencyViolationShouldFail() - { - //CREATE - dynamic D = new JObject(); - D.name = Util.Uniquify("PutConcurrencyViolationShouldFail"); - D.notes = "notes"; - D.customFields = Util.UserRequiredCustomFieldsJsonString(); - D.active = true; - D.login = Util.Uniquify("LOGIN"); - D.password = Util.Uniquify("PASSWORD"); - D.roles = 0;//norole - - D.userType = 3;//non scheduleable - - ApiResponse R = await Util.PostAsync("User", await Util.GetTokenAsync("superuser", "l3tm3in"), D.ToString()); - Util.ValidateDataReturnResponseOk(R); - long D1Id = R.ObjectResponse["data"]["id"].Value(); - uint OriginalConcurrencyToken = R.ObjectResponse["data"]["concurrency"].Value(); - - - //UPDATE - //PUT - - D.name = Util.Uniquify("PutConcurrencyViolationShouldFail UPDATE VIA PUT "); - D.concurrency = OriginalConcurrencyToken - 1;//bad token - D.id=D1Id; - ApiResponse PUTTestResponse = await Util.PutAsync("User", await Util.GetTokenAsync("superuser", "l3tm3in"), D.ToString()); - Util.ValidateConcurrencyError(PUTTestResponse); - } - - - - /// - /// - /// - [Fact] - public async void PutPasswordShouldWork() - { - //CREATE - dynamic d = new JObject(); - d.name = Util.Uniquify("PutPasswordShouldWork"); - - d.active = true; - d.login = Util.Uniquify("LOGIN"); - d.password = Util.Uniquify("PASSWORD"); - d.roles = 0;//norole - - d.userType = 3;//non scheduleable - //Required by form custom rules - d.notes = "notes"; - d.customFields = Util.UserRequiredCustomFieldsJsonString(); - - ApiResponse a = await Util.PostAsync("User", await Util.GetTokenAsync("superuser", "l3tm3in"), d.ToString()); - Util.ValidateDataReturnResponseOk(a); - long UserId = a.ObjectResponse["data"]["id"].Value(); - uint OriginalConcurrencyToken = a.ObjectResponse["data"]["concurrency"].Value(); - - //Test can login - dynamic DCreds = new JObject(); - DCreds.password = d.password; - DCreds.login = d.login; - a = await Util.PostAsync("auth", null, DCreds.ToString()); - Util.ValidateDataReturnResponseOk(a); - - //GET user (login changed concurrency token above) - a = await Util.GetAsync("User/" + UserId.ToString(), await Util.GetTokenAsync("superuser", "l3tm3in")); - Util.ValidateDataReturnResponseOk(a); - d = a.ObjectResponse["data"]; - - - //PUT - var NewPassword = "NEW_PASSWORD"; - d.password = NewPassword; - d.login=DCreds.login; - a = await Util.PutAsync("User", await Util.GetTokenAsync("superuser", "l3tm3in"), d.ToString()); - Util.ValidateDataReturnResponseOk(a); - - //Test can login with new creds - //dynamic DCreds = new JObject(); - DCreds.password = NewPassword; - // DCreds.login = d.login; - a = await Util.PostAsync("auth", null, DCreds.ToString()); - Util.ValidateDataReturnResponseOk(a); - } - - - /// - /// - /// - [Fact] - public async void NonUniqueLoginShouldFail() - { - var UniqueLogin = Util.Uniquify("NonUniqueLoginShouldFail"); - //CREATE FIRST USER - dynamic d = new JObject(); - d.name = Util.Uniquify("NonUniqueLoginShouldFail"); - d.notes = "notes"; - d.customFields = Util.UserRequiredCustomFieldsJsonString(); - d.active = false; - d.login = UniqueLogin; - d.password = Util.Uniquify("PASSWORD"); - d.roles = 0;//norole - d.userType = 3;//non scheduleable - - ApiResponse a = await Util.PostAsync("User", await Util.GetTokenAsync("superuser", "l3tm3in"), d.ToString()); - Util.ValidateDataReturnResponseOk(a); - - - - //Attempt create second with same login - d = new JObject(); - d.name = Util.Uniquify("2NonUniqueLoginShouldFail"); - d.notes = "notes"; - d.customFields = Util.UserRequiredCustomFieldsJsonString(); - d.active = false; - d.login = UniqueLogin; - d.password = Util.Uniquify("PASSWORD"); - d.roles = 0;//norole - d.userType = 3;//non scheduleable - - a = await Util.PostAsync("User", await Util.GetTokenAsync("superuser", "l3tm3in"), d.ToString()); - - Util.ValidateErrorCodeResponse(a, 2200, 400); - Util.ShouldContainValidationError(a, "Login", "2206"); - /* - "{\"error\":{\"code\":\"2200\",\"details\":[{\"target\":\"Login\",\"error\":\"2206\"}],\"message\":\"Object did not pass validation\"}}" - */ - - } - - - - //================================================== - - }//eoc -}//eons +using System; +using Xunit; +using Newtonsoft.Json.Linq; +using FluentAssertions; + +namespace raven_integration +{ + + public class UserCrud + { + + /// + /// Test all CRUD routes for a User + /// + [Fact] + public async Task CRUD() + { + + //CREATE + dynamic D1 = new JObject(); + D1.name = Util.Uniquify("First Test User"); + + D1.active = true; + D1.login = Util.Uniquify("LOGIN"); + D1.password = Util.Uniquify("PASSWORD"); + D1.roles = 0;//norole + + D1.userType = 3;//non scheduleable + + //Required by form custom rules + D1.notes = "notes"; + D1.customFields = Util.UserRequiredCustomFieldsJsonString(); + + ApiResponse R1 = await Util.PostAsync("User", await Util.GetTokenAsync("superuser", "l3tm3in"), D1.ToString()); + Util.ValidateDataReturnResponseOk(R1); + long d1Id = R1.ObjectResponse["data"]["id"].Value(); + + + dynamic D2 = new JObject(); + D2.name = Util.Uniquify("Second Test User"); + //Required by form custom rules + D2.notes = "notes"; + D2.customFields = Util.UserRequiredCustomFieldsJsonString(); + D2.active = true; + D2.login = Util.Uniquify("LOGIN"); + D2.password = Util.Uniquify("PASSWORD"); + D2.roles = 0;//norole + + D2.userType = 3;//non scheduleable + + ApiResponse R2 = await Util.PostAsync("User", await Util.GetTokenAsync("superuser", "l3tm3in"), D2.ToString()); + Util.ValidateDataReturnResponseOk(R2); + long d2Id = R2.ObjectResponse["data"]["id"].Value(); + + + //RETRIEVE + + //Get one + ApiResponse R3 = await Util.GetAsync("User/" + d2Id.ToString(), await Util.GetTokenAsync("superuser", "l3tm3in")); + Util.ValidateDataReturnResponseOk(R3); + R3.ObjectResponse["data"]["name"].Value().Should().Be(D2.name.ToString()); + + + + //UPDATE + //PUT + + //update w2id + D2.name = Util.Uniquify("UPDATED VIA PUT SECOND TEST User"); + D2.concurrency = R2.ObjectResponse["data"]["concurrency"].Value(); + D2.id=d2Id; + ApiResponse PUTTestResponse = await Util.PutAsync("User" , await Util.GetTokenAsync("superuser", "l3tm3in"), D2.ToString()); + Util.ValidateHTTPStatusCode(PUTTestResponse, 200); + + //check PUT worked + ApiResponse checkPUTWorked = await Util.GetAsync("User/" + d2Id.ToString(), await Util.GetTokenAsync("superuser", "l3tm3in")); + Util.ValidateNoErrorInResponse(checkPUTWorked); + checkPUTWorked.ObjectResponse["data"]["name"].Value().Should().Be(D2.name.ToString()); + uint concurrency = PUTTestResponse.ObjectResponse["data"]["concurrency"].Value(); + + //DELETE + ApiResponse DELETETestResponse = await Util.DeleteAsync("User/" + d2Id.ToString(), await Util.GetTokenAsync("superuser", "l3tm3in")); + Util.ValidateHTTPStatusCode(DELETETestResponse, 204); + } + + + /// + /// + /// + [Fact] + public async Task UserWithActivityShouldNotBeDeleteable() + { + ApiResponse a = await Util.DeleteAsync("User/1", await Util.GetTokenAsync("superuser", "l3tm3in")); + Util.ValidateErrorCodeResponse(a, 2200, 400); + a.ObjectResponse["error"]["details"][0]["message"].Value().Should().Contain("LT:ErrorDBForeignKeyViolation"); + } + + + /// + /// Test not found + /// + [Fact] + public async Task GetNonExistentItemShouldError() + { + //Get non existant + //Should return status code 404, api error code 2010 + ApiResponse R = await Util.GetAsync("User/999999", await Util.GetTokenAsync("superuser", "l3tm3in")); + Util.ValidateResponseNotFound(R); + } + + /// + /// Test bad modelstate + /// + [Fact] + public async Task GetBadModelStateShouldError() + { + //Get non existant + //Should return status code 400, api error code 2200 and a first target in details of "id" + ApiResponse R = await Util.GetAsync("User/2q2", await Util.GetTokenAsync("superuser", "l3tm3in")); + Util.ValidateBadModelStateResponse(R, "id"); + } + + + /// + /// + /// + [Fact] + public async Task PutConcurrencyViolationShouldFail() + { + //CREATE + dynamic D = new JObject(); + D.name = Util.Uniquify("PutConcurrencyViolationShouldFail"); + D.notes = "notes"; + D.customFields = Util.UserRequiredCustomFieldsJsonString(); + D.active = true; + D.login = Util.Uniquify("LOGIN"); + D.password = Util.Uniquify("PASSWORD"); + D.roles = 0;//norole + + D.userType = 3;//non scheduleable + + ApiResponse R = await Util.PostAsync("User", await Util.GetTokenAsync("superuser", "l3tm3in"), D.ToString()); + Util.ValidateDataReturnResponseOk(R); + long D1Id = R.ObjectResponse["data"]["id"].Value(); + uint OriginalConcurrencyToken = R.ObjectResponse["data"]["concurrency"].Value(); + + + //UPDATE + //PUT + + D.name = Util.Uniquify("PutConcurrencyViolationShouldFail UPDATE VIA PUT "); + D.concurrency = OriginalConcurrencyToken - 1;//bad token + D.id=D1Id; + ApiResponse PUTTestResponse = await Util.PutAsync("User", await Util.GetTokenAsync("superuser", "l3tm3in"), D.ToString()); + Util.ValidateConcurrencyError(PUTTestResponse); + } + + + + /// + /// + /// + [Fact] + public async Task PutPasswordShouldWork() + { + //CREATE + dynamic d = new JObject(); + d.name = Util.Uniquify("PutPasswordShouldWork"); + + d.active = true; + d.login = Util.Uniquify("LOGIN"); + d.password = Util.Uniquify("PASSWORD"); + d.roles = 0;//norole + + d.userType = 3;//non scheduleable + //Required by form custom rules + d.notes = "notes"; + d.customFields = Util.UserRequiredCustomFieldsJsonString(); + + ApiResponse a = await Util.PostAsync("User", await Util.GetTokenAsync("superuser", "l3tm3in"), d.ToString()); + Util.ValidateDataReturnResponseOk(a); + long UserId = a.ObjectResponse["data"]["id"].Value(); + uint OriginalConcurrencyToken = a.ObjectResponse["data"]["concurrency"].Value(); + + //Test can login + dynamic DCreds = new JObject(); + DCreds.password = d.password; + DCreds.login = d.login; + a = await Util.PostAsync("auth", null, DCreds.ToString()); + Util.ValidateDataReturnResponseOk(a); + + //GET user (login changed concurrency token above) + a = await Util.GetAsync("User/" + UserId.ToString(), await Util.GetTokenAsync("superuser", "l3tm3in")); + Util.ValidateDataReturnResponseOk(a); + d = a.ObjectResponse["data"]; + + + //PUT + var NewPassword = "NEW_PASSWORD"; + d.password = NewPassword; + d.login=DCreds.login; + a = await Util.PutAsync("User", await Util.GetTokenAsync("superuser", "l3tm3in"), d.ToString()); + Util.ValidateDataReturnResponseOk(a); + + //Test can login with new creds + //dynamic DCreds = new JObject(); + DCreds.password = NewPassword; + // DCreds.login = d.login; + a = await Util.PostAsync("auth", null, DCreds.ToString()); + Util.ValidateDataReturnResponseOk(a); + } + + + /// + /// + /// + [Fact] + public async Task NonUniqueLoginShouldFail() + { + var UniqueLogin = Util.Uniquify("NonUniqueLoginShouldFail"); + //CREATE FIRST USER + dynamic d = new JObject(); + d.name = Util.Uniquify("NonUniqueLoginShouldFail"); + d.notes = "notes"; + d.customFields = Util.UserRequiredCustomFieldsJsonString(); + d.active = false; + d.login = UniqueLogin; + d.password = Util.Uniquify("PASSWORD"); + d.roles = 0;//norole + d.userType = 3;//non scheduleable + + ApiResponse a = await Util.PostAsync("User", await Util.GetTokenAsync("superuser", "l3tm3in"), d.ToString()); + Util.ValidateDataReturnResponseOk(a); + + + + //Attempt create second with same login + d = new JObject(); + d.name = Util.Uniquify("2NonUniqueLoginShouldFail"); + d.notes = "notes"; + d.customFields = Util.UserRequiredCustomFieldsJsonString(); + d.active = false; + d.login = UniqueLogin; + d.password = Util.Uniquify("PASSWORD"); + d.roles = 0;//norole + d.userType = 3;//non scheduleable + + a = await Util.PostAsync("User", await Util.GetTokenAsync("superuser", "l3tm3in"), d.ToString()); + + Util.ValidateErrorCodeResponse(a, 2200, 400); + Util.ShouldContainValidationError(a, "Login", "2206"); + /* + "{\"error\":{\"code\":\"2200\",\"details\":[{\"target\":\"Login\",\"error\":\"2206\"}],\"message\":\"Object did not pass validation\"}}" + */ + + } + + + + //================================================== + + }//eoc +}//eons diff --git a/User/UserInactive.cs b/User/UserInactive.cs index 7f41241..d75b56a 100644 --- a/User/UserInactive.cs +++ b/User/UserInactive.cs @@ -1,29 +1,29 @@ -using Xunit; -using Newtonsoft.Json.Linq; - -namespace raven_integration -{ - - public class UserInactive - { - - /// - /// Inactive user should not be able to login - /// - [Fact] - public async void InactiveUserCantLogin() - { - dynamic DCreds = new JObject(); - DCreds.password = DCreds.login = "TEST_INACTIVE"; - ApiResponse a = await Util.PostAsync("auth", null, DCreds.ToString()); - Util.ValidateErrorCodeResponse(a,2003, 401); - } - - - - - - //================================================== - - }//eoc -}//eons +using Xunit; +using Newtonsoft.Json.Linq; + +namespace raven_integration +{ + + public class UserInactive + { + + /// + /// Inactive user should not be able to login + /// + [Fact] + public async Task InactiveUserCantLogin() + { + dynamic DCreds = new JObject(); + DCreds.password = DCreds.login = "TEST_INACTIVE"; + ApiResponse a = await Util.PostAsync("auth", null, DCreds.ToString()); + Util.ValidateErrorCodeResponse(a,2003, 401); + } + + + + + + //================================================== + + }//eoc +}//eons diff --git a/User/UserOptions.cs b/User/UserOptions.cs index e105693..9cd1c3a 100644 --- a/User/UserOptions.cs +++ b/User/UserOptions.cs @@ -1,122 +1,122 @@ -using System; -using Xunit; -using Newtonsoft.Json.Linq; -using FluentAssertions; - -namespace raven_integration -{ - - public class UserOptions - { - - /// - /// Test all CRUD routes for a UserOptions object - /// - [Fact] - public async void CRUD() - { - - //CREATE a user - dynamic D1 = new JObject(); - D1.name = Util.Uniquify("Test UserOptions User"); - - D1.active = true; - D1.login = Util.Uniquify("LOGIN"); - D1.password = Util.Uniquify("PASSWORD"); - D1.roles = 0;//norole - D1.userType = 3;//non scheduleable - D1.notes = "notes"; - D1.customFields = Util.UserRequiredCustomFieldsJsonString(); - - ApiResponse R = await Util.PostAsync("User", await Util.GetTokenAsync("superuser", "l3tm3in"), D1.ToString()); - Util.ValidateDataReturnResponseOk(R); - long UserId = R.ObjectResponse["data"]["id"].Value(); - - //Now there should be a user options available for this user - - //RETRIEVE companion USEROPTIONS object - R = await Util.GetAsync("user-option/" + UserId.ToString(), await Util.GetTokenAsync("superuser", "l3tm3in")); - Util.ValidateDataReturnResponseOk(R); - //ensure the default value is set - R.ObjectResponse["data"]["uiColor"].Value().Should().Be("#000000"); - uint concurrency = R.ObjectResponse["data"]["concurrency"].Value(); - - //UPDATE - - //PUT - dynamic D2 = new JObject(); - D2.translationId = 1; - D2.emailAddress = "testuseroptions@helloayanova.com"; - D2.languageOverride = "de-DE"; - D2.timeZoneOverride = "Europe/Berlin"; - D2.currencyName = "EUR"; - D2.hour12 = false; - D2.uiColor = "#ffaaff"; - D2.concurrency = concurrency; - ApiResponse PUTTestResponse = await Util.PutAsync("user-option/" + UserId.ToString(), await Util.GetTokenAsync("superuser", "l3tm3in"), D2.ToString()); - Util.ValidateHTTPStatusCode(PUTTestResponse, 200); - - //VALIDATE - R = await Util.GetAsync("user-option/" + UserId.ToString(), await Util.GetTokenAsync("superuser", "l3tm3in")); - Util.ValidateDataReturnResponseOk(R); - //ensure the default value is set - /* - "{\"data\":{\"id\":44,\"concurrency\":7144348,\"emailAddress\":null,\"uiColor\":0,\"languageOverride\":null,\"timeZoneOverride\":null,\"currencyName\":\"USD\",\"hour12\":true,\"userId\":44}}" - */ - R.ObjectResponse["data"]["emailAddress"].Value().Should().Be(D2.emailAddress.ToString()); - R.ObjectResponse["data"]["languageOverride"].Value().Should().Be(D2.languageOverride.ToString()); - R.ObjectResponse["data"]["timeZoneOverride"].Value().Should().Be(D2.timeZoneOverride.ToString()); - R.ObjectResponse["data"]["currencyName"].Value().Should().Be(D2.currencyName.ToString()); - R.ObjectResponse["data"]["hour12"].Value().Should().Be((bool)D2.hour12); - R.ObjectResponse["data"]["uiColor"].Value().Should().Be(D2.uiColor.ToString()); - R.ObjectResponse["data"]["translationId"].Value().Should().Be((long)D2.translationId); - concurrency = R.ObjectResponse["data"]["concurrency"].Value(); - - - //DELETE USER - ApiResponse DELETETestResponse = await Util.DeleteAsync("User/" + UserId.ToString(), await Util.GetTokenAsync("superuser", "l3tm3in")); - Util.ValidateHTTPStatusCode(DELETETestResponse, 204); - - //CHECK DELETE USER REMOVED USEROPTIONS - R = await Util.GetAsync("user-option/" + UserId.ToString(), await Util.GetTokenAsync("superuser", "l3tm3in")); - Util.ValidateResponseNotFound(R); - } - - - /// - /// Test not found - /// - [Fact] - public async void GetNonExistentItemShouldError() - { - //Get non existant - //Should return status code 404, api error code 2010 - ApiResponse R = await Util.GetAsync("user-option/999999", await Util.GetTokenAsync("superuser", "l3tm3in")); - Util.ValidateResponseNotFound(R); - } - - /// - /// Test bad modelstate - /// - [Fact] - public async void GetBadModelStateShouldError() - { - //Get non existant - //Should return status code 400, api error code 2200 and a first target in details of "id" - ApiResponse R = await Util.GetAsync("user-option/2q2", await Util.GetTokenAsync("superuser", "l3tm3in")); - Util.ValidateBadModelStateResponse(R, "id"); - } - - - - - - - - - - - //================================================== - - }//eoc -}//eons +using System; +using Xunit; +using Newtonsoft.Json.Linq; +using FluentAssertions; + +namespace raven_integration +{ + + public class UserOptions + { + + /// + /// Test all CRUD routes for a UserOptions object + /// + [Fact] + public async Task CRUD() + { + + //CREATE a user + dynamic D1 = new JObject(); + D1.name = Util.Uniquify("Test UserOptions User"); + + D1.active = true; + D1.login = Util.Uniquify("LOGIN"); + D1.password = Util.Uniquify("PASSWORD"); + D1.roles = 0;//norole + D1.userType = 3;//non scheduleable + D1.notes = "notes"; + D1.customFields = Util.UserRequiredCustomFieldsJsonString(); + + ApiResponse R = await Util.PostAsync("User", await Util.GetTokenAsync("superuser", "l3tm3in"), D1.ToString()); + Util.ValidateDataReturnResponseOk(R); + long UserId = R.ObjectResponse["data"]["id"].Value(); + + //Now there should be a user options available for this user + + //RETRIEVE companion USEROPTIONS object + R = await Util.GetAsync("user-option/" + UserId.ToString(), await Util.GetTokenAsync("superuser", "l3tm3in")); + Util.ValidateDataReturnResponseOk(R); + //ensure the default value is set + R.ObjectResponse["data"]["uiColor"].Value().Should().Be("#000000"); + uint concurrency = R.ObjectResponse["data"]["concurrency"].Value(); + + //UPDATE + + //PUT + dynamic D2 = new JObject(); + D2.translationId = 1; + D2.emailAddress = "testuseroptions@helloayanova.com"; + D2.languageOverride = "de-DE"; + D2.timeZoneOverride = "Europe/Berlin"; + D2.currencyName = "EUR"; + D2.hour12 = false; + D2.uiColor = "#ffaaff"; + D2.concurrency = concurrency; + ApiResponse PUTTestResponse = await Util.PutAsync("user-option/" + UserId.ToString(), await Util.GetTokenAsync("superuser", "l3tm3in"), D2.ToString()); + Util.ValidateHTTPStatusCode(PUTTestResponse, 200); + + //VALIDATE + R = await Util.GetAsync("user-option/" + UserId.ToString(), await Util.GetTokenAsync("superuser", "l3tm3in")); + Util.ValidateDataReturnResponseOk(R); + //ensure the default value is set + /* + "{\"data\":{\"id\":44,\"concurrency\":7144348,\"emailAddress\":null,\"uiColor\":0,\"languageOverride\":null,\"timeZoneOverride\":null,\"currencyName\":\"USD\",\"hour12\":true,\"userId\":44}}" + */ + R.ObjectResponse["data"]["emailAddress"].Value().Should().Be(D2.emailAddress.ToString()); + R.ObjectResponse["data"]["languageOverride"].Value().Should().Be(D2.languageOverride.ToString()); + R.ObjectResponse["data"]["timeZoneOverride"].Value().Should().Be(D2.timeZoneOverride.ToString()); + R.ObjectResponse["data"]["currencyName"].Value().Should().Be(D2.currencyName.ToString()); + R.ObjectResponse["data"]["hour12"].Value().Should().Be((bool)D2.hour12); + R.ObjectResponse["data"]["uiColor"].Value().Should().Be(D2.uiColor.ToString()); + R.ObjectResponse["data"]["translationId"].Value().Should().Be((long)D2.translationId); + concurrency = R.ObjectResponse["data"]["concurrency"].Value(); + + + //DELETE USER + ApiResponse DELETETestResponse = await Util.DeleteAsync("User/" + UserId.ToString(), await Util.GetTokenAsync("superuser", "l3tm3in")); + Util.ValidateHTTPStatusCode(DELETETestResponse, 204); + + //CHECK DELETE USER REMOVED USEROPTIONS + R = await Util.GetAsync("user-option/" + UserId.ToString(), await Util.GetTokenAsync("superuser", "l3tm3in")); + Util.ValidateResponseNotFound(R); + } + + + /// + /// Test not found + /// + [Fact] + public async Task GetNonExistentItemShouldError() + { + //Get non existant + //Should return status code 404, api error code 2010 + ApiResponse R = await Util.GetAsync("user-option/999999", await Util.GetTokenAsync("superuser", "l3tm3in")); + Util.ValidateResponseNotFound(R); + } + + /// + /// Test bad modelstate + /// + [Fact] + public async Task GetBadModelStateShouldError() + { + //Get non existant + //Should return status code 400, api error code 2200 and a first target in details of "id" + ApiResponse R = await Util.GetAsync("user-option/2q2", await Util.GetTokenAsync("superuser", "l3tm3in")); + Util.ValidateBadModelStateResponse(R, "id"); + } + + + + + + + + + + + //================================================== + + }//eoc +}//eons diff --git a/Widget/WidgetCrud.cs b/Widget/WidgetCrud.cs index fe10f21..ef5d111 100644 --- a/Widget/WidgetCrud.cs +++ b/Widget/WidgetCrud.cs @@ -1,199 +1,199 @@ -using System; -using Xunit; -using Newtonsoft.Json.Linq; -using FluentAssertions; - -namespace raven_integration -{ - - public class WidgetCrud - { - - /// - /// Test all CRUD routes for a widget - /// - [Fact] - public async void CRUD() - { - /* - { - "id": 0, - "name": "string", - "dollarAmount": 0, - "active": true, - "roles": 0 - } - */ - //CREATE - dynamic w1 = new JObject(); - w1.name = Util.Uniquify("First Test WIDGET"); - w1.dollarAmount = 1.11m; - w1.active = true; - w1.usertype = 1; - w1.notes = "The quick brown fox jumped over the six lazy dogs!"; - w1.customFields = Util.WidgetRequiredCustomFieldsJsonString(); - - //Tags - dynamic dTagsArray = new JArray(); - dTagsArray.Add("Red Tag"); - dTagsArray.Add("ORANGE IS THE NEW BLACK"); - dTagsArray.Add("yellow"); - dTagsArray.Add("green"); - dTagsArray.Add("blue"); - dTagsArray.Add("indigo"); - dTagsArray.Add("VIOLET Tag"); - w1.tags = dTagsArray; - - ApiResponse r1 = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w1.ToString()); - Util.ValidateDataReturnResponseOk(r1); - long w1Id = r1.ObjectResponse["data"]["id"].Value(); - ((long)r1.ObjectResponse["data"]["serial"]).Should().NotBe(0); - - dynamic w2 = new JObject(); - w2.name = Util.Uniquify("Second Test WIDGET"); - w2.dollarAmount = 2.22m; - w2.active = true; - w2.usertype = 1; - w2.notes = "What is the frequency Kenneth?"; - w2.tags = dTagsArray; - w2.customFields = Util.WidgetRequiredCustomFieldsJsonString(); - - ApiResponse r2 = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w2.ToString()); - Util.ValidateDataReturnResponseOk(r2); - long w2Id = r2.ObjectResponse["data"]["id"].Value(); - - //RETRIEVE - - //Get one - ApiResponse r3 = await Util.GetAsync("widget/" + w2Id.ToString(), await Util.GetTokenAsync("superuser", "l3tm3in")); - Util.ValidateDataReturnResponseOk(r3); - r3.ObjectResponse["data"]["name"].Value().Should().Be(w2.name.ToString()); - r3.ObjectResponse["data"]["notes"].Value().Should().Be(w2.notes.ToString()); - var returnedTags = ((JArray)r3.ObjectResponse["data"]["tags"]); - returnedTags.Count.Should().Be(7); - - - - - //UPDATE - //PUT - - //update w2id - w2.name = Util.Uniquify("UPDATED VIA PUT SECOND TEST WIDGET"); - w2.id = w2Id; - w2.serial = 123456L; - w2.concurrency = r2.ObjectResponse["data"]["concurrency"].Value(); - ApiResponse PUTTestResponse = await Util.PutAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w2.ToString()); - Util.ValidateHTTPStatusCode(PUTTestResponse, 200); - - //check PUT worked - ApiResponse checkPUTWorked = await Util.GetAsync("widget/" + w2Id.ToString(), await Util.GetTokenAsync("superuser", "l3tm3in")); - Util.ValidateNoErrorInResponse(checkPUTWorked); - checkPUTWorked.ObjectResponse["data"]["name"].Value().Should().Be(w2.name.ToString()); - checkPUTWorked.ObjectResponse["data"]["serial"].Value().Should().Be(123456L); - uint concurrency = PUTTestResponse.ObjectResponse["data"]["concurrency"].Value(); - - //DELETE - ApiResponse DELETETestResponse = await Util.DeleteAsync("widget/" + w2Id.ToString(), await Util.GetTokenAsync("superuser", "l3tm3in")); - Util.ValidateHTTPStatusCode(DELETETestResponse, 204); - } - - - - - - - /// - /// Test not found - /// - [Fact] - public async void GetNonExistentItemShouldError() - { - //Get non existant - //Should return status code 404, api error code 2010 - ApiResponse a = await Util.GetAsync("widget/999999", await Util.GetTokenAsync("superuser", "l3tm3in")); - Util.ValidateResponseNotFound(a); - } - - /// - /// Test bad modelstate - /// - [Fact] - public async void GetBadModelStateShouldError() - { - //Get non existant - //Should return status code 400, api error code 2200 and a first target in details of "id" - ApiResponse a = await Util.GetAsync("widget/2q2", await Util.GetTokenAsync("superuser", "l3tm3in")); - Util.ValidateBadModelStateResponse(a, "id"); - } - - - /// - /// Test server exception - /// - [Fact] - public async void ServerExceptionShouldErrorPropertly() - { - //Get non existant - //Should return status code 400, api error code 2200 and a first target in details of "id" - ApiResponse a = await Util.GetAsync("widget/exception", await Util.GetTokenAsync("superuser", "l3tm3in")); - Util.ValidateServerExceptionResponse(a); - } - - - - /// - /// Test server alt exception - /// - [Fact] - public async void ServerAltExceptionShouldErrorPropertly() - { - //Get non existant - //Should return status code 400, api error code 2200 and a first target in details of "id" - ApiResponse a = await Util.GetAsync("widget/altexception", await Util.GetTokenAsync("superuser", "l3tm3in")); - Util.ValidateServerExceptionResponse(a); - } - - - - - /// - /// - /// - [Fact] - public async void PutConcurrencyViolationShouldFail() - { - - //CREATE - dynamic w2 = new JObject(); - w2.name = Util.Uniquify("PutConcurrencyViolationShouldFail"); - w2.dollarAmount = 2.22m; - w2.active = true; - w2.usertype = 1; - w2.notes = "blah"; - w2.customFields = Util.WidgetRequiredCustomFieldsJsonString(); - - - ApiResponse r2 = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w2.ToString()); - Util.ValidateDataReturnResponseOk(r2); - uint OriginalConcurrencyToken = r2.ObjectResponse["data"]["concurrency"].Value(); - w2 = r2.ObjectResponse["data"]; - - - //UPDATE - //PUT - - w2.name = Util.Uniquify("PutConcurrencyViolationShouldFail UPDATE VIA PUT "); - w2.concurrency = OriginalConcurrencyToken - 1;//bad token - ApiResponse PUTTestResponse = await Util.PutAsync("widget/", await Util.GetTokenAsync("superuser", "l3tm3in"), w2.ToString()); - Util.ValidateConcurrencyError(PUTTestResponse); - - } - - - - - //================================================== - - }//eoc -}//eons +using System; +using Xunit; +using Newtonsoft.Json.Linq; +using FluentAssertions; + +namespace raven_integration +{ + + public class WidgetCrud + { + + /// + /// Test all CRUD routes for a widget + /// + [Fact] + public async Task CRUD() + { + /* + { + "id": 0, + "name": "string", + "dollarAmount": 0, + "active": true, + "roles": 0 + } + */ + //CREATE + dynamic w1 = new JObject(); + w1.name = Util.Uniquify("First Test WIDGET"); + w1.dollarAmount = 1.11m; + w1.active = true; + w1.usertype = 1; + w1.notes = "The quick brown fox jumped over the six lazy dogs!"; + w1.customFields = Util.WidgetRequiredCustomFieldsJsonString(); + + //Tags + dynamic dTagsArray = new JArray(); + dTagsArray.Add("Red Tag"); + dTagsArray.Add("ORANGE IS THE NEW BLACK"); + dTagsArray.Add("yellow"); + dTagsArray.Add("green"); + dTagsArray.Add("blue"); + dTagsArray.Add("indigo"); + dTagsArray.Add("VIOLET Tag"); + w1.tags = dTagsArray; + + ApiResponse r1 = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w1.ToString()); + Util.ValidateDataReturnResponseOk(r1); + long w1Id = r1.ObjectResponse["data"]["id"].Value(); + ((long)r1.ObjectResponse["data"]["serial"]).Should().NotBe(0); + + dynamic w2 = new JObject(); + w2.name = Util.Uniquify("Second Test WIDGET"); + w2.dollarAmount = 2.22m; + w2.active = true; + w2.usertype = 1; + w2.notes = "What is the frequency Kenneth?"; + w2.tags = dTagsArray; + w2.customFields = Util.WidgetRequiredCustomFieldsJsonString(); + + ApiResponse r2 = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w2.ToString()); + Util.ValidateDataReturnResponseOk(r2); + long w2Id = r2.ObjectResponse["data"]["id"].Value(); + + //RETRIEVE + + //Get one + ApiResponse r3 = await Util.GetAsync("widget/" + w2Id.ToString(), await Util.GetTokenAsync("superuser", "l3tm3in")); + Util.ValidateDataReturnResponseOk(r3); + r3.ObjectResponse["data"]["name"].Value().Should().Be(w2.name.ToString()); + r3.ObjectResponse["data"]["notes"].Value().Should().Be(w2.notes.ToString()); + var returnedTags = ((JArray)r3.ObjectResponse["data"]["tags"]); + returnedTags.Count.Should().Be(7); + + + + + //UPDATE + //PUT + + //update w2id + w2.name = Util.Uniquify("UPDATED VIA PUT SECOND TEST WIDGET"); + w2.id = w2Id; + w2.serial = 123456L; + w2.concurrency = r2.ObjectResponse["data"]["concurrency"].Value(); + ApiResponse PUTTestResponse = await Util.PutAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w2.ToString()); + Util.ValidateHTTPStatusCode(PUTTestResponse, 200); + + //check PUT worked + ApiResponse checkPUTWorked = await Util.GetAsync("widget/" + w2Id.ToString(), await Util.GetTokenAsync("superuser", "l3tm3in")); + Util.ValidateNoErrorInResponse(checkPUTWorked); + checkPUTWorked.ObjectResponse["data"]["name"].Value().Should().Be(w2.name.ToString()); + checkPUTWorked.ObjectResponse["data"]["serial"].Value().Should().Be(123456L); + uint concurrency = PUTTestResponse.ObjectResponse["data"]["concurrency"].Value(); + + //DELETE + ApiResponse DELETETestResponse = await Util.DeleteAsync("widget/" + w2Id.ToString(), await Util.GetTokenAsync("superuser", "l3tm3in")); + Util.ValidateHTTPStatusCode(DELETETestResponse, 204); + } + + + + + + + /// + /// Test not found + /// + [Fact] + public async Task GetNonExistentItemShouldError() + { + //Get non existant + //Should return status code 404, api error code 2010 + ApiResponse a = await Util.GetAsync("widget/999999", await Util.GetTokenAsync("superuser", "l3tm3in")); + Util.ValidateResponseNotFound(a); + } + + /// + /// Test bad modelstate + /// + [Fact] + public async Task GetBadModelStateShouldError() + { + //Get non existant + //Should return status code 400, api error code 2200 and a first target in details of "id" + ApiResponse a = await Util.GetAsync("widget/2q2", await Util.GetTokenAsync("superuser", "l3tm3in")); + Util.ValidateBadModelStateResponse(a, "id"); + } + + + /// + /// Test server exception + /// + [Fact] + public async Task ServerExceptionShouldErrorPropertly() + { + //Get non existant + //Should return status code 400, api error code 2200 and a first target in details of "id" + ApiResponse a = await Util.GetAsync("widget/exception", await Util.GetTokenAsync("superuser", "l3tm3in")); + Util.ValidateServerExceptionResponse(a); + } + + + + /// + /// Test server alt exception + /// + [Fact] + public async Task ServerAltExceptionShouldErrorPropertly() + { + //Get non existant + //Should return status code 400, api error code 2200 and a first target in details of "id" + ApiResponse a = await Util.GetAsync("widget/altexception", await Util.GetTokenAsync("superuser", "l3tm3in")); + Util.ValidateServerExceptionResponse(a); + } + + + + + /// + /// + /// + [Fact] + public async Task PutConcurrencyViolationShouldFail() + { + + //CREATE + dynamic w2 = new JObject(); + w2.name = Util.Uniquify("PutConcurrencyViolationShouldFail"); + w2.dollarAmount = 2.22m; + w2.active = true; + w2.usertype = 1; + w2.notes = "blah"; + w2.customFields = Util.WidgetRequiredCustomFieldsJsonString(); + + + ApiResponse r2 = await Util.PostAsync("widget", await Util.GetTokenAsync("superuser", "l3tm3in"), w2.ToString()); + Util.ValidateDataReturnResponseOk(r2); + uint OriginalConcurrencyToken = r2.ObjectResponse["data"]["concurrency"].Value(); + w2 = r2.ObjectResponse["data"]; + + + //UPDATE + //PUT + + w2.name = Util.Uniquify("PutConcurrencyViolationShouldFail UPDATE VIA PUT "); + w2.concurrency = OriginalConcurrencyToken - 1;//bad token + ApiResponse PUTTestResponse = await Util.PutAsync("widget/", await Util.GetTokenAsync("superuser", "l3tm3in"), w2.ToString()); + Util.ValidateConcurrencyError(PUTTestResponse); + + } + + + + + //================================================== + + }//eoc +}//eons diff --git a/Widget/WidgetRights.cs b/Widget/WidgetRights.cs index af4d1a8..240eaf6 100644 --- a/Widget/WidgetRights.cs +++ b/Widget/WidgetRights.cs @@ -1,81 +1,81 @@ -using System; -using Xunit; -using Newtonsoft.Json.Linq; -using FluentAssertions; -using System.Collections.Generic; -using System.Collections.Concurrent; - -namespace raven_integration -{ - // [Collection("APICOLLECTION")] - public class WidgetRights - { - - - /// - /// Test not authorized error return - /// - [Fact] - public async void ServerShouldNotAllowUnauthenticatedAccess() - { - ApiResponse a = await Util.GetAsync("widget/list"); - Util.ValidateHTTPStatusCode(a, 401); - } - - /// - /// Test insufficient read rights error return - /// - [Fact] - public async void ServerShouldNotAllowReadUnauthorizedAccess() - { - ApiResponse a = await Util.GetAsync("widget/listwidgets", await Util.GetTokenAsync( "OpsAdminFull")); - //2004 unauthorized - Util.ValidateErrorCodeResponse(a, 2004, 403); - } - - - - /// - /// Test insufficient create rights error return - /// - [Fact] - public async void ServerShouldNotAllowCreateUnauthorizedAccess() - { - //CREATE - dynamic d = new JObject(); - d.name = Util.Uniquify("ServerShouldNotAllowCreateUnauthorizedAccess TEST WIDGET"); - d.created = DateTime.Now.ToString(); - d.dollarAmount = 1.11m; - d.active = true; - d.usertype = 1; - - //BizAdminLimited user should not be able to create a widget, only read them - ApiResponse a = await Util.PostAsync("widget", await Util.GetTokenAsync( "BizAdminLimited"), d.ToString()); - - //2004 unauthorized - Util.ValidateErrorCodeResponse(a, 2004, 403); - } - - - - - - - - - - - - - - - - - - - - - //================================================== - - }//eoc -}//eons +using System; +using Xunit; +using Newtonsoft.Json.Linq; +using FluentAssertions; +using System.Collections.Generic; +using System.Collections.Concurrent; + +namespace raven_integration +{ + // [Collection("APICOLLECTION")] + public class WidgetRights + { + + + /// + /// Test not authorized error return + /// + [Fact] + public async Task ServerShouldNotAllowUnauthenticatedAccess() + { + ApiResponse a = await Util.GetAsync("widget/list"); + Util.ValidateHTTPStatusCode(a, 401); + } + + /// + /// Test insufficient read rights error return + /// + [Fact] + public async Task ServerShouldNotAllowReadUnauthorizedAccess() + { + ApiResponse a = await Util.GetAsync("widget/listwidgets", await Util.GetTokenAsync( "OpsAdminFull")); + //2004 unauthorized + Util.ValidateErrorCodeResponse(a, 2004, 403); + } + + + + /// + /// Test insufficient create rights error return + /// + [Fact] + public async Task ServerShouldNotAllowCreateUnauthorizedAccess() + { + //CREATE + dynamic d = new JObject(); + d.name = Util.Uniquify("ServerShouldNotAllowCreateUnauthorizedAccess TEST WIDGET"); + d.created = DateTime.Now.ToString(); + d.dollarAmount = 1.11m; + d.active = true; + d.usertype = 1; + + //BizAdminLimited user should not be able to create a widget, only read them + ApiResponse a = await Util.PostAsync("widget", await Util.GetTokenAsync( "BizAdminLimited"), d.ToString()); + + //2004 unauthorized + Util.ValidateErrorCodeResponse(a, 2004, 403); + } + + + + + + + + + + + + + + + + + + + + + //================================================== + + }//eoc +}//eons diff --git a/Widget/WidgetValidationTests.cs b/Widget/WidgetValidationTests.cs index e1dfa31..a64f070 100644 --- a/Widget/WidgetValidationTests.cs +++ b/Widget/WidgetValidationTests.cs @@ -1,239 +1,239 @@ -using System; -using Xunit; -using Newtonsoft.Json.Linq; -using FluentAssertions; -using System.Collections.Generic; -using System.Collections.Concurrent; - -namespace raven_integration -{ - public class WidgetValidationTest - { - - - // /// - // /// Test business rule should be active on new - // /// - // [Fact] - // public async void BusinessRuleNewShouldBeActiveShouldWork() - // { - // //CREATE attempt with broken rules - // dynamic d = new JObject(); - // d.name = Util.Uniquify("ServerShouldDisAllowOwnerOnlyRightsUserToDeleteNonOwned TEST WIDGET"); - // d.created = DateTime.Now.ToString(); - // d.dollarAmount = 1.11m; - // d.active = false;//<--- BROKEN RULE new widget must be active = true!! - // d.usertype = 1; - - // //create via inventory full test user - // ApiResponse a = await Util.PostAsync("widget", await Util.GetTokenAsync("InventoryFull"), d.ToString()); - - // Util.ValidateErrorCodeResponse(a, 2200, 400); - // Util.ShouldContainValidationError(a, "Active", "2203"); - - // } - - - - - /// - /// Test business rule name should be unique - /// - [Fact] - public async void BusinessRuleNameMustBeUnique() - { - //CREATE attempt with broken rules - dynamic d = new JObject(); - d.name = Util.Uniquify("BusinessRuleNameMustBeUnique TEST WIDGET"); - d.notes = "blah"; - d.customFields = Util.WidgetRequiredCustomFieldsJsonString(); - d.created = DateTime.Now.ToString(); - d.dollarAmount = 1.11m; - d.active = true; - d.usertype = 1; - - //create via inventory full test user - ApiResponse a = await Util.PostAsync("widget", await Util.GetTokenAsync("InventoryFull"), d.ToString()); - Util.ValidateDataReturnResponseOk(a); - - //Now try to create again with same name - a = await Util.PostAsync("widget", await Util.GetTokenAsync("InventoryFull"), d.ToString()); - - //2002 in-valid expected - Util.ValidateErrorCodeResponse(a, 2200, 400); - Util.ShouldContainValidationError(a, "Name", "2206"); - - } - - - - /// - /// - /// - [Fact] - public async void BusinessRuleNameRequired() - { - - dynamic d = new JObject(); - d.name = ""; - d.created = DateTime.Now.ToString(); - d.dollarAmount = 1.11m; - d.active = true; - d.usertype = 1; - - //create via inventory full test user - ApiResponse a = await Util.PostAsync("widget", await Util.GetTokenAsync("InventoryFull"), d.ToString()); - - - //2002 in-valid expected - Util.ValidateErrorCodeResponse(a, 2200, 400); - //This is a modelstate error so even though it would be a 2201 in other circumstances here it's a 2203 - //Maybe a todo is to refine this a bit - Util.ShouldContainValidationError(a, "Name", "2203"); - - } - - /// - /// - /// - [Fact] - public async void BusinessRuleNameLengthExceeded() - { - - dynamic d = new JObject(); - d.name = new string('A', 256); ; - d.created = DateTime.Now.ToString(); - d.dollarAmount = 1.11m; - d.active = true; - d.usertype = 1; - - //create via inventory full test user - ApiResponse a = await Util.PostAsync("widget", await Util.GetTokenAsync("InventoryFull"), d.ToString()); - - - //2002 in-valid expected - Util.ValidateErrorCodeResponse(a, 2200, 400); - Util.ShouldContainValidationError(a, "Name", "2202", "255 max"); - - } - - - - - /// - /// - /// - [Fact] - public async void BusinessRuleStartDateWithoutEndDateShouldError() - { - - dynamic d = new JObject(); - d.name = Util.Uniquify("BusinessRuleStartDateWithoutEndDateShouldError TEST"); - d.created = DateTime.Now.ToString(); - d.startDate = d.created; - //NO END DATE ERRROR - d.dollarAmount = 1.11m; - d.active = true; - d.usertype = 1; - - //create via inventory full test user - ApiResponse a = await Util.PostAsync("widget", await Util.GetTokenAsync("InventoryFull"), d.ToString()); - - - //2002 in-valid expected - Util.ValidateErrorCodeResponse(a, 2200, 400); - Util.ShouldContainValidationError(a, "EndDate", "2201"); - - } - - - - /// - /// - /// - [Fact] - public async void BusinessRuleEndDateWithoutStartDateShouldError() - { - - dynamic d = new JObject(); - d.name = Util.Uniquify("BusinessRuleEndDateWithoutStartDateShouldError TEST"); - d.created = DateTime.Now.ToString(); - d.endDate = d.created; - //NO START DATE ERRROR - d.dollarAmount = 1.11m; - d.active = true; - d.usertype = 1; - - //create via inventory full test user - ApiResponse a = await Util.PostAsync("widget", await Util.GetTokenAsync("InventoryFull"), d.ToString()); - - - //2002 in-valid expected - Util.ValidateErrorCodeResponse(a, 2200, 400); - Util.ShouldContainValidationError(a, "StartDate", "2201"); - - } - - - /// - /// - /// - [Fact] - public async void BusinessRuleEndDateBeforeStartDateShouldError() - { - - dynamic d = new JObject(); - d.name = Util.Uniquify("BusinessRuleEndDateBeforeStartDateShouldError TEST"); - d.created = DateTime.Now.ToString(); - d.startDate = DateTime.Now.ToString(); - d.endDate = DateTime.Now.AddHours(-1).ToString(); - //NO START DATE ERRROR - d.dollarAmount = 1.11m; - d.active = true; - d.usertype = 1; - - //create via inventory full test user - ApiResponse a = await Util.PostAsync("widget", await Util.GetTokenAsync("InventoryFull"), d.ToString()); - - - //2002 in-valid expected - Util.ValidateErrorCodeResponse(a, 2200, 400); - Util.ShouldContainValidationError(a, "StartDate", "2207"); - - } - - - - /// - /// - /// - [Fact] - public async void BusinessRuleEnumInvalidShouldError() - { - - dynamic d = new JObject(); - d.name = Util.Uniquify("BusinessRuleEnumInvalidShouldError TEST"); - d.created = DateTime.Now.ToString(); - - //NO END DATE ERRROR - d.dollarAmount = 1.11m; - d.active = true; - d.usertype = -1;//<---BAD VALUE - d.Notes = "blah"; - d.customFields = Util.WidgetRequiredCustomFieldsJsonString(); - - - //create via inventory full test user - ApiResponse a = await Util.PostAsync("widget", await Util.GetTokenAsync("InventoryFull"), d.ToString()); - - - //2002 in-valid expected - Util.ValidateErrorCodeResponse(a, 2200, 400); - Util.ShouldContainValidationError(a, "UserType", "2203"); - - } - - //================================================== - - }//eoc -}//eons +using System; +using Xunit; +using Newtonsoft.Json.Linq; +using FluentAssertions; +using System.Collections.Generic; +using System.Collections.Concurrent; + +namespace raven_integration +{ + public class WidgetValidationTest + { + + + // /// + // /// Test business rule should be active on new + // /// + // [Fact] + // public async Task BusinessRuleNewShouldBeActiveShouldWork() + // { + // //CREATE attempt with broken rules + // dynamic d = new JObject(); + // d.name = Util.Uniquify("ServerShouldDisAllowOwnerOnlyRightsUserToDeleteNonOwned TEST WIDGET"); + // d.created = DateTime.Now.ToString(); + // d.dollarAmount = 1.11m; + // d.active = false;//<--- BROKEN RULE new widget must be active = true!! + // d.usertype = 1; + + // //create via inventory full test user + // ApiResponse a = await Util.PostAsync("widget", await Util.GetTokenAsync("InventoryFull"), d.ToString()); + + // Util.ValidateErrorCodeResponse(a, 2200, 400); + // Util.ShouldContainValidationError(a, "Active", "2203"); + + // } + + + + + /// + /// Test business rule name should be unique + /// + [Fact] + public async Task BusinessRuleNameMustBeUnique() + { + //CREATE attempt with broken rules + dynamic d = new JObject(); + d.name = Util.Uniquify("BusinessRuleNameMustBeUnique TEST WIDGET"); + d.notes = "blah"; + d.customFields = Util.WidgetRequiredCustomFieldsJsonString(); + d.created = DateTime.Now.ToString(); + d.dollarAmount = 1.11m; + d.active = true; + d.usertype = 1; + + //create via inventory full test user + ApiResponse a = await Util.PostAsync("widget", await Util.GetTokenAsync("InventoryFull"), d.ToString()); + Util.ValidateDataReturnResponseOk(a); + + //Now try to create again with same name + a = await Util.PostAsync("widget", await Util.GetTokenAsync("InventoryFull"), d.ToString()); + + //2002 in-valid expected + Util.ValidateErrorCodeResponse(a, 2200, 400); + Util.ShouldContainValidationError(a, "Name", "2206"); + + } + + + + /// + /// + /// + [Fact] + public async Task BusinessRuleNameRequired() + { + + dynamic d = new JObject(); + d.name = ""; + d.created = DateTime.Now.ToString(); + d.dollarAmount = 1.11m; + d.active = true; + d.usertype = 1; + + //create via inventory full test user + ApiResponse a = await Util.PostAsync("widget", await Util.GetTokenAsync("InventoryFull"), d.ToString()); + + + //2002 in-valid expected + Util.ValidateErrorCodeResponse(a, 2200, 400); + //This is a modelstate error so even though it would be a 2201 in other circumstances here it's a 2203 + //Maybe a todo is to refine this a bit + Util.ShouldContainValidationError(a, "Name", "2203"); + + } + + /// + /// + /// + [Fact] + public async Task BusinessRuleNameLengthExceeded() + { + + dynamic d = new JObject(); + d.name = new string('A', 256); ; + d.created = DateTime.Now.ToString(); + d.dollarAmount = 1.11m; + d.active = true; + d.usertype = 1; + + //create via inventory full test user + ApiResponse a = await Util.PostAsync("widget", await Util.GetTokenAsync("InventoryFull"), d.ToString()); + + + //2002 in-valid expected + Util.ValidateErrorCodeResponse(a, 2200, 400); + Util.ShouldContainValidationError(a, "Name", "2202", "255 max"); + + } + + + + + /// + /// + /// + [Fact] + public async Task BusinessRuleStartDateWithoutEndDateShouldError() + { + + dynamic d = new JObject(); + d.name = Util.Uniquify("BusinessRuleStartDateWithoutEndDateShouldError TEST"); + d.created = DateTime.Now.ToString(); + d.startDate = d.created; + //NO END DATE ERRROR + d.dollarAmount = 1.11m; + d.active = true; + d.usertype = 1; + + //create via inventory full test user + ApiResponse a = await Util.PostAsync("widget", await Util.GetTokenAsync("InventoryFull"), d.ToString()); + + + //2002 in-valid expected + Util.ValidateErrorCodeResponse(a, 2200, 400); + Util.ShouldContainValidationError(a, "EndDate", "2201"); + + } + + + + /// + /// + /// + [Fact] + public async Task BusinessRuleEndDateWithoutStartDateShouldError() + { + + dynamic d = new JObject(); + d.name = Util.Uniquify("BusinessRuleEndDateWithoutStartDateShouldError TEST"); + d.created = DateTime.Now.ToString(); + d.endDate = d.created; + //NO START DATE ERRROR + d.dollarAmount = 1.11m; + d.active = true; + d.usertype = 1; + + //create via inventory full test user + ApiResponse a = await Util.PostAsync("widget", await Util.GetTokenAsync("InventoryFull"), d.ToString()); + + + //2002 in-valid expected + Util.ValidateErrorCodeResponse(a, 2200, 400); + Util.ShouldContainValidationError(a, "StartDate", "2201"); + + } + + + /// + /// + /// + [Fact] + public async Task BusinessRuleEndDateBeforeStartDateShouldError() + { + + dynamic d = new JObject(); + d.name = Util.Uniquify("BusinessRuleEndDateBeforeStartDateShouldError TEST"); + d.created = DateTime.Now.ToString(); + d.startDate = DateTime.Now.ToString(); + d.endDate = DateTime.Now.AddHours(-1).ToString(); + //NO START DATE ERRROR + d.dollarAmount = 1.11m; + d.active = true; + d.usertype = 1; + + //create via inventory full test user + ApiResponse a = await Util.PostAsync("widget", await Util.GetTokenAsync("InventoryFull"), d.ToString()); + + + //2002 in-valid expected + Util.ValidateErrorCodeResponse(a, 2200, 400); + Util.ShouldContainValidationError(a, "StartDate", "2207"); + + } + + + + /// + /// + /// + [Fact] + public async Task BusinessRuleEnumInvalidShouldError() + { + + dynamic d = new JObject(); + d.name = Util.Uniquify("BusinessRuleEnumInvalidShouldError TEST"); + d.created = DateTime.Now.ToString(); + + //NO END DATE ERRROR + d.dollarAmount = 1.11m; + d.active = true; + d.usertype = -1;//<---BAD VALUE + d.Notes = "blah"; + d.customFields = Util.WidgetRequiredCustomFieldsJsonString(); + + + //create via inventory full test user + ApiResponse a = await Util.PostAsync("widget", await Util.GetTokenAsync("InventoryFull"), d.ToString()); + + + //2002 in-valid expected + Util.ValidateErrorCodeResponse(a, 2200, 400); + Util.ShouldContainValidationError(a, "UserType", "2203"); + + } + + //================================================== + + }//eoc +}//eons diff --git a/WorkOrder/WorkOrderCrud.cs b/WorkOrder/WorkOrderCrud.cs index 9fd53b7..88ab6cf 100644 --- a/WorkOrder/WorkOrderCrud.cs +++ b/WorkOrder/WorkOrderCrud.cs @@ -1,690 +1,690 @@ -using System.Linq; -using Xunit; -using Newtonsoft.Json.Linq; -using FluentAssertions; - -namespace raven_integration -{ - - public class WorkOrderCrud - { - - /// - /// Test all CRUD routes for a WorkOrder - /// Build up graph, update graph, remove graph bit by bit - /// - [Fact] - public async void CRUD() - { - ///////////////////////////////////////////////////////////////////////// - // CREATE - // - dynamic d = new JObject(); - d.active = true; - d.notes = "WOHEADER The quick brown fox jumped over the six lazy dogs!"; - d.wiki = "no wiki"; - - //Tags - dynamic dTagsArray = new JArray(); - dTagsArray.Add("wo-Red"); - dTagsArray.Add("wo-green"); - dTagsArray.Add("wo-blue"); - d.tags = dTagsArray; - - ApiResponse a = await Util.PostAsync("workorder", await Util.GetTokenAsync("superuser", "l3tm3in"), d.ToString()); - Util.ValidateDataReturnResponseOk(a); - dynamic WorkorderToUpdate = a.ObjectResponse["data"]; - long WorkOrderId = a.ObjectResponse["data"]["id"].Value(); - ((long)a.ObjectResponse["data"]["serial"]).Should().NotBe(0); - - #region CREATE first woitem - - //CREATE WOITEM 1 - d = new JObject(); - d.active = true; - d.notes = "woitem The quick brown fox jumped over the six lazy dogs!"; - d.wiki = "# woitem test wiki"; - d.workOrderId = WorkOrderId; - - //Tags - dTagsArray = new JArray(); - dTagsArray.Add("woitem-Red"); - dTagsArray.Add("woitem-green"); - dTagsArray.Add("woitem-blue"); - d.tags = dTagsArray; - - a = await Util.PostAsync("workorder/items", await Util.GetTokenAsync("superuser", "l3tm3in"), d.ToString()); - Util.ValidateDataReturnResponseOk(a); - dynamic WorkOrderItemToUpdate = a.ObjectResponse["data"]; - - long WorkOrderItem1Id = a.ObjectResponse["data"]["id"].Value(); - - - - //CREATE WOITEMPART - d = new JObject(); - d.active = true; - d.notes = "woitempart The quick brown fox jumped over the six lazy dogs!"; - d.wiki = "# woitempart test wiki"; - d.workOrderItemId = WorkOrderItem1Id; - - //Tags - dTagsArray = new JArray(); - dTagsArray.Add("woitempart-Red"); - dTagsArray.Add("woitempart-green"); - dTagsArray.Add("woitempart-blue"); - d.tags = dTagsArray; - - a = await Util.PostAsync("workorder/items/parts", await Util.GetTokenAsync("superuser", "l3tm3in"), d.ToString()); - Util.ValidateDataReturnResponseOk(a); - dynamic dPartToUpdate = a.ObjectResponse["data"]; - long PartId = (long)a.ObjectResponse["data"]["id"]; - - - //CREATE TWO WOITEMLABORS - //ONE - d = new JObject(); - d.active = true; - d.notes = "woitemlabor The quick brown fox jumped over the six lazy dogs!"; - d.wiki = "# woitemlabor test wiki"; - d.workOrderItemId = WorkOrderItem1Id; - - //Tags - dTagsArray = new JArray(); - dTagsArray.Add("woitemlabor-Red"); - dTagsArray.Add("woitemlabor-green"); - dTagsArray.Add("woitemlabor-blue"); - d.tags = dTagsArray; - - a = await Util.PostAsync("workorder/items/labors", await Util.GetTokenAsync("superuser", "l3tm3in"), d.ToString()); - Util.ValidateDataReturnResponseOk(a); - dynamic dLaborOne = a.ObjectResponse["data"]; - long Labor1Id = a.ObjectResponse["data"]["id"].Value(); - - //TWO - d = new JObject(); - d.active = true; - d.notes = "woitemlabor2 The quick brown fox jumped over the six lazy dogs!"; - d.wiki = "# woitemlabor2 test wiki"; - d.workOrderItemId = WorkOrderItem1Id; - - //Tags - dTagsArray = new JArray(); - dTagsArray.Add("woitemlabor-Red"); - dTagsArray.Add("woitemlabor-green"); - dTagsArray.Add("woitemlabor-blue"); - d.tags = dTagsArray; - - a = await Util.PostAsync("workorder/items/labors", await Util.GetTokenAsync("superuser", "l3tm3in"), d.ToString()); - Util.ValidateDataReturnResponseOk(a); - long WorkOrderItemLaborId2 = a.ObjectResponse["data"]["id"].Value(); - - #endregion create first woitem - - #region CREATE Second woitem - ///////////////////////////////////////// - // Second woitem - // - - //CREATE WOITEM-2 - d = new JObject(); - d.active = true; - d.notes = "woitem-2"; - d.wiki = "# woitem test wiki"; - d.workOrderId = WorkOrderId; - - //Tags - dTagsArray = new JArray(); - dTagsArray.Add("woitem-Red"); - dTagsArray.Add("woitem-green"); - dTagsArray.Add("woitem-blue"); - d.tags = dTagsArray; - - a = await Util.PostAsync("workorder/items", await Util.GetTokenAsync("superuser", "l3tm3in"), d.ToString()); - Util.ValidateDataReturnResponseOk(a); - long WorkOrderItem2Id = a.ObjectResponse["data"]["id"].Value(); - - - - //CREATE WOITEMPART-2 - d = new JObject(); - d.active = true; - d.notes = "woitem-2-part"; - d.wiki = "# woitempart test wiki"; - d.workOrderItemId = WorkOrderItem2Id; - - //Tags - dTagsArray = new JArray(); - dTagsArray.Add("woitempart-Red"); - dTagsArray.Add("woitempart-green"); - dTagsArray.Add("woitempart-blue"); - d.tags = dTagsArray; - - a = await Util.PostAsync("workorder/items/parts", await Util.GetTokenAsync("superuser", "l3tm3in"), d.ToString()); - Util.ValidateDataReturnResponseOk(a); - - - //CREATE WOITEMLABOR(S)-2 - - //ONE-2 - d = new JObject(); - d.active = true; - d.notes = "woitem-2-labor The quick brown fox jumped over the six lazy dogs!"; - d.wiki = "# woitemlabor test wiki"; - d.workOrderItemId = WorkOrderItem2Id; - - //Tags - dTagsArray = new JArray(); - dTagsArray.Add("woitemlabor-Red"); - dTagsArray.Add("woitemlabor-green"); - dTagsArray.Add("woitemlabor-blue"); - d.tags = dTagsArray; - - a = await Util.PostAsync("workorder/items/labors", await Util.GetTokenAsync("superuser", "l3tm3in"), d.ToString()); - Util.ValidateDataReturnResponseOk(a); - - //TWO-2 - d = new JObject(); - d.active = true; - d.notes = "woitem-2-labor2 The quick brown fox jumped over the six lazy dogs!"; - d.wiki = "# woitemlabor2 test wiki"; - d.workOrderItemId = WorkOrderItem2Id; - - //Tags - dTagsArray = new JArray(); - dTagsArray.Add("woitemlabor-Red"); - dTagsArray.Add("woitemlabor-green"); - dTagsArray.Add("woitemlabor-blue"); - d.tags = dTagsArray; - - a = await Util.PostAsync("workorder/items/labors", await Util.GetTokenAsync("superuser", "l3tm3in"), d.ToString()); - Util.ValidateDataReturnResponseOk(a); - - - //expense - d = new JObject(); - d.active = true; - d.notes = "woitem-2-expense"; - d.wiki = "# expense test wiki"; - d.workOrderItemId = WorkOrderItem2Id; - - //Tags - dTagsArray = new JArray(); - dTagsArray.Add("expense-Red"); - dTagsArray.Add("expense-green"); - dTagsArray.Add("expense-blue"); - d.tags = dTagsArray; - - a = await Util.PostAsync("workorder/items/expenses", await Util.GetTokenAsync("superuser", "l3tm3in"), d.ToString()); - Util.ValidateDataReturnResponseOk(a); - long TestExpenseId = (long)a.ObjectResponse["data"]["id"]; - - - //loan - d = new JObject(); - d.active = true; - d.notes = "woitem-2-loan"; - d.wiki = "# loan test wiki"; - d.workOrderItemId = WorkOrderItem2Id; - - //Tags - dTagsArray = new JArray(); - dTagsArray.Add("loan-Red"); - dTagsArray.Add("loan-green"); - dTagsArray.Add("loan-blue"); - d.tags = dTagsArray; - - a = await Util.PostAsync("workorder/items/loans", await Util.GetTokenAsync("superuser", "l3tm3in"), d.ToString()); - Util.ValidateDataReturnResponseOk(a); - - - //partrequest - d = new JObject(); - d.active = true; - d.notes = "partrequest-2-partrequest"; - d.wiki = "# partrequest test wiki"; - d.workOrderItemId = WorkOrderItem2Id; - - //Tags - dTagsArray = new JArray(); - dTagsArray.Add("partrequest-Red"); - dTagsArray.Add("partrequest-green"); - dTagsArray.Add("partrequest-blue"); - d.tags = dTagsArray; - - a = await Util.PostAsync("workorder/items/partrequests", await Util.GetTokenAsync("superuser", "l3tm3in"), d.ToString()); - Util.ValidateDataReturnResponseOk(a); - - //scheduleduser - d = new JObject(); - d.active = true; - d.notes = "woitem-2-scheduleduser"; - d.wiki = "# scheduleduser test wiki"; - d.workOrderItemId = WorkOrderItem2Id; - - //Tags - dTagsArray = new JArray(); - dTagsArray.Add("scheduleduser-Red"); - dTagsArray.Add("scheduleduser-green"); - dTagsArray.Add("scheduleduser-blue"); - d.tags = dTagsArray; - - a = await Util.PostAsync("workorder/items/scheduledusers", await Util.GetTokenAsync("superuser", "l3tm3in"), d.ToString()); - Util.ValidateDataReturnResponseOk(a); - - - //task - d = new JObject(); - d.active = true; - d.notes = "woitem-2-task"; - d.wiki = "# task test wiki"; - d.workOrderItemId = WorkOrderItem2Id; - - //Tags - dTagsArray = new JArray(); - dTagsArray.Add("task-Red"); - dTagsArray.Add("task-green"); - dTagsArray.Add("task-blue"); - d.tags = dTagsArray; - - a = await Util.PostAsync("workorder/items/tasks", await Util.GetTokenAsync("superuser", "l3tm3in"), d.ToString()); - Util.ValidateDataReturnResponseOk(a); - - - //travel - d = new JObject(); - d.active = true; - d.notes = "woitem-2-travel"; - d.wiki = "# travel test wiki"; - d.workOrderItemId = WorkOrderItem2Id; - - //Tags - dTagsArray = new JArray(); - dTagsArray.Add("travel-Red"); - dTagsArray.Add("travel-green"); - dTagsArray.Add("travel-blue"); - d.tags = dTagsArray; - - a = await Util.PostAsync("workorder/items/travels", await Util.GetTokenAsync("superuser", "l3tm3in"), d.ToString()); - Util.ValidateDataReturnResponseOk(a); - - - //unit - d = new JObject(); - d.active = true; - d.notes = "woitem-2-unit"; - d.wiki = "# unit test wiki"; - d.workOrderItemId = WorkOrderItem2Id; - - //Tags - dTagsArray = new JArray(); - dTagsArray.Add("unit-Red"); - dTagsArray.Add("unit-green"); - dTagsArray.Add("unit-blue"); - d.tags = dTagsArray; - - a = await Util.PostAsync("workorder/items/units", await Util.GetTokenAsync("superuser", "l3tm3in"), d.ToString()); - Util.ValidateDataReturnResponseOk(a); - - #endregion create second woitem - - #region UPDATE - ///////////////////////////////////////////////////////////////////////// - //UPDATES - // - - dLaborOne.notes = "UpdatedLaborNotes"; - a = await Util.PutAsync("workorder/items/labors", await Util.GetTokenAsync("superuser", "l3tm3in"), dLaborOne.ToString()); - Util.ValidateDataReturnResponseOk(a); - - dPartToUpdate.notes = "UpdatedPartNotes"; - a = await Util.PutAsync("workorder/items/parts", await Util.GetTokenAsync("superuser", "l3tm3in"), dPartToUpdate.ToString()); - Util.ValidateDataReturnResponseOk(a); - - WorkOrderItemToUpdate.notes = "UpdatedWoItemNotes"; - a = await Util.PutAsync("workorder/items", await Util.GetTokenAsync("superuser", "l3tm3in"), WorkOrderItemToUpdate.ToString()); - Util.ValidateDataReturnResponseOk(a); - - WorkorderToUpdate.notes = "UpdatedWoNotes"; - a = await Util.PutAsync("workorder", await Util.GetTokenAsync("superuser", "l3tm3in"), WorkorderToUpdate.ToString()); - Util.ValidateDataReturnResponseOk(a); - - #endregion update - - #region Validate all create and update - - //RETRIEVE WORKORDER AND VALIDATE ENTIRE - a = await Util.GetAsync("workorder/" + WorkOrderId.ToString(), await Util.GetTokenAsync("superuser", "l3tm3in")); - Util.ValidateDataReturnResponseOk(a); - - var w = a.ObjectResponse["data"]; - w["items"].Count().Should().Be(2); - ((string)w["notes"]).Should().Be("UpdatedWoNotes"); - - - var woitem1 = w["items"].FirstOrDefault(z => (long)z["id"] == WorkOrderItem1Id); - woitem1["labors"].Count().Should().Be(2); - woitem1["parts"].Count().Should().Be(1); - ((string)woitem1["notes"]).Should().Be("UpdatedWoItemNotes"); - ((string)woitem1["labors"].FirstOrDefault(z => (long)z["id"] == Labor1Id)["notes"]).Should().Be("UpdatedLaborNotes"); - ((string)woitem1["parts"].FirstOrDefault(z => (long)z["id"] == PartId)["notes"]).Should().Be("UpdatedPartNotes"); - - var woitem2 = w["items"].FirstOrDefault(z => (long)z["id"] == WorkOrderItem2Id); - woitem2["labors"].Count().Should().Be(2); - woitem2["parts"].Count().Should().Be(1); - ((string)woitem2["notes"]).Should().Be("woitem-2"); - woitem2["labors"].FirstOrDefault(z => (string)z["notes"] == "woitem-2-labor2 The quick brown fox jumped over the six lazy dogs!").Should().NotBeNull(); - woitem2["parts"].FirstOrDefault(z => (string)z["notes"] == "woitem-2-part").Should().NotBeNull(); - woitem2["parts"].FirstOrDefault(z => (string)z["notes"] == "bogus").Should().BeNull(); - - woitem2["expenses"].Count().Should().Be(1); - woitem2["loans"].Count().Should().Be(1); - woitem2["partRequests"].Count().Should().Be(1); - woitem2["scheduledUsers"].Count().Should().Be(1); - woitem2["tasks"].Count().Should().Be(1); - woitem2["travels"].Count().Should().Be(1); - woitem2["units"].Count().Should().Be(1); - - - #endregion validate entire - - - //Test get ancestor route - var AyaTypeWorkOrderItemExpense = 36; - a = await Util.GetAsync($"search/ancestor/{AyaTypeWorkOrderItemExpense}/{TestExpenseId}", await Util.GetTokenAsync("superuser", "l3tm3in")); - Util.ValidateDataReturnResponseOk(a); - - - #region DELETE - a = await Util.DeleteAsync("workorder/items/labors/" + Labor1Id.ToString(), await Util.GetTokenAsync("superuser", "l3tm3in")); - Util.ValidateHTTPStatusCode(a, 204); - a = await Util.GetAsync("workorder/items/labors/" + Labor1Id.ToString(), await Util.GetTokenAsync("superuser", "l3tm3in")); - Util.ValidateHTTPStatusCode(a, 404); - - a = await Util.DeleteAsync("workorder/items/" + WorkOrderItem2Id.ToString(), await Util.GetTokenAsync("superuser", "l3tm3in")); - Util.ValidateHTTPStatusCode(a, 204); - a = await Util.GetAsync("workorder/items/" + WorkOrderItem2Id.ToString(), await Util.GetTokenAsync("superuser", "l3tm3in")); - Util.ValidateHTTPStatusCode(a, 404); - - a = await Util.DeleteAsync("workorder/" + WorkOrderId.ToString(), await Util.GetTokenAsync("superuser", "l3tm3in")); - Util.ValidateHTTPStatusCode(a, 204); - a = await Util.GetAsync("workorder/" + WorkOrderId.ToString(), await Util.GetTokenAsync("superuser", "l3tm3in")); - Util.ValidateHTTPStatusCode(a, 404); - - #endregion delete - - } - - - - [Fact] - public async void ConfirmDeleteTransactionWorksAtServer() - { - ApiResponse a = await Util.GetAsync("build-mode", await Util.GetTokenAsync("superuser", "l3tm3in")); - Util.ValidateDataReturnResponseOk(a); - var BuildMode = (string)a.ObjectResponse["data"]["buildMode"]; - - if (BuildMode == "DEBUG")//The key phrase that triggers exception during delete only exists in debug builds of server - { - - dynamic d = new JObject(); - d.active = true; - d.notes = "WOHEADER"; - d.wiki = "INTEGRATION_DELETE_TEST_FAIL_BEFORE_COMMIT";//<-- key phrase triggers server exception in Workorder immediately before it would normally commit the whole thing - - a = await Util.PostAsync("workorder", await Util.GetTokenAsync("superuser", "l3tm3in"), d.ToString()); - Util.ValidateDataReturnResponseOk(a); - long WorkOrderId = a.ObjectResponse["data"]["id"].Value(); - - //CREATE WOITEM 1 - d = new JObject(); - d.active = true; - d.workOrderId = WorkOrderId; - a = await Util.PostAsync("workorder/items", await Util.GetTokenAsync("superuser", "l3tm3in"), d.ToString()); - Util.ValidateDataReturnResponseOk(a); - long WorkOrderItem1Id = a.ObjectResponse["data"]["id"].Value(); - - //CREATE WOITEMPART - d = new JObject(); - d.active = true; - d.workOrderItemId = WorkOrderItem1Id; - a = await Util.PostAsync("workorder/items/parts", await Util.GetTokenAsync("superuser", "l3tm3in"), d.ToString()); - Util.ValidateDataReturnResponseOk(a); - - //CREATE TWO WOITEMLABORS - //ONE - d = new JObject(); - d.active = true; - d.workOrderItemId = WorkOrderItem1Id; - a = await Util.PostAsync("workorder/items/labors", await Util.GetTokenAsync("superuser", "l3tm3in"), d.ToString()); - Util.ValidateDataReturnResponseOk(a); - - //TWO - d = new JObject(); - d.active = true; - d.workOrderItemId = WorkOrderItem1Id; - a = await Util.PostAsync("workorder/items/labors", await Util.GetTokenAsync("superuser", "l3tm3in"), d.ToString()); - Util.ValidateDataReturnResponseOk(a); - - //CREATE WOITEM-2 - d = new JObject(); - d.active = true; - d.workOrderId = WorkOrderId; - a = await Util.PostAsync("workorder/items", await Util.GetTokenAsync("superuser", "l3tm3in"), d.ToString()); - Util.ValidateDataReturnResponseOk(a); - long WorkOrderItem2Id = (long)a.ObjectResponse["data"]["id"]; - - //CREATE WOITEMPART-2 - d = new JObject(); - d.active = true; - d.workOrderItemId = WorkOrderItem2Id; - a = await Util.PostAsync("workorder/items/parts", await Util.GetTokenAsync("superuser", "l3tm3in"), d.ToString()); - Util.ValidateDataReturnResponseOk(a); - - //CREATE WOITEMLABOR(S)-2 - //ONE-2 - d = new JObject(); - d.active = true; - d.workOrderItemId = WorkOrderItem2Id; - a = await Util.PostAsync("workorder/items/labors", await Util.GetTokenAsync("superuser", "l3tm3in"), d.ToString()); - Util.ValidateDataReturnResponseOk(a); - - //TWO-2 - d = new JObject(); - d.active = true; - d.workOrderItemId = WorkOrderItem2Id; - a = await Util.PostAsync("workorder/items/labors", await Util.GetTokenAsync("superuser", "l3tm3in"), d.ToString()); - Util.ValidateDataReturnResponseOk(a); - - a = await Util.DeleteAsync("workorder/" + WorkOrderId.ToString(), await Util.GetTokenAsync("superuser", "l3tm3in")); - Util.ValidateErrorCodeResponse(a, 2200, 400); - - //now confirm the workorder is still there and with it's children intact - //RETRIEVE WORKORDER AND VALIDATE ENTIRE - a = await Util.GetAsync("workorder/" + WorkOrderId.ToString(), await Util.GetTokenAsync("superuser", "l3tm3in")); - Util.ValidateDataReturnResponseOk(a); - - var w = a.ObjectResponse["data"]; - w["items"].Count().Should().Be(2); - - var woitem1 = w["items"].FirstOrDefault(z => (long)z["id"] == WorkOrderItem1Id); - woitem1["labors"].Count().Should().Be(2); - woitem1["parts"].Count().Should().Be(1); - - var woitem2 = w["items"].FirstOrDefault(z => (long)z["id"] == WorkOrderItem2Id); - woitem2["labors"].Count().Should().Be(2); - woitem2["parts"].Count().Should().Be(1); - - } - - } - - - - - /// - /// Test all CRUD routes for a WorkOrder - /// Build up graph, update graph, remove graph bit by bit - /// - [Fact] - public async void DuplicateWorks() - { - ///////////////////////////////////////////////////////////////////////// - // CREATE - // - dynamic d = new JObject(); - d.active = true; - d.notes = "WOHEADER DuplicateWorks"; - d.wiki = "DuplicateWorks integration test"; - - ApiResponse a = await Util.PostAsync("workorder", await Util.GetTokenAsync("superuser", "l3tm3in"), d.ToString()); - Util.ValidateDataReturnResponseOk(a); - dynamic WorkorderToUpdate = a.ObjectResponse["data"]; - long WorkOrderId = a.ObjectResponse["data"]["id"].Value(); - - #region CREATE first woitem - - //CREATE WOITEM 1 - d = new JObject(); - d.active = true; - d.notes = "woitem DuplicateWorks"; - d.wiki = "# woitem test wiki"; - d.workOrderId = WorkOrderId; - - a = await Util.PostAsync("workorder/items", await Util.GetTokenAsync("superuser", "l3tm3in"), d.ToString()); - Util.ValidateDataReturnResponseOk(a); - dynamic WorkOrderItemToUpdate = a.ObjectResponse["data"]; - long WorkOrderItem1Id = a.ObjectResponse["data"]["id"].Value(); - - //CREATE WOITEMPART - d = new JObject(); - d.active = true; - d.notes = "woitempart DuplicateWorks"; - // d.wiki = "# woitempart test wiki"; - d.workOrderItemId = WorkOrderItem1Id; - - a = await Util.PostAsync("workorder/items/parts", await Util.GetTokenAsync("superuser", "l3tm3in"), d.ToString()); - Util.ValidateDataReturnResponseOk(a); - dynamic dPartToUpdate = a.ObjectResponse["data"]; - long PartId = (long)a.ObjectResponse["data"]["id"]; - - //CREATE TWO WOITEMLABORS - //ONE - d = new JObject(); - d.active = true; - d.notes = "woitemlabor DuplicateWorks"; - // d.wiki = "# woitemlabor test wiki"; - d.workOrderItemId = WorkOrderItem1Id; - - - a = await Util.PostAsync("workorder/items/labors", await Util.GetTokenAsync("superuser", "l3tm3in"), d.ToString()); - Util.ValidateDataReturnResponseOk(a); - dynamic dLaborOne = a.ObjectResponse["data"]; - long Labor1Id = a.ObjectResponse["data"]["id"].Value(); - - //TWO - d = new JObject(); - d.active = true; - d.notes = "woitemlabor2 DuplicateWorks"; - // d.wiki = "# woitemlabor2 test wiki"; - d.workOrderItemId = WorkOrderItem1Id; - - - a = await Util.PostAsync("workorder/items/labors", await Util.GetTokenAsync("superuser", "l3tm3in"), d.ToString()); - Util.ValidateDataReturnResponseOk(a); - long WorkOrderItemLaborId2 = a.ObjectResponse["data"]["id"].Value(); - - #endregion create first woitem - - #region CREATE Second woitem - ///////////////////////////////////////// - // Second woitem - // - //CREATE WOITEM-2 - d = new JObject(); - d.active = true; - d.notes = "woitem-2 DuplicateWorks"; - d.wiki = "# woitem test wiki"; - d.workOrderId = WorkOrderId; - - a = await Util.PostAsync("workorder/items", await Util.GetTokenAsync("superuser", "l3tm3in"), d.ToString()); - Util.ValidateDataReturnResponseOk(a); - long WorkOrderItem2Id = a.ObjectResponse["data"]["id"].Value(); - - //CREATE WOITEMPART-2 - d = new JObject(); - d.active = true; - d.notes = "woitem-2-partDuplicateWorks"; - // d.wiki = "# woitempart test wiki"; - d.workOrderItemId = WorkOrderItem2Id; - - a = await Util.PostAsync("workorder/items/parts", await Util.GetTokenAsync("superuser", "l3tm3in"), d.ToString()); - Util.ValidateDataReturnResponseOk(a); - - //CREATE WOITEMLABOR(S)-2 - //ONE-2 - d = new JObject(); - d.active = true; - d.notes = "woitem-2-laborDuplicateWorks"; - //d.wiki = "# woitemlabor test wiki"; - d.workOrderItemId = WorkOrderItem2Id; - a = await Util.PostAsync("workorder/items/labors", await Util.GetTokenAsync("superuser", "l3tm3in"), d.ToString()); - Util.ValidateDataReturnResponseOk(a); - - //TWO-2 - d = new JObject(); - d.active = true; - d.notes = "woitem-2-labor2DuplicateWorks"; - //d.wiki = "# woitemlabor2 test wiki"; - d.workOrderItemId = WorkOrderItem2Id; - a = await Util.PostAsync("workorder/items/labors", await Util.GetTokenAsync("superuser", "l3tm3in"), d.ToString()); - Util.ValidateDataReturnResponseOk(a); - - #endregion create second woitem - - - - #region Duplicate and Validate - - //DUPLICATE - should make a copy of above, save and return entire object graph just like a get operation - a = await Util.PostAsync("workorder/duplicate/" + WorkOrderId.ToString(), await Util.GetTokenAsync("superuser", "l3tm3in"), d.ToString()); - Util.ValidateDataReturnResponseOk(a); - long DuplicateWorkOrderId = a.ObjectResponse["data"]["id"].Value(); - DuplicateWorkOrderId.Should().NotBe(WorkOrderId); - ((long)a.ObjectResponse["data"]["serial"]).Should().NotBe(0); - - // //RETRIEVE WORKORDER AND VALIDATE ENTIRE - // a = await Util.GetAsync("workorder/" + WorkOrderId.ToString(), await Util.GetTokenAsync("superuser", "l3tm3in")); - // Util.ValidateDataReturnResponseOk(a); - - var w = a.ObjectResponse["data"]; - w["items"].Count().Should().Be(2); - ((string)w["notes"]).Should().Be("WOHEADER DuplicateWorks"); - - - var woitem1 = w["items"].FirstOrDefault(z => (long)z["id"] == WorkOrderItem1Id); - woitem1["labors"].Count().Should().Be(2); - woitem1["parts"].Count().Should().Be(1); - ((string)woitem1["notes"]).Should().Be("woitem DuplicateWorks"); - ((string)woitem1["labors"].FirstOrDefault(z => (long)z["id"] == Labor1Id)["notes"]).Should().Be("woitemlabor DuplicateWorks"); - ((string)woitem1["parts"].FirstOrDefault(z => (long)z["id"] == PartId)["notes"]).Should().Be("woitempart DuplicateWorks"); - - var woitem2 = w["items"].FirstOrDefault(z => (long)z["id"] == WorkOrderItem2Id); - woitem2["labors"].Count().Should().Be(2); - woitem2["parts"].Count().Should().Be(1); - ((string)woitem2["notes"]).Should().Be("woitem-2 DuplicateWorks"); - woitem2["labors"].FirstOrDefault(z => (string)z["notes"] == "woitem-2-labor2DuplicateWorks").Should().NotBeNull(); - woitem2["parts"].FirstOrDefault(z => (string)z["notes"] == "woitem-2-partDuplicateWorks").Should().NotBeNull(); - - #endregion validate entire - - - - } - - - - //================================================== - - }//eoc -}//eons +using System.Linq; +using Xunit; +using Newtonsoft.Json.Linq; +using FluentAssertions; + +namespace raven_integration +{ + + public class WorkOrderCrud + { + + /// + /// Test all CRUD routes for a WorkOrder + /// Build up graph, update graph, remove graph bit by bit + /// + [Fact] + public async Task CRUD() + { + ///////////////////////////////////////////////////////////////////////// + // CREATE + // + dynamic d = new JObject(); + d.active = true; + d.notes = "WOHEADER The quick brown fox jumped over the six lazy dogs!"; + d.wiki = "no wiki"; + + //Tags + dynamic dTagsArray = new JArray(); + dTagsArray.Add("wo-Red"); + dTagsArray.Add("wo-green"); + dTagsArray.Add("wo-blue"); + d.tags = dTagsArray; + + ApiResponse a = await Util.PostAsync("workorder", await Util.GetTokenAsync("superuser", "l3tm3in"), d.ToString()); + Util.ValidateDataReturnResponseOk(a); + dynamic WorkorderToUpdate = a.ObjectResponse["data"]; + long WorkOrderId = a.ObjectResponse["data"]["id"].Value(); + ((long)a.ObjectResponse["data"]["serial"]).Should().NotBe(0); + + #region CREATE first woitem + + //CREATE WOITEM 1 + d = new JObject(); + d.active = true; + d.notes = "woitem The quick brown fox jumped over the six lazy dogs!"; + d.wiki = "# woitem test wiki"; + d.workOrderId = WorkOrderId; + + //Tags + dTagsArray = new JArray(); + dTagsArray.Add("woitem-Red"); + dTagsArray.Add("woitem-green"); + dTagsArray.Add("woitem-blue"); + d.tags = dTagsArray; + + a = await Util.PostAsync("workorder/items", await Util.GetTokenAsync("superuser", "l3tm3in"), d.ToString()); + Util.ValidateDataReturnResponseOk(a); + dynamic WorkOrderItemToUpdate = a.ObjectResponse["data"]; + + long WorkOrderItem1Id = a.ObjectResponse["data"]["id"].Value(); + + + + //CREATE WOITEMPART + d = new JObject(); + d.active = true; + d.notes = "woitempart The quick brown fox jumped over the six lazy dogs!"; + d.wiki = "# woitempart test wiki"; + d.workOrderItemId = WorkOrderItem1Id; + + //Tags + dTagsArray = new JArray(); + dTagsArray.Add("woitempart-Red"); + dTagsArray.Add("woitempart-green"); + dTagsArray.Add("woitempart-blue"); + d.tags = dTagsArray; + + a = await Util.PostAsync("workorder/items/parts", await Util.GetTokenAsync("superuser", "l3tm3in"), d.ToString()); + Util.ValidateDataReturnResponseOk(a); + dynamic dPartToUpdate = a.ObjectResponse["data"]; + long PartId = (long)a.ObjectResponse["data"]["id"]; + + + //CREATE TWO WOITEMLABORS + //ONE + d = new JObject(); + d.active = true; + d.notes = "woitemlabor The quick brown fox jumped over the six lazy dogs!"; + d.wiki = "# woitemlabor test wiki"; + d.workOrderItemId = WorkOrderItem1Id; + + //Tags + dTagsArray = new JArray(); + dTagsArray.Add("woitemlabor-Red"); + dTagsArray.Add("woitemlabor-green"); + dTagsArray.Add("woitemlabor-blue"); + d.tags = dTagsArray; + + a = await Util.PostAsync("workorder/items/labors", await Util.GetTokenAsync("superuser", "l3tm3in"), d.ToString()); + Util.ValidateDataReturnResponseOk(a); + dynamic dLaborOne = a.ObjectResponse["data"]; + long Labor1Id = a.ObjectResponse["data"]["id"].Value(); + + //TWO + d = new JObject(); + d.active = true; + d.notes = "woitemlabor2 The quick brown fox jumped over the six lazy dogs!"; + d.wiki = "# woitemlabor2 test wiki"; + d.workOrderItemId = WorkOrderItem1Id; + + //Tags + dTagsArray = new JArray(); + dTagsArray.Add("woitemlabor-Red"); + dTagsArray.Add("woitemlabor-green"); + dTagsArray.Add("woitemlabor-blue"); + d.tags = dTagsArray; + + a = await Util.PostAsync("workorder/items/labors", await Util.GetTokenAsync("superuser", "l3tm3in"), d.ToString()); + Util.ValidateDataReturnResponseOk(a); + long WorkOrderItemLaborId2 = a.ObjectResponse["data"]["id"].Value(); + + #endregion create first woitem + + #region CREATE Second woitem + ///////////////////////////////////////// + // Second woitem + // + + //CREATE WOITEM-2 + d = new JObject(); + d.active = true; + d.notes = "woitem-2"; + d.wiki = "# woitem test wiki"; + d.workOrderId = WorkOrderId; + + //Tags + dTagsArray = new JArray(); + dTagsArray.Add("woitem-Red"); + dTagsArray.Add("woitem-green"); + dTagsArray.Add("woitem-blue"); + d.tags = dTagsArray; + + a = await Util.PostAsync("workorder/items", await Util.GetTokenAsync("superuser", "l3tm3in"), d.ToString()); + Util.ValidateDataReturnResponseOk(a); + long WorkOrderItem2Id = a.ObjectResponse["data"]["id"].Value(); + + + + //CREATE WOITEMPART-2 + d = new JObject(); + d.active = true; + d.notes = "woitem-2-part"; + d.wiki = "# woitempart test wiki"; + d.workOrderItemId = WorkOrderItem2Id; + + //Tags + dTagsArray = new JArray(); + dTagsArray.Add("woitempart-Red"); + dTagsArray.Add("woitempart-green"); + dTagsArray.Add("woitempart-blue"); + d.tags = dTagsArray; + + a = await Util.PostAsync("workorder/items/parts", await Util.GetTokenAsync("superuser", "l3tm3in"), d.ToString()); + Util.ValidateDataReturnResponseOk(a); + + + //CREATE WOITEMLABOR(S)-2 + + //ONE-2 + d = new JObject(); + d.active = true; + d.notes = "woitem-2-labor The quick brown fox jumped over the six lazy dogs!"; + d.wiki = "# woitemlabor test wiki"; + d.workOrderItemId = WorkOrderItem2Id; + + //Tags + dTagsArray = new JArray(); + dTagsArray.Add("woitemlabor-Red"); + dTagsArray.Add("woitemlabor-green"); + dTagsArray.Add("woitemlabor-blue"); + d.tags = dTagsArray; + + a = await Util.PostAsync("workorder/items/labors", await Util.GetTokenAsync("superuser", "l3tm3in"), d.ToString()); + Util.ValidateDataReturnResponseOk(a); + + //TWO-2 + d = new JObject(); + d.active = true; + d.notes = "woitem-2-labor2 The quick brown fox jumped over the six lazy dogs!"; + d.wiki = "# woitemlabor2 test wiki"; + d.workOrderItemId = WorkOrderItem2Id; + + //Tags + dTagsArray = new JArray(); + dTagsArray.Add("woitemlabor-Red"); + dTagsArray.Add("woitemlabor-green"); + dTagsArray.Add("woitemlabor-blue"); + d.tags = dTagsArray; + + a = await Util.PostAsync("workorder/items/labors", await Util.GetTokenAsync("superuser", "l3tm3in"), d.ToString()); + Util.ValidateDataReturnResponseOk(a); + + + //expense + d = new JObject(); + d.active = true; + d.notes = "woitem-2-expense"; + d.wiki = "# expense test wiki"; + d.workOrderItemId = WorkOrderItem2Id; + + //Tags + dTagsArray = new JArray(); + dTagsArray.Add("expense-Red"); + dTagsArray.Add("expense-green"); + dTagsArray.Add("expense-blue"); + d.tags = dTagsArray; + + a = await Util.PostAsync("workorder/items/expenses", await Util.GetTokenAsync("superuser", "l3tm3in"), d.ToString()); + Util.ValidateDataReturnResponseOk(a); + long TestExpenseId = (long)a.ObjectResponse["data"]["id"]; + + + //loan + d = new JObject(); + d.active = true; + d.notes = "woitem-2-loan"; + d.wiki = "# loan test wiki"; + d.workOrderItemId = WorkOrderItem2Id; + + //Tags + dTagsArray = new JArray(); + dTagsArray.Add("loan-Red"); + dTagsArray.Add("loan-green"); + dTagsArray.Add("loan-blue"); + d.tags = dTagsArray; + + a = await Util.PostAsync("workorder/items/loans", await Util.GetTokenAsync("superuser", "l3tm3in"), d.ToString()); + Util.ValidateDataReturnResponseOk(a); + + + //partrequest + d = new JObject(); + d.active = true; + d.notes = "partrequest-2-partrequest"; + d.wiki = "# partrequest test wiki"; + d.workOrderItemId = WorkOrderItem2Id; + + //Tags + dTagsArray = new JArray(); + dTagsArray.Add("partrequest-Red"); + dTagsArray.Add("partrequest-green"); + dTagsArray.Add("partrequest-blue"); + d.tags = dTagsArray; + + a = await Util.PostAsync("workorder/items/partrequests", await Util.GetTokenAsync("superuser", "l3tm3in"), d.ToString()); + Util.ValidateDataReturnResponseOk(a); + + //scheduleduser + d = new JObject(); + d.active = true; + d.notes = "woitem-2-scheduleduser"; + d.wiki = "# scheduleduser test wiki"; + d.workOrderItemId = WorkOrderItem2Id; + + //Tags + dTagsArray = new JArray(); + dTagsArray.Add("scheduleduser-Red"); + dTagsArray.Add("scheduleduser-green"); + dTagsArray.Add("scheduleduser-blue"); + d.tags = dTagsArray; + + a = await Util.PostAsync("workorder/items/scheduledusers", await Util.GetTokenAsync("superuser", "l3tm3in"), d.ToString()); + Util.ValidateDataReturnResponseOk(a); + + + //task + d = new JObject(); + d.active = true; + d.notes = "woitem-2-task"; + d.wiki = "# task test wiki"; + d.workOrderItemId = WorkOrderItem2Id; + + //Tags + dTagsArray = new JArray(); + dTagsArray.Add("task-Red"); + dTagsArray.Add("task-green"); + dTagsArray.Add("task-blue"); + d.tags = dTagsArray; + + a = await Util.PostAsync("workorder/items/tasks", await Util.GetTokenAsync("superuser", "l3tm3in"), d.ToString()); + Util.ValidateDataReturnResponseOk(a); + + + //travel + d = new JObject(); + d.active = true; + d.notes = "woitem-2-travel"; + d.wiki = "# travel test wiki"; + d.workOrderItemId = WorkOrderItem2Id; + + //Tags + dTagsArray = new JArray(); + dTagsArray.Add("travel-Red"); + dTagsArray.Add("travel-green"); + dTagsArray.Add("travel-blue"); + d.tags = dTagsArray; + + a = await Util.PostAsync("workorder/items/travels", await Util.GetTokenAsync("superuser", "l3tm3in"), d.ToString()); + Util.ValidateDataReturnResponseOk(a); + + + //unit + d = new JObject(); + d.active = true; + d.notes = "woitem-2-unit"; + d.wiki = "# unit test wiki"; + d.workOrderItemId = WorkOrderItem2Id; + + //Tags + dTagsArray = new JArray(); + dTagsArray.Add("unit-Red"); + dTagsArray.Add("unit-green"); + dTagsArray.Add("unit-blue"); + d.tags = dTagsArray; + + a = await Util.PostAsync("workorder/items/units", await Util.GetTokenAsync("superuser", "l3tm3in"), d.ToString()); + Util.ValidateDataReturnResponseOk(a); + + #endregion create second woitem + + #region UPDATE + ///////////////////////////////////////////////////////////////////////// + //UPDATES + // + + dLaborOne.notes = "UpdatedLaborNotes"; + a = await Util.PutAsync("workorder/items/labors", await Util.GetTokenAsync("superuser", "l3tm3in"), dLaborOne.ToString()); + Util.ValidateDataReturnResponseOk(a); + + dPartToUpdate.notes = "UpdatedPartNotes"; + a = await Util.PutAsync("workorder/items/parts", await Util.GetTokenAsync("superuser", "l3tm3in"), dPartToUpdate.ToString()); + Util.ValidateDataReturnResponseOk(a); + + WorkOrderItemToUpdate.notes = "UpdatedWoItemNotes"; + a = await Util.PutAsync("workorder/items", await Util.GetTokenAsync("superuser", "l3tm3in"), WorkOrderItemToUpdate.ToString()); + Util.ValidateDataReturnResponseOk(a); + + WorkorderToUpdate.notes = "UpdatedWoNotes"; + a = await Util.PutAsync("workorder", await Util.GetTokenAsync("superuser", "l3tm3in"), WorkorderToUpdate.ToString()); + Util.ValidateDataReturnResponseOk(a); + + #endregion update + + #region Validate all create and update + + //RETRIEVE WORKORDER AND VALIDATE ENTIRE + a = await Util.GetAsync("workorder/" + WorkOrderId.ToString(), await Util.GetTokenAsync("superuser", "l3tm3in")); + Util.ValidateDataReturnResponseOk(a); + + var w = a.ObjectResponse["data"]; + w["items"].Count().Should().Be(2); + ((string)w["notes"]).Should().Be("UpdatedWoNotes"); + + + var woitem1 = w["items"].FirstOrDefault(z => (long)z["id"] == WorkOrderItem1Id); + woitem1["labors"].Count().Should().Be(2); + woitem1["parts"].Count().Should().Be(1); + ((string)woitem1["notes"]).Should().Be("UpdatedWoItemNotes"); + ((string)woitem1["labors"].FirstOrDefault(z => (long)z["id"] == Labor1Id)["notes"]).Should().Be("UpdatedLaborNotes"); + ((string)woitem1["parts"].FirstOrDefault(z => (long)z["id"] == PartId)["notes"]).Should().Be("UpdatedPartNotes"); + + var woitem2 = w["items"].FirstOrDefault(z => (long)z["id"] == WorkOrderItem2Id); + woitem2["labors"].Count().Should().Be(2); + woitem2["parts"].Count().Should().Be(1); + ((string)woitem2["notes"]).Should().Be("woitem-2"); + woitem2["labors"].FirstOrDefault(z => (string)z["notes"] == "woitem-2-labor2 The quick brown fox jumped over the six lazy dogs!").Should().NotBeNull(); + woitem2["parts"].FirstOrDefault(z => (string)z["notes"] == "woitem-2-part").Should().NotBeNull(); + woitem2["parts"].FirstOrDefault(z => (string)z["notes"] == "bogus").Should().BeNull(); + + woitem2["expenses"].Count().Should().Be(1); + woitem2["loans"].Count().Should().Be(1); + woitem2["partRequests"].Count().Should().Be(1); + woitem2["scheduledUsers"].Count().Should().Be(1); + woitem2["tasks"].Count().Should().Be(1); + woitem2["travels"].Count().Should().Be(1); + woitem2["units"].Count().Should().Be(1); + + + #endregion validate entire + + + //Test get ancestor route + var AyaTypeWorkOrderItemExpense = 36; + a = await Util.GetAsync($"search/ancestor/{AyaTypeWorkOrderItemExpense}/{TestExpenseId}", await Util.GetTokenAsync("superuser", "l3tm3in")); + Util.ValidateDataReturnResponseOk(a); + + + #region DELETE + a = await Util.DeleteAsync("workorder/items/labors/" + Labor1Id.ToString(), await Util.GetTokenAsync("superuser", "l3tm3in")); + Util.ValidateHTTPStatusCode(a, 204); + a = await Util.GetAsync("workorder/items/labors/" + Labor1Id.ToString(), await Util.GetTokenAsync("superuser", "l3tm3in")); + Util.ValidateHTTPStatusCode(a, 404); + + a = await Util.DeleteAsync("workorder/items/" + WorkOrderItem2Id.ToString(), await Util.GetTokenAsync("superuser", "l3tm3in")); + Util.ValidateHTTPStatusCode(a, 204); + a = await Util.GetAsync("workorder/items/" + WorkOrderItem2Id.ToString(), await Util.GetTokenAsync("superuser", "l3tm3in")); + Util.ValidateHTTPStatusCode(a, 404); + + a = await Util.DeleteAsync("workorder/" + WorkOrderId.ToString(), await Util.GetTokenAsync("superuser", "l3tm3in")); + Util.ValidateHTTPStatusCode(a, 204); + a = await Util.GetAsync("workorder/" + WorkOrderId.ToString(), await Util.GetTokenAsync("superuser", "l3tm3in")); + Util.ValidateHTTPStatusCode(a, 404); + + #endregion delete + + } + + + + [Fact] + public async Task ConfirmDeleteTransactionWorksAtServer() + { + ApiResponse a = await Util.GetAsync("build-mode", await Util.GetTokenAsync("superuser", "l3tm3in")); + Util.ValidateDataReturnResponseOk(a); + var BuildMode = (string)a.ObjectResponse["data"]["buildMode"]; + + if (BuildMode == "DEBUG")//The key phrase that triggers exception during delete only exists in debug builds of server + { + + dynamic d = new JObject(); + d.active = true; + d.notes = "WOHEADER"; + d.wiki = "INTEGRATION_DELETE_TEST_FAIL_BEFORE_COMMIT";//<-- key phrase triggers server exception in Workorder immediately before it would normally commit the whole thing + + a = await Util.PostAsync("workorder", await Util.GetTokenAsync("superuser", "l3tm3in"), d.ToString()); + Util.ValidateDataReturnResponseOk(a); + long WorkOrderId = a.ObjectResponse["data"]["id"].Value(); + + //CREATE WOITEM 1 + d = new JObject(); + d.active = true; + d.workOrderId = WorkOrderId; + a = await Util.PostAsync("workorder/items", await Util.GetTokenAsync("superuser", "l3tm3in"), d.ToString()); + Util.ValidateDataReturnResponseOk(a); + long WorkOrderItem1Id = a.ObjectResponse["data"]["id"].Value(); + + //CREATE WOITEMPART + d = new JObject(); + d.active = true; + d.workOrderItemId = WorkOrderItem1Id; + a = await Util.PostAsync("workorder/items/parts", await Util.GetTokenAsync("superuser", "l3tm3in"), d.ToString()); + Util.ValidateDataReturnResponseOk(a); + + //CREATE TWO WOITEMLABORS + //ONE + d = new JObject(); + d.active = true; + d.workOrderItemId = WorkOrderItem1Id; + a = await Util.PostAsync("workorder/items/labors", await Util.GetTokenAsync("superuser", "l3tm3in"), d.ToString()); + Util.ValidateDataReturnResponseOk(a); + + //TWO + d = new JObject(); + d.active = true; + d.workOrderItemId = WorkOrderItem1Id; + a = await Util.PostAsync("workorder/items/labors", await Util.GetTokenAsync("superuser", "l3tm3in"), d.ToString()); + Util.ValidateDataReturnResponseOk(a); + + //CREATE WOITEM-2 + d = new JObject(); + d.active = true; + d.workOrderId = WorkOrderId; + a = await Util.PostAsync("workorder/items", await Util.GetTokenAsync("superuser", "l3tm3in"), d.ToString()); + Util.ValidateDataReturnResponseOk(a); + long WorkOrderItem2Id = (long)a.ObjectResponse["data"]["id"]; + + //CREATE WOITEMPART-2 + d = new JObject(); + d.active = true; + d.workOrderItemId = WorkOrderItem2Id; + a = await Util.PostAsync("workorder/items/parts", await Util.GetTokenAsync("superuser", "l3tm3in"), d.ToString()); + Util.ValidateDataReturnResponseOk(a); + + //CREATE WOITEMLABOR(S)-2 + //ONE-2 + d = new JObject(); + d.active = true; + d.workOrderItemId = WorkOrderItem2Id; + a = await Util.PostAsync("workorder/items/labors", await Util.GetTokenAsync("superuser", "l3tm3in"), d.ToString()); + Util.ValidateDataReturnResponseOk(a); + + //TWO-2 + d = new JObject(); + d.active = true; + d.workOrderItemId = WorkOrderItem2Id; + a = await Util.PostAsync("workorder/items/labors", await Util.GetTokenAsync("superuser", "l3tm3in"), d.ToString()); + Util.ValidateDataReturnResponseOk(a); + + a = await Util.DeleteAsync("workorder/" + WorkOrderId.ToString(), await Util.GetTokenAsync("superuser", "l3tm3in")); + Util.ValidateErrorCodeResponse(a, 2200, 400); + + //now confirm the workorder is still there and with it's children intact + //RETRIEVE WORKORDER AND VALIDATE ENTIRE + a = await Util.GetAsync("workorder/" + WorkOrderId.ToString(), await Util.GetTokenAsync("superuser", "l3tm3in")); + Util.ValidateDataReturnResponseOk(a); + + var w = a.ObjectResponse["data"]; + w["items"].Count().Should().Be(2); + + var woitem1 = w["items"].FirstOrDefault(z => (long)z["id"] == WorkOrderItem1Id); + woitem1["labors"].Count().Should().Be(2); + woitem1["parts"].Count().Should().Be(1); + + var woitem2 = w["items"].FirstOrDefault(z => (long)z["id"] == WorkOrderItem2Id); + woitem2["labors"].Count().Should().Be(2); + woitem2["parts"].Count().Should().Be(1); + + } + + } + + + + + /// + /// Test all CRUD routes for a WorkOrder + /// Build up graph, update graph, remove graph bit by bit + /// + [Fact] + public async Task DuplicateWorks() + { + ///////////////////////////////////////////////////////////////////////// + // CREATE + // + dynamic d = new JObject(); + d.active = true; + d.notes = "WOHEADER DuplicateWorks"; + d.wiki = "DuplicateWorks integration test"; + + ApiResponse a = await Util.PostAsync("workorder", await Util.GetTokenAsync("superuser", "l3tm3in"), d.ToString()); + Util.ValidateDataReturnResponseOk(a); + dynamic WorkorderToUpdate = a.ObjectResponse["data"]; + long WorkOrderId = a.ObjectResponse["data"]["id"].Value(); + + #region CREATE first woitem + + //CREATE WOITEM 1 + d = new JObject(); + d.active = true; + d.notes = "woitem DuplicateWorks"; + d.wiki = "# woitem test wiki"; + d.workOrderId = WorkOrderId; + + a = await Util.PostAsync("workorder/items", await Util.GetTokenAsync("superuser", "l3tm3in"), d.ToString()); + Util.ValidateDataReturnResponseOk(a); + dynamic WorkOrderItemToUpdate = a.ObjectResponse["data"]; + long WorkOrderItem1Id = a.ObjectResponse["data"]["id"].Value(); + + //CREATE WOITEMPART + d = new JObject(); + d.active = true; + d.notes = "woitempart DuplicateWorks"; + // d.wiki = "# woitempart test wiki"; + d.workOrderItemId = WorkOrderItem1Id; + + a = await Util.PostAsync("workorder/items/parts", await Util.GetTokenAsync("superuser", "l3tm3in"), d.ToString()); + Util.ValidateDataReturnResponseOk(a); + dynamic dPartToUpdate = a.ObjectResponse["data"]; + long PartId = (long)a.ObjectResponse["data"]["id"]; + + //CREATE TWO WOITEMLABORS + //ONE + d = new JObject(); + d.active = true; + d.notes = "woitemlabor DuplicateWorks"; + // d.wiki = "# woitemlabor test wiki"; + d.workOrderItemId = WorkOrderItem1Id; + + + a = await Util.PostAsync("workorder/items/labors", await Util.GetTokenAsync("superuser", "l3tm3in"), d.ToString()); + Util.ValidateDataReturnResponseOk(a); + dynamic dLaborOne = a.ObjectResponse["data"]; + long Labor1Id = a.ObjectResponse["data"]["id"].Value(); + + //TWO + d = new JObject(); + d.active = true; + d.notes = "woitemlabor2 DuplicateWorks"; + // d.wiki = "# woitemlabor2 test wiki"; + d.workOrderItemId = WorkOrderItem1Id; + + + a = await Util.PostAsync("workorder/items/labors", await Util.GetTokenAsync("superuser", "l3tm3in"), d.ToString()); + Util.ValidateDataReturnResponseOk(a); + long WorkOrderItemLaborId2 = a.ObjectResponse["data"]["id"].Value(); + + #endregion create first woitem + + #region CREATE Second woitem + ///////////////////////////////////////// + // Second woitem + // + //CREATE WOITEM-2 + d = new JObject(); + d.active = true; + d.notes = "woitem-2 DuplicateWorks"; + d.wiki = "# woitem test wiki"; + d.workOrderId = WorkOrderId; + + a = await Util.PostAsync("workorder/items", await Util.GetTokenAsync("superuser", "l3tm3in"), d.ToString()); + Util.ValidateDataReturnResponseOk(a); + long WorkOrderItem2Id = a.ObjectResponse["data"]["id"].Value(); + + //CREATE WOITEMPART-2 + d = new JObject(); + d.active = true; + d.notes = "woitem-2-partDuplicateWorks"; + // d.wiki = "# woitempart test wiki"; + d.workOrderItemId = WorkOrderItem2Id; + + a = await Util.PostAsync("workorder/items/parts", await Util.GetTokenAsync("superuser", "l3tm3in"), d.ToString()); + Util.ValidateDataReturnResponseOk(a); + + //CREATE WOITEMLABOR(S)-2 + //ONE-2 + d = new JObject(); + d.active = true; + d.notes = "woitem-2-laborDuplicateWorks"; + //d.wiki = "# woitemlabor test wiki"; + d.workOrderItemId = WorkOrderItem2Id; + a = await Util.PostAsync("workorder/items/labors", await Util.GetTokenAsync("superuser", "l3tm3in"), d.ToString()); + Util.ValidateDataReturnResponseOk(a); + + //TWO-2 + d = new JObject(); + d.active = true; + d.notes = "woitem-2-labor2DuplicateWorks"; + //d.wiki = "# woitemlabor2 test wiki"; + d.workOrderItemId = WorkOrderItem2Id; + a = await Util.PostAsync("workorder/items/labors", await Util.GetTokenAsync("superuser", "l3tm3in"), d.ToString()); + Util.ValidateDataReturnResponseOk(a); + + #endregion create second woitem + + + + #region Duplicate and Validate + + //DUPLICATE - should make a copy of above, save and return entire object graph just like a get operation + a = await Util.PostAsync("workorder/duplicate/" + WorkOrderId.ToString(), await Util.GetTokenAsync("superuser", "l3tm3in"), d.ToString()); + Util.ValidateDataReturnResponseOk(a); + long DuplicateWorkOrderId = a.ObjectResponse["data"]["id"].Value(); + DuplicateWorkOrderId.Should().NotBe(WorkOrderId); + ((long)a.ObjectResponse["data"]["serial"]).Should().NotBe(0); + + // //RETRIEVE WORKORDER AND VALIDATE ENTIRE + // a = await Util.GetAsync("workorder/" + WorkOrderId.ToString(), await Util.GetTokenAsync("superuser", "l3tm3in")); + // Util.ValidateDataReturnResponseOk(a); + + var w = a.ObjectResponse["data"]; + w["items"].Count().Should().Be(2); + ((string)w["notes"]).Should().Be("WOHEADER DuplicateWorks"); + + + var woitem1 = w["items"].FirstOrDefault(z => (long)z["id"] == WorkOrderItem1Id); + woitem1["labors"].Count().Should().Be(2); + woitem1["parts"].Count().Should().Be(1); + ((string)woitem1["notes"]).Should().Be("woitem DuplicateWorks"); + ((string)woitem1["labors"].FirstOrDefault(z => (long)z["id"] == Labor1Id)["notes"]).Should().Be("woitemlabor DuplicateWorks"); + ((string)woitem1["parts"].FirstOrDefault(z => (long)z["id"] == PartId)["notes"]).Should().Be("woitempart DuplicateWorks"); + + var woitem2 = w["items"].FirstOrDefault(z => (long)z["id"] == WorkOrderItem2Id); + woitem2["labors"].Count().Should().Be(2); + woitem2["parts"].Count().Should().Be(1); + ((string)woitem2["notes"]).Should().Be("woitem-2 DuplicateWorks"); + woitem2["labors"].FirstOrDefault(z => (string)z["notes"] == "woitem-2-labor2DuplicateWorks").Should().NotBeNull(); + woitem2["parts"].FirstOrDefault(z => (string)z["notes"] == "woitem-2-partDuplicateWorks").Should().NotBeNull(); + + #endregion validate entire + + + + } + + + + //================================================== + + }//eoc +}//eons diff --git a/raven-integration.csproj b/raven-integration.csproj index 8e6348f..359b3e5 100644 --- a/raven-integration.csproj +++ b/raven-integration.csproj @@ -1,16 +1,19 @@ - netcoreapp3.1 + net8.0 + enable false true - - - - + + + + + + diff --git a/util.cs b/util.cs index 1c60722..aa1df0b 100644 --- a/util.cs +++ b/util.cs @@ -1,654 +1,654 @@ -using System; -using System.Threading.Tasks; -using System.Net.Http; -using System.Net.Http.Headers; -using Newtonsoft.Json.Linq; -using FluentAssertions; -using System.Collections.Concurrent; - -namespace raven_integration -{ - public static class TimeZoneAdjustmentExtension - { - - public static DateTime ToOffsetAdjustedUniversalTime(this DateTime dtIn) - { - //Date filtering tests MUST use a relative time zone adjusted to users's forced user options time zone - //or the tests that cross dst / pst boundaries will fail - //See servers spec doc core-locale-currency-numbers-time-and-dates.txt for details - //####################################################################################################### - double TIME_ZONE_ADJUSTMENT = -7;// <---=== SET THIS TO SAME AS GENERATED DATA OFFSET AT SERVER - //####################################################################################################### - - return DateTime.SpecifyKind(dtIn.AddHours(((TIME_ZONE_ADJUSTMENT) * -1)), DateTimeKind.Utc); - - } - } - - public static class Util - { - //####################################################################################################### - //public static string API_BASE_URL = "http://localhost:7575/api/v8/"; - public static string API_BASE_URL = "https://devtest.ayanova.com/api/v8.0/"; - - public static string TEST_DATA_FOLDER = @"..\..\..\testdata\"; - //####################################################################################################### - - - - - public const string OpEquality = "="; - public const string OpGreaterThan = ">"; - public const string OpGreaterThanOrEqualTo = ">="; - public const string OpLessThan = "<"; - public const string OpLessThanOrEqualTo = "<="; - public const string OpNotEqual = "!="; - public const string OpNotLike = "!%"; - public const string OpStartsWith = "%-"; - public const string OpEndsWith = "-%"; - public const string OpContains = "-%-"; - public const string OpNotContains = "!-%-"; - - private static HttpClient client { get; } = new HttpClient(); - - - - // public static ConcurrentDictionary authDict = new ConcurrentDictionary();//10,32 - - private static AutoId Auto { get; } = new AutoId(0); - - //DateTime adjustment methods for relative date filter testing - // public static DateTime RelativeToday() - // { - // Double TimeZoneAdjustment = ((double)TIME_ZONE_ADJUSTMENT) * -1; - // return DateTime.Today.AddHours(TimeZoneAdjustment); - // } - // public static DateTime RelativeNow() - // { - // Double TimeZoneAdjustment = ((double)TIME_ZONE_ADJUSTMENT) * -1; - // return DateTime.Now.AddHours(TimeZoneAdjustment); - // } - - // public static DateTime ToOffsetAdjustedUniversalTime(DateTime dtIn) - // { - // Double TimeZoneAdjustment = ((double)TIME_ZONE_ADJUSTMENT) * -1; - // return dtIn.AddHours(TimeZoneAdjustment).ToUniversalTime(); - // } - - - - - public static string Uniquify(string s) - { - // return s + " " + Auto.GetNext().ToString(); - return s + " " + (Auto.GetNext() + ((DateTimeOffset)DateTime.Now).ToUnixTimeMilliseconds()).ToString(); - } - - public async static Task GetTokenAsync(string login, string password = null) - { - return await CredRepo.GetTokenAsync(login, password); - // if (password == null) - // password = login; - - // if (!authDict.ContainsKey(login)) - // { - // dynamic creds = new JObject(); - // creds.login = login; - // creds.password = password; - - // ApiResponse a = await Util.PostAsync("auth", null, creds.ToString()); - // //Put this in when having concurrency issue during auth and old style dl token creation during login - // ValidateDataReturnResponseOk(a); - - // authDict[login] = a.ObjectResponse["data"]["token"].Value(); - // } - // return authDict[login]; - } - - - - static bool bInitialized = false; - private static void init() - { - if (bInitialized) return; - if (!System.IO.Directory.Exists(TEST_DATA_FOLDER)) - throw new ArgumentOutOfRangeException($"Test data folder {TEST_DATA_FOLDER} not found, current folder is {System.AppDomain.CurrentDomain.BaseDirectory}"); - - client.DefaultRequestHeaders.Accept.Clear(); - client.DefaultRequestHeaders.Accept.Add(new MediaTypeWithQualityHeaderValue("application/json")); - bInitialized = true; - } - - public static string CleanApiRoute(string route) - { - route = route.TrimStart('/'); - return API_BASE_URL + route; - } - - /// - /// Get the path to the server root with route appended - /// this is used to fetch non-api docs etc - /// - /// - /// - public static string CleanNonApiRoute(string route) - { - // public static string API_BASE_URL = "http://localhost:7575/api/v8/"; - //public static string API_BASE_URL = "https://test.helloayanova.com/api/v8.0/"; - - - if (!route.StartsWith('/')) - { - route = "/" + route; - } - - return API_BASE_URL.Split("/api/")[0] + route; - } - - public async static Task GetAsync(string route, string authToken = null)//, string bodyJsonData = null) - { - init(); - - var requestMessage = new HttpRequestMessage(HttpMethod.Get, CleanApiRoute(route)); - if (!string.IsNullOrWhiteSpace(authToken)) - requestMessage.Headers.Authorization = new AuthenticationHeaderValue("Bearer", authToken); - - // if (!string.IsNullOrWhiteSpace(bodyJsonData)) - // requestMessage.Content = new StringContent(bodyJsonData, System.Text.Encoding.UTF8, "application/json"); - - HttpResponseMessage response = await client.SendAsync(requestMessage); - var responseAsString = await response.Content.ReadAsStringAsync(); - - return new ApiResponse() { HttpResponse = response, ObjectResponse = Parse(responseAsString) }; - } - - - public async static Task GetTextResultAsync(string route, string authToken = null, string bodyJsonData = null) - { - init(); - - var requestMessage = new HttpRequestMessage(HttpMethod.Get, CleanApiRoute(route)); - if (!string.IsNullOrWhiteSpace(authToken)) - requestMessage.Headers.Authorization = new AuthenticationHeaderValue("Bearer", authToken); - - if (!string.IsNullOrWhiteSpace(bodyJsonData)) - requestMessage.Content = new StringContent(bodyJsonData, System.Text.Encoding.UTF8, "application/json"); - - HttpResponseMessage response = await client.SendAsync(requestMessage); - var responseAsString = await response.Content.ReadAsStringAsync(); - - return new ApiTextResponse() { HttpResponse = response, TextResponse = responseAsString }; - } - - - public async static Task GetNonApiPageAsync(string route) - { - init(); - var requestMessage = new HttpRequestMessage(HttpMethod.Get, CleanNonApiRoute(route)); - HttpResponseMessage response = await client.SendAsync(requestMessage); - var responseAsString = await response.Content.ReadAsStringAsync(); - return new ApiTextResponse() { HttpResponse = response, TextResponse = responseAsString }; - } - - - - - public static async Task DownloadFileAsync(string route, string authToken = null) - { - - init(); - var requestMessage = new HttpRequestMessage(HttpMethod.Get, CleanApiRoute(route)); - if (!string.IsNullOrWhiteSpace(authToken)) - requestMessage.Headers.Authorization = new AuthenticationHeaderValue("Bearer", authToken); - - HttpResponseMessage response = await client.SendAsync(requestMessage); - return response; - // if (response.IsSuccessStatusCode) - // { - // return await response.Content.ReadAsByteArrayAsync(); - // } - - // return null; - } - - - public async static Task PostAsync(string route, string authToken = null, string postJson = null) - { - init(); - - var requestMessage = new HttpRequestMessage(HttpMethod.Post, CleanApiRoute(route)); - if (!string.IsNullOrWhiteSpace(authToken)) - requestMessage.Headers.Authorization = new AuthenticationHeaderValue("Bearer", authToken); - - if (!string.IsNullOrWhiteSpace(postJson)) - requestMessage.Content = new StringContent(postJson, System.Text.Encoding.UTF8, "application/json"); - - HttpResponseMessage response = await client.SendAsync(requestMessage); - var responseAsString = await response.Content.ReadAsStringAsync(); - - return new ApiResponse() { HttpResponse = response, ObjectResponse = Parse(responseAsString) }; - } - - public async static Task PostFormDataAsync(string route, MultipartFormDataContent formContent, string authToken = null) - { - init(); - - var requestMessage = new HttpRequestMessage(HttpMethod.Post, CleanApiRoute(route)); - if (!string.IsNullOrWhiteSpace(authToken)) - requestMessage.Headers.Authorization = new AuthenticationHeaderValue("Bearer", authToken); - - requestMessage.Content = formContent; - - HttpResponseMessage response = await client.SendAsync(requestMessage); - var responseAsString = await response.Content.ReadAsStringAsync(); - - return new ApiResponse() { HttpResponse = response, ObjectResponse = Parse(responseAsString) }; - } - - - public async static Task PutAsync(string route, string authToken = null, string putJson = null) - { - init(); - - var requestMessage = new HttpRequestMessage(HttpMethod.Put, CleanApiRoute(route)); - if (!string.IsNullOrWhiteSpace(authToken)) - requestMessage.Headers.Authorization = new AuthenticationHeaderValue("Bearer", authToken); - - if (!string.IsNullOrWhiteSpace(putJson)) - requestMessage.Content = new StringContent(putJson, System.Text.Encoding.UTF8, "application/json"); - - HttpResponseMessage response = await client.SendAsync(requestMessage); - var responseAsString = await response.Content.ReadAsStringAsync(); - - return new ApiResponse() { HttpResponse = response, ObjectResponse = Parse(responseAsString) }; - } - - - public async static Task PatchAsync(string route, string authToken = null, string patchJson = null) - { - init(); - - var method = new HttpMethod("PATCH"); - - var requestMessage = new HttpRequestMessage(method, CleanApiRoute(route)); - if (!string.IsNullOrWhiteSpace(authToken)) - requestMessage.Headers.Authorization = new AuthenticationHeaderValue("Bearer", authToken); - - if (!string.IsNullOrWhiteSpace(patchJson)) - requestMessage.Content = new StringContent(patchJson, System.Text.Encoding.UTF8, "application/json-patch+json"); - - HttpResponseMessage response = await client.SendAsync(requestMessage); - var responseAsString = await response.Content.ReadAsStringAsync(); - - return new ApiResponse() { HttpResponse = response, ObjectResponse = Parse(responseAsString) }; - } - - - public async static Task DeleteAsync(string route, string authToken = null) - { - init(); - - var requestMessage = new HttpRequestMessage(HttpMethod.Delete, CleanApiRoute(route)); - if (!string.IsNullOrWhiteSpace(authToken)) - requestMessage.Headers.Authorization = new AuthenticationHeaderValue("Bearer", authToken); - - HttpResponseMessage response = await client.SendAsync(requestMessage); - var responseAsString = await response.Content.ReadAsStringAsync(); - - return new ApiResponse() { HttpResponse = response, ObjectResponse = Parse(responseAsString) }; - } - - - - /// - /// - /// - /// - /// - public static JObject Parse(string jsonString) - { - if (string.IsNullOrWhiteSpace(jsonString)) - { - return null; - } - return JObject.Parse(jsonString); - } - - //https://www.newtonsoft.com/json/help/html/FromObject.htm - private static string ObjectToJsonString(object o) - { - JObject j = (JObject)JToken.FromObject(o); - return j.ToString(); - } - - public static void ValidateDataReturnResponseOk(ApiResponse a) - { - a.ObjectResponse.Should().NotBeNull("No response was found at all?! Nothing to validate"); - - var ErrorMessage = string.Empty; - var ERR = a.ObjectResponse["error"]; - if (ERR != null) - { - ErrorMessage = a.ObjectResponse.ToString(); - // var ecode = ERR["code"]; - // if (ecode != null) - // ErrorMessage += $"CODE: {ecode} "; - - // var emsg = ERR["message"]; - // if (emsg != null) - // ErrorMessage += $"MESSAGE: {emsg} "; - - // var etarget = ERR["target"]; - // if (etarget != null) - // ErrorMessage += $"TARGET: {etarget} "; - } - - a.ObjectResponse["error"].Should().BeNull("because there should not be an error on an api call, error result was: {0}", ErrorMessage); - a.ObjectResponse["data"].Should().NotBeNull("A result should be returned"); - } - - public static void ValidateNoErrorInResponse(ApiResponse a) - { - a.ObjectResponse["error"].Should().BeNull("There should not be an error on an api call"); - } - - public static void ValidateHTTPStatusCode(ApiResponse a, int DesiredStatusCode) - { - ((int)a.HttpResponse.StatusCode).Should().Be(DesiredStatusCode); - } - - public static void ValidateHTTPStatusCode(ApiTextResponse t, int DesiredStatusCode) - { - ((int)t.HttpResponse.StatusCode).Should().Be(DesiredStatusCode); - } - - /// - /// validate a not found response - /// - /// - public static void ValidateResponseNotFound(ApiResponse a) - { - ((int)a.HttpResponse.StatusCode).Should().Be(404); - a.ObjectResponse["error"].Should().NotBeNull("There should be an error on the api call"); - a.ObjectResponse["error"]["code"].Value().Should().Be(2010); - } - - - /// - /// validate a concurrency error - /// - /// - public static void ValidateConcurrencyError(ApiResponse a) - { - ((int)a.HttpResponse.StatusCode).Should().Be(409); - a.ObjectResponse["error"].Should().NotBeNull("There should be an error on the api call"); - //a.ObjectResponse["error"]["code"].Value().Should().Be(2005); - } - - - /// - /// validate that the call violates referential integrity - /// - /// - public static void ValidateViolatesReferentialIntegrityError(ApiResponse a) - { - ((int)a.HttpResponse.StatusCode).Should().Be(400); - a.ObjectResponse["error"].Should().NotBeNull("There should be an error on the api call"); - a.ObjectResponse["error"]["code"].Value().Should().Be(2200); - } - - - - /// - /// validate a bad ModelState response - /// - /// - public static void ValidateBadModelStateResponse(ApiResponse a, string CheckFirstTargetExists = null) - { - ((int)a.HttpResponse.StatusCode).Should().Be(400); - a.ObjectResponse["error"].Should().NotBeNull("There should be an error on the api call"); - a.ObjectResponse["error"]["code"].Value().Should().Be(2200); - a.ObjectResponse["error"]["details"].Should().NotBeNull("There should be error details on the api call"); - if (!string.IsNullOrWhiteSpace(CheckFirstTargetExists)) - { - a.ObjectResponse["error"]["details"][0]["target"].Value().Should().Be(CheckFirstTargetExists); - } - } - - - - - // public enum ValidationErrorType - // { - // RequiredPropertyEmpty = 1, - // LengthExceeded = 2, - // NotUnique = 3, - // StartDateMustComeBeforeEndDate = 4, - // InvalidValue = 5 - - // } - - /// - /// assert contains validation target and error code - /// - /// - /// - /// - public static void ShouldContainValidationError(ApiResponse a, string target, string error, string shouldContainInMessage = null) - { - a.ObjectResponse["error"]["details"].Should().NotBeNull("There should be Details on the api call"); - if (shouldContainInMessage != null) - { - a.ObjectResponse["error"]["details"].Should().Contain( - z => z["target"].Value() == target && - z["error"].Value() == error && - z["message"].Value().Contains(shouldContainInMessage)); - } - else - { - a.ObjectResponse["error"]["details"].Should().Contain(z => z["target"].Value() == target && z["error"].Value() == error); - } - } - - - /// - /// validate server exception response - /// - /// - public static void ValidateServerExceptionResponse(ApiResponse a) - { - ((int)a.HttpResponse.StatusCode).Should().Be(500); - a.ObjectResponse["error"].Should().NotBeNull("There should be an error on the api call"); - a.ObjectResponse["error"]["code"].Value().Should().Be(2002); - } - - - /// - /// Validate an expected api error code and http code response - /// - /// - /// - /// - public static void ValidateErrorCodeResponse(ApiResponse a, int apiErrorCode, int httpStatusCode) - { - ((int)a.HttpResponse.StatusCode).Should().Be(httpStatusCode); - a.ObjectResponse["error"].Should().NotBeNull("There should be an error on the api call"); - a.ObjectResponse["error"]["code"].Value().Should().Be(apiErrorCode); - } - - - public static string GenerateCustomFieldsJsonString( - string c1 = null, string c2 = null, string c3 = null, string c4 = null, - string c5 = null, string c6 = null, string c7 = null, string c8 = null, string c9 = null, - string c10 = null, string c11 = null, string c12 = null, string c13 = null, - string c14 = null, string c15 = null, string c16 = null - ) - { - - //Custom fields - //"[{c1:"blah"}] - dynamic dCustomField = new JObject(); - dCustomField.c1 = c1; - dCustomField.c2 = c2; - dCustomField.c3 = c3; - dCustomField.c4 = c4; - dCustomField.c5 = c5; - dCustomField.c6 = c6; - dCustomField.c7 = c7; - dCustomField.c8 = c8; - dCustomField.c9 = c9; - dCustomField.c10 = c10; - dCustomField.c11 = c11; - dCustomField.c12 = c12; - dCustomField.c13 = c13; - dCustomField.c14 = c14; - dCustomField.c15 = c15; - dCustomField.c16 = c16; - return dCustomField.ToString(); - } - - /// - /// Generate a custom fields string that satisfies the rules in the sample test data - /// - /// - public static string WidgetRequiredCustomFieldsJsonString() - {/*CURRENT TEMPLATE DEFINITION FOR WIDGET CUSTOM FIELDS, FROM SEEDER.CS SERVER PROJECT - var fc = new FormCustom() - { - FormKey = ObjectFields.WIDGET_KEY, - Template = @"[ - { - ""fld"": ""WidgetNotes"", - ""required"": true - }, - { - ""fld"": ""WidgetCustom1"", - ""required"": false, - ""type"": 1 - }, - { - ""fld"": ""WidgetCustom2"", - ""required"": true, - ""type"": 4 - }, - { - ""fld"": ""WidgetCustom3"", - ""required"": false, - ""type"": 5 - }, - { - ""fld"": ""WidgetCustom4"", - ""required"": false, - ""type"": 6 - }, - { - ""fld"": ""WidgetCustom5"", - ""required"": false, - ""type"": 8 - }, - { - ""fld"": ""WidgetCustom6"", - ""required"": false, - ""type"": 2 - }, - { - ""fld"": ""WidgetCustom7"", - ""required"": false, - ""type"": 3 - } - ]" - }; - */ - - //Custom fields - //"[{c1:"blah"}] - dynamic dCustomField = new JObject(); - dCustomField.c1 = "2019-02-08T06:31:48.0019809Z"; - dCustomField.c2 = "c2 text"; - dCustomField.c3 = "333"; - dCustomField.c4 = "true"; - dCustomField.c5 = "5.55"; - return dCustomField.ToString(); - } - - - - - /// - /// Generate a custom fields string that satisfies the rules in this project (formCustom) - /// - /// - public static string UserRequiredCustomFieldsJsonString() - { - //Note c1 is only required custom, c2 is defined but is not required so skipping it here - dynamic dCustomField = new JObject(); - dCustomField.c1 = "UnitTestUtilSampleText"; - return dCustomField.ToString(); - } - - //// [{fld:"COLUMN UNIQUE KEY ID",sort:"-" or "+",filter:{any:true/false,items:[{FILTER OBJECT SEE BELOW}]} }, {key:"second column unique key"},{...etc...}] - public static object BuildSimpleFilterDataListViewColumn(string fieldKey, string filterOp, object filterValue, string sort = null) - { - dynamic d = new JObject(); - d.fld = fieldKey; - if (sort != null) - d.sort = sort; - - dynamic filter = new JObject(); - dynamic items = new JArray(); - dynamic fitem = new JObject(); - fitem.op = filterOp; - fitem.value = filterValue; - items.Add(fitem); - filter.items = items; - d.filter = filter; - return d; - - } - - - - public static object BuildSimpleSortDataListViewColumn(string fieldKey, string sort) - { - dynamic d = new JObject(); - d.fld = fieldKey; - d.sort = sort; - return d; - } - //t(dfilter, dsortarray, 999, 0, false, "UserDataList")); - // public static string BuildDataListRequest(object p = null, object o = null, int limit = 999, int offset = 0, bool bWhatever=false, string dataListKey = "TestWidgetDataList") - // { - // throw new System.NotImplementedException(); - // } - - public static string BuildDataListRequestEx(dynamic dListView = null, int limit = 999, int offset = 0, string dataListKey = "TestWidgetDataList") - { - /* - { - "offset": 0, - "limit": 3, - "dataListKey": "TestWidgetDataList", - "listView": "" - } - */ - dynamic d = new JObject(); - d.offset = offset; - d.limit = limit; - - d.dataListKey = dataListKey; - if (dListView != null) - d.ListView = dListView.ToString(Newtonsoft.Json.Formatting.None); - - return d.ToString(Newtonsoft.Json.Formatting.None); - - - } - - - - - - //--------- - - }//eoc -}//eons +using System; +using System.Threading.Tasks; +using System.Net.Http; +using System.Net.Http.Headers; +using Newtonsoft.Json.Linq; +using FluentAssertions; +using System.Collections.Concurrent; + +namespace raven_integration +{ + public static class TimeZoneAdjustmentExtension + { + + public static DateTime ToOffsetAdjustedUniversalTime(this DateTime dtIn) + { + //Date filtering tests MUST use a relative time zone adjusted to users's forced user options time zone + //or the tests that cross dst / pst boundaries will fail + //See servers spec doc core-locale-currency-numbers-time-and-dates.txt for details + //####################################################################################################### + double TIME_ZONE_ADJUSTMENT = -7;// <---=== SET THIS TO SAME AS GENERATED DATA OFFSET AT SERVER + //####################################################################################################### + + return DateTime.SpecifyKind(dtIn.AddHours(((TIME_ZONE_ADJUSTMENT) * -1)), DateTimeKind.Utc); + + } + } + + public static class Util + { + //####################################################################################################### + //public static string API_BASE_URL = "http://localhost:7575/api/v8/"; + public static string API_BASE_URL = "https://devtest.ayanova.com/api/v8.0/"; + + public static string TEST_DATA_FOLDER = @"..\..\..\testdata\"; + //####################################################################################################### + + + + + public const string OpEquality = "="; + public const string OpGreaterThan = ">"; + public const string OpGreaterThanOrEqualTo = ">="; + public const string OpLessThan = "<"; + public const string OpLessThanOrEqualTo = "<="; + public const string OpNotEqual = "!="; + public const string OpNotLike = "!%"; + public const string OpStartsWith = "%-"; + public const string OpEndsWith = "-%"; + public const string OpContains = "-%-"; + public const string OpNotContains = "!-%-"; + + private static HttpClient client { get; } = new HttpClient(); + + + + // public static ConcurrentDictionary authDict = new ConcurrentDictionary();//10,32 + + private static AutoId Auto { get; } = new AutoId(0); + + //DateTime adjustment methods for relative date filter testing + // public static DateTime RelativeToday() + // { + // Double TimeZoneAdjustment = ((double)TIME_ZONE_ADJUSTMENT) * -1; + // return DateTime.Today.AddHours(TimeZoneAdjustment); + // } + // public static DateTime RelativeNow() + // { + // Double TimeZoneAdjustment = ((double)TIME_ZONE_ADJUSTMENT) * -1; + // return DateTime.Now.AddHours(TimeZoneAdjustment); + // } + + // public static DateTime ToOffsetAdjustedUniversalTime(DateTime dtIn) + // { + // Double TimeZoneAdjustment = ((double)TIME_ZONE_ADJUSTMENT) * -1; + // return dtIn.AddHours(TimeZoneAdjustment).ToUniversalTime(); + // } + + + + + public static string Uniquify(string s) + { + // return s + " " + Auto.GetNext().ToString(); + return s + " " + (Auto.GetNext() + ((DateTimeOffset)DateTime.Now).ToUnixTimeMilliseconds()).ToString(); + } + + public async static Task GetTokenAsync(string login, string password = null) + { + return await CredRepo.GetTokenAsync(login, password); + // if (password == null) + // password = login; + + // if (!authDict.ContainsKey(login)) + // { + // dynamic creds = new JObject(); + // creds.login = login; + // creds.password = password; + + // ApiResponse a = await Util.PostAsync("auth", null, creds.ToString()); + // //Put this in when having concurrency issue during auth and old style dl token creation during login + // ValidateDataReturnResponseOk(a); + + // authDict[login] = a.ObjectResponse["data"]["token"].Value(); + // } + // return authDict[login]; + } + + + + static bool bInitialized = false; + private static void init() + { + if (bInitialized) return; + if (!System.IO.Directory.Exists(TEST_DATA_FOLDER)) + throw new ArgumentOutOfRangeException($"Test data folder {TEST_DATA_FOLDER} not found, current folder is {System.AppDomain.CurrentDomain.BaseDirectory}"); + + client.DefaultRequestHeaders.Accept.Clear(); + client.DefaultRequestHeaders.Accept.Add(new MediaTypeWithQualityHeaderValue("application/json")); + bInitialized = true; + } + + public static string CleanApiRoute(string route) + { + route = route.TrimStart('/'); + return API_BASE_URL + route; + } + + /// + /// Get the path to the server root with route appended + /// this is used to fetch non-api docs etc + /// + /// + /// + public static string CleanNonApiRoute(string route) + { + // public static string API_BASE_URL = "http://localhost:7575/api/v8/"; + //public static string API_BASE_URL = "https://test.helloayanova.com/api/v8.0/"; + + + if (!route.StartsWith('/')) + { + route = "/" + route; + } + + return API_BASE_URL.Split("/api/")[0] + route; + } + + public async static Task GetAsync(string route, string authToken = null)//, string bodyJsonData = null) + { + init(); + + var requestMessage = new HttpRequestMessage(HttpMethod.Get, CleanApiRoute(route)); + if (!string.IsNullOrWhiteSpace(authToken)) + requestMessage.Headers.Authorization = new AuthenticationHeaderValue("Bearer", authToken); + + // if (!string.IsNullOrWhiteSpace(bodyJsonData)) + // requestMessage.Content = new StringContent(bodyJsonData, System.Text.Encoding.UTF8, "application/json"); + + HttpResponseMessage response = await client.SendAsync(requestMessage); + var responseAsString = await response.Content.ReadAsStringAsync(); + + return new ApiResponse() { HttpResponse = response, ObjectResponse = Parse(responseAsString) }; + } + + + public async static Task GetTextResultAsync(string route, string authToken = null, string bodyJsonData = null) + { + init(); + + var requestMessage = new HttpRequestMessage(HttpMethod.Get, CleanApiRoute(route)); + if (!string.IsNullOrWhiteSpace(authToken)) + requestMessage.Headers.Authorization = new AuthenticationHeaderValue("Bearer", authToken); + + if (!string.IsNullOrWhiteSpace(bodyJsonData)) + requestMessage.Content = new StringContent(bodyJsonData, System.Text.Encoding.UTF8, "application/json"); + + HttpResponseMessage response = await client.SendAsync(requestMessage); + var responseAsString = await response.Content.ReadAsStringAsync(); + + return new ApiTextResponse() { HttpResponse = response, TextResponse = responseAsString }; + } + + + public async static Task GetNonApiPageAsync(string route) + { + init(); + var requestMessage = new HttpRequestMessage(HttpMethod.Get, CleanNonApiRoute(route)); + HttpResponseMessage response = await client.SendAsync(requestMessage); + var responseAsString = await response.Content.ReadAsStringAsync(); + return new ApiTextResponse() { HttpResponse = response, TextResponse = responseAsString }; + } + + + + + public static async Task DownloadFileAsync(string route, string authToken = null) + { + + init(); + var requestMessage = new HttpRequestMessage(HttpMethod.Get, CleanApiRoute(route)); + if (!string.IsNullOrWhiteSpace(authToken)) + requestMessage.Headers.Authorization = new AuthenticationHeaderValue("Bearer", authToken); + + HttpResponseMessage response = await client.SendAsync(requestMessage); + return response; + // if (response.IsSuccessStatusCode) + // { + // return await response.Content.ReadAsByteArrayAsync(); + // } + + // return null; + } + + + public async static Task PostAsync(string route, string authToken = null, string postJson = null) + { + init(); + + var requestMessage = new HttpRequestMessage(HttpMethod.Post, CleanApiRoute(route)); + if (!string.IsNullOrWhiteSpace(authToken)) + requestMessage.Headers.Authorization = new AuthenticationHeaderValue("Bearer", authToken); + + if (!string.IsNullOrWhiteSpace(postJson)) + requestMessage.Content = new StringContent(postJson, System.Text.Encoding.UTF8, "application/json"); + + HttpResponseMessage response = await client.SendAsync(requestMessage); + var responseAsString = await response.Content.ReadAsStringAsync(); + + return new ApiResponse() { HttpResponse = response, ObjectResponse = Parse(responseAsString) }; + } + + public async static Task PostFormDataAsync(string route, MultipartFormDataContent formContent, string authToken = null) + { + init(); + + var requestMessage = new HttpRequestMessage(HttpMethod.Post, CleanApiRoute(route)); + if (!string.IsNullOrWhiteSpace(authToken)) + requestMessage.Headers.Authorization = new AuthenticationHeaderValue("Bearer", authToken); + + requestMessage.Content = formContent; + + HttpResponseMessage response = await client.SendAsync(requestMessage); + var responseAsString = await response.Content.ReadAsStringAsync(); + + return new ApiResponse() { HttpResponse = response, ObjectResponse = Parse(responseAsString) }; + } + + + public async static Task PutAsync(string route, string authToken = null, string putJson = null) + { + init(); + + var requestMessage = new HttpRequestMessage(HttpMethod.Put, CleanApiRoute(route)); + if (!string.IsNullOrWhiteSpace(authToken)) + requestMessage.Headers.Authorization = new AuthenticationHeaderValue("Bearer", authToken); + + if (!string.IsNullOrWhiteSpace(putJson)) + requestMessage.Content = new StringContent(putJson, System.Text.Encoding.UTF8, "application/json"); + + HttpResponseMessage response = await client.SendAsync(requestMessage); + var responseAsString = await response.Content.ReadAsStringAsync(); + + return new ApiResponse() { HttpResponse = response, ObjectResponse = Parse(responseAsString) }; + } + + + public async static Task PatchAsync(string route, string authToken = null, string patchJson = null) + { + init(); + + var method = new HttpMethod("PATCH"); + + var requestMessage = new HttpRequestMessage(method, CleanApiRoute(route)); + if (!string.IsNullOrWhiteSpace(authToken)) + requestMessage.Headers.Authorization = new AuthenticationHeaderValue("Bearer", authToken); + + if (!string.IsNullOrWhiteSpace(patchJson)) + requestMessage.Content = new StringContent(patchJson, System.Text.Encoding.UTF8, "application/json-patch+json"); + + HttpResponseMessage response = await client.SendAsync(requestMessage); + var responseAsString = await response.Content.ReadAsStringAsync(); + + return new ApiResponse() { HttpResponse = response, ObjectResponse = Parse(responseAsString) }; + } + + + public async static Task DeleteAsync(string route, string authToken = null) + { + init(); + + var requestMessage = new HttpRequestMessage(HttpMethod.Delete, CleanApiRoute(route)); + if (!string.IsNullOrWhiteSpace(authToken)) + requestMessage.Headers.Authorization = new AuthenticationHeaderValue("Bearer", authToken); + + HttpResponseMessage response = await client.SendAsync(requestMessage); + var responseAsString = await response.Content.ReadAsStringAsync(); + + return new ApiResponse() { HttpResponse = response, ObjectResponse = Parse(responseAsString) }; + } + + + + /// + /// + /// + /// + /// + public static JObject Parse(string jsonString) + { + if (string.IsNullOrWhiteSpace(jsonString)) + { + return null; + } + return JObject.Parse(jsonString); + } + + //https://www.newtonsoft.com/json/help/html/FromObject.htm + private static string ObjectToJsonString(object o) + { + JObject j = (JObject)JToken.FromObject(o); + return j.ToString(); + } + + public static void ValidateDataReturnResponseOk(ApiResponse a) + { + a.ObjectResponse.Should().NotBeNull("No response was found at all?! Nothing to validate"); + + var ErrorMessage = string.Empty; + var ERR = a.ObjectResponse["error"]; + if (ERR != null) + { + ErrorMessage = a.ObjectResponse.ToString(); + // var ecode = ERR["code"]; + // if (ecode != null) + // ErrorMessage += $"CODE: {ecode} "; + + // var emsg = ERR["message"]; + // if (emsg != null) + // ErrorMessage += $"MESSAGE: {emsg} "; + + // var etarget = ERR["target"]; + // if (etarget != null) + // ErrorMessage += $"TARGET: {etarget} "; + } + + a.ObjectResponse["error"].Should().BeNull("because there should not be an error on an api call, error result was: {0}", ErrorMessage); + a.ObjectResponse["data"].Should().NotBeNull("A result should be returned"); + } + + public static void ValidateNoErrorInResponse(ApiResponse a) + { + a.ObjectResponse["error"].Should().BeNull("There should not be an error on an api call"); + } + + public static void ValidateHTTPStatusCode(ApiResponse a, int DesiredStatusCode) + { + ((int)a.HttpResponse.StatusCode).Should().Be(DesiredStatusCode); + } + + public static void ValidateHTTPStatusCode(ApiTextResponse t, int DesiredStatusCode) + { + ((int)t.HttpResponse.StatusCode).Should().Be(DesiredStatusCode); + } + + /// + /// validate a not found response + /// + /// + public static void ValidateResponseNotFound(ApiResponse a) + { + ((int)a.HttpResponse.StatusCode).Should().Be(404); + a.ObjectResponse["error"].Should().NotBeNull("There should be an error on the api call"); + a.ObjectResponse["error"]["code"].Value().Should().Be(2010); + } + + + /// + /// validate a concurrency error + /// + /// + public static void ValidateConcurrencyError(ApiResponse a) + { + ((int)a.HttpResponse.StatusCode).Should().Be(409); + a.ObjectResponse["error"].Should().NotBeNull("There should be an error on the api call"); + //a.ObjectResponse["error"]["code"].Value().Should().Be(2005); + } + + + /// + /// validate that the call violates referential integrity + /// + /// + public static void ValidateViolatesReferentialIntegrityError(ApiResponse a) + { + ((int)a.HttpResponse.StatusCode).Should().Be(400); + a.ObjectResponse["error"].Should().NotBeNull("There should be an error on the api call"); + a.ObjectResponse["error"]["code"].Value().Should().Be(2200); + } + + + + /// + /// validate a bad ModelState response + /// + /// + public static void ValidateBadModelStateResponse(ApiResponse a, string CheckFirstTargetExists = null) + { + ((int)a.HttpResponse.StatusCode).Should().Be(400); + a.ObjectResponse["error"].Should().NotBeNull("There should be an error on the api call"); + a.ObjectResponse["error"]["code"].Value().Should().Be(2200); + a.ObjectResponse["error"]["details"].Should().NotBeNull("There should be error details on the api call"); + if (!string.IsNullOrWhiteSpace(CheckFirstTargetExists)) + { + a.ObjectResponse["error"]["details"][0]["target"].Value().Should().Be(CheckFirstTargetExists); + } + } + + + + + // public enum ValidationErrorType + // { + // RequiredPropertyEmpty = 1, + // LengthExceeded = 2, + // NotUnique = 3, + // StartDateMustComeBeforeEndDate = 4, + // InvalidValue = 5 + + // } + + /// + /// assert contains validation target and error code + /// + /// + /// + /// + public static void ShouldContainValidationError(ApiResponse a, string target, string error, string shouldContainInMessage = null) + { + a.ObjectResponse["error"]["details"].Should().NotBeNull("There should be Details on the api call"); + if (shouldContainInMessage != null) + { + a.ObjectResponse["error"]["details"].Should().Contain( + z => z["target"].Value() == target && + z["error"].Value() == error && + z["message"].Value().Contains(shouldContainInMessage)); + } + else + { + a.ObjectResponse["error"]["details"].Should().Contain(z => z["target"].Value() == target && z["error"].Value() == error); + } + } + + + /// + /// validate server exception response + /// + /// + public static void ValidateServerExceptionResponse(ApiResponse a) + { + ((int)a.HttpResponse.StatusCode).Should().Be(500); + a.ObjectResponse["error"].Should().NotBeNull("There should be an error on the api call"); + a.ObjectResponse["error"]["code"].Value().Should().Be(2002); + } + + + /// + /// Validate an expected api error code and http code response + /// + /// + /// + /// + public static void ValidateErrorCodeResponse(ApiResponse a, int apiErrorCode, int httpStatusCode) + { + ((int)a.HttpResponse.StatusCode).Should().Be(httpStatusCode); + a.ObjectResponse["error"].Should().NotBeNull("There should be an error on the api call"); + a.ObjectResponse["error"]["code"].Value().Should().Be(apiErrorCode); + } + + + public static string GenerateCustomFieldsJsonString( + string c1 = null, string c2 = null, string c3 = null, string c4 = null, + string c5 = null, string c6 = null, string c7 = null, string c8 = null, string c9 = null, + string c10 = null, string c11 = null, string c12 = null, string c13 = null, + string c14 = null, string c15 = null, string c16 = null + ) + { + + //Custom fields + //"[{c1:"blah"}] + dynamic dCustomField = new JObject(); + dCustomField.c1 = c1; + dCustomField.c2 = c2; + dCustomField.c3 = c3; + dCustomField.c4 = c4; + dCustomField.c5 = c5; + dCustomField.c6 = c6; + dCustomField.c7 = c7; + dCustomField.c8 = c8; + dCustomField.c9 = c9; + dCustomField.c10 = c10; + dCustomField.c11 = c11; + dCustomField.c12 = c12; + dCustomField.c13 = c13; + dCustomField.c14 = c14; + dCustomField.c15 = c15; + dCustomField.c16 = c16; + return dCustomField.ToString(); + } + + /// + /// Generate a custom fields string that satisfies the rules in the sample test data + /// + /// + public static string WidgetRequiredCustomFieldsJsonString() + {/*CURRENT TEMPLATE DEFINITION FOR WIDGET CUSTOM FIELDS, FROM SEEDER.CS SERVER PROJECT + var fc = new FormCustom() + { + FormKey = ObjectFields.WIDGET_KEY, + Template = @"[ + { + ""fld"": ""WidgetNotes"", + ""required"": true + }, + { + ""fld"": ""WidgetCustom1"", + ""required"": false, + ""type"": 1 + }, + { + ""fld"": ""WidgetCustom2"", + ""required"": true, + ""type"": 4 + }, + { + ""fld"": ""WidgetCustom3"", + ""required"": false, + ""type"": 5 + }, + { + ""fld"": ""WidgetCustom4"", + ""required"": false, + ""type"": 6 + }, + { + ""fld"": ""WidgetCustom5"", + ""required"": false, + ""type"": 8 + }, + { + ""fld"": ""WidgetCustom6"", + ""required"": false, + ""type"": 2 + }, + { + ""fld"": ""WidgetCustom7"", + ""required"": false, + ""type"": 3 + } + ]" + }; + */ + + //Custom fields + //"[{c1:"blah"}] + dynamic dCustomField = new JObject(); + dCustomField.c1 = "2019-02-08T06:31:48.0019809Z"; + dCustomField.c2 = "c2 text"; + dCustomField.c3 = "333"; + dCustomField.c4 = "true"; + dCustomField.c5 = "5.55"; + return dCustomField.ToString(); + } + + + + + /// + /// Generate a custom fields string that satisfies the rules in this project (formCustom) + /// + /// + public static string UserRequiredCustomFieldsJsonString() + { + //Note c1 is only required custom, c2 is defined but is not required so skipping it here + dynamic dCustomField = new JObject(); + dCustomField.c1 = "UnitTestUtilSampleText"; + return dCustomField.ToString(); + } + + //// [{fld:"COLUMN UNIQUE KEY ID",sort:"-" or "+",filter:{any:true/false,items:[{FILTER OBJECT SEE BELOW}]} }, {key:"second column unique key"},{...etc...}] + public static object BuildSimpleFilterDataListViewColumn(string fieldKey, string filterOp, object filterValue, string sort = null) + { + dynamic d = new JObject(); + d.fld = fieldKey; + if (sort != null) + d.sort = sort; + + dynamic filter = new JObject(); + dynamic items = new JArray(); + dynamic fitem = new JObject(); + fitem.op = filterOp; + fitem.value = filterValue; + items.Add(fitem); + filter.items = items; + d.filter = filter; + return d; + + } + + + + public static object BuildSimpleSortDataListViewColumn(string fieldKey, string sort) + { + dynamic d = new JObject(); + d.fld = fieldKey; + d.sort = sort; + return d; + } + //t(dfilter, dsortarray, 999, 0, false, "UserDataList")); + // public static string BuildDataListRequest(object p = null, object o = null, int limit = 999, int offset = 0, bool bWhatever=false, string dataListKey = "TestWidgetDataList") + // { + // throw new System.NotImplementedException(); + // } + + public static string BuildDataListRequestEx(dynamic dListView = null, int limit = 999, int offset = 0, string dataListKey = "TestWidgetDataList") + { + /* + { + "offset": 0, + "limit": 3, + "dataListKey": "TestWidgetDataList", + "listView": "" + } + */ + dynamic d = new JObject(); + d.offset = offset; + d.limit = limit; + + d.dataListKey = dataListKey; + if (dListView != null) + d.ListView = dListView.ToString(Newtonsoft.Json.Formatting.None); + + return d.ToString(Newtonsoft.Json.Formatting.None); + + + } + + + + + + //--------- + + }//eoc +}//eons