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

eidolon

v1.6.0

Published

Generate JSON or JSON Schema from Refract & MSON data structures

Downloads

27

Readme

Eidolon

Build Status Coverage Status NPM version License

Generate examples and JSON Schema from Refract data structures. Data structures can come from MSON or other input sources.

Given the following MSON attributes from e.g. API Blueprint:

+ Attributes
  + name: Daniel (required) - User's first name
  + age: 10 (required, number) - Age in years

It would generate the following JSON example and JSON Schema:

{
  "name": "Daniel",
  "age": 10
}
{
  "$schema": "http://json-schema.org/draft-04/schema#",
  "type": "object",
  "required": ["name", "age"],
  "properties": {
    "name": {
      "type": "string",
      "description": "User's first name"
    },
    "age": {
      "type": "number",
      "description": "Age in years"
    }
  }
}

Installation & Usage

This project is available via npm:

npm install eidolon

There are two ways to use the module: either via module-level methods or by instantiating a class instance.

import eidolon, {Eidolon} from 'eidolon';

const input = {"element": "string", "content": "Hello"};
const dataStructures = {};

let example, schema;

// Method 1: module methods
example = eidolon.example(input, dataStructures, options);
schema = eidolon.schema(input, dataStructures);

// Method 2: class instance
const instance = new Eidolon(dataStructures, options);
example = instance.example(input);
schema = instance.schema(input);

Choose whichever method better suits your use case.

Example & Schema Serialization

Examples and JSON Schema are created as plain Javascript objects. As such, they can be serialized into various formats, such as JSON, YAML, and other more esoteric formats. In the case of JSON Schema, it probably makes the most sense to stick with JSON.

example = instance.example(input);

// Print as JSON
console.log(JSON.stringify(example, null, 2));

// Print as YAML (after `npm install js-yaml`)
import yaml from 'js-yaml';
console.log(yaml.safeDump(example));

Features

The following features are supported by the example and JSON Schema generators. Note that not all MSON features are supported (yet)!

Example Generator

  • Simple types, enums, arrays, objects
  • Property descriptions
  • References
  • Mixins (Includes)
  • Arrays with members of different types
  • One Of properties (the first is always selected)
  • Circular references generated as null

JSON Schema Generator

  • Simple types, enums, arrays, objects
  • Property descriptions
  • Required, default, nullable properties
  • References
  • Mixins (Includes)
  • Arrays with members of different types
  • One Of (mutually exclusive) properties
  • Circular references generated as an empty schema

Notable Missing Features

The following list of features in no particular order are known to be missing or cause issues. Please feel free to open a pull request with new features and fixes based on this list! wink wink nudge nudge :beers:

  • Better support for circular references
  • Variable values
  • Variable property names
  • Variable type names
  • Extend element support
  • Remote referenced elements (e.g. via HTTP)
  • Namespace prefixes

Link Relations

Elements may be given link relations when dereferencing or processing inheritance that help to describe the origin of a particular element, such as wheterh it was included vs. inherited or whether the element constitutes a circular reference to a previous element in the hierarchy.

Inheritance

Inheritance link relations come in two forms. The first, called inherited is for the element which inherits from another element. The second, called inherited-member is for elements of type member within an object that have been inherited from a parent object. MSON example:

# MyObject (MyBase):
+ id (number)

Inclusion

Inclusion link relations are for elements of type member within an object that have been included from a parent object. MSON example:

# MyObject
+ Include MyBase

Circular References

Circular reference link relations are for elements whose ancestral chain contains itself, causing a loop. Processing will stop and this link relation will be added so you can detect this case. MSON example:

# Person
+ address (Address)

# Address
+ owner (Person)

Origins and Link Definitions

Description | Relation | Href ------------------ | -------- | ---- Inherited | origin | http://refract.link/inherited/ Inherited member | origin | http://refract.link/inherited-member/ Included member | origin | http://refract.link/included-member/ Circular reference | origin | http://refract.link/circular-reference/

Reference

eidolon.Eidolon([dataStructures], [options])

This class is used to save state between calls to example and schema. It is used just like the functions below, except that you pass your data structures to the constructor instead of to each method.

Available options:

Option Name | Description | Default ------------ | ----------- | ------- defaultValue | Function to generate a default value function (refractElement, path) | Built-in eidolon.defaultValue. seed | Seed for the random generator used to create default values | -

import {Eidolon} from 'eidolon';

const instance = new Eidolon();
const input = {element: 'string', content: 'hello'};

let example = instance.example(input);
let schema = instance.schema(input);
let dereferenced = instance.dereference(input);

eidolon.example(input, [dataStructures], [options])

Generate a new example from the given input refract object and an optional mapping of data structures, where the key is the data structure name and the value is the data structure definition.

Available options are described in the Eidolon class above.

import eidolon from 'eidolon';

const input = {element: 'string', content: 'hello'};
let example = eidolon.example(input);

eidolon.schema(input, [dataStructures])

Generate a new JSON schema from the given input refract object and an optional mapping of data structures, where the key is the data structure name and the value is the data structure definition.

import eidolon from 'eidolon';

const input = {element: 'string', content: 'hello'};
let schema = eidolon.schema(input);

eidolon.dereference(input, [dataStructures], [known])

Dereference an input element or structure of elements with the given data structures. This will return the same element or structure with resolved references so you do not have to handle inheritance or object includes. Each resolved reference will include the name of the referenced type or mixin in the meta.ref property. If given, known is an array of element names from ancestors of this element, used to detect circular references.

import eidolon from 'eidolon';

const input = {
  element: 'MyString'
};
const dataStructures = {
  MyElement: {
    element: 'string',
    meta: {
      id: 'MyString'
    },
    content: 'Hello, world!'
  }
};

let dereferenced = eidolon.dereference(input, dataStructures);

console.log(dereferenced.element);  // => 'string'
console.log(dereferenced.content);  // => 'Hello, world!'
console.log(dereferenced.meta.ref); // => 'MyString'

eidolon.inherit(base, element)

Generate a new element with merged properties from both base and element, taking care to prevent duplicate members. This utility can be used when traversing the element tree.

import eidolon from 'eidolon';

const base = {
  element: 'number',
  meta: {
    id: 'NullableNumber',
    default: 0
  },
  attributes: {
    typeAttributes: ['nullable']
  }
};

const element = {
  element: 'NullableNumber',
  attributes: {
    default: 2
  },
  content: 10
}

let merged = eidolon.inherit(base, element);

// Merged now looks like:
{
  element: 'number',
  meta: {
    ref: 'NullableNumber',
    links: [
      {
        relation: 'origin',
        href: 'http://refract.link/inherited/'
      }
    ]
  },
  attributes: {
    default: 2,
    typeAttributes: ['nullable']
  },
  content: 10
}

License

Copyright © 2016 Daniel G. Taylor

http://dgt.mit-license.org/