mirror of https://github.com/jackc/pgx.git
Replace some old database/sql compatibility
parent
ad785d8134
commit
eb0a4c9626
|
@ -461,6 +461,8 @@ func (w timeWrapper) TimeValue() (Time, error) {
|
||||||
|
|
||||||
type durationWrapper time.Duration
|
type durationWrapper time.Duration
|
||||||
|
|
||||||
|
func (w durationWrapper) SkipUnderlyingTypePlan() {}
|
||||||
|
|
||||||
func (w *durationWrapper) ScanInterval(v Interval) error {
|
func (w *durationWrapper) ScanInterval(v Interval) error {
|
||||||
if !v.Valid {
|
if !v.Valid {
|
||||||
return fmt.Errorf("cannot scan NULL into *time.Interval")
|
return fmt.Errorf("cannot scan NULL into *time.Interval")
|
||||||
|
|
|
@ -1,41 +0,0 @@
|
||||||
package pgtype
|
|
||||||
|
|
||||||
import (
|
|
||||||
"database/sql/driver"
|
|
||||||
"errors"
|
|
||||||
)
|
|
||||||
|
|
||||||
func DatabaseSQLValue(ci *ConnInfo, src Value) (interface{}, error) {
|
|
||||||
if valuer, ok := src.(driver.Valuer); ok {
|
|
||||||
return valuer.Value()
|
|
||||||
}
|
|
||||||
|
|
||||||
if textEncoder, ok := src.(TextEncoder); ok {
|
|
||||||
buf, err := textEncoder.EncodeText(ci, nil)
|
|
||||||
if err != nil {
|
|
||||||
return nil, err
|
|
||||||
}
|
|
||||||
return string(buf), nil
|
|
||||||
}
|
|
||||||
|
|
||||||
if binaryEncoder, ok := src.(BinaryEncoder); ok {
|
|
||||||
buf, err := binaryEncoder.EncodeBinary(ci, nil)
|
|
||||||
if err != nil {
|
|
||||||
return nil, err
|
|
||||||
}
|
|
||||||
return buf, nil
|
|
||||||
}
|
|
||||||
|
|
||||||
return nil, errors.New("cannot convert to database/sql compatible value")
|
|
||||||
}
|
|
||||||
|
|
||||||
func EncodeValueText(src TextEncoder) (interface{}, error) {
|
|
||||||
buf, err := src.EncodeText(nil, make([]byte, 0, 32))
|
|
||||||
if err != nil {
|
|
||||||
return nil, err
|
|
||||||
}
|
|
||||||
if buf == nil {
|
|
||||||
return nil, nil
|
|
||||||
}
|
|
||||||
return string(buf), err
|
|
||||||
}
|
|
|
@ -520,41 +520,6 @@ func (plan scanPlanDstTextDecoder) Scan(ci *ConnInfo, oid uint32, formatCode int
|
||||||
return newPlan.Scan(ci, oid, formatCode, src, dst)
|
return newPlan.Scan(ci, oid, formatCode, src, dst)
|
||||||
}
|
}
|
||||||
|
|
||||||
type scanPlanDataTypeSQLScanner DataType
|
|
||||||
|
|
||||||
func (plan *scanPlanDataTypeSQLScanner) Scan(ci *ConnInfo, oid uint32, formatCode int16, src []byte, dst interface{}) error {
|
|
||||||
scanner, ok := dst.(sql.Scanner)
|
|
||||||
if !ok {
|
|
||||||
newPlan := ci.PlanScan(oid, formatCode, dst)
|
|
||||||
return newPlan.Scan(ci, oid, formatCode, src, dst)
|
|
||||||
}
|
|
||||||
|
|
||||||
dt := (*DataType)(plan)
|
|
||||||
if dt.Codec != nil {
|
|
||||||
sqlValue, err := dt.Codec.DecodeDatabaseSQLValue(ci, oid, formatCode, src)
|
|
||||||
if err != nil {
|
|
||||||
return err
|
|
||||||
}
|
|
||||||
return scanner.Scan(sqlValue)
|
|
||||||
}
|
|
||||||
var err error
|
|
||||||
switch formatCode {
|
|
||||||
case BinaryFormatCode:
|
|
||||||
err = dt.binaryDecoder.DecodeBinary(ci, src)
|
|
||||||
case TextFormatCode:
|
|
||||||
err = dt.textDecoder.DecodeText(ci, src)
|
|
||||||
}
|
|
||||||
if err != nil {
|
|
||||||
return err
|
|
||||||
}
|
|
||||||
|
|
||||||
sqlSrc, err := DatabaseSQLValue(ci, dt.Value)
|
|
||||||
if err != nil {
|
|
||||||
return err
|
|
||||||
}
|
|
||||||
return scanner.Scan(sqlSrc)
|
|
||||||
}
|
|
||||||
|
|
||||||
type scanPlanDataTypeAssignTo DataType
|
type scanPlanDataTypeAssignTo DataType
|
||||||
|
|
||||||
func (plan *scanPlanDataTypeAssignTo) Scan(ci *ConnInfo, oid uint32, formatCode int16, src []byte, dst interface{}) error {
|
func (plan *scanPlanDataTypeAssignTo) Scan(ci *ConnInfo, oid uint32, formatCode int16, src []byte, dst interface{}) error {
|
||||||
|
@ -596,6 +561,18 @@ func (plan *scanPlanDataTypeAssignTo) Scan(ci *ConnInfo, oid uint32, formatCode
|
||||||
return assignToErr
|
return assignToErr
|
||||||
}
|
}
|
||||||
|
|
||||||
|
type scanPlanCodecSQLScanner struct{ c Codec }
|
||||||
|
|
||||||
|
func (plan *scanPlanCodecSQLScanner) Scan(ci *ConnInfo, oid uint32, formatCode int16, src []byte, dst interface{}) error {
|
||||||
|
value, err := plan.c.DecodeDatabaseSQLValue(ci, oid, formatCode, src)
|
||||||
|
if err != nil {
|
||||||
|
return err
|
||||||
|
}
|
||||||
|
|
||||||
|
scanner := dst.(sql.Scanner)
|
||||||
|
return scanner.Scan(value)
|
||||||
|
}
|
||||||
|
|
||||||
type scanPlanSQLScanner struct{}
|
type scanPlanSQLScanner struct{}
|
||||||
|
|
||||||
func (scanPlanSQLScanner) Scan(ci *ConnInfo, oid uint32, formatCode int16, src []byte, dst interface{}) error {
|
func (scanPlanSQLScanner) Scan(ci *ConnInfo, oid uint32, formatCode int16, src []byte, dst interface{}) error {
|
||||||
|
@ -1176,7 +1153,7 @@ func (ci *ConnInfo) PlanScan(oid uint32, formatCode int16, dst interface{}) Scan
|
||||||
for _, f := range tryWrappers {
|
for _, f := range tryWrappers {
|
||||||
if wrapperPlan, nextDst, ok := f(dst); ok {
|
if wrapperPlan, nextDst, ok := f(dst); ok {
|
||||||
if nextPlan := ci.PlanScan(oid, formatCode, nextDst); nextPlan != nil {
|
if nextPlan := ci.PlanScan(oid, formatCode, nextDst); nextPlan != nil {
|
||||||
if _, ok := nextPlan.(*scanPlanDataTypeAssignTo); !ok { // avoid fallthrough -- this will go away when old system removed.
|
if _, ok := nextPlan.(scanPlanReflection); !ok { // avoid fallthrough -- this will go away when old system removed.
|
||||||
wrapperPlan.SetNext(nextPlan)
|
wrapperPlan.SetNext(nextPlan)
|
||||||
return wrapperPlan
|
return wrapperPlan
|
||||||
}
|
}
|
||||||
|
@ -1187,16 +1164,11 @@ func (ci *ConnInfo) PlanScan(oid uint32, formatCode int16, dst interface{}) Scan
|
||||||
if _, ok := dst.(*interface{}); ok {
|
if _, ok := dst.(*interface{}); ok {
|
||||||
return &pointerEmptyInterfaceScanPlan{codec: dt.Codec}
|
return &pointerEmptyInterfaceScanPlan{codec: dt.Codec}
|
||||||
}
|
}
|
||||||
}
|
|
||||||
|
|
||||||
if dt != nil {
|
|
||||||
if _, ok := dst.(sql.Scanner); ok {
|
if _, ok := dst.(sql.Scanner); ok {
|
||||||
if _, found := ci.preferAssignToOverSQLScannerTypes[reflect.TypeOf(dst)]; !found {
|
return &scanPlanCodecSQLScanner{c: dt.Codec}
|
||||||
return (*scanPlanDataTypeSQLScanner)(dt)
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
return (*scanPlanDataTypeAssignTo)(dt)
|
|
||||||
}
|
|
||||||
|
|
||||||
if _, ok := dst.(sql.Scanner); ok {
|
if _, ok := dst.(sql.Scanner); ok {
|
||||||
return scanPlanSQLScanner{}
|
return scanPlanSQLScanner{}
|
||||||
|
|
Loading…
Reference in New Issue