internal ScalarTypeModel( TypeModelContainer container, Type type, int size) : base(type, container) { this.size = size; }
public void Facade_NullReturnedFromConverter2() { TypeModelContainer container = TypeModelContainer.CreateDefault(); container.RegisterTypeFacade <long?, DateTimeOffset?, InvalidNullableDateTimeNullableLongConverter>(); FlatBufferSerializer serializer = new FlatBufferSerializer( new FlatBufferSerializerOptions(FlatBufferDeserializationOption.Greedy), container); byte[] destination = new byte[200]; var compiled = serializer.Compile <ExtensionTable <DateTimeOffset?> >(); try { serializer.Serialize( new ExtensionTable <DateTimeOffset?> { Item = DateTimeOffset.UtcNow }, destination); Assert.Fail(); } catch (InvalidOperationException ex) { Assert.IsTrue(ex.Message.Contains("ITypeFacadeConverter")); } }
// TODO: consider moving to TableOrStructDefinition. private static string GenerateSerializerForType(Assembly assembly, TableOrStructDefinition tableOrStruct) { CSharpHelpers.ConvertProtectedInternalToProtected = false; try { Type type = assembly.GetType(tableOrStruct.FullName); var options = new FlatBufferSerializerOptions(tableOrStruct.RequestedSerializer.Value); var generator = new RoslynSerializerGenerator(options, TypeModelContainer.CreateDefault()); var method = generator .GetType() .GetMethod(nameof(RoslynSerializerGenerator.GenerateCSharp), BindingFlags.Instance | BindingFlags.NonPublic | BindingFlags.Public) .MakeGenericMethod(type); try { string code = (string)method.Invoke(generator, new[] { "private" }); return(code); } catch (TargetInvocationException ex) { ExceptionDispatchInfo.Capture(ex.InnerException).Throw(); throw; } } finally { CSharpHelpers.ConvertProtectedInternalToProtected = true; } }
public void Facade_NullReturnedFromConverter() { TypeModelContainer container = TypeModelContainer.CreateDefault(); container.RegisterTypeFacade <string, DateTimeOffset, InvalidDateTimeStringConverter>(); FlatBufferSerializer serializer = new FlatBufferSerializer( new FlatBufferSerializerOptions(FlatBufferDeserializationOption.Greedy), container); byte[] destination = new byte[200]; var compiled = serializer.Compile <ExtensionTable <DateTimeOffset> >(); try { serializer.Serialize( new ExtensionTable <DateTimeOffset> { Item = DateTimeOffset.UtcNow }, destination); Assert.False(true, "expected exception"); } catch (InvalidOperationException ex) { Assert.Contains("ITypeFacadeConverter", ex.Message); } }
public static void Run() { TypeModelContainer container = TypeModelContainer.CreateDefault(); container.RegisterTypeFacade <long, DateTimeOffset, DateTimeOffsetTypeFacadeConverter>(); container.RegisterTypeFacade <byte[], Guid, GuidByteArrayConverter>(); var example = new FacadeExampleTable { Guid = Guid.NewGuid(), Timestamp = DateTimeOffset.UtcNow, }; FlatBufferSerializer serializer = new FlatBufferSerializer( new FlatBufferSerializerOptions(FlatBufferDeserializationOption.PropertyCache), container); byte[] destination = new byte[1024]; serializer.Serialize(example, destination); var parsed = serializer.Parse <FacadeExampleTable>(destination); Debug.Assert(parsed.Guid == example.Guid); Debug.Assert(parsed.Timestamp == example.Timestamp); }
/// <summary> /// Creates a FlatSharp type model container with default support. /// </summary> public static TypeModelContainer CreateDefault() { var container = new TypeModelContainer(); container.RegisterProvider(new ScalarTypeModelProvider()); container.RegisterProvider(new FlatSharpTypeModelProvider()); return(container); }
private static string CreateCSharp(BaseSchemaMember rootNode, CompilerOptions options) { ErrorContext.Current.ThrowIfHasErrors(); if (string.IsNullOrEmpty(rootNode.DeclaringFile)) { throw new InvalidFbsFileException("FlatSharp.Internal: RootNode missing declaring file"); } Assembly? assembly = null; CodeWriter writer = new CodeWriter(); var steps = new[] { CodeWritingPass.Initialization, CodeWritingPass.PropertyModeling, CodeWritingPass.SerializerGeneration, CodeWritingPass.RpcGeneration, }; foreach (var step in steps) { var localOptions = options; if (step <= CodeWritingPass.PropertyModeling) { localOptions = localOptions with { NullableWarnings = false }; } if (step > CodeWritingPass.Initialization) { string code = writer.ToString(); (assembly, _, _) = RoslynSerializerGenerator.CompileAssembly(code, true); } writer = new CodeWriter(); rootNode.WriteCode( writer, new CompileContext { CompilePass = step, Options = localOptions, RootFile = rootNode.DeclaringFile, PreviousAssembly = assembly, TypeModelContainer = TypeModelContainer.CreateDefault(), }); ErrorContext.Current.ThrowIfHasErrors(); } string rawCode = writer.ToString(); string formattedCode = RoslynSerializerGenerator.GetFormattedText(rawCode); return(formattedCode); } }
/// <summary> /// Returns the fully qualified clone method name. /// </summary> public static string GenerateCloneMethodsForAssembly( CodeWriter writer, CompilerOptions options, Assembly assembly, TypeModelContainer container) { string @namespace = $"FlatSharp.Compiler.Generated"; string className = $"CloneHelpers_{Guid.NewGuid():n}"; string methodName = "Clone"; string fullyQualifiedMethodName = $"{@namespace}.{className}.{methodName}"; HashSet <Type> seenTypes = new HashSet <Type>(); foreach (var type in assembly.GetTypes()) { if (type.IsNested) { continue; } if (container.TryCreateTypeModel(type, out var typeModel)) { typeModel.TraverseObjectGraph(seenTypes); } } Dictionary <Type, string> methodNameMap = new Dictionary <Type, string>(); foreach (var seenType in seenTypes) { methodNameMap[seenType] = fullyQualifiedMethodName; } writer.AppendLine($"namespace {@namespace}"); using (writer.WithBlock()) { writer.AppendLine($"internal static class {className}"); using (writer.WithBlock()) { foreach (var seenType in seenTypes) { if (!container.TryCreateTypeModel(seenType, out ITypeModel? model)) { ErrorContext.Current.RegisterError($"Unable to create type model for Type '{seenType.FullName}.'"); continue; } GenerateCloneMethod(writer, options, model, methodNameMap); } } } return(fullyQualifiedMethodName); }
public bool TryCreateTypeModel(TypeModelContainer container, Type type, [NotNullWhen(true)] out ITypeModel?typeModel) { if (type == typeof(TType)) { typeModel = this.model; return(true); } typeModel = null; return(false); }
public void Facade_SortedVector() { TypeModelContainer container = TypeModelContainer.CreateDefault(); container.RegisterTypeFacade <long, DateTimeOffset, DateTimeTicksConverter>(); var ex = Assert.Throws <InvalidFlatBufferDefinitionException>( () => container.CreateTypeModel(typeof(ExtensionTable <IIndexedVector <DateTimeOffset, KeyTable> >))); Assert.Equal( "Table FlatSharpTests.TypeFacadeTests.KeyTable declares a key property on a type that that does not support being a key in a sorted vector.", ex.Message); }
public static ParserCodeGenContext CreateParserContext(FlatBufferSerializerOptions?options = null) { return(new ParserCodeGenContext( "a", "b", "c", false, "d", new ReturnsRandomDictionary(), new ReturnsRandomDictionary(), options ?? new FlatBufferSerializerOptions(), TypeModelContainer.CreateDefault(), new Dictionary <ITypeModel, List <TableFieldContext> >())); }
public void Facade_Chained() { TypeModelContainer container = TypeModelContainer.CreateDefault(); container.RegisterTypeFacade <long, TimeSpan, TimeSpanTicksConverter>(); container.RegisterTypeFacade <TimeSpan, DateTimeOffset, DateTimeTimeSpanConverter>(); DateTimeOffset ts = DateTimeOffset.UtcNow; TimeSpan span = ts - DateTimeOffset.MinValue; long expectedValue = span.Ticks; this.FacadeTest <long, TimeSpan, TimeSpanTicksConverter>(expectedValue, span, container); this.FacadeTest <TimeSpan, DateTimeOffset, DateTimeTimeSpanConverter>(span, ts, container); }
private void FacadeTest <TUnderlyingType, TType, TConverter>( TUnderlyingType underlyingValue, TType value, TypeModelContainer container = null) where TConverter : struct, ITypeFacadeConverter <TUnderlyingType, TType> { if (container == null) { container = TypeModelContainer.CreateDefault(); container.RegisterTypeFacade <TUnderlyingType, TType, TConverter>(); } FlatBufferSerializer serializer = new FlatBufferSerializer( new FlatBufferSerializerOptions(FlatBufferDeserializationOption.Greedy), container); byte[] destination = new byte[1024]; byte[] destination2 = new byte[1024]; var compiled = serializer.Compile <ExtensionTable <TType> >(); var underlyingItem = new ExtensionTable <TUnderlyingType> { Item = underlyingValue }; var facadeItem = new ExtensionTable <TType> { Item = value }; serializer.Serialize(facadeItem, destination); serializer.Serialize(underlyingItem, destination2); Assert.True(destination.AsSpan().SequenceEqual(destination2)); var parsed = serializer.Parse <ExtensionTable <TType> >(destination); Assert.Equal(parsed.Item, value); Assert.Equal(serializer.GetMaxSize(facadeItem), serializer.GetMaxSize(underlyingItem)); }
internal BaseVectorOfUnionTypeModel(Type vectorType, TypeModelContainer provider) : base(vectorType, provider) { this.ItemTypeModel = null!; }
/// <summary> /// Tries to create a type model based on the given type. /// </summary> public bool TryCreateTypeModel(TypeModelContainer container, Type type, [NotNullWhen(true)] out ITypeModel?typeModel) { if (type == typeof(string)) { typeModel = new StringTypeModel(container); return(true); } if (type.IsArray) { if (typeof(IFlatBufferUnion).IsAssignableFrom(type.GetElementType())) { typeModel = new ArrayVectorOfUnionTypeModel(type, container); } else { typeModel = new ArrayVectorTypeModel(type, container); } return(true); } if (type.IsGenericType) { var genericDef = type.GetGenericTypeDefinition(); if (genericDef == typeof(IList <>) || genericDef == typeof(IReadOnlyList <>)) { if (typeof(IFlatBufferUnion).IsAssignableFrom(type.GetGenericArguments()[0])) { typeModel = new ListVectorOfUnionTypeModel(type, container); } else { typeModel = new ListVectorTypeModel(type, container); } return(true); } if (genericDef == typeof(Memory <>) || genericDef == typeof(ReadOnlyMemory <>)) { typeModel = new MemoryVectorTypeModel(type, container); return(true); } if (genericDef == typeof(IIndexedVector <,>)) { typeModel = new IndexedVectorTypeModel(type, container); return(true); } } if (typeof(IFlatBufferUnion).IsAssignableFrom(type)) { typeModel = new UnionTypeModel(type, container); return(true); } if (type.IsEnum) { typeModel = new EnumTypeModel(type, container); return(true); } var underlyingType = Nullable.GetUnderlyingType(type); if (underlyingType is not null) { typeModel = new NullableTypeModel(container, type); return(true); } var tableAttribute = type.GetCustomAttribute <FlatBufferTableAttribute>(); var structAttribute = type.GetCustomAttribute <FlatBufferStructAttribute>(); if (tableAttribute is not null && structAttribute is not null) { throw new InvalidFlatBufferDefinitionException($"Type '{CSharpHelpers.GetCompilableTypeName(type)}' is declared as both [FlatBufferTable] and [FlatBufferStruct]."); }
internal TableTypeModel(Type clrType, TypeModelContainer typeModelProvider) : base(clrType, typeModelProvider) { }
internal EnumTypeModel(Type type, TypeModelContainer typeModelContainer) : base(type, typeModelContainer) { this.underlyingTypeModel = null !; }
/// <summary> /// Creates a new FlatBufferSerializer using the given options. /// </summary> public FlatBufferSerializer(FlatBufferSerializerOptions options) : this(options, TypeModelContainer.CreateDefault()) { }
public static bool TryResolve(string type, out ITypeModel builtInType) { return(TryResolve(type, TypeModelContainer.CreateDefault(), out builtInType)); }
public BoolTypeModel(TypeModelContainer container) : base(container, typeof(bool), sizeof(bool)) { }
public bool TryCreateTypeModel( TypeModelContainer container, Type type, [NotNullWhen(true)] out ITypeModel?typeModel) { typeModel = null; if (type == typeof(bool)) { typeModel = new BoolTypeModel(container); return(true); } if (type == typeof(byte)) { typeModel = new ByteTypeModel(container); return(true); } if (type == typeof(sbyte)) { typeModel = new SByteTypeModel(container); return(true); } if (type == typeof(ushort)) { typeModel = new UShortTypeModel(container); return(true); } if (type == typeof(short)) { typeModel = new ShortTypeModel(container); return(true); } if (type == typeof(int)) { typeModel = new IntTypeModel(container); return(true); } if (type == typeof(uint)) { typeModel = new UIntTypeModel(container); return(true); } if (type == typeof(long)) { typeModel = new LongTypeModel(container); return(true); } if (type == typeof(ulong)) { typeModel = new ULongTypeModel(container); return(true); } if (type == typeof(float)) { typeModel = new FloatTypeModel(container); return(true); } if (type == typeof(double)) { typeModel = new DoubleTypeModel(container); return(true); } return(false); }
public DoubleTypeModel(TypeModelContainer container) : base(container, typeof(double), sizeof(double)) { }
public ArrayVectorOfUnionTypeModel(Type clrType, TypeModelContainer container) : base(clrType, container) { }
public ULongTypeModel(TypeModelContainer container) : base(container, typeof(ulong), sizeof(ulong)) { }
public UIntTypeModel(TypeModelContainer container) : base(container, typeof(uint), sizeof(uint)) { }
public SByteTypeModel(TypeModelContainer container) : base(container, typeof(sbyte), sizeof(sbyte)) { }
private static bool TryResolve(string type, TypeModelContainer provider, out ITypeModel builtInType) { return(provider.TryResolveFbsAlias(type, out builtInType)); }
public UShortTypeModel(TypeModelContainer container) : base(container, typeof(ushort), sizeof(ushort)) { }
public FloatTypeModel(TypeModelContainer container) : base(container, typeof(float), sizeof(float)) { }
/// <summary> /// Creates a new FlatBufferSerializer using the given options and type model provider. /// </summary> public FlatBufferSerializer(FlatBufferSerializerOptions options, TypeModelContainer typeModelContainer) { this.container = typeModelContainer ?? throw new ArgumentNullException(nameof(typeModelContainer)); this.Options = options ?? throw new ArgumentNullException(nameof(options)); }