-
Notifications
You must be signed in to change notification settings - Fork 0
Commit
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.
Merge pull request #11 from ducksoop/develop
[ADD/UPDATE] Insert, Update, and Delete Commands
- Loading branch information
Showing
27 changed files
with
2,695 additions
and
139 deletions.
There are no files selected for viewing
This file was deleted.
Oops, something went wrong.
This file was deleted.
Oops, something went wrong.
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
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
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
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,37 @@ | ||
using QuickbaseNet.Errors; | ||
|
||
namespace QuickbaseNet.UnitTests.Tests; | ||
|
||
public class QuickbaseResultTests | ||
{ | ||
[Fact] | ||
public void Constructor_ThrowsArgumentException_WhenInvalidErrorForSuccess() | ||
{ | ||
// Arrange | ||
var isSuccess = true; | ||
var invalidError = QuickbaseError.ClientError("InvalidError", "Invalid error occurred", "Description"); | ||
|
||
// Act & Assert | ||
Assert.Throws<ArgumentException>(() => new TestableQuickbaseResult(isSuccess, invalidError)); | ||
} | ||
|
||
[Fact] | ||
public void Constructor_ThrowsArgumentException_WhenInvalidErrorForFailure() | ||
{ | ||
// Arrange | ||
var isSuccess = false; | ||
var invalidError = QuickbaseError.None; | ||
|
||
// Act & Assert | ||
Assert.Throws<ArgumentException>(() => new TestableQuickbaseResult(isSuccess, invalidError)); | ||
} | ||
} | ||
|
||
internal class TestableQuickbaseResult : QuickbaseResult | ||
{ | ||
public TestableQuickbaseResult(bool isSuccess, QuickbaseError quickbaseError) | ||
: base(isSuccess, quickbaseError) | ||
{ | ||
// This constructor allows access to the protected internal constructor of QuickbaseResult | ||
} | ||
} |
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
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,130 @@ | ||
namespace QuickbaseNet.UnitTests.Utility; | ||
|
||
using System; | ||
using System.Collections.Generic; | ||
using System.Diagnostics.CodeAnalysis; | ||
using System.Linq; | ||
using System.Reflection; | ||
|
||
using AutoBogus; | ||
|
||
using Bogus; | ||
|
||
[ExcludeFromCodeCoverage] | ||
public class Builder | ||
{ | ||
public T Build<T>() where T : class | ||
{ | ||
var binder = new AutoBinder(); | ||
|
||
Faker<T> model = new AutoFaker<T>(binder) | ||
.RuleForType(typeof(uint), rule => rule.Random.UInt(1, int.MaxValue)) | ||
.RuleForType(typeof(uint?), rule => (uint?)rule.Random.UInt(1, int.MaxValue)) | ||
.RuleForType(typeof(int), rule => rule.Random.Int()) | ||
.RuleForType(typeof(int?), rule => (int?)rule.Random.Int()) | ||
.RuleForType(typeof(DateTime), rule => | ||
{ | ||
DateTime date = rule.Date.Recent(); | ||
return new DateTime( | ||
date.Year, | ||
date.Month, | ||
date.Day | ||
); | ||
}) | ||
.RuleForType(typeof(DateTime?), rule => | ||
{ | ||
DateTime date = rule.Date.Recent(); | ||
return (DateTime?)new DateTime( | ||
date.Year, | ||
date.Month, | ||
date.Day | ||
); | ||
}) | ||
.RuleForType(typeof(DateTimeOffset?), rule => | ||
{ | ||
DateTimeOffset date = rule.Date.Recent(); | ||
return (DateTimeOffset?)new DateTime( | ||
date.Year, | ||
date.Month, | ||
date.Day | ||
); | ||
}) | ||
.RuleForType(typeof(byte), rule => rule.Random.Byte()) | ||
.RuleForType(typeof(byte?), rule => (byte?)rule.Random.Byte()) | ||
.RuleForType(typeof(sbyte), rule => rule.Random.SByte()) | ||
.RuleForType(typeof(string), rule => rule.Random.AlphaNumeric(10)) | ||
.RuleForType(typeof(decimal), rule => rule.Finance.Amount(min: 0.01M, max: 99999.99M, decimals: 2)) | ||
.RuleForType(typeof(decimal?), rule => (decimal?)rule.Finance.Amount(min: 0.01M, max: 99999.99M, decimals: 2)) | ||
.RuleForType(typeof(ushort), rule => rule.Random.UShort()) | ||
.RuleForType(typeof(short), rule => rule.Random.Short()) | ||
.RuleForType(typeof(long), rule => rule.Random.Long()) | ||
.RuleForType(typeof(ulong), rule => rule.Random.ULong()) | ||
.RuleForType(typeof(bool), rule => rule.Random.Bool()) | ||
.RuleForType(typeof(bool?), rule => (bool?)rule.Random.Bool()); | ||
|
||
model = AddEnumRules(model, binder); | ||
|
||
//int seed = DateTime.UtcNow.Millisecond; | ||
//return model.UseSeed(seed).Generate(); | ||
return model.Generate(); | ||
} | ||
|
||
/// <summary> | ||
/// Adds the ability to generate random valid enum values | ||
/// </summary> | ||
/// <remarks> | ||
/// Bogus currently doesn't appear to have a way to create rules for types that aren't well known at compile time. To generate random values for enum properties | ||
/// we have to find properties on <typeparamref name="T"/> that are enum and get a list of valid values for that enum and pick one of those randomly. | ||
/// | ||
/// Bogus appears to do similar things when creating rules for well known types too, so this is at least similar. | ||
/// | ||
/// This also excludes enum members whose name is "None" when it is the first member of the enum as that is usually not a valid value. | ||
/// This follows the convention for other nubmer types not generating zeroes | ||
/// </remarks> | ||
private Faker<T> AddEnumRules<T>(Faker<T> faker, IBinder binder) where T : class | ||
{ | ||
// find enum properties using the binder | ||
IEnumerable<PropertyInfo> enumProperties = binder.GetMembers(typeof(T)) | ||
.Select(item => item.Value) | ||
.OfType<PropertyInfo>() | ||
.Where(item => item.PropertyType.IsEnum); | ||
|
||
Faker<T> result = faker; | ||
if (enumProperties.Any()) | ||
{ | ||
result = result.FinishWith((fk, target) => | ||
{ | ||
foreach (PropertyInfo enumProperty in enumProperties) | ||
{ | ||
// None = 0 is typically not a valid value, so for the sake of generating sane values it will be skipped | ||
var minIndex = 0; | ||
string[] enumNames = Enum.GetNames(enumProperty.PropertyType); | ||
if (enumNames[0].ToLower() == "none") | ||
{ | ||
minIndex = 1; | ||
} | ||
|
||
Array enumValues = Enum.GetValues(enumProperty.PropertyType); | ||
var randomIndex = fk.Random.Int(minIndex, enumValues.Length - 1); | ||
object randomEnumValue = enumValues.GetValue(randomIndex); | ||
Check warning on line 109 in QuickbaseNet.UnitTests/Utility/Builder.cs GitHub Actions / build-and-deploy
|
||
|
||
enumProperty.SetValue(target, randomEnumValue); | ||
} | ||
}); | ||
} | ||
|
||
return result; | ||
} | ||
|
||
public IEnumerable<T> Build<T>(int howMany) where T : class | ||
{ | ||
var models = new List<T>(); | ||
for (int i = 0; i < howMany; i++) | ||
{ | ||
T model = Build<T>(); | ||
models.Add(model); | ||
} | ||
|
||
return models; | ||
} | ||
} |
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
Oops, something went wrong.