英文:
Filtering what information is displayed from MongoDB in Go api
问题
我是Go和React的新手,我正在使用它们进行这个小项目。Go正在运行一个使用Mongodb的后端API。
我在Go中从Mongo中获取用户列表,然后将其发送到React,问题是Mongo给我返回了用户的所有字段(_id、password和username),我只想要username字段。我不明白如何过滤这些字段并阻止所有字段从Go发送到React。
Go API的JSON输出:
{
"Success": true,
"Data": [
{
"_id": "6205ac3d72c15c920a424608",
"password": {
"Subtype": 0,
"Data": "removed for security"
},
"username": "removed for security"
},
{
"_id": "6206b44afb8b044fdba76b8f",
"password": {
"Subtype": 0,
"Data": "removed for security"
},
"username": "removed for security"
}
]
}
这是我指定路由的Go代码:
// 路由:获取用户列表
func RouteGetUsers(w http.ResponseWriter, r *http.Request, p httprouter.Params) {
// 设置内容类型为JSON
w.Header().Set("Content-Type", "application/json")
type Response struct {
Success bool `json:"Success"`
Data []bson.M `json:"Data"`
}
// 加载环境变量文件
err := godotenv.Load("variables.env")
if err != nil {
log.Fatal("加载.env文件时出错")
}
// 获取Mongo DB环境变量
uri := os.Getenv("MONGO_URI")
if uri == "" {
log.Fatal("您必须设置您的'MONGO_URI'环境变量。请参阅\n\t https://docs.mongodb.com/drivers/go/current/usage-examples/#environment-variable")
}
// 连接到Mongo数据库
client, err := mongo.Connect(context.TODO(), options.Client().ApplyURI(uri))
if err != nil {
panic(err)
}
// 在函数结束时关闭数据库连接
defer func() {
if err := client.Disconnect(context.TODO()); err != nil {
panic(err)
}
}()
// 选择数据库名称和集合名称
coll := client.Database("go_project1").Collection("users")
// 查询数据库获取用户列表
cursor, err := coll.Find(context.TODO(), bson.D{})
// 如果没有找到文档,则发送响应并返回
if err == mongo.ErrNoDocuments {
fmt.Printf("未找到文档")
return
}
// 设置一个变量用于存储数据库结果
var results []bson.M
// 将所有数据库结果发送到results变量
if err = cursor.All(context.TODO(), &results); err != nil {
panic(err)
}
// 使用Response结构设置一个变量
response := Response{
Success: true,
Data: results,
}
// 转换为JSON
responseJson, err := json.Marshal(response)
if err != nil {
fmt.Println(err)
}
// 以JSON格式向用户发送成功响应
fmt.Fprintf(w, "%s\n", responseJson)
}
英文:
I am new to Go and React, both of which I am using for this mini project. Go is running a backend api using Mongodb.
I am fetching the user list from Mongo in Go, and then sending that to React, problem is Mongo is giving me all of the fields for the user (_id, password, and username), I only want username. I am not understanding how I can filter this and prevent all fields from being sent from Go to React.
JSON Output from Go API:
{
"Success": true,
"Data": [
{
"_id": "6205ac3d72c15c920a424608",
"password": {
"Subtype": 0,
"Data": "removed for security"
},
"username": "removed for security"
},
{
"_id": "6206b44afb8b044fdba76b8f",
"password": {
"Subtype": 0,
"Data": "removed for security"
},
"username": "removed for security"
}
]
}
Here is my Go code for the specified route:
// Route: Get Users, for getting a list of users
func RouteGetUsers(w http.ResponseWriter, r *http.Request, p httprouter.Params) {
// Set content-type to JSON
w.Header().Set("Content-Type", "application/json")
type Response struct {
Success bool `json:"Success"`
Data []bson.M `json:"Data"`
}
// Load the env file
err := godotenv.Load("variables.env")
if err != nil {
log.Fatal("Error loading .env file")
}
// Get Mongo DB environment variable
uri := os.Getenv("MONGO_URI")
if uri == "" {
log.Fatal("You must set your 'MONGO_URI' environmental variable. See\n\t https://docs.mongodb.com/drivers/go/current/usage-examples/#environment-variable")
}
// Connect to Mongo Database
client, err := mongo.Connect(context.TODO(), options.Client().ApplyURI(uri))
if err != nil {
panic(err)
}
// Close the database connection at the end of the function
defer func() {
if err := client.Disconnect(context.TODO()); err != nil {
panic(err)
}
}()
// Select the database name and collection name
coll := client.Database("go_project1").Collection("users")
// Query the database for the user list
cursor, err := coll.Find(context.TODO(), bson.D{})
// If no documents were found, send a response and return
if err == mongo.ErrNoDocuments {
fmt.Printf("No documents were found")
return
}
// Setup a variable for the database results
var results []bson.M
// Send all database results to results variable
if err = cursor.All(context.TODO(), &results); err != nil {
panic(err)
}
// Setup a variable with the ResponseStandard struct
response := Response{
Success: true,
Data: results,
}
// Marshal into JSON
responseJson, err := json.Marshal(response)
if err != nil {
fmt.Println(err)
}
// Send success response to user in JSON
fmt.Fprintf(w, "%s\n", responseJson)
}
答案1
得分: 1
使用投影选项:
opts := options.Find().SetProjection(bson.D{{"username", 1}})
cursor, err := coll.Find(context.TODO(), bson.D{}, opts)
作为第二种方法:声明一个包含你想要的字段的类型,并将其提取到该类型中。
type Data struct {
Username string `bson:"username" json:"username"`
}
...
var data []Data
if err = cursor.All(context.TODO(), &data); err != nil { ...
...
var response = struct {
Success bool `json:"Success"`
Data []Data `json:"Data"`
}{
true,
data,
}
responseJson, err := json.Marshal(response)
...
第三种方法:过滤问题中的映射:
for _, result := range results {
for k := range result {
if k != "username" {
delete(result, k)
}
}
}
英文:
Use the projection option:
opts := options.Find().SetProjection(bson.D{{"username", 1}})
cursor, err := coll.Find(context.TODO(), bson.D{}, opts)
As second approach: Declare a type with the fields you want, and fetch to that type.
type Data struct {
Username string `bson:"username" json:"username"`
}
...
var data []Data
if err = cursor.All(context.TODO(), &data); err != nil { ...
...
var response = struct {
Success bool `json:"Success"`
Data []Data `json:"Data"`
}{
true,
data,
}
responseJson, err := json.Marshal(response)
...
A third approach: Filter the maps in the question:
for _, result := range results {
for k := range result {
if k != "username" {
delete(result, k)
}
}
}
通过集体智慧和协作来改善编程学习和解决问题的方式。致力于成为全球开发者共同参与的知识库,让每个人都能够通过互相帮助和分享经验来进步。
评论