diff --git a/ui/desktop/app/routes/scopes/scope/projects/targets.js b/ui/desktop/app/routes/scopes/scope/projects/targets.js
index 9d98bb1ab..a88a5e5e1 100644
--- a/ui/desktop/app/routes/scopes/scope/projects/targets.js
+++ b/ui/desktop/app/routes/scopes/scope/projects/targets.js
@@ -48,11 +48,16 @@ export default class ScopesScopeProjectsTargetsRoute extends Route {
@action
async connect(model) {
try {
- await this.ipc.invoke('cli');
- const connection = await this.ipc.invoke('connect', {
+ // Check for cli
+ const cliPath = await this.ipc.invoke('cliPath');
+ if(!cliPath) throw new Error('Cannot find boundary cli.')
+
+ // Create target session
+ const connection = this.ipc.invoke('connect', {
target_id: model.target.id,
token: this.session.data.authenticated.token,
});
+
// Show the user a modal with basic connection info.
this.confirm.confirm(connection, { isConnectSuccess: true });
} catch(e) {
diff --git a/ui/desktop/app/templates/scopes/scope/projects/targets/index.hbs b/ui/desktop/app/templates/scopes/scope/projects/targets/index.hbs
index 7d2ea2383..8c3c463e5 100644
--- a/ui/desktop/app/templates/scopes/scope/projects/targets/index.hbs
+++ b/ui/desktop/app/templates/scopes/scope/projects/targets/index.hbs
@@ -34,6 +34,7 @@
{{model.project.name}}
+
{{model.project.id}}
diff --git a/ui/desktop/electron-app/src/handlers.js b/ui/desktop/electron-app/src/handlers.js
index d747c556c..3dc473c23 100644
--- a/ui/desktop/electron-app/src/handlers.js
+++ b/ui/desktop/electron-app/src/handlers.js
@@ -21,9 +21,9 @@ handle('getOrigin', () => origin);
handle('setOrigin', (requestOrigin) => origin = requestOrigin);
/**
- * Detect boundary cli in env path
+ * Detect boundary cli path
*/
-handle('cli', async () => {
+handle('cliPath', async () => {
const cliPath = await lookpath('boundary');
if(!cliPath) throw new Error({ message: 'Cannot find boundary cli.'})
return cliPath;
diff --git a/ui/desktop/electron-app/src/spawn-promise.js b/ui/desktop/electron-app/src/spawn-promise.js
index 1fdac9a6e..5fa22cf4c 100644
--- a/ui/desktop/electron-app/src/spawn-promise.js
+++ b/ui/desktop/electron-app/src/spawn-promise.js
@@ -1,17 +1,17 @@
const { spawn } = require('child_process');
-/**
- * Attempt to parse output string to JSON.
- * When JSON is successfully parsed, consider stdout fully read.
-*/
-// TODO: Potential use for BufferList?
-const resolveOutput = (resolve, outputStream) => {
+// Verify json
+const isJSON = (data) => {
+ let jsonData;
+ if(typeof data !== 'string') data = JSON.stringify(data)
try {
- resolve(JSON.parse(outputStream));
+ jsonData = JSON.parse(data);
} catch (e) {
- // Ignore JSON parse errors while stdout buffers.
+ // Ignore parse errors
}
-};
+
+ return (typeof jsonData === 'object');
+}
// You can throw exceptions, or allow them to occur, and this is supported.
// Exceptions thrown in this way will be returned to the UI as an
@@ -27,15 +27,6 @@ const resolveOutput = (resolve, outputStream) => {
// error from the underlying exec implementation. It's not a very
// helpful message for users, so it's recommended to craft nice
// POJO representation and throw it or promise->reject it.
-const rejectError = (reject, message) => {
- try {
- const errorMessage = JSON.parse(message);
- reject(new Error(errorMessage.error));
- } catch (e) {
- // Ignore JSON parse errors while stderr buffers.
- }
-};
-
module.exports = function spawnPromise (command) {
return new Promise((resolve, reject) => {
const childProcess = spawn('boundary', command);
@@ -44,12 +35,12 @@ module.exports = function spawnPromise (command) {
childProcess.stdout.on('data', (data) => {
outputStream += data.toString();
- resolveOutput(resolve, outputStream);
+ if(isJSON(outputStream)) resolve(JSON.parse(outputStream));
});
childProcess.stderr.on('data', (data) => {
errorStream += data.toString();
- rejectError(reject, errorStream);
+ if(isJSON(errorStream)) reject(new Error(JSON.parse(errorStream)?.error));
});
});
-}
\ No newline at end of file
+}