Welcome to mirror list, hosted at ThFree Co, Russian Federation.

github.com/aspnet/MessagePack-CSharp.git - Unnamed repository; edit this file 'description' to name the repository.
summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorpCYSl5EDgo <31692496+pCYSl5EDgo@users.noreply.github.com>2022-02-13 00:14:41 +0300
committerGitHub <noreply@github.com>2022-02-13 00:14:41 +0300
commit8da2ab05f9cc1b1c2c3dd5e32a57ec57ecb4dbd8 (patch)
treeab791d4d8e610c6249b64b4ae62e34baa11b7980
parent71a223ac73b9e91a82ecbcdf4119f47d1262711a (diff)
Fix nullable annotation errorneous handling (#1395)
* Fix nullable member file name handling Generating multiple files including the letter '?'. Invalid file name char should be avoided.
-rw-r--r--global.json2
-rw-r--r--sandbox/TestData2/A.cs3
-rw-r--r--sandbox/TestData2/B.cs3
-rw-r--r--sandbox/TestData2/C.cs3
-rw-r--r--src/MessagePack.GeneratorCore/CodeAnalysis/TypeCollector.cs7
-rw-r--r--src/MessagePack.GeneratorCore/CodeGenerator.cs72
6 files changed, 79 insertions, 11 deletions
diff --git a/global.json b/global.json
index d46619b0..2645bb53 100644
--- a/global.json
+++ b/global.json
@@ -1,6 +1,6 @@
{
"sdk": {
- "version": "6.0.101",
+ "version": "6.0.102",
"rollForward": "patch",
"allowPrerelease": false
}
diff --git a/sandbox/TestData2/A.cs b/sandbox/TestData2/A.cs
index d32265ab..a7eeef9d 100644
--- a/sandbox/TestData2/A.cs
+++ b/sandbox/TestData2/A.cs
@@ -3,11 +3,12 @@
#pragma warning disable SA1307 // Accessible fields should begin with upper-case letter
#pragma warning disable SA1401 // Fields should be private
+#nullable enable
namespace TestData2;
[MessagePackObject(true)]
public class A
{
- public int a; public List<B> bs; public C c;
+ public int a; public List<B?>? bs; public C? c;
}
diff --git a/sandbox/TestData2/B.cs b/sandbox/TestData2/B.cs
index 70e9f358..d9c4029e 100644
--- a/sandbox/TestData2/B.cs
+++ b/sandbox/TestData2/B.cs
@@ -3,11 +3,12 @@
#pragma warning disable SA1307 // Accessible fields should begin with upper-case letter
#pragma warning disable SA1401 // Fields should be private
+#nullable enable
namespace TestData2;
[MessagePackObject(true)]
public class B
{
- public List<A> ass; public C c; public int a;
+ public List<A?>? ass; public C? c; public int a;
}
diff --git a/sandbox/TestData2/C.cs b/sandbox/TestData2/C.cs
index 5de4a080..741517ff 100644
--- a/sandbox/TestData2/C.cs
+++ b/sandbox/TestData2/C.cs
@@ -3,11 +3,12 @@
#pragma warning disable SA1307 // Accessible fields should begin with upper-case letter
#pragma warning disable SA1401 // Fields should be private
+#nullable enable
namespace TestData2;
[MessagePackObject(true)]
public class C
{
- public B b; public int a;
+ public B? b; public int a;
}
diff --git a/src/MessagePack.GeneratorCore/CodeAnalysis/TypeCollector.cs b/src/MessagePack.GeneratorCore/CodeAnalysis/TypeCollector.cs
index d2537dcd..935ceb87 100644
--- a/src/MessagePack.GeneratorCore/CodeAnalysis/TypeCollector.cs
+++ b/src/MessagePack.GeneratorCore/CodeAnalysis/TypeCollector.cs
@@ -971,10 +971,11 @@ namespace MessagePackCompiler.CodeAnalysis
{
var name = type.ContainingType is object ? GetMinimallyQualifiedClassName(type.ContainingType) + "_" : string.Empty;
name += type.ToDisplayString(SymbolDisplayFormat.MinimallyQualifiedFormat);
- name = name.Replace(".", "_");
- name = name.Replace("<", "_");
- name = name.Replace(">", "_");
+ name = name.Replace('.', '_');
+ name = name.Replace('<', '_');
+ name = name.Replace('>', '_');
name = Regex.Replace(name, @"\[([,])*\]", match => $"Array{match.Length - 1}");
+ name = name.Replace("?", string.Empty);
return name;
}
diff --git a/src/MessagePack.GeneratorCore/CodeGenerator.cs b/src/MessagePack.GeneratorCore/CodeGenerator.cs
index f9654693..1f48973e 100644
--- a/src/MessagePack.GeneratorCore/CodeGenerator.cs
+++ b/src/MessagePack.GeneratorCore/CodeGenerator.cs
@@ -2,6 +2,7 @@
// Licensed under the MIT license. See LICENSE file in the project root for full license information.
using System;
+using System.Collections.Generic;
using System.Diagnostics;
using System.IO;
using System.Linq;
@@ -16,6 +17,8 @@ namespace MessagePackCompiler
{
public class CodeGenerator
{
+ private static readonly HashSet<char> InvalidFileCharSet = new(Path.GetInvalidFileNameChars());
+
private static readonly Encoding NoBomUtf8 = new UTF8Encoding(false);
private readonly Action<string> logger;
@@ -212,15 +215,76 @@ namespace MessagePackCompiler
private Task OutputToDirAsync(string dir, string ns, string name, string multipleOutSymbol, string text)
{
- if (multipleOutSymbol == string.Empty)
+ var builder = new StringBuilder();
+ void AppendDir(string dir)
+ {
+ if (dir.Length != 0)
+ {
+ builder.Append(dir);
+ if (dir[dir.Length - 1] != Path.DirectorySeparatorChar && dir[dir.Length - 1] != Path.AltDirectorySeparatorChar)
+ {
+ builder.Append(Path.DirectorySeparatorChar);
+ }
+ }
+ }
+
+ void AppendChar(char c)
+ {
+ if (c == '.' || InvalidFileCharSet.Contains(c))
+ {
+ builder.Append('_');
+ }
+ else
+ {
+ builder.Append(c);
+ }
+ }
+
+ void Append(string text)
{
- return OutputAsync(Path.Combine(dir, $"{ns}_{name}".Replace(".", "_").Replace("global::", string.Empty) + ".cs"), text);
+ var span = text.AsSpan();
+ while (!span.IsEmpty)
+ {
+ var index = span.IndexOf("global::".AsSpan());
+ if (index == -1)
+ {
+ foreach (var c in span)
+ {
+ AppendChar(c);
+ }
+
+ break;
+ }
+
+ if (index == 0)
+ {
+ span = span.Slice("global::".Length);
+ continue;
+ }
+
+ foreach (var c in span.Slice(0, index))
+ {
+ AppendChar(c);
+ }
+
+ span = span.Slice(index + "global::".Length);
+ }
}
- else
+
+ AppendDir(dir);
+
+ if (!string.IsNullOrWhiteSpace(multipleOutSymbol))
{
text = $"#if {multipleOutSymbol}" + Environment.NewLine + text + Environment.NewLine + "#endif";
- return OutputAsync(Path.Combine(dir, MultiSymbolToSafeFilePath(multipleOutSymbol), $"{ns}_{name}".Replace(".", "_").Replace("global::", string.Empty) + ".cs"), text);
+ AppendDir(MultiSymbolToSafeFilePath(multipleOutSymbol));
}
+
+ Append(ns);
+ builder.Append('_');
+ Append(name);
+ builder.Append(".cs");
+
+ return OutputAsync(builder.ToString(), text);
}
private Task OutputAsync(string path, string text)