Skip to content
Draft
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
23 changes: 22 additions & 1 deletion core/typecollection/typecollection.go
Original file line number Diff line number Diff line change
Expand Up @@ -182,7 +182,28 @@ func (pgs *TypeCollection) GetType(ctx context.Context, name id.Type) (*pgtypes.
if !ok {
return nil, nil
}
tbl, schema, err := pgs.getTable(sqlCtx, name.SchemaName(), name.TypeName())
typeName := name.TypeName()

// A name starting with "_" may be the implicit array type for a table's composite row type.
// PostgreSQL implicitly creates an array type for every user-defined type (including the
// composite type that is implicitly created for each table). Look up the element type by
// stripping the leading "_", and if a matching table exists, build the array type on the fly.
if strings.HasPrefix(typeName, "_") {
elemTbl, schema, err := pgs.getTable(sqlCtx, name.SchemaName(), typeName[1:])
if err != nil {
return nil, err
}
if elemTbl != nil {
compositeType, err := pgs.tableToType(sqlCtx, elemTbl, schema)
if err != nil {
return nil, err
}
return pgtypes.CreateArrayTypeFromBaseType(compositeType), nil
}
return nil, nil
}

tbl, schema, err := pgs.getTable(sqlCtx, name.SchemaName(), typeName)
if err != nil || tbl == nil {
return nil, err
}
Expand Down
4 changes: 2 additions & 2 deletions postgres/parser/sem/tree/format.go
Original file line number Diff line number Diff line change
Expand Up @@ -442,9 +442,9 @@ func AsStringWithFQNames(n NodeFormatter, ann *Annotations) string {
return ctx.CloseAndGetString()
}

// AsString pretty prints a node to a string.
// AsString pretty prints a node to a string, with unquoted identifiers.
func AsString(n NodeFormatter) string {
return AsStringWithFlags(n, FmtSimple)
return AsStringWithFlags(n, FmtSimple|FmtBareIdentifiers)
}

// ErrString pretty prints a node to a string. Identifiers are not quoted.
Expand Down
4 changes: 4 additions & 0 deletions server/analyzer/validate_create_table.go
Original file line number Diff line number Diff line change
Expand Up @@ -124,6 +124,10 @@ func schToColMap(sch sql.Schema) map[string]*sql.Column {
func validateIndex(ctx *sql.Context, colMap map[string]*sql.Column, idxDef *sql.IndexDef) error {
seenCols := make(map[string]struct{})
for _, idxCol := range idxDef.Columns {
if idxCol.Expression != nil {
continue
}

schCol, exists := colMap[strings.ToLower(idxCol.Name)]
if !exists {
return sql.ErrKeyColumnDoesNotExist.New(idxCol.Name)
Expand Down
2 changes: 1 addition & 1 deletion server/ast/create_function.go
Original file line number Diff line number Diff line change
Expand Up @@ -226,7 +226,7 @@ func convertSQLStmts(stmts parser.Statements, params []pgnodes.RoutineParam) (st
StrVal: "", // must be empty string
}
// placeholder name is empty
if param.Name == "\"\"" {
if param.Name == "" {
n := fmt.Sprintf("$%d", i+1)
paramMap[n] = tv
params[i].Name = n
Expand Down
4 changes: 0 additions & 4 deletions server/ast/index_elem.go
Original file line number Diff line number Diff line change
Expand Up @@ -27,10 +27,6 @@ import (
func nodeIndexElemList(ctx *Context, node tree.IndexElemList) ([]*vitess.IndexField, error) {
vitessIndexColumns := make([]*vitess.IndexField, 0, len(node))
for _, inputColumn := range node {
if inputColumn.Expr != nil {
return nil, errors.Errorf("expression index attribute is not yet supported")
}

if inputColumn.Collation != "" {
logrus.Warn("index attribute collation is not yet supported, ignoring")
}
Expand Down
12 changes: 7 additions & 5 deletions server/ast/resolvable_type_reference.go
Original file line number Diff line number Diff line change
Expand Up @@ -41,9 +41,12 @@ func nodeResolvableTypeReference(ctx *Context, typ tree.ResolvableTypeReference,
switch columnType := typ.(type) {
case *tree.ArrayTypeReference:
if uon, ok := columnType.ElementType.(*tree.UnresolvedObjectName); ok {
return nodeResolvableTypeReference(ctx, uon, mayBeTrigger)
tn := uon.ToTableName()
columnTypeName = tn.Object() + "[]"
doltgresType = pgtypes.NewUnresolvedArrayDoltgresType(tn.Schema(), tn.Object())
} else {
return nil, nil, errors.Errorf("the given array type is not yet supported")
}
return nil, nil, errors.Errorf("the given array type is not yet supported")
case *tree.OIDTypeReference:
return nil, nil, errors.Errorf("referencing types by their OID is not yet supported")
case *tree.UnresolvedObjectName:
Expand All @@ -69,9 +72,8 @@ func nodeResolvableTypeReference(ctx *Context, typ tree.ResolvableTypeReference,
// currently the built-in types will be resolved, so it can retrieve its array type
doltgresType = baseResolvedType.ToArrayType()
} else {
// TODO: handle array type of non-built-in types
baseResolvedType.TypCategory = pgtypes.TypeCategory_ArrayTypes
doltgresType = baseResolvedType
// User-defined element type: build an unresolved array type with the proper structure.
doltgresType = pgtypes.NewUnresolvedArrayDoltgresType(baseResolvedType.ID.SchemaName(), baseResolvedType.ID.TypeName())
}
}
} else if columnType.Family() == types.GeometryFamily {
Expand Down
3 changes: 3 additions & 0 deletions server/tables/information_schema/columns_table.go
Original file line number Diff line number Diff line change
Expand Up @@ -204,6 +204,9 @@ func getRowsFromTable(ctx *sql.Context, db information_schema.DbWithNames, t sql

tblName := t.Name()
for i, col := range information_schema.SchemaForTable(t, db.Database, allColsWithDefaultValue) {
if col.HiddenSystem {
continue
}
r := getRowFromColumn(ctx, i, col, db.CatalogName, db.SchemaName, tblName)
if r != nil {
rows = append(rows, r)
Expand Down
22 changes: 21 additions & 1 deletion server/types/type.go
Original file line number Diff line number Diff line change
Expand Up @@ -122,6 +122,19 @@ func NewUnresolvedDoltgresTypeFromID(idType id.Type) *DoltgresType {
}
}

// NewUnresolvedArrayDoltgresType returns an unresolved DoltgresType for an array of a user-defined element type.
// TypCategory and Elem are pre-filled so that IsArrayType() returns true before full resolution from the type
// collection. The array type ID follows the Postgres convention of "_" + element type name.
func NewUnresolvedArrayDoltgresType(sch, elemName string) *DoltgresType {
return &DoltgresType{
ID: id.NewType(sch, "_"+elemName),
IsUnresolved: true,
TypCategory: TypeCategory_ArrayTypes,
Elem: id.NewType(sch, elemName),
Array: id.NullType,
}
}

// AnalyzeFuncName returns the name that would be displayed in pg_type for the `typanalyze` field.
func (t *DoltgresType) AnalyzeFuncName() string {
return globalFunctionRegistry.GetString(t.AnalyzeFunc)
Expand All @@ -143,6 +156,9 @@ func (t *DoltgresType) ArrayBaseType() *DoltgresType {
// we return for analysis
elem, ok = LogicalArrayElementTypes[t.ID]
if !ok {
if t.IsUnresolved && t.Elem != id.NullType {
return NewUnresolvedDoltgresType(t.Elem.SchemaName(), t.Elem.TypeName())
}
panic(fmt.Sprintf("cannot get base type from: %s", t.Name()))
}
}
Expand Down Expand Up @@ -923,7 +939,11 @@ func (t *DoltgresType) ToArrayType() *DoltgresType {
}
arr, ok := IDToBuiltInDoltgresType[t.Array]
if !ok {
panic(fmt.Sprintf("cannot get array type from: %s", t.Name()))
if t.Array == id.NullType {
panic(fmt.Sprintf("cannot get array type from: %s", t.Name()))
}
// User-defined type: the array type is not in the built-in map, so build it from this base type.
return CreateArrayTypeFromBaseType(t)
}
newArr := *arr.WithAttTypMod(t.attTypMod)
newArr.InternalName = fmt.Sprintf("%s[]", t.String())
Expand Down
Loading
Loading