Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Added support for nullable value types and enums #14

Merged
merged 1 commit into from
Sep 24, 2020
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
32 changes: 32 additions & 0 deletions source/Ocl/Converters/EnumAttributeOclConverter.cs
Original file line number Diff line number Diff line change
@@ -0,0 +1,32 @@
using System;

namespace Octopus.Ocl.Converters
{
public class EnumAttributeOclConverter : OclConverter
{
public override bool CanConvert(Type type)
=> type.IsEnum;

public override object? FromElement(OclConversionContext context, Type type, IOclElement element, Func<object?> getCurrentValue)
{
if (element is OclAttribute attribute)
{
if (attribute.Value == null)
return null;

if (attribute.Value is string str)
return Enum.Parse(type, str);

if (attribute.Value is OclStringLiteral strLit)
return Enum.Parse(type, strLit.Value);

throw new Exception("Enum values must be specified as a string");
}

throw new OclException("Can only convert attribute elements");
}

protected override IOclElement ConvertInternal(OclConversionContext context, string name, object obj)
=> new OclAttribute(GetName(name, obj), obj.ToString());
}
}
9 changes: 8 additions & 1 deletion source/Ocl/OclAttribute.cs
Original file line number Diff line number Diff line change
Expand Up @@ -50,11 +50,18 @@ public object? Value
}

public static bool IsSupportedValueType(Type type)
=> type.IsPrimitive ||
{
bool IsNullableSupportedValueType()
=> type.IsGenericType && type.GetGenericTypeDefinition() == typeof(Nullable<>) && IsSupportedValueType(type.GetGenericArguments()[0]);

return type.IsPrimitive ||
type == typeof(string) ||
type == typeof(decimal) ||
type == typeof(OclStringLiteral) ||
IsNullableSupportedValueType() ||
IsSupportedValueCollectionType(type);
}


internal static bool IsSupportedValueCollectionType(Type type)
=> (type.IsArray && type.GetArrayRank() == 1 && IsSupportedValueType(type.GetElementType()!)) ||
Expand Down
1 change: 1 addition & 0 deletions source/Ocl/OclConversionContext.cs
Original file line number Diff line number Diff line change
Expand Up @@ -16,6 +16,7 @@ internal OclConversionContext(OclSerializerOptions options)
.Concat(
new IOclConverter[]
{
new EnumAttributeOclConverter(),
new DefaultAttributeOclConverter(),
new DefaultCollectionOclConverter(),
new DefaultBlockOclConverter(),
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -29,6 +29,19 @@ public void IntAttribute()
.BeEquivalentTo(new Car() { Doors = 4 });
}

[Test]
public void IntNullAttribute()
{
var document = new OclDocument()
{
new OclAttribute("Doors", null)
};

OclConvert.Deserialize<Car>(document, new OclSerializerOptions())
.Should()
.BeEquivalentTo(new Car() { Doors = null });
}

[Test]
public void StringAttribute()
{
Expand All @@ -42,6 +55,19 @@ public void StringAttribute()
.BeEquivalentTo(new Car() { Name = "Mystery Machine" });
}

[Test]
public void EnumAttribute()
{
var document = new OclDocument()
{
new OclAttribute("Type", "Suv")
};

OclConvert.Deserialize<Car>(document, new OclSerializerOptions())
.Should()
.BeEquivalentTo(new Car() { Type = CarType.Suv });
}

[Test]
public void Block()
{
Expand Down Expand Up @@ -127,9 +153,16 @@ public void ExceptionIsThrownIfPropertyDoesNotExist()
class Car
{
public string Name { get; set; } = "";
public int Doors { get; set; }
public int? Doors { get; set; }
public Person? Driver { get; set; }
public List<Person>? Passengers { get; set; }
public CarType Type { get; set; }
}

enum CarType
{
Hatchback,
Suv
}

class Person
Expand Down
17 changes: 17 additions & 0 deletions source/Tests/ToOclDoc/ToOclBodyDefaultBehaviourFixture.cs
Original file line number Diff line number Diff line change
@@ -1,5 +1,6 @@
using System;
using System.Collections.Generic;
using System.Reflection;
using NUnit.Framework;
using Octopus.Ocl;

Expand Down Expand Up @@ -47,6 +48,22 @@ public void ListOfComplexTypesProperty()
);
}

[Test]
public void Enum()
{
var data = new
{
MyProp = BindingFlags.Static
};

var result = OclConvert.ToOclDocument(data, new OclSerializerOptions());

result.Should()
.HaveChildrenExactly(
new OclAttribute("MyProp", "Static")
);
}

class Car
{
public int Doors { get; } = 2;
Expand Down