[Package][dqlx] - DGraph Query Builder

Hello Community!

I wanted to reach out to introduce you Deku, the first DGraph Query Builder.

I’m planning to cut the first stable release end of this week, in mean time I wanted to gather some of your feedback on the overall API and if you like/dislike the concept.

Why?

The DGraph query language is awesome! it is really powerful, and you can achieve a lot with it.
However, as you start trying to add dynamicity (like any other declarative query language) you soon starts
fiddling with a lot strings concatenations and can quickly get messy.

Deku tries to simplify the construction of DGraph Queries and mutations with a fluent API.

Features

  • Schema Builder (Types, Predicates, Indexes)
  • Filtering - Connecting Filters (AND / OR)
  • Nested Selection / Filters
  • Functions
  • Pagination
  • Aggregation
  • Sorting
  • GroupBy
  • Multiple Query Block
  • Query Variables
  • Values Variables
  • Facets
  • Mutations

Simple Query Example

query, variables, err := dql.
    Query("bladerunner", dql.EqFn("item", "value")).
    Fields(`
        uid
        name
        initial_release_date
        netflix_id
    `).
    Filter(dql.Eq{"field1": "value1"}).
    ToDQL()


print(query)

Produces

query Bladerunner($0:string, $1:string) {
    bladerunner(func: eq(item,$0)) @filter(eq(field1,$1)) {
        uid
        name
        initial_release_date
        netflix_id
    }
}

Nested Query Example

The true power of Deku shows when you start getting serious

query, variables, err := dql.
    Query("bladerunner", dql.EqFn("name@en", "Blade Runner")).
    Fields(`
        uid
        name
        initial_release_date
        netflix_id
    `).
    Edge("authors", dql.Fields(`
        uid
        name
        surname
        age
    `), dql.Eq{"age": 20}).
    Edge("actors", dql.Fields(`
        uid
        surname
        age
    `), dql.Gt{"age": []int{18, 20, 30}}).
    Edge("actors->rewards"), dql.Fields(`
        uid
        points
    `), dql.Gt{"points": 3}).
    ToDQL()

Produces

query Bladerunner($0:string, $1:int, $2:int, $3:int, $4:int, $5:int) {
    bladerunner(func: eq(name@en,$0)) {
        uid
        name
        initial_release_date
        netflix_id
        authors @filter(eq(age,$1)) {
            uid
            name
            surname
            age
        }
        actors @filter(gt(age,[$2,$3,$4])) {
            uid
            surname
            age
            rewards @filter(gt(points,$5)) {
                uid
                points
            }
        }
    }
}

Don’t forget to check the repository for more information leave a star if you like it.

The documentation is working progress, until then refer to the Test Cases for more sofisticated queries

Regards!

6 Likes

Awesome!
Note there is an incomplete query AST to string implementation within dgraph itself - much different than your API in deku, but its the AST that dgraph parses into.

An issue was raised here about the AsString() function being incomplete: Printing gql+- queries with AsString produces bad query for certain query root functions

1 Like

You are absolutely right!
Going the AST way and use the ToString() would have been much easier to develop.

Building Deku has been fun, I had to go through the query language in depth so that was a great learning curve.

Also it could be a good example on how other languages could implement a Query Builder which are not able to hook into the native AST of dgraph

However, as you mentioned since the ToString() implementation have some issue, I will probably hold off for a while at writing the V2 version of Deku using the AST internally but still keeping the same Public API without breaking changes.

The Goal was to make a builder which is developer friendly other than working directly with the AST

1 Like

Whoa this is so awesome!

1 Like

The project has been renamed to dqlx!

I’ve worked non-stop this weekend to add lots of features and stability fixes to the library!
I hope you guys enjoy it! :grinning_face_with_smiling_eyes:

Ah don’t forget to check the documentation: dqlx | dqlx

3 Likes

changed the topic title for you :slight_smile:

1 Like

Thank you!

When you guys have some time, please feel free to give me some feedback.
The only way to make it even better is to let me know what guys would like to see in the library and of course anything that you’d like to be changed!

Thanks again