/** * * Copyright (c) 2016, Intel Corporation. * * This program is licensed under the terms and conditions of the * Apache License, version 2.0. The full text of the Apache License is at * http://www.apache.org/licenses/LICENSE-2.0 */ "use strict"; /** * This class will instantiate the ORM, load in the models, call the method * to create db connections, test the connection, then create the tables and * relationships if not present */ const fs = require('fs'), path = require('path'), Sequelize = require('sequelize'), config = require('config'); function init() { const db = { sequelize: new Sequelize(config.get("db.photos")), Sequelize: Sequelize }; return db.sequelize.authenticate().then(function () { const Album = db.sequelize.define('album', { id: { type: Sequelize.INTEGER, primaryKey: true, autoIncrement: true }, path: Sequelize.STRING, name: Sequelize.STRING, parentId: { type: Sequelize.INTEGER, allowNull: true } }, { timestamps: false, classMethods: { associate: function() { Album.hasOne(Album, {as:'Album', foreignKey: 'parentId'}); } } }); const Photo = db.sequelize.define('photo', { id: { type: Sequelize.INTEGER, primaryKey: true, autoIncrement: true }, name: Sequelize.STRING, filename: Sequelize.STRING, added: Sequelize.DATE, modified: Sequelize.DATE, updated: Sequelize.DATE, scanned: Sequelize.DATE, taken: Sequelize.DATE, width: Sequelize.INTEGER, height: Sequelize.INTEGER, size: Sequelize.INTEGER, faces: { type: Sequelize.INTEGER, defaultValue: -1 /* not scanned */ }, duplicate: { type: Sequelize.BOOLEAN, defaultValue: 0 }, deleted: { type: Sequelize.BOOLEAN, defaultValue: 0 }, albumId: { type: Sequelize.INTEGER, allowNull: true, references: { model: Album, key: 'id', } } }, { timestamps: false }); const Identity = db.sequelize.define('identity', { id: { type: Sequelize.INTEGER, primaryKey: true, autoIncrement: true }, lastName: Sequelize.STRING, firstName: Sequelize.STRING, middleName: Sequelize.STRING, name: { type: Sequelize.STRING, allowNull: false } }, { timestamps: false }); const Face = db.sequelize.define('face', { id: { type: Sequelize.INTEGER, primaryKey: true, autoIncrement: true }, photoId: { type: Sequelize.INTEGER, allowNull: false, references: { model: Photo, key: 'id', } }, identityId: { type: Sequelize.INTEGER, allowNull: true, references: { model: Identity, key: 'id', } }, identityDistance: { /* How far are markers from identity match? */ type: Sequelize.DOUBLE, defaultValue: -1.0 }, faceConfidence: { /* How confident that this is a face? */ type: Sequelize.DOUBLE, defaultValue: 0 }, lastComparedId: { type: Sequelize.INTEGER, allowNull: true, }, top: Sequelize.FLOAT, /* 0..1 * photo.height */ left: Sequelize.FLOAT, /* 0..1 * photo.width */ bottom: Sequelize.FLOAT, /* 0..1 * photo.height */ right: Sequelize.FLOAT, /* 0..1 * photo.width */ }, { timestamps: false, classMethods: { associate: function() { Album.hasOne(Face, {as:'Face', foreignKey: 'lastComparedId'}); } } }); const FaceDescriptor = db.sequelize.define('facedescriptor', { faceId: { type: Sequelize.INTEGER, primaryKey: true, references: { model: Face, key: 'id', } }, descriptors: Sequelize.BLOB }, { timestamps: false }); const FaceDistances = db.sequelize.define('facedistance', { face1Id: { type: Sequelize.INTEGER, allowNull: false, references: { model: Face, key: 'id', } }, face2Id: { type: Sequelize.INTEGER, allowNull: false, references: { model: Face, key: 'id', } }, distance: { type: Sequelize.DOUBLE, defaultValue: 1.0 } }, { timestamps: false }); const PhotoHash = db.sequelize.define('photohash', { hash: { type: Sequelize.STRING, primaryKey: true, unique: true }, photoId: { type: Sequelize.INTEGER, allowNull: true, references: { model: Photo, key: 'id', } } }, { timestamps: false }); return db.sequelize.sync({ force: false }).then(function () { return db; }); }).catch(function (error) { console.log("ERROR: Failed to authenticate with PHOTOS DB"); console.log("ERROR: " + JSON.stringify(config.get("db"), null, 2)); console.log(error); throw error; }); } module.exports = init();