Files
reflux/fieldx
what 659fc10bae fix: 修正 Example 函数命名与输出注释位置,让 go vet / go test 恢复可用
go vet ./... 此前有 13 处失败, 导致 go test ./...(默认带 vet)根本跑不起来,
必须加 -vet=off。这是既存问题, 与实现改动无关。

命名问题(12 处): Example 函数名的前缀必须是包内真实存在的标识符。
  ExampleStructMap_*  -> ExampleR_*         (包里没有 StructMap)
  ExampleSet_*        -> ExampleR_Set_*     (Set 是 R 的方法, 不是包级函数)
  ExampleAppend_*     -> ExampleR_Append_*  (同上)
  ExampleSchema_Unmarshal -> ExampleSchema_unmarshalJSON
                                            (Schema 没有 Unmarshal 方法,
                                             这个例子演示的是 json.Unmarshal)

输出注释位置(1 处): ExampleR_Append_typeConversionError 的 // Output: 后面
还跟着一条注释, 违反"Output 必须是最后一个注释块"。因为格式不合法, Go 一直
没把它当输出例子比对 —— 里面写的期望输出其实是错的(与实际信息不符)也没被发现。
把注释挪到 defer 之前, 并把期望输出更正为真实的 panic 信息。
已验证: 故意改错期望输出现在会导致测试失败, 说明确实在比对了。

现在 go vet ./... 干净, go test ./... 无需 -vet=off 即可运行。
2026-08-28 17:02:56 +08:00
..

FieldX - Schema-based Object Generator

FieldX 提供了基于预定义 Schema 生成 map[string]any 对象的功能。

功能特性

  • 固定值字段 (string): 在生成的对象中设置固定的字符串值
  • 字段引用 (field): 从源对象中获取指定字段的值,支持嵌套路径访问
  • 嵌套对象 (object): 支持生成多层嵌套的复杂对象结构

快速开始

import "git.fsdpf.net/go/reflux/fieldx"

// 1. 定义 JSON Schema
jsonSchema := `{
    "name": {"type": "field", "value": "userName"},
    "status": {"type": "string", "value": "active"}
}`

// 2. 从 JSON 创建 Schema
schema, _ := fieldx.SchemaFromJSON(jsonSchema)

// 3. 直接生成对象 (一行代码!)
source := map[string]any{"userName": "Alice"}
result, _ := schema.Generate(source)

// result: map[name:Alice status:active]

使用示例

推荐方式: 直接使用 Schema

最简单直接的方式:

import "git.fsdpf.net/go/reflux/fieldx"

// 1. 从 JSON 创建 Schema
schema, _ := fieldx.SchemaFromJSON(`{
    "name": {"type": "field", "value": "userName"},
    "status": {"type": "string", "value": "active"}
}`)

// 2. 直接生成对象
source := map[string]any{"userName": "Alice"}
result, _ := schema.Generate(source)
// result: map[name:Alice status:active]

创建 Schema 的方式

方式一: SchemaFromJSON (推荐)

schema, _ := fieldx.SchemaFromJSON(jsonStr)

方式二: json.Unmarshal

var schema fieldx.Schema
json.Unmarshal([]byte(jsonStr), &schema)

方式三: SchemaFromMap

var data map[string]any
json.Unmarshal([]byte(jsonStr), &data)
schema, _ := fieldx.SchemaFromMap(data)

方式四: 编程方式

schema := fieldx.Schema{
    "field": fieldx.Field{
        Type: fieldx.FieldTypeString,
        Value: "value",
    },
}

嵌套对象示例

schema := fieldx.Schema{
    "type": fieldx.Field{
        Type:  fieldx.FieldTypeString,
        Value: "user_profile",
    },
    "user": fieldx.Field{
        Type: fieldx.FieldTypeObject,
        Fields: fieldx.Schema{
            "id": fieldx.Field{
                Type:  fieldx.FieldTypeField,
                Value: "userId",
            },
            "name": fieldx.Field{
                Type:  fieldx.FieldTypeField,
                Value: "userName",
            },
        },
    },
}

source := map[string]any{
    "userId":   123,
    "userName": "Alice",
}

result, _ := schema.Generate(source)
// result: {"type": "user_profile", "user": {"id": 123, "name": "Alice"}}

嵌套路径访问

支持使用点号分隔的路径从嵌套的源对象中获取值:

schema := fieldx.Schema{
    "userId": fieldx.Field{
        Type:  fieldx.FieldTypeField,
        Value: "user.id",  // 使用点号访问嵌套字段
    },
    "userEmail": fieldx.Field{
        Type:  fieldx.FieldTypeField,
        Value: "user.contact.email",  // 支持多层嵌套
    },
}

source := map[string]any{
    "user": map[string]any{
        "id": 456,
        "contact": map[string]any{
            "email": "alice@example.com",
        },
    },
}

result, _ := schema.Generate(source)
// result: {"userId": 456, "userEmail": "alice@example.com"}

字段类型说明

FieldTypeString

固定字符串值类型。

fieldx.Field{
    Type:  fieldx.FieldTypeString,
    Value: "固定的字符串值",
}

FieldTypeField

从源对象获取字段值,支持点号分隔的嵌套路径。

fieldx.Field{
    Type:  fieldx.FieldTypeField,
    Value: "user.profile.name",  // 支持嵌套路径
}

FieldTypeObject

嵌套对象类型,使用 Fields 字段定义子结构。

fieldx.Field{
    Type: fieldx.FieldTypeObject,
    Fields: fieldx.Schema{
        // 嵌套的字段定义
    },
}

JSON Schema 格式

Schema 可以从 JSON 反序列化,这是最方便的使用方式:

基本格式

{
  "字段名": {
    "type": "string|field|object",
    "value": "根据type不同而不同",
    "fields": {/* 当type为object时使用 */}
  }
}

类型说明

1. string - 固定字符串值

{"type": "string", "value": "固定值"}

2. field - 从源对象获取字段(支持点号分隔的嵌套路径)

{"type": "field", "value": "user.name"}

3. object - 嵌套对象

{
  "type": "object",
  "fields": {
    "子字段名": {"type": "...", "value": "..."}
  }
}

完整 JSON Schema 示例

{
  "type": {
    "type": "string",
    "value": "user_profile"
  },
  "userId": {
    "type": "field",
    "value": "user.id"
  },
  "userName": {
    "type": "field",
    "value": "user.name"
  },
  "contact": {
    "type": "object",
    "fields": {
      "email": {
        "type": "field",
        "value": "user.email"
      },
      "phone": {
        "type": "string",
        "value": "N/A"
      }
    }
  }
}

使用此 Schema:

// 1. 从 JSON 创建 Schema
schema, _ := fieldx.SchemaFromJSON(jsonSchema)

// 2. 准备源数据
source := map[string]any{
    "user": map[string]any{
        "id":    123,
        "name":  "Alice",
        "email": "alice@example.com",
    },
}

// 3. 生成对象
result, _ := schema.Generate(source)

// 结果:
// {
//   "type": "user_profile",
//   "userId": 123,
//   "userName": "Alice",
//   "contact": {
//     "email": "alice@example.com",
//     "phone": "N/A"
//   }
// }

错误处理

当引用的字段不存在时,Generate() 方法会返回错误:

result, err := schema.Generate(source)
if err != nil {
    // 处理错误,例如:
    // "failed to generate field xxx: field not found: yyy"
}

完整示例

查看 example_test.go 获取更多使用示例。