How to sort, paginate normalized results?

Per Sort by relation fields or even nested relation field - #4 by selmeci it’s possible to paginate normalized results, but I haven’t been able to figure out how.

I have a schema:

type FooType {
  foo_type_name: string
  // plus some others
}
foo_type_name: string @index(exact) .

type Foo {
  foo_name: string
  foo_type: FooType
}
foo_name: string .
foo_type: uid @reverse .

and I want to get N Foos that are of type A or B. I can write a query like:

query {
  types as var(func: eq(foo_type_name, "A", "B"))
  foo(func: uid(types), first: 1) @normalize {
    ~foo_type {
      uid
      foo_name: foo_name
  }
}

however as you’d expect, this will result all type A nodes and no type B nodes, when I really just wanted 1 node, which could be either type A or type B. FWIW, I’m only using @normalize to get the results in a single array, in the hopes that I can sort, limit, and paginate it as a single result.

I’ve tried aliasing the result of foo (foo as var(func...)) and then paginate those results (bar(func: uid(foo), first: 1) { ... }), but the results are the same. I’m not sure it would be performant even if it did do what I had hoped.

I wouldn’t be surprised if I’m on the wrong track here. If there’s a better way to paginate these results, with or without normalize, I’m all ears. This is just an amalgamation of what I have found while reading the documentation and filled in with examples. I’m hoping I don’t have to create distinct edges for each type (there are several), although I believe that would work when used with @filter(has(type_a) or has(type_b)).

This gets closer, but pagination doesn’t work right (after doesn’t work anyway, offset does, but is problematic):

query {
  var(func: eq(foo_type_name, "A", "B")) {
    foos as ~foo_type
  }
  foo(func: uid(foos), first: 1) @normalize {
    uid
    foo_name: foo_name
  }
}

You won’t get an error if you add after next to first. Instead, you’ll get the first page of results as though you passed no after.

Here’s a solution that does the job:

query {
  var(func: eq(foo_type_name, "A", "B")) {
    foos as ~foo_type (after: 0x123)
  }
  foo(func: uid(foos), first: 1) @normalize {
    uid
    foo_name: foo_name
  }
}

The key is to put after in the reverse predicate var query and first in the query that accepts the “result” of the first query. Also, I’m not sure @normalize has anything to do with the issue after all.

This topic was automatically closed 30 days after the last reply. New replies are no longer allowed.