mirror of
https://github.com/corda/corda.git
synced 2024-12-28 00:38:55 +00:00
Create a capsule for Node Explorer, and allow login via command line parameters to bypass login screen.
This commit is contained in:
parent
30f9cc8fcd
commit
f9ac03287c
@ -13,6 +13,7 @@ include 'experimental:sandbox'
|
||||
include 'test-utils'
|
||||
include 'tools:demobench'
|
||||
include 'tools:explorer'
|
||||
include 'tools:explorer:capsule'
|
||||
include 'tools:loadtest'
|
||||
include 'docs/source/example-code' // Note that we are deliberately choosing to use '/' here. With ':' gradle would treat the directories as actual projects.
|
||||
include 'samples:attachment-demo'
|
||||
|
54
tools/explorer/capsule/build.gradle
Normal file
54
tools/explorer/capsule/build.gradle
Normal file
@ -0,0 +1,54 @@
|
||||
/**
|
||||
* This build.gradle exists to package Node Explorer as an executable fat jar.
|
||||
*/
|
||||
apply plugin: 'us.kirchmeier.capsule'
|
||||
|
||||
description 'Node Explorer'
|
||||
|
||||
repositories {
|
||||
mavenLocal()
|
||||
mavenCentral()
|
||||
maven {
|
||||
url 'http://oss.sonatype.org/content/repositories/snapshots'
|
||||
}
|
||||
jcenter()
|
||||
maven {
|
||||
url 'https://dl.bintray.com/kotlin/exposed'
|
||||
}
|
||||
}
|
||||
|
||||
// Force the Caplet to target Java 6. This ensures that running 'java -jar explorer.jar' on any Java 6 VM upwards
|
||||
// will get as far as the Capsule version checks, meaning that if your JVM is too old, you will at least get
|
||||
// a sensible error message telling you what to do rather than a bytecode version exception that doesn't.
|
||||
// If we introduce .java files into this module that need Java 8+ then we will have to push the caplet into
|
||||
// its own module so its target can be controlled individually, but for now this suffices.
|
||||
sourceCompatibility = 1.6
|
||||
targetCompatibility = 1.6
|
||||
|
||||
dependencies {
|
||||
compile project(':tools:explorer')
|
||||
}
|
||||
|
||||
task buildExplorerJAR(type: FatCapsule) {
|
||||
applicationClass 'net.corda.explorer.Main'
|
||||
archiveName "node-explorer-${corda_version}.jar"
|
||||
applicationSource = files(project.tasks.findByName('jar'), '../build/classes/main/ExplorerCaplet.class')
|
||||
classifier 'fat'
|
||||
|
||||
capsuleManifest {
|
||||
systemProperties['visualvm.display.name'] = 'Node Explorer'
|
||||
minJavaVersion = '1.8.0'
|
||||
// This version is known to work and avoids earlier 8u versions that have bugs.
|
||||
minUpdateVersion['1.8'] = '102'
|
||||
caplets = ['ExplorerCaplet']
|
||||
|
||||
// JVM configuration:
|
||||
// - Constrain to small heap sizes to ease development on low end devices.
|
||||
// - Switch to the G1 GC which is going to be the default in Java 9 and gives low pause times/string dedup.
|
||||
//
|
||||
// If you change these flags, please also update Driver.kt
|
||||
jvmArgs = ['-Xmx200m', '-XX:+UseG1GC']
|
||||
}
|
||||
}
|
||||
|
||||
build.dependsOn buildExplorerJAR
|
49
tools/explorer/src/main/java/ExplorerCaplet.java
Normal file
49
tools/explorer/src/main/java/ExplorerCaplet.java
Normal file
@ -0,0 +1,49 @@
|
||||
import java.io.File;
|
||||
import java.nio.file.Path;
|
||||
import java.util.List;
|
||||
import java.util.Map;
|
||||
|
||||
public class ExplorerCaplet extends Capsule {
|
||||
|
||||
protected ExplorerCaplet(Capsule pred) {
|
||||
super(pred);
|
||||
}
|
||||
|
||||
/**
|
||||
* Overriding the Caplet classpath generation via the intended interface in Capsule.
|
||||
*/
|
||||
@Override
|
||||
@SuppressWarnings("unchecked")
|
||||
protected <T> T attribute(Map.Entry<String, T> attr) {
|
||||
// Equality is used here because Capsule never instantiates these attributes but instead reuses the ones
|
||||
// defined as public static final fields on the Capsule class, therefore referential equality is safe.
|
||||
if (ATTR_APP_CLASS_PATH == attr) {
|
||||
T cp = super.attribute(attr);
|
||||
List<Path> classpath = augmentClasspath((List<Path>) cp, "plugins");
|
||||
return (T) augmentClasspath(classpath, "dependencies");
|
||||
}
|
||||
return super.attribute(attr);
|
||||
}
|
||||
|
||||
// TODO: Make directory configurable via the capsule manifest.
|
||||
// TODO: Add working directory variable to capsules string replacement variables.
|
||||
private List<Path> augmentClasspath(List<Path> classpath, String dirName) {
|
||||
File dir = new File(dirName);
|
||||
if (!dir.exists()) {
|
||||
dir.mkdir();
|
||||
}
|
||||
|
||||
File[] files = dir.listFiles();
|
||||
for (File file : files) {
|
||||
if (file.isFile() && isJAR(file)) {
|
||||
classpath.add(file.toPath().toAbsolutePath());
|
||||
}
|
||||
}
|
||||
return classpath;
|
||||
}
|
||||
|
||||
private Boolean isJAR(File file) {
|
||||
return file.getName().toLowerCase().endsWith(".jar");
|
||||
}
|
||||
|
||||
}
|
@ -55,9 +55,39 @@ class Main : App(MainView::class) {
|
||||
}.showAndWait().get()
|
||||
if (button != ButtonType.OK) it.consume()
|
||||
}
|
||||
stage.hide()
|
||||
loginView.login()
|
||||
stage.show()
|
||||
|
||||
val hostname = parameters.named["host"]
|
||||
val port = asInteger(parameters.named["port"])
|
||||
val username = parameters.named["username"]
|
||||
val password = parameters.named["password"]
|
||||
var isLoggedIn = false
|
||||
|
||||
if ((hostname != null) && (port != null) && (username != null) && (password != null)) {
|
||||
try {
|
||||
loginView.login(hostname, port, username, password)
|
||||
isLoggedIn = true
|
||||
} catch (e: Exception) {
|
||||
ExceptionDialog(e).apply { initOwner(stage.scene.window) }.showAndWait()
|
||||
}
|
||||
}
|
||||
|
||||
if (!isLoggedIn) {
|
||||
stage.hide()
|
||||
loginView.login()
|
||||
stage.show()
|
||||
}
|
||||
}
|
||||
|
||||
private fun asInteger(s: String?): Int? {
|
||||
if (s == null) {
|
||||
return null;
|
||||
}
|
||||
|
||||
try {
|
||||
return s.toInt();
|
||||
} catch (e: NumberFormatException) {
|
||||
return null
|
||||
}
|
||||
}
|
||||
|
||||
init {
|
||||
|
@ -38,6 +38,10 @@ class LoginView : View() {
|
||||
private val keyStorePasswordProperty by objectProperty(SettingsModel::keyStorePasswordProperty)
|
||||
private val trustStorePasswordProperty by objectProperty(SettingsModel::trustStorePasswordProperty)
|
||||
|
||||
fun login(host: String?, port: Int, username: String, password: String) {
|
||||
getModel<NodeMonitorModel>().register(HostAndPort.fromParts(host, port), configureSSL(), username, password)
|
||||
}
|
||||
|
||||
fun login() {
|
||||
val status = Dialog<LoginStatus>().apply {
|
||||
dialogPane = root
|
||||
@ -46,7 +50,7 @@ class LoginView : View() {
|
||||
ButtonBar.ButtonData.OK_DONE -> try {
|
||||
root.isDisable = true
|
||||
// TODO : Run this async to avoid UI lockup.
|
||||
getModel<NodeMonitorModel>().register(HostAndPort.fromParts(hostTextField.text, portProperty.value), configureSSL(), usernameTextField.text, passwordTextField.text)
|
||||
login(hostTextField.text, portProperty.value, usernameTextField.text, passwordTextField.text)
|
||||
if (!rememberMe.value) {
|
||||
username.value = ""
|
||||
host.value = ""
|
||||
|
Loading…
Reference in New Issue
Block a user