Skip to content

Commit 8f36c13

Browse files
mazitovtMarcin Romaszewicz
andauthored
fix: support encoding.TextMarshaler in StyleParamWithLocation (#634)
Co-authored-by: Marcin Romaszewicz <47459980+deepmap-marcinr@users.noreply.github.com>
1 parent 6bf4c7c commit 8f36c13

2 files changed

Lines changed: 35 additions & 0 deletions

File tree

styleparam.go

Lines changed: 20 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -14,6 +14,7 @@
1414
package runtime
1515

1616
import (
17+
"encoding"
1718
"errors"
1819
"fmt"
1920
"net/url"
@@ -62,6 +63,25 @@ func StyleParamWithLocation(style string, explode bool, paramName string, paramL
6263
t = v.Type()
6364
}
6465

66+
// If the value implements encoding.TextMarshaler we use it for marshaling
67+
// https://github.com/deepmap/oapi-codegen/issues/504
68+
if tu, ok := value.(encoding.TextMarshaler); ok {
69+
t := reflect.Indirect(reflect.ValueOf(value)).Type()
70+
convertableToTime := t.ConvertibleTo(reflect.TypeOf(time.Time{}))
71+
convertableToDate := t.ConvertibleTo(reflect.TypeOf(types.Date{}))
72+
73+
// Since both time.Time and types.Date implement encoding.TextMarshaler
74+
// we should avoid calling theirs MarshalText()
75+
if !convertableToTime && !convertableToDate {
76+
b, err := tu.MarshalText()
77+
if err != nil {
78+
return "", fmt.Errorf("error marshaling '%s' as text: %s", value, err)
79+
}
80+
81+
return stylePrimitive(style, explode, paramName, paramLocation, string(b))
82+
}
83+
}
84+
6585
switch t.Kind() {
6686
case reflect.Slice:
6787
n := v.Len()

styleparam_test.go

Lines changed: 15 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -14,6 +14,7 @@
1414
package runtime
1515

1616
import (
17+
"github.com/google/uuid"
1718
"testing"
1819
"time"
1920

@@ -676,4 +677,18 @@ func TestStyleParam(t *testing.T) {
676677
result, err = StyleParamWithLocation("simple", false, "id", ParamLocationQuery, object3)
677678
assert.NoError(t, err)
678679
assert.EqualValues(t, "date_field,1996-03-19,time_field,1996-03-19T00%3A00%3A00Z,uuid_field,baa07328-452e-40bd-aa2e-fa823ec13605", result)
680+
681+
// Test handling of struct that implement encoding.TextMarshaler
682+
timeVal = time.Date(1996, time.March, 19, 0, 0, 0, 0, time.UTC)
683+
684+
result, err = StyleParamWithLocation("simple", false, "id", ParamLocationQuery, timeVal)
685+
assert.NoError(t, err)
686+
assert.EqualValues(t, "1996-03-19T00%3A00%3A00Z", result)
687+
688+
uuidD := uuid.MustParse("972beb41-e5ea-4b31-a79a-96f4999d8769")
689+
690+
result, err = StyleParamWithLocation("simple", false, "id", ParamLocationQuery, uuidD)
691+
assert.NoError(t, err)
692+
assert.EqualValues(t, "972beb41-e5ea-4b31-a79a-96f4999d8769", result)
693+
679694
}

0 commit comments

Comments
 (0)