2
0

Fix scanning a table type into a struct

Table types have system / hidden columns like tableoid, cmax, xmax, etc.
These are not included when sending or receiving composite types.

https://github.com/jackc/pgx/issues/1576
This commit is contained in:
Jack Christensen
2023-04-20 20:12:20 -05:00
parent 2cf1541bb9
commit 67f2a41587
2 changed files with 48 additions and 1 deletions
+3 -1
View File
@@ -1282,7 +1282,9 @@ func (c *Conn) getCompositeFields(ctx context.Context, oid uint32) ([]pgtype.Com
var fieldOID uint32
rows, _ := c.Query(ctx, `select attname, atttypid
from pg_attribute
where attrelid=$1 and not attisdropped
where attrelid=$1
and not attisdropped
and attnum > 0
order by attnum`,
typrelid,
)
+45
View File
@@ -208,3 +208,48 @@ create type point3d as (
}
})
}
// Test for composite type from table instead of create type. Table types have system / hidden columns like tableoid,
// cmax, xmax, etc. These are not included when sending or receiving composite types.
//
// https://github.com/jackc/pgx/issues/1576
func TestCompositeCodecTranscodeStructWrapperForTable(t *testing.T) {
skipCockroachDB(t, "Server does not support composite types (see https://github.com/cockroachdb/cockroach/issues/27792)")
defaultConnTestRunner.RunTest(context.Background(), t, func(ctx context.Context, t testing.TB, conn *pgx.Conn) {
_, err := conn.Exec(ctx, `drop table if exists point3d;
create table point3d (
x float8,
y float8,
z float8
);`)
require.NoError(t, err)
defer conn.Exec(ctx, "drop table point3d")
dt, err := conn.LoadType(ctx, "point3d")
require.NoError(t, err)
conn.TypeMap().RegisterType(dt)
formats := []struct {
name string
code int16
}{
{name: "TextFormat", code: pgx.TextFormatCode},
{name: "BinaryFormat", code: pgx.BinaryFormatCode},
}
type anotherPoint struct {
X, Y, Z float64
}
for _, format := range formats {
input := anotherPoint{X: 1, Y: 2, Z: 3}
var output anotherPoint
err := conn.QueryRow(ctx, "select $1::point3d", pgx.QueryResultFormats{format.code}, input).Scan(&output)
require.NoErrorf(t, err, "%v", format.name)
require.Equalf(t, input, output, "%v", format.name)
}
})
}