OrchardCore 中为现有类型 实现自定义 Graphql 查询
Posted 韩严重的博客
tags:
篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了OrchardCore 中为现有类型 实现自定义 Graphql 查询相关的知识,希望对你有一定的参考价值。
很多情况下,需要自定义逻辑来实现 Graphql查询,
比如 通过Graphql 查询当前用户信息
因为 Graphql 是强类型的,所以我们要先实现一个Schema
定义一个类,实现 OrchardCore.Apis.GraphQL.ISchemaBuilder 接口
public class UserInfoQueryFieldTypeProvider : ISchemaBuilder
构建自定义字段
public Task BuildAsync(ISchema schema) //从已注册类型中查找指定类型字段 var typetype = schema.Query.Fields.OfType<ContentItemsFieldType>() .FirstOrDefault(x => x.Name == "UserProfile"); if (typetype == null) return null; //因为系统自动注册的类型是集合形式的,所以先要进行转换 var type = (ListGraphType)typetype.ResolvedType; var field = new FieldType Name = "Me", Description = S["Information about the current login user."], Type = typeof(ContentItemInterface), ResolvedType = type.ResolvedType, Resolver = new AsyncFieldResolver<ContentItem>(ResolveAsync) ; schema.Query.AddField(field); return Task.CompletedTask;
告知 系统何时更新Schema ,因为我们的 当前用户是 基于现有动态类型实现的,所以监听 类型定义的变更即可
public Task<string> GetIdentifierAsync() var contentDefinitionManager = _httpContextAccessor.HttpContext.RequestServices.GetService<IContentDefinitionManager>(); return contentDefinitionManager.GetIdentifierAsync();
自定义逻辑实现:
private async Task<ContentItem> ResolveAsync(IResolveFieldContext context) var serviceProvider = _httpContextAccessor.HttpContext.RequestServices; var userManager = serviceProvider.GetRequiredService<UserManager<IUser>>(); var user = await userManager.FindByNameAsync(_httpContextAccessor.HttpContext.User.Identity.Name) as User; var contentManager = serviceProvider.GetService<IContentManager>(); var contentItem = await contentManager.GetAsync(user.UserId); if (contentItem == null) contentItem = await contentManager.NewAsync("UserProfile"); contentItem.Owner = user.UserId; contentItem.Alter<UserProfile>(profile => profile.Roles.Values = user.RoleNames.ToArray(); profile.UserName.Text = user.UserName; profile.Email.Text = user.Email; ); return contentItem;
最后别忘了向DI注册
services.AddSingleton<ISchemaBuilder, UserInfoQueryFieldTypeProvider>();
以上示例实现了一个 非集合类型的查询
如果 需要返回集合类型 参考如下代码:
public Task BuildAsync(ISchema schema) var typetype = schema.Query.Fields.OfType<ContentItemsFieldType>() .FirstOrDefault(x => x.Name == nameof(AntdMenuItem)); if (typetype == null) return Task.CompletedTask; var field = new FieldType Name = "userMenus", Description = S["获取用户菜单"], Type = typeof(ListGraphType<ContentItemType>), ResolvedType = typetype.ResolvedType, Resolver = new LockedAsyncFieldResolver<IEnumerable<ContentItem>>(ResolveAsync) ; schema.Query.AddField(field); return Task.CompletedTask;
Orchard Core 文档翻译 自动路由 Autoroute (OrchardCore.Autoroute)
Autoroute (OrchardCore.Autoroute)
此模块允许您为内容项指定自定义URL(永久链接 permalink)。
Autoroute Part
将此部分附加到内容类型以指定内容项的自定义URL。
然后,转到内容类型的定义并编辑 Autoroute Part:
- 使用Liquid表达式输入Pattern,该表达式将表示生成的slug。
具有TitlePart的内容的示例将使用它来生成slug:
{{ ContentItem | display_text | slugify }}
具有ListPart和TitlePart(ig:BlogPost嵌套在博客中)的内容示例将使用容器和标题生成slug:
{{ ContentItem | container | display_text | slugify }}/{{ ContentItem | display_text | slugify }}`
- 如果您希望在编辑内容项时能够输入自定义路径,请选中“Allow custom path”。
- 如果您希望能够将内容项目设置为主页,请选中 ‘Show homepage options‘
Autoroute Alias
只要您可以通过别名检索内容,就可以通过URL检索具有Autoroute的内容项(请参阅下面的示例)。这个语法是 slug:<URL>
, e.g. slug:my-blog/my-blog-post
.
Liquid
启用Autoroute后,您可以在liquid 视图和templates中按URL检索内容:
{% assign my_content = Content["slug:my-blog/my-blog-post"] %}
or
{% assign my_content = Content.Slug["my-blog/my-blog-post"] %}
以上是关于OrchardCore 中为现有类型 实现自定义 Graphql 查询的主要内容,如果未能解决你的问题,请参考以下文章
我们如何在 Hive 中为自定义 Writable 类型编写自定义 ObjectInspector?
如何在 WooCommerce 中为自定义产品类型启用价格和库存