Nodes now need a setup step before running.

This commit is contained in:
Clinton Alexander
2016-06-14 16:07:29 +01:00
parent 86b5b7299a
commit 6b886bde4a
6 changed files with 35 additions and 25 deletions

View File

@ -121,8 +121,6 @@ abstract class AbstractNode(val dir: Path, val configuration: NodeConfiguration,
require(!started) { "Node has already been started" } require(!started) { "Node has already been started" }
log.info("Node starting up ...") log.info("Node starting up ...")
createNodeDir()
val storageServices = initialiseStorageService(dir) val storageServices = initialiseStorageService(dir)
storage = storageServices.first storage = storageServices.first
checkpointStorage = storageServices.second checkpointStorage = storageServices.second
@ -154,6 +152,14 @@ abstract class AbstractNode(val dir: Path, val configuration: NodeConfiguration,
return this return this
} }
/**
* Run any tasks that are needed to ensure the node is in a correct state before running start()
*/
open fun setup(): AbstractNode {
createNodeDir()
return this
}
private fun buildAdvertisedServices() { private fun buildAdvertisedServices() {
val serviceTypes = info.advertisedServices val serviceTypes = info.advertisedServices
if (NetworkMapService.Type in serviceTypes) makeNetworkMapService() if (NetworkMapService.Type in serviceTypes) makeNetworkMapService()
@ -319,7 +325,7 @@ abstract class AbstractNode(val dir: Path, val configuration: NodeConfiguration,
return NodeAttachmentService(attachmentsDir, services.monitoringService.metrics) return NodeAttachmentService(attachmentsDir, services.monitoringService.metrics)
} }
private fun createNodeDir() { protected fun createNodeDir() {
if (!Files.exists(dir)) { if (!Files.exists(dir)) {
Files.createDirectories(dir) Files.createDirectories(dir)
} }

View File

@ -153,6 +153,11 @@ class Node(dir: Path, val p2pAddr: HostAndPort, configuration: NodeConfiguration
return this return this
} }
override fun setup(): Node {
super.setup()
return this
}
override fun stop() { override fun stop() {
webServer.stop() webServer.stop()
super.stop() super.stop()
@ -165,24 +170,23 @@ class Node(dir: Path, val p2pAddr: HostAndPort, configuration: NodeConfiguration
// file that we'll do our best to delete on exit. But if we don't, it'll be overwritten next time. If it already // file that we'll do our best to delete on exit. But if we don't, it'll be overwritten next time. If it already
// exists, we try to take the file lock first before replacing it and if that fails it means we're being started // exists, we try to take the file lock first before replacing it and if that fails it means we're being started
// twice with the same directory: that's a user error and we should bail out. // twice with the same directory: that's a user error and we should bail out.
if(Files.exists(dir)) { val pidPath = dir.resolve("process-id")
val pidPath = dir.resolve("process-id") val file = pidPath.toFile()
val file = pidPath.toFile() if (!file.exists()) {
if (!file.exists()) { file.createNewFile()
file.createNewFile()
}
file.deleteOnExit()
val f = RandomAccessFile(file, "rw")
val l = f.channel.tryLock()
if (l == null) {
println("It appears there is already a node running with the specified data directory $dir")
println("Shut that other node down and try again. It may have process ID ${file.readText()}")
System.exit(1)
}
nodeFileLock = l
val ourProcessID: String = ManagementFactory.getRuntimeMXBean().name.split("@")[0]
f.setLength(0)
f.write(ourProcessID.toByteArray())
} }
file.deleteOnExit()
val f = RandomAccessFile(file, "rw")
val l = f.channel.tryLock()
if (l == null) {
println("It appears there is already a node running with the specified data directory $dir")
println("Shut that other node down and try again. It may have process ID ${file.readText()}")
System.exit(1)
}
nodeFileLock = l
val ourProcessID: String = ManagementFactory.getRuntimeMXBean().name.split("@")[0]
f.setLength(0)
f.write(ourProcessID.toByteArray())
} }
} }

View File

@ -121,7 +121,7 @@ class MockNetwork(private val threadPerNode: Boolean = false,
override val nearestCity: String = "Atlantis" override val nearestCity: String = "Atlantis"
} }
val node = nodeFactory.create(path, config, this, networkMapAddress, advertisedServices.toSet(), id, keyPair) val node = nodeFactory.create(path, config, this, networkMapAddress, advertisedServices.toSet(), id, keyPair)
if (start) node.start() if (start) node.setup().start()
_nodes.add(node) _nodes.add(node)
return node return node
} }

View File

@ -401,7 +401,7 @@ private fun startNode(params : NodeParams) : Node {
val node = logElapsedTime("Node startup") { Node(params.dir, myNetAddr, config, networkMapId, val node = logElapsedTime("Node startup") { Node(params.dir, myNetAddr, config, networkMapId,
advertisedServices, DemoClock(), advertisedServices, DemoClock(),
listOf(InterestRateSwapAPI::class.java)).start() } listOf(InterestRateSwapAPI::class.java)).setup().start() }
// TODO: This should all be replaced by the identity service being updated // TODO: This should all be replaced by the identity service being updated
// as the network map changes. // as the network map changes.

View File

@ -75,7 +75,7 @@ fun main(args: Array<String>) {
val node = logElapsedTime("Node startup") { Node(dir, myNetAddr, config, networkMapAddress, val node = logElapsedTime("Node startup") { Node(dir, myNetAddr, config, networkMapAddress,
advertisedServices, DemoClock(), advertisedServices, DemoClock(),
listOf(InterestRateSwapAPI::class.java)).start() } listOf(InterestRateSwapAPI::class.java)).setup().start() }
val notary = node.services.networkMapCache.notaryNodes[0] val notary = node.services.networkMapCache.notaryNodes[0]

View File

@ -129,7 +129,7 @@ fun main(args: Array<String>) {
// And now construct then start the node object. It takes a little while. // And now construct then start the node object. It takes a little while.
val node = logElapsedTime("Node startup") { val node = logElapsedTime("Node startup") {
Node(directory, myNetAddr, config, networkMapId, advertisedServices).start() Node(directory, myNetAddr, config, networkMapId, advertisedServices).setup().start()
} }
// What happens next depends on the role. The buyer sits around waiting for a trade to start. The seller role // What happens next depends on the role. The buyer sits around waiting for a trade to start. The seller role