Skip to content

Commit 7aa2268

Browse files
Merge pull request #418 from konstantingross/master
Shell API adapted to Electron 9.0.0
2 parents fabd25a + b08222b commit 7aa2268

File tree

10 files changed

+106
-161
lines changed

10 files changed

+106
-161
lines changed

ElectronNET.API/Entities/Error.cs

Lines changed: 0 additions & 16 deletions
This file was deleted.
Lines changed: 9 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -1,16 +1,22 @@
1-
using System.ComponentModel;
1+
using System;
2+
using System.ComponentModel;
23

34
namespace ElectronNET.API.Entities
45
{
56
/// <summary>
6-
///
7+
/// Controls the behavior of OpenExternal.
78
/// </summary>
89
public class OpenExternalOptions
910
{
1011
/// <summary>
11-
/// true to bring the opened application to the foreground. The default is true.
12+
/// <see langword="true"/> to bring the opened application to the foreground. The default is <see langword="true"/>.
1213
/// </summary>
1314
[DefaultValue(true)]
1415
public bool Activate { get; set; } = true;
16+
17+
/// <summary>
18+
/// The working directory.
19+
/// </summary>
20+
public string WorkingDirectory { get; set; }
1521
}
1622
}

ElectronNET.API/Entities/ShortcutDetails.cs

Lines changed: 9 additions & 9 deletions
Original file line numberDiff line numberDiff line change
@@ -1,38 +1,38 @@
1-
namespace ElectronNET.API
1+
namespace ElectronNET.API.Entities
22
{
33
/// <summary>
4-
///
4+
/// Structure of a shortcut.
55
/// </summary>
66
public class ShortcutDetails
77
{
88
/// <summary>
9-
/// The Application User Model ID. Default is empty.
9+
/// The Application User Model ID. Default is <see cref="string.Empty"/>.
1010
/// </summary>
1111
public string AppUserModelId { get; set; }
1212

1313
/// <summary>
14-
/// The arguments to be applied to target when launching from this shortcut. Default is empty.
14+
/// The arguments to be applied to <see cref="Target"/> when launching from this shortcut. Default is <see cref="string.Empty"/>.
1515
/// </summary>
1616
public string Args { get; set; }
1717

1818
/// <summary>
19-
/// The working directory. Default is empty.
19+
/// The working directory. Default is <see cref="string.Empty"/>.
2020
/// </summary>
2121
public string Cwd { get; set; }
2222

2323
/// <summary>
24-
/// The description of the shortcut. Default is empty.
24+
/// The description of the shortcut. Default is <see cref="string.Empty"/>.
2525
/// </summary>
2626
public string Description { get; set; }
2727

2828
/// <summary>
29-
/// The path to the icon, can be a DLL or EXE. icon and iconIndex have to be set
30-
/// together.Default is empty, which uses the target's icon.
29+
/// The path to the icon, can be a DLL or EXE. <see cref="Icon"/> and <see cref="IconIndex"/> have to be set
30+
/// together. Default is <see cref="string.Empty"/>, which uses the target's icon.
3131
/// </summary>
3232
public string Icon { get; set; }
3333

3434
/// <summary>
35-
/// The resource ID of icon when icon is a DLL or EXE. Default is 0.
35+
/// The resource ID of icon when <see cref="Icon"/> is a DLL or EXE. Default is 0.
3636
/// </summary>
3737
public int IconIndex { get; set; }
3838

Lines changed: 12 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -1,23 +1,28 @@
1-
namespace ElectronNET.API
1+
using System.ComponentModel;
2+
3+
namespace ElectronNET.API.Entities
24
{
35
/// <summary>
4-
///
6+
/// Defines the ShortcutLinkOperation enumeration.
57
/// </summary>
68
public enum ShortcutLinkOperation
79
{
810
/// <summary>
911
/// Creates a new shortcut, overwriting if necessary.
1012
/// </summary>
11-
create,
13+
[Description("create")]
14+
Create,
1215

1316
/// <summary>
1417
/// Updates specified properties only on an existing shortcut.
1518
/// </summary>
16-
update,
19+
[Description("update")]
20+
Update,
1721

1822
/// <summary>
19-
/// Overwrites an existing shortcut, fails if the shortcut doesnt exist.
23+
/// Overwrites an existing shortcut, fails if the shortcut doesn't exist.
2024
/// </summary>
21-
replace
25+
[Description("replace")]
26+
Replace
2227
}
23-
}
28+
}

ElectronNET.API/Shell.cs

Lines changed: 45 additions & 92 deletions
Original file line numberDiff line numberDiff line change
@@ -2,9 +2,8 @@
22
using Newtonsoft.Json;
33
using Newtonsoft.Json.Linq;
44
using Newtonsoft.Json.Serialization;
5-
using System;
6-
using System.Collections.Generic;
75
using System.Threading.Tasks;
6+
using ElectronNET.API.Extensions;
87

98
namespace ElectronNET.API
109
{
@@ -40,17 +39,14 @@ internal static Shell Instance
4039
/// <summary>
4140
/// Show the given file in a file manager. If possible, select the file.
4241
/// </summary>
43-
/// <param name="fullPath"></param>
44-
/// <returns>Whether the item was successfully shown.</returns>
45-
public Task<bool> ShowItemInFolderAsync(string fullPath)
42+
/// <param name="fullPath">The full path to the directory / file.</param>
43+
public Task ShowItemInFolderAsync(string fullPath)
4644
{
47-
var taskCompletionSource = new TaskCompletionSource<bool>();
45+
var taskCompletionSource = new TaskCompletionSource<object>();
4846

49-
BridgeConnector.Socket.On("shell-showItemInFolderCompleted", (success) =>
47+
BridgeConnector.Socket.On("shell-showItemInFolderCompleted", () =>
5048
{
5149
BridgeConnector.Socket.Off("shell-showItemInFolderCompleted");
52-
53-
taskCompletionSource.SetResult((bool)success);
5450
});
5551

5652
BridgeConnector.Socket.Emit("shell-showItemInFolder", fullPath);
@@ -61,17 +57,17 @@ public Task<bool> ShowItemInFolderAsync(string fullPath)
6157
/// <summary>
6258
/// Open the given file in the desktop's default manner.
6359
/// </summary>
64-
/// <param name="path">The path to the file.</param>
60+
/// <param name="path">The path to the directory / file.</param>
6561
/// <returns>The error message corresponding to the failure if a failure occurred, otherwise <see cref="string.Empty"/>.</returns>
6662
public Task<string> OpenPathAsync(string path)
6763
{
6864
var taskCompletionSource = new TaskCompletionSource<string>();
6965

70-
BridgeConnector.Socket.On("shell-openPathCompleted", (success) =>
66+
BridgeConnector.Socket.On("shell-openPathCompleted", (errorMessage) =>
7167
{
7268
BridgeConnector.Socket.Off("shell-openPathCompleted");
7369

74-
taskCompletionSource.SetResult((string) success);
70+
taskCompletionSource.SetResult((string) errorMessage);
7571
});
7672

7773
BridgeConnector.Socket.Emit("shell-openPath", path);
@@ -83,106 +79,61 @@ public Task<string> OpenPathAsync(string path)
8379
/// Open the given external protocol URL in the desktop’s default manner.
8480
/// (For example, mailto: URLs in the user’s default mail agent).
8581
/// </summary>
86-
/// <param name="url"></param>
87-
/// <returns>Whether an application was available to open the URL.
88-
/// If callback is specified, always returns true.</returns>
89-
public Task<bool> OpenExternalAsync(string url)
82+
/// <param name="url">Max 2081 characters on windows.</param>
83+
/// <returns>The error message corresponding to the failure if a failure occurred, otherwise <see cref="string.Empty"/>.</returns>
84+
public Task<string> OpenExternalAsync(string url)
9085
{
91-
var taskCompletionSource = new TaskCompletionSource<bool>();
92-
93-
BridgeConnector.Socket.On("shell-openExternalCompleted", (success) =>
94-
{
95-
BridgeConnector.Socket.Off("shell-openExternalCompleted");
96-
97-
taskCompletionSource.SetResult((bool)success);
98-
});
99-
100-
BridgeConnector.Socket.Emit("shell-openExternal", url);
101-
102-
return taskCompletionSource.Task;
86+
return OpenExternalAsync(url, null);
10387
}
10488

10589
/// <summary>
10690
/// Open the given external protocol URL in the desktop’s default manner.
10791
/// (For example, mailto: URLs in the user’s default mail agent).
10892
/// </summary>
109-
/// <param name="url"></param>
110-
/// <param name="options">macOS only</param>
111-
/// <returns>Whether an application was available to open the URL.
112-
/// If callback is specified, always returns true.</returns>
113-
public Task<bool> OpenExternalAsync(string url, OpenExternalOptions options)
93+
/// <param name="url">Max 2081 characters on windows.</param>
94+
/// <param name="options">Controls the behavior of OpenExternal.</param>
95+
/// <returns>The error message corresponding to the failure if a failure occurred, otherwise <see cref="string.Empty"/>.</returns>
96+
public Task<string> OpenExternalAsync(string url, OpenExternalOptions options)
11497
{
115-
var taskCompletionSource = new TaskCompletionSource<bool>();
98+
var taskCompletionSource = new TaskCompletionSource<string>();
11699

117-
BridgeConnector.Socket.On("shell-openExternalCompleted", (success) =>
100+
BridgeConnector.Socket.On("shell-openExternalCompleted", (error) =>
118101
{
119102
BridgeConnector.Socket.Off("shell-openExternalCompleted");
120103

121-
taskCompletionSource.SetResult((bool)success);
104+
taskCompletionSource.SetResult((string) error);
122105
});
123106

124-
BridgeConnector.Socket.Emit("shell-openExternal", url, JObject.FromObject(options, _jsonSerializer));
125-
126-
return taskCompletionSource.Task;
127-
}
128-
129-
/// <summary>
130-
/// Open the given external protocol URL in the desktop’s default manner.
131-
/// (For example, mailto: URLs in the user’s default mail agent).
132-
/// </summary>
133-
/// <param name="url"></param>
134-
/// <param name="options">macOS only</param>
135-
/// <param name="errorAction">Action to get the error message.</param>
136-
/// <returns>Whether an application was available to open the URL.
137-
/// If callback is specified, always returns true.</returns>
138-
public Task<bool> OpenExternalAsync(string url, OpenExternalOptions options, Action<Error> errorAction)
139-
{
140-
var taskCompletionSource = new TaskCompletionSource<bool>();
141-
142-
BridgeConnector.Socket.On("shell-openExternalCompleted", (success) =>
107+
if (options == null)
143108
{
144-
BridgeConnector.Socket.Off("shell-openExternalCompleted");
145-
146-
taskCompletionSource.SetResult((bool)success);
147-
});
148-
149-
BridgeConnector.Socket.Off("shell-openExternalCallback");
150-
BridgeConnector.Socket.On("shell-openExternalCallback", (args) => {
151-
var urlKey = ((JArray)args).First.ToString();
152-
var error = ((JArray)args).Last.ToObject<Error>();
153-
154-
if(_openExternalCallbacks.ContainsKey(urlKey))
155-
{
156-
_openExternalCallbacks[urlKey](error);
157-
}
158-
});
159-
160-
_openExternalCallbacks.Add(url, errorAction);
161-
162-
BridgeConnector.Socket.Emit("shell-openExternal", url, JObject.FromObject(options, _jsonSerializer), true);
109+
BridgeConnector.Socket.Emit("shell-openExternal", url);
110+
}
111+
else
112+
{
113+
BridgeConnector.Socket.Emit("shell-openExternal", url, JObject.FromObject(options, _jsonSerializer));
114+
}
163115

164116
return taskCompletionSource.Task;
165117
}
166118

167-
private Dictionary<string, Action<Error>> _openExternalCallbacks = new Dictionary<string, Action<Error>>();
168-
169119
/// <summary>
170-
/// Move the given file to trash and returns a boolean status for the operation.
120+
/// Move the given file to trash and returns a <see cref="bool"/> status for the operation.
171121
/// </summary>
172-
/// <param name="fullPath"></param>
122+
/// <param name="fullPath">The full path to the directory / file.</param>
123+
/// <param name="deleteOnFail">Whether or not to unilaterally remove the item if the Trash is disabled or unsupported on the volume.</param>
173124
/// <returns> Whether the item was successfully moved to the trash.</returns>
174-
public Task<bool> MoveItemToTrashAsync(string fullPath)
125+
public Task<bool> MoveItemToTrashAsync(string fullPath, bool deleteOnFail)
175126
{
176127
var taskCompletionSource = new TaskCompletionSource<bool>();
177128

178129
BridgeConnector.Socket.On("shell-moveItemToTrashCompleted", (success) =>
179130
{
180131
BridgeConnector.Socket.Off("shell-moveItemToTrashCompleted");
181132

182-
taskCompletionSource.SetResult((bool)success);
133+
taskCompletionSource.SetResult((bool) success);
183134
});
184135

185-
BridgeConnector.Socket.Emit("shell-moveItemToTrash", fullPath);
136+
BridgeConnector.Socket.Emit("shell-moveItemToTrash", fullPath, deleteOnFail);
186137

187138
return taskCompletionSource.Task;
188139
}
@@ -198,9 +149,9 @@ public void Beep()
198149
/// <summary>
199150
/// Creates or updates a shortcut link at shortcutPath.
200151
/// </summary>
201-
/// <param name="shortcutPath"></param>
202-
/// <param name="operation"></param>
203-
/// <param name="options"></param>
152+
/// <param name="shortcutPath">The path to the shortcut.</param>
153+
/// <param name="operation">Default is <see cref="ShortcutLinkOperation.Create"/></param>
154+
/// <param name="options">Structure of a shortcut.</param>
204155
/// <returns>Whether the shortcut was created successfully.</returns>
205156
public Task<bool> WriteShortcutLinkAsync(string shortcutPath, ShortcutLinkOperation operation, ShortcutDetails options)
206157
{
@@ -210,21 +161,20 @@ public Task<bool> WriteShortcutLinkAsync(string shortcutPath, ShortcutLinkOperat
210161
{
211162
BridgeConnector.Socket.Off("shell-writeShortcutLinkCompleted");
212163

213-
taskCompletionSource.SetResult((bool)success);
164+
taskCompletionSource.SetResult((bool) success);
214165
});
215166

216-
BridgeConnector.Socket.Emit("shell-writeShortcutLink", shortcutPath, operation.ToString(), JObject.FromObject(options, _jsonSerializer));
167+
BridgeConnector.Socket.Emit("shell-writeShortcutLink", shortcutPath, operation.GetDescription(), JObject.FromObject(options, _jsonSerializer));
217168

218169
return taskCompletionSource.Task;
219170
}
220171

221172
/// <summary>
222173
/// Resolves the shortcut link at shortcutPath.
223-
///
224174
/// An exception will be thrown when any error happens.
225175
/// </summary>
226-
/// <param name="shortcutPath"></param>
227-
/// <returns></returns>
176+
/// <param name="shortcutPath">The path tot the shortcut.</param>
177+
/// <returns><see cref="ShortcutDetails"/> of the shortcut.</returns>
228178
public Task<ShortcutDetails> ReadShortcutLinkAsync(string shortcutPath)
229179
{
230180
var taskCompletionSource = new TaskCompletionSource<ShortcutDetails>();
@@ -233,19 +183,22 @@ public Task<ShortcutDetails> ReadShortcutLinkAsync(string shortcutPath)
233183
{
234184
BridgeConnector.Socket.Off("shell-readShortcutLinkCompleted");
235185

236-
taskCompletionSource.SetResult((ShortcutDetails)shortcutDetails);
186+
var shortcutObject = shortcutDetails as JObject;
187+
var details = shortcutObject?.ToObject<ShortcutDetails>();
188+
189+
taskCompletionSource.SetResult(details);
237190
});
238191

239192
BridgeConnector.Socket.Emit("shell-readShortcutLink", shortcutPath);
240193

241194
return taskCompletionSource.Task;
242195
}
243196

244-
private JsonSerializer _jsonSerializer = new JsonSerializer()
197+
private readonly JsonSerializer _jsonSerializer = new JsonSerializer()
245198
{
246199
ContractResolver = new CamelCasePropertyNamesContractResolver(),
247200
NullValueHandling = NullValueHandling.Ignore,
248201
DefaultValueHandling = DefaultValueHandling.Ignore
249202
};
250203
}
251-
}
204+
}

0 commit comments

Comments
 (0)