mirror of
https://github.com/DeviceFarmer/stf.git
synced 2026-04-18 00:53:19 +02:00
update built-in objects in the database (#846)
Signed-off-by: Denis barbaron <denis.barbaron@orange.com>
This commit is contained in:
@@ -1,5 +1,5 @@
|
||||
/**
|
||||
* Copyright © 2019 contains code contributed by Orange SA, authors: Denis Barbaron - Licensed under the Apache license 2.0
|
||||
* Copyright © 2019-2025 contains code contributed by Orange SA, authors: Denis Barbaron - Licensed under the Apache license 2.0
|
||||
**/
|
||||
|
||||
module.exports.command = 'migrate'
|
||||
@@ -23,20 +23,23 @@ module.exports.handler = function() {
|
||||
return new Promise(function(resolve, reject) {
|
||||
setTimeout(function() {
|
||||
return dbapi.getGroupByIndex(apiutil.ROOT, 'privilege').then(function(group) {
|
||||
// signatures of built-in objects are defined
|
||||
const env = {
|
||||
STF_ROOT_GROUP_NAME: group ? group.name : 'Common'
|
||||
, STF_ADMIN_NAME: group ? group.owner.name : 'administrator'
|
||||
, STF_ADMIN_EMAIL: group ? group.owner.email : 'administrator@fakedomain.com'
|
||||
}
|
||||
for (const i in env) {
|
||||
if (process.env[i]) {
|
||||
env[i] = process.env[i]
|
||||
}
|
||||
}
|
||||
if (!group) {
|
||||
const env = {
|
||||
STF_ROOT_GROUP_NAME: 'Common'
|
||||
, STF_ADMIN_NAME: 'administrator'
|
||||
, STF_ADMIN_EMAIL: 'administrator@fakedomain.com'
|
||||
}
|
||||
for (const i in env) {
|
||||
if (process.env[i]) {
|
||||
env[i] = process.env[i]
|
||||
}
|
||||
}
|
||||
// root group does not exist, so bootstrap is created
|
||||
return dbapi.createBootStrap(env)
|
||||
}
|
||||
return group
|
||||
// bootstrap is updated with new signatures
|
||||
return dbapi.updateBootStrap(group, env)
|
||||
})
|
||||
.then(function() {
|
||||
resolve(true)
|
||||
|
||||
166
lib/db/api.js
166
lib/db/api.js
@@ -14,6 +14,15 @@ const uuid = require('uuid')
|
||||
const apiutil = require('../util/apiutil')
|
||||
const Promise = require('bluebird')
|
||||
const _ = require('lodash')
|
||||
const logger = require('../util/logger')
|
||||
const log = logger.createLogger('db:api')
|
||||
|
||||
function getDevices() {
|
||||
return db.run(r.table('devices'))
|
||||
.then(function(cursor) {
|
||||
return cursor.toArray()
|
||||
})
|
||||
}
|
||||
|
||||
dbapi.DuplicateSecondaryIndexError = function DuplicateSecondaryIndexError() {
|
||||
Error.call(this)
|
||||
@@ -35,6 +44,156 @@ dbapi.unlockBookingObjects = function() {
|
||||
])
|
||||
}
|
||||
|
||||
dbapi.updateBootStrap = function(rootGroup, env) {
|
||||
const rootGroupNameHasChanged = rootGroup.name !== env.STF_ROOT_GROUP_NAME
|
||||
const adminEmailHasChanged = rootGroup.owner.email !== env.STF_ADMIN_EMAIL
|
||||
const adminNameHasChanged = rootGroup.owner.name !== env.STF_ADMIN_NAME
|
||||
|
||||
function createNewAdminUser() {
|
||||
if (!adminEmailHasChanged) {
|
||||
if (adminNameHasChanged) {
|
||||
log.error('Forbidden (user name cannot be changed)')
|
||||
return Promise.resolve(false)
|
||||
}
|
||||
return Promise.resolve(true)
|
||||
}
|
||||
|
||||
return dbapi.createUser(env.STF_ADMIN_EMAIL,
|
||||
env.STF_ADMIN_NAME,
|
||||
'127.0.0.1').then(function(stats) {
|
||||
if (!stats.inserted) {
|
||||
log.error('Forbidden (user already exists)')
|
||||
return false
|
||||
}
|
||||
log.info('Created (user name:%s email:%s)'
|
||||
, env.STF_ADMIN_NAME
|
||||
, env.STF_ADMIN_EMAIL)
|
||||
|
||||
return dbapi.loadUser(rootGroup.owner.email).then(function(oldAdminUser) {
|
||||
return db.run(r.table('users').get(env.STF_ADMIN_EMAIL).update({
|
||||
privilege: oldAdminUser.privilege
|
||||
, groups: oldAdminUser.groups
|
||||
, settings: oldAdminUser.settings
|
||||
}))
|
||||
})
|
||||
})
|
||||
.catch(function(err) {
|
||||
log.error('Failed to create user')
|
||||
return Promise.reject(err)
|
||||
})
|
||||
}
|
||||
|
||||
function updateDevicesForMigration() {
|
||||
return getDevices().then(function(devices) {
|
||||
return Promise.map(devices, function(device) {
|
||||
return db.run(r.table('devices').get(device.serial).update({
|
||||
group: {
|
||||
name:
|
||||
r.branch(
|
||||
r.expr(rootGroupNameHasChanged)
|
||||
.eq(true)
|
||||
.and(r.row('group')('id')
|
||||
.eq(rootGroup.id))
|
||||
, env.STF_ROOT_GROUP_NAME
|
||||
, r.row('group')('name'))
|
||||
, originName:
|
||||
r.branch(
|
||||
r.expr(rootGroupNameHasChanged)
|
||||
.eq(true)
|
||||
.and(r.row('group')('origin')
|
||||
.eq(rootGroup.id))
|
||||
, env.STF_ROOT_GROUP_NAME
|
||||
, r.row('group')('originName'))
|
||||
, owner:
|
||||
r.branch(
|
||||
r.expr(adminEmailHasChanged)
|
||||
.eq(true)
|
||||
.and(r.row('group')('id')
|
||||
.eq(rootGroup.id))
|
||||
, {
|
||||
name: env.STF_ADMIN_NAME
|
||||
, email: env.STF_ADMIN_EMAIL
|
||||
}
|
||||
, r.row('group')('owner'))
|
||||
}
|
||||
}))
|
||||
})
|
||||
})
|
||||
}
|
||||
|
||||
function updateGroupsForMigration() {
|
||||
if (rootGroupNameHasChanged && !adminEmailHasChanged) {
|
||||
return db.run(r.table('groups').get(rootGroup.id).update({
|
||||
name: env.STF_ROOT_GROUP_NAME
|
||||
}))
|
||||
}
|
||||
|
||||
return dbapi.getGroups().then(function(groups) {
|
||||
return Promise.map(groups, function(group) {
|
||||
return db.run(r.table('groups').get(group.id).update({
|
||||
name:
|
||||
r.branch(
|
||||
r.expr(rootGroupNameHasChanged)
|
||||
.eq(true)
|
||||
.and(r.row('id')
|
||||
.eq(rootGroup.id))
|
||||
, env.STF_ROOT_GROUP_NAME
|
||||
, r.row('name'))
|
||||
, owner:
|
||||
r.branch(
|
||||
r.expr(adminEmailHasChanged)
|
||||
.eq(true)
|
||||
.and(r.row('owner')('email')
|
||||
.eq(rootGroup.owner.email))
|
||||
, {
|
||||
name: env.STF_ADMIN_NAME
|
||||
, email: env.STF_ADMIN_EMAIL
|
||||
}
|
||||
, r.row('owner'))
|
||||
, users:
|
||||
r.branch(
|
||||
r.expr(adminEmailHasChanged)
|
||||
.eq(true)
|
||||
, _.union([env.STF_ADMIN_EMAIL], _.difference(group.users, [rootGroup.owner.email]))
|
||||
, r.row('users'))
|
||||
}))
|
||||
})
|
||||
})
|
||||
}
|
||||
|
||||
return createNewAdminUser().then(function(success) {
|
||||
if (!success || !rootGroupNameHasChanged && !adminEmailHasChanged) {
|
||||
return false
|
||||
}
|
||||
|
||||
return updateGroupsForMigration().then(function() {
|
||||
return updateDevicesForMigration()
|
||||
})
|
||||
.then(function() {
|
||||
if (adminEmailHasChanged) {
|
||||
return dbapi.removeUserAccessTokens(rootGroup.owner.email)
|
||||
}
|
||||
return true
|
||||
})
|
||||
.then(function() {
|
||||
if (adminEmailHasChanged) {
|
||||
return dbapi.deleteUser(rootGroup.owner.email)
|
||||
}
|
||||
return true
|
||||
})
|
||||
})
|
||||
.then(function(success) {
|
||||
if (success) {
|
||||
log.info('Built-in objects have been updated successfully')
|
||||
}
|
||||
return success
|
||||
})
|
||||
.catch(function(err) {
|
||||
log.error('Failed to update built-in objects, potential data consistency issue')
|
||||
return Promise.reject(err)
|
||||
})
|
||||
}
|
||||
|
||||
dbapi.createBootStrap = function(env) {
|
||||
const now = Date.now()
|
||||
|
||||
@@ -78,13 +237,6 @@ dbapi.createBootStrap = function(env) {
|
||||
})
|
||||
}
|
||||
|
||||
function getDevices() {
|
||||
return db.run(r.table('devices'))
|
||||
.then(function(cursor) {
|
||||
return cursor.toArray()
|
||||
})
|
||||
}
|
||||
|
||||
function updateDevicesForMigration(group) {
|
||||
return getDevices().then(function(devices) {
|
||||
return Promise.map(devices, function(device) {
|
||||
|
||||
Reference in New Issue
Block a user