diff --git a/.BinaryPrefs/Appegy.BinaryStorage.csproj.DotSettings b/.BinaryPrefs/Appegy.BinaryStorage.csproj.DotSettings index ebb0e9d..aeb09c3 100644 --- a/.BinaryPrefs/Appegy.BinaryStorage.csproj.DotSettings +++ b/.BinaryPrefs/Appegy.BinaryStorage.csproj.DotSettings @@ -2,4 +2,5 @@ True True True + True True \ No newline at end of file diff --git a/Runtime/BinaryStorage.cs b/Runtime/BinaryStorage.cs index df78146..a721de9 100644 --- a/Runtime/BinaryStorage.cs +++ b/Runtime/BinaryStorage.cs @@ -22,6 +22,11 @@ public partial class BinaryStorage : IDisposable /// public bool AutoSave { get; set; } + /// + /// Gets or sets the behavior when a requested key is not found in the storage. + /// + public MissingKeyBehavior MissingKeyBehavior { get; set; } = MissingKeyBehavior.ReturnDefaultValueOnly; + /// /// Gets a value indicating whether there are unsaved changes. /// @@ -85,18 +90,27 @@ public virtual bool Supports() /// /// The type of the value. /// The key to get the value for. - /// The initial value to use if the key does not exist. + /// The default value to use if the key does not exist. /// The value associated with the key. - public virtual T Get(string key, T initValue = default) + public virtual T Get(string key, T defaultValue = default) { ThrowIfDisposed(); ThrowIfCollection(); - var record = GetRecord(key) ?? AddRecord(key, initValue); - if (record is not Record typedRecord) + var record = GetRecord(key); + switch (record) { - throw new UnexpectedTypeException(key, nameof(Get), record.Type, typeof(T)); + case Record typedRecord: + return typedRecord.Value; + case not null: + throw new UnexpectedTypeException(key, nameof(Get), record.Type, typeof(T)); + case null: + return MissingKeyBehavior switch + { + MissingKeyBehavior.InitializeWithDefaultValue => AddRecord(key, defaultValue).Value, + MissingKeyBehavior.ReturnDefaultValueOnly => defaultValue, + _ => throw new UnexpectedEnumException(typeof(MissingKeyBehavior), MissingKeyBehavior) + }; } - return typedRecord.Value; } /// @@ -105,9 +119,9 @@ public virtual T Get(string key, T initValue = default) /// The type of the value. /// The key to set the value for. /// The value to set. - /// Whether to override the type if the key already exists. + /// Whether to override the value if the key already exists but with another type. /// True if the value was set; otherwise, false. - public virtual bool Set(string key, T value, bool overrideTypeIfExists = false) + public virtual bool Set(string key, T value, bool overrideTypeMismatch = false) { ThrowIfDisposed(); ThrowIfCollection(); @@ -124,7 +138,7 @@ public virtual bool Set(string key, T value, bool overrideTypeIfExists = fals return ChangeRecord(typedRecord, value); } - if (!overrideTypeIfExists) + if (!overrideTypeMismatch) { throw new UnexpectedTypeException(key, nameof(Set), record.Type, typeof(T)); } @@ -295,7 +309,7 @@ private TCollection GetCollectionOf(string key) /// The key to add the record for. /// The value to add. /// The added record. - private Record AddRecord(string key, T value) + private Record AddRecord(string key, T value) { var typeIndex = _supportedTypes.FindIndex(static c => c is TypedBinarySection); if (typeIndex == -1) diff --git a/Runtime/Exceptions/UnexpectedEnumException.cs b/Runtime/Exceptions/UnexpectedEnumException.cs new file mode 100644 index 0000000..a2993b1 --- /dev/null +++ b/Runtime/Exceptions/UnexpectedEnumException.cs @@ -0,0 +1,12 @@ +using System; + +namespace Appegy.Storage +{ + public class UnexpectedEnumException : Exception + { + public UnexpectedEnumException(Type actualType, Enum value) + : base($"Unexpected enum type {actualType.Name}.{value}") + { + } + } +} \ No newline at end of file diff --git a/Runtime/Exceptions/UnexpectedEnumException.cs.meta b/Runtime/Exceptions/UnexpectedEnumException.cs.meta new file mode 100644 index 0000000..9db80e9 --- /dev/null +++ b/Runtime/Exceptions/UnexpectedEnumException.cs.meta @@ -0,0 +1,3 @@ +fileFormatVersion: 2 +guid: 5b21c62ef5a94febbb48b44a2a028238 +timeCreated: 1718985451 \ No newline at end of file diff --git a/Runtime/Settings.meta b/Runtime/Settings.meta new file mode 100644 index 0000000..26af7dc --- /dev/null +++ b/Runtime/Settings.meta @@ -0,0 +1,3 @@ +fileFormatVersion: 2 +guid: a50c284b3de641f89748b9b07b637dea +timeCreated: 1718983768 \ No newline at end of file diff --git a/Runtime/Settings/MissingKeyBehavior.cs b/Runtime/Settings/MissingKeyBehavior.cs new file mode 100644 index 0000000..3f8457d --- /dev/null +++ b/Runtime/Settings/MissingKeyBehavior.cs @@ -0,0 +1,18 @@ +namespace Appegy.Storage +{ + /// + /// Specifies the behavior when a requested key is not found in the storage. + /// + public enum MissingKeyBehavior + { + /// + /// Initializes the key with the provided default value and stores it. + /// + InitializeWithDefaultValue, + + /// + /// Returns the provided default value without storing it. + /// + ReturnDefaultValueOnly + } +} \ No newline at end of file diff --git a/Runtime/Settings/MissingKeyBehavior.cs.meta b/Runtime/Settings/MissingKeyBehavior.cs.meta new file mode 100644 index 0000000..0fcae80 --- /dev/null +++ b/Runtime/Settings/MissingKeyBehavior.cs.meta @@ -0,0 +1,3 @@ +fileFormatVersion: 2 +guid: 2e3e5b590d684ac69d989d05720c7722 +timeCreated: 1718983775 \ No newline at end of file