feat: 增强 map 大小写不敏感支持和函数重命名
- 新增 tryMapFieldKey 函数,返回 map 中实际存在的键(支持大小写转换) - 优化 setFieldValue 方法,使用 tryMapFieldKey 查找已存在字段并更新 - 优化 setNestedValue 方法,修复嵌套 map 大小写处理和 interface 包装问题 - 重命名函数以提高代码清晰度: - tryStructField → tryStructFieldValue - tryMapField → tryMapFieldValue - tryMapFieldWithKey → tryMapFieldKey - 新增 rfx_map_case_test.go 包含 16 个测试用例,覆盖基本、嵌套、边界等场景
This commit is contained in:
39
rfx.go
39
rfx.go
@@ -131,7 +131,7 @@ func (r *rfx) setNestedValue(current reflect.Value, keys []string, v any) bool {
|
||||
|
||||
switch current.Kind() {
|
||||
case reflect.Struct:
|
||||
field := tryStructField(current, firstKey)
|
||||
field := tryStructFieldValue(current, firstKey)
|
||||
if !field.IsValid() {
|
||||
return false
|
||||
}
|
||||
@@ -139,24 +139,34 @@ func (r *rfx) setNestedValue(current reflect.Value, keys []string, v any) bool {
|
||||
|
||||
case reflect.Map:
|
||||
// Map 的特殊处理
|
||||
mapKey := reflect.ValueOf(firstKey)
|
||||
mapValue := current.MapIndex(mapKey)
|
||||
// 使用 tryMapFieldKey 获取实际的键
|
||||
actualKey := tryMapFieldKey(current, firstKey)
|
||||
if !actualKey.IsValid() {
|
||||
return false
|
||||
}
|
||||
|
||||
mapValue := current.MapIndex(actualKey)
|
||||
if !mapValue.IsValid() {
|
||||
return false
|
||||
}
|
||||
|
||||
// 解开 interface 包装获取实际的值
|
||||
actualValue := mapValue
|
||||
for actualValue.Kind() == reflect.Interface && !actualValue.IsNil() {
|
||||
actualValue = actualValue.Elem()
|
||||
}
|
||||
|
||||
// 创建 map 值的副本以便修改
|
||||
valueCopy := reflect.New(mapValue.Type()).Elem()
|
||||
valueCopy.Set(mapValue)
|
||||
valueCopy := reflect.New(actualValue.Type()).Elem()
|
||||
valueCopy.Set(actualValue)
|
||||
|
||||
// 在副本上递归设置值
|
||||
if !r.setNestedValue(valueCopy, remainingKeys, v) {
|
||||
return false
|
||||
}
|
||||
|
||||
// 将修改后的值设置回 map
|
||||
current.SetMapIndex(mapKey, valueCopy)
|
||||
// 将修改后的值设置回 map,使用实际找到的键
|
||||
current.SetMapIndex(actualKey, valueCopy)
|
||||
return true
|
||||
|
||||
case reflect.Slice, reflect.Array:
|
||||
@@ -200,7 +210,7 @@ func (r *rfx) setFieldValue(target reflect.Value, key string, v any) bool {
|
||||
|
||||
switch target.Kind() {
|
||||
case reflect.Struct:
|
||||
field := tryStructField(target, key)
|
||||
field := tryStructFieldValue(target, key)
|
||||
if !field.IsValid() || !field.CanSet() {
|
||||
return false
|
||||
}
|
||||
@@ -210,6 +220,19 @@ func (r *rfx) setFieldValue(target reflect.Value, key string, v any) bool {
|
||||
target.Set(reflect.MakeMap(target.Type()))
|
||||
}
|
||||
|
||||
// 先尝试使用 tryMapFieldKey 检查字段是否已存在并获取实际的键
|
||||
actualKey := tryMapFieldKey(target, key)
|
||||
if actualKey.IsValid() {
|
||||
// 字段已存在,创建新值用于设置
|
||||
newValue := reflect.New(target.Type().Elem()).Elem()
|
||||
if !r.setValue(newValue, v) {
|
||||
return false
|
||||
}
|
||||
target.SetMapIndex(actualKey, newValue)
|
||||
return true
|
||||
}
|
||||
|
||||
// 字段不存在,创建新的 map 值
|
||||
// 处理 nil 值的情况
|
||||
if v == nil {
|
||||
target.SetMapIndex(reflect.ValueOf(key), reflect.Zero(target.Type().Elem()))
|
||||
|
||||
Reference in New Issue
Block a user