feat: changed old server ports so it can coexists with the new server
feat: removed deleted references from old server feat: created reset and migrate mutations on gql server and correspondent functions on new settings loader feat: created front end for the config migration with reset and migrate functionalities style: add spacing between buttons Signed-off-by: Liordino Neto <liordinoneto@gmail.com>
This commit is contained in:
parent
368d528ee2
commit
df8a1804a3
6 changed files with 144 additions and 65 deletions
|
|
@ -31,7 +31,6 @@ const server = require('./server')
|
||||||
const transactions = require('./transactions')
|
const transactions = require('./transactions')
|
||||||
const customers = require('../customers')
|
const customers = require('../customers')
|
||||||
const logs = require('../logs')
|
const logs = require('../logs')
|
||||||
const supportLogs = require('../support_logs')
|
|
||||||
const funding = require('./funding')
|
const funding = require('./funding')
|
||||||
const supportServer = require('./admin-support')
|
const supportServer = require('./admin-support')
|
||||||
|
|
||||||
|
|
@ -208,29 +207,6 @@ app.get('/api/logs', (req, res, next) => {
|
||||||
.catch(next)
|
.catch(next)
|
||||||
})
|
})
|
||||||
|
|
||||||
app.get('/api/support_logs', (req, res, next) => {
|
|
||||||
return supportLogs.batch()
|
|
||||||
.then(supportLogs => res.send({ supportLogs }))
|
|
||||||
.catch(next)
|
|
||||||
})
|
|
||||||
|
|
||||||
app.get('/api/support_logs/logs', (req, res, next) => {
|
|
||||||
return supportLogs.get(req.query.supportLogId)
|
|
||||||
.then(log => (!_.isNil(log) && !_.isEmpty(log)) ? log : supportLogs.batch().then(_.first))
|
|
||||||
.then(result => {
|
|
||||||
const log = result || {}
|
|
||||||
return logs.getMachineLogs(log.deviceId, log.timestamp)
|
|
||||||
})
|
|
||||||
.then(r => res.send(r))
|
|
||||||
.catch(next)
|
|
||||||
})
|
|
||||||
|
|
||||||
app.post('/api/support_logs', (req, res, next) => {
|
|
||||||
return supportLogs.insert(req.query.deviceId)
|
|
||||||
.then(r => res.send(r))
|
|
||||||
.catch(next)
|
|
||||||
})
|
|
||||||
|
|
||||||
app.patch('/api/customer/:id', (req, res, next) => {
|
app.patch('/api/customer/:id', (req, res, next) => {
|
||||||
if (!req.params.id) return res.status(400).send({Error: 'Requires id'})
|
if (!req.params.id) return res.status(400).send({Error: 'Requires id'})
|
||||||
const token = req.token || req.cookies.token
|
const token = req.token || req.cookies.token
|
||||||
|
|
@ -349,7 +325,7 @@ wss.on('connection', ws => {
|
||||||
})
|
})
|
||||||
|
|
||||||
function run () {
|
function run () {
|
||||||
const serverPort = devMode ? 8070 : 443
|
const serverPort = devMode ? 8072 : 443
|
||||||
const supportPort = 8071
|
const supportPort = 8071
|
||||||
|
|
||||||
const serverLog = `lamassu-admin-server listening on port ${serverPort}`
|
const serverLog = `lamassu-admin-server listening on port ${serverPort}`
|
||||||
|
|
|
||||||
|
|
@ -10,8 +10,6 @@ const _ = require('lodash/fp')
|
||||||
const serveStatic = require('serve-static')
|
const serveStatic = require('serve-static')
|
||||||
const path = require('path')
|
const path = require('path')
|
||||||
|
|
||||||
const logs = require('../logs')
|
|
||||||
const supportLogs = require('../support_logs')
|
|
||||||
const options = require('../options')
|
const options = require('../options')
|
||||||
|
|
||||||
app.use(morgan('dev'))
|
app.use(morgan('dev'))
|
||||||
|
|
@ -30,29 +28,6 @@ const certOptions = {
|
||||||
rejectUnauthorized: true
|
rejectUnauthorized: true
|
||||||
}
|
}
|
||||||
|
|
||||||
app.get('/api/support_logs', (req, res, next) => {
|
|
||||||
return supportLogs.batch()
|
|
||||||
.then(supportLogs => res.send({ supportLogs }))
|
|
||||||
.catch(next)
|
|
||||||
})
|
|
||||||
|
|
||||||
app.get('/api/support_logs/logs', (req, res, next) => {
|
|
||||||
return supportLogs.get(req.query.supportLogId)
|
|
||||||
.then(log => (!_.isNil(log) && !_.isEmpty(log)) ? log : supportLogs.batch().then(_.first))
|
|
||||||
.then(result => {
|
|
||||||
const log = result || {}
|
|
||||||
return logs.getUnlimitedMachineLogs(log.deviceId, log.timestamp)
|
|
||||||
})
|
|
||||||
.then(r => res.send(r))
|
|
||||||
.catch(next)
|
|
||||||
})
|
|
||||||
|
|
||||||
app.post('/api/support_logs', (req, res, next) => {
|
|
||||||
return supportLogs.insert(req.query.deviceId)
|
|
||||||
.then(r => res.send(r))
|
|
||||||
.catch(next)
|
|
||||||
})
|
|
||||||
|
|
||||||
function run (port) {
|
function run (port) {
|
||||||
return new Promise((resolve, reject) => {
|
return new Promise((resolve, reject) => {
|
||||||
const webServer = https.createServer(certOptions, app)
|
const webServer = https.createServer(certOptions, app)
|
||||||
|
|
|
||||||
|
|
@ -271,8 +271,11 @@ const typeDefs = gql`
|
||||||
machineAction(deviceId:ID!, action: MachineAction!, cassette1: Int, cassette2: Int, newName: String): Machine
|
machineAction(deviceId:ID!, action: MachineAction!, cassette1: Int, cassette2: Int, newName: String): Machine
|
||||||
setCustomer(customerId: ID!, customerInput: CustomerInput): Customer
|
setCustomer(customerId: ID!, customerInput: CustomerInput): Customer
|
||||||
saveConfig(config: JSONObject): JSONObject
|
saveConfig(config: JSONObject): JSONObject
|
||||||
|
resetConfig(schemaVersion: Int): JSONObject
|
||||||
createPairingTotem(name: String!): String
|
createPairingTotem(name: String!): String
|
||||||
saveAccounts(accounts: JSONObject): JSONObject
|
saveAccounts(accounts: JSONObject): JSONObject
|
||||||
|
resetAccounts(schemaVersion: Int): JSONObject
|
||||||
|
migrateConfigAndAccounts: JSONObject
|
||||||
revokeToken(token: String!): UserToken
|
revokeToken(token: String!): UserToken
|
||||||
deleteBlacklistRow(cryptoCode: String!, address: String!): Blacklist
|
deleteBlacklistRow(cryptoCode: String!, address: String!): Blacklist
|
||||||
insertBlacklistRow(cryptoCode: String!, address: String!): Blacklist
|
insertBlacklistRow(cryptoCode: String!, address: String!): Blacklist
|
||||||
|
|
@ -331,6 +334,7 @@ const resolvers = {
|
||||||
machineAction: (...[, { deviceId, action, cassette1, cassette2, newName }]) => machineAction({ deviceId, action, cassette1, cassette2, newName }),
|
machineAction: (...[, { deviceId, action, cassette1, cassette2, newName }]) => machineAction({ deviceId, action, cassette1, cassette2, newName }),
|
||||||
createPairingTotem: (...[, { name }]) => pairing.totem(name),
|
createPairingTotem: (...[, { name }]) => pairing.totem(name),
|
||||||
saveAccounts: (...[, { accounts }]) => settingsLoader.saveAccounts(accounts),
|
saveAccounts: (...[, { accounts }]) => settingsLoader.saveAccounts(accounts),
|
||||||
|
resetAccounts: (...[, { schemaVersion }]) => settingsLoader.resetAccounts(schemaVersion),
|
||||||
setCustomer: (root, args, context, info) => {
|
setCustomer: (root, args, context, info) => {
|
||||||
const token = context.req.cookies && context.req.cookies.token
|
const token = context.req.cookies && context.req.cookies.token
|
||||||
return customers.updateCustomer(args.customerId, args.customerInput, token)
|
return customers.updateCustomer(args.customerId, args.customerInput, token)
|
||||||
|
|
@ -340,6 +344,8 @@ const resolvers = {
|
||||||
notify()
|
notify()
|
||||||
return it
|
return it
|
||||||
}),
|
}),
|
||||||
|
resetConfig: (...[, { schemaVersion }]) => settingsLoader.resetConfig(schemaVersion),
|
||||||
|
migrateConfigAndAccounts: () => settingsLoader.migrate(),
|
||||||
deleteBlacklistRow: (...[, { cryptoCode, address }]) =>
|
deleteBlacklistRow: (...[, { cryptoCode, address }]) =>
|
||||||
blacklist.deleteFromBlacklist(cryptoCode, address),
|
blacklist.deleteFromBlacklist(cryptoCode, address),
|
||||||
insertBlacklistRow: (...[, { cryptoCode, address }]) =>
|
insertBlacklistRow: (...[, { cryptoCode, address }]) =>
|
||||||
|
|
|
||||||
|
|
@ -1,21 +1,33 @@
|
||||||
const _ = require('lodash/fp')
|
const _ = require('lodash/fp')
|
||||||
const db = require('./db')
|
const db = require('./db')
|
||||||
|
const migration = require('./config-migration')
|
||||||
|
|
||||||
|
const OLD_SETTINGS_LOADER_SCHEMA_VERSION = 1
|
||||||
const NEW_SETTINGS_LOADER_SCHEMA_VERSION = 2
|
const NEW_SETTINGS_LOADER_SCHEMA_VERSION = 2
|
||||||
|
|
||||||
|
const accountsSql = `update user_config set data = $2, valid = $3, schema_version = $4 where type = $1;
|
||||||
|
insert into user_config (type, data, valid, schema_version)
|
||||||
|
select $1, $2, $3, $4 where $1 not in (select type from user_config)`
|
||||||
function saveAccounts (accountsToSave) {
|
function saveAccounts (accountsToSave) {
|
||||||
const sql = `update user_config set data = $2, valid = $3, schema_version = $4 where type = $1;
|
|
||||||
insert into user_config (type, data, valid, schema_version)
|
|
||||||
select $1, $2, $3, $4 where $1 not in (select type from user_config)`
|
|
||||||
|
|
||||||
return loadAccounts()
|
return loadAccounts()
|
||||||
.then(currentAccounts => {
|
.then(currentAccounts => {
|
||||||
const newAccounts = _.assign(currentAccounts, accountsToSave)
|
const newAccounts = _.assign(currentAccounts, accountsToSave)
|
||||||
return db.none(sql, ['accounts', { accounts: newAccounts }, true, NEW_SETTINGS_LOADER_SCHEMA_VERSION])
|
return db.none(accountsSql, ['accounts', { accounts: newAccounts }, true, NEW_SETTINGS_LOADER_SCHEMA_VERSION])
|
||||||
})
|
})
|
||||||
}
|
}
|
||||||
|
function resetAccounts (schemaVersion) {
|
||||||
|
return db.none(
|
||||||
|
accountsSql,
|
||||||
|
[
|
||||||
|
'accounts',
|
||||||
|
{ accounts: NEW_SETTINGS_LOADER_SCHEMA_VERSION ? {} : [] },
|
||||||
|
true,
|
||||||
|
schemaVersion
|
||||||
|
]
|
||||||
|
)
|
||||||
|
}
|
||||||
|
|
||||||
function loadAccounts () {
|
function loadAccounts (schemaVersion) {
|
||||||
const sql = `select data
|
const sql = `select data
|
||||||
from user_config
|
from user_config
|
||||||
where type=$1
|
where type=$1
|
||||||
|
|
@ -24,22 +36,34 @@ function loadAccounts () {
|
||||||
order by id desc
|
order by id desc
|
||||||
limit 1`
|
limit 1`
|
||||||
|
|
||||||
return db.oneOrNone(sql, ['accounts', NEW_SETTINGS_LOADER_SCHEMA_VERSION])
|
return db.oneOrNone(sql, ['accounts', schemaVersion || NEW_SETTINGS_LOADER_SCHEMA_VERSION])
|
||||||
.then(_.compose(_.defaultTo({}), _.get('data.accounts')))
|
.then(_.compose(_.defaultTo({}), _.get('data.accounts')))
|
||||||
}
|
}
|
||||||
|
|
||||||
|
const configSql = 'insert into user_config (type, data, valid, schema_version) values ($1, $2, $3, $4)'
|
||||||
function saveConfig (config) {
|
function saveConfig (config) {
|
||||||
const sql = 'insert into user_config (type, data, valid, schema_version) values ($1, $2, $3, $4)'
|
console.log(config)
|
||||||
|
|
||||||
return loadLatestConfigOrNone()
|
return loadLatestConfigOrNone()
|
||||||
.then(currentConfig => {
|
.then(currentConfig => {
|
||||||
const newConfig = _.assign(currentConfig, config)
|
const newConfig = _.assign(currentConfig, config)
|
||||||
return db.none(sql, ['config', { config: newConfig }, true, NEW_SETTINGS_LOADER_SCHEMA_VERSION])
|
return db.none(configSql, ['config', { config: newConfig }, true, NEW_SETTINGS_LOADER_SCHEMA_VERSION])
|
||||||
})
|
})
|
||||||
}
|
}
|
||||||
|
|
||||||
function loadLatest () {
|
function resetConfig (schemaVersion) {
|
||||||
return Promise.all([loadLatestConfigOrNone(), loadAccounts()])
|
return db.none(
|
||||||
|
configSql,
|
||||||
|
[
|
||||||
|
'config',
|
||||||
|
{ config: schemaVersion === NEW_SETTINGS_LOADER_SCHEMA_VERSION ? {} : [] },
|
||||||
|
true,
|
||||||
|
schemaVersion
|
||||||
|
]
|
||||||
|
)
|
||||||
|
}
|
||||||
|
|
||||||
|
function loadLatest (schemaVersion) {
|
||||||
|
return Promise.all([loadLatestConfigOrNone(schemaVersion), loadAccounts(schemaVersion)])
|
||||||
.then(([config, accounts]) => ({
|
.then(([config, accounts]) => ({
|
||||||
config,
|
config,
|
||||||
accounts
|
accounts
|
||||||
|
|
@ -62,7 +86,7 @@ function loadLatestConfig () {
|
||||||
})
|
})
|
||||||
}
|
}
|
||||||
|
|
||||||
function loadLatestConfigOrNone () {
|
function loadLatestConfigOrNone (schemaVersion) {
|
||||||
const sql = `select data
|
const sql = `select data
|
||||||
from user_config
|
from user_config
|
||||||
where type=$1
|
where type=$1
|
||||||
|
|
@ -70,7 +94,7 @@ function loadLatestConfigOrNone () {
|
||||||
order by id desc
|
order by id desc
|
||||||
limit 1`
|
limit 1`
|
||||||
|
|
||||||
return db.oneOrNone(sql, ['config', NEW_SETTINGS_LOADER_SCHEMA_VERSION])
|
return db.oneOrNone(sql, ['config', schemaVersion || NEW_SETTINGS_LOADER_SCHEMA_VERSION])
|
||||||
.then(row => row ? row.data.config : {})
|
.then(row => row ? row.data.config : {})
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
@ -103,12 +127,26 @@ function load (versionId) {
|
||||||
}))
|
}))
|
||||||
}
|
}
|
||||||
|
|
||||||
|
function migrate () {
|
||||||
|
return loadLatest(OLD_SETTINGS_LOADER_SCHEMA_VERSION)
|
||||||
|
.then(res => {
|
||||||
|
const migrated = migration.migrate(res.config, res.accounts)
|
||||||
|
saveConfig(migrated.config)
|
||||||
|
saveAccounts(migrated.accounts)
|
||||||
|
|
||||||
|
return migrated
|
||||||
|
})
|
||||||
|
}
|
||||||
|
|
||||||
module.exports = {
|
module.exports = {
|
||||||
saveConfig,
|
saveConfig,
|
||||||
|
resetConfig,
|
||||||
saveAccounts,
|
saveAccounts,
|
||||||
|
resetAccounts,
|
||||||
loadAccounts,
|
loadAccounts,
|
||||||
loadLatest,
|
loadLatest,
|
||||||
loadLatestConfig,
|
loadLatestConfig,
|
||||||
loadLatestConfigOrNone,
|
loadLatestConfigOrNone,
|
||||||
load
|
load,
|
||||||
|
migrate
|
||||||
}
|
}
|
||||||
|
|
|
||||||
82
new-lamassu-admin/src/pages/ConfigMigration.js
Normal file
82
new-lamassu-admin/src/pages/ConfigMigration.js
Normal file
|
|
@ -0,0 +1,82 @@
|
||||||
|
import { useMutation } from '@apollo/react-hooks'
|
||||||
|
import { Box } from '@material-ui/core'
|
||||||
|
import { makeStyles } from '@material-ui/core/styles'
|
||||||
|
import gql from 'graphql-tag'
|
||||||
|
import React, { useState } from 'react'
|
||||||
|
|
||||||
|
import Title from 'src/components/Title'
|
||||||
|
import { Button } from 'src/components/buttons'
|
||||||
|
|
||||||
|
const styles = {
|
||||||
|
button: {
|
||||||
|
marginBottom: 10
|
||||||
|
}
|
||||||
|
}
|
||||||
|
const useStyles = makeStyles(styles)
|
||||||
|
|
||||||
|
const RESET = gql`
|
||||||
|
mutation Reset($schemaVersion: Int) {
|
||||||
|
resetConfig(schemaVersion: $schemaVersion)
|
||||||
|
resetAccounts(schemaVersion: $schemaVersion)
|
||||||
|
}
|
||||||
|
`
|
||||||
|
|
||||||
|
const MIGRATE = gql`
|
||||||
|
mutation Migrate {
|
||||||
|
migrateConfigAndAccounts
|
||||||
|
}
|
||||||
|
`
|
||||||
|
|
||||||
|
const OLD_SCHEMA_VERSION = 1
|
||||||
|
const NEW_SCHEMA_VERSION = 2
|
||||||
|
|
||||||
|
const ConfigMigration = () => {
|
||||||
|
const [loading, setLoading] = useState(false)
|
||||||
|
const [reset] = useMutation(RESET, {
|
||||||
|
onCompleted: () => setLoading(false)
|
||||||
|
})
|
||||||
|
|
||||||
|
const [migrate] = useMutation(MIGRATE, {
|
||||||
|
onCompleted: () => setLoading(false)
|
||||||
|
})
|
||||||
|
|
||||||
|
const classes = useStyles()
|
||||||
|
|
||||||
|
const innerReset = schemaVersion => {
|
||||||
|
setLoading(true)
|
||||||
|
reset({ variables: { schemaVersion } })
|
||||||
|
}
|
||||||
|
|
||||||
|
const innerMigrate = () => {
|
||||||
|
setLoading(true)
|
||||||
|
migrate()
|
||||||
|
}
|
||||||
|
|
||||||
|
return (
|
||||||
|
<>
|
||||||
|
<Title>Config Migration</Title>
|
||||||
|
<Box display="flex" alignItems="center" flexDirection="column">
|
||||||
|
<Button
|
||||||
|
className={classes.button}
|
||||||
|
disabled={loading}
|
||||||
|
onClick={() => innerReset(OLD_SCHEMA_VERSION)}>
|
||||||
|
Reset old admin
|
||||||
|
</Button>
|
||||||
|
<Button
|
||||||
|
className={classes.button}
|
||||||
|
disabled={loading}
|
||||||
|
onClick={() => innerReset(NEW_SCHEMA_VERSION)}>
|
||||||
|
Reset new admin
|
||||||
|
</Button>
|
||||||
|
<Button
|
||||||
|
className={classes.button}
|
||||||
|
disabled={loading}
|
||||||
|
onClick={() => innerMigrate()}>
|
||||||
|
Migrate
|
||||||
|
</Button>
|
||||||
|
</Box>
|
||||||
|
</>
|
||||||
|
)
|
||||||
|
}
|
||||||
|
|
||||||
|
export default ConfigMigration
|
||||||
|
|
@ -13,6 +13,7 @@ import AuthRegister from 'src/pages/AuthRegister'
|
||||||
import Blacklist from 'src/pages/Blacklist'
|
import Blacklist from 'src/pages/Blacklist'
|
||||||
import Cashout from 'src/pages/Cashout'
|
import Cashout from 'src/pages/Cashout'
|
||||||
import Commissions from 'src/pages/Commissions'
|
import Commissions from 'src/pages/Commissions'
|
||||||
|
import ConfigMigration from 'src/pages/ConfigMigration'
|
||||||
import { Customers, CustomerProfile } from 'src/pages/Customers'
|
import { Customers, CustomerProfile } from 'src/pages/Customers'
|
||||||
import Funding from 'src/pages/Funding'
|
import Funding from 'src/pages/Funding'
|
||||||
import Locales from 'src/pages/Locales'
|
import Locales from 'src/pages/Locales'
|
||||||
|
|
@ -259,6 +260,7 @@ const Routes = () => {
|
||||||
</Route>
|
</Route>
|
||||||
<Route path="/wizard" component={Wizard} />
|
<Route path="/wizard" component={Wizard} />
|
||||||
<Route path="/register" component={AuthRegister} />
|
<Route path="/register" component={AuthRegister} />
|
||||||
|
<Route path="/configmigration" component={ConfigMigration} />
|
||||||
{flattened.map(({ route, component: Page, key }) => (
|
{flattened.map(({ route, component: Page, key }) => (
|
||||||
<Route path={route} key={key}>
|
<Route path={route} key={key}>
|
||||||
<Page name={key} />
|
<Page name={key} />
|
||||||
|
|
|
||||||
Loading…
Add table
Add a link
Reference in a new issue