krypton-orm

    0.0.16 • Public • Published

    Build Status Code Climate Test Coverage NPM

    Krypton ORM

    Krypton is a full featured Javascript ORM for SQL Databases

    Krypton Features:

    • Declarative way of defining models
    • Mechanism to eager load relations *
    • Use the full feature-set of Knex.js *
    • Easy to use transactions *
    • Easy to declare validations
    • Promise based

    * Work in progress

    Constraints

    • Build arround Neon
    • Use Knex as the query builder
    • DB column_names must be snake_case
    • Don't handle migrations
    • Don't handle database schema creation

    TODO

    • This README
    • Add more relation types, currently there are HasOne, HasMany and HasManyThrough.
    • Add transactions

    Examples

    var Knex = require('knex');
     
    // Create a knex instance
    var knex = Knex({
      client: 'postgres',
      connection: {
        database: 'database-name',
        user:     'DBUser',
        password: 'DBPass'
      }
    });
     
    // Log queries
    knex.on('query', function(data) {
      console.log(data);
    });
     
    // Bind the knex instance to the Krypton Base Model Class
    // (Yes you can have multiple knex instances binded to different Models :) )
    Krypton.Model.knex(knex);
     
    // Create some Models
    Class('Voice').inherits(Krypton.Model)({
      tableName : 'Voices',
     
      /*
        attributes are used for validation (whitelist) at saving. Whenever a
        model instance is saved it is checked against this schema.
      */
      attributes : ['id', 'title', 'description', 'createdAt', 'updatedAt']
    });
     
    Class('Entity').inherits(Krypton.Model)({
      tableName : 'Entities',
     
      attributes : ['id', ..., 'createdAt', 'updatedAt']
    })
     
    // This object defines the relations to other models.
    // I intentionaly declared this outside the Entity Class because it has a circular
    // relation ('organizations')
    Entity.relations = {
      voices : {
        type : 'HasMany',
        relatedModel : Voice,
        ownerCol : 'id',
        relatedCol : 'owner_id'
      },
     
      organizations : {
        type : 'HasManyThrough',
        relatedModel : Entity,
        ownerCol : 'id',
        relatedCol : 'id',
        scope : ['Entities.type', '=', 'organization'],
        through : {
            tableName : 'EntityOwner',
            ownerCol : 'owner_id',
            relatedCol : 'owned_id'
            scope : null
        }
      }
    }
     
    Class('User').inherits(Krypton.Model)({
      tableName : 'Users',
     
      attributes : ['id', ..., 'createdAt', 'updatedAt'],
     
      relations : {
        entity : {
          type : 'HasOne',
          relatedModel : Entity,
          ownerCol : 'entity_id',
          relatedCol : 'id'
        }
      }
    });

    Queries

    var userQuery = User.query();
    // => returns a QueryBuilder instance
     
    userQuery.where({id : 1});
    // or userQuery.where('id', '<', 5) or whatever knex expression you want to use.
     
     
    // include(relationExpression)
    // Relation expression is a simple DSL for expressing relation trees.
    userQuery.include('entity.[voices, organizations]');
    // This means: Load the User(s) and its entity and the voices of its entity and the organizations of its entity
     
    userQuery.then(function(result) {
      console.log(result)
    });
     

    ActiveRecord Style callbacks

    Callbacks are hooks into the life cycle of an Krypton Model instance that allow you to trigger logic before or after an alteration of the object state.

    • Implemented callbacks:
      • beforeValidation
      • afterValidation
      • beforeSave
      • beforeCreate
      • beforeUpdate
      • afterCreate
      • afterUpdate
      • afterSave
      • beforeDestroy
      • afterDestroy

    API:

    // @property on <public> [Function]
    // @method
    // @argument hook <required> [String]
    // @argument handler(callback) <required> [Function]
    // @return this;

    Examples:

    Model('User').inherits(Krypton.Model)({
        prototype : {
            init : function(config) {
                Krypton.Model.prototype.init.call(this, config);
     
                var model = this;
     
                model.on('beforeValidation', function(next) {
                    bcrypt.hash(model.password, null, null, function(err, hash) {
                        model.encryptedPassword = hash;
                        delete model.password;
                        next();
                    });
                });
     
                model.on('beforeValidation', function(next) {
                    model.count++
                });
            }
        }
    });

    OR

    var user = new User();
     
    user.on('beforeUpdate', handler(callback))

    Note on Krypton Knex instance handling

    Krypton.Model defines a class method named ::knex(), this method returns the Knex instance that has been assigned to the Class (with ::knex(knex)) or throws an error if none is available.

    Internally #create(), #query(), #update() and #destroy() all use the provided Knex instance (in their params), the model instance's ._knex or the instance returned by ::knex().

    If one of those methods receives a Knex instance they will set the model instance's ._knex property, which the model stuff can make use of. Before this happens the model instance's ._knex property is undefined.

    Install

    npm i krypton-orm

    DownloadsWeekly Downloads

    20

    Version

    0.0.16

    License

    MIT

    Last publish

    Collaborators

    • sgarza