/// <summary>Helper: put the buffer into a MemoryStream and create a new instance to deserializing into</summary> public static DescriptorProto Deserialize(byte[] buffer) { DescriptorProto instance = new DescriptorProto(); using (var ms = new MemoryStream(buffer)) Deserialize(ms, instance); return instance; }
/// <summary> /// Obtain a set of all names defined for a message /// </summary> protected HashSet <string> BuildConflicts(DescriptorProto parent, bool includeDescendents) { var conflicts = new HashSet <string>( IsCaseSensitive ? StringComparer.OrdinalIgnoreCase : StringComparer.Ordinal); if (parent != null) { conflicts.Add(GetName(parent)); if (includeDescendents) { foreach (var type in parent.NestedTypes) { conflicts.Add(GetName(type)); } foreach (var type in parent.EnumTypes) { conflicts.Add(GetName(type)); } } } return(conflicts); }
private void RecursiveAnalyzeMessageDescriptor(DescriptorProto messageType, ProtoNode protoNode, string packagePath) { protoNode.Types.Add(GetOrCreateTypeNode(GetPackagePath(packagePath, messageType.name), protoNode.Proto, messageType)); foreach (var extension in messageType.extension) { if (!string.IsNullOrEmpty(extension.extendee)) { protoNode.Types.Add(GetOrCreateTypeNode(GetPackagePath(packagePath, extension.extendee))); } } foreach (var enumType in messageType.enum_type) { protoNode.Types.Add(GetOrCreateTypeNode( GetPackagePath(GetPackagePath(packagePath, messageType.name), enumType.name), protoNode.Proto, enumType)); } foreach (var field in messageType.field) { if (IsNamedType(field.type) && !string.IsNullOrEmpty(field.type_name)) { protoNode.Types.Add(GetOrCreateTypeNode(GetPackagePath(packagePath, field.type_name))); } if (!string.IsNullOrEmpty(field.extendee)) { protoNode.Types.Add(GetOrCreateTypeNode(GetPackagePath(packagePath, field.extendee))); } } foreach (var nested in messageType.nested_type) { RecursiveAnalyzeMessageDescriptor(nested, protoNode, GetPackagePath(packagePath, messageType.name)); } }
private static void ConstructMethod(CodeTypeDeclaration myClass, DescriptorProto message, Dictionary <CodeMemberField, FieldDescriptorProto> fieldInfo) { //Add Construct Method CodeStatementCollection constructerStatements = new CodeStatementCollection(); foreach (CodeTypeMember field in myClass.Members) { if (field is CodeMemberField) { CodeMemberField curField = field as CodeMemberField; FieldDescriptorProto fieldDescriptorProto = fieldInfo[curField]; var leftVariable = new CodeVariableReferenceExpression(curField.Name); string rightVariableString; if (fieldDescriptorProto.Label.Equals(FieldDescriptorProto.Types.Label.LABEL_REPEATED)) { rightVariableString = $"new {curField.Type.BaseType}()"; } else { rightVariableString = GenerateInitialString(fieldDescriptorProto, curField.Type.BaseType); } constructerStatements.Add(new CodeAssignStatement(leftVariable, new CodeSnippetExpression(rightVariableString))); } } //读取oneof if (message.UnknownFields[8].LengthDelimitedList.Count > 0) { foreach (var oneOfMessage in message.UnknownFields[8].LengthDelimitedList) { string str = oneOfMessage.ParseString(); string name = str.ToCamel(); string finalString = $"{message.Name}.{name}OneofCase"; constructerStatements.Add(new CodeAssignStatement(new CodeSnippetExpression(name), new CodeSnippetExpression($"({finalString})0"))); } } AddCodeConstructor(myClass, ToWrapperString(message.Name), constructerStatements); }
internal static OneOfStub[] Build(GeneratorContext context, DescriptorProto message) { if (message.OneofDecls.Count == 0) { return(null); } var stubs = new OneOfStub[message.OneofDecls.Count]; int index = 0; foreach (var decl in message.OneofDecls) { stubs[index] = new OneOfStub(decl, index); index++; } foreach (var field in message.Fields) { if (field.ShouldSerializeOneofIndex()) { stubs[field.OneofIndex].AccountFor(field.type, field.TypeName); } } return(stubs); }
public Descriptor(DescriptorPool pool, ProtoBase parent, DescriptorProto def) { Define = def; base.Init(pool, parent); // 字段 for (int i = 0; i < def.field.Count; i++) { var fieldDef = def.field[i]; var fieldD = new FieldDescriptor(this, fieldDef); _fieldByName.Add(fieldDef.name, fieldD); _fieldByFieldNumber.Add(fieldD.Number, fieldD); } // 内嵌消息 for (int i = 0; i < def.nested_type.Count; i++) { var nestedDef = def.nested_type[i]; var msgD = new Descriptor(pool, this, nestedDef); _nestedMsg.Add(nestedDef.name, msgD); } // 内嵌枚举 for (int i = 0; i < def.enum_type.Count; i++) { var nestedDef = def.enum_type[i]; var enumD = new EnumDescriptor(pool, this, nestedDef); _nestedEnum.Add(nestedDef.name, enumD); } }
/// <summary> /// Start a message /// </summary> protected override void WriteMessageHeader(GeneratorContext ctx, DescriptorProto obj, ref object state) { var name = ctx.NameNormalizer.GetName(obj); var tw = ctx.Write($@"[global::ProtoBuf.ProtoContract("); if (name != obj.Name) { tw.Write($@"Name = @""{obj.Name}"""); } tw.WriteLine(")]"); WriteOptions(ctx, obj.Options); tw = ctx.Write($"{GetAccess(GetAccess(obj))} partial class {Escape(name)}"); if (obj.ExtensionRanges.Count != 0) { tw.Write(" : global::ProtoBuf.IExtensible"); } tw.WriteLine(); ctx.WriteLine("{").Indent(); if (obj.Options?.MessageSetWireFormat == true) { ctx.WriteLine("#error message_set_wire_format is not currently implemented").WriteLine(); } if (obj.ExtensionRanges.Count != 0) { ctx.WriteLine($"private global::ProtoBuf.IExtension {FieldPrefix}extensionData;") .WriteLine($"global::ProtoBuf.IExtension global::ProtoBuf.IExtensible.GetExtensionObject(bool createIfMissing)"); if (ctx.Supports(CSharp6)) { ctx.Indent().WriteLine($"=> global::ProtoBuf.Extensible.GetExtensionObject(ref {FieldPrefix}extensionData, createIfMissing);").Outdent().WriteLine(); } else { ctx.WriteLine("{").Indent().WriteLine($"return global::ProtoBuf.Extensible.GetExtensionObject(ref {FieldPrefix}extensionData, createIfMissing);").Outdent().WriteLine("}"); } } }
/// <summary> /// Get the preferred name for an element /// </summary> protected virtual string GetName(DescriptorProto parent, string preferred, string fallback, bool includeDescendents) { var conflicts = BuildConflicts(parent, includeDescendents); if (!conflicts.Contains(preferred)) { return(preferred); } if (!conflicts.Contains(fallback)) { return(fallback); } var attempt = preferred + "Value"; if (!conflicts.Contains(attempt)) { return(attempt); } attempt = fallback + "Value"; if (!conflicts.Contains(attempt)) { return(attempt); } int i = 1; while (true) { attempt = preferred + i.ToString(); if (!conflicts.Contains(attempt)) { return(attempt); } } }
protected override void WriteReadFun(GeneratorContext ctx, DescriptorProto obj, OneOfStub[] oneOfs) { ctx.WriteLine($"public void MergeFrom(byte[] _bytes){"{"}").Indent(); ctx.WriteLine("Google.Protobuf.CodedInputStream input = new Google.Protobuf.CodedInputStream(_bytes);"); ctx.WriteLine("uint tag;"); ctx.WriteLine("while ((tag = input.ReadTag()) != 0) {").Indent(); ctx.WriteLine("switch(tag) {").Indent(); ctx.WriteLine("default:").Indent(); ctx.WriteLine("input.SkipLastField();"); ctx.WriteLine("break;").Outdent(); foreach (var inner in obj.Fields) { WriteFileRead(ctx, inner, oneOfs); } ctx.Outdent().WriteLine("}"); //switch ctx.Outdent().WriteLine("}"); //while ctx.WriteLine("input.Dispose();"); ctx.Outdent().WriteLine("}"); }
/// <summary> /// Start a message /// </summary> protected override void WriteMessageHeader(GeneratorContext ctx, DescriptorProto message, ref object state) { var name = ctx.NameNormalizer.GetName(message); var tw = ctx.Write("<Global.ProtoBuf.ProtoContract("); if (name != message.Name) { tw.Write($@"Name := ""{message.Name}"""); } tw.WriteLine(")> _"); WriteOptions(ctx, message.Options); ctx.WriteLine($"Partial {GetAccess(GetAccess(message))} Class {Escape(name)}"); ctx.Indent().WriteLine("Implements Global.ProtoBuf.IExtensible").WriteLine(); if (message.Options?.MessageSetWireFormat == true) { ctx.WriteLine("REM #error message_set_wire_format is not currently implemented").WriteLine(); } ctx.WriteLine($"Private {FieldPrefix}extensionData As Global.ProtoBuf.IExtension").WriteLine() .WriteLine($"Private Function GetExtensionObject(ByVal createIfMissing As Boolean) As Global.ProtoBuf.IExtension Implements Global.ProtoBuf.IExtensible.GetExtensionObject") .Indent().WriteLine($"Return Global.ProtoBuf.Extensible.GetExtensionObject({FieldPrefix}extensionData, createIfMissing)") .Outdent().WriteLine("End Function").WriteLine(); }
=> obj.Options?.MapEntry ?? false; // don't write this type - use a dictionary instead /// <summary> /// Emit code representing a message type /// </summary> protected virtual void WriteMessage(GeneratorContext ctx, DescriptorProto obj) { object state = null; if (ShouldOmitMessage(ctx, obj, ref state)) { return; } WriteMessageHeader(ctx, obj, ref state); var oneOfs = OneOfStub.Build(ctx, obj); foreach (var inner in obj.Fields) { WriteField(ctx, inner, ref state, oneOfs); } foreach (var inner in obj.NestedTypes) { WriteMessage(ctx, inner); } foreach (var inner in obj.EnumTypes) { WriteEnum(ctx, inner); } if (obj.Extensions.Count != 0) { object extState = null; WriteExtensionsHeader(ctx, obj, ref extState); foreach (var ext in obj.Extensions) { WriteExtension(ctx, ext); } WriteExtensionsFooter(ctx, obj, ref extState); } WriteMessageFooter(ctx, obj, ref state); }
private void PushDescriptorName(DescriptorProto proto) { messageNameStack.Push(proto.name); }
private void DumpDescriptor(DescriptorProto proto, FileDescriptorProto set, StringBuilder sb, int level) { PushDescriptorName(proto); var levelspace = new string('\t', level); sb.AppendLine($"{levelspace}message {proto.name} {{"); foreach (var option in DumpOptions(proto.options)) { sb.AppendLine($"{levelspace}\toption {option.Key} = {option.Value};"); } foreach (var field in proto.nested_type) { DumpDescriptor(field, set, sb, level + 1); } DumpExtensionDescriptor(proto.extension, sb, $"{levelspace}\t"); foreach (var field in proto.enum_type) { DumpEnumDescriptor(field, sb, level + 1); } foreach (var field in proto.field.Where(x => !x.oneof_indexSpecified)) { var enumLookup = new List <EnumDescriptorProto>(); enumLookup.AddRange(set.enum_type); // add global enums enumLookup.AddRange(proto.enum_type); // add this message's nested enums sb.AppendLine($"{levelspace}\t{BuildDescriptorDeclaration(field)}"); } for (var i = 0; i < proto.oneof_decl.Count; i++) { var oneof = proto.oneof_decl[i]; var fields = proto.field.Where(x => x.oneof_indexSpecified && x.oneof_index == i).ToArray(); sb.AppendLine($"{levelspace}\toneof {oneof.name} {{"); foreach (var field in fields) { sb.AppendLine($"{levelspace}\t\t{BuildDescriptorDeclaration(field, emitFieldLabel: false)}"); } sb.AppendLine($"{levelspace}\t}}"); } if (proto.extension_range.Count > 0) { sb.AppendLine(); } foreach (var range in proto.extension_range) { var max = Convert.ToString(range.end); // http://code.google.com/apis/protocolbuffers/docs/proto.html#extensions // If your numbering convention might involve extensions having very large numbers as tags, you can specify // that your extension range goes up to the maximum possible field number using the max keyword: // max is 2^29 - 1, or 536,870,911. if (range.end >= 536870911) { max = "max"; } sb.AppendLine($"{levelspace}\textensions {range.start} to {max};"); } sb.AppendLine($"{levelspace}}}"); sb.AppendLine(); PopDescriptorName(); }
/// <summary> /// End a message /// </summary> protected override void WriteMessageFooter(GeneratorContext ctx, DescriptorProto obj, ref object state) { ctx.Outdent().WriteLine("}").WriteLine(); }
/// <summary>Helper: Serialize with a varint length prefix</summary> public static void SerializeLengthDelimited(Stream stream, DescriptorProto instance) { var data = SerializeToBytes(instance); global::SilentOrbit.ProtocolBuffers.ProtocolParser.WriteUInt32(stream, (uint)data.Length); stream.Write(data, 0, data.Length); }
protected override void WriteExtensionsFooter(GeneratorContext ctx, DescriptorProto message, ref object state) { }
/// <summary>Helper: create a new instance to deserializing into</summary> public static DescriptorProto Deserialize(Stream stream) { DescriptorProto instance = new DescriptorProto(); Deserialize(stream, instance); return instance; }
/// <summary>Serialize the instance into the stream</summary> public static void Serialize(Stream stream, DescriptorProto instance) { var msField = global::SilentOrbit.ProtocolBuffers.ProtocolParser.Stack.Pop(); if (instance.Name != null) { // Key for field: 1, LengthDelimited stream.WriteByte(10); global::SilentOrbit.ProtocolBuffers.ProtocolParser.WriteBytes(stream, Encoding.UTF8.GetBytes(instance.Name)); } if (instance.Field != null) { foreach (var i2 in instance.Field) { // Key for field: 2, LengthDelimited stream.WriteByte(18); msField.SetLength(0); Google.Protobuf.FieldDescriptorProto.Serialize(msField, i2); // Length delimited byte array uint length2 = (uint)msField.Length; global::SilentOrbit.ProtocolBuffers.ProtocolParser.WriteUInt32(stream, length2); msField.WriteTo(stream); } } if (instance.Extension != null) { foreach (var i6 in instance.Extension) { // Key for field: 6, LengthDelimited stream.WriteByte(50); msField.SetLength(0); Google.Protobuf.FieldDescriptorProto.Serialize(msField, i6); // Length delimited byte array uint length6 = (uint)msField.Length; global::SilentOrbit.ProtocolBuffers.ProtocolParser.WriteUInt32(stream, length6); msField.WriteTo(stream); } } if (instance.NestedType != null) { foreach (var i3 in instance.NestedType) { // Key for field: 3, LengthDelimited stream.WriteByte(26); msField.SetLength(0); Google.Protobuf.DescriptorProto.Serialize(msField, i3); // Length delimited byte array uint length3 = (uint)msField.Length; global::SilentOrbit.ProtocolBuffers.ProtocolParser.WriteUInt32(stream, length3); msField.WriteTo(stream); } } if (instance.EnumType != null) { foreach (var i4 in instance.EnumType) { // Key for field: 4, LengthDelimited stream.WriteByte(34); msField.SetLength(0); Google.Protobuf.EnumDescriptorProto.Serialize(msField, i4); // Length delimited byte array uint length4 = (uint)msField.Length; global::SilentOrbit.ProtocolBuffers.ProtocolParser.WriteUInt32(stream, length4); msField.WriteTo(stream); } } if (instance.ExtensionRangeField != null) { foreach (var i5 in instance.ExtensionRangeField) { // Key for field: 5, LengthDelimited stream.WriteByte(42); msField.SetLength(0); Google.Protobuf.DescriptorProto.ExtensionRange.Serialize(msField, i5); // Length delimited byte array uint length5 = (uint)msField.Length; global::SilentOrbit.ProtocolBuffers.ProtocolParser.WriteUInt32(stream, length5); msField.WriteTo(stream); } } if (instance.Options != null) { // Key for field: 7, LengthDelimited stream.WriteByte(58); msField.SetLength(0); Google.Protobuf.MessageOptions.Serialize(msField, instance.Options); // Length delimited byte array uint length7 = (uint)msField.Length; global::SilentOrbit.ProtocolBuffers.ProtocolParser.WriteUInt32(stream, length7); msField.WriteTo(stream); } global::SilentOrbit.ProtocolBuffers.ProtocolParser.Stack.Push(msField); }
/// <summary> /// Emit code beginning a constructor, if one is required /// </summary> /// <returns>true if a constructor is required</returns> protected virtual bool WriteContructorHeader(GeneratorContext ctx, DescriptorProto obj, ref object state) => false;
/// <summary> /// Emit code terminating a constructor, if one is required /// </summary> protected virtual void WriteConstructorFooter(GeneratorContext ctx, DescriptorProto obj, ref object state) { }
void DumpDescriptor(FileDescriptorProto source, DescriptorProto proto, StringBuilder sb, int level, ref bool marker) { PushDescriptorName(proto); var levelspace = new string( '\t', level ); var innerMarker = false; AppendHeadingSpace(sb, ref marker); sb.AppendLine($"{levelspace}message {proto.name} {{"); var options = DumpOptions(source, proto.options); foreach (var option in options) { AppendHeadingSpace(sb, ref innerMarker); sb.AppendLine($"{levelspace}\toption {option.Key} = {option.Value};"); } if (options.Count > 0) { innerMarker = true; } if (proto.extension.Count > 0) { DumpExtensionDescriptors(source, proto.extension, sb, level + 1, ref innerMarker); } foreach (var field in proto.nested_type) { DumpDescriptor(source, field, sb, level + 1, ref innerMarker); } foreach (var field in proto.enum_type) { DumpEnumDescriptor(source, field, sb, level + 1, ref innerMarker); } var rootFields = proto.field.Where(x => !x.oneof_indexSpecified).ToList(); foreach (var field in rootFields) { AppendHeadingSpace(sb, ref innerMarker); sb.AppendLine($"{levelspace}\t{BuildDescriptorDeclaration( source, field )}"); } if (rootFields.Count > 0) { innerMarker = true; } for (var i = 0; i < proto.oneof_decl.Count; i++) { var oneof = proto.oneof_decl[i]; var fields = proto.field.Where(x => x.oneof_indexSpecified && x.oneof_index == i).ToArray(); AppendHeadingSpace(sb, ref innerMarker); sb.AppendLine($"{levelspace}\toneof {oneof.name} {{"); foreach (var field in fields) { sb.AppendLine( $"{levelspace}\t\t{BuildDescriptorDeclaration( source, field, emitFieldLabel: false )}"); } sb.AppendLine($"{levelspace}\t}}"); innerMarker = true; } foreach (var range in proto.extension_range) { var max = Convert.ToString(range.end); // http://code.google.com/apis/protocolbuffers/docs/proto.html#extensions // If your numbering convention might involve extensions having very large numbers as tags, you can specify // that your extension range goes up to the maximum possible field number using the max keyword: // max is 2^29 - 1, or 536,870,911. if (range.end >= 536870911) { max = "max"; } AppendHeadingSpace(sb, ref innerMarker); sb.AppendLine($"{levelspace}\textensions {range.start} to {max};"); } sb.AppendLine($"{levelspace}}}"); marker = true; PopDescriptorName(); }
private static void OutputBaseFromWrapper(CodeTypeDeclaration myClass, DescriptorProto message, Dictionary <CodeMemberField, FieldDescriptorProto> fieldInfo) { //Add OutputBaseFromWrapper CodeStatementCollection outputBaseFromWrapperStatements = new CodeStatementCollection(); outputBaseFromWrapperStatements.Add(new CodeAssignStatement(new CodeVariableReferenceExpression($"{message.Name} { baseString }"), new CodeVariableReferenceExpression($"new {message.Name}()"))); foreach (CodeTypeMember field in myClass.Members) { if (field is CodeMemberField) { CodeMemberField curField = field as CodeMemberField; FieldDescriptorProto fieldDescriptorProto = fieldInfo[curField]; var leftVariable = new CodeVariableReferenceExpression($"{baseString}.{curField.Name}"); string rightVariableString = ""; if (fieldDescriptorProto.Label.Equals(FieldDescriptorProto.Types.Label.LABEL_REPEATED)) { string tempClassStr = fieldDescriptorProto.TypeName; if (fieldDescriptorProto.Type.Equals(FieldDescriptorProto.Types.Type.TYPE_MESSAGE) || fieldDescriptorProto.Type.Equals(FieldDescriptorProto.Types.Type.TYPE_ENUM)) { if (tempClassStr.Split('.').Length == 3) { tempClassStr = tempClassStr.Split('.')[2]; } else { Console.WriteLine($"Wrong Length in {message.Name} : {fieldDescriptorProto.TypeName}"); } } else if (fieldDescriptorProto.Type.Equals(FieldDescriptorProto.Types.Type.TYPE_BYTES)) { tempClassStr = "Google.Protobuf.ByteString"; } else { try { tempClassStr = $"{typeMap[fieldDescriptorProto.Type]}"; } catch (Exception) { Console.WriteLine($"No Map in {fieldDescriptorProto.Type.ToString()}"); } } string forVariableStr = "pos"; string tempVar = "tempVar"; string firstRightVariavleString = ""; CodeStatement firstStatement; CodeStatement codeStatement; CodeStatement lastStatement; //get first firstRightVariavleString = GenerateInitialString(fieldDescriptorProto, tempClassStr); firstStatement = new CodeAssignStatement(new CodeVariableReferenceExpression($"{tempClassStr} {tempVar}"), new CodeSnippetExpression(firstRightVariavleString)); if (fieldDescriptorProto.Type.Equals(FieldDescriptorProto.Types.Type.TYPE_BYTES)) { firstStatement = new CodeAssignStatement(new CodeVariableReferenceExpression($"{tempClassStr} {tempVar}"), new CodeSnippetExpression($"Google.Protobuf.ByteString.CopyFrom({firstRightVariavleString})")); } //get mid rightVariableString = GenerateOutputString(fieldDescriptorProto, $"{curField.Name}[{forVariableStr}]"); codeStatement = new CodeAssignStatement(new CodeVariableReferenceExpression(tempVar), new CodeVariableReferenceExpression(rightVariableString)); //get last lastStatement = new CodeSnippetStatement($"\t\t\t\t{baseString}.{curField.Name}.Add({tempVar});"); // Creates a for loop that sets testInt to 0 and continues incrementing testInt by 1 each loop until testInt is not less than 10. CodeIterationStatement forLoop = new CodeIterationStatement( // initStatement parameter for pre-loop initialization. new CodeVariableDeclarationStatement(typeof(int), forVariableStr, new CodePrimitiveExpression(0)), // testExpression parameter to test for continuation condition. new CodeBinaryOperatorExpression(new CodeVariableReferenceExpression(forVariableStr), CodeBinaryOperatorType.LessThan, new CodeSnippetExpression($"{curField.Name}.Count")), // incrementStatement parameter indicates statement to execute after each iteration. new CodeAssignStatement(new CodeVariableReferenceExpression(forVariableStr), new CodeBinaryOperatorExpression( new CodeVariableReferenceExpression(forVariableStr), CodeBinaryOperatorType.Add, new CodePrimitiveExpression(1))), // statements parameter contains the statements to execute during each interation of the loop. new CodeStatement[] { firstStatement, codeStatement, lastStatement }); outputBaseFromWrapperStatements.Add(forLoop); } else { CodeStatement codeStatement; rightVariableString = GenerateOutputString(fieldDescriptorProto, curField.Name); codeStatement = new CodeAssignStatement(leftVariable, new CodeVariableReferenceExpression(rightVariableString)); outputBaseFromWrapperStatements.Add(codeStatement); } } } //读取oneof if (message.UnknownFields[8].LengthDelimitedList.Count > 0) { foreach (var oneOfMessage in message.UnknownFields[8].LengthDelimitedList) { string str = oneOfMessage.ParseString(); string name = str.ToCamel(); string className = $"{message.Name}.{name}OneofCase"; string finalString = ""; foreach (CodeTypeMember field in myClass.Members) { if (field is CodeMemberField) { CodeMemberField curField = field as CodeMemberField; FieldDescriptorProto fieldDescriptorProto = fieldInfo[curField]; var leftVariable = $"{baseString}.{curField.Name}"; string rightVariableString = ""; rightVariableString = GenerateOutputString(fieldDescriptorProto, curField.Name); finalString += $@" case {className}.{curField.Name}: {leftVariable} = {rightVariableString}; break;"; } } outputBaseFromWrapperStatements.Add(new CodeSnippetStatement($@" {baseString}.Clear{name}(); switch({name}) {{{finalString} }}")); } } outputBaseFromWrapperStatements.Add(new CodeVariableReferenceExpression($"return { baseString }")); AddPublicMethod(myClass, "OutputBaseFromWrapper", outputBaseFromWrapperStatements, new CodeTypeReference(message.Name)); }
private static void LoadBaseToWrapper(CodeTypeDeclaration myClass, DescriptorProto message, Dictionary <CodeMemberField, FieldDescriptorProto> fieldInfo) { //Add LoadBaseToWrapper Method CodeStatementCollection loadBaseToWrapperStatements = new CodeStatementCollection(); foreach (CodeTypeMember field in myClass.Members) { if (field is CodeMemberField) { CodeMemberField curField = field as CodeMemberField; FieldDescriptorProto fieldDescriptorProto = fieldInfo[curField]; var leftVariable = new CodeVariableReferenceExpression(curField.Name); string rightVariableString = ""; if (fieldDescriptorProto.Label.Equals(FieldDescriptorProto.Types.Label.LABEL_REPEATED)) { string tempClassStr = fieldDescriptorProto.TypeName; loadBaseToWrapperStatements.Add(new CodeSnippetStatement($"\t\t\t{curField.Name}.Clear();")); if (fieldDescriptorProto.Type.Equals(FieldDescriptorProto.Types.Type.TYPE_MESSAGE) || fieldDescriptorProto.Type.Equals(FieldDescriptorProto.Types.Type.TYPE_ENUM)) { if (tempClassStr.Split('.').Length == 3) { tempClassStr = tempClassStr.Split('.')[2]; if (fieldDescriptorProto.Type.Equals(FieldDescriptorProto.Types.Type.TYPE_MESSAGE)) { tempClassStr = ToWrapperString(tempClassStr); } } else { Console.WriteLine($"Wrong Length in {message.Name} : {fieldDescriptorProto.TypeName}"); } } else { try { tempClassStr = $"{typeMap[fieldDescriptorProto.Type]}"; } catch (Exception) { Console.WriteLine($"No Map in {fieldDescriptorProto.Type.ToString()}"); } } string forVariableStr = "pos"; string tempVar = "tempVar"; string firstRightVariavleString; CodeStatement firstStatement; CodeStatement codeStatement; CodeStatement lastStatement; //get first firstRightVariavleString = GenerateInitialString(fieldDescriptorProto, tempClassStr); firstStatement = new CodeAssignStatement(new CodeVariableReferenceExpression($"{tempClassStr} {tempVar}"), new CodeSnippetExpression(firstRightVariavleString)); //get mid if (fieldDescriptorProto.Type.Equals(FieldDescriptorProto.Types.Type.TYPE_MESSAGE)) { rightVariableString = $"{tempVar}.LoadBaseToWrapper({baseString}.{curField.Name}[{forVariableStr}]);"; codeStatement = new CodeSnippetStatement($"\t\t\t\t\t{rightVariableString}"); } else if (fieldDescriptorProto.Type.Equals(FieldDescriptorProto.Types.Type.TYPE_BYTES)) { rightVariableString = $"{baseString}.{curField.Name}[{forVariableStr}].ToByteArray()"; codeStatement = new CodeAssignStatement(new CodeVariableReferenceExpression(tempVar), new CodeVariableReferenceExpression(rightVariableString)); } else { rightVariableString = $"{baseString}.{curField.Name}[{forVariableStr}]"; codeStatement = new CodeAssignStatement(new CodeVariableReferenceExpression(tempVar), new CodeVariableReferenceExpression(rightVariableString)); } //get last lastStatement = new CodeSnippetStatement($"\t\t\t\t\t{curField.Name}.Add({tempVar});"); //生成循环 // Creates a for loop that sets testInt to 0 and continues incrementing testInt by 1 each loop until testInt is not less than 10. CodeIterationStatement forLoop = new CodeIterationStatement( // initStatement parameter for pre-loop initialization. new CodeVariableDeclarationStatement(typeof(int), forVariableStr, new CodePrimitiveExpression(0)), // testExpression parameter to test for continuation condition. new CodeBinaryOperatorExpression(new CodeVariableReferenceExpression(forVariableStr), CodeBinaryOperatorType.LessThan, new CodeSnippetExpression($"{baseString}.{curField.Name}.Count")), // incrementStatement parameter indicates statement to execute after each iteration. new CodeAssignStatement(new CodeVariableReferenceExpression(forVariableStr), new CodeBinaryOperatorExpression( new CodeVariableReferenceExpression(forVariableStr), CodeBinaryOperatorType.Add, new CodePrimitiveExpression(1))), // statements parameter contains the statements to execute during each interation of the loop. new CodeStatement[] { firstStatement, codeStatement, lastStatement }); // Create a CodeConditionStatement that tests a boolean value named boolean. CodeConditionStatement conditionalStatement = new CodeConditionStatement( // The condition to test. new CodeVariableReferenceExpression($"{baseString}.{curField.Name} != null"), // The statements to execute if the condition evaluates to true. new CodeStatement[] { forLoop }); loadBaseToWrapperStatements.Add(conditionalStatement); } else { CodeStatement codeStatement; if (fieldDescriptorProto.Type.Equals(FieldDescriptorProto.Types.Type.TYPE_MESSAGE)) { rightVariableString = $"\t\t\t{curField.Name}.LoadBaseToWrapper({baseString}.{curField.Name});"; codeStatement = new CodeSnippetStatement(rightVariableString); // Create a CodeConditionStatement that tests a boolean value named boolean. codeStatement = new CodeConditionStatement( // The condition to test. new CodeVariableReferenceExpression($"{baseString}.{curField.Name} != null"), // The statements to execute if the condition evaluates to true. new CodeStatement[] { codeStatement }); } else if (fieldDescriptorProto.Type.Equals(FieldDescriptorProto.Types.Type.TYPE_BYTES)) { rightVariableString = $"{baseString}.{curField.Name}.ToByteArray()"; codeStatement = new CodeAssignStatement(leftVariable, new CodeVariableReferenceExpression(rightVariableString)); } else { rightVariableString = $"{baseString}.{curField.Name}"; codeStatement = new CodeAssignStatement(leftVariable, new CodeVariableReferenceExpression(rightVariableString)); } loadBaseToWrapperStatements.Add(codeStatement); } } } //读取oneof if (message.UnknownFields[8].LengthDelimitedList.Count > 0) { foreach (var oneOfMessage in message.UnknownFields[8].LengthDelimitedList) { string str = oneOfMessage.ParseString(); string name = str.ToCamel(); string finalString = $"{message.Name}.{name}OneofCase"; loadBaseToWrapperStatements.Add(new CodeAssignStatement(new CodeSnippetExpression(name), new CodeSnippetExpression($"{baseString}.{name}Case"))); } } AddPublicMethod(myClass, "LoadBaseToWrapper", loadBaseToWrapperStatements, new CodeTypeReference(typeof(void)), new string[] { message.Name }, new string[] { baseString }); }
private void DumpDescriptor(DescriptorProto proto, FileDescriptorProto set, StringBuilder sb, int level) { PushDescriptorName(proto); string levelspace = new String('\t', level); sb.AppendLine(levelspace + "message " + proto.name + " {"); foreach (var option in DumpOptions(proto.options)) { sb.AppendLine(levelspace + "\toption " + option.Key + " = " + option.Value + ";"); } foreach (DescriptorProto field in proto.nested_type) { DumpDescriptor(field, set, sb, level + 1); } DumpExtensionDescriptor(proto.extension, sb, levelspace + '\t'); foreach (EnumDescriptorProto field in proto.enum_type) { DumpEnumDescriptor(field, sb, level + 1); } foreach (FieldDescriptorProto field in proto.field) { var enumLookup = new List <EnumDescriptorProto>(); enumLookup.AddRange(set.enum_type); // add global enums enumLookup.AddRange(proto.enum_type); // add this message's nested enums sb.AppendLine(levelspace + "\t" + BuildDescriptorDeclaration(field)); } if (proto.extension_range.Count > 0) { sb.AppendLine(); } foreach (DescriptorProto.ExtensionRange range in proto.extension_range) { string max = Convert.ToString(range.end); // http://code.google.com/apis/protocolbuffers/docs/proto.html#extensions // If your numbering convention might involve extensions having very large numbers as tags, you can specify // that your extension range goes up to the maximum possible field number using the max keyword: // max is 2^29 - 1, or 536,870,911. if (range.end >= 536870911) { max = "max"; } sb.AppendLine(levelspace + "\textensions " + range.start + " to " + max + ";"); } sb.AppendLine(levelspace + "}"); sb.AppendLine(); PopDescriptorName(); }
/// <summary> /// Ends an extensions block /// </summary> protected override void WriteExtensionsFooter(GeneratorContext ctx, DescriptorProto obj, ref object state) { // ctx.Outdent().WriteLine("End Module"); }
protected override void WriteMessageHeader(GeneratorContext ctx, DescriptorProto obj, ref object state) { throw new NotImplementedException(); }
/// <summary>Helper: create a new instance to deserializing into</summary> public static DescriptorProto DeserializeLength(Stream stream, int length) { DescriptorProto instance = new DescriptorProto(); DeserializeLength(stream, length, instance); return instance; }
/// <summary> /// Ends an extensions block /// </summary> protected override void WriteExtensionsFooter(GeneratorContext ctx, DescriptorProto message, ref object state) { ctx.Outdent().WriteLine("}"); }
/// <summary>Helper: create a new instance to deserializing into</summary> public static DescriptorProto DeserializeLengthDelimited(Stream stream) { DescriptorProto instance = new DescriptorProto(); DeserializeLengthDelimited(stream, instance); return instance; }
protected abstract void WriteReadFun(GeneratorContext ctx, DescriptorProto obj, OneOfStub[] oneOfs);
/// <summary>Serialize the instance into the stream</summary> public static void Serialize(Stream stream, DescriptorProto instance) { if (instance.Name != null) { // Key for field: 1, LengthDelimited stream.WriteByte(10); global::SilentOrbit.ProtocolBuffers.ProtocolParser.WriteBytes(stream, Encoding.UTF8.GetBytes(instance.Name)); } if (instance.Field != null) { foreach (var i2 in instance.Field) { // Key for field: 2, LengthDelimited stream.WriteByte(18); using (var ms2 = new MemoryStream()) { Google.protobuf.FieldDescriptorProto.Serialize(ms2, i2); // Length delimited byte array uint ms2Length = (uint)ms2.Length; global::SilentOrbit.ProtocolBuffers.ProtocolParser.WriteUInt32(stream, ms2Length); stream.Write(ms2.GetBuffer(), 0, (int)ms2Length); } } } if (instance.Extension != null) { foreach (var i6 in instance.Extension) { // Key for field: 6, LengthDelimited stream.WriteByte(50); using (var ms6 = new MemoryStream()) { Google.protobuf.FieldDescriptorProto.Serialize(ms6, i6); // Length delimited byte array uint ms6Length = (uint)ms6.Length; global::SilentOrbit.ProtocolBuffers.ProtocolParser.WriteUInt32(stream, ms6Length); stream.Write(ms6.GetBuffer(), 0, (int)ms6Length); } } } if (instance.NestedType != null) { foreach (var i3 in instance.NestedType) { // Key for field: 3, LengthDelimited stream.WriteByte(26); using (var ms3 = new MemoryStream()) { Google.protobuf.DescriptorProto.Serialize(ms3, i3); // Length delimited byte array uint ms3Length = (uint)ms3.Length; global::SilentOrbit.ProtocolBuffers.ProtocolParser.WriteUInt32(stream, ms3Length); stream.Write(ms3.GetBuffer(), 0, (int)ms3Length); } } } if (instance.EnumType != null) { foreach (var i4 in instance.EnumType) { // Key for field: 4, LengthDelimited stream.WriteByte(34); using (var ms4 = new MemoryStream()) { Google.protobuf.EnumDescriptorProto.Serialize(ms4, i4); // Length delimited byte array uint ms4Length = (uint)ms4.Length; global::SilentOrbit.ProtocolBuffers.ProtocolParser.WriteUInt32(stream, ms4Length); stream.Write(ms4.GetBuffer(), 0, (int)ms4Length); } } } if (instance.ExtensionRangeField != null) { foreach (var i5 in instance.ExtensionRangeField) { // Key for field: 5, LengthDelimited stream.WriteByte(42); using (var ms5 = new MemoryStream()) { Google.protobuf.DescriptorProto.ExtensionRange.Serialize(ms5, i5); // Length delimited byte array uint ms5Length = (uint)ms5.Length; global::SilentOrbit.ProtocolBuffers.ProtocolParser.WriteUInt32(stream, ms5Length); stream.Write(ms5.GetBuffer(), 0, (int)ms5Length); } } } if (instance.Options != null) { // Key for field: 7, LengthDelimited stream.WriteByte(58); using (var ms7 = new MemoryStream()) { Google.protobuf.MessageOptions.Serialize(ms7, instance.Options); // Length delimited byte array uint ms7Length = (uint)ms7.Length; global::SilentOrbit.ProtocolBuffers.ProtocolParser.WriteUInt32(stream, ms7Length); stream.Write(ms7.GetBuffer(), 0, (int)ms7Length); } } }
/// <summary> /// Emit code preceeding a set of message fields /// </summary> protected abstract void WriteMessageHeader(GeneratorContext ctx, DescriptorProto obj, ref object state);
/// <summary>Helper: Serialize into a MemoryStream and return its byte array</summary> public static byte[] SerializeToBytes(DescriptorProto instance) { using (var ms = new MemoryStream()) { Serialize(ms, instance); return ms.ToArray(); } }
/// <summary> /// Obtain the access of an item, accounting for the model's hierarchy /// </summary> protected Access GetAccess(DescriptorProto obj) => NullIfInherit(obj?.Options?.GetOptions()?.Access) ?? GetAccess(obj?.Parent) ?? Access.Public;
/// <summary> /// Emit code following a set of extension fields /// </summary> protected virtual void WriteExtensionsFooter(GeneratorContext ctx, DescriptorProto file, ref object state) { }
public static void AddClass(DescriptorProto message, CodeNamespace myNamespace) { Dictionary <CodeMemberField, FieldDescriptorProto> fieldInfo = new Dictionary <CodeMemberField, FieldDescriptorProto>(); //Code:代码体 CodeTypeDeclaration myClass = new CodeTypeDeclaration(ToWrapperString(message.Name)); //指定为类 myClass.IsClass = true; //添加基类 myClass.BaseTypes.Add($"ProtoBaseWrapper<{message.Name}>"); //设置类的访问类型 myClass.TypeAttributes = TypeAttributes.Public; // | TypeAttributes.Sealed; //设置类序列化 myClass.CustomAttributes.Add(new CodeAttributeDeclaration("System.Serializable")); //把这个类放在这个命名空间下 myNamespace.Types.Add(myClass); //生成变量 for (int i = 0; i < message.FieldList.Count; i++) { string tempStr = message.FieldList[i].TypeName; if (message.FieldList[i].Type.Equals(FieldDescriptorProto.Types.Type.TYPE_MESSAGE) || message.FieldList[i].Type.Equals(FieldDescriptorProto.Types.Type.TYPE_ENUM)) { if (tempStr.Split('.').Length == 3) { tempStr = tempStr.Split('.')[2]; if (message.FieldList[i].Type.Equals(FieldDescriptorProto.Types.Type.TYPE_MESSAGE)) { tempStr = ToWrapperString(tempStr); } if (message.FieldList[i].Label.Equals(FieldDescriptorProto.Types.Label.LABEL_REPEATED)) { tempStr = ToListString(tempStr); } } else { Console.WriteLine($"Wrong Length in {message.Name} : {message.FieldList[i].TypeName}"); } } else { try { tempStr = $"{typeMap[message.FieldList[i].Type]}"; if (message.FieldList[i].Label.Equals(FieldDescriptorProto.Types.Label.LABEL_REPEATED)) { tempStr = ToListString(tempStr); } } catch (Exception) { Console.WriteLine($"No Map in {message.FieldList[i].Type.ToString()}"); } } string name = message.FieldList[i].Name.ToCamel(); fieldInfo[AddPublicStringField(myClass, tempStr, name)] = message.FieldList[i]; } ConstructMethod(myClass, message, fieldInfo); LoadBaseToWrapper(myClass, message, fieldInfo); OutputBaseFromWrapper(myClass, message, fieldInfo); //读取oneof if (message.UnknownFields[8].LengthDelimitedList.Count > 0) { foreach (var oneOfMessage in message.UnknownFields[8].LengthDelimitedList) { string str = oneOfMessage.ParseString(); string name = str.ToCamel(); string finalString = $"{message.Name}.{name}OneofCase"; AddPublicStringField(myClass, finalString, name); } } }
/// <summary> /// Check whether a particular message should be suppressed - for example because it represents a map /// </summary> protected virtual bool ShouldOmitMessage(GeneratorContext ctx, DescriptorProto obj, ref object state) => obj.Options?.MapEntry ?? false; // don't write this type - use a dictionary instead
public static string GetMessageCSharpName(DescriptorProto proto_msg, string ns) { return(string.IsNullOrEmpty(ns) ? "Magic.Cougar." + proto_msg.Name : ns + "." + proto_msg.Name); }