public async void Column__Error_On_Identity_Column_Nullable(string errorLocation, string column) { var mb = @"mb.Database(nameof(Database)) .Table(d => d.Table(t => t.Users) " + string.Format(column, errorLocation) + @" .Build()) .Build();"; await VerifyErrorRaised(mb, ModelBuilderError.ColumnIdentityNullable(), errorLocation); }
static FuzzyTableModel ParseTableColumn(SyntaxNodeAnalysisContext context, InvocationExpressionSyntax expression, FuzzyDatabaseModel partialDatabase) { var innerModel = ParseTableChain(context, expression, partialDatabase); var arguments = AH.ParseArguments(context, expression); var columnArg = arguments["column"]; var typeArg = arguments["type"]; var nullableArg = arguments["nullable"]; var maxLengthArg = arguments["maxLength"]; var nameArg = arguments["name"]; var defaultValueArg = arguments["defaultValue"]; var identityArg = arguments["identity"]; var converterArg = arguments["converter"]; if (AH.IsNull(context, columnArg)) { context.ReportDiagnostic(BuilderError.ArgumentNull("column").MakeDiagnostic(columnArg.GetLocation())); } var property = AH.ParseSelector(context, columnArg); var fuzzyColumnModel = new FuzzyColumnModel() { Property = property, MaxLength = AH.ParseConstantArgument(context, maxLengthArg, () => AH.Just(null as int?)), IsIdentity = AH.ParseConstantArgument(context, identityArg, () => AH.Just(false)), IsNullable = AH.ParseConstantArgument(context, nullableArg, () => AH.Just(false)), Type = AH.ParseConstantArgument(context, typeArg, () => new Optional <SqlType>()), Name = AH.ParseConstantArgument(context, nameArg, () => !property.HasValue ? new Optional <string>() : AH.Just(property.Value?.Name)) }; if (fuzzyColumnModel.Property.HasValue) { var otherColumn = innerModel.Columns.FirstOrDefault(t => t.Property.HasValue && t.Property.Value.Name == fuzzyColumnModel.Property.Value.Name); if (otherColumn != null) { context.ReportDiagnostic(ModelBuilderError.ColumnRepeatedSelector(ToTypeString(innerModel.Property), ToString(fuzzyColumnModel.Property), ToString(otherColumn.Name)).MakeDiagnostic(columnArg.GetLocation())); } } if (fuzzyColumnModel.Name.HasValue) { if (innerModel.Columns.Any(c => c.Name.HasValue && c.Name.Value == fuzzyColumnModel.Name.Value)) { context.ReportDiagnostic(ModelBuilderError.ColumnRepeatedName(ToString(innerModel.Name), ToString(fuzzyColumnModel.Name)).MakeDiagnostic(nameArg == null ? columnArg.GetLocation() : nameArg.GetLocation())); } } if (fuzzyColumnModel.Property.HasValue && fuzzyColumnModel.Type.HasValue) { if (fuzzyColumnModel.Property.Value.Type.TypeKind == TypeKind.Enum) { if (!(fuzzyColumnModel.Type.Value == SqlType.String || SqlTypeHelpers.IsIntegral(fuzzyColumnModel.Type.Value))) { context.ReportDiagnostic(ModelBuilderError.ColumnEnumNotStringOrIntegralType().MakeDiagnostic(typeArg.GetLocation())); } if (fuzzyColumnModel.Type.Value == SqlType.String && fuzzyColumnModel.MaxLength.HasValue) { var namedType = fuzzyColumnModel.Property.Value.Type as INamedTypeSymbol; var longestEnum = namedType.MemberNames.OrderByDescending(n => n.Length).First(); if (fuzzyColumnModel.MaxLength.Value != null && longestEnum.Length > fuzzyColumnModel.MaxLength.Value) { context.ReportDiagnostic(ModelBuilderError.ColumnEnumLongerThanMaxStringSize($"{namedType.Name}.{longestEnum}", (int)fuzzyColumnModel.MaxLength.Value).MakeDiagnostic(maxLengthArg.GetLocation())); } } } else if (fuzzyColumnModel.Property.Value.Type.Name == "DateTimeOffset" || fuzzyColumnModel.Property.Value.Type.Name == "Guid") { //if ((fuzzyColumnModel.Property.Value.Type.Name == "DateTimeOffset" && fuzzyColumnModel.Type.Value != SqlType.DateTimeOffset) || // (fuzzyColumnModel.Property.Value.Type.Name == "Guid" && fuzzyColumnModel.Type.Value != SqlType.Guid)) // context.ReportDiagnostic(Diagnostic.Create(_descriptors[InvalidSqlType], typeArg.GetLocation())); } else { var propertyType = fuzzyColumnModel.Property.Value.Type.SpecialType; //if (!_defaultTypeMappings[propertyType].Contains(fuzzyColumnModel.Type.Value)) // context.ReportDiagnostic(Diagnostic.Create(_descriptors[InvalidSqlType], typeArg.GetLocation())); } } if (fuzzyColumnModel.Type.HasValue && fuzzyColumnModel.IsIdentity.HasValue && fuzzyColumnModel.IsIdentity.Value == true) { var nonIdentityTypes = new List <SqlType>() { SqlType.String, SqlType.Bit, SqlType.Date, SqlType.Time, SqlType.DateTime, SqlType.DateTimeOffset, SqlType.Single, SqlType.Double, SqlType.Guid }; //if (nonIdentityTypes.Contains(fuzzyColumnModel.Type.Value)) // context.ReportDiagnostic(Diagnostic.Create(_descriptors[InvalidSqlTypeForIdentity], identityArg.GetLocation())); } if (fuzzyColumnModel.IsIdentity.HasValue && fuzzyColumnModel.IsIdentity.Value == true && fuzzyColumnModel.IsNullable.HasValue && fuzzyColumnModel.IsNullable.Value == true) { context.ReportDiagnostic(ModelBuilderError.ColumnIdentityNullable().MakeDiagnostic(nullableArg.GetLocation())); } innerModel.Columns.Add(fuzzyColumnModel); return(innerModel); }
public static IColumn <TDatabase, TTable> Column <TDatabase, TTable, TColumn>(this IColumnBuilder <TDatabase, TTable> @this, Expression <Func <TTable, TColumn> > column, SqlType type, bool nullable = false, int?maxLength = null, string name = null, TColumn defaultValue = default(TColumn), bool identity = false, IDatabaseTypeConverter <TColumn> converter = null) { var builder = @this as InternalTableBuilder <TDatabase, TTable>; var property = ExpressionHelpers.ParsePropertySelector(column ?? throw ModelBuilderError.ArgumentNull(nameof(column)).AsException()); { var priorColumn = builder.Columns.FirstOrDefault(c => c.Property.Name == property.Name); if (priorColumn != null) { throw ModelBuilderError.ColumnRepeatedSelector(typeof(TTable).Name, property.Name, priorColumn.Name).AsException(); } } var columnName = name ?? property.Name; if (builder.Columns.Any(t => t.Name == columnName)) { throw ModelBuilderError.ColumnRepeatedName(builder.Name, columnName).AsException(); } if (nullable && identity) { throw ModelBuilderError.ColumnIdentityNullable().AsException(); } if (property.Type.GetTypeInfo().IsEnum) { if (!(type == SqlType.String || SqlTypeHelpers.IsIntegral(type))) { throw ModelBuilderError.ColumnEnumNotStringOrIntegralType().AsException(); } var values = Enum.GetValues(property.Type); if (type == SqlType.String) { var maxValue = values.Cast <object>() .Select(e => e.ToString()) .OrderByDescending(e => e.Length) .First(); if (maxLength != null && maxValue.Length > maxLength) { throw ModelBuilderError.ColumnEnumLongerThanMaxStringSize($"{property.Type.ToString()}.{maxValue}", (int)maxLength).AsException(); } } else { } } builder.Columns.Add(new ColumnModel(name: columnName, property: property, sqlType: type, isNullable: nullable, isIdentity: identity, defaultValue: defaultValue)); return(builder); }