示例#1
0
        private async Task <ClrQuery> ParseClrQueryAsync(Context context, Q q, ISchemaEntity?schema)
        {
            var components = ResolvedComponents.Empty;

            if (schema != null)
            {
                components = await appprovider.GetComponentsAsync(schema);
            }

            var query = q.Query;

            if (!string.IsNullOrWhiteSpace(q.QueryAsJson))
            {
                query = ParseJson(context, schema, q.QueryAsJson, components);
            }
            else if (q?.JsonQuery != null)
            {
                query = ParseJson(context, schema, q.JsonQuery, components);
            }
            else if (!string.IsNullOrWhiteSpace(q?.QueryAsOdata))
            {
                query = ParseOData(context, schema, q.QueryAsOdata, components);
            }

            return(query);
        }
        private ClrQuery ParseJson(Context context, ISchemaEntity?schema, Query <IJsonValue> query,
                                   ResolvedComponents components)
        {
            var jsonSchema = BuildJsonSchema(context, schema, components);

            return(jsonSchema.Convert(query));
        }
示例#3
0
        private ClrQuery ParseJson(Context context, ISchemaEntity?schema, Query <IJsonValue> query,
                                   ResolvedComponents components)
        {
            var queryModel = BuildQueryModel(context, schema, components);

            return(queryModel.Convert(query));
        }
示例#4
0
        private ClrQuery ParseOData(Context context, ISchemaEntity?schema, string odata,
                                    ResolvedComponents components)
        {
            try
            {
                var model = BuildEdmModel(context, schema, components);

                return(model.ParseQuery(odata).ToQuery());
            }
            catch (ValidationException)
            {
                throw;
            }
            catch (NotSupportedException)
            {
                throw new ValidationException(T.Get("common.odataNotSupported", new { odata }));
            }
            catch (ODataException ex)
            {
                var message = ex.Message;

                throw new ValidationException(T.Get("common.odataFailure", new { odata, message }), ex);
            }
            catch (Exception)
            {
                throw new ValidationException(T.Get("common.odataNotSupported", new { odata }));
            }
        }
示例#5
0
        private ClrQuery ParseJson(Context context, ISchemaEntity?schema, string json,
                                   ResolvedComponents components)
        {
            var queryModel = BuildQueryModel(context, schema, components);

            return(queryModel.Parse(json, jsonSerializer));
        }
示例#6
0
        public async Task <ISchemaEntity?> GetSchemaAsync(Context context, string schemaIdOrName)
        {
            Guard.NotNull(context, nameof(context));
            Guard.NotNullOrEmpty(schemaIdOrName, nameof(schemaIdOrName));

            ISchemaEntity?schema = null;

            var canCache = !context.IsFrontendClient;

            if (Guid.TryParse(schemaIdOrName, out var guid))
            {
                var schemaId = DomainId.Create(guid);

                schema = await appProvider.GetSchemaAsync(context.App.Id, schemaId, canCache);
            }

            if (schema == null)
            {
                schema = await appProvider.GetSchemaAsync(context.App.Id, schemaIdOrName, canCache);
            }

            if (schema != null && !HasPermission(context, schema, Permissions.AppContentsReadOwn))
            {
                throw new DomainForbiddenException(T.Get("schemas.noPermission"));
            }

            return(schema);
        }
        public async Task <ISchemaEntity> GetSchemaOrThrowAsync(Context context, string schemaIdOrName)
        {
            ISchemaEntity?schema = null;

            var canCache = !context.IsFrontendClient;

            if (Guid.TryParse(schemaIdOrName, out var guid))
            {
                var schemaId = DomainId.Create(guid);

                schema = await appProvider.GetSchemaAsync(context.App.Id, schemaId, false, canCache);
            }

            if (schema == null)
            {
                schema = await appProvider.GetSchemaAsync(context.App.Id, schemaIdOrName, canCache);
            }

            if (schema == null)
            {
                throw new DomainObjectNotFoundException(schemaIdOrName);
            }

            return(schema);
        }
示例#8
0
        private static string BuildJsonCacheKey(IAppEntity app, ISchemaEntity?schema, bool withHidden)
        {
            if (schema == null)
            {
                return($"JSON/__generic");
            }

            return($"JSON/{app.Version}/{schema.Id}_{schema.Version}/{withHidden}");
        }
示例#9
0
        private QueryModel BuildQueryModel(Context context, ISchemaEntity?schema,
                                           ResolvedComponents components)
        {
            var cacheKey = BuildJsonCacheKey(context.App, schema, context.IsFrontendClient);

            var result = cache.GetOrCreate(cacheKey, entry =>
            {
                entry.AbsoluteExpirationRelativeToNow = CacheTime;

                return(ContentQueryModel.Build(schema?.SchemaDef, context.App.PartitionResolver(), components));
            });

            return(result);
        }
示例#10
0
        private IEdmModel BuildEdmModel(Context context, ISchemaEntity?schema,
                                        ResolvedComponents components)
        {
            var cacheKey = BuildEmdCacheKey(context.App, schema, context.IsFrontendClient);

            var result = cache.GetOrCreate <IEdmModel>(cacheKey, entry =>
            {
                entry.AbsoluteExpirationRelativeToNow = CacheTime;

                return(BuildQueryModel(context, schema, components).ConvertToEdm("Contents", schema?.SchemaDef.Name ?? "Generic"));
            });

            return(result);
        }
示例#11
0
        public virtual ValueTask <Q> ParseAsync(Context context, Q q, ISchemaEntity?schema = null)
        {
            Guard.NotNull(context, nameof(context));
            Guard.NotNull(q, nameof(q));

            using (Profiler.TraceMethod <ContentQueryParser>())
            {
                var query = q.Query;

                if (!string.IsNullOrWhiteSpace(q.JsonQueryString))
                {
                    query = ParseJson(context, schema, q.JsonQueryString);
                }
                else if (q?.JsonQuery != null)
                {
                    query = ParseJson(context, schema, q.JsonQuery);
                }
                else if (!string.IsNullOrWhiteSpace(q?.ODataQuery))
                {
                    query = ParseOData(context, schema, q.ODataQuery);
                }

                if (query.Sort.Count == 0)
                {
                    query.Sort.Add(new SortNode(new List <string> {
                        "lastModified"
                    }, SortOrder.Descending));
                }

                if (!query.Sort.Any(x => string.Equals(x.Path.ToString(), "id", StringComparison.OrdinalIgnoreCase)))
                {
                    query.Sort.Add(new SortNode(new List <string> {
                        "id"
                    }, SortOrder.Ascending));
                }

                if (query.Take == long.MaxValue)
                {
                    query.Take = options.DefaultPageSize;
                }
                else if (query.Take > options.MaxResults)
                {
                    query.Take = options.MaxResults;
                }

                q = q !.WithQuery(query);

                return(new ValueTask <Q>(q));
            }
        }
示例#12
0
        private IEdmModel BuildEdmModel(Context context, ISchemaEntity?schema)
        {
            if (schema == null)
            {
                return(genericEdmModel);
            }

            var cacheKey = BuildEmdCacheKey(context.App, schema, context.IsFrontendClient);

            var result = cache.GetOrCreate <IEdmModel>(cacheKey, entry =>
            {
                entry.AbsoluteExpirationRelativeToNow = CacheTime;

                return(BuildEdmModel(schema.SchemaDef, context.App, context.IsFrontendClient));
            });

            return(result);
        }
示例#13
0
        public static async Task <ContentsDto> FromContentsAsync(IResultList <IEnrichedContentEntity> contents, Resources resources,
                                                                 ISchemaEntity?schema, IContentWorkflow workflow)
        {
            var result = new ContentsDto
            {
                Total = contents.Total,
                Items = contents.Select(x => ContentDto.FromDomain(x, resources)).ToArray()
            };

            if (schema != null)
            {
                await result.AssignStatusesAsync(workflow, schema);

                await result.CreateLinksAsync(resources, workflow, schema);
            }

            return(result);
        }
示例#14
0
        public static async Task <ContentsDto> FromContentsAsync(IResultList <IEnrichedContentEntity> contents, Context context, ApiController controller,
                                                                 ISchemaEntity?schema, IContentWorkflow workflow)
        {
            var result = new ContentsDto
            {
                Total = contents.Total,
                Items = contents.Select(x => ContentDto.FromContent(context, x, controller)).ToArray()
            };

            if (schema != null)
            {
                await result.AssignStatusesAsync(workflow, schema);

                result.CreateLinks(controller, schema.AppId.Name, schema.SchemaDef.Name);
            }

            return(result);
        }
        private JsonSchema BuildJsonSchema(Context context, ISchemaEntity?schema,
                                           ResolvedComponents components)
        {
            if (schema == null)
            {
                return(genericJsonSchema);
            }

            var cacheKey = BuildJsonCacheKey(context.App, schema, context.IsFrontendClient);

            var result = cache.GetOrCreate(cacheKey, entry =>
            {
                entry.AbsoluteExpirationRelativeToNow = CacheTime;

                return(BuildJsonSchema(schema.SchemaDef, context.App, components, context.IsFrontendClient));
            });

            return(result);
        }
示例#16
0
        private ClrQuery ParseQuery(Context context, Q q, ISchemaEntity?schema)
        {
            var query = q.Query;

            if (!string.IsNullOrWhiteSpace(q.JsonQueryString))
            {
                query = ParseJson(context, schema, q.JsonQueryString);
            }
            else if (q?.JsonQuery != null)
            {
                query = ParseJson(context, schema, q.JsonQuery);
            }
            else if (!string.IsNullOrWhiteSpace(q?.ODataQuery))
            {
                query = ParseOData(context, schema, q.ODataQuery);
            }

            return(query);
        }
示例#17
0
        public virtual async Task <Q> ParseAsync(Context context, Q q, ISchemaEntity?schema = null)
        {
            Guard.NotNull(context, nameof(context));
            Guard.NotNull(q, nameof(q));

            using (Profiler.TraceMethod <ContentQueryParser>())
            {
                var query = ParseQuery(context, q, schema);

                await TransformFilterAsync(query, context, schema);

                WithSorting(query);
                WithPaging(query);

                q = q !.WithQuery(query);

                return(q);
            }
        }
        public async Task <ISchemaEntity> GetSchemaOrThrowAsync(Context context, string schemaIdOrName)
        {
            ISchemaEntity?schema = null;

            if (Guid.TryParse(schemaIdOrName, out var id))
            {
                schema = await appProvider.GetSchemaAsync(context.App.Id, id);
            }

            if (schema == null)
            {
                schema = await appProvider.GetSchemaAsync(context.App.Id, schemaIdOrName);
            }

            if (schema == null)
            {
                throw new DomainObjectNotFoundException(schemaIdOrName, typeof(ISchemaEntity));
            }

            return(schema);
        }
示例#19
0
        private async Task TransformFilterAsync(ClrQuery query, Context context, ISchemaEntity?schema)
        {
            if (query.Filter != null && schema != null)
            {
                query.Filter = await GeoQueryTransformer.TransformAsync(query.Filter, context, schema, textIndex);
            }

            if (!string.IsNullOrWhiteSpace(query.FullText))
            {
                if (schema == null)
                {
                    throw new InvalidOperationException();
                }

                var textQuery = new TextQuery(query.FullText, 1000)
                {
                    PreferredSchemaId = schema.Id
                };

                var fullTextIds = await textIndex.SearchAsync(context.App, textQuery, context.Scope());

                var fullTextFilter = ClrFilter.Eq("id", "__notfound__");

                if (fullTextIds?.Any() == true)
                {
                    fullTextFilter = ClrFilter.In("id", fullTextIds.Select(x => x.ToString()).ToList());
                }

                if (query.Filter != null)
                {
                    query.Filter = ClrFilter.And(query.Filter, fullTextFilter);
                }
                else
                {
                    query.Filter = fullTextFilter;
                }

                query.FullText = null;
            }
        }
示例#20
0
        public virtual async Task <Q> ParseAsync(Context context, Q q, ISchemaEntity?schema = null)
        {
            Guard.NotNull(context, nameof(context));
            Guard.NotNull(q, nameof(q));

            using (Telemetry.Activities.StartActivity("ContentQueryParser/ParseAsync"))
            {
                var query = await ParseClrQueryAsync(context, q, schema);

                await TransformFilterAsync(query, context, schema);

                WithSorting(query);
                WithPaging(query, q);

                q = q.WithQuery(query);

                if (context.ShouldSkipTotal())
                {
                    q = q.WithoutTotal();
                }

                return(q);
            }
        }
示例#21
0
        public async Task <List <(IContentEntity Content, ISchemaEntity Schema)> > DoAsync(Guid appId, ISchemaEntity?schema, HashSet <Guid> ids, Status[]?status, bool includeDraft)
        {
            Guard.NotNull(ids);

            var find = Collection.Find(CreateFilter(appId, ids, status)).WithoutDraft(includeDraft);

            var contentItems = await find.ToListAsync();

            var contentSchemas = await GetSchemasAsync(appId, schema, contentItems);

            var result = new List <(IContentEntity Content, ISchemaEntity Schema)>();

            foreach (var contentEntity in contentItems)
            {
                if (contentEntity.HasStatus(status) && contentSchemas.TryGetValue(contentEntity.IndexedSchemaId, out var contentSchema))
                {
                    contentEntity.ParseData(contentSchema.SchemaDef, serializer);

                    result.Add((contentEntity, contentSchema));
                }
            }

            return(result);
        }
示例#22
0
        public async Task <List <(IContentEntity Content, ISchemaEntity Schema)> > DoAsync(DomainId appId, ISchemaEntity?schema, HashSet <DomainId> ids, bool canCache)
        {
            Guard.NotNull(ids, nameof(ids));

            var find = Collection.Find(CreateFilter(appId, ids));

            var contentItems = await find.ToListAsync();

            var contentSchemas = await GetSchemasAsync(appId, schema, contentItems, canCache);

            var result = new List <(IContentEntity Content, ISchemaEntity Schema)>();

            foreach (var contentEntity in contentItems)
            {
                if (contentSchemas.TryGetValue(contentEntity.IndexedSchemaId, out var contentSchema))
                {
                    contentEntity.ParseData(contentSchema.SchemaDef, converter);

                    result.Add((contentEntity, contentSchema));
                }
            }

            return(result);
        }
示例#23
0
        private async Task <IDictionary <DomainId, ISchemaEntity> > GetSchemasAsync(DomainId appId, ISchemaEntity?schema, List <MongoContentEntity> contentItems, bool canCache)
        {
            var schemas = new Dictionary <DomainId, ISchemaEntity>();

            if (schema != null)
            {
                schemas[schema.Id] = schema;
            }

            var schemaIds = contentItems.Select(x => x.IndexedSchemaId).Distinct();

            foreach (var schemaId in schemaIds)
            {
                if (!schemas.ContainsKey(schemaId))
                {
                    var found = await appProvider.GetSchemaAsync(appId, schemaId, false, canCache);

                    if (found != null)
                    {
                        schemas[schemaId] = found;
                    }
                }
            }

            return(schemas);
        }
示例#24
0
        private ClrQuery ParseJson(Context context, ISchemaEntity?schema, Query <IJsonValue> query)
        {
            var jsonSchema = BuildJsonSchema(context, schema);

            return(jsonSchema.Convert(query));
        }
示例#25
0
        private ClrQuery ParseJson(Context context, ISchemaEntity?schema, string json)
        {
            var jsonSchema = BuildJsonSchema(context, schema);

            return(jsonSchema.Parse(json, jsonSerializer));
        }