diff --git a/ExternalConnectors/AWS/AWSConnectionForm.Designer.cs b/ExternalConnectors/AWS/AWSConnectionForm.Designer.cs
new file mode 100644
index 00000000..054d814e
--- /dev/null
+++ b/ExternalConnectors/AWS/AWSConnectionForm.Designer.cs
@@ -0,0 +1,207 @@
+namespace ExternalConnectors.AWS
+{
+ partial class AWSConnectionForm
+ {
+ ///
+ /// Required designer variable.
+ ///
+ private System.ComponentModel.IContainer components = null;
+
+ ///
+ /// Clean up any resources being used.
+ ///
+ /// true if managed resources should be disposed; otherwise, false.
+ protected override void Dispose(bool disposing)
+ {
+ if (disposing && (components != null))
+ {
+ components.Dispose();
+ }
+ base.Dispose(disposing);
+ }
+
+ #region Windows Form Designer generated code
+
+ ///
+ /// Required method for Designer support - do not modify
+ /// the contents of this method with the code editor.
+ ///
+ private void InitializeComponent()
+ {
+ this.tbAccesKeyID = new System.Windows.Forms.TextBox();
+ this.tbAccesKey = new System.Windows.Forms.TextBox();
+ this.btnOK = new System.Windows.Forms.Button();
+ this.btnCancel = new System.Windows.Forms.Button();
+ this.tableLayoutPanel1 = new System.Windows.Forms.TableLayoutPanel();
+ this.tbRegion = new System.Windows.Forms.TextBox();
+ this.label3 = new System.Windows.Forms.Label();
+ this.label1 = new System.Windows.Forms.Label();
+ this.label2 = new System.Windows.Forms.Label();
+ this.tableLayoutPanel2 = new System.Windows.Forms.TableLayoutPanel();
+ this.tableLayoutPanel1.SuspendLayout();
+ this.tableLayoutPanel2.SuspendLayout();
+ this.SuspendLayout();
+ //
+ // tbAccesKeyID
+ //
+ this.tbAccesKeyID.Dock = System.Windows.Forms.DockStyle.Fill;
+ this.tbAccesKeyID.Location = new System.Drawing.Point(260, 7);
+ this.tbAccesKeyID.Margin = new System.Windows.Forms.Padding(6, 7, 6, 7);
+ this.tbAccesKeyID.Name = "tbAccesKeyID";
+ this.tbAccesKeyID.Size = new System.Drawing.Size(842, 35);
+ this.tbAccesKeyID.TabIndex = 0;
+ //
+ // tbAccesKey
+ //
+ this.tbAccesKey.Dock = System.Windows.Forms.DockStyle.Fill;
+ this.tbAccesKey.Location = new System.Drawing.Point(260, 86);
+ this.tbAccesKey.Margin = new System.Windows.Forms.Padding(6, 7, 6, 7);
+ this.tbAccesKey.Name = "tbAccesKey";
+ this.tbAccesKey.Size = new System.Drawing.Size(842, 35);
+ this.tbAccesKey.TabIndex = 2;
+ //
+ // btnOK
+ //
+ this.btnOK.Anchor = System.Windows.Forms.AnchorStyles.Right;
+ this.btnOK.DialogResult = System.Windows.Forms.DialogResult.OK;
+ this.btnOK.Location = new System.Drawing.Point(378, 23);
+ this.btnOK.Margin = new System.Windows.Forms.Padding(6, 7, 6, 7);
+ this.btnOK.Name = "btnOK";
+ this.btnOK.Size = new System.Drawing.Size(150, 53);
+ this.btnOK.TabIndex = 10;
+ this.btnOK.Text = "OK";
+ this.btnOK.UseVisualStyleBackColor = true;
+ //
+ // btnCancel
+ //
+ this.btnCancel.Anchor = System.Windows.Forms.AnchorStyles.Left;
+ this.btnCancel.DialogResult = System.Windows.Forms.DialogResult.Cancel;
+ this.btnCancel.Location = new System.Drawing.Point(580, 23);
+ this.btnCancel.Margin = new System.Windows.Forms.Padding(6, 7, 6, 7);
+ this.btnCancel.Name = "btnCancel";
+ this.btnCancel.Size = new System.Drawing.Size(150, 53);
+ this.btnCancel.TabIndex = 11;
+ this.btnCancel.Text = "Cancel";
+ this.btnCancel.UseVisualStyleBackColor = true;
+ //
+ // tableLayoutPanel1
+ //
+ this.tableLayoutPanel1.ColumnCount = 2;
+ this.tableLayoutPanel1.ColumnStyles.Add(new System.Windows.Forms.ColumnStyle(System.Windows.Forms.SizeType.Percent, 22.92994F));
+ this.tableLayoutPanel1.ColumnStyles.Add(new System.Windows.Forms.ColumnStyle(System.Windows.Forms.SizeType.Percent, 77.07006F));
+ this.tableLayoutPanel1.Controls.Add(this.tbRegion, 1, 2);
+ this.tableLayoutPanel1.Controls.Add(this.label3, 0, 2);
+ this.tableLayoutPanel1.Controls.Add(this.label1, 0, 0);
+ this.tableLayoutPanel1.Controls.Add(this.label2, 0, 1);
+ this.tableLayoutPanel1.Controls.Add(this.tbAccesKeyID, 1, 0);
+ this.tableLayoutPanel1.Controls.Add(this.tbAccesKey, 1, 1);
+ this.tableLayoutPanel1.Dock = System.Windows.Forms.DockStyle.Top;
+ this.tableLayoutPanel1.Location = new System.Drawing.Point(0, 0);
+ this.tableLayoutPanel1.Margin = new System.Windows.Forms.Padding(6, 7, 6, 7);
+ this.tableLayoutPanel1.Name = "tableLayoutPanel1";
+ this.tableLayoutPanel1.RowCount = 3;
+ this.tableLayoutPanel1.RowStyles.Add(new System.Windows.Forms.RowStyle(System.Windows.Forms.SizeType.Percent, 50F));
+ this.tableLayoutPanel1.RowStyles.Add(new System.Windows.Forms.RowStyle(System.Windows.Forms.SizeType.Percent, 50F));
+ this.tableLayoutPanel1.RowStyles.Add(new System.Windows.Forms.RowStyle(System.Windows.Forms.SizeType.Absolute, 46F));
+ this.tableLayoutPanel1.RowStyles.Add(new System.Windows.Forms.RowStyle(System.Windows.Forms.SizeType.Absolute, 46F));
+ this.tableLayoutPanel1.RowStyles.Add(new System.Windows.Forms.RowStyle(System.Windows.Forms.SizeType.Absolute, 46F));
+ this.tableLayoutPanel1.Size = new System.Drawing.Size(1108, 205);
+ this.tableLayoutPanel1.TabIndex = 12;
+ //
+ // tbRegion
+ //
+ this.tbRegion.Dock = System.Windows.Forms.DockStyle.Fill;
+ this.tbRegion.Location = new System.Drawing.Point(260, 165);
+ this.tbRegion.Margin = new System.Windows.Forms.Padding(6, 7, 6, 7);
+ this.tbRegion.Name = "tbRegion";
+ this.tbRegion.Size = new System.Drawing.Size(842, 35);
+ this.tbRegion.TabIndex = 6;
+ //
+ // label3
+ //
+ this.label3.AutoSize = true;
+ this.label3.Dock = System.Windows.Forms.DockStyle.Fill;
+ this.label3.Location = new System.Drawing.Point(6, 158);
+ this.label3.Margin = new System.Windows.Forms.Padding(6, 0, 6, 0);
+ this.label3.Name = "label3";
+ this.label3.Size = new System.Drawing.Size(242, 47);
+ this.label3.TabIndex = 5;
+ this.label3.Text = "Region";
+ this.label3.TextAlign = System.Drawing.ContentAlignment.MiddleLeft;
+ //
+ // label1
+ //
+ this.label1.AutoSize = true;
+ this.label1.Dock = System.Windows.Forms.DockStyle.Fill;
+ this.label1.Location = new System.Drawing.Point(6, 0);
+ this.label1.Margin = new System.Windows.Forms.Padding(6, 0, 6, 0);
+ this.label1.Name = "label1";
+ this.label1.Size = new System.Drawing.Size(242, 79);
+ this.label1.TabIndex = 2;
+ this.label1.Text = "Access Key ID";
+ this.label1.TextAlign = System.Drawing.ContentAlignment.MiddleLeft;
+ //
+ // label2
+ //
+ this.label2.AutoSize = true;
+ this.label2.Dock = System.Windows.Forms.DockStyle.Fill;
+ this.label2.Location = new System.Drawing.Point(6, 79);
+ this.label2.Margin = new System.Windows.Forms.Padding(6, 0, 6, 0);
+ this.label2.Name = "label2";
+ this.label2.Size = new System.Drawing.Size(242, 79);
+ this.label2.TabIndex = 4;
+ this.label2.Text = "Access Key";
+ this.label2.TextAlign = System.Drawing.ContentAlignment.MiddleLeft;
+ //
+ // tableLayoutPanel2
+ //
+ this.tableLayoutPanel2.ColumnCount = 5;
+ this.tableLayoutPanel2.ColumnStyles.Add(new System.Windows.Forms.ColumnStyle(System.Windows.Forms.SizeType.Absolute, 160F));
+ this.tableLayoutPanel2.ColumnStyles.Add(new System.Windows.Forms.ColumnStyle(System.Windows.Forms.SizeType.Percent, 50F));
+ this.tableLayoutPanel2.ColumnStyles.Add(new System.Windows.Forms.ColumnStyle(System.Windows.Forms.SizeType.Absolute, 40F));
+ this.tableLayoutPanel2.ColumnStyles.Add(new System.Windows.Forms.ColumnStyle(System.Windows.Forms.SizeType.Percent, 50F));
+ this.tableLayoutPanel2.ColumnStyles.Add(new System.Windows.Forms.ColumnStyle(System.Windows.Forms.SizeType.Absolute, 160F));
+ this.tableLayoutPanel2.Controls.Add(this.btnOK, 1, 0);
+ this.tableLayoutPanel2.Controls.Add(this.btnCancel, 3, 0);
+ this.tableLayoutPanel2.Dock = System.Windows.Forms.DockStyle.Bottom;
+ this.tableLayoutPanel2.Location = new System.Drawing.Point(0, 344);
+ this.tableLayoutPanel2.Margin = new System.Windows.Forms.Padding(6, 7, 6, 7);
+ this.tableLayoutPanel2.Name = "tableLayoutPanel2";
+ this.tableLayoutPanel2.RowCount = 1;
+ this.tableLayoutPanel2.RowStyles.Add(new System.Windows.Forms.RowStyle(System.Windows.Forms.SizeType.Percent, 100F));
+ this.tableLayoutPanel2.Size = new System.Drawing.Size(1108, 99);
+ this.tableLayoutPanel2.TabIndex = 13;
+ //
+ // AWSConnectionForm
+ //
+ this.AcceptButton = this.btnOK;
+ this.AutoScaleDimensions = new System.Drawing.SizeF(12F, 30F);
+ this.AutoScaleMode = System.Windows.Forms.AutoScaleMode.Font;
+ this.ClientSize = new System.Drawing.Size(1108, 443);
+ this.Controls.Add(this.tableLayoutPanel2);
+ this.Controls.Add(this.tableLayoutPanel1);
+ this.Margin = new System.Windows.Forms.Padding(6, 7, 6, 7);
+ this.Name = "AWSConnectionForm";
+ this.Text = "AWS EC2 API Login Data";
+ this.Activated += new System.EventHandler(this.AWSConnectionForm_Activated);
+ this.tableLayoutPanel1.ResumeLayout(false);
+ this.tableLayoutPanel1.PerformLayout();
+ this.tableLayoutPanel2.ResumeLayout(false);
+ this.ResumeLayout(false);
+
+ }
+
+ #endregion
+
+ public System.Windows.Forms.TextBox tbAccesKeyID;
+ public System.Windows.Forms.TextBox tbAccesKey;
+ private System.Windows.Forms.Button btnOK;
+ private System.Windows.Forms.Button btnCancel;
+ private System.Windows.Forms.TableLayoutPanel tableLayoutPanel1;
+ private System.Windows.Forms.Label label2;
+ private System.Windows.Forms.Label label1;
+ private System.Windows.Forms.TableLayoutPanel tableLayoutPanel2;
+ public System.Windows.Forms.TextBox tbRegion;
+ private System.Windows.Forms.Label label3;
+ }
+}
\ No newline at end of file
diff --git a/ExternalConnectors/AWS/AWSConnectionForm.cs b/ExternalConnectors/AWS/AWSConnectionForm.cs
new file mode 100644
index 00000000..196613ed
--- /dev/null
+++ b/ExternalConnectors/AWS/AWSConnectionForm.cs
@@ -0,0 +1,16 @@
+namespace ExternalConnectors.AWS
+{
+ public partial class AWSConnectionForm : Form
+ {
+ public AWSConnectionForm()
+ {
+ InitializeComponent();
+
+ }
+
+ private void AWSConnectionForm_Activated(object sender, EventArgs e)
+ {
+ tbAccesKeyID.Focus();
+ }
+ }
+}
diff --git a/ExternalConnectors/AWS/AWSConnectionForm.resx b/ExternalConnectors/AWS/AWSConnectionForm.resx
new file mode 100644
index 00000000..f298a7be
--- /dev/null
+++ b/ExternalConnectors/AWS/AWSConnectionForm.resx
@@ -0,0 +1,60 @@
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+ text/microsoft-resx
+
+
+ 2.0
+
+
+ System.Resources.ResXResourceReader, System.Windows.Forms, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089
+
+
+ System.Resources.ResXResourceWriter, System.Windows.Forms, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089
+
+
\ No newline at end of file
diff --git a/ExternalConnectors/AWS/EC2FetchDataService.cs b/ExternalConnectors/AWS/EC2FetchDataService.cs
new file mode 100644
index 00000000..fbb13f50
--- /dev/null
+++ b/ExternalConnectors/AWS/EC2FetchDataService.cs
@@ -0,0 +1,119 @@
+using Amazon;
+using Amazon.EC2;
+using Amazon.EC2.Model;
+using Microsoft.Win32;
+
+namespace ExternalConnectors.AWS
+{
+ public class EC2FetchDataService
+ {
+ private static DateTime lastFetch;
+ private static List? lastData;
+
+ // input must be in format "AWSAPI:instanceid" where instanceid is the ec2 instance id, e.g. i-066f750a76c97583d
+ public static async Task GetEC2InstanceDataAsync(string input)
+ {
+ // get secret id
+ if (!input.StartsWith("AWSAPI:"))
+ throw new Exception("calling this function requires AWSAPI: input");
+ string InstanceID = input[7..];
+
+ // init connection credentials, display popup if necessary
+ AWSConnectionData.Init();
+ var alldata = await GetEC2IPDataAsync();
+ var found = alldata.Where(x => x.InstanceId == InstanceID).SingleOrDefault();
+ return (found == null) ? "" : found.PublicIP;
+ }
+
+ private static async Task> GetEC2IPDataAsync()
+ {
+ // caching
+ TimeSpan timeSpan = DateTime.Now - lastFetch;
+ if (timeSpan.TotalMinutes < 1 && lastData != null)
+ return lastData;
+
+ AWSConfigs.AWSRegion = AWSConnectionData.region;
+ string awsAccessKeyId = AWSConnectionData.awsKeyID;
+ string awsSecretAccessKey = AWSConnectionData.awsKey;
+
+ var _client = new AmazonEC2Client(awsAccessKeyId, awsSecretAccessKey, RegionEndpoint.EUCentral1);
+ bool done = false;
+
+ List instanceList = new();
+ var request = new DescribeInstancesRequest();
+ while (!done)
+ {
+ DescribeInstancesResponse response = await _client.DescribeInstancesAsync(request);
+
+ foreach (var reservation in response.Reservations)
+ {
+ foreach (var instance in reservation.Instances)
+ {
+ string vmname = "";
+ foreach (var tag in instance.Tags)
+ {
+ if (tag.Key == "Name")
+ {
+ vmname = tag.Value;
+ }
+ }
+ InstanceInfo inf = new(instance, vmname);
+ instanceList.Add(inf);
+ }
+ }
+
+ request.NextToken = response.NextToken;
+
+ if (response.NextToken == null)
+ {
+ done = true;
+ }
+ }
+
+ lastData = instanceList.OrderBy(x => x.Name).ToList();
+ lastFetch = DateTime.Now;
+ return lastData;
+ }
+
+
+ public static class AWSConnectionData
+ {
+ private static readonly RegistryKey key = Registry.CurrentUser.CreateSubKey(@"SOFTWARE\mRemoteAWSInterface");
+
+ public static string awsKeyID = "";
+ public static string awsKey = "";
+ public static string region = "eu-central-1";
+
+ public static void Init()
+ {
+ if (awsKey != "")
+ return;
+
+ // display gui and ask for data
+ AWSConnectionForm f = new();
+ f.tbAccesKeyID.Text = "" + key.GetValue("KeyID");
+ f.tbAccesKey.Text = "" + key.GetValue("Key");
+ f.tbRegion.Text = "" + key.GetValue("Region");
+ if (f.tbRegion.Text == null || f.tbRegion.Text.Length < 2)
+ f.tbRegion.Text = region;
+ _ = f.ShowDialog();
+
+ if (f.DialogResult != DialogResult.OK)
+ return;
+
+ // store values to memory
+ awsKeyID = f.tbAccesKeyID.Text;
+ awsKey = f.tbAccesKey.Text;
+ region = f.tbRegion.Text;
+
+
+ // write values to registry
+ key.SetValue("KeyID", awsKeyID);
+ key.SetValue("Key", awsKey);
+ key.SetValue("Region", region);
+ key.Close();
+ }
+ }
+
+ }
+}
diff --git a/ExternalConnectors/AWS/InstanceInfo.cs b/ExternalConnectors/AWS/InstanceInfo.cs
new file mode 100644
index 00000000..eeeeee9b
--- /dev/null
+++ b/ExternalConnectors/AWS/InstanceInfo.cs
@@ -0,0 +1,33 @@
+using Amazon.EC2.Model;
+using System;
+
+namespace ExternalConnectors.AWS
+{
+ public class InstanceInfo
+ {
+ public string InstanceId { get; }
+ public string Name { get; }
+ public string Status { get; }
+ public string PublicIP { get; }
+ public string PrivateIP { get; }
+ public InstanceInfo(Instance instance, string name)
+ {
+ InstanceId = instance.InstanceId;
+ Name = name;
+
+ switch(instance.State.Code)
+ {
+ case 0: Status = "Pending"; break;
+ case 16: Status = "Running"; break;
+ case 32: Status = "Shutdown"; break;
+ case 48: Status = "Terminated"; break;
+ case 64: Status = "Stopping"; break;
+ case 80: Status = "Stopped"; break;
+ default: Status = "Unknown"; break;
+ };
+
+ PublicIP = instance.PublicIpAddress;
+ PrivateIP = instance.PrivateIpAddress;
+ }
+ }
+}
diff --git a/ExternalConnectors/ExternalConnectors.csproj b/ExternalConnectors/ExternalConnectors.csproj
new file mode 100644
index 00000000..e792ce36
--- /dev/null
+++ b/ExternalConnectors/ExternalConnectors.csproj
@@ -0,0 +1,26 @@
+
+
+
+ net6.0-windows
+ enable
+ enable
+ Library
+ True
+
+
+
+
+
+
+
+
+
+
+ Form
+
+
+ Form
+
+
+
+
diff --git a/ExternalConnectors/TSS/SSConnectionForm.Designer.cs b/ExternalConnectors/TSS/SSConnectionForm.Designer.cs
new file mode 100644
index 00000000..dfeb387a
--- /dev/null
+++ b/ExternalConnectors/TSS/SSConnectionForm.Designer.cs
@@ -0,0 +1,256 @@
+namespace ExternalConnectors.TSS
+{
+ partial class SSConnectionForm
+ {
+ ///
+ /// Required designer variable.
+ ///
+ private System.ComponentModel.IContainer components = null;
+
+ ///
+ /// Clean up any resources being used.
+ ///
+ /// true if managed resources should be disposed; otherwise, false.
+ protected override void Dispose(bool disposing)
+ {
+ if (disposing && (components != null))
+ {
+ components.Dispose();
+ }
+ base.Dispose(disposing);
+ }
+
+ #region Windows Form Designer generated code
+
+ ///
+ /// Required method for Designer support - do not modify
+ /// the contents of this method with the code editor.
+ ///
+ private void InitializeComponent()
+ {
+ this.tbSSURL = new System.Windows.Forms.TextBox();
+ this.tbUsername = new System.Windows.Forms.TextBox();
+ this.label3 = new System.Windows.Forms.Label();
+ this.tbPassword = new System.Windows.Forms.TextBox();
+ this.btnOK = new System.Windows.Forms.Button();
+ this.btnCancel = new System.Windows.Forms.Button();
+ this.tableLayoutPanel1 = new System.Windows.Forms.TableLayoutPanel();
+ this.label5 = new System.Windows.Forms.Label();
+ this.label1 = new System.Windows.Forms.Label();
+ this.label2 = new System.Windows.Forms.Label();
+ this.cbUseSSO = new System.Windows.Forms.CheckBox();
+ this.tableLayoutPanel2 = new System.Windows.Forms.TableLayoutPanel();
+ this.label4 = new System.Windows.Forms.Label();
+ this.tableLayoutPanel1.SuspendLayout();
+ this.tableLayoutPanel2.SuspendLayout();
+ this.SuspendLayout();
+ //
+ // tbSSURL
+ //
+ this.tbSSURL.Dock = System.Windows.Forms.DockStyle.Fill;
+ this.tbSSURL.Location = new System.Drawing.Point(445, 7);
+ this.tbSSURL.Margin = new System.Windows.Forms.Padding(6, 7, 6, 7);
+ this.tbSSURL.Name = "tbSSURL";
+ this.tbSSURL.Size = new System.Drawing.Size(921, 35);
+ this.tbSSURL.TabIndex = 0;
+ //
+ // tbUsername
+ //
+ this.tbUsername.Dock = System.Windows.Forms.DockStyle.Fill;
+ this.tbUsername.Location = new System.Drawing.Point(445, 69);
+ this.tbUsername.Margin = new System.Windows.Forms.Padding(6, 7, 6, 7);
+ this.tbUsername.Name = "tbUsername";
+ this.tbUsername.Size = new System.Drawing.Size(921, 35);
+ this.tbUsername.TabIndex = 2;
+ //
+ // label3
+ //
+ this.label3.AutoSize = true;
+ this.label3.Dock = System.Windows.Forms.DockStyle.Fill;
+ this.label3.Location = new System.Drawing.Point(6, 124);
+ this.label3.Margin = new System.Windows.Forms.Padding(6, 0, 6, 0);
+ this.label3.Name = "label3";
+ this.label3.Size = new System.Drawing.Size(427, 46);
+ this.label3.TabIndex = 5;
+ this.label3.Text = "Password";
+ this.label3.TextAlign = System.Drawing.ContentAlignment.MiddleLeft;
+ //
+ // tbPassword
+ //
+ this.tbPassword.Dock = System.Windows.Forms.DockStyle.Fill;
+ this.tbPassword.Location = new System.Drawing.Point(445, 131);
+ this.tbPassword.Margin = new System.Windows.Forms.Padding(6, 7, 6, 7);
+ this.tbPassword.Name = "tbPassword";
+ this.tbPassword.Size = new System.Drawing.Size(921, 35);
+ this.tbPassword.TabIndex = 4;
+ this.tbPassword.UseSystemPasswordChar = true;
+ //
+ // btnOK
+ //
+ this.btnOK.Anchor = System.Windows.Forms.AnchorStyles.Right;
+ this.btnOK.DialogResult = System.Windows.Forms.DialogResult.OK;
+ this.btnOK.Location = new System.Drawing.Point(510, 23);
+ this.btnOK.Margin = new System.Windows.Forms.Padding(6, 7, 6, 7);
+ this.btnOK.Name = "btnOK";
+ this.btnOK.Size = new System.Drawing.Size(150, 53);
+ this.btnOK.TabIndex = 10;
+ this.btnOK.Text = "OK";
+ this.btnOK.UseVisualStyleBackColor = true;
+ //
+ // btnCancel
+ //
+ this.btnCancel.Anchor = System.Windows.Forms.AnchorStyles.Left;
+ this.btnCancel.DialogResult = System.Windows.Forms.DialogResult.Cancel;
+ this.btnCancel.Location = new System.Drawing.Point(712, 23);
+ this.btnCancel.Margin = new System.Windows.Forms.Padding(6, 7, 6, 7);
+ this.btnCancel.Name = "btnCancel";
+ this.btnCancel.Size = new System.Drawing.Size(150, 53);
+ this.btnCancel.TabIndex = 11;
+ this.btnCancel.Text = "Cancel";
+ this.btnCancel.UseVisualStyleBackColor = true;
+ //
+ // tableLayoutPanel1
+ //
+ this.tableLayoutPanel1.ColumnCount = 2;
+ this.tableLayoutPanel1.ColumnStyles.Add(new System.Windows.Forms.ColumnStyle(System.Windows.Forms.SizeType.Percent, 32.06997F));
+ this.tableLayoutPanel1.ColumnStyles.Add(new System.Windows.Forms.ColumnStyle(System.Windows.Forms.SizeType.Percent, 67.93003F));
+ this.tableLayoutPanel1.Controls.Add(this.label5, 0, 3);
+ this.tableLayoutPanel1.Controls.Add(this.label1, 0, 0);
+ this.tableLayoutPanel1.Controls.Add(this.label2, 0, 1);
+ this.tableLayoutPanel1.Controls.Add(this.label3, 0, 2);
+ this.tableLayoutPanel1.Controls.Add(this.tbSSURL, 1, 0);
+ this.tableLayoutPanel1.Controls.Add(this.tbUsername, 1, 1);
+ this.tableLayoutPanel1.Controls.Add(this.tbPassword, 1, 2);
+ this.tableLayoutPanel1.Controls.Add(this.cbUseSSO, 0, 3);
+ this.tableLayoutPanel1.Dock = System.Windows.Forms.DockStyle.Top;
+ this.tableLayoutPanel1.Location = new System.Drawing.Point(0, 0);
+ this.tableLayoutPanel1.Margin = new System.Windows.Forms.Padding(6, 7, 6, 7);
+ this.tableLayoutPanel1.Name = "tableLayoutPanel1";
+ this.tableLayoutPanel1.RowCount = 4;
+ this.tableLayoutPanel1.RowStyles.Add(new System.Windows.Forms.RowStyle(System.Windows.Forms.SizeType.Percent, 50F));
+ this.tableLayoutPanel1.RowStyles.Add(new System.Windows.Forms.RowStyle(System.Windows.Forms.SizeType.Percent, 50F));
+ this.tableLayoutPanel1.RowStyles.Add(new System.Windows.Forms.RowStyle(System.Windows.Forms.SizeType.Absolute, 46F));
+ this.tableLayoutPanel1.RowStyles.Add(new System.Windows.Forms.RowStyle(System.Windows.Forms.SizeType.Absolute, 46F));
+ this.tableLayoutPanel1.RowStyles.Add(new System.Windows.Forms.RowStyle(System.Windows.Forms.SizeType.Absolute, 46F));
+ this.tableLayoutPanel1.RowStyles.Add(new System.Windows.Forms.RowStyle(System.Windows.Forms.SizeType.Absolute, 46F));
+ this.tableLayoutPanel1.RowStyles.Add(new System.Windows.Forms.RowStyle(System.Windows.Forms.SizeType.Absolute, 46F));
+ this.tableLayoutPanel1.Size = new System.Drawing.Size(1372, 217);
+ this.tableLayoutPanel1.TabIndex = 12;
+ //
+ // label5
+ //
+ this.label5.AutoSize = true;
+ this.label5.Dock = System.Windows.Forms.DockStyle.Fill;
+ this.label5.Location = new System.Drawing.Point(445, 170);
+ this.label5.Margin = new System.Windows.Forms.Padding(6, 0, 6, 0);
+ this.label5.Name = "label5";
+ this.label5.Size = new System.Drawing.Size(921, 47);
+ this.label5.TabIndex = 15;
+ this.label5.Text = "For SSO to work, additional IIS configuration is required!";
+ this.label5.TextAlign = System.Drawing.ContentAlignment.MiddleLeft;
+ //
+ // label1
+ //
+ this.label1.AutoSize = true;
+ this.label1.Dock = System.Windows.Forms.DockStyle.Fill;
+ this.label1.Location = new System.Drawing.Point(6, 0);
+ this.label1.Margin = new System.Windows.Forms.Padding(6, 0, 6, 0);
+ this.label1.Name = "label1";
+ this.label1.Size = new System.Drawing.Size(427, 62);
+ this.label1.TabIndex = 2;
+ this.label1.Text = "Secret Server URL";
+ this.label1.TextAlign = System.Drawing.ContentAlignment.MiddleLeft;
+ //
+ // label2
+ //
+ this.label2.AutoSize = true;
+ this.label2.Dock = System.Windows.Forms.DockStyle.Fill;
+ this.label2.Location = new System.Drawing.Point(6, 62);
+ this.label2.Margin = new System.Windows.Forms.Padding(6, 0, 6, 0);
+ this.label2.Name = "label2";
+ this.label2.Size = new System.Drawing.Size(427, 62);
+ this.label2.TabIndex = 4;
+ this.label2.Text = "DOMAIN\\Username";
+ this.label2.TextAlign = System.Drawing.ContentAlignment.MiddleLeft;
+ //
+ // cbUseSSO
+ //
+ this.cbUseSSO.AutoSize = true;
+ this.cbUseSSO.Location = new System.Drawing.Point(6, 177);
+ this.cbUseSSO.Margin = new System.Windows.Forms.Padding(6, 7, 6, 0);
+ this.cbUseSSO.Name = "cbUseSSO";
+ this.cbUseSSO.Size = new System.Drawing.Size(117, 34);
+ this.cbUseSSO.TabIndex = 14;
+ this.cbUseSSO.Text = "Use SSO";
+ this.cbUseSSO.UseVisualStyleBackColor = true;
+ this.cbUseSSO.CheckedChanged += new System.EventHandler(this.cbUseSSO_CheckedChanged);
+ //
+ // tableLayoutPanel2
+ //
+ this.tableLayoutPanel2.ColumnCount = 5;
+ this.tableLayoutPanel2.ColumnStyles.Add(new System.Windows.Forms.ColumnStyle(System.Windows.Forms.SizeType.Absolute, 160F));
+ this.tableLayoutPanel2.ColumnStyles.Add(new System.Windows.Forms.ColumnStyle(System.Windows.Forms.SizeType.Percent, 50F));
+ this.tableLayoutPanel2.ColumnStyles.Add(new System.Windows.Forms.ColumnStyle(System.Windows.Forms.SizeType.Absolute, 40F));
+ this.tableLayoutPanel2.ColumnStyles.Add(new System.Windows.Forms.ColumnStyle(System.Windows.Forms.SizeType.Percent, 50F));
+ this.tableLayoutPanel2.ColumnStyles.Add(new System.Windows.Forms.ColumnStyle(System.Windows.Forms.SizeType.Absolute, 160F));
+ this.tableLayoutPanel2.Controls.Add(this.btnOK, 1, 0);
+ this.tableLayoutPanel2.Controls.Add(this.btnCancel, 3, 0);
+ this.tableLayoutPanel2.Dock = System.Windows.Forms.DockStyle.Bottom;
+ this.tableLayoutPanel2.Location = new System.Drawing.Point(0, 298);
+ this.tableLayoutPanel2.Margin = new System.Windows.Forms.Padding(6, 7, 6, 7);
+ this.tableLayoutPanel2.Name = "tableLayoutPanel2";
+ this.tableLayoutPanel2.RowCount = 1;
+ this.tableLayoutPanel2.RowStyles.Add(new System.Windows.Forms.RowStyle(System.Windows.Forms.SizeType.Percent, 100F));
+ this.tableLayoutPanel2.Size = new System.Drawing.Size(1372, 99);
+ this.tableLayoutPanel2.TabIndex = 13;
+ //
+ // label4
+ //
+ this.label4.AutoSize = true;
+ this.label4.Dock = System.Windows.Forms.DockStyle.Fill;
+ this.label4.Location = new System.Drawing.Point(0, 217);
+ this.label4.Margin = new System.Windows.Forms.Padding(6, 0, 6, 0);
+ this.label4.Name = "label4";
+ this.label4.Size = new System.Drawing.Size(599, 30);
+ this.label4.TabIndex = 14;
+ this.label4.Text = "URL is the base URL, like https://cred.domain.local/SecretServer";
+ this.label4.TextAlign = System.Drawing.ContentAlignment.MiddleLeft;
+ //
+ // SSConnectionForm
+ //
+ this.AcceptButton = this.btnOK;
+ this.AutoScaleDimensions = new System.Drawing.SizeF(12F, 30F);
+ this.AutoScaleMode = System.Windows.Forms.AutoScaleMode.Font;
+ this.ClientSize = new System.Drawing.Size(1372, 397);
+ this.Controls.Add(this.label4);
+ this.Controls.Add(this.tableLayoutPanel2);
+ this.Controls.Add(this.tableLayoutPanel1);
+ this.Margin = new System.Windows.Forms.Padding(6, 7, 6, 7);
+ this.Name = "SSConnectionForm";
+ this.Text = "Secret Server API Login Data";
+ this.Activated += new System.EventHandler(this.SSConnectionForm_Activated);
+ this.tableLayoutPanel1.ResumeLayout(false);
+ this.tableLayoutPanel1.PerformLayout();
+ this.tableLayoutPanel2.ResumeLayout(false);
+ this.ResumeLayout(false);
+ this.PerformLayout();
+
+ }
+
+ #endregion
+ private System.Windows.Forms.Label label3;
+
+ public System.Windows.Forms.TextBox tbSSURL;
+ public System.Windows.Forms.TextBox tbUsername;
+ public System.Windows.Forms.TextBox tbPassword;
+ private System.Windows.Forms.Button btnOK;
+ private System.Windows.Forms.Button btnCancel;
+ private System.Windows.Forms.TableLayoutPanel tableLayoutPanel1;
+ private System.Windows.Forms.Label label2;
+ private System.Windows.Forms.Label label1;
+ private System.Windows.Forms.TableLayoutPanel tableLayoutPanel2;
+ public System.Windows.Forms.CheckBox cbUseSSO;
+ private System.Windows.Forms.Label label4;
+ private Label label5;
+ }
+}
\ No newline at end of file
diff --git a/ExternalConnectors/TSS/SSConnectionForm.cs b/ExternalConnectors/TSS/SSConnectionForm.cs
new file mode 100644
index 00000000..be3a5a3e
--- /dev/null
+++ b/ExternalConnectors/TSS/SSConnectionForm.cs
@@ -0,0 +1,30 @@
+namespace ExternalConnectors.TSS
+{
+ public partial class SSConnectionForm : Form
+ {
+ public SSConnectionForm()
+ {
+ InitializeComponent();
+ }
+
+ private void SSConnectionForm_Activated(object sender, EventArgs e)
+ {
+ SetVisibility();
+ if (cbUseSSO.Checked)
+ btnOK.Focus();
+ else
+ tbPassword.Focus();
+ }
+
+ private void cbUseSSO_CheckedChanged(object sender, EventArgs e)
+ {
+ SetVisibility();
+ }
+ private void SetVisibility()
+ {
+ bool ch = cbUseSSO.Checked;
+ tbPassword.Enabled = !ch;
+ tbUsername.Enabled = !ch;
+ }
+ }
+}
diff --git a/ExternalConnectors/TSS/SSConnectionForm.resx b/ExternalConnectors/TSS/SSConnectionForm.resx
new file mode 100644
index 00000000..f298a7be
--- /dev/null
+++ b/ExternalConnectors/TSS/SSConnectionForm.resx
@@ -0,0 +1,60 @@
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+ text/microsoft-resx
+
+
+ 2.0
+
+
+ System.Resources.ResXResourceReader, System.Windows.Forms, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089
+
+
+ System.Resources.ResXResourceWriter, System.Windows.Forms, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089
+
+
\ No newline at end of file
diff --git a/ExternalConnectors/TSS/SecretServerAuthentication.cs b/ExternalConnectors/TSS/SecretServerAuthentication.cs
new file mode 100644
index 00000000..cad1844b
--- /dev/null
+++ b/ExternalConnectors/TSS/SecretServerAuthentication.cs
@@ -0,0 +1,364 @@
+//----------------------
+//
+// Generated using the NSwag toolchain v13.14.8.0 (NJsonSchema v10.5.2.0 (Newtonsoft.Json v11.0.0.0)) (http://NSwag.org)
+//
+//----------------------
+
+#pragma warning disable 108 // Disable "CS0108 '{derivedDto}.ToJson()' hides inherited member '{dtoBase}.ToJson()'. Use the new keyword if hiding was intended."
+#pragma warning disable 114 // Disable "CS0114 '{derivedDto}.RaisePropertyChanged(String)' hides inherited member 'dtoBase.RaisePropertyChanged(String)'. To make the current member override that implementation, add the override keyword. Otherwise add the new keyword."
+#pragma warning disable 472 // Disable "CS0472 The result of the expression is always 'false' since a value of type 'Int32' is never equal to 'null' of type 'Int32?'
+#pragma warning disable 1573 // Disable "CS1573 Parameter '...' has no matching param tag in the XML comment for ...
+#pragma warning disable 1591 // Disable "CS1591 Missing XML comment for publicly visible type or member ..."
+#pragma warning disable 8073 // Disable "CS8073 The result of the expression is always 'false' since a value of type 'T' is never equal to 'null' of type 'T?'"
+#pragma warning disable 3016 // Disable "CS3016 Arrays as attribute arguments is not CLS-compliant"
+
+namespace SecretServerAuthentication.TSS
+{
+ using System = global::System;
+
+ [System.CodeDom.Compiler.GeneratedCode("NSwag", "13.14.8.0 (NJsonSchema v10.5.2.0 (Newtonsoft.Json v11.0.0.0))")]
+ public partial class OAuth2ServiceClient
+ {
+ private string _baseUrl = "";
+ private System.Net.Http.HttpClient _httpClient;
+ private System.Lazy _settings;
+
+ public OAuth2ServiceClient(string baseUrl, System.Net.Http.HttpClient httpClient)
+ {
+ BaseUrl = baseUrl;
+ _httpClient = httpClient;
+ _settings = new System.Lazy(CreateSerializerSettings);
+ }
+
+ private Newtonsoft.Json.JsonSerializerSettings CreateSerializerSettings()
+ {
+ var settings = new Newtonsoft.Json.JsonSerializerSettings();
+ UpdateJsonSerializerSettings(settings);
+ return settings;
+ }
+
+ public string BaseUrl
+ {
+ get { return _baseUrl; }
+ set { _baseUrl = value; }
+ }
+
+ protected Newtonsoft.Json.JsonSerializerSettings JsonSerializerSettings { get { return _settings.Value; } }
+
+ partial void UpdateJsonSerializerSettings(Newtonsoft.Json.JsonSerializerSettings settings);
+
+
+ partial void PrepareRequest(System.Net.Http.HttpClient client, System.Net.Http.HttpRequestMessage request, string url);
+ partial void PrepareRequest(System.Net.Http.HttpClient client, System.Net.Http.HttpRequestMessage request, System.Text.StringBuilder urlBuilder);
+ partial void ProcessResponse(System.Net.Http.HttpClient client, System.Net.Http.HttpResponseMessage response);
+ /// Retrieve or Refresh Access Token
+ /// Authentication grant type. Use 'password' when authenticating, and 'refresh_token' when refreshing a token.
+ /// Secret Server authentication username. Required when authenticating.
+ /// Secret Server authentication password. Required when authenticating.
+ /// The refresh token. Required when refreshing a token.
+ /// Successful retrieval of an access token
+ /// A server side error occurred.
+ public System.Threading.Tasks.Task AuthorizeAsync(Grant_type grant_type, string username, string password, string refresh_token)
+ {
+ return AuthorizeAsync(grant_type, username, password, refresh_token, System.Threading.CancellationToken.None);
+ }
+
+ /// A cancellation token that can be used by other objects or threads to receive notice of cancellation.
+ /// Retrieve or Refresh Access Token
+ /// Authentication grant type. Use 'password' when authenticating, and 'refresh_token' when refreshing a token.
+ /// Secret Server authentication username. Required when authenticating.
+ /// Secret Server authentication password. Required when authenticating.
+ /// The refresh token. Required when refreshing a token.
+ /// Successful retrieval of an access token
+ /// A server side error occurred.
+ public async System.Threading.Tasks.Task AuthorizeAsync(Grant_type grant_type, string username, string password, string refresh_token, System.Threading.CancellationToken cancellationToken)
+ {
+ var urlBuilder_ = new System.Text.StringBuilder();
+ urlBuilder_.Append(BaseUrl != null ? BaseUrl.TrimEnd('/') : "").Append("/oauth2/token");
+
+ var client_ = _httpClient;
+ var disposeClient_ = false;
+ try
+ {
+ using (var request_ = new System.Net.Http.HttpRequestMessage())
+ {
+ var keyValues_ = new System.Collections.Generic.List>();
+ if (grant_type == null)
+ throw new System.ArgumentNullException("grant_type");
+ else
+ keyValues_.Add(new System.Collections.Generic.KeyValuePair("grant_type", ConvertToString(grant_type, System.Globalization.CultureInfo.InvariantCulture)));
+ if (username != null)
+ keyValues_.Add(new System.Collections.Generic.KeyValuePair("username", ConvertToString(username, System.Globalization.CultureInfo.InvariantCulture)));
+ if (password != null)
+ keyValues_.Add(new System.Collections.Generic.KeyValuePair("password", ConvertToString(password, System.Globalization.CultureInfo.InvariantCulture)));
+ if (refresh_token != null)
+ keyValues_.Add(new System.Collections.Generic.KeyValuePair("refresh_token", ConvertToString(refresh_token, System.Globalization.CultureInfo.InvariantCulture)));
+ request_.Content = new System.Net.Http.FormUrlEncodedContent(keyValues_);
+ request_.Method = new System.Net.Http.HttpMethod("POST");
+ request_.Headers.Accept.Add(System.Net.Http.Headers.MediaTypeWithQualityHeaderValue.Parse("application/json"));
+
+ PrepareRequest(client_, request_, urlBuilder_);
+
+ var url_ = urlBuilder_.ToString();
+ request_.RequestUri = new System.Uri(url_, System.UriKind.RelativeOrAbsolute);
+
+ PrepareRequest(client_, request_, url_);
+
+ var response_ = await client_.SendAsync(request_, System.Net.Http.HttpCompletionOption.ResponseHeadersRead, cancellationToken).ConfigureAwait(false);
+ var disposeResponse_ = true;
+ try
+ {
+ var headers_ = System.Linq.Enumerable.ToDictionary(response_.Headers, h_ => h_.Key, h_ => h_.Value);
+ if (response_.Content != null && response_.Content.Headers != null)
+ {
+ foreach (var item_ in response_.Content.Headers)
+ headers_[item_.Key] = item_.Value;
+ }
+
+ ProcessResponse(client_, response_);
+
+ var status_ = (int)response_.StatusCode;
+ if (status_ == 200)
+ {
+ var objectResponse_ = await ReadObjectResponseAsync(response_, headers_, cancellationToken).ConfigureAwait(false);
+ if (objectResponse_.Object == null)
+ {
+ throw new ApiException("Response was null which was not expected.", status_, objectResponse_.Text, headers_, null);
+ }
+ return objectResponse_.Object;
+ }
+ else
+ if (status_ == 400)
+ {
+ var objectResponse_ = await ReadObjectResponseAsync(response_, headers_, cancellationToken).ConfigureAwait(false);
+ if (objectResponse_.Object == null)
+ {
+ throw new ApiException("Response was null which was not expected.", status_, objectResponse_.Text, headers_, null);
+ }
+ throw new ApiException("An error occurred", status_, objectResponse_.Text, headers_, objectResponse_.Object, null);
+ }
+ else
+ {
+ var responseData_ = response_.Content == null ? null : await response_.Content.ReadAsStringAsync().ConfigureAwait(false);
+ throw new ApiException("The HTTP status code of the response was not expected (" + status_ + ").", status_, responseData_, headers_, null);
+ }
+ }
+ finally
+ {
+ if (disposeResponse_)
+ response_.Dispose();
+ }
+ }
+ }
+ finally
+ {
+ if (disposeClient_)
+ client_.Dispose();
+ }
+ }
+
+ protected struct ObjectResponseResult
+ {
+ public ObjectResponseResult(T responseObject, string responseText)
+ {
+ this.Object = responseObject;
+ this.Text = responseText;
+ }
+
+ public T Object { get; }
+
+ public string Text { get; }
+ }
+
+ public bool ReadResponseAsString { get; set; }
+
+ protected virtual async System.Threading.Tasks.Task> ReadObjectResponseAsync(System.Net.Http.HttpResponseMessage response, System.Collections.Generic.IReadOnlyDictionary> headers, System.Threading.CancellationToken cancellationToken)
+ {
+ if (response == null || response.Content == null)
+ {
+ return new ObjectResponseResult(default(T), string.Empty);
+ }
+
+ if (ReadResponseAsString)
+ {
+ var responseText = await response.Content.ReadAsStringAsync().ConfigureAwait(false);
+ try
+ {
+ var typedBody = Newtonsoft.Json.JsonConvert.DeserializeObject(responseText, JsonSerializerSettings);
+ return new ObjectResponseResult(typedBody, responseText);
+ }
+ catch (Newtonsoft.Json.JsonException exception)
+ {
+ var message = "Could not deserialize the response body string as " + typeof(T).FullName + ".";
+ throw new ApiException(message, (int)response.StatusCode, responseText, headers, exception);
+ }
+ }
+ else
+ {
+ try
+ {
+ using (var responseStream = await response.Content.ReadAsStreamAsync().ConfigureAwait(false))
+ using (var streamReader = new System.IO.StreamReader(responseStream))
+ using (var jsonTextReader = new Newtonsoft.Json.JsonTextReader(streamReader))
+ {
+ var serializer = Newtonsoft.Json.JsonSerializer.Create(JsonSerializerSettings);
+ var typedBody = serializer.Deserialize(jsonTextReader);
+ return new ObjectResponseResult(typedBody, string.Empty);
+ }
+ }
+ catch (Newtonsoft.Json.JsonException exception)
+ {
+ var message = "Could not deserialize the response body stream as " + typeof(T).FullName + ".";
+ throw new ApiException(message, (int)response.StatusCode, string.Empty, headers, exception);
+ }
+ }
+ }
+
+ private string ConvertToString(object value, System.Globalization.CultureInfo cultureInfo)
+ {
+ if (value == null)
+ {
+ return "";
+ }
+
+ if (value is System.Enum)
+ {
+ var name = System.Enum.GetName(value.GetType(), value);
+ if (name != null)
+ {
+ var field = System.Reflection.IntrospectionExtensions.GetTypeInfo(value.GetType()).GetDeclaredField(name);
+ if (field != null)
+ {
+ var attribute = System.Reflection.CustomAttributeExtensions.GetCustomAttribute(field, typeof(System.Runtime.Serialization.EnumMemberAttribute))
+ as System.Runtime.Serialization.EnumMemberAttribute;
+ if (attribute != null)
+ {
+ return attribute.Value != null ? attribute.Value : name;
+ }
+ }
+
+ var converted = System.Convert.ToString(System.Convert.ChangeType(value, System.Enum.GetUnderlyingType(value.GetType()), cultureInfo));
+ return converted == null ? string.Empty : converted;
+ }
+ }
+ else if (value is bool)
+ {
+ return System.Convert.ToString((bool)value, cultureInfo).ToLowerInvariant();
+ }
+ else if (value is byte[])
+ {
+ return System.Convert.ToBase64String((byte[])value);
+ }
+ else if (value.GetType().IsArray)
+ {
+ var array = System.Linq.Enumerable.OfType