高橋  花子

高橋 花子

1647093600

フィルタリングとページ付け機能をGraphQLAPIに追加する

これはチュートリアルのエキサイティングなセクションであり、多くの堅牢なAPIのいくつかの主要な機能を実装します。目標は、フィルタリングとページネーションのパラメーターを提供することにより、クライアントがクエリによってLink返される要素のリストを制約できるようにすることです。feed

飛び込みましょう!🚀

フィルタリング

を使用するPrismaClientことで、あまり労力をかけずにAPIにフィルタリング機能を実装できます。前の章と同様に、クエリ解決の大幅な強化はPrismaによって実行されます。あなたがする必要があるのはそれに着信クエリを転送することです。

最初のステップは、APIを介して公開するフィルターについて考えることです。あなたの場合、APIのクエリはフィルター文字列feedを受け入れます。その場合、クエリは、またはにそのフィルタ文字列が含まれている要素のみを返す必要があります。Linkurl description

先に進み、アプリケーションスキーマfilterのクエリに文字列を追加します。feed

... / hackernews-node / src / schema.graphql

type Query {
  info: String!
  feed(filter: String): [Link!]!
}

feed次に、クライアントが提供できる新しいパラメーターを考慮して、リゾルバーの実装を更新する必要があります。

リゾルバを開いsrc/resolvers/Query.jsて更新し、feed次のようにします。

... / hackernews-node / src / resolvers / Query.js

async function feed(parent, args, context, info) {
  const where = args.filter
    ? {
      OR: [
        { description: { contains: args.filter } },
        { url: { contains: args.filter } },
      ],
    }
    : {}

  const links = await context.prisma.link.findMany({
    where,
  })

  return links
}

filter文字列が指定されていない場合、オブジェクトは単なる空のオブジェクトになり、クエリwhereの応答を返すときにPrismaClientによってフィルタリング条件が適用されることはありません。links

filter着信によって運ばれる場合は、上から2つのフィルター条件を表すオブジェクトをargs作成しています。whereこの引数は、指定された条件に準拠しない要素をwhere除外するためにPrismaによって使用されます。Link

フィルタリング機能は以上です。先に進み、フィルターAPIをテストします-使用できるサンプルクエリは次のとおりです。

query {
  feed(filter: "QL") {
    id
    description
    url
    postedBy {
      id
      name
    }
  }
}

サンプルクエリ

ページ付け

ページ付けは、API設計では難しいトピックです。大まかに言えば、それに取り組むための2つの主要なアプローチがあります。

  • Limit-Offset:取得するアイテムのインデックスを提供することにより、リストの特定のチャンクを要求します(実際、ほとんどの場合、開始インデックス(offset)と取得するアイテムの数(limit)を提供します) 。
  • カーソルベース:このページネーションモデルはもう少し高度です。リスト内のすべての要素は、一意のID(カーソル)に関連付けられています。次に、リストをページングするクライアントは、開始要素のカーソルと、取得するアイテムの数を提供します。

Prismaは、両方のページネーションアプローチをサポートしています(詳細については、ドキュメントを参照してください)。このチュートリアルでは、制限オフセットページネーションを実装します。

:両方のページネーションアプローチの背後にある考え方について詳しくは、こちらをご覧ください。

Prisma APIでは、制限とオフセットの名前が異なります。

  • 制限はと呼ばれ、指定された開始インデックスの後に要素takeを「取得」していることを意味します。x
  • 返されるアイテムを収集する前にリスト内のその多くの要素をスキップしているため、開始インデックスはと呼ばれます。提供されていない場合、デフォルトで提供さskipれます。その場合、ページネーションは常にリストの最初から始まります。skip0

したがって、先に進んで、skiptake引数をfeedクエリに追加します。

アプリケーションスキーマを開き、引数を受け入れるようにクエリを調整しますfeedskiptake

... / hackernews-node / src / schema.graphql

type Query {
  info: String!
  feed(filter: String, skip: Int, take: Int): [Link!]!
}

次に、リゾルバーの実装に移ります。

で、リゾルバsrc/resolvers/Query.jsの実装を調整します。feed

... / hackernews-node / src / resolvers / Query.js

async function feed(parent, args, context, info) {
  const where = args.filter
    ? {
      OR: [
        { description: { contains: args.filter } },
        { url: { contains: args.filter } },
      ],
    }
    : {}

  const links = await context.prisma.link.findMany({
    where,
    skip: args.skip,
    take: args.take,
  })

  return links
}

ここで実際に変更されているのは、クエリの呼び出しが、着信オブジェクトlinksによって運ばれる可能性のある2つの追加の引数を受け取ることです。args繰り返しになりますが、Prismaが残りの面倒をみます。

Linkリストから2番目を返す次のクエリを使用して、ページネーションAPIをテストできます。

query {
  feed(take: 1, skip: 1) {
    id
    description
    url
  }
}

ページネーションAPIをテストします

 

並べ替え

Prismaを使用すると、特定の基準に従ってソート(順序付け)された要素のリストを返すことができます。たとえば、Linksのリストをまたはのアルファベット順に並べ替えることができurlますdescription。Hacker News APIの場合、正確に並べ替える方法はクライアントに任せて、PrismaAPIのすべての順序付けオプションをGraphQLサーバーのAPIに含めます。inputこれを行うには、順序付けオプションを表すタイプと列挙型を作成します。

次の列挙型定義を次のように追加しますschema.graphql

... / hackernews-node / src / schema.graphql

input LinkOrderByInput {
  description: Sort
  url: Sort
  createdAt: Sort
}

enum Sort {
  asc
  desc
}

Linkこれは、要素のリストを並べ替えることができるさまざまな方法を表しています。

次に、引数feedを含めるようにクエリを再度調整します。orderBy

... / hackernews-node / src / schema.graphql

type Query {
  info: String!
  feed(filter: String, skip: Int, take: Int, orderBy: LinkOrderByInput): [Link!]!
}

リゾルバーの実装は、ページネーションAPIで行ったものと似ています。

feedのリゾルバーの実装を更新し、引数をPrismaにsrc/resolvers/Query.js渡します。orderBy

... / hackernews-node / src / resolvers / Query.js

async function feed(parent, args, context, info) {
  const where = args.filter
    ? {
      OR: [
        { description: { contains: args.filter } },
        { url: { contains: args.filter } },
      ],
    }
    : {}

  const links = await context.prisma.link.findMany({
    where,
    skip: args.skip,
    take: args.take,
    orderBy: args.orderBy,
  })

  return links
}

素晴らしい!返されたリンクを作成日で並べ替えるクエリは次のとおりです。

query {
  feed(orderBy: { createdAt: asc }) {
    id
    description
    url
  }
}

要素の合計量を返すLink

Hacker News APIに実装する最後のことは、データベースに現在保存されている Link要素の数に関する情報です。そのためには、feedクエリを少しリファクタリングし、APIから返される新しいタイプを作成しますFeed

新しいFeedタイプをGraphQLスキーマに追加します。feed次に、それに応じてクエリの戻りタイプも調整します。

... / hackernews-node / src / schema.graphql

type Query {
  info: String!
  feed(filter: String, skip: Int, take: Int, orderBy: LinkOrderByInput): Feed!
}

type Feed {
  links: [Link!]!
  count: Int!
}

次に、feedリゾルバを再度調整します。

... / hackernews-node / src / resolvers / Query.js

async function feed(parent, args, context, info) {
  const where = args.filter
    ? {
      OR: [
        { description: { contains: args.filter } },
        { url: { contains: args.filter } },
      ],
    }
    : {}

  const links = await context.prisma.link.findMany({
    where,
    skip: args.skip,
    take: args.take,
    orderBy: args.orderBy,
  })

  const count = await context.prisma.link.count({ where })

  return {
    links,
    count,
  }
}

これで、改良されたfeedクエリを次のようにテストできます。

query {
  feed {
    count
    links {
      id
      description
      url
    }
  }
}

改良されたフィードクエリをテストするリンク:https ://www.howtographql.com/graphql-js/8-filtering-pagination-and-sorting/

#graphql #javascript #api 

What is GEEK

Buddha Community

フィルタリングとページ付け機能をGraphQLAPIに追加する
高橋  花子

高橋 花子

1647093600

フィルタリングとページ付け機能をGraphQLAPIに追加する

これはチュートリアルのエキサイティングなセクションであり、多くの堅牢なAPIのいくつかの主要な機能を実装します。目標は、フィルタリングとページネーションのパラメーターを提供することにより、クライアントがクエリによってLink返される要素のリストを制約できるようにすることです。feed

飛び込みましょう!🚀

フィルタリング

を使用するPrismaClientことで、あまり労力をかけずにAPIにフィルタリング機能を実装できます。前の章と同様に、クエリ解決の大幅な強化はPrismaによって実行されます。あなたがする必要があるのはそれに着信クエリを転送することです。

最初のステップは、APIを介して公開するフィルターについて考えることです。あなたの場合、APIのクエリはフィルター文字列feedを受け入れます。その場合、クエリは、またはにそのフィルタ文字列が含まれている要素のみを返す必要があります。Linkurl description

先に進み、アプリケーションスキーマfilterのクエリに文字列を追加します。feed

... / hackernews-node / src / schema.graphql

type Query {
  info: String!
  feed(filter: String): [Link!]!
}

feed次に、クライアントが提供できる新しいパラメーターを考慮して、リゾルバーの実装を更新する必要があります。

リゾルバを開いsrc/resolvers/Query.jsて更新し、feed次のようにします。

... / hackernews-node / src / resolvers / Query.js

async function feed(parent, args, context, info) {
  const where = args.filter
    ? {
      OR: [
        { description: { contains: args.filter } },
        { url: { contains: args.filter } },
      ],
    }
    : {}

  const links = await context.prisma.link.findMany({
    where,
  })

  return links
}

filter文字列が指定されていない場合、オブジェクトは単なる空のオブジェクトになり、クエリwhereの応答を返すときにPrismaClientによってフィルタリング条件が適用されることはありません。links

filter着信によって運ばれる場合は、上から2つのフィルター条件を表すオブジェクトをargs作成しています。whereこの引数は、指定された条件に準拠しない要素をwhere除外するためにPrismaによって使用されます。Link

フィルタリング機能は以上です。先に進み、フィルターAPIをテストします-使用できるサンプルクエリは次のとおりです。

query {
  feed(filter: "QL") {
    id
    description
    url
    postedBy {
      id
      name
    }
  }
}

サンプルクエリ

ページ付け

ページ付けは、API設計では難しいトピックです。大まかに言えば、それに取り組むための2つの主要なアプローチがあります。

  • Limit-Offset:取得するアイテムのインデックスを提供することにより、リストの特定のチャンクを要求します(実際、ほとんどの場合、開始インデックス(offset)と取得するアイテムの数(limit)を提供します) 。
  • カーソルベース:このページネーションモデルはもう少し高度です。リスト内のすべての要素は、一意のID(カーソル)に関連付けられています。次に、リストをページングするクライアントは、開始要素のカーソルと、取得するアイテムの数を提供します。

Prismaは、両方のページネーションアプローチをサポートしています(詳細については、ドキュメントを参照してください)。このチュートリアルでは、制限オフセットページネーションを実装します。

:両方のページネーションアプローチの背後にある考え方について詳しくは、こちらをご覧ください。

Prisma APIでは、制限とオフセットの名前が異なります。

  • 制限はと呼ばれ、指定された開始インデックスの後に要素takeを「取得」していることを意味します。x
  • 返されるアイテムを収集する前にリスト内のその多くの要素をスキップしているため、開始インデックスはと呼ばれます。提供されていない場合、デフォルトで提供さskipれます。その場合、ページネーションは常にリストの最初から始まります。skip0

したがって、先に進んで、skiptake引数をfeedクエリに追加します。

アプリケーションスキーマを開き、引数を受け入れるようにクエリを調整しますfeedskiptake

... / hackernews-node / src / schema.graphql

type Query {
  info: String!
  feed(filter: String, skip: Int, take: Int): [Link!]!
}

次に、リゾルバーの実装に移ります。

で、リゾルバsrc/resolvers/Query.jsの実装を調整します。feed

... / hackernews-node / src / resolvers / Query.js

async function feed(parent, args, context, info) {
  const where = args.filter
    ? {
      OR: [
        { description: { contains: args.filter } },
        { url: { contains: args.filter } },
      ],
    }
    : {}

  const links = await context.prisma.link.findMany({
    where,
    skip: args.skip,
    take: args.take,
  })

  return links
}

ここで実際に変更されているのは、クエリの呼び出しが、着信オブジェクトlinksによって運ばれる可能性のある2つの追加の引数を受け取ることです。args繰り返しになりますが、Prismaが残りの面倒をみます。

Linkリストから2番目を返す次のクエリを使用して、ページネーションAPIをテストできます。

query {
  feed(take: 1, skip: 1) {
    id
    description
    url
  }
}

ページネーションAPIをテストします

 

並べ替え

Prismaを使用すると、特定の基準に従ってソート(順序付け)された要素のリストを返すことができます。たとえば、Linksのリストをまたはのアルファベット順に並べ替えることができurlますdescription。Hacker News APIの場合、正確に並べ替える方法はクライアントに任せて、PrismaAPIのすべての順序付けオプションをGraphQLサーバーのAPIに含めます。inputこれを行うには、順序付けオプションを表すタイプと列挙型を作成します。

次の列挙型定義を次のように追加しますschema.graphql

... / hackernews-node / src / schema.graphql

input LinkOrderByInput {
  description: Sort
  url: Sort
  createdAt: Sort
}

enum Sort {
  asc
  desc
}

Linkこれは、要素のリストを並べ替えることができるさまざまな方法を表しています。

次に、引数feedを含めるようにクエリを再度調整します。orderBy

... / hackernews-node / src / schema.graphql

type Query {
  info: String!
  feed(filter: String, skip: Int, take: Int, orderBy: LinkOrderByInput): [Link!]!
}

リゾルバーの実装は、ページネーションAPIで行ったものと似ています。

feedのリゾルバーの実装を更新し、引数をPrismaにsrc/resolvers/Query.js渡します。orderBy

... / hackernews-node / src / resolvers / Query.js

async function feed(parent, args, context, info) {
  const where = args.filter
    ? {
      OR: [
        { description: { contains: args.filter } },
        { url: { contains: args.filter } },
      ],
    }
    : {}

  const links = await context.prisma.link.findMany({
    where,
    skip: args.skip,
    take: args.take,
    orderBy: args.orderBy,
  })

  return links
}

素晴らしい!返されたリンクを作成日で並べ替えるクエリは次のとおりです。

query {
  feed(orderBy: { createdAt: asc }) {
    id
    description
    url
  }
}

要素の合計量を返すLink

Hacker News APIに実装する最後のことは、データベースに現在保存されている Link要素の数に関する情報です。そのためには、feedクエリを少しリファクタリングし、APIから返される新しいタイプを作成しますFeed

新しいFeedタイプをGraphQLスキーマに追加します。feed次に、それに応じてクエリの戻りタイプも調整します。

... / hackernews-node / src / schema.graphql

type Query {
  info: String!
  feed(filter: String, skip: Int, take: Int, orderBy: LinkOrderByInput): Feed!
}

type Feed {
  links: [Link!]!
  count: Int!
}

次に、feedリゾルバを再度調整します。

... / hackernews-node / src / resolvers / Query.js

async function feed(parent, args, context, info) {
  const where = args.filter
    ? {
      OR: [
        { description: { contains: args.filter } },
        { url: { contains: args.filter } },
      ],
    }
    : {}

  const links = await context.prisma.link.findMany({
    where,
    skip: args.skip,
    take: args.take,
    orderBy: args.orderBy,
  })

  const count = await context.prisma.link.count({ where })

  return {
    links,
    count,
  }
}

これで、改良されたfeedクエリを次のようにテストできます。

query {
  feed {
    count
    links {
      id
      description
      url
    }
  }
}

改良されたフィードクエリをテストするリンク:https ://www.howtographql.com/graphql-js/8-filtering-pagination-and-sorting/

#graphql #javascript #api