Created
August 16, 2013 15:39
-
-
Save mcnemesis/6250972 to your computer and use it in GitHub Desktop.
A Simple, 1-class non-obtrusive No-SQL DB for Windows Phone 8, Windows Store + (RT)
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
using Newtonsoft.Json; | |
using System; | |
using System.Collections.Generic; | |
using System.IO; | |
using System.Linq; | |
using System.Text; | |
using System.Threading.Tasks; | |
using Windows.Storage; | |
namespace MyCHILD | |
{ | |
class DataDictionary | |
{ | |
public delegate void StoreInitiatedCallback(); | |
/// <summary> | |
/// Name of the root folder containing the store items | |
/// </summary> | |
private const String DICTIONARY_ROOT = "DATA_DICTIONARY"; | |
private List<String> _keys = new List<string>(); | |
private const String _keyKEYS = ".KEYS"; | |
//keys others are not allowed to use (for internal usage only) | |
private String[] _restrictedKeys = new String[] { _keyKEYS }; | |
private StorageFolder rootFolder; | |
/// <summary> | |
/// All the KEYs in the Dictionary | |
/// </summary> | |
List<String> KEYS { get { return _keys; } } | |
internal async Task init(StoreInitiatedCallback callback) { | |
await _initRoot(); | |
await loadKeys(); | |
callback(); | |
} | |
private async Task _initRoot() | |
{ | |
StorageFolder folder = ApplicationData.Current.LocalFolder; | |
try | |
{ | |
await folder.CreateFolderAsync(DICTIONARY_ROOT, CreationCollisionOption.FailIfExists); | |
} | |
catch (Exception e) { | |
} | |
rootFolder = await folder.GetFolderAsync(DICTIONARY_ROOT); | |
} | |
private async Task loadKeys() | |
{ | |
String jKEYS = await ReadString(_keyKEYS); | |
_keys = JsonConvert.DeserializeObject<List<String>>(jKEYS); | |
_keys = (_keys == null) ? new List<String>() : _keys; | |
} | |
public bool Exists(String KEY) | |
{ | |
return _keys.Contains(_getSafeKey(KEY)); | |
} | |
/// <summary> | |
/// Write a string to the Dictionary | |
/// Doesn't try to secure the key -- useful for writting meta-data | |
/// </summary> | |
/// <param name="KEY"></param> | |
/// <param name="DATA"></param> | |
/// <returns></returns> | |
async private Task<bool> _WriteString(string KEY, string DATA) | |
{ | |
byte[] data = Encoding.UTF8.GetBytes(DATA); | |
try | |
{ | |
StorageFile file = await rootFolder.CreateFileAsync(KEY, CreationCollisionOption.ReplaceExisting); | |
using (Stream s = await file.OpenStreamForWriteAsync()) | |
{ | |
await s.WriteAsync(data, 0, data.Length); | |
if (!Exists(KEY)) | |
await _saveKEY(KEY); | |
} | |
return true; | |
} | |
catch (Exception e) | |
{ | |
return false; | |
} | |
} | |
/// <summary> | |
/// Safely write a string to the Dictionary | |
/// </summary> | |
/// <param name="KEY"></param> | |
/// <param name="DATA"></param> | |
/// <returns></returns> | |
async public Task<bool> WriteString(string KEY, string DATA) | |
{ | |
return await _WriteString(_getSafeKey(KEY), DATA); | |
} | |
async private Task<bool> _saveKEY(string KEY) | |
{ | |
if (!_keys.Contains(KEY)) | |
{ | |
_keys.Add(KEY); | |
await _saveKEYS(); | |
} | |
return true; | |
} | |
async private Task<bool> _saveKEYS() | |
{ | |
String jKEYS = JsonConvert.SerializeObject(_keys, Formatting.Indented); | |
await _WriteString(_keyKEYS, jKEYS); //uses the internal/meta-data version of WriteString, which doesn't secure the key | |
return true; | |
} | |
private string _getSafeKey(string KEY) | |
{ | |
if (_restrictedKeys.Contains(KEY)) | |
return String.Format("_{0}_", KEY); | |
else | |
return KEY; | |
} | |
async public Task<string> ReadString(string KEY) | |
{ | |
byte[] data; | |
try | |
{ | |
StorageFile file = await rootFolder.GetFileAsync(KEY); | |
using (Stream s = await file.OpenStreamForReadAsync()) | |
{ | |
data = new byte[s.Length]; | |
await s.ReadAsync(data, 0, (int)s.Length); | |
} | |
return Encoding.UTF8.GetString(data, 0, data.Length); | |
} | |
catch (Exception e) | |
{ | |
} | |
return ""; | |
} | |
async private Task<bool> _Delete(String KEY) | |
{ | |
try | |
{ | |
StorageFile file = await rootFolder.GetFileAsync(KEY); | |
await file.DeleteAsync(); | |
return true; | |
} | |
catch (Exception e) | |
{ | |
return false; | |
} | |
} | |
async public Task<bool> Delete(String KEY) | |
{ | |
if (Exists(KEY)) | |
{ | |
return await _Delete(_getSafeKey(KEY)); | |
} | |
else | |
return false; | |
} | |
} | |
} |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment