Remove desktop terminals

This commit is contained in:
crschnick
2025-01-04 07:52:00 +00:00
parent db0dda5efe
commit 2b495f6a61
8 changed files with 4 additions and 532 deletions
@@ -5,7 +5,6 @@ import io.xpipe.app.ext.ProcessControlProvider;
import io.xpipe.app.prefs.ExternalApplicationType;
import io.xpipe.app.util.*;
import io.xpipe.core.process.*;
import io.xpipe.core.util.FailableFunction;
import lombok.Getter;
@@ -613,11 +612,11 @@ public interface ExternalTerminalType extends PrefsChoiceValue {
MACOS_TERMINAL,
TERMIUS);
List<ExternalTerminalType> ALL = getTypes(OsType.getLocal(), false, true);
List<ExternalTerminalType> ALL = getTypes(OsType.getLocal(), true);
List<ExternalTerminalType> ALL_ON_ALL_PLATFORMS = getTypes(null, false, true);
List<ExternalTerminalType> ALL_ON_ALL_PLATFORMS = getTypes(null, true);
static List<ExternalTerminalType> getTypes(OsType osType, boolean remote, boolean custom) {
static List<ExternalTerminalType> getTypes(OsType osType, boolean custom) {
var all = new ArrayList<ExternalTerminalType>();
if (osType == null || osType.equals(OsType.WINDOWS)) {
all.addAll(WINDOWS_TERMINALS);
@@ -628,9 +627,6 @@ public interface ExternalTerminalType extends PrefsChoiceValue {
if (osType == null || osType.equals(OsType.MACOS)) {
all.addAll(MACOS_TERMINALS);
}
if (remote) {
all.removeIf(externalTerminalType -> externalTerminalType.remoteLaunchCommand(null) == null);
}
// Prefer recommended
all.sort(Comparator.comparingInt(o -> (o.isRecommended() ? -1 : 0)));
if (custom) {
@@ -690,11 +686,6 @@ public interface ExternalTerminalType extends PrefsChoiceValue {
default void launch(TerminalLaunchConfiguration configuration) throws Exception {}
default FailableFunction<TerminalLaunchConfiguration, String, Exception> remoteLaunchCommand(
ShellDialect systemDialect) {
return null;
}
abstract class WindowsType extends ExternalApplicationType.WindowsType implements ExternalTerminalType {
public WindowsType(String id, String executable) {
@@ -747,19 +738,6 @@ public interface ExternalTerminalType extends PrefsChoiceValue {
launch(configuration.getColoredTitle(), args);
}
@Override
public FailableFunction<TerminalLaunchConfiguration, String, Exception> remoteLaunchCommand(
ShellDialect systemDialect) {
return launchConfiguration -> {
var args = toCommand(launchConfiguration);
args.add(0, executable);
if (explicitlyAsync) {
args = systemDialect.launchAsnyc(args);
}
return args.buildSimple();
};
}
protected abstract CommandBuilder toCommand(TerminalLaunchConfiguration configuration) throws Exception;
}
}
@@ -4,8 +4,6 @@ import io.xpipe.app.util.CommandSupport;
import io.xpipe.app.util.LocalShell;
import io.xpipe.core.process.CommandBuilder;
import io.xpipe.core.process.ShellControl;
import io.xpipe.core.process.ShellDialect;
import io.xpipe.core.util.FailableFunction;
public class GnomeTerminalType extends ExternalTerminalType.PathCheckType implements TrackableTerminalType {
@@ -50,16 +48,4 @@ public class GnomeTerminalType extends ExternalTerminalType.PathCheckType implem
}
}
@Override
public FailableFunction<TerminalLaunchConfiguration, String, Exception> remoteLaunchCommand(
ShellDialect systemDialect) {
return launchConfiguration -> {
var toExecute = CommandBuilder.of()
.add(executable, "-v", "--title")
.addQuoted(launchConfiguration.getColoredTitle())
.add("--")
.addFile(launchConfiguration.getScriptFile());
return toExecute.buildSimple();
};
}
}
@@ -2,10 +2,8 @@ package io.xpipe.app.terminal;
import io.xpipe.app.util.LocalShell;
import io.xpipe.core.process.CommandBuilder;
import io.xpipe.core.process.ShellDialect;
import io.xpipe.core.process.ShellDialects;
import io.xpipe.core.process.TerminalInitFunction;
import io.xpipe.core.util.FailableFunction;
public class WarpTerminalType extends ExternalTerminalType.MacOsType {
@@ -52,18 +50,6 @@ public class WarpTerminalType extends ExternalTerminalType.MacOsType {
.addFile(configuration.getScriptFile()));
}
@Override
public FailableFunction<TerminalLaunchConfiguration, String, Exception> remoteLaunchCommand(
ShellDialect systemDialect) {
return launchConfiguration -> {
var toExecute = CommandBuilder.of()
.add("open", "-a")
.addQuoted("Warp.app")
.addFile(launchConfiguration.getScriptFile());
return toExecute.buildSimple();
};
}
@Override
public TerminalInitFunction additionalInitCommands() {
return TerminalInitFunction.of(sc -> {
@@ -1,29 +0,0 @@
package io.xpipe.ext.base.desktop;
import io.xpipe.app.storage.DataStoreEntryRef;
import io.xpipe.app.util.Validators;
import io.xpipe.core.store.DataStore;
import io.xpipe.ext.base.SelfReferentialStore;
import com.fasterxml.jackson.annotation.JsonTypeName;
import lombok.Value;
import lombok.experimental.SuperBuilder;
import lombok.extern.jackson.Jacksonized;
@Value
@SuperBuilder
@Jacksonized
@JsonTypeName("desktopCommand")
public class DesktopCommandStore implements DataStore, SelfReferentialStore {
private final DataStoreEntryRef<DesktopEnvironmentStore> environment;
private final String script;
@Override
public void checkComplete() throws Throwable {
Validators.nonNull(environment);
Validators.isType(environment, DesktopEnvironmentStore.class);
environment.checkComplete();
Validators.nonNull(script);
}
}
@@ -1,138 +0,0 @@
package io.xpipe.ext.base.desktop;
import io.xpipe.app.browser.BrowserFullSessionModel;
import io.xpipe.app.comp.base.IntegratedTextAreaComp;
import io.xpipe.app.comp.store.StoreChoiceComp;
import io.xpipe.app.comp.store.StoreEntryWrapper;
import io.xpipe.app.comp.store.StoreViewState;
import io.xpipe.app.ext.*;
import io.xpipe.app.storage.DataStoreEntry;
import io.xpipe.app.util.DataStoreFormatter;
import io.xpipe.app.util.OptionsBuilder;
import io.xpipe.core.store.DataStore;
import javafx.beans.binding.Bindings;
import javafx.beans.property.BooleanProperty;
import javafx.beans.property.Property;
import javafx.beans.property.SimpleObjectProperty;
import javafx.beans.property.SimpleStringProperty;
import java.util.List;
public class DesktopCommandStoreProvider implements DataStoreProvider {
@Override
public DataStoreUsageCategory getUsageCategory() {
return DataStoreUsageCategory.DESKTOP;
}
@Override
public ActionProvider.Action browserAction(
BrowserFullSessionModel sessionModel, DataStoreEntry store, BooleanProperty busy) {
return launchAction(store);
}
@Override
public ActionProvider.Action launchAction(DataStoreEntry store) {
return new ActionProvider.Action() {
@Override
public void execute() throws Exception {
DesktopCommandStore s = store.getStore().asNeeded();
var baseEntry = s.getEnvironment().getStore().getBase().get();
var baseActivate = baseEntry.getProvider().activateAction(baseEntry);
if (baseActivate != null) {
baseActivate.execute();
}
s.getEnvironment().getStore().runDesktopTerminal(store.getName(), s.getScript());
}
};
}
@Override
public DataStoreCreationCategory getCreationCategory() {
return DataStoreCreationCategory.DESKTOP;
}
@Override
public DataStoreEntry getDisplayParent(DataStoreEntry store) {
DesktopCommandStore s = store.getStore().asNeeded();
return s.getEnvironment().get();
}
@Override
public GuiDialog guiDialog(DataStoreEntry entry, Property<DataStore> store) {
DesktopCommandStore st = (DesktopCommandStore) store.getValue();
var env = new SimpleObjectProperty<>(st.getEnvironment());
var script = new SimpleStringProperty(st.getScript());
return new OptionsBuilder()
.nameAndDescription("desktopEnvironmentBase")
.addComp(
new StoreChoiceComp<>(
StoreChoiceComp.Mode.HOST,
entry,
env,
DesktopEnvironmentStore.class,
desktopStoreDataStoreEntryRef ->
desktopStoreDataStoreEntryRef.getStore().supportsDesktopAccess(),
StoreViewState.get().getAllConnectionsCategory()),
env)
.nonNull()
.nameAndDescription("desktopCommandScript")
.addComp(
new IntegratedTextAreaComp(
script,
false,
"commands",
Bindings.createStringBinding(
() -> {
return env.getValue() != null
&& env.getValue()
.getStore()
.getDialect()
!= null
? env.getValue()
.getStore()
.getDialect()
.getScriptFileEnding()
: "sh";
},
env)),
script)
.nonNull()
.bind(
() -> {
return DesktopCommandStore.builder()
.environment(env.get())
.script(script.get())
.build();
},
store)
.buildDialog();
}
public String summaryString(StoreEntryWrapper wrapper) {
DesktopCommandStore s = wrapper.getEntry().getStore().asNeeded();
return DataStoreFormatter.toApostropheName(s.getEnvironment().get()) + " config";
}
@Override
public String getDisplayIconFileName(DataStore store) {
return "base:desktopCommand_icon.svg";
}
@Override
public DataStore defaultStore() {
return DesktopCommandStore.builder().build();
}
@Override
public List<String> getPossibleNames() {
return List.of("desktopCommand");
}
@Override
public List<Class<?>> getStoreClasses() {
return List.of(DesktopCommandStore.class);
}
}
@@ -1,114 +0,0 @@
package io.xpipe.ext.base.desktop;
import io.xpipe.app.storage.DataStoreEntryRef;
import io.xpipe.app.terminal.ExternalTerminalType;
import io.xpipe.app.terminal.TerminalLaunchConfiguration;
import io.xpipe.app.util.Validators;
import io.xpipe.core.process.OsType;
import io.xpipe.core.process.ShellDialect;
import io.xpipe.core.store.DataStore;
import io.xpipe.core.store.FilePath;
import io.xpipe.ext.base.SelfReferentialStore;
import io.xpipe.ext.base.script.ScriptStore;
import com.fasterxml.jackson.annotation.JsonTypeName;
import lombok.Value;
import lombok.experimental.SuperBuilder;
import lombok.extern.jackson.Jacksonized;
import java.util.ArrayList;
import java.util.List;
@Value
@SuperBuilder
@Jacksonized
@JsonTypeName("desktopEnvironment")
public class DesktopEnvironmentStore implements DesktopBaseStore, DataStore, SelfReferentialStore {
private final DataStoreEntryRef<DesktopBaseStore> base;
private final ExternalTerminalType terminal;
private final ShellDialect dialect;
private final List<DataStoreEntryRef<ScriptStore>> scripts;
private final String initScript;
@Override
public void checkComplete() throws Throwable {
Validators.nonNull(base);
Validators.isType(base, DesktopBaseStore.class);
base.checkComplete();
Validators.nonNull(terminal);
Validators.nonNull(dialect);
}
public List<DataStoreEntryRef<ScriptStore>> getEffectiveScripts() {
return scripts != null
? scripts.stream().filter(scriptStore -> scriptStore != null).toList()
: List.of();
}
public String getMergedInitCommands(String command) {
var f = ScriptStore.flatten(scripts);
var filtered = f.stream()
.filter(simpleScriptStore ->
simpleScriptStore.getStore().getMinimumDialect().isCompatibleTo(dialect))
.toList();
var initCommands = new ArrayList<>(filtered.stream()
.map(simpleScriptStore -> simpleScriptStore.getStore().getCommands())
.toList());
if (initScript != null) {
initCommands.add(initScript);
}
if (command != null) {
initCommands.add(command);
}
var joined = String.join(dialect.getNewLine().getNewLineString(), initCommands);
return joined;
}
@Override
public boolean supportsDesktopAccess() {
return base.getStore().supportsDesktopAccess();
}
@Override
public void runDesktopApplication(String name, DesktopApplicationStore applicationStore) throws Exception {
var fullName = name + " [" + getSelfEntry().getName() + "]";
base.getStore().runDesktopApplication(fullName, applicationStore);
}
@Override
public void runDesktopScript(String name, String script) throws Exception {
var fullName = getSelfEntry().getName();
base.getStore().runDesktopScript(fullName, getMergedInitCommands(script));
}
@Override
public FilePath createScript(ShellDialect dialect, String content) throws Exception {
return base.getStore().createScript(dialect, content);
}
public void runDesktopTerminal(String name, String script) throws Exception {
var launchCommand = terminal.remoteLaunchCommand(base.getStore().getUsedDialect());
var toExecute = (script != null
? getMergedInitCommands(
script + "\n" + dialect.getPauseCommand() + "\n" + dialect.getNormalExitCommand())
: getMergedInitCommands(null));
var scriptFile = base.getStore().createScript(dialect, toExecute);
var launchScriptFile = base.getStore()
.createScript(
dialect,
dialect.prepareTerminalInitFileOpenCommand(dialect, null, scriptFile.toString(), false));
var launchConfig = new TerminalLaunchConfiguration(null, name, name, true, launchScriptFile, dialect);
base.getStore().runDesktopScript(name, launchCommand.apply(launchConfig));
}
@Override
public ShellDialect getUsedDialect() {
return dialect;
}
@Override
public OsType getUsedOsType() {
return base != null ? base.getStore().getUsedOsType() : null;
}
}
@@ -1,193 +0,0 @@
package io.xpipe.ext.base.desktop;
import io.xpipe.app.browser.BrowserFullSessionModel;
import io.xpipe.app.comp.Comp;
import io.xpipe.app.comp.base.ChoiceComp;
import io.xpipe.app.comp.base.IntegratedTextAreaComp;
import io.xpipe.app.comp.store.StoreChoiceComp;
import io.xpipe.app.comp.store.StoreEntryWrapper;
import io.xpipe.app.comp.store.StoreListChoiceComp;
import io.xpipe.app.comp.store.StoreViewState;
import io.xpipe.app.core.AppExtensionManager;
import io.xpipe.app.ext.*;
import io.xpipe.app.storage.DataStoreEntry;
import io.xpipe.app.terminal.ExternalTerminalType;
import io.xpipe.app.util.DataStoreFormatter;
import io.xpipe.app.util.OptionsBuilder;
import io.xpipe.core.store.DataStore;
import io.xpipe.ext.base.script.ScriptStore;
import javafx.beans.binding.Bindings;
import javafx.beans.property.*;
import javafx.collections.FXCollections;
import lombok.SneakyThrows;
import java.util.ArrayList;
import java.util.List;
public class DesktopEnvironmentStoreProvider implements DataStoreProvider {
@Override
public DataStoreUsageCategory getUsageCategory() {
return DataStoreUsageCategory.DESKTOP;
}
@Override
public ActionProvider.Action browserAction(
BrowserFullSessionModel sessionModel, DataStoreEntry store, BooleanProperty busy) {
return launchAction(store);
}
@Override
public ActionProvider.Action activateAction(DataStoreEntry store) {
return new ActionProvider.Action() {
@Override
public void execute() throws Exception {
DesktopEnvironmentStore s = store.getStore().asNeeded();
var a = s.getBase()
.get()
.getProvider()
.activateAction(s.getBase().get());
if (a != null) {
a.execute();
}
}
};
}
@Override
public ActionProvider.Action launchAction(DataStoreEntry store) {
return new ActionProvider.Action() {
@Override
public void execute() throws Exception {
DesktopEnvironmentStore s = store.getStore().asNeeded();
var a = s.getBase()
.get()
.getProvider()
.activateAction(s.getBase().get());
if (a != null) {
a.execute();
}
var fullName = store.getName();
s.runDesktopTerminal(fullName, null);
}
};
}
@Override
public DataStoreCreationCategory getCreationCategory() {
return DataStoreCreationCategory.DESKTOP;
}
@Override
public DataStoreEntry getDisplayParent(DataStoreEntry store) {
DesktopEnvironmentStore s = store.getStore().asNeeded();
return s.getBase().get();
}
@Override
@SneakyThrows
public GuiDialog guiDialog(DataStoreEntry entry, Property<DataStore> store) {
DesktopEnvironmentStore st = (DesktopEnvironmentStore) store.getValue();
var host = new SimpleObjectProperty<>(st.getBase());
var terminal = new SimpleObjectProperty<>(st.getTerminal());
var dialect = new SimpleObjectProperty<>(st.getDialect());
var scripts =
new SimpleListProperty<>(FXCollections.observableArrayList(new ArrayList<>(st.getEffectiveScripts())));
var initScript = new SimpleStringProperty(st.getInitScript());
Comp<?> dialectChoice = (Comp<?>) Class.forName(
AppExtensionManager.getInstance()
.getExtendedLayer()
.findModule("io.xpipe.ext.proc")
.orElseThrow(),
"io.xpipe.ext.proc.ShellDialectChoiceComp")
.getDeclaredConstructor(Property.class, boolean.class)
.newInstance(dialect, false);
return new OptionsBuilder()
.nameAndDescription("desktopHost")
.addComp(
new StoreChoiceComp<>(
StoreChoiceComp.Mode.HOST,
entry,
host,
DesktopBaseStore.class,
desktopStoreDataStoreEntryRef ->
desktopStoreDataStoreEntryRef.getStore().supportsDesktopAccess(),
StoreViewState.get().getAllConnectionsCategory()),
host)
.nonNull()
.nameAndDescription("desktopTerminal")
.addComp(
ChoiceComp.ofTranslatable(
terminal, ExternalTerminalType.getTypes(st.getUsedOsType(), true, false), true)
.maxWidth(2000),
terminal)
.nonNull()
.nameAndDescription("desktopShellDialect")
.addComp(dialectChoice, dialect)
.nonNull()
.nameAndDescription("desktopSnippets")
.addComp(
new StoreListChoiceComp<>(
scripts,
ScriptStore.class,
scriptStore -> !scripts.contains(scriptStore),
StoreViewState.get().getAllScriptsCategory()),
scripts)
.nameAndDescription("desktopInitScript")
.addComp(
new IntegratedTextAreaComp(
initScript,
false,
"commands",
Bindings.createStringBinding(
() -> {
return dialect.getValue() != null
? dialect.getValue().getScriptFileEnding()
: "sh";
},
dialect)),
initScript)
.bind(
() -> {
return DesktopEnvironmentStore.builder()
.base(host.get())
.terminal(terminal.get())
.dialect(dialect.get())
.scripts(scripts.get())
.initScript(initScript.get())
.build();
},
store)
.buildDialog();
}
public String summaryString(StoreEntryWrapper wrapper) {
DesktopEnvironmentStore s = wrapper.getEntry().getStore().asNeeded();
return DataStoreFormatter.toApostropheName(s.getBase().get()) + " environment";
}
@Override
public String getDisplayIconFileName(DataStore store) {
return "base:desktopEnvironment_icon.svg";
}
@Override
public DataStore defaultStore() {
return DesktopEnvironmentStore.builder().build();
}
@Override
public List<String> getPossibleNames() {
return List.of("desktopEnvironment");
}
@Override
public List<Class<?>> getStoreClasses() {
return List.of(DesktopEnvironmentStore.class);
}
}
+1 -5
View File
@@ -5,9 +5,6 @@ import io.xpipe.app.ext.DataStoreProvider;
import io.xpipe.ext.base.action.*;
import io.xpipe.ext.base.browser.*;
import io.xpipe.ext.base.browser.compress.*;
import io.xpipe.ext.base.desktop.DesktopApplicationStoreProvider;
import io.xpipe.ext.base.desktop.DesktopCommandStoreProvider;
import io.xpipe.ext.base.desktop.DesktopEnvironmentStoreProvider;
import io.xpipe.ext.base.identity.*;
import io.xpipe.ext.base.script.*;
import io.xpipe.ext.base.service.*;
@@ -15,6 +12,7 @@ import io.xpipe.ext.base.store.StorePauseAction;
import io.xpipe.ext.base.store.StoreRestartAction;
import io.xpipe.ext.base.store.StoreStartAction;
import io.xpipe.ext.base.store.StoreStopAction;
import io.xpipe.ext.base.desktop.DesktopApplicationStoreProvider;
open module io.xpipe.ext.base {
exports io.xpipe.ext.base;
@@ -102,9 +100,7 @@ open module io.xpipe.ext.base {
MappedServiceStoreProvider,
FixedServiceStoreProvider,
SimpleScriptStoreProvider,
DesktopEnvironmentStoreProvider,
DesktopApplicationStoreProvider,
DesktopCommandStoreProvider,
LocalIdentityStoreProvider,
SyncedIdentityStoreProvider,
ScriptGroupStoreProvider;