This reverts commit 6b8a345241
.
This commit is contained in:
parent
b1429e1df3
commit
1646c50a94
@ -44,7 +44,7 @@ const usage = 'Usage: xen-api <url> [<user> [<password>]]'
|
||||
|
||||
async function main(createClient) {
|
||||
const opts = minimist(process.argv.slice(2), {
|
||||
string: ['session-id', 'fallback-addresses'],
|
||||
string: ['session-id'],
|
||||
boolean: ['allow-unauthorized', 'help', 'read-only', 'verbose'],
|
||||
|
||||
alias: {
|
||||
@ -82,10 +82,6 @@ async function main(createClient) {
|
||||
})
|
||||
}
|
||||
|
||||
let fallBackAddresses = []
|
||||
if (opts['fallback-addresses']) {
|
||||
fallBackAddresses = opts['fallback-addresses'].split(',')
|
||||
}
|
||||
const xapi = createClient({
|
||||
url: opts._[0],
|
||||
allowUnauthorized: opts.au,
|
||||
@ -93,7 +89,6 @@ async function main(createClient) {
|
||||
debounce: opts.debounce != null ? +opts.debounce : null,
|
||||
readOnly: opts.ro,
|
||||
syncStackTraces: true,
|
||||
fallBackAddresses,
|
||||
})
|
||||
await xapi.connect()
|
||||
|
||||
|
@ -8,7 +8,6 @@ import noop from 'lodash/noop'
|
||||
import omit from 'lodash/omit'
|
||||
import ProxyAgent from 'proxy-agent'
|
||||
import { coalesceCalls } from '@vates/coalesce-calls'
|
||||
import { synchronized } from 'decorator-synchronized'
|
||||
import { Collection } from 'xo-collection'
|
||||
import { EventEmitter } from 'events'
|
||||
import { Index } from 'xo-collection/index'
|
||||
@ -121,7 +120,7 @@ export class Xapi extends EventEmitter {
|
||||
delete url.username
|
||||
delete url.password
|
||||
}
|
||||
this._fallBackAddresses = opts.fallBackAddresses ?? []
|
||||
|
||||
this._allowUnauthorized = opts.allowUnauthorized
|
||||
if (opts.httpProxy !== undefined) {
|
||||
this._httpAgent = new ProxyAgent(this._httpProxy)
|
||||
@ -682,85 +681,6 @@ export class Xapi extends EventEmitter {
|
||||
// Private
|
||||
// ===========================================================================
|
||||
|
||||
@synchronized()
|
||||
async _updateUrlFromFallbackAdresses(method, args, startTime) {
|
||||
debug('%s: will try to find a new master', this._humanId)
|
||||
const hostAddresses = this._fallBackAddresses
|
||||
|
||||
// there can be a master only if there is more than 1 host
|
||||
if (hostAddresses.length < 2) {
|
||||
return false
|
||||
}
|
||||
|
||||
// another call to _updateUrlFromFallbackAdresses has already connected us to the right host
|
||||
try {
|
||||
await this._transport('session.get_auth_user_name', [])
|
||||
debug('%s: host was already ok', this._humanId)
|
||||
// host is ok, nothing to do here
|
||||
return true
|
||||
} catch (error) {
|
||||
if (!['EHOSTUNREACH', 'HOST_IS_SLAVE', 'ENOTFOUND', 'MESSAGE_PARAMETER_COUNT_MISMATCH'].includes(error.code)) {
|
||||
throw this._augmentCallError(error, method, args, startTime)
|
||||
}
|
||||
}
|
||||
|
||||
for (const hostAdress of hostAddresses) {
|
||||
// we already tested the current master
|
||||
if (hostAdress === this._url.hostname) {
|
||||
debug(`%s: don't recheck currrent host`, this._humanId)
|
||||
continue
|
||||
}
|
||||
// since this method is @syncrhonized , there can be only on call at once
|
||||
this._setUrl({ ...this._url, hostname: hostAdress })
|
||||
|
||||
try {
|
||||
// will not succeed without sessionId, but I only want to know if this host is entitled to answer (he's the master)
|
||||
await this._transport('session.get_auth_user_name', [])
|
||||
// success
|
||||
return true
|
||||
} catch (error) {
|
||||
// this host is also down, try the next one
|
||||
if (error.code === 'EHOSTUNREACH' || error.code === 'ENOTFOUND') {
|
||||
debug(`%s: slave %s is alsoa unreachable`, this._humanId, hostAdress)
|
||||
continue
|
||||
}
|
||||
|
||||
if (error.code === 'HOST_IS_SLAVE') {
|
||||
debug('%s: slave %s told us the master is %s', this._humanId, hostAdress, error.params[0])
|
||||
this._setUrl({ ...this._url, hostname: hostAdress })
|
||||
return true // we found the master no need to check for the other slave
|
||||
}
|
||||
|
||||
if (error.code === 'MESSAGE_PARAMETER_COUNT_MISMATCH') {
|
||||
debug('%s: found new master %s master', this._humanId, hostAdress)
|
||||
// lucky : we found the master with the first host answering
|
||||
return true // we found the master no need to check for the other slave
|
||||
}
|
||||
// any other error should be reported
|
||||
throw this._augmentCallError(error, method, args, startTime)
|
||||
}
|
||||
}
|
||||
return false
|
||||
}
|
||||
|
||||
_augmentCallError(error, method, args, startTime) {
|
||||
// do not log the session ID
|
||||
//
|
||||
// TODO: should log at the session level to avoid logging sensitive
|
||||
// values?
|
||||
const params = args[0] === this._sessionId ? args.slice(1) : args
|
||||
|
||||
error.call = {
|
||||
method,
|
||||
params:
|
||||
// it pass server's credentials as param
|
||||
method === 'session.login_with_password' ? '* obfuscated *' : replaceSensitiveValues(params, '* obfuscated *'),
|
||||
}
|
||||
|
||||
debug('%s: %s(...) [%s] =!> %s', this._humanId, method, ms(Date.now() - startTime), error)
|
||||
return error
|
||||
}
|
||||
|
||||
async _call(method, args, timeout = this._callTimeout(method, args)) {
|
||||
const startTime = Date.now()
|
||||
try {
|
||||
@ -768,14 +688,24 @@ export class Xapi extends EventEmitter {
|
||||
debug('%s: %s(...) [%s] ==> %s', this._humanId, method, ms(Date.now() - startTime), kindOf(result))
|
||||
return result
|
||||
} catch (error) {
|
||||
if (this._fallBackAddresses?.length > 1 && ['EHOSTUNREACH', 'HOST_IS_SLAVE', 'ENOTFOUND'].includes(error.code)) {
|
||||
const updatedHostUrl = await this._updateUrlFromFallbackAdresses(method, args, startTime)
|
||||
if (updatedHostUrl) {
|
||||
// try again
|
||||
return this._call(method, args, timeout)
|
||||
}
|
||||
// do not log the session ID
|
||||
//
|
||||
// TODO: should log at the session level to avoid logging sensitive
|
||||
// values?
|
||||
const params = args[0] === this._sessionId ? args.slice(1) : args
|
||||
|
||||
error.call = {
|
||||
method,
|
||||
params:
|
||||
// it pass server's credentials as param
|
||||
method === 'session.login_with_password'
|
||||
? '* obfuscated *'
|
||||
: replaceSensitiveValues(params, '* obfuscated *'),
|
||||
}
|
||||
throw this._augmentCallError(error, method, args, startTime)
|
||||
|
||||
debug('%s: %s(...) [%s] =!> %s', this._humanId, method, ms(Date.now() - startTime), error)
|
||||
|
||||
throw error
|
||||
}
|
||||
}
|
||||
|
||||
@ -852,8 +782,8 @@ export class Xapi extends EventEmitter {
|
||||
// unnecessary renewal
|
||||
_sessionOpenRetryOptions = {
|
||||
tries: 2,
|
||||
when: [{ code: 'HOST_IS_SLAVE' }],
|
||||
onRetry: async error => {
|
||||
when: { code: 'HOST_IS_SLAVE' },
|
||||
onRetry: error => {
|
||||
this._setUrl({ ...this._url, hostname: error.params[0] })
|
||||
},
|
||||
}
|
||||
@ -1120,6 +1050,7 @@ export class Xapi extends EventEmitter {
|
||||
delete taskWatchers[ref]
|
||||
}
|
||||
}
|
||||
|
||||
// read-only call, automatically retry in case of connection issues
|
||||
_roCall(method, args) {
|
||||
return pRetry(() => this._sessionCall(method, args), this._roCallRetryOptions)
|
||||
@ -1160,7 +1091,6 @@ export class Xapi extends EventEmitter {
|
||||
await this._refreshCachedRecords(types)
|
||||
this._resolveObjectsFetched()
|
||||
this._resolveObjectsFetched = undefined
|
||||
this.emit('eventFetchedSuccess')
|
||||
|
||||
// event loop
|
||||
const debounce = this._debounce
|
||||
@ -1192,10 +1122,6 @@ export class Xapi extends EventEmitter {
|
||||
// eslint-disable-next-line no-labels
|
||||
continue mainLoop
|
||||
}
|
||||
if (code === 'EHOSTUNREACH') {
|
||||
// maybe the master has been demoted
|
||||
await this._findCurrentMaster()
|
||||
}
|
||||
|
||||
this.emit('eventFetchingError', error)
|
||||
this._watchEventsError = error
|
||||
|
@ -112,10 +112,6 @@ set.params = {
|
||||
optional: true,
|
||||
type: ['string', 'null'],
|
||||
},
|
||||
fallbackAddresses: {
|
||||
type: ['string', 'null'],
|
||||
optional: true,
|
||||
},
|
||||
}
|
||||
|
||||
// -------------------------------------------------------------------
|
||||
|
@ -14,7 +14,7 @@ import * as XenStore from '../_XenStore.mjs'
|
||||
import Xapi from '../xapi/index.mjs'
|
||||
import xapiObjectToXo from '../xapi-object-to-xo.mjs'
|
||||
import XapiStats from '../xapi-stats.mjs'
|
||||
import { camelToSnakeCase, forEach, isEmpty, noop, popProperty } from '../utils.mjs'
|
||||
import { camelToSnakeCase, forEach, isEmpty, popProperty } from '../utils.mjs'
|
||||
import { Servers } from '../models/server.mjs'
|
||||
|
||||
// ===================================================================
|
||||
@ -133,7 +133,7 @@ export default class {
|
||||
|
||||
async updateXenServer(
|
||||
id,
|
||||
{ allowUnauthorized, enabled, error, host, label, password, readOnly, username, httpProxy, fallbackAddresses }
|
||||
{ allowUnauthorized, enabled, error, host, label, password, readOnly, username, httpProxy }
|
||||
) {
|
||||
const server = await this._getXenServer(id)
|
||||
const xapi = this._xapis[id]
|
||||
@ -176,9 +176,6 @@ export default class {
|
||||
// if value is null, pass undefined to the model , so it will delete this optionnal property from the Server object
|
||||
server.set('httpProxy', httpProxy === null ? undefined : httpProxy)
|
||||
}
|
||||
if (fallbackAddresses !== undefined) {
|
||||
server.set('fallBackAddresses', fallbackAddresses === null ? undefined : JSON.stringify(fallbackAddresses))
|
||||
}
|
||||
await this._servers.update(server)
|
||||
}
|
||||
|
||||
@ -300,14 +297,6 @@ export default class {
|
||||
})
|
||||
}
|
||||
|
||||
async _updateFallBackAdresses(xapi) {
|
||||
const hosts = await xapi.getAllRecords('host')
|
||||
const fallbackAddresses = hosts.map(({ address }) => address)
|
||||
for (const host of hosts) {
|
||||
await this.updateXenServer(host.id, { fallbackAddresses })
|
||||
}
|
||||
}
|
||||
|
||||
async connectXenServer(id) {
|
||||
const server = await this.getXenServer(id)
|
||||
|
||||
@ -316,10 +305,7 @@ export default class {
|
||||
}
|
||||
|
||||
const { config } = this._app
|
||||
let fallBackAddresses
|
||||
try {
|
||||
fallBackAddresses = JSON.parse(server.fallBackAddresses)
|
||||
} catch (e) {}
|
||||
|
||||
let { poolMarkingInterval, poolMarkingMaxAge, poolMarkingPrefix, ...xapiOptions } = config.get('xapiOptions')
|
||||
poolMarkingInterval = parseDuration(poolMarkingInterval)
|
||||
poolMarkingMaxAge = parseDuration(poolMarkingMaxAge)
|
||||
@ -330,7 +316,6 @@ export default class {
|
||||
|
||||
...xapiOptions,
|
||||
httpProxy: server.httpProxy,
|
||||
fallBackAddresses,
|
||||
guessVhdSizeOnImport: config.get('guessVhdSizeOnImport'),
|
||||
|
||||
auth: {
|
||||
@ -356,8 +341,6 @@ export default class {
|
||||
throw new PoolAlreadyConnected(poolId, serverIdsByPool[poolId], server.id)
|
||||
}
|
||||
|
||||
await this._updateFallBackAdresses(xapi).catch(noop)
|
||||
|
||||
serverIdsByPool[poolId] = server.id
|
||||
|
||||
xapi.xo = (() => {
|
||||
@ -486,14 +469,6 @@ export default class {
|
||||
|
||||
this.updateXenServer(id, { error: null })::ignoreErrors()
|
||||
|
||||
const xo = this
|
||||
// when the data are loaded, update the fall back adresses of all the hosts of this pool
|
||||
xapi.once('eventFetchedSuccess', async function eventFetchedSuccessListener() {
|
||||
const hosts = await this.getAllRecords('host')
|
||||
const hostAddresses = hosts.map(({ address }) => address).join(';')
|
||||
await xo.updateXenServer(server.id, { fallbackAddresses: hostAddresses })
|
||||
})
|
||||
|
||||
xapi.once('eventFetchingError', function eventFetchingErrorListener() {
|
||||
const timeout = setTimeout(() => {
|
||||
xapi.xo.uninstall()
|
||||
|
Loading…
Reference in New Issue
Block a user