mirror of https://github.com/Squidex/squidex.git
committed by
GitHub
25 changed files with 729 additions and 121 deletions
@ -0,0 +1,136 @@ |
|||||
|
// ==========================================================================
|
||||
|
// Squidex Headless CMS
|
||||
|
// ==========================================================================
|
||||
|
// Copyright (c) Squidex UG (haftungsbeschraenkt)
|
||||
|
// All rights reserved. Licensed under the MIT license.
|
||||
|
// ==========================================================================
|
||||
|
|
||||
|
using System; |
||||
|
using System.Collections.Generic; |
||||
|
using System.Threading.Tasks; |
||||
|
using MongoDB.Bson; |
||||
|
using MongoDB.Driver; |
||||
|
using Newtonsoft.Json; |
||||
|
using Squidex.Domain.Apps.Core.Assets; |
||||
|
using Squidex.Domain.Apps.Entities.Assets.Repositories; |
||||
|
using Squidex.Domain.Apps.Entities.MongoDb.Assets; |
||||
|
using Squidex.Domain.Apps.Entities.TestHelpers; |
||||
|
using Squidex.Infrastructure; |
||||
|
using Squidex.Infrastructure.Json.Objects; |
||||
|
using Squidex.Infrastructure.MongoDb; |
||||
|
|
||||
|
namespace Squidex.Domain.Apps.Entities.Assets.MongoDb |
||||
|
{ |
||||
|
public sealed class AssetsQueryFixture |
||||
|
{ |
||||
|
private readonly Random random = new Random(); |
||||
|
private readonly int numValues = 250; |
||||
|
private readonly IMongoClient mongoClient = new MongoClient("mongodb://localhost"); |
||||
|
private readonly IMongoDatabase mongoDatabase; |
||||
|
|
||||
|
public IAssetRepository AssetRepository { get; } |
||||
|
|
||||
|
public NamedId<Guid>[] AppIds { get; } = new[] |
||||
|
{ |
||||
|
NamedId.Of(Guid.Parse("3b5ba909-e5a5-4858-9d0d-df4ff922d452"), "my-app1"), |
||||
|
NamedId.Of(Guid.Parse("4b3672c1-97c6-4e0b-a067-71e9e9a29db9"), "my-app1") |
||||
|
}; |
||||
|
|
||||
|
public AssetsQueryFixture() |
||||
|
{ |
||||
|
mongoDatabase = mongoClient.GetDatabase("QueryTests"); |
||||
|
|
||||
|
SetupJson(); |
||||
|
|
||||
|
var assetRepository = new MongoAssetRepository(mongoDatabase); |
||||
|
|
||||
|
Task.Run(async () => |
||||
|
{ |
||||
|
await assetRepository.InitializeAsync(); |
||||
|
|
||||
|
await mongoDatabase.RunCommandAsync<BsonDocument>("{ profile : 0 }"); |
||||
|
await mongoDatabase.DropCollectionAsync("system.profile"); |
||||
|
|
||||
|
var collection = assetRepository.GetInternalCollection(); |
||||
|
|
||||
|
var assetCount = await collection.Find(new BsonDocument()).CountDocumentsAsync(); |
||||
|
|
||||
|
if (assetCount == 0) |
||||
|
{ |
||||
|
var batch = new List<MongoAssetEntity>(); |
||||
|
|
||||
|
async Task ExecuteBatchAsync(MongoAssetEntity? entity) |
||||
|
{ |
||||
|
if (entity != null) |
||||
|
{ |
||||
|
batch.Add(entity); |
||||
|
} |
||||
|
|
||||
|
if ((entity == null || batch.Count >= 1000) && batch.Count > 0) |
||||
|
{ |
||||
|
await collection.InsertManyAsync(batch); |
||||
|
|
||||
|
batch.Clear(); |
||||
|
} |
||||
|
} |
||||
|
|
||||
|
foreach (var appId in AppIds) |
||||
|
{ |
||||
|
for (var i = 0; i < numValues; i++) |
||||
|
{ |
||||
|
var fileName = i.ToString(); |
||||
|
|
||||
|
for (var j = 0; j < numValues; j++) |
||||
|
{ |
||||
|
var tag = j.ToString(); |
||||
|
|
||||
|
var asset = new MongoAssetEntity |
||||
|
{ |
||||
|
Id = Guid.NewGuid(), |
||||
|
AppId = appId, |
||||
|
Tags = new HashSet<string> { tag }, |
||||
|
FileHash = fileName, |
||||
|
FileName = fileName, |
||||
|
FileSize = 1024, |
||||
|
IndexedAppId = appId.Id, |
||||
|
IsDeleted = false, |
||||
|
IsProtected = false, |
||||
|
Metadata = new AssetMetadata |
||||
|
{ |
||||
|
["value"] = JsonValue.Create(tag) |
||||
|
}, |
||||
|
Slug = fileName, |
||||
|
}; |
||||
|
|
||||
|
await ExecuteBatchAsync(asset); |
||||
|
} |
||||
|
} |
||||
|
} |
||||
|
|
||||
|
await ExecuteBatchAsync(null); |
||||
|
} |
||||
|
|
||||
|
await mongoDatabase.RunCommandAsync<BsonDocument>("{ profile : 2 }"); |
||||
|
}).Wait(); |
||||
|
|
||||
|
AssetRepository = assetRepository; |
||||
|
} |
||||
|
|
||||
|
private static void SetupJson() |
||||
|
{ |
||||
|
var jsonSerializer = JsonSerializer.Create(JsonHelper.DefaultSettings()); |
||||
|
|
||||
|
BsonJsonConvention.Register(jsonSerializer); |
||||
|
} |
||||
|
|
||||
|
public Guid RandomAppId() |
||||
|
{ |
||||
|
return AppIds[random.Next(0, AppIds.Length)].Id; |
||||
|
} |
||||
|
|
||||
|
public string RandomValue() |
||||
|
{ |
||||
|
return random.Next(0, numValues).ToString(); |
||||
|
} |
||||
|
} |
||||
|
} |
||||
@ -0,0 +1,146 @@ |
|||||
|
// ==========================================================================
|
||||
|
// Squidex Headless CMS
|
||||
|
// ==========================================================================
|
||||
|
// Copyright (c) Squidex UG (haftungsbeschraenkt)
|
||||
|
// All rights reserved. Licensed under the MIT license.
|
||||
|
// ==========================================================================
|
||||
|
|
||||
|
using System; |
||||
|
using System.Collections.Generic; |
||||
|
using System.Linq; |
||||
|
using System.Threading.Tasks; |
||||
|
using Squidex.Infrastructure; |
||||
|
using Squidex.Infrastructure.Queries; |
||||
|
using Xunit; |
||||
|
using F = Squidex.Infrastructure.Queries.ClrFilter; |
||||
|
|
||||
|
#pragma warning disable SA1300 // Element should begin with upper-case letter
|
||||
|
|
||||
|
namespace Squidex.Domain.Apps.Entities.Assets.MongoDb |
||||
|
{ |
||||
|
[Trait("Category", "Dependencies")] |
||||
|
public class AssetsQueryTests : IClassFixture<AssetsQueryFixture> |
||||
|
{ |
||||
|
public AssetsQueryFixture _ { get; } |
||||
|
|
||||
|
public AssetsQueryTests(AssetsQueryFixture fixture) |
||||
|
{ |
||||
|
_ = fixture; |
||||
|
} |
||||
|
|
||||
|
[Fact] |
||||
|
public async Task Should_find_asset_by_slug() |
||||
|
{ |
||||
|
var asset = await _.AssetRepository.FindAssetBySlugAsync(_.RandomAppId(), _.RandomValue()); |
||||
|
|
||||
|
Assert.NotNull(asset); |
||||
|
} |
||||
|
|
||||
|
[Fact] |
||||
|
public async Task Should_query_asset_by_hash() |
||||
|
{ |
||||
|
var assets = await _.AssetRepository.QueryByHashAsync(_.RandomAppId(), _.RandomValue()); |
||||
|
|
||||
|
Assert.NotNull(assets); |
||||
|
} |
||||
|
|
||||
|
[Fact] |
||||
|
public async Task Should_verify_ids() |
||||
|
{ |
||||
|
var ids = Enumerable.Repeat(0, 50).Select(_ => Guid.NewGuid()).ToHashSet(); |
||||
|
|
||||
|
var assets = await _.AssetRepository.QueryIdsAsync(_.RandomAppId(), ids); |
||||
|
|
||||
|
Assert.NotNull(assets); |
||||
|
} |
||||
|
|
||||
|
[Theory] |
||||
|
[MemberData(nameof(ParentIds))] |
||||
|
public async Task Should_query_assets_by_default(Guid? parentId) |
||||
|
{ |
||||
|
var query = new ClrQuery(); |
||||
|
|
||||
|
var assets = await QueryAsync(parentId, query); |
||||
|
|
||||
|
Assert.NotNull(assets); |
||||
|
} |
||||
|
|
||||
|
[Theory] |
||||
|
[MemberData(nameof(ParentIds))] |
||||
|
public async Task Should_query_assets_by_tags(Guid? parentId) |
||||
|
{ |
||||
|
var query = new ClrQuery |
||||
|
{ |
||||
|
Filter = F.Eq("Tags", _.RandomValue()) |
||||
|
}; |
||||
|
|
||||
|
var assets = await QueryAsync(parentId, query); |
||||
|
|
||||
|
Assert.NotNull(assets); |
||||
|
} |
||||
|
|
||||
|
[Theory] |
||||
|
[MemberData(nameof(ParentIds))] |
||||
|
public async Task Should_query_assets_by_tags_and_name(Guid? parentId) |
||||
|
{ |
||||
|
var query = new ClrQuery |
||||
|
{ |
||||
|
Filter = F.And(F.Eq("Tags", _.RandomValue()), F.Contains("FileName", _.RandomValue())) |
||||
|
}; |
||||
|
|
||||
|
var assets = await QueryAsync(parentId, query); |
||||
|
|
||||
|
Assert.NotNull(assets); |
||||
|
} |
||||
|
|
||||
|
[Theory] |
||||
|
[MemberData(nameof(ParentIds))] |
||||
|
public async Task Should_query_assets_by_fileName(Guid? parentId) |
||||
|
{ |
||||
|
var query = new ClrQuery |
||||
|
{ |
||||
|
Filter = F.Contains("FileName", _.RandomValue()) |
||||
|
}; |
||||
|
|
||||
|
var assets = await QueryAsync(parentId, query); |
||||
|
|
||||
|
Assert.NotNull(assets); |
||||
|
} |
||||
|
|
||||
|
[Theory] |
||||
|
[MemberData(nameof(ParentIds))] |
||||
|
public async Task Should_query_assets_by_fileName_and_tags(Guid? parentId) |
||||
|
{ |
||||
|
var query = new ClrQuery |
||||
|
{ |
||||
|
Filter = F.And(F.Contains("FileName", _.RandomValue()), F.Eq("Tags", _.RandomValue())) |
||||
|
}; |
||||
|
|
||||
|
var assets = await QueryAsync(parentId, query); |
||||
|
|
||||
|
Assert.NotNull(assets); |
||||
|
} |
||||
|
|
||||
|
public static IEnumerable<object?[]> ParentIds() |
||||
|
{ |
||||
|
yield return new object?[] { null }; |
||||
|
yield return new object?[] { Guid.Empty }; |
||||
|
} |
||||
|
|
||||
|
private async Task<IResultList<IAssetEntity>> QueryAsync(Guid? parentId, ClrQuery query) |
||||
|
{ |
||||
|
query.Top = 1000; |
||||
|
|
||||
|
query.Skip = 100; |
||||
|
|
||||
|
query.Sort = new List<SortNode> |
||||
|
{ |
||||
|
new SortNode("LastModified", SortOrder.Descending) |
||||
|
}; |
||||
|
|
||||
|
var assets = await _.AssetRepository.QueryAsync(_.RandomAppId(), parentId, query); |
||||
|
|
||||
|
return assets; |
||||
|
} |
||||
|
} |
||||
|
} |
||||
@ -0,0 +1,211 @@ |
|||||
|
// ==========================================================================
|
||||
|
// Squidex Headless CMS
|
||||
|
// ==========================================================================
|
||||
|
// Copyright (c) Squidex UG (haftungsbeschraenkt)
|
||||
|
// All rights reserved. Licensed under the MIT license.
|
||||
|
// ==========================================================================
|
||||
|
|
||||
|
using System; |
||||
|
using System.Collections.Generic; |
||||
|
using System.Threading.Tasks; |
||||
|
using FakeItEasy; |
||||
|
using MongoDB.Bson; |
||||
|
using MongoDB.Driver; |
||||
|
using Newtonsoft.Json; |
||||
|
using Squidex.Domain.Apps.Core; |
||||
|
using Squidex.Domain.Apps.Core.Contents; |
||||
|
using Squidex.Domain.Apps.Core.Schemas; |
||||
|
using Squidex.Domain.Apps.Entities.Apps; |
||||
|
using Squidex.Domain.Apps.Entities.Contents.Repositories; |
||||
|
using Squidex.Domain.Apps.Entities.Contents.Text; |
||||
|
using Squidex.Domain.Apps.Entities.MongoDb.Contents; |
||||
|
using Squidex.Domain.Apps.Entities.Schemas; |
||||
|
using Squidex.Domain.Apps.Entities.TestHelpers; |
||||
|
using Squidex.Infrastructure; |
||||
|
using Squidex.Infrastructure.Json.Objects; |
||||
|
using Squidex.Infrastructure.MongoDb; |
||||
|
|
||||
|
namespace Squidex.Domain.Apps.Entities.Contents.MongoDb |
||||
|
{ |
||||
|
public sealed class ContentsQueryFixture |
||||
|
{ |
||||
|
private readonly Random random = new Random(); |
||||
|
private readonly int numValues = 10000; |
||||
|
private readonly IMongoClient mongoClient = new MongoClient("mongodb://localhost"); |
||||
|
private readonly IMongoDatabase mongoDatabase; |
||||
|
|
||||
|
public IContentRepository ContentRepository { get; } |
||||
|
|
||||
|
public NamedId<Guid>[] AppIds { get; } = new[] |
||||
|
{ |
||||
|
NamedId.Of(Guid.Parse("3b5ba909-e5a5-4858-9d0d-df4ff922d452"), "my-app1"), |
||||
|
NamedId.Of(Guid.Parse("4b3672c1-97c6-4e0b-a067-71e9e9a29db9"), "my-app1") |
||||
|
}; |
||||
|
|
||||
|
public NamedId<Guid>[] SchemaIds { get; } = new[] |
||||
|
{ |
||||
|
NamedId.Of(Guid.Parse("3b5ba909-e5a5-4858-9d0d-df4ff922d452"), "my-schema1"), |
||||
|
NamedId.Of(Guid.Parse("4b3672c1-97c6-4e0b-a067-71e9e9a29db9"), "my-schema2"), |
||||
|
NamedId.Of(Guid.Parse("76357c9b-0514-4377-9fcc-a632e7ef960d"), "my-schema3"), |
||||
|
NamedId.Of(Guid.Parse("164c451e-e5a8-41f8-8aaf-e4b56603d7e7"), "my-schema4"), |
||||
|
NamedId.Of(Guid.Parse("741e902c-fdfa-41ad-8e5a-b7cb9d6e3d94"), "my-schema5") |
||||
|
}; |
||||
|
|
||||
|
public ContentsQueryFixture() |
||||
|
{ |
||||
|
mongoDatabase = mongoClient.GetDatabase("QueryTests"); |
||||
|
|
||||
|
SetupJson(); |
||||
|
|
||||
|
var contentRepository = |
||||
|
new MongoContentRepository( |
||||
|
mongoDatabase, |
||||
|
CreateAppProvider(), |
||||
|
CreateTextIndexer(), |
||||
|
JsonHelper.DefaultSerializer); |
||||
|
|
||||
|
Task.Run(async () => |
||||
|
{ |
||||
|
await contentRepository.InitializeAsync(); |
||||
|
|
||||
|
await mongoDatabase.RunCommandAsync<BsonDocument>("{ profile : 0 }"); |
||||
|
await mongoDatabase.DropCollectionAsync("system.profile"); |
||||
|
|
||||
|
var collection = contentRepository.GetInternalCollection(); |
||||
|
|
||||
|
var contentCount = await collection.Find(new BsonDocument()).CountDocumentsAsync(); |
||||
|
|
||||
|
if (contentCount == 0) |
||||
|
{ |
||||
|
var batch = new List<MongoContentEntity>(); |
||||
|
|
||||
|
async Task ExecuteBatchAsync(MongoContentEntity? entity) |
||||
|
{ |
||||
|
if (entity != null) |
||||
|
{ |
||||
|
batch.Add(entity); |
||||
|
} |
||||
|
|
||||
|
if ((entity == null || batch.Count >= 1000) && batch.Count > 0) |
||||
|
{ |
||||
|
await collection.InsertManyAsync(batch); |
||||
|
|
||||
|
batch.Clear(); |
||||
|
} |
||||
|
} |
||||
|
|
||||
|
foreach (var appId in AppIds) |
||||
|
{ |
||||
|
foreach (var schemaId in SchemaIds) |
||||
|
{ |
||||
|
for (var i = 0; i < numValues; i++) |
||||
|
{ |
||||
|
var value = i.ToString(); |
||||
|
|
||||
|
var data = |
||||
|
new IdContentData() |
||||
|
.AddField(1, |
||||
|
new ContentFieldData() |
||||
|
.AddJsonValue(JsonValue.Create(value))); |
||||
|
|
||||
|
var content = new MongoContentEntity |
||||
|
{ |
||||
|
Id = Guid.NewGuid(), |
||||
|
AppId = appId, |
||||
|
DataByIds = data, |
||||
|
DataDraftByIds = data, |
||||
|
IndexedAppId = appId.Id, |
||||
|
IndexedSchemaId = schemaId.Id, |
||||
|
IsDeleted = false, |
||||
|
IsPending = false, |
||||
|
SchemaId = schemaId, |
||||
|
Status = Status.Published |
||||
|
}; |
||||
|
|
||||
|
await ExecuteBatchAsync(content); |
||||
|
} |
||||
|
} |
||||
|
} |
||||
|
|
||||
|
await ExecuteBatchAsync(null); |
||||
|
} |
||||
|
|
||||
|
await mongoDatabase.RunCommandAsync<BsonDocument>("{ profile : 2 }"); |
||||
|
}).Wait(); |
||||
|
|
||||
|
ContentRepository = contentRepository; |
||||
|
} |
||||
|
|
||||
|
private static IAppProvider CreateAppProvider() |
||||
|
{ |
||||
|
var appProvider = A.Fake<IAppProvider>(); |
||||
|
|
||||
|
A.CallTo(() => appProvider.GetSchemaAsync(A<Guid>.Ignored, A<Guid>.Ignored, false)) |
||||
|
.ReturnsLazily(x => Task.FromResult<ISchemaEntity?>(CreateSchema(x.GetArgument<Guid>(0)!, x.GetArgument<Guid>(1)!))); |
||||
|
|
||||
|
return appProvider; |
||||
|
} |
||||
|
|
||||
|
private static ITextIndexer CreateTextIndexer() |
||||
|
{ |
||||
|
var textIndexer = A.Fake<ITextIndexer>(); |
||||
|
|
||||
|
A.CallTo(() => textIndexer.SearchAsync(A<string>.Ignored, A<IAppEntity>.Ignored, A<Guid>.Ignored, A<Scope>.Ignored)) |
||||
|
.Returns(new List<Guid> { Guid.NewGuid() }); |
||||
|
|
||||
|
return textIndexer; |
||||
|
} |
||||
|
|
||||
|
private static void SetupJson() |
||||
|
{ |
||||
|
var jsonSerializer = JsonSerializer.Create(JsonHelper.DefaultSettings()); |
||||
|
|
||||
|
BsonJsonConvention.Register(jsonSerializer); |
||||
|
} |
||||
|
|
||||
|
public Guid RandomAppId() |
||||
|
{ |
||||
|
return AppIds[random.Next(0, AppIds.Length)].Id; |
||||
|
} |
||||
|
|
||||
|
public IAppEntity RandomApp() |
||||
|
{ |
||||
|
return CreateApp(RandomAppId()); |
||||
|
} |
||||
|
|
||||
|
public Guid RandomSchemaId() |
||||
|
{ |
||||
|
return SchemaIds[random.Next(0, SchemaIds.Length)].Id; |
||||
|
} |
||||
|
|
||||
|
public ISchemaEntity RandomSchema() |
||||
|
{ |
||||
|
return CreateSchema(RandomAppId(), RandomSchemaId()); |
||||
|
} |
||||
|
|
||||
|
public string RandomValue() |
||||
|
{ |
||||
|
return random.Next(0, numValues).ToString(); |
||||
|
} |
||||
|
|
||||
|
private static IAppEntity CreateApp(Guid appId) |
||||
|
{ |
||||
|
return Mocks.App(NamedId.Of(appId, "my-app")); |
||||
|
} |
||||
|
|
||||
|
private static ISchemaEntity CreateSchema(Guid appId, Guid schemaId) |
||||
|
{ |
||||
|
var schemaDef = |
||||
|
new Schema("my-schema") |
||||
|
.AddField(Fields.String(1, "value", Partitioning.Invariant)); |
||||
|
|
||||
|
var schema = |
||||
|
Mocks.Schema( |
||||
|
NamedId.Of(appId, "my-app"), |
||||
|
NamedId.Of(schemaId, "my-schema"), |
||||
|
schemaDef); |
||||
|
|
||||
|
return schema; |
||||
|
} |
||||
|
} |
||||
|
} |
||||
@ -0,0 +1,143 @@ |
|||||
|
// ==========================================================================
|
||||
|
// Squidex Headless CMS
|
||||
|
// ==========================================================================
|
||||
|
// Copyright (c) Squidex UG (haftungsbeschraenkt)
|
||||
|
// All rights reserved. Licensed under the MIT license.
|
||||
|
// ==========================================================================
|
||||
|
|
||||
|
using System; |
||||
|
using System.Collections.Generic; |
||||
|
using System.Linq; |
||||
|
using System.Threading.Tasks; |
||||
|
using NodaTime; |
||||
|
using Squidex.Domain.Apps.Core.Contents; |
||||
|
using Squidex.Infrastructure; |
||||
|
using Squidex.Infrastructure.Queries; |
||||
|
using Squidex.Infrastructure.Tasks; |
||||
|
using Xunit; |
||||
|
using F = Squidex.Infrastructure.Queries.ClrFilter; |
||||
|
|
||||
|
#pragma warning disable SA1300 // Element should begin with upper-case letter
|
||||
|
|
||||
|
namespace Squidex.Domain.Apps.Entities.Contents.MongoDb |
||||
|
{ |
||||
|
[Trait("Category", "Dependencies")] |
||||
|
public class ContentsQueryTests : IClassFixture<ContentsQueryFixture> |
||||
|
{ |
||||
|
public ContentsQueryFixture _ { get; } |
||||
|
|
||||
|
public ContentsQueryTests(ContentsQueryFixture fixture) |
||||
|
{ |
||||
|
_ = fixture; |
||||
|
} |
||||
|
|
||||
|
[Fact] |
||||
|
public async Task Should_verify_ids() |
||||
|
{ |
||||
|
var ids = Enumerable.Repeat(0, 50).Select(_ => Guid.NewGuid()).ToHashSet(); |
||||
|
|
||||
|
var contents = await _.ContentRepository.QueryIdsAsync(_.RandomAppId(), ids); |
||||
|
|
||||
|
Assert.NotNull(contents); |
||||
|
} |
||||
|
|
||||
|
[Fact] |
||||
|
public async Task Should_query_contents_by_ids() |
||||
|
{ |
||||
|
var ids = Enumerable.Repeat(0, 50).Select(_ => Guid.NewGuid()).ToHashSet(); |
||||
|
|
||||
|
var contents = await _.ContentRepository.QueryAsync(_.RandomApp(), new[] { Status.Published }, ids, true); |
||||
|
|
||||
|
Assert.NotNull(contents); |
||||
|
} |
||||
|
|
||||
|
[Fact] |
||||
|
public async Task Should_query_contents_by_ids_and_schema() |
||||
|
{ |
||||
|
var ids = Enumerable.Repeat(0, 50).Select(_ => Guid.NewGuid()).ToHashSet(); |
||||
|
|
||||
|
var contents = await _.ContentRepository.QueryAsync(_.RandomApp(), _.RandomSchema(), new[] { Status.Published }, ids, true); |
||||
|
|
||||
|
Assert.NotNull(contents); |
||||
|
} |
||||
|
|
||||
|
[Fact] |
||||
|
public async Task Should_query_contents_by_filter() |
||||
|
{ |
||||
|
var filter = F.Eq("data.value.iv", _.RandomValue()); |
||||
|
|
||||
|
var contents = await _.ContentRepository.QueryIdsAsync(_.RandomAppId(), _.RandomSchemaId(), filter); |
||||
|
|
||||
|
Assert.NotNull(contents); |
||||
|
} |
||||
|
|
||||
|
[Fact] |
||||
|
public async Task Should_query_contents_scheduled() |
||||
|
{ |
||||
|
var time = SystemClock.Instance.GetCurrentInstant(); |
||||
|
|
||||
|
await _.ContentRepository.QueryScheduledWithoutDataAsync(time, _ => TaskHelper.Done); |
||||
|
} |
||||
|
|
||||
|
[Theory] |
||||
|
[MemberData(nameof(Statuses))] |
||||
|
public async Task Should_query_contents_by_default(Status[]? status) |
||||
|
{ |
||||
|
var query = new ClrQuery(); |
||||
|
|
||||
|
var contents = await QueryAsync(status, query); |
||||
|
|
||||
|
Assert.NotNull(contents); |
||||
|
} |
||||
|
|
||||
|
[Theory] |
||||
|
[MemberData(nameof(Statuses))] |
||||
|
public async Task Should_query_contents_with_query_fulltext(Status[]? status) |
||||
|
{ |
||||
|
var query = new ClrQuery |
||||
|
{ |
||||
|
FullText = "hello" |
||||
|
}; |
||||
|
|
||||
|
var contents = await QueryAsync(status, query); |
||||
|
|
||||
|
Assert.NotNull(contents); |
||||
|
} |
||||
|
|
||||
|
[Theory] |
||||
|
[MemberData(nameof(Statuses))] |
||||
|
public async Task Should_query_contents_with_query_filter(Status[]? status) |
||||
|
{ |
||||
|
var query = new ClrQuery |
||||
|
{ |
||||
|
Filter = F.Eq("data.value.iv", _.RandomValue()) |
||||
|
}; |
||||
|
|
||||
|
var contents = await QueryAsync(status, query); |
||||
|
|
||||
|
Assert.NotNull(contents); |
||||
|
} |
||||
|
|
||||
|
public static IEnumerable<object?[]> Statuses() |
||||
|
{ |
||||
|
yield return new object?[] { null }; |
||||
|
yield return new object?[] { new[] { Status.Published } }; |
||||
|
} |
||||
|
|
||||
|
private async Task<IResultList<IContentEntity>> QueryAsync(Status[]? status, ClrQuery query) |
||||
|
{ |
||||
|
query.Top = 1000; |
||||
|
|
||||
|
query.Skip = 100; |
||||
|
|
||||
|
query.Sort = new List<SortNode> |
||||
|
{ |
||||
|
new SortNode("LastModified", SortOrder.Descending) |
||||
|
}; |
||||
|
|
||||
|
var contents = await _.ContentRepository.QueryAsync(_.RandomApp(), _.RandomSchema(), status, true, query, true); |
||||
|
|
||||
|
return contents; |
||||
|
} |
||||
|
} |
||||
|
} |
||||
Loading…
Reference in new issue