Fix scanning json column into **string

refs https://github.com/jackc/pgx/issues/1470
pull/1477/head
Jack Christensen 2023-01-20 18:38:11 -06:00
parent 516300aabf
commit e48e7a7189
2 changed files with 29 additions and 3 deletions

View File

@ -95,11 +95,22 @@ func (JSONCodec) PlanScan(m *Map, oid uint32, format int16, target any) ScanPlan
// https://github.com/jackc/pgx/issues/1418
case sql.Scanner:
return &scanPlanSQLScanner{formatCode: format}
default:
return scanPlanJSONToJSONUnmarshal{}
}
// This is to fix **string scanning. It seems wrong to special case sql.Scanner and pointer to pointer, but it's not
// clear what a better solution would be.
//
// https://github.com/jackc/pgx/issues/1470
if wrapperPlan, nextDst, ok := TryPointerPointerScanPlan(target); ok {
if nextPlan := m.planScan(oid, format, nextDst); nextPlan != nil {
if _, failed := nextPlan.(*scanPlanFail); !failed {
wrapperPlan.SetNext(nextPlan)
return wrapperPlan
}
}
}
return scanPlanJSONToJSONUnmarshal{}
}
type scanPlanAnyToString struct{}

View File

@ -101,6 +101,21 @@ func TestJSONCodecUnmarshalSQLNull(t *testing.T) {
})
}
// https://github.com/jackc/pgx/issues/1470
func TestJSONCodecPointerToPointerToString(t *testing.T) {
defaultConnTestRunner.RunTest(context.Background(), t, func(ctx context.Context, t testing.TB, conn *pgx.Conn) {
var s *string
err := conn.QueryRow(ctx, "select '{}'::json").Scan(&s)
require.NoError(t, err)
require.NotNil(t, s)
require.Equal(t, "{}", *s)
err = conn.QueryRow(ctx, "select null::json").Scan(&s)
require.NoError(t, err)
require.Nil(t, s)
})
}
func TestJSONCodecClearExistingValueBeforeUnmarshal(t *testing.T) {
defaultConnTestRunner.RunTest(context.Background(), t, func(ctx context.Context, t testing.TB, conn *pgx.Conn) {
m := map[string]any{}