ketr.photos/server/db/photos.js
James Ketrenos 1975b174a8 Functional for editing clusters; need to add merging
Signed-off-by: James Ketrenos <james_git@ketrenos.com>
2023-01-19 00:51:40 -08:00

260 lines
6.2 KiB
JavaScript
Executable File

/**
* * 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 */
},
faceScannedWith: {
type: Sequelize.INTEGER,
defaultValue: 0
},
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,
displayName: {
type: Sequelize.STRING,
allowNull: false
},
descriptors: Sequelize.BLOB /* average of all faces mapped to this */
}, {
timestamps: false
});
const FaceDescriptor = db.sequelize.define('facedescriptor', {
id: {
type: Sequelize.INTEGER,
primaryKey: true,
autoIncrement: true
},
descriptors: Sequelize.BLOB
}, {
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',
}
},
scanVersion: {
type: Sequelize.INTEGER,
/*
* 0 - original scan type
* 1 - Retinaface w/ 0.25% face margin
*/
defaultValue: 0
},
focus: { /* focal via laplacian variance https://pyimagesearch.com/2015/09/07/blur-detection-with-opencv/ */
type: Sequelize.DOUBLE,
defaultValue: 0
},
top: Sequelize.FLOAT, /* 0..1 * photoId.height */
left: Sequelize.FLOAT, /* 0..1 * photoId.width */
bottom: Sequelize.FLOAT, /* 0..1 * photoId.height */
right: Sequelize.FLOAT, /* 0..1 * photoId.width */
faceConfidence: { /* How confident that this is a face? */
type: Sequelize.DOUBLE,
defaultValue: 0
},
descriptorId: {
type: Sequelize.INTEGER,
allowNull: true,
references: {
model: FaceDescriptor,
key: 'id',
}
},
identityId: {
type: Sequelize.INTEGER,
allowNull: true,
references: {
model: Identity,
key: 'id',
}
},
classifiedBy: {
type: Sequelize.DataTypes.ENUM(
'machine',
'human',
'not-a-face'), /* implies "human"; identityId=NULL */
defaultValue: 'machine',
},
lastComparedId: {
type: Sequelize.INTEGER,
allowNull: true,
}
}, {
timestamps: false,
classMethods: {
associate: function() {
Album.hasOne(Face, {as:'Face', foreignKey: 'lastComparedId'});
}
}
});
const FaceDistances = db.sequelize.define('facedistance', {
descriptor1Id: {
type: Sequelize.INTEGER,
allowNull: false,
references: {
model: FaceDescriptor,
key: 'id',
}
},
descriptor2Id: {
type: Sequelize.INTEGER,
allowNull: false,
references: {
model: FaceDescriptor,
key: 'id',
}
},
distanceCosine: {
type: Sequelize.DOUBLE,
defaultValue: 1.0
},
distanceEuclidian: {
type: Sequelize.DOUBLE,
defaultValue: 1.0
},
distanceEuclidianL2: {
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();