/// <summary>
    ///     Builds an <see cref="CreateUserDefinedTableTypeOperation" /> to create a new user-defined table type.
    /// </summary>
    /// <typeparam name="TColumns"> Type of a typically anonymous type for building columns. </typeparam>
    /// <param name="name"> The name of the user-defined table type. </param>
    /// <param name="columns">
    ///     A delegate using a <see cref="ColumnsBuilder" /> to create an anonymous type configuring the columns of the user-defined table type.
    /// </param>
    /// <param name="schema"> The schema that contains the user-defined table type, or <c>null</c> to use the default schema. </param>
    /// <returns> A builder to allow annotations to be added to the operation. </returns>
    public static MigrationBuilder CreateUserDefinedTableType <TColumns>(
        this MigrationBuilder builder,
        string name,
        Func <UserDefinedTableTypeColumnsBuilder, TColumns> columns,
        string schema = null)
    {
        var createUdtOperation = new CreateUserDefinedTableTypeOperation
        {
            Name   = name,
            Schema = schema
        };
        var columnBuilder = new UserDefinedTableTypeColumnsBuilder(createUdtOperation);
        var columnsObject = columns(columnBuilder);
        var columnMap     = new Dictionary <PropertyInfo, AddColumnOperation>();

        foreach (var property in typeof(TColumns).GetTypeInfo().DeclaredProperties)
        {
            var addColumnOperation = ((IInfrastructure <AddColumnOperation>)property.GetMethod.Invoke(columnsObject, null)).Instance;
            if (addColumnOperation.Name == null)
            {
                addColumnOperation.Name = property.Name;
            }
            columnMap.Add(property, addColumnOperation);
        }
        builder.Operations.Add(createUdtOperation);
        return(builder);
    }
 private void GenerateCreateUdt(
     CreateUserDefinedTableTypeOperation operation,
     IModel model,
     MigrationCommandListBuilder builder)
 {
     builder
     .Append("CREATE TYPE ")
     .Append(Dependencies.SqlGenerationHelper.DelimitIdentifier(operation.Name, operation.Schema))
     .AppendLine(" AS TABLE (");
     using (builder.Indent())
     {
         for (var i = 0; i < operation.Columns.Count; i++)
         {
             var column = operation.Columns[i];
             ColumnDefinition(column, model, builder);
             if (i != operation.Columns.Count - 1)
             {
                 builder.AppendLine(",");
             }
         }
         builder.AppendLine();
     }
     builder.Append(")");
     builder.AppendLine(Dependencies.SqlGenerationHelper.StatementTerminator).EndCommand();
 }
 /// <summary>
 ///     Constructs a builder for the given <see cref="CreateUserDefinedTableTypeOperation" />.
 /// </summary>
 /// <param name="createUserDefinedTableTypeOperation"> The operation. </param>
 public UserDefinedTableTypeColumnsBuilder(CreateUserDefinedTableTypeOperation createUserDefinedTableTypeOperation)
 {
     _createTableOperation = createUserDefinedTableTypeOperation ??
                             throw new ArgumentNullException(nameof(createUserDefinedTableTypeOperation));
 }