-
Notifications
You must be signed in to change notification settings - Fork 0
/
Program.cs
314 lines (274 loc) · 10.7 KB
/
Program.cs
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
234
235
236
237
238
239
240
241
242
243
244
245
246
247
248
249
250
251
252
253
254
255
256
257
258
259
260
261
262
263
264
265
266
267
268
269
270
271
272
273
274
275
276
277
278
279
280
281
282
283
284
285
286
287
288
289
290
291
292
293
294
295
296
297
298
299
300
301
302
303
304
305
306
307
308
309
310
311
312
313
314
using System;
using System.Linq;
using PerrysNetConsole;
using System.IO;
using Microsoft.Extensions.Configuration;
using Microsoft.Extensions.Configuration.Json;
using Microsoft.Extensions.Configuration.Binder;
using NewJson = Newtonsoft.Json;
using CommandLine;
using System.Threading.Tasks;
using maliasmgr.Extensions;
using System.Text;
using System.Collections.Generic;
namespace maliasmgr
{
public class Program
{
// Available providers
private static Data.IProvider[] Providers = new Data.IProvider[] {
new Provider.AllInkl.AllInklProvider()
// add your providers here
};
public static int Main(string[] args)
{
// Console output settings
CoEx.ForcedBufferWidth = 100;
// Load settings
var config = LoadConfiguration();
if (string.IsNullOrWhiteSpace(config.Provider))
{
CoEx.WriteLine($"No provider configured in '{GetConfigPath()}'");
return 99;
}
// Load provider
var provider = CreateProvider(config);
if (provider == null)
{
CoEx.WriteLine("No valid provider was loaded.");
return 99;
}
// Parse arguments
int returnCode = 99;
Parser.Default.ParseArguments<Args>(args).WithParsed(o =>
{
if (o.Info)
{
// Show current info
returnCode = ShowInfo(config, o, provider);
}
if (!string.IsNullOrWhiteSpace(o.CreateName))
{
// Create a new alias
returnCode = CreateAlias(config, o, provider).WaitForValue<int>();
}
if (!string.IsNullOrWhiteSpace(o.DeleteAlias))
{
// Delete an existing alias
returnCode = DeleteAlias(config, o, provider).WaitForValue<int>();
}
else if (o.List)
{
// List existing aliases
returnCode = ListAliases(config, o, provider).WaitForValue<int>();
}
});
return returnCode;
}
/// <summary>
/// Helper for a yes/no prompt
/// </summary>
/// <param name="question">Question to ask</param>
/// <returns>true of yes was typed</returns>
private static bool YesNo(string question)
{
var prompt = new Prompt()
{
AllowEmpty = false,
Choices = new string[] { "y", "n" },
Default = "n",
Prefix = question,
ValidateChoices = true
};
return prompt.DoPrompt() == "y";
}
/// <summary>
/// Show current setup
/// </summary>
/// <param name="config">Config</param>
/// <param name="args">CMD Args</param>
/// <param name="provider">Provider</param>
/// <returns>Exit code</returns>
private static int ShowInfo(Data.MailiasConfig config, Args args, Data.IProvider provider)
{
CoEx.WriteLine($"Used Provider: {config.Provider}");
CoEx.WriteLine($"Mail Domain: {config.MailDomain}");
CoEx.WriteLine($"Alias Target: {config.TargetAddress}");
CoEx.WriteLine($"Prefix: {config.Prefix}");
CoEx.WriteLine($"Code Length: {config.UniqeIdLength}");
return 0;
}
/// <summary>
/// Create an alias
/// </summary>
/// <param name="config">Config</param>
/// <param name="args">CMD Args</param>
/// <param name="provider">Provider</param>
/// <returns>Exit code</returns>
private static async Task<int> CreateAlias(Data.MailiasConfig config, Args args, Data.IProvider provider)
{
// Create a new random id
var chars = "abcdefghijklmnopqrstuvwxyz0123456789";
var builder = new StringBuilder();
var random = new Random();
while(builder.Length < config.UniqeIdLength)
{
var index = random.Next(0, chars.Length - 1);
builder.Append(chars[index]);
}
// Build the email address
var prefix = string.IsNullOrWhiteSpace(config.Prefix) ? "" : config.Prefix + ".";
var key = builder.ToString();
var mailAddress = $"{prefix}{args.CreateName}.{key}@{config.MailDomain}";
// Check if the email address already exists
var exists = (await provider.GetAliases(config))
.FirstOrDefault(a => a.SourceAddress.StartsWith($"{prefix}{args.CreateName}."));
if (exists != null && args.Force == false)
{
if (!YesNo($"There is already an alias ({exists.SourceAddress}) with this name. Proceed?"))
{
return 1;
}
}
// Delete the existing alias
if (exists != null && args.DeleteExisting)
{
if (args.Force || YesNo($"Dou you want do delete the existing alias '{exists.SourceAddress}', before creating a new one?"))
{
var deleteExistingResult = await provider.DeleteAliasAddress(exists.SourceAddress);
if (deleteExistingResult != Data.DeleteResult.Success && !args.Silent)
{
CoEx.WriteLine("Deleting existing alias failed.");
return 1;
}
}
}
// Create the new alias
var result = await provider.CreateAlias(mailAddress, config.TargetAddress);
if (result == Data.CreateResult.Success || result == Data.CreateResult.AlreadyExists)
{
CoEx.WriteLine(mailAddress);
return 0;
}
else
{
if (!args.Silent)
{
CoEx.WriteLine("Creation failed.");
}
return 1;
}
}
/// <summary>
/// Delete an existing alias
/// </summary>
/// <param name="config">Config</param>
/// <param name="args">CMD Args</param>
/// <param name="provider">Provider</param>
/// <returns>Exit Code</returns>
private static async Task<int> DeleteAlias(Data.MailiasConfig config, Args args, Data.IProvider provider)
{
var exists = (await provider.GetAliases(config))
.Any(alias => alias.SourceAddress == args.DeleteAlias);
if (exists)
{
if (args.Force || YesNo("Really delete alias '" + args.DeleteAlias + "'?"))
{
var result = await provider.DeleteAliasAddress(args.DeleteAlias);
if (result == Data.DeleteResult.Success)
{
return 0;
}
if (!args.Silent)
{
CoEx.WriteLine("Delete failed.");
}
return 1;
}
else
{
return 0;
}
}
else
{
if (!args.Silent)
{
CoEx.WriteLine("Alias not found or didn't match the format of an alias which was created with this application.");
}
return 1;
}
}
/// <summary>
/// List existing aliases
/// </summary>
/// <param name="config">Config</param>
/// <param name="args">CMD Args</param>
/// <param name="provider">Provider</param>
/// <returns>Exit Code</returns>
private static async Task<int> ListAliases(Data.MailiasConfig config, Args args, Data.IProvider provider)
{
// Table header
var header = new string[] { "Source", "Targets" };
// Convert the alias items into table rows
var aliases = (await provider.GetAliases(config))
.Select(a => a.SourceAddress)
.ToList();
if(aliases.Count > 0)
{
CoEx.WriteLine(string.Join(Environment.NewLine, aliases));
return 0;
}
else
{
// no aliases found
return 1;
}
}
/// <summary>
/// Default location for the configuration file
/// </summary>
/// <returns>Path of the configuration file</returns>
private static string GetConfigPath()
{
var path = System.Environment.GetFolderPath(Environment.SpecialFolder.UserProfile);
return Path.Combine(path, "malias.json");
}
/// <summary>
/// Load the application configuration file
/// ~/malias.json
/// </summary>
/// <returns>Deserialized configuration</returns>
private static Data.MailiasConfig LoadConfiguration()
{
var configFile = GetConfigPath();
// create empty config if the file does not exists
if (!File.Exists(configFile))
{
var emptyConfig = new Data.MailiasConfig();
var emptyConfigText = NewJson.JsonConvert.SerializeObject(emptyConfig, NewJson.Formatting.Indented);
File.WriteAllText(configFile, emptyConfigText);
}
// Parse config
var configBuilder = new ConfigurationBuilder()
.AddJsonFile(configFile, false, false)
.Build();
return configBuilder.Get<Data.MailiasConfig>();
}
/// <summary>
/// Create a provider instance
/// </summary>
/// <param name="config">Config</param>
/// <returns>The created provider</returns>
private static Data.IProvider CreateProvider(Data.MailiasConfig config)
{
Data.IProvider provider = Providers.SingleOrDefault(p => p.ProviderKey == config.Provider);
if (provider == null)
{
return null;
}
provider.Configure(config);
return provider;
}
}
}