Report any optional containers that aren't being run

Change-type: patch
Signed-off-by: Cameron Diver <cameron@balena.io>
This commit is contained in:
Cameron Diver 2019-11-05 10:00:12 +00:00
parent f75b8aad2b
commit 8223bf2ccb
2 changed files with 34 additions and 14 deletions

View File

@ -735,18 +735,23 @@ module.exports = class ApplicationManager extends EventEmitter
@proxyvisor.setTargetInTransaction(dependent, trx) @proxyvisor.setTargetInTransaction(dependent, trx)
contractViolators = {} contractViolators = {}
Promise.props(contractsFulfilled).then (fulfilledContracts) -> Promise.props(contractsFulfilled).then (fulfilledContracts) =>
filteredApps = _.cloneDeep(apps) filteredApps = _.cloneDeep(apps)
_.each fulfilledContracts, ({ valid, unmetServices, fulfilledServices }, appId) -> _.each(
if not valid fulfilledContracts,
contractViolators[apps[appId].name] = unmetServices ({ valid, unmetServices, fulfilledServices, unmetAndOptional }, appId) =>
delete filteredApps[appId] if not valid
else contractViolators[apps[appId].name] = unmetServices
# valid is true, but we could still be missing delete filteredApps[appId]
# some optional containers, and need to filter else
# these out of the target state # valid is true, but we could still be missing
filteredApps[appId].services = _.pickBy filteredApps[appId].services, ({ serviceName }) -> # some optional containers, and need to filter
fulfilledServices.includes(serviceName) # these out of the target state
filteredApps[appId].services = _.pickBy filteredApps[appId].services, ({ serviceName }) ->
fulfilledServices.includes(serviceName)
if unmetAndOptional.length != 0
@reportOptionalContainers(unmetAndOptional)
)
if trx? if trx?
setInTransaction(filteredApps, trx) setInTransaction(filteredApps, trx)
else else
@ -1008,3 +1013,12 @@ module.exports = class ApplicationManager extends EventEmitter
return volumes.map((v) -> { action: 'removeVolume', current: v }) return volumes.map((v) -> { action: 'removeVolume', current: v })
localModeSwitchCompletion: => @localModeManager.switchCompletion() localModeSwitchCompletion: => @localModeManager.switchCompletion()
reportOptionalContainers: (serviceNames) =>
# Print logs to the console and dashboard, letting the
# user know that we're not going to run certain services
# because of their contract
message = "Not running containers because of contract violations: #{serviceNames.join('. ')}"
log.info(message)
@logger.logSystemMessage(message, {}, 'optionalContainerViolation', true)

View File

@ -22,6 +22,7 @@ export async function containerContractsFulfilled(
valid: boolean; valid: boolean;
unmetServices: string[]; unmetServices: string[];
fulfilledServices: string[]; fulfilledServices: string[];
unmetAndOptional: string[];
}> { }> {
const containers = _(serviceContracts) const containers = _(serviceContracts)
.map('contract') .map('contract')
@ -76,6 +77,7 @@ export async function containerContractsFulfilled(
valid: false, valid: false,
unmetServices: _.keys(serviceContracts), unmetServices: _.keys(serviceContracts),
fulfilledServices: [], fulfilledServices: [],
unmetAndOptional: [],
}; };
} }
@ -90,6 +92,7 @@ export async function containerContractsFulfilled(
valid: true, valid: true,
unmetServices: [], unmetServices: [],
fulfilledServices: _.keys(serviceContracts), fulfilledServices: _.keys(serviceContracts),
unmetAndOptional: [],
}; };
} else { } else {
// If we got here, it means that at least one of the // If we got here, it means that at least one of the
@ -112,15 +115,18 @@ export async function containerContractsFulfilled(
}, },
); );
const valid = !_.some( const [unmetAndRequired, unmetAndOptional] = _.partition(
unfulfilledServices, unfulfilledServices,
svcName => !serviceContracts[svcName].optional, serviceName => {
return !serviceContracts[serviceName].optional;
},
); );
return { return {
valid, valid: unmetAndRequired.length === 0,
unmetServices: unfulfilledServices, unmetServices: unfulfilledServices,
fulfilledServices, fulfilledServices,
unmetAndOptional,
}; };
} }
} }