mirror of
https://github.com/pomerium/pomerium.git
synced 2025-07-25 20:49:30 +02:00
jwt: require logged in user to return .pomerium/jwt (#3809)
jwt: require logged in user to return .pomerium/jwt (#3807) * jwt: require logged in user to return .pomerium/jwt * fix test * update test Co-authored-by: Caleb Doxsey <cdoxsey@pomerium.com>
This commit is contained in:
parent
ebee7c7920
commit
0b3d4f3a6f
4 changed files with 24 additions and 5 deletions
|
@ -59,6 +59,7 @@ default deny = [false, set()]
|
|||
|
||||
pomerium_routes_0 = [true, {"pomerium-route"}] {
|
||||
contains(input.http.url, "/.pomerium/")
|
||||
not contains(input.http.url, "/.pomerium/jwt")
|
||||
}
|
||||
|
||||
else = [false, {"non-pomerium-route"}] {
|
||||
|
|
|
@ -11,6 +11,9 @@ var pomeriumRoutesBody = ast.Body{
|
|||
ast.MustParseExpr(`
|
||||
contains(input.http.url, "/.pomerium/")
|
||||
`),
|
||||
ast.MustParseExpr(`
|
||||
not contains(input.http.url, "/.pomerium/jwt")
|
||||
`),
|
||||
}
|
||||
|
||||
type pomeriumRoutesCriterion struct {
|
||||
|
|
|
@ -8,6 +8,7 @@ import (
|
|||
"net/http"
|
||||
"net/url"
|
||||
|
||||
"github.com/go-jose/go-jose/v3/jwt"
|
||||
"github.com/gorilla/mux"
|
||||
|
||||
"github.com/pomerium/pomerium/internal/httputil"
|
||||
|
@ -178,12 +179,25 @@ func (p *Proxy) ProgrammaticLogin(w http.ResponseWriter, r *http.Request) error
|
|||
|
||||
// jwtAssertion returns the current request's JWT assertion (rfc7519#section-10.3.1).
|
||||
func (p *Proxy) jwtAssertion(w http.ResponseWriter, r *http.Request) error {
|
||||
assertionJWT := r.Header.Get(httputil.HeaderPomeriumJWTAssertion)
|
||||
if assertionJWT == "" {
|
||||
rawAssertionJWT := r.Header.Get(httputil.HeaderPomeriumJWTAssertion)
|
||||
if rawAssertionJWT == "" {
|
||||
return httputil.NewError(http.StatusNotFound, errors.New("jwt not found"))
|
||||
}
|
||||
|
||||
assertionJWT, err := jwt.ParseSigned(rawAssertionJWT)
|
||||
if err != nil {
|
||||
return httputil.NewError(http.StatusNotFound, errors.New("jwt not found"))
|
||||
}
|
||||
|
||||
var dst struct {
|
||||
Subject string `json:"sub"`
|
||||
}
|
||||
if assertionJWT.UnsafeClaimsWithoutVerification(&dst) != nil || dst.Subject == "" {
|
||||
return httputil.NewError(http.StatusUnauthorized, errors.New("jwt not found"))
|
||||
}
|
||||
|
||||
w.Header().Set("Content-Type", "application/jwt")
|
||||
w.WriteHeader(http.StatusOK)
|
||||
_, _ = io.WriteString(w, assertionJWT)
|
||||
_, _ = io.WriteString(w, rawAssertionJWT)
|
||||
return nil
|
||||
}
|
||||
|
|
|
@ -547,13 +547,14 @@ func TestProxy_jwt(t *testing.T) {
|
|||
}
|
||||
|
||||
// with upstream request headers being set
|
||||
rawJWT := "eyJ0eXAiOiJKV1QiLCJhbGciOiJIUzI1NiJ9.eyJzdWIiOiIxMjM0NTY3ODkwIiwibmFtZSI6IkpvaG4gRG9lIiwiYWRtaW4iOnRydWUsImlhdCI6MTY3MDg4OTI0MSwiZXhwIjoxNjcwODkyODQxfQ.YoROB12_-a8VxikPqrYOA576pLYoLFeGwXAOWCGpXgM"
|
||||
req, _ = http.NewRequest("GET", "https://www.example.com/.pomerium/jwt", nil)
|
||||
w = httptest.NewRecorder()
|
||||
req.Header.Set(httputil.HeaderPomeriumJWTAssertion, "MOCK_JWT")
|
||||
req.Header.Set(httputil.HeaderPomeriumJWTAssertion, rawJWT)
|
||||
err = proxy.jwtAssertion(w, req)
|
||||
if !assert.NoError(t, err) {
|
||||
return
|
||||
}
|
||||
assert.Equal(t, "application/jwt", w.Header().Get("Content-Type"))
|
||||
assert.Equal(t, w.Body.String(), "MOCK_JWT")
|
||||
assert.Equal(t, w.Body.String(), rawJWT)
|
||||
}
|
||||
|
|
Loading…
Add table
Add a link
Reference in a new issue