I read the few posted issues regarding the use of context.Context with *gin.Context. Maybe I'm missing something, but it seems the advice is to derive an AppEngine context from the gin.Context. This generally works, but there seems to be no way to get the gin.Context back from the derived context. I ended up changing the Value() method to the following:

func (c *Context) Value(key interface{}) interface{} {
    switch key {
    case -1:
        return c
    case 0:
        return c.Request
    }

    if keyAsString, ok := key.(string); ok {
        val, _ := c.Get(keyAsString)
        return val
    }
    return nil
}

Passing -1 to Value returns the gin.Context, which allows calling the various methods on the gin.Context (e.g., PostForm, Param, etc.)

Basically, my question is whether there is already to retrieve the gin.Context from the AppEngine context derived from gin.Context, without changing the existing code.

Comment From: ljluestc

package main

import (
    "context"
    "fmt"
    "github.com/gin-gonic/gin"
    "net/http"
)

// Define a custom key type to avoid key collisions
type contextKey string

const ginContextKey contextKey = "ginContext"

// A simple handler to simulate the usage
func handler(c *gin.Context) {
    // Store *gin.Context into context.Context
    ctx := context.WithValue(c, ginContextKey, c)

    // Call another function passing context
    anotherFunction(ctx)
}

func anotherFunction(ctx context.Context) {
    // Retrieve *gin.Context from context
    ginContext := ctx.Value(ginContextKey).(*gin.Context)

    // Now you can use ginContext methods
    param := ginContext.Param("id")
    fmt.Printf("Retrieved Param: %s\n", param)

    // Continue using ginContext as needed
}

func main() {
    r := gin.Default()

    r.GET("/test/:id", handler)

    r.Run(":8080")
}