feat(plugin): supports using json marshal to correct string types by … (#758)
This commit is contained in:
parent
3030d4d627
commit
d58783b11c
|
|
@ -263,28 +263,28 @@ func MustString(value any) string {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
func TryFixValueType(paramName string, schemaRef *openapi3.SchemaRef, value any) (any, error) {
|
func TryCorrectValueType(paramName string, schemaRef *openapi3.SchemaRef, value any) (any, error) {
|
||||||
if value == nil {
|
if value == nil {
|
||||||
return "", fmt.Errorf("value of '%s' is nil", paramName)
|
return "", fmt.Errorf("value of '%s' is nil", paramName)
|
||||||
}
|
}
|
||||||
|
|
||||||
switch schemaRef.Value.Type {
|
switch schemaRef.Value.Type {
|
||||||
case openapi3.TypeString:
|
case openapi3.TypeString:
|
||||||
return tryString(value)
|
return tryCorrectString(value)
|
||||||
case openapi3.TypeNumber:
|
case openapi3.TypeNumber:
|
||||||
return tryFloat64(value)
|
return tryCorrectFloat64(value)
|
||||||
case openapi3.TypeInteger:
|
case openapi3.TypeInteger:
|
||||||
return tryInt64(value)
|
return tryCorrectInt64(value)
|
||||||
case openapi3.TypeBoolean:
|
case openapi3.TypeBoolean:
|
||||||
return tryBool(value)
|
return tryCorrectBool(value)
|
||||||
case openapi3.TypeArray:
|
case openapi3.TypeArray:
|
||||||
arrVal, ok := value.([]any)
|
arrVal, ok := value.([]any)
|
||||||
if !ok {
|
if !ok {
|
||||||
return nil, fmt.Errorf("[TryFixValueType] value '%s' is not array", paramName)
|
return nil, fmt.Errorf("[TryCorrectValueType] value '%s' is not array", paramName)
|
||||||
}
|
}
|
||||||
|
|
||||||
for i, v := range arrVal {
|
for i, v := range arrVal {
|
||||||
_v, err := TryFixValueType(paramName, schemaRef.Value.Items, v)
|
_v, err := TryCorrectValueType(paramName, schemaRef.Value.Items, v)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return nil, err
|
return nil, err
|
||||||
}
|
}
|
||||||
|
|
@ -296,7 +296,7 @@ func TryFixValueType(paramName string, schemaRef *openapi3.SchemaRef, value any)
|
||||||
case openapi3.TypeObject:
|
case openapi3.TypeObject:
|
||||||
mapVal, ok := value.(map[string]any)
|
mapVal, ok := value.(map[string]any)
|
||||||
if !ok {
|
if !ok {
|
||||||
return nil, fmt.Errorf("[TryFixValueType] value '%s' is not object", paramName)
|
return nil, fmt.Errorf("[TryCorrectValueType] value '%s' is not object", paramName)
|
||||||
}
|
}
|
||||||
|
|
||||||
for k, v := range mapVal {
|
for k, v := range mapVal {
|
||||||
|
|
@ -305,7 +305,7 @@ func TryFixValueType(paramName string, schemaRef *openapi3.SchemaRef, value any)
|
||||||
continue
|
continue
|
||||||
}
|
}
|
||||||
|
|
||||||
_v, err := TryFixValueType(k, p, v)
|
_v, err := TryCorrectValueType(k, p, v)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return nil, err
|
return nil, err
|
||||||
}
|
}
|
||||||
|
|
@ -315,11 +315,11 @@ func TryFixValueType(paramName string, schemaRef *openapi3.SchemaRef, value any)
|
||||||
|
|
||||||
return mapVal, nil
|
return mapVal, nil
|
||||||
default:
|
default:
|
||||||
return nil, fmt.Errorf("[TryFixValueType] unsupported schema type '%s'", schemaRef.Value.Type)
|
return nil, fmt.Errorf("[TryCorrectValueType] unsupported schema type '%s'", schemaRef.Value.Type)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
func tryString(value any) (string, error) {
|
func tryCorrectString(value any) (string, error) {
|
||||||
switch val := value.(type) {
|
switch val := value.(type) {
|
||||||
case string:
|
case string:
|
||||||
return val, nil
|
return val, nil
|
||||||
|
|
@ -331,11 +331,15 @@ func tryString(value any) (string, error) {
|
||||||
case json.Number:
|
case json.Number:
|
||||||
return val.String(), nil
|
return val.String(), nil
|
||||||
default:
|
default:
|
||||||
return "", fmt.Errorf("cannot convert type from '%T' to string", val)
|
b, err := sonic.MarshalString(value)
|
||||||
|
if err != nil {
|
||||||
|
return "", fmt.Errorf("tryCorrectString failed, err=%w", err)
|
||||||
|
}
|
||||||
|
return b, nil
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
func tryInt64(value any) (int64, error) {
|
func tryCorrectInt64(value any) (int64, error) {
|
||||||
switch val := value.(type) {
|
switch val := value.(type) {
|
||||||
case string:
|
case string:
|
||||||
vi64, _ := strconv.ParseInt(val, 10, 64)
|
vi64, _ := strconv.ParseInt(val, 10, 64)
|
||||||
|
|
@ -352,7 +356,7 @@ func tryInt64(value any) (int64, error) {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
func tryBool(value any) (bool, error) {
|
func tryCorrectBool(value any) (bool, error) {
|
||||||
switch val := value.(type) {
|
switch val := value.(type) {
|
||||||
case string:
|
case string:
|
||||||
return strconv.ParseBool(val)
|
return strconv.ParseBool(val)
|
||||||
|
|
@ -363,7 +367,7 @@ func tryBool(value any) (bool, error) {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
func tryFloat64(value any) (float64, error) {
|
func tryCorrectFloat64(value any) (float64, error) {
|
||||||
switch val := value.(type) {
|
switch val := value.(type) {
|
||||||
case string:
|
case string:
|
||||||
return strconv.ParseFloat(val, 64)
|
return strconv.ParseFloat(val, 64)
|
||||||
|
|
|
||||||
|
|
@ -1100,15 +1100,15 @@ func (t *toolExecutor) processWithInvalidRespProcessStrategyOfReturnErr(_ contex
|
||||||
processor = func(paramName string, paramVal any, schemaVal *openapi3.Schema) (any, error) {
|
processor = func(paramName string, paramVal any, schemaVal *openapi3.Schema) (any, error) {
|
||||||
switch schemaVal.Type {
|
switch schemaVal.Type {
|
||||||
case openapi3.TypeObject:
|
case openapi3.TypeObject:
|
||||||
newParamValMap := map[string]any{}
|
|
||||||
paramValMap, ok := paramVal.(map[string]any)
|
paramValMap, ok := paramVal.(map[string]any)
|
||||||
if !ok {
|
if !ok {
|
||||||
return nil, errorx.New(errno.ErrPluginExecuteToolFailed, errorx.KVf(errno.PluginMsgKey,
|
return nil, errorx.New(errno.ErrPluginExecuteToolFailed, errorx.KVf(errno.PluginMsgKey,
|
||||||
"expected '%s' to be of type 'object', but got '%T'", paramName, paramVal))
|
"expected '%s' to be of type 'object', but got '%T'", paramName, paramVal))
|
||||||
}
|
}
|
||||||
|
|
||||||
|
newParamValMap := map[string]any{}
|
||||||
for paramName_, paramVal_ := range paramValMap {
|
for paramName_, paramVal_ := range paramValMap {
|
||||||
paramSchema_, ok := schemaVal.Properties[paramName]
|
paramSchema_, ok := schemaVal.Properties[paramName_]
|
||||||
if !ok || t.disabledParam(paramSchema_.Value) { // Only the object field can be disabled, and the top level of request and response must be the object structure
|
if !ok || t.disabledParam(paramSchema_.Value) { // Only the object field can be disabled, and the top level of request and response must be the object structure
|
||||||
continue
|
continue
|
||||||
}
|
}
|
||||||
|
|
@ -1122,13 +1122,13 @@ func (t *toolExecutor) processWithInvalidRespProcessStrategyOfReturnErr(_ contex
|
||||||
return newParamValMap, nil
|
return newParamValMap, nil
|
||||||
|
|
||||||
case openapi3.TypeArray:
|
case openapi3.TypeArray:
|
||||||
newParamValSlice := []any{}
|
|
||||||
paramValSlice, ok := paramVal.([]any)
|
paramValSlice, ok := paramVal.([]any)
|
||||||
if !ok {
|
if !ok {
|
||||||
return nil, errorx.New(errno.ErrPluginExecuteToolFailed, errorx.KVf(errno.PluginMsgKey,
|
return nil, errorx.New(errno.ErrPluginExecuteToolFailed, errorx.KVf(errno.PluginMsgKey,
|
||||||
"expected '%s' to be of type 'array', but got '%T'", paramName, paramVal))
|
"expected '%s' to be of type 'array', but got '%T'", paramName, paramVal))
|
||||||
}
|
}
|
||||||
|
|
||||||
|
newParamValSlice := []any{}
|
||||||
for _, paramVal_ := range paramValSlice {
|
for _, paramVal_ := range paramValSlice {
|
||||||
newParamVal, err := processor(paramName, paramVal_, schemaVal.Items.Value)
|
newParamVal, err := processor(paramName, paramVal_, schemaVal.Items.Value)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
|
|
@ -1426,7 +1426,7 @@ func (t *toolExecutor) buildRequestBody(ctx context.Context, op *model.Openapi3O
|
||||||
continue
|
continue
|
||||||
}
|
}
|
||||||
|
|
||||||
_value, err := encoder.TryFixValueType(paramName, prop, value)
|
_value, err := encoder.TryCorrectValueType(paramName, prop, value)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return nil, "", err
|
return nil, "", err
|
||||||
}
|
}
|
||||||
|
|
|
||||||
Loading…
Reference in New Issue