README
# Apatite
Object persistence framework for Node.js. ORM framework supports: MySQL, Oracle, Postgres, SQL Server, Sqlite.
Features
- Based on object oriented principles.
- Zero dependencies.
- Transaction based.
- Generate (or execute) SQL scripts to create tables/columns for models/attributes.
- Apart from standard mappings, supports inheritence mapping too.
- Optional objects session cache management.
Prerequisites
- Node version >=12.13.1.
- oracledb if you plan to use Oracle: $ npm install oracledb@4.1.0
- pg if you plan to use Postgres: $ npm install pg@6.1.5
- mysql if you plan to use Mysql: $ npm install mysql@2.17.1
- tedious if you plan to use Microsoft SQL Server: $ npm install tedious@2.0.0, optionally for connection pool: tedious-connection-pool : $ npm install tedious-connection-pool@1.0.5
- sqlite3 if you plan to use Sqlite: $ npm install sqlite3@3.1.8
Installation
C:\my-project> npm install apatite
Quick Start
Install the prerequisites.
Create your class and define a static method getModelDescriptor which takes apatite as an argument.
class Department {
constructor() {
this.oid = 0;
this.name = '';
}
printName() {
console.log(this.name);
}
static getModelDescriptor(apatite) {
var table = apatite.newTable('DEPT');
var modelDescriptor = apatite.newModelDescriptor(this, table);
var column = table.addNewColumn('OID', apatite.dialect.newSerialType());
column.bePrimaryKey();
modelDescriptor.newSimpleMapping('oid', column);
column = table.addNewColumn('NAME', apatite.dialect.newVarCharType(100));
modelDescriptor.newSimpleMapping('name', column);
return modelDescriptor;
}
}
You could also create descriptor from a simple object:
static getModelDescriptor(apatite) {
var object = {
table: 'DEPT',
model: this,
mappings: [
{attr: 'oid', col: 'OID', pk: true, type: 'serial'},
{attr: 'name', col: 'NAME', type: 'varchar', length: 100}
]
}
return apatite.newDescriptorFromObject(object);
}
- Register your models.
// Oracle
var connOptions = { userName: 'apatite', password: 'apatite', connectionInfo: 'localhost/apatite' };
var apatite = require('apatite').forOracle(connOptions);
// Postgres
var connOptions = { userName: 'apatite', password: 'apatite', connectionInfo: 'localhost/apatite' };
var apatite = require('apatite').forPostgres(connOptions);
// Mysql
var connOptions = { userName: 'apatite', password: 'apatite', connectionInfo: 'localhost/apatite' };
var apatite = require('apatite').forMysql(connOptions);
// Mssql
var connOptions = { userName: 'apatite', password: 'apatite', connectionInfo: 'localhost/apatite' };
var apatite = require('apatite').forMssql(connOptions);
// Sqlite
var connOptions = { connectionInfo: ':memory:' };
var apatite = require('apatite').forSqlite(connOptions);
apatite.registerModel(Department);
- Create session and start querying your objects.
// Creates a new session and database connection
apatite.newSession(function (err, session) {
if (err) {
console.error(err.message);
return;
}
var query = session.newQuery(Department);
query.execute(function(err, departments) {
if (err) {
console.error(err.message);
return;
}
console.log(JSON.stringify(departments));
if (departments.length)
departments[0].printName();
endSession(session);
});
});
//closes the database connection
function endSession(session) {
session.end(function(err) {
if (err)
console.error(err.message);
})
}
// Using promise to execute queries
// Creates a new session and database connection
apatite.newSession(function (err, session) {
if (err) {
console.error(err.message);
return;
}
var query = session.newQuery(Department);
var promise = query.execute();
promise.then(function(departments) {
console.log(JSON.stringify(departments));
if (departments.length)
departments[0].printName();
endSession(session);
}, function(err) {
console.error(err.message);
endSession(session);
});
});
//closes the database connection
function endSession(session) {
session.end(function(err) {
if (err)
console.error(err.message);
})
}
//query results from cursor stream
apatite.newSession(function (err, session) {
var query = session.newQuery(Department)
query.returnCursorStream = true
query.execute(function (err, cursorStream) {
if (err) {
console.log(err)
return endSession(session)
}
cursorStream.on('error', function(cursorStreamErr) {
console.log(cursorStreamErr)
endSession(session)
})
cursorStream.on('result', function(department) {
console.log(JSON.stringify(department))
})
cursorStream.on('end', function() {
endSession(session)
})
})
})
function endSession(session) {
session.end(function (endConnErr) {
if (endConnErr)
return console.log(endConnErr)
console.log('Connection ended.')
})
}
- Do changes to your objects and save.
...
// Create new department
var department = new Department();
department.name = 'Sales';
// Register it to session
var changesToDo = function (changesDone) {
session.registerNew(department);
changesDone(); // must be called when you are done with all changes
}
session.doChangesAndSave(changesToDo, function (saveErr) {
if (saveErr)
console.error(saveErr.message);
});
...
...
// Change an existing department
var query = session.newQuery(Department);
query.attr('name').eq('Sales');
// Or you could create query from an array
// const query = session.newQueryFromArray(Department, [['name', '=', 'Sales']])
query.execute(function(executeErr, departments) {
if (executeErr) {
return console.error(executeErr);
}
var changesToDo = function (changesDone) {
departments[0].name = 'Pre-Sales';
changesDone(); // must be called when you are done with all changes
}
session.doChangesAndSave(changesToDo, function (saveErr) {
if (saveErr)
console.error(saveErr.message);
});
});
...
...
// Delete an existing department
var changesToDo = function (changesDone) {
var query = session.newQuery(Department);
query.attr('name').eq('Pre-Sales');
// Or you could create query from an array
// const query = session.newQueryFromArray(Department, [['name', '=', 'Pre-Sales']])
query.execute(function(executeErr, departments) {
if (executeErr) {
changesDone(executeErr);
return;
}
session.registerDelete(departments[0]);
changesDone(); // must be called when you are done with all changes
});
}
session.doChangesAndSave(changesToDo, function (saveErr) {
if (saveErr)
console.error(saveErr.message);
});
...
Contributions
Welcome.
Links
Tests
Install all supported databases and then install dependencies:
C:\my-project> npm install
Run the tests:
C:\my-project> npm test