Refined Command Line Structure

This commit is contained in:
Stef Tervelde
2025-04-19 09:34:06 +02:00
parent fd571d13d5
commit 51c9734d2a
4 changed files with 60 additions and 41 deletions

View File

@@ -123,7 +123,7 @@ dependencies {
testImplementation(libs.junitJupiter)
testImplementation(libs.junitJupiterParams)
implementation("com.github.ajalt.clikt:clikt:5.0.2")
implementation(libs.clikt)
}
tasks.test {

View File

@@ -4,45 +4,49 @@ import com.github.ajalt.clikt.command.SuspendingCliktCommand
import com.github.ajalt.clikt.command.main
import com.github.ajalt.clikt.core.Context
import com.github.ajalt.clikt.core.subcommands
import com.github.ajalt.clikt.parameters.arguments.argument
import com.github.ajalt.clikt.parameters.arguments.multiple
import com.github.ajalt.clikt.parameters.options.flag
import com.github.ajalt.clikt.parameters.options.option
import processing.app.ui.Start
// TODO: Allow Start to run on no args
// TODO: Modify InstallCommander to use the new structure
// TODO: Move dependency to gradle toml
// TODO: Add the options/arguments for Base arguments
class Processing(val args: Array<String>): SuspendingCliktCommand(name = "Processing"){
class Processing: SuspendingCliktCommand("processing"){
val sketches by argument().multiple(default = emptyList())
override fun help(context: Context) = "Start the Processing IDE"
override val invokeWithoutSubcommand = true
override suspend fun run() {
if(currentContext.invokedSubcommand == null){
Start.main(args)
val subcommand = currentContext.invokedSubcommand
if (subcommand == null) {
Start.main(sketches.toTypedArray())
}
}
}
suspend fun main(args: Array<String>) = Processing(args)
.subcommands(
LSP(args),
LegacyCLI(args)
)
.main(args)
suspend fun main(args: Array<String>){
Processing()
.subcommands(
LSP(),
LegacyCLI(args)
)
.main(args)
}
class LSP(val args: Array<String>): SuspendingCliktCommand("lsp"){
class LSP: SuspendingCliktCommand("lsp"){
override fun help(context: Context) = "Start the Processing Language Server"
override suspend fun run(){
try {
// Indirect invocation since app does not depend on java mode
Class.forName("processing.mode.java.lsp.PdeLanguageServer")
.getMethod("main", Array<String>::class.java)
.invoke(null, *arrayOf<Any>(args))
.invoke(null, *arrayOf<Any>(emptyList<String>()))
} catch (e: Exception) {
throw InternalError("Failed to invoke main method", e)
}
}
}
class LegacyCLI(val args: Array<String>): SuspendingCliktCommand(name = "cli"){
class LegacyCLI(val args: Array<String>): SuspendingCliktCommand( "cli"){
override fun help(context: Context) = "Legacy processing-java command line interface"
val help by option("--help").flag()
@@ -57,12 +61,15 @@ class LegacyCLI(val args: Array<String>): SuspendingCliktCommand(name = "cli"){
val variant: String? by option("--variant")
override suspend fun run(){
val cliArgs = args.filter { it != "cli" }.toTypedArray()
val cliArgs = args.filter { it != "cli" }
try {
if(build){
System.setProperty("java.awt.headless", "true")
}
// Indirect invocation since app does not depend on java mode
Class.forName("processing.mode.java.Commander")
.getMethod("main", Array<String>::class.java)
.invoke(null, *arrayOf<Any>(cliArgs))
.invoke(null, *arrayOf<Any>(cliArgs.toTypedArray()))
} catch (e: Exception) {
throw InternalError("Failed to invoke main method", e)
}

View File

@@ -86,30 +86,41 @@ public class InstallCommander implements Tool {
PrintWriter writer = PApplet.createWriter(file);
writer.print("#!/bin/sh\n\n");
writer.print("# Prevents processing-java from stealing focus, see:\n" +
"# https://github.com/processing/processing/issues/3996.\n" +
"OPTION_FOR_HEADLESS_RUN=\"\"\n" +
"for ARG in \"$@\"\n" +
"do\n" +
" if [ \"$ARG\" = \"--build\" ]; then\n" +
" OPTION_FOR_HEADLESS_RUN=\"-Djava.awt.headless=true\"\n" +
" fi\n" +
"done\n\n");
var resourcesDir = System.getProperty("compose.application.resources.dir");
if(resourcesDir != null) {
// Gradle based distributable
var appBinary = (resourcesDir
.split("\\.app")[0] + ".app/Contents/MacOS/Processing")
.replaceAll(" ", "\\\\ ");
writer.print(appBinary + " cli $@");
String javaRoot = Platform.getContentFile(".").getCanonicalPath();
} else {
// Ant based distributable
writer.print("# Prevents processing-java from stealing focus, see:\n" +
"# https://github.com/processing/processing/issues/3996.\n" +
"OPTION_FOR_HEADLESS_RUN=\"\"\n" +
"for ARG in \"$@\"\n" +
"do\n" +
" if [ \"$ARG\" = \"--build\" ]; then\n" +
" OPTION_FOR_HEADLESS_RUN=\"-Djava.awt.headless=true\"\n" +
" fi\n" +
"done\n\n");
StringList jarList = new StringList();
addJarList(jarList, new File(javaRoot));
addJarList(jarList, new File(javaRoot, "core/library"));
addJarList(jarList, new File(javaRoot, "modes/java/mode"));
String classPath = jarList.join(":").replaceAll(javaRoot + "\\/?", "");
String javaRoot = Platform.getContentFile(".").getCanonicalPath();
writer.println("cd \"" + javaRoot + "\" && " +
Platform.getJavaPath().replaceAll(" ", "\\\\ ") +
" -Djna.nosys=true" +
" $OPTION_FOR_HEADLESS_RUN" +
" -cp \"" + classPath + "\"" +
" processing.mode.java.Commander \"$@\"");
StringList jarList = new StringList();
addJarList(jarList, new File(javaRoot));
addJarList(jarList, new File(javaRoot, "core/library"));
addJarList(jarList, new File(javaRoot, "modes/java/mode"));
String classPath = jarList.join(":").replaceAll(javaRoot + "\\/?", "");
writer.println("cd \"" + javaRoot + "\" && " +
Platform.getJavaPath().replaceAll(" ", "\\\\ ") +
" -Djna.nosys=true" +
" $OPTION_FOR_HEADLESS_RUN" +
" -cp \"" + classPath + "\"" +
" processing.mode.java.Commander \"$@\"");
}
writer.flush();
writer.close();
file.setExecutable(true);

View File

@@ -27,6 +27,7 @@ lsp4j = { module = "org.eclipse.lsp4j:org.eclipse.lsp4j", version = "0.22.0" }
jsoup = { module = "org.jsoup:jsoup", version = "1.17.2" }
markdown = { module = "com.mikepenz:multiplatform-markdown-renderer-m2", version = "0.31.0" }
markdownJVM = { module = "com.mikepenz:multiplatform-markdown-renderer-jvm", version = "0.31.0" }
clikt = { module = "com.github.ajalt.clikt:clikt", version = "5.0.2" }
[plugins]
jetbrainsCompose = { id = "org.jetbrains.compose", version.ref = "compose-plugin" }