英文:
How to store a value of type context.CancelFunc using context.WithValue()?
问题
要在ctx中存储string类型的数据,需要使用类型定义来定义键和值,如下所示:
    // 用于表示追踪ID的类型
    type TraceID string
    
    // 用于键的类型定义。键是特定类型的,只有相同类型的值才能匹配。
    type TraceIDKey int
    
    func main() {
    
    	// 为此请求创建一个追踪ID。
    	traceID := TraceID("f47ac10b-58cc-0372-8567-0e02b2c3d479")
    
    	// 声明一个值为零的键,类型为TraceIDKey。
    	const traceIDKey TraceIDKey = 0
    
    	// 使用键类型的零值将traceID值存储在上下文中。
    	ctx := context.WithValue(context.Background(), traceIDKey, traceID)
    
    	// 从上下文值中检索该追踪ID值。
    	if uuid, ok := ctx.Value(traceIDKey).(TraceID); ok {
    		fmt.Println("TraceID:", uuid)
    	}
    
    	// 不使用正确的键类型从上下文值中检索该追踪ID值。
    	if _, ok := ctx.Value(0).(TraceID); !ok {
    		fmt.Println("TraceID Not Found")
    	}
    }
如何使用context.WithValue() API存储context.CancelFunc类型的值?
英文:
To store string type data in ctx, type definitions need to be used for both key & value, as shown below:
    // Sample program to show how to store and retrieve
    // values from a context.
    package main
    
    import (
    	"context"
    	"fmt"
    )
    
    // TraceID represents the trace id.
    type TraceID string
    
    // TraceIDKey is the type of value to use for the key. The key is
    // type specific and only values of the same type will match.
    type TraceIDKey int
    
    func main() {
    
    	// Create a traceID for this request.
    	traceID := TraceID("f47ac10b-58cc-0372-8567-0e02b2c3d479")
    
    	// Declare a key with the value of zero of type userKey.
    	const traceIDKey TraceIDKey = 0
    
    	// Store the traceID value inside the context with a value of
    	// zero for the key type.
    	ctx := context.WithValue(context.Background(), traceIDKey, traceID)
    
    	// Retrieve that traceID value from the Context value bag.
    	if uuid, ok := ctx.Value(traceIDKey).(TraceID); ok {
    		fmt.Println("TraceID:", uuid)
    	}
    
    	// Retrieve that traceID value from the Context value bag not
    	// using the proper key type.
    	if _, ok := ctx.Value(0).(TraceID); !ok {
    		fmt.Println("TraceID Not Found")
    	}
    }
<hr>
How to store a value of type context.CancelFunc using context.WithValue() api?
答案1
得分: 4
你部分正确。你应该使用自定义类型作为上下文键,而不是使用内置类型,以确保避免冲突。这个类型应该是未导出的,除非你希望其他包能够读取/写入你的上下文键。然而,值可以是任何你喜欢的类型,例如:
package main
import (
	"context"
	"fmt"
)
type contextKey int
const (
	traceIDKey contextKey = iota
	aFunctionWhyNot
)
func main() {
	// 为这个请求创建一个 traceID。
	traceID := "f47ac10b-58cc-0372-8567-0e02b2c3d479"
	// 使用零值为键类型,在上下文中存储 traceID 值。
	ctx := context.WithValue(context.Background(), traceIDKey, traceID)
	// 从上下文值中检索 traceID 值。
	if uuid, ok := ctx.Value(traceIDKey).(string); ok {
		fmt.Println("TraceID:", uuid)
	}
	// 或者一个函数
	ctx = context.WithValue(ctx, aFunctionWhyNot, func() { fmt.Println("lol, I'm a function on a context") })
	// 可以调用它
	if f, ok := ctx.Value(aFunctionWhyNot).(func()); ok {
		f()
	}
}
希望对你有帮助!
英文:
You are partially correct. You should use a bespoke type for your context key rather than the builtin types to make collisions impossible. This type should be unexported unless you want other packages to be able to read/write your context key. However the value can be anything you like, eg:
package main
import (
	"context"
	"fmt"
)
type contextKey int
const (
	traceIDKey contextKey = iota
	aFunctionWhyNot
)
func main() {
	// Create a traceID for this request.
	traceID := "f47ac10b-58cc-0372-8567-0e02b2c3d479"
	// Store the traceID value inside the context with a value of
	// zero for the key type.
	ctx := context.WithValue(context.Background(), traceIDKey, traceID)
	// Retrieve that traceID value from the Context value bag.
	if uuid, ok := ctx.Value(traceIDKey).(string); ok {
		fmt.Println("TraceID:", uuid)
	}
	// Or a function
	ctx = context.WithValue(ctx, aFunctionWhyNot, func() { fmt.Println("lol, I'm a function on a context") })
	// Call it maybe
	if f, ok := ctx.Value(aFunctionWhyNot).(func()); ok {
		f()
	}
}
答案2
得分: 2
你可以像存储其他任何值一样,将函数存储在上下文中:
type cancelFuncKeyType struct{}
var cancelFuncKey = cancelFuncKeyType{}
...
newctx := context.WithValue(oldctx, cancelFuncKey, cancelFunc)
cFunc := newctx.Value(cancelFuncKey).(context.CancelFunc)
英文:
You can store a function in the context the same way you store any other value:
type cancelFuncKeyType struct{}
var cancelFuncKey =cancelFuncKeyType{}
...
newctx:=context.WithValue(oldctx,cancelFuncKey,cancelFunc)
cFunc:=newctx.Value(cancelFuncKey).(context.CancelFunc)
通过集体智慧和协作来改善编程学习和解决问题的方式。致力于成为全球开发者共同参与的知识库,让每个人都能够通过互相帮助和分享经验来进步。


评论