2017-09-26 127 views
0

我深陷的杂草可能是一个简单的问题。我需要通过调用第三方CAS认证服务来包装func。我正在使用go-cas来做到这一点,直到我开始添加路由需求。我选择了Julien Schmidt的httprouter,不知何故我需要将它与go-cas一起工作。链接CAS中间件和httprouter()路由

如果我没有弄错,我需要使用某种定制设计的中间件从处理程序到处理程序。我觉得链需要去是这样的:

http.Handler - > FUNC(http.ResponseWriter,* http.Request,httprouter.Params)

...第一次是什么CAS想,和第二个是httprouter想要的。但是我现在很迷茫,因为我无法做出正确的决定。

感谢您的任何建议!


在下面的代码,调用...

router.Handler("GET", "/", client.HandleFunc(defaultHandler)) 

...产生此错误:

“不能使用的DefaultHandler(类型FUNC(http.ResponseWriter,* HTTP .Request,httprouter.Params))作为参数类型FUNC(http.ResponseWriter,* http.Request)到client.HandleFunc”

这里的非工作代码:

package main 

import (
    "fmt" 
    "log" 
    "net/http" 
    "strings" 
    "time" 

    "github.com/go-cas/cas" 
    "github.com/julienschmidt/httprouter" 
) 

func defaultHandler(w http.ResponseWriter, r *http.Request, ps httprouter.Params) { 
    if !cas.IsAuthenticated(r) { 
     cas.RedirectToLogin(w, r) 
    } 

    pageID := ps.ByName("pageID") 

    type pageModel struct { 
     Title string 
     PageID string 
    } 

    model := pageModel{ 
     Title: "Seminars", 
     PageID: pageID, 
    } 
    render.ToBrowser(w, "views/index.html", &model) 
} 


func main() { 

    u, _ := url.Parse("https://cas_example_server.com") 

    client := cas.NewClient(&cas.Options{ 
     URL: u, 
    }) 

    router := httprouter.New() 

    //This line fails with the message: 

    //"Cannot use defaultHandler (type func(http.ResponseWriter, *http.Request, httprouter.Params)) 
    //as type func(http.ResponseWriter, *http.Request) in argument to client.HandleFunc" 

    router.Handler("GET", "/", client.HandleFunc(defaultHandler)) 

    err := http.ListenAndServe(":8080", router) 
    if err != nil { 
     panic(err) 
    } 

} 

回答

0

中间件可以使用请求上下文来将数据传递到不同的签名处理程序:

import (
    "net/http" 
    "net/url" 

    "github.com/go-cas/cas" 
    "github.com/julienschmidt/httprouter" 
    "golang.org/x/net/context" 
) 

func defaultHandler(w http.ResponseWriter, r *http.Request) { 
    if !cas.IsAuthenticated(r) { 
     cas.RedirectToLogin(w, r) 
    } 

    ps := r.Context().Value("params").(httprouter.Params) 

    // business logic 
} 


func main() { 

    u, _ := url.Parse("https://cas_example_server.com") 

    client := cas.NewClient(&cas.Options{ 
     URL: u, 
    }) 

    router := httprouter.New() 

    //This line fails with the message: 

    //"Cannot use defaultHandler (type func(http.ResponseWriter, *http.Request, httprouter.Params)) 
    //as type func(http.ResponseWriter, *http.Request) in argument to client.HandleFunc" 

    router.Handler("GET", "/", func(w http.ResponseWriter, r *http.Request, ps httprouter.Params) { 
     newContext := context.WithValue(r.Context(), "params", ps) 
     r.WithContext(newContext) 
     client.HandleFunc(defaultHandler)(w, r) 
    }) 

    err := http.ListenAndServe(":8080", router) 
    if err != nil { 
     panic(err) 
    } 

} 

UPDATE: 有许多有用的库来保存你的HTTP处理程序堆栈这样https://github.com/urfave/negroni