1using System.Diagnostics;
15 private readonly LinkedList<TaskCompletionSource<bool>> tasksWaiting =
new();
16 private readonly
string dataFolder;
19 private bool? initialized =
null;
20 private bool started =
false;
25 public StorageService()
27 string AppDataFolder = Environment.GetFolderPath(Environment.SpecialFolder.ApplicationData);
28 this.dataFolder = Path.Combine(AppDataFolder,
"Data");
31 string name = Environment.GetEnvironmentVariable(
"NEUROACCESS_DATA_PROFILE") ??
"";
32 this.dataFolder = Path.Combine(AppDataFolder,
"Data" + name);
39 public string DataFolder => this.dataFolder;
41 #region LifeCycle management
44 public async Task Init(CancellationToken? cancellationToken)
46 lock (this.tasksWaiting)
59 if (this.databaseProvider is
null)
61 this.databaseProvider = await this.CreateDatabaseFile();
64 await this.databaseProvider.
Start();
67 if (this.databaseProvider is not
null)
78 ServiceRef.LogService.LogException(e1);
90 Directory.Delete(this.dataFolder,
true);
92 this.databaseProvider = await this.CreateDatabaseFile();
96 await this.databaseProvider.
Start();
109 ServiceRef.LogService.LogException(e3);
111 await App.StopAsync();
119 this.InitDone(
false);
122 private void InitDone(
bool Result)
124 lock (this.tasksWaiting)
126 this.initialized = Result;
128 foreach (TaskCompletionSource<bool> Wait
in this.tasksWaiting)
129 Wait.TrySetResult(Result);
131 this.tasksWaiting.Clear();
136 public Task<bool> WaitInitDone()
138 lock (this.tasksWaiting)
140 if (this.initialized.HasValue)
141 return Task.FromResult<
bool>(this.initialized.Value);
143 TaskCompletionSource<bool> Wait =
new();
144 this.tasksWaiting.AddLast(Wait);
151 public async Task Shutdown()
153 lock (this.tasksWaiting)
155 this.initialized =
null;
156 this.started =
false;
161 if (this.persistedEventLog is not
null)
165 this.persistedEventLog =
null;
168 if (this.databaseProvider is not
null)
171 await this.databaseProvider.
Flush();
172 await this.databaseProvider.
Stop();
173 this.databaseProvider =
null;
178 ServiceRef.LogService.LogException(ex);
182 private Task<FilesProvider> CreateDatabaseFile()
184 FilesProvider.AsyncFileIo =
true;
186 (
int)Constants.Timeouts.Database.TotalMilliseconds, ServiceRef.CryptoService.GetCustomKey);
192 [Obsolete(
"Use DisposeAsync() instead.")]
193 public void Dispose()
195 this.DisposeAsync().Wait();
201 public async Task DisposeAsync()
203 if (this.persistedEventLog is not
null)
206 this.persistedEventLog =
null;
209 if (this.databaseProvider is not
null)
212 this.databaseProvider =
null;
218 public async Task Insert(
object obj)
224 public async Task Update(
object obj)
230 public Task<T> FindFirstDeleteRest<T>() where T : class
232 return Database.FindFirstDeleteRest<T>();
235 public Task<T> FindFirstIgnoreRest<T>() where T : class
237 return Database.FindFirstIgnoreRest<T>();
248 public void FlagForRepair()
250 this.DeleteFile(
"Start.txt");
251 this.DeleteFile(
"Stop.txt");
254 private void DeleteFile(
string FileName)
258 FileName = Path.Combine(this.dataFolder, FileName);
260 if (File.Exists(FileName))
261 File.Delete(FileName);
Static class managing the application event log. Applications and services log events on this static ...
static void Register(IEventSink EventSink)
Registers an event sink with the event log. Call Unregister(IEventSink) to unregister it,...
static Exception UnnestException(Exception Exception)
Unnests an exception, to extract the relevant inner exception.
static bool Unregister(IEventSink EventSink)
Unregisters an event sink from the event log.
Creates an even sink that stores incoming (logged) events in the local object database,...
override Task DisposeAsync()
IDisposableAsync.DisposeAsync()
Static interface for database persistence. In order to work, a database provider has to be assigned t...
static bool HasProvider
If a database provider is registered.
static void Register(IDatabaseProvider DatabaseProvider)
Registers a database provider for use from the static Database class, throughout the lifetime of the ...
static IDatabaseProvider Provider
Registered database provider.
static Task< bool > Export(IDatabaseExport Output)
Performs an export of the database.
static async Task Update(object Object)
Updates an object in the database.
static async Task Insert(object Object)
Inserts an object into the default collection of the database.
Persists objects into binary files.
async Task DisposeAsync()
IDisposableAsync.DisposeAsync
async Task Stop()
Called when processing ends.
async Task Flush()
Persists any pending changes.
async Task< string[]> RepairIfInproperShutdown(string XsltPath)
Checks if the database needs repairing. This is done by checking the last start and stop timetamps to...
Task Start()
Called when processing starts.
static Task< FilesProvider > CreateAsync(string Folder, string DefaultCollectionName, int BlockSize, int BlocksInCache, int BlobBlockSize, Encoding Encoding, int TimeoutMilliseconds, CustomKeyHandler CustomKeyMethod)
Persists objects into binary files.
Interface for asynchronously disposable objects.
Task Flush()
Persists any pending changes.
Interface for database exports.