...
1 package pgtype_test
2
3 import (
4 "context"
5 "errors"
6 "fmt"
7 "os"
8
9 "github.com/jackc/pgtype"
10 pgx "github.com/jackc/pgx/v4"
11 )
12
13 type MyType struct {
14 a int32
15 b *string
16 }
17
18 func (dst *MyType) DecodeBinary(ci *pgtype.ConnInfo, src []byte) error {
19 if src == nil {
20 return errors.New("NULL values can't be decoded. Scan into a &*MyType to handle NULLs")
21 }
22
23 if err := (pgtype.CompositeFields{&dst.a, &dst.b}).DecodeBinary(ci, src); err != nil {
24 return err
25 }
26
27 return nil
28 }
29
30 func (src MyType) EncodeBinary(ci *pgtype.ConnInfo, buf []byte) (newBuf []byte, err error) {
31 a := pgtype.Int4{src.a, pgtype.Present}
32 var b pgtype.Text
33 if src.b != nil {
34 b = pgtype.Text{*src.b, pgtype.Present}
35 } else {
36 b = pgtype.Text{Status: pgtype.Null}
37 }
38
39 return (pgtype.CompositeFields{&a, &b}).EncodeBinary(ci, buf)
40 }
41
42 func ptrS(s string) *string {
43 return &s
44 }
45
46 func E(err error) {
47 if err != nil {
48 panic(err)
49 }
50 }
51
52
53
54 func Example_customCompositeTypes() {
55 conn, err := pgx.Connect(context.Background(), os.Getenv("PGX_TEST_DATABASE"))
56 E(err)
57
58 defer conn.Close(context.Background())
59 _, err = conn.Exec(context.Background(), `drop type if exists mytype;
60
61 create type mytype as (
62 a int4,
63 b text
64 );`)
65 E(err)
66 defer conn.Exec(context.Background(), "drop type mytype")
67
68 var result *MyType
69
70
71 err = conn.QueryRow(context.Background(), "select $1::mytype",
72 pgx.QueryResultFormats{pgx.BinaryFormatCode}, MyType{1, ptrS("foo")}).
73 Scan(&result)
74 E(err)
75
76 fmt.Printf("First row: a=%d b=%s\n", result.a, *result.b)
77
78
79 err = conn.QueryRow(context.Background(), "select NULL::mytype", pgx.QueryResultFormats{pgx.BinaryFormatCode}).Scan(&result)
80 E(err)
81
82 fmt.Printf("Second row: %v\n", result)
83
84
85
86
87 }
88
View as plain text