Strapi之Entity Service API

夏星阑
2023-12-01

Query Engine API 和 Entity Service API 都是 Strapi 平台提供的 API,但是它们的功能和用途有所不同。

Entity Service API 主要用于管理实体对象的创建、读取、更新和删除操作,它是对 Strapi 数据库的一种抽象,用于对实体对象进行 CURD 操作。通过 Entity Service API,您可以方便地将实体对象存储在 Strapi 平台上,并对其进行 CRUD 操作。

而 Query Engine API 则是用于从 Strapi 数据库中查询实体对象数据的 API,它提供了强大的查询和过滤功能,用于满足业务需求。通过 Query Engine API,您可以方便地查询、过滤、排序、分页实体对象数据,以满足您的业务需求。

因此,可以说 Entity Service API 和 Query Engine API 是 Strapi 平台中实体对象管理和数据查询的核心 API。Entity Service API 用于管理实体对象,而 Query Engine API 用于查询实体对象数据。二者结合使用,可以使得对于实体对象的管理和查询变得更加方便和灵活。

UID

首先要理解下UID,uid表示要查找的实体的唯一标识符(Unique Identifier),它用于在数据库中唯一地标识该实体。uid通常由开发人员在实体创建时指定,并在实体被保存到数据库中时分配。在调用findOne方法时,你需要提供一个有效的uid,以便API可以在数据库中查找与该uid匹配的实体。

例如,在一个电子商务应用程序中,你可能有一个名为“Product”的实体,其中每个产品都有一个唯一的产品ID(product ID)。当调用findOne方法来查找特定的产品时,需要提供该产品的ID作为uid参数。

以下是在Node.js中使用Entity Service API的findOne方法查找特定产品的示例代码:

const { EntityServiceClient } = require('entity-service-sdk');
const client = new EntityServiceClient('http://localhost:8000');

// 查找产品
async function findProduct(productId) {
  try {
    const product = await client.findOne({
      kind: 'Product',
      uid: productId
    });
    return product;
  } catch (error) {
    console.log(error);
    return null;
  }
}

// 调用findProduct方法查找产品
findProduct('12345').then(product => {
  if (product) {
    console.log(product);
  } else {
    console.log("未找到该产品");
  }
});

另外,在Entity Service API官方示例中,提到了一种将uid标识符格式化为[category]::[content-type]的方式。这种格式化方式是为了方便开发者在uid中包含实体类型信息,并且可读性更好。

例如,如果应用程序有一个名为“Product”的实体类型,并且想为每个产品分配一个唯一的uid,那么可以使用[category]::[content-type]格式将uid标识符格式化为“Product::12345”,其中“Product”表示实体类型,而“12345”表示产品的唯一标识符。

在使用这种格式化方式时,需要注意确保category和content-type之间使用双冒号(::)分隔,以避免与uid中可能包含的其他冒号产生混淆。此外,需要确保category和content-type的命名规范符合应用程序的要求,并且不包含双冒号、空格、标点符号等特殊字符。

需要注意的是,这种uid格式化方式并不是Entity Service API的强制要求,完全可以使用其他格式或方式来表示实体的唯一标识符。但如果你的应用程序需要在uid中包含实体类型信息,并且希望uid具有一定的可读性和格式规范,那么这种格式化方式可能会有所帮助。

CRUD操作

findOne()

返回数据居库中与参数匹配的第一个记录。

语法定义为:findOne(uid: string, id: ID, parameters: Params) ⇒ Entry

const entry = await strapi.entityService.findOne('api::article.article', 1, {
  fields: ['title', 'description'],
  populate: { category: true },
});

findMany()

返回与参数匹配的所有数据。

语法定义为:findMany(uid: string, parameters: Params) ⇒ Entry[]

const entries = await strapi.entityService.findMany('api::article.article', {
  fields: ['title', 'description'],
  filters: { title: 'Hello World' },
  sort: { createdAt: 'DESC' },
  populate: { category: true },
});

create()

创建一条记录并返回
语法定义:create(uid: string, parameters: Params) ⇒ Entry

const entry = await strapi.entityService.create('api::article.article', {
  data: {
    title: 'My Article',
  },
});

update()

更新一条记录并返回
语法定义:update(uid: string,id: ID, parameters: Params) ⇒ Entry

const entry = await strapi.entityService.update('api::article.article', 1, {
  data: {
    title: 'xxx',
  },
});

delete()

删除一条记录并返回
语法定义:delete(uid: string,id: ID, parameters: Params) ⇒ Entry

const entry = await strapi.entityService.delete('api::article.article', 1);

Filtering

findMay方法中提供了filter实现过滤效果,结果用过滤器参数进行过滤,过滤器接受 logical operators 逻辑运算符和 attribute operators 属性运算符。每个运算符都应该以$为前缀。

Logical operators

  • $and:逻辑“与”,用于匹配所有指定的条件。
  • $or:逻辑“或”,用于匹配任何指定的条件。
  • $not:逻辑“非”,用于匹配不符合指定条件的结果。

Attribute Operators

  • $eq:匹配等于指定值的结果。
  • $ne:匹配不等于指定值的结果。
  • $lt:匹配小于指定值的结果。
  • $lte:匹配小于或等于指定值的结果。
  • $gt:匹配大于指定值的结果。
  • $gte:匹配大于或等于指定值的结果。
  • $in:匹配包含在指定数组中的值的结果。
  • $nin:匹配不包含在指定数组中的值的结果。
  • $contains:匹配包含指定子字符串的结果。
  • $ncontains:匹配不包含指定子字符串的结果。
  • $null:匹配为 null 的结果。
  • $nnull:匹配不为 null 的结果。
  • $empty:匹配为空的结果。
  • $nempty:匹配不为空的结果。

Populating

在Strapi中,Populating是指在一个请求中同时获取相关联的记录,而不是在多个请求中获取每个记录。这个过程类似于SQL中的JOIN操作。 Strapi通过使用Mongoose(MongoDB的对象文档映射器)的populate方法来实现Populating。

例如,假设现在有一个名为"Article"的模型,并且该模型具有一个名为"author"的字段,该字段引用另一个名为"User"的模型。如果我们想获取一篇文章及其作者的信息,可以使用populate方法在一个请求中获取这两个记录:

const article = await strapi.query('article').findOne({ id: 1 }).populate('author');

这将返回一个包含文章和作者信息的对象。如果没有使用populate方法,那么我们将需要使用两个请求来获取这些信息。第一个请求获取文章信息,第二个请求获取作者信息。这将导致不必要的网络延迟和性能问题。

Populating在Strapi中非常常用,因为它可以简化代码并提高性能。但是,如果在一个请求中获取太多的记录,可能会影响性能。因此,请确保只获取必要的记录。

Ordering & Pagination

使用排序和分页选项来获取特定数量的结果并按特定方式排序。

其中ordering使用sort进行排序操作

  • single:单个排序
strapi.entityService.findMany('api::article.article', {
  sort: 'id',
});

// single with direction
strapi.entityService.findMany('api::article.article', {
  sort: { id: 'desc' },
});
  • multiple:多个排序
strapi.entityService.findMany('api::article.article', {
  sort: ['publishDate', 'name'],
});

// multiple with direction
strapi.entityService.findMany('api::article.article', {
  sort: [{ title: 'asc' }, { publishedAt: 'desc' }],
});
  • relational ordering:基于关系的字段排序

在Strapi中,关系字段是一种用于建立数据之间关系的字段类型。例如,一个“文章”数据类型可能包含一个关系字段,该字段与“作者”数据类型相关联,以指示该文章是由哪个作者创建的。在某些情况下,我们可能希望根据与关系字段相关联的数据类型的字段进行排序。例如,如果正在显示所有文章,并希望按作者姓名对它们进行排序,则可以使用相关联的“作者”数据类型的“姓名”字段进行排序。这种排序方法称为基于关系的字段排序,它允许我们按照与当前数据类型相关联的其他数据类型的字段进行排序,从而更好地组织和呈现数据。

strapi.entityService.findMany('api::article.article', {
  sort: {
    author: {
      name: 'asc',
    },
  },
});

使用start和limit进行页面操作

strapi.entityService.findMany('api::article.article', {
  start: 10,
  limit: 15,
});
 类似资料: