如果不使用索引(例如,Set 数据结构)来存储 nfType
相关的记录,我们可以直接将所有 NF Profile 存储为 Hash,并在每次查询时遍历所有记录。尽管这种方法在数据量较小时可以工作,但在大规模数据时效率会低下。
数据结构设计
- 使用 Hash 存储每个 NF Profile:
- 键:
nfprofile:<id>
(唯一标识符) - 字段:
nfType
nfStatus
plmnList
ipv4Addresses
nfInstanceId
- 键:
示例代码实现
下面是 Go 语言中如何实现这个数据结构,并提供存储和获取功能的示例代码。
1. 实现存储与获取方法
package main
import (
"context"
"encoding/json"
"fmt"
"log"
"github.com/go-redis/redis/v8"
)
type NfProfile struct {
ID string `json:"_id"`
NfType string `json:"nfType"`
NfStatus string `json:"nfStatus"`
PmlnList []Plmn `json:"plmnList"`
Ipv4Addresses []string `json:"ipv4Addresses"`
NfInstanceId string `json:"nfInstanceId"`
}
type Plmn struct {
MCC string `json:"mcc"`
MNC string `json:"mnc"`
}
// 将NfProfile数据保存到Redis
func storeProfile(ctx context.Context, rdb *redis.Client, profile NfProfile) error {
key := fmt.Sprintf("nfprofile:%s", profile.ID)
// 存入Hash表
if err := rdb.HSet(ctx, key, map[string]interface{}{
"nfType": profile.NfType,
"nfStatus": profile.NfStatus,
"plmnList": profile.PmlnList,
"ipv4Addresses": profile.Ipv4Addresses,
"nfInstanceId": profile.NfInstanceId,
}).Err(); err != nil {
return err
}
return nil
}
// 获取所有 NfProfiles 并根据 nfType 筛选
func getProfilesByNfType(ctx context.Context, rdb *redis.Client, nfType string) ([]NfProfile, error) {
var profiles []NfProfile
keys, err := rdb.Keys(ctx, "nfprofile:*").Result() // 获取所有NF Profiles的键
if err != nil || len(keys) == 0 {
return nil , err
}
for _, key := range keys {
recordData, err := rdb.HGetAll(ctx, key).Result()
if err != nil || len(recordData) == 0 { continue }
// 检查 nfType 是否匹配
if recordData["nfType"] == nfType {
var profile NfProfile
// 手动赋值字段信息
profile.ID = key[len("nfprofile:"):]
// 获取其他字段信息并解析为对应类型
if val, exists := recordData["nfStatus"]; exists {
profile.NfStatus = val
}
if val , exists:=recordData["plmnList"]; exists{
json.Unmarshal([]byte(val),&profile.PmlnList)
}
if val , exists:=recordData["ipv4Addresses"]; exists{
json.Unmarshal([]byte(val),&profile.Ipv4Addresses)
}
if val , exists:=recordData["nfInstanceId"]; exists{
profile.NfInstanceId =val
}
profiles = append(profiles ,profile)
}
}
return profiles,nil
}
func main() {
ctx := context.Background()
rdb := redis.NewClient(&redis.Options{
Addr: "localhost:6379",
})
defer rdb.Close()
profile1 := NfProfile{
ID: "123",
NfType: "gateway",
NfStatus: "active",
PmlnList: []Plmn{{MCC: "460", MNC: "00"}},
Ipv4Addresses: []string{"192.168.1.1"},
NfInstanceId: "inst123",
}
err := storeProfile(ctx,rdb ,profile1)
if err !=nil{ log.Fatalf("Failed to store data in Redis : %v",err)}
profiles ,err:=getProfilesByNfType (ctx,rdb,"gateway")
if err!=nil{log.Fatalf("Failed to retrieve data : %v",err)}
fmt.Printf("Retrieved Profiles by Type 'gateway': %+v\n", profiles)
}
注意事项:
- 性能问题:由于我们没有建立索引,这种方式在数据库中的记录数量很大时,性能会变得非常低下。
- JSON 序列化与反序列化:对于复杂的数据结构(如切片),需要通过 JSON 来进行存取,你可能还需额外处理编码和解码。
- 错误处理:确保你有良好的错误处理,以避免程序因单个操作失败而崩溃。
这样你就能通过简单的方法实现基于 NF Type 的记录存储与获取,而无需创建额外的索引。
内容由零声教学AI助手提供,问题来源于学员提问