npm package discovery and stats viewer.

Discover Tips

  • General search

    [free text search, go nuts!]

  • Package details

    pkg:[package-name]

  • User packages

    @[username]

Sponsor

Optimize Toolset

I’ve always been into building performant and accessible sites, but lately I’ve been taking it extremely seriously. So much so that I’ve been building a tool to help me optimize and monitor the sites that I build to make sure that I’m making an attempt to offer the best experience to those who visit them. If you’re into performant, accessible and SEO friendly sites, you might like it too! You can check it out at Optimize Toolset.

About

Hi, 👋, I’m Ryan Hefner  and I built this site for me, and you! The goal of this site was to provide an easy way for me to check the stats on my npm packages, both for prioritizing issues and updates, and to give me a little kick in the pants to keep up on stuff.

As I was building it, I realized that I was actually using the tool to build the tool, and figured I might as well put this out there and hopefully others will find it to be a fast and useful way to search and browse npm packages as I have.

If you’re interested in other things I’m working on, follow me on Twitter or check out the open source projects I’ve been publishing on GitHub.

I am also working on a Twitter bot for this site to tweet the most popular, newest, random packages from npm. Please follow that account now and it will start sending out packages soon–ish.

Open Software & Tools

This site wouldn’t be possible without the immense generosity and tireless efforts from the people who make contributions to the world and share their work via open source initiatives. Thank you 🙏

© 2024 – Pkg Stats / Ryan Hefner

miniql

v0.0.22

Published

A tiny JSON-based query language inspired by GraphQL

Downloads

19

Readme

MiniQL

A tiny JSON-based query language inspired by GraphQL

Pronounced "miniquel", similar to "miniscule".

New to this? Check out the examples below or jump to getting started.

For a quick idea of what queries look like and how they work, jump straight into the interactive example.

Skip to the end to see how you can support the developer.

Follow the developer on Twitter for updates: @ashleydavis75.

Love this? Please star this repo!

MiniQL in a nutshell

Diagram of MiniQL

Examples

Interactive example

There's an interactive browser-only example of MiniQL here:

https://miniql.github.io/miniql-interactive-example/

You fnd find the code for it here:

https://github.com/miniql/miniql-interactive-example

Node.js + CSV files

Here is an example of making MiniQL queries against a CSV file dataset under Node.js:

https://github.com/miniql/miniql-csv-example

Node.js + JSON files

Here is an example of making MiniQL queries against a JSON file dataset under Node.js:

https://github.com/miniql/miniql-json-example

JavaScript notebook

Here is an easy to read MiniQL example in a JavaScript notebook

https://miniql.github.io/notebook-example/

Frontend + Express REST API + MongoDB

Here is an example of using MiniQL to make queries against a MongoDB database through an Express REST API to display query results in the frontend.

https://github.com/miniql/miniql-express-mongodb-example

Motivation

GraphQL is awesome, but sometimes the following can be annoying...

  • It is big and complicated.
  • It introduces a new language into your stack.
  • I don't want to define a "schema".
    • Schemaless is the best way to prototype an MVP when you don't know what the data is yet.
  • It's tedious to have to specify everything you want returned.
    • Sometimes you just want everything returned! Especially when you are exploring your data!

Aims

  • To be tiny, yet flexible.
  • To easily create queries.
  • To easily implement the backend.
  • To have a single query end point where auth can be implemented.
  • To avoid having many separate REST APIs.
  • To be able to retreive aggregate and optimized data to the front end.
  • To be able to easily explore data.
  • To not impose unecessary structure or rules on your data!
  • Make the most of the backend capabilities (eg search and filtering capability in the database)

Features

  • The query language is JSON and can easily be sent over the weire.
  • The results are JSON and can easiy be received over the wire.
  • MiniQL works in both Node.js and the browser.
    • MiniQL can potentially work in other programming languages, if someone wants to create an implementation for their own fav language.
  • Decouples the query engine from entity resolution ([separation of concerns](https://
  • There is no enforced schema, just like MongoDB.
    • But you can easily make your own JSON schema for validation and intellisense in the frontend. en.wikipedia.org/wiki/Separation_of_concerns)).
  • There is no built-in type system - use your programming language for that! (e.g. TypeScript)
  • Follows relationships and resolves nested entities.
    • You control how the relationships in your data are defined.
  • Aggregates query results from different data sources.
  • Supports arbitrary user-defined types of operations:
    • The MiniQL convertion is have "get" or "update" operations.
    • But use whatever names you like.
    • You can have any other operations as well with whatever names you like.
  • Optionally alias entities in the output. You control the field names that returned in the query result.
  • The "query" is passed through to the resolver, you can build your own resolver or use one of the existing plugins:

Bring your own

MiniQL delegates queries for entities to the query resolver.

The query resolver is something that you implmenent or is provided by a MiniQL plugin (such as the JSON plugin, the CSV plugin or the Inline data plugin).

Implementing your own resolver means you can have what ever features you like in the backend.

Adding features like these is completely under your control:

  • Pagination
  • Retrieving total entities
  • Entity search and filtering
  • Included fields
  • Excluded fields
  • Or anthing else you can think of!

You can manage how data is returned, e.g:

  • Blacklisted fields
  • Whitelisted fields
  • All data, partial data, whatever you want!

Future

  • Add a configurable MongoDB resolver.
  • Caching and aggregation (wishlist)
  • Hooks - be notifed when particular entities/fields have been updated.
  • Optimisation to do queries in parallel.
  • Built-in filtering?
  • How to retreieve a count after search/filtering is applied.

Getting started

Install MiniQL:

npm install --save miniql

Import MiniQL (JavaScript):

const { miniql } = require("miniql");

Import MiniQL (TypeScript):

import { miniql } from "miniql";

Now we must create a query resolver. For this example we'll use a character entity (see the Star Wars data in the interactive example).

We need to define functions for retrieving and updating our character entity:

const queryResolver = {
    get: {
        character: {
            invoke: async (args: any, context: any) => { // Handles a 'get' query.
                if (args.name !== undefined) {
                    // Asking for a particular named character.
                    // Look up the single named character in your database and return it.
                    const theCharacter = ...;
                    return theCharacter;
                }
                else {
                    // Asking for all characters.
                    // Look up all characters in your database and return them.
                    const allCharacters = ...;
                    return allCharacters;
                }
            }
        }
    },

    update: {
        character: {
            invoke: async (args: any, context: any) => { // Handles an 'update' query.
                if (args.name !== undefined) {
                    const updateParams = args.params;
                    // Store `updateParams` against the single 
                    // named character in your database.
                }
                else {
                    const updateParams = args.params;
                    // Add a new named character with 
                    // `updateParams` in your database.
                }
            },
        },
    },
};

There's various plugins that can create a query resolver for us depending on our data source:

A MonogDB query resolver is coming soon! If you'd like to implement a resolver for your own favorite database please let me know.

Now that we have a query resolver we can execute queries against it with MiniQL.

First we need a query, let's create one to get the character called "Darth Vader":

const getQuery = {
    get: { // This is a 'get' operation.
        character: {
            args: {
                name: "Darth Vader", // We are retrieving the record for Mr Vader.
            },
        },
    },
};

Now we can execute the get query to retreive the record for Mr Vader:

const context = {}; // Global context passed to our resolver.
const queryResult = await miniql(getQuery, queryResolver, {}); // Executes the query.
console.log(queryResult);

Here's the output of the query:

{
    "character": {
        "name": "Darth Vader",
        "height": 202,
        "mass": 136,
        "hair_color": "none",
        "skin_color": "white",
        "eye_color": "yellow",
        "birth_year": "41.9BBY",
        "gender": "male",
        "homeworld": "Tatooine",
        "species": "Human"
    }
}

Now let's execute an update query to modify mr Vader's record:

const updateQuery = {
    update: { // This is an 'update' operation.
        character: {
            args: {
                name: "Darth Vader",
                params: {
                    // Sets Mr Vaders hair color.
                    hair_color: "brown", // At least it was brown back when he had hair.
                },
            },
        },
    },
};

Now we execute the update query against our query resolver:

const context = {};
await miniql(updateQuery, queryResolver, {});

Mr Vader's hair color is now set to "brown".

Have fun with MiniQL!

More advanced documentation is coming soon! Follow for updates.

Wishlist

  • Parallelise complex queries over multiple nodes.

Support the developer

You can help support my work in any of the following ways: