Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
Show all changes
30 commits
Select commit Hold shift + click to select a range
8c1704c
[csharp] Explicitly set supportsInheritance
jimschubert Oct 17, 2016
44009b5
[csharp] set supportsInheritance for client
jimschubert Oct 23, 2016
148ccbb
include nice improvement of https://github.com/jimschubert/swagger-co…
manuc66 Jun 22, 2017
bf11a65
remove duplicate base validations
manuc66 Jun 22, 2017
08d74a4
remove useless tests
manuc66 Jun 22, 2017
a923569
restore documentation for properties coming from parent
manuc66 Jun 22, 2017
a490e2d
launch bin/security/csharp-petstore.sh
manuc66 Jun 22, 2017
79a5091
Merge branch 'csharp/3829' of github.com:jimschubert/swagger-codegen …
manuc66 Jun 23, 2017
1d43add
Merge branch 'feature/csharp-subtypes' of github.com:manuc66/swagger-…
manuc66 Jun 23, 2017
725e1db
it's impossible to call an explicitly implemented interface-method on…
manuc66 Jun 23, 2017
a98218c
restore portion of code that was lost
manuc66 Jun 23, 2017
2a73320
regenerate more
manuc66 Jun 23, 2017
7e38479
fix missing using
manuc66 Jun 23, 2017
5667128
take the multi .net compatible revision
manuc66 Jun 23, 2017
44101e4
keep generated model simple when no hierarchy involved
manuc66 Jun 23, 2017
ece2618
regenerate with:
manuc66 Jun 24, 2017
21691a0
fix inheritance GetHashCode and Equals
manuc66 Jun 24, 2017
7ee5ba9
fix sln indentation and the missing windows runner for dotnet2
manuc66 Jun 24, 2017
25bd939
override instead of hiding the base method
manuc66 Jun 24, 2017
451a768
By default the value of the discriminator property must be the name o…
manuc66 Jun 24, 2017
14da2e6
Add test for subtype deserialisation from parent type
manuc66 Jun 24, 2017
7958517
add missing '.bat' and use the 'call' template from javascript-petsto…
manuc66 Jul 1, 2017
b0a65be
fix default value bug
manuc66 Jul 1, 2017
8913055
cleanup copyright information
manuc66 Jul 1, 2017
cf89bc3
Merge branch 'master' into feature/csharp-subtypes
manuc66 Jul 17, 2017
d9d5782
formatting after merge
manuc66 Jul 19, 2017
6b2f15b
Merge branch 'master' into feature/csharp-subtypes
manuc66 Jul 29, 2017
ae77527
fix merge
manuc66 Jul 29, 2017
cfe5bb6
applying bin/csharp-petstore-all.sh
manuc66 Jul 29, 2017
c5687c1
applying bin/security/csharp-petstore.sh
manuc66 Jul 29, 2017
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
Empty file modified bin/csharp-dotnet2-petstore.sh
100755 → 100644
Empty file.
10 changes: 10 additions & 0 deletions bin/security/windows/csharp-petstore.bat
Original file line number Diff line number Diff line change
@@ -0,0 +1,10 @@
set executable=.\modules\swagger-codegen-cli\target\swagger-codegen-cli.jar

If Not Exist %executable% (
mvn clean package
)

REM set JAVA_OPTS=%JAVA_OPTS% -Xmx1024M
set ags=generate -i modules/swagger-codegen/src/test/resources/2_0/petstore-security-test.yaml -l csharp -o samples/client/petstore-security-test/csharp/SwaggerClient --additional-properties packageGuid={8CE139DF-64BC-4591-85F8-8506C2B67514}

java %JAVA_OPTS% -jar %executable% %ags%
10 changes: 10 additions & 0 deletions bin/windows/csharp-dotnet2-petstore.bat
Original file line number Diff line number Diff line change
@@ -0,0 +1,10 @@
set executable=.\modules\swagger-codegen-cli\target\swagger-codegen-cli.jar

If Not Exist %executable% (
mvn clean package
)

REM set JAVA_OPTS=%JAVA_OPTS% -Xmx1024M
set ags=generate -i modules/swagger-codegen/src/test/resources/2_0/petstore.yaml -l CsharpDotNet2 -o samples/client/petstore/csharp-dotnet2/SwaggerClientTest/Lib/SwaggerClient --additional-properties hideGenerationTimestamp=true

java %JAVA_OPTS% -jar %executable% %ags%
12 changes: 9 additions & 3 deletions bin/windows/csharp-petstore-all.bat
Original file line number Diff line number Diff line change
@@ -1,8 +1,14 @@
REM C# Petstore API client
.\bin\windows\csharp-petstore.bat
call .\bin\windows\csharp-petstore.bat

REM C# Petstore API client with PropertyChanged
.\bin\windows\csharp-property-changed-petstore.bat
call .\bin\windows\csharp-property-changed-petstore.bat

REM C# Petstore API client (v5.0 for .net standarnd 1.3+)
.\bin\windows\csharp-petstore-netstandard.bat
call .\bin\windows\csharp-petstore-netstandard.bat

call .\bin\windows\csharp-dotnet2-petstore.bat

call .\bin\windows\csharp-petstore-netcore-project.bat

call .\bin\windows\csharp-property-changed-petstore.bat
2 changes: 1 addition & 1 deletion bin/windows/csharp-property-changed-petstore.bat
Original file line number Diff line number Diff line change
Expand Up @@ -5,6 +5,6 @@ If Not Exist %executable% (
)

REM set JAVA_OPTS=%JAVA_OPTS% -Xmx1024M
set ags=generate -i modules/swagger-codegen/src/test/resources/2_0/petstore-with-fake-endpoints-models-for-testing.yaml -l csharp -o samples\client\petstore\csharp\SwaggerClientNetStandard --additional-properties targetFramework=v5.0,packageGuid={3AB1F259-1769-484B-9411-84505FCCBD55}
set ags=generate -i modules/swagger-codegen/src/test/resources/2_0/petstore-with-fake-endpoints-models-for-testing.yaml -l csharp -o samples\client\petstore\csharp\SwaggerClientWithPropertyChanged --additional-properties=generatePropertyChanged=true,packageGuid={5CD900DE-8266-412F-A758-28E1F9C623D5}

java %JAVA_OPTS% -jar %executable% %ags%
Original file line number Diff line number Diff line change
Expand Up @@ -3134,6 +3134,7 @@ private void addVars(CodegenModel m, List<CodegenProperty> vars, Map<String, Pro
if (Boolean.TRUE.equals(cp.isReadOnly)) {
m.readOnlyVars.add(cp);
} else { // else add to readWriteVars (list of properties)
// FIXME: readWriteVars can contain duplicated properties. Debug/breakpoint here while running C# generator (Dog and Cat models)
m.readWriteVars.add(cp);
}
}
Expand Down

Large diffs are not rendered by default.

Original file line number Diff line number Diff line change
@@ -0,0 +1,272 @@
using System;
using System.Collections;
using System.Collections.Generic;
using System.Linq;
using System.Reflection;
using Newtonsoft.Json;
using Newtonsoft.Json.Linq;

namespace JsonSubTypes
{
// Copied from project https://github.com/manuc66/JsonSubTypes
// https://raw.githubusercontent.com/manuc66/JsonSubTypes/07403192ea3f4959f6d42f5966ac56ceb0d6095b/JsonSubTypes/JsonSubtypes.cs

public class JsonSubtypes : JsonConverter
{
[AttributeUsage(AttributeTargets.Class | AttributeTargets.Interface, AllowMultiple = true)]
public class KnownSubTypeAttribute : Attribute
{
public Type SubType { get; private set; }
public object AssociatedValue { get; private set; }

public KnownSubTypeAttribute(Type subType, object associatedValue)
{
SubType = subType;
AssociatedValue = associatedValue;
}
}
[AttributeUsage(AttributeTargets.Class | AttributeTargets.Interface, AllowMultiple = true)]
public class KnownSubTypeWithPropertyAttribute : Attribute
{
public Type SubType { get; private set; }
public string PropertyName { get; private set; }

public KnownSubTypeWithPropertyAttribute(Type subType, string propertyName)
{
SubType = subType;
PropertyName = propertyName;
}
}

private readonly string _typeMappingPropertyName;

private bool _isInsideRead;
private JsonReader _reader;

public override bool CanRead
{
get
{
if (!_isInsideRead)
return true;

return !string.IsNullOrEmpty(_reader.Path);
}
}

public sealed override bool CanWrite
{
get { return false; }
}

public JsonSubtypes()
{
}

public JsonSubtypes(string typeMappingPropertyName)
{
_typeMappingPropertyName = typeMappingPropertyName;
}

public override bool CanConvert(Type objectType)
{
return _typeMappingPropertyName != null;
}

public override void WriteJson(JsonWriter writer, object value, JsonSerializer serializer)
{
throw new NotImplementedException();
}

public override object ReadJson(JsonReader reader, Type objectType, object existingValue, JsonSerializer serializer)
{
if (reader.TokenType == JsonToken.Comment)
reader.Read();

switch (reader.TokenType)
{
case JsonToken.Null:
return null;
case JsonToken.StartArray:
return ReadArray(reader, objectType, serializer);
case JsonToken.StartObject:
return ReadObject(reader, objectType, serializer);
default:
throw new Exception("Array: Unrecognized token: " + reader.TokenType);
}
}

private IList ReadArray(JsonReader reader, Type targetType, JsonSerializer serializer)
{
var elementType = GetElementType(targetType);

var list = CreateCompatibleList(targetType, elementType);

while (reader.TokenType != JsonToken.EndArray && reader.Read())
{
switch (reader.TokenType)
{
case JsonToken.Null:
list.Add(reader.Value);
break;
case JsonToken.Comment:
break;
case JsonToken.StartObject:
list.Add(ReadObject(reader, elementType, serializer));
break;
case JsonToken.EndArray:
break;
default:
throw new Exception("Array: Unrecognized token: " + reader.TokenType);
}
}
if (targetType.IsArray)
{
var array = Array.CreateInstance(targetType.GetElementType(), list.Count);
list.CopyTo(array, 0);
list = array;
}
return list;
}

private static IList CreateCompatibleList(Type targetContainerType, Type elementType)
{
IList list;
if (targetContainerType.IsArray || targetContainerType.GetTypeInfo().IsAbstract)
{
list = (IList)Activator.CreateInstance(typeof(List<>).MakeGenericType(elementType));
}
else
{
list = (IList)Activator.CreateInstance(targetContainerType);
}
return list;
}

private static Type GetElementType(Type arrayOrGenericContainer)
{
Type elementType;
if (arrayOrGenericContainer.IsArray)
{
elementType = arrayOrGenericContainer.GetElementType();
}
else
{
elementType = arrayOrGenericContainer.GenericTypeArguments[0];
}
return elementType;
}

private object ReadObject(JsonReader reader, Type objectType, JsonSerializer serializer)
{
var jObject = JObject.Load(reader);

var targetType = GetType(jObject, objectType) ?? objectType;

return _ReadJson(CreateAnotherReader(jObject, reader), targetType, null, serializer);
}

private static JsonReader CreateAnotherReader(JObject jObject, JsonReader reader)
{
var jObjectReader = jObject.CreateReader();
jObjectReader.Culture = reader.Culture;
jObjectReader.CloseInput = reader.CloseInput;
jObjectReader.SupportMultipleContent = reader.SupportMultipleContent;
jObjectReader.DateTimeZoneHandling = reader.DateTimeZoneHandling;
jObjectReader.FloatParseHandling = reader.FloatParseHandling;
jObjectReader.DateFormatString = reader.DateFormatString;
jObjectReader.DateParseHandling = reader.DateParseHandling;
return jObjectReader;
}

public Type GetType(JObject jObject, Type parentType)
{
if (_typeMappingPropertyName == null)
{
return GetTypeByPropertyPresence(jObject, parentType);
}
return GetTypeFromDiscriminatorValue(jObject, parentType);
}

private static Type GetTypeByPropertyPresence(JObject jObject, Type parentType)
{
foreach (var type in parentType.GetTypeInfo().GetCustomAttributes<KnownSubTypeWithPropertyAttribute>())
{
JToken ignore;
if (jObject.TryGetValue(type.PropertyName, out ignore))
{
return type.SubType;
}
}
return null;
}

private Type GetTypeFromDiscriminatorValue(JObject jObject, Type parentType)
{
JToken jToken;
if (!jObject.TryGetValue(_typeMappingPropertyName, out jToken)) return null;

var discriminatorValue = jToken.ToObject<object>();
if (discriminatorValue == null) return null;

var typeMapping = GetSubTypeMapping(parentType);
if (typeMapping.Any())
{
return GetTypeFromMapping(typeMapping, discriminatorValue);
}
return GetTypeByName(discriminatorValue as string, parentType);
}

private static Type GetTypeByName(string typeName, Type parentType)
{
if (typeName == null)
return null;

var insideAssembly = parentType.GetTypeInfo().Assembly;

var typeByName = insideAssembly.GetType(typeName);
if (typeByName == null)
{
var searchLocation = parentType.FullName.Substring(0, parentType.FullName.Length - parentType.Name.Length);
typeByName = insideAssembly.GetType(searchLocation + typeName, false, true);
}
return typeByName;
}

private static Type GetTypeFromMapping(IReadOnlyDictionary<object, Type> typeMapping, object discriminatorValue)
{
var targetlookupValueType = typeMapping.First().Key.GetType();
var lookupValue = ConvertJsonValueToType(discriminatorValue, targetlookupValueType);

Type targetType;
return typeMapping.TryGetValue(lookupValue, out targetType) ? targetType : null;
}

private static Dictionary<object, Type> GetSubTypeMapping(Type type)
{
return type.GetTypeInfo().GetCustomAttributes<KnownSubTypeAttribute>().ToDictionary(x => x.AssociatedValue, x => x.SubType);
}

private static object ConvertJsonValueToType(object objectType, Type targetlookupValueType)
{
if (targetlookupValueType.GetTypeInfo().IsEnum)
return Enum.ToObject(targetlookupValueType, objectType);

return Convert.ChangeType(objectType, targetlookupValueType);
}

protected object _ReadJson(JsonReader reader, Type objectType, object existingValue, JsonSerializer serializer)
{
_reader = reader;
_isInsideRead = true;
try
{
return serializer.Deserialize(reader, objectType);
}
finally
{
_isInsideRead = false;
}
}
}
}
34 changes: 17 additions & 17 deletions modules/swagger-codegen/src/main/resources/csharp/Solution.mustache
Original file line number Diff line number Diff line change
Expand Up @@ -7,21 +7,21 @@ EndProject
{{^excludeTests}}Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "{{testPackageName}}", "src\{{testPackageName}}\{{testPackageName}}.csproj", "{19F1DEBC-DE5E-4517-8062-F000CD499087}"
EndProject
{{/excludeTests}}Global
GlobalSection(SolutionConfigurationPlatforms) = preSolution
Debug|Any CPU = Debug|Any CPU
Release|Any CPU = Release|Any CPU
EndGlobalSection
GlobalSection(ProjectConfigurationPlatforms) = postSolution
{{packageGuid}}.Debug|Any CPU.ActiveCfg = Debug|Any CPU
{{packageGuid}}.Debug|Any CPU.Build.0 = Debug|Any CPU
{{packageGuid}}.Release|Any CPU.ActiveCfg = Release|Any CPU
{{packageGuid}}.Release|Any CPU.Build.0 = Release|Any CPU
{19F1DEBC-DE5E-4517-8062-F000CD499087}.Debug|Any CPU.ActiveCfg = Debug|Any CPU
{19F1DEBC-DE5E-4517-8062-F000CD499087}.Debug|Any CPU.Build.0 = Debug|Any CPU
{19F1DEBC-DE5E-4517-8062-F000CD499087}.Release|Any CPU.ActiveCfg = Release|Any CPU
{19F1DEBC-DE5E-4517-8062-F000CD499087}.Release|Any CPU.Build.0 = Release|Any CPU
EndGlobalSection
GlobalSection(SolutionProperties) = preSolution
HideSolutionNode = FALSE
EndGlobalSection
GlobalSection(SolutionConfigurationPlatforms) = preSolution
Debug|Any CPU = Debug|Any CPU
Release|Any CPU = Release|Any CPU
EndGlobalSection
GlobalSection(ProjectConfigurationPlatforms) = postSolution
{{packageGuid}}.Debug|Any CPU.ActiveCfg = Debug|Any CPU
{{packageGuid}}.Debug|Any CPU.Build.0 = Debug|Any CPU
{{packageGuid}}.Release|Any CPU.ActiveCfg = Release|Any CPU
{{packageGuid}}.Release|Any CPU.Build.0 = Release|Any CPU
{19F1DEBC-DE5E-4517-8062-F000CD499087}.Debug|Any CPU.ActiveCfg = Debug|Any CPU
{19F1DEBC-DE5E-4517-8062-F000CD499087}.Debug|Any CPU.Build.0 = Debug|Any CPU
{19F1DEBC-DE5E-4517-8062-F000CD499087}.Release|Any CPU.ActiveCfg = Release|Any CPU
{19F1DEBC-DE5E-4517-8062-F000CD499087}.Release|Any CPU.Build.0 = Release|Any CPU
EndGlobalSection
GlobalSection(SolutionProperties) = preSolution
HideSolutionNode = FALSE
EndGlobalSection
EndGlobal
Original file line number Diff line number Diff line change
Expand Up @@ -12,6 +12,13 @@ using System.Collections.ObjectModel;
using System.Runtime.Serialization;
using Newtonsoft.Json;
using Newtonsoft.Json.Converters;
{{#models}}
{{#model}}
{{#discriminator}}
using JsonSubTypes;
{{/discriminator}}
{{/model}}
{{/models}}
{{^netStandard}}
{{#generatePropertyChanged}}
using PropertyChanged;
Expand Down
Loading