mirror of
https://github.com/coder/coder.git
synced 2025-07-03 16:13:58 +00:00
feat: enable key rotation (#15066)
This PR contains the remaining logic necessary to hook up key rotation to the product.
This commit is contained in:
@ -13,6 +13,7 @@ import (
|
||||
"testing"
|
||||
"time"
|
||||
|
||||
"github.com/go-jose/go-jose/v4/jwt"
|
||||
"github.com/google/uuid"
|
||||
"github.com/stretchr/testify/assert"
|
||||
"github.com/stretchr/testify/require"
|
||||
@ -20,6 +21,7 @@ import (
|
||||
"github.com/coder/coder/v2/agent/agenttest"
|
||||
"github.com/coder/coder/v2/coderd/coderdtest"
|
||||
"github.com/coder/coder/v2/coderd/httpmw"
|
||||
"github.com/coder/coder/v2/coderd/jwtutils"
|
||||
"github.com/coder/coder/v2/coderd/workspaceapps"
|
||||
"github.com/coder/coder/v2/coderd/workspaceapps/appurl"
|
||||
"github.com/coder/coder/v2/codersdk"
|
||||
@ -94,8 +96,7 @@ func Test_ResolveRequest(t *testing.T) {
|
||||
_ = closer.Close()
|
||||
})
|
||||
|
||||
ctx, cancel := context.WithTimeout(context.Background(), testutil.WaitMedium)
|
||||
t.Cleanup(cancel)
|
||||
ctx := testutil.Context(t, testutil.WaitMedium)
|
||||
|
||||
firstUser := coderdtest.CreateFirstUser(t, client)
|
||||
me, err := client.User(ctx, codersdk.Me)
|
||||
@ -276,15 +277,17 @@ func Test_ResolveRequest(t *testing.T) {
|
||||
_ = w.Body.Close()
|
||||
|
||||
require.Equal(t, &workspaceapps.SignedToken{
|
||||
RegisteredClaims: jwtutils.RegisteredClaims{
|
||||
Expiry: jwt.NewNumericDate(token.Expiry.Time()),
|
||||
},
|
||||
Request: req,
|
||||
Expiry: token.Expiry, // ignored to avoid flakiness
|
||||
UserID: me.ID,
|
||||
WorkspaceID: workspace.ID,
|
||||
AgentID: agentID,
|
||||
AppURL: appURL,
|
||||
}, token)
|
||||
require.NotZero(t, token.Expiry)
|
||||
require.WithinDuration(t, time.Now().Add(workspaceapps.DefaultTokenExpiry), token.Expiry, time.Minute)
|
||||
require.WithinDuration(t, time.Now().Add(workspaceapps.DefaultTokenExpiry), token.Expiry.Time(), time.Minute)
|
||||
|
||||
// Check that the token was set in the response and is valid.
|
||||
require.Len(t, w.Cookies(), 1)
|
||||
@ -292,10 +295,11 @@ func Test_ResolveRequest(t *testing.T) {
|
||||
require.Equal(t, codersdk.SignedAppTokenCookie, cookie.Name)
|
||||
require.Equal(t, req.BasePath, cookie.Path)
|
||||
|
||||
parsedToken, err := api.AppSecurityKey.VerifySignedToken(cookie.Value)
|
||||
var parsedToken workspaceapps.SignedToken
|
||||
err := jwtutils.Verify(ctx, api.AppSigningKeyCache, cookie.Value, &parsedToken)
|
||||
require.NoError(t, err)
|
||||
// normalize expiry
|
||||
require.WithinDuration(t, token.Expiry, parsedToken.Expiry, 2*time.Second)
|
||||
require.WithinDuration(t, token.Expiry.Time(), parsedToken.Expiry.Time(), 2*time.Second)
|
||||
parsedToken.Expiry = token.Expiry
|
||||
require.Equal(t, token, &parsedToken)
|
||||
|
||||
@ -314,7 +318,7 @@ func Test_ResolveRequest(t *testing.T) {
|
||||
})
|
||||
require.True(t, ok)
|
||||
// normalize expiry
|
||||
require.WithinDuration(t, token.Expiry, secondToken.Expiry, 2*time.Second)
|
||||
require.WithinDuration(t, token.Expiry.Time(), secondToken.Expiry.Time(), 2*time.Second)
|
||||
secondToken.Expiry = token.Expiry
|
||||
require.Equal(t, token, secondToken)
|
||||
}
|
||||
@ -540,13 +544,16 @@ func Test_ResolveRequest(t *testing.T) {
|
||||
// App name differs
|
||||
AppSlugOrPort: appNamePublic,
|
||||
}).Normalize(),
|
||||
Expiry: time.Now().Add(time.Minute),
|
||||
RegisteredClaims: jwtutils.RegisteredClaims{
|
||||
Expiry: jwt.NewNumericDate(time.Now().Add(time.Minute)),
|
||||
},
|
||||
UserID: me.ID,
|
||||
WorkspaceID: workspace.ID,
|
||||
AgentID: agentID,
|
||||
AppURL: appURL,
|
||||
}
|
||||
badTokenStr, err := api.AppSecurityKey.SignToken(badToken)
|
||||
|
||||
badTokenStr, err := jwtutils.Sign(ctx, api.AppSigningKeyCache, badToken)
|
||||
require.NoError(t, err)
|
||||
|
||||
req := (workspaceapps.Request{
|
||||
@ -589,7 +596,8 @@ func Test_ResolveRequest(t *testing.T) {
|
||||
require.Len(t, cookies, 1)
|
||||
require.Equal(t, cookies[0].Name, codersdk.SignedAppTokenCookie)
|
||||
require.NotEqual(t, cookies[0].Value, badTokenStr)
|
||||
parsedToken, err := api.AppSecurityKey.VerifySignedToken(cookies[0].Value)
|
||||
var parsedToken workspaceapps.SignedToken
|
||||
err = jwtutils.Verify(ctx, api.AppSigningKeyCache, cookies[0].Value, &parsedToken)
|
||||
require.NoError(t, err)
|
||||
require.Equal(t, appNameOwner, parsedToken.AppSlugOrPort)
|
||||
})
|
||||
|
Reference in New Issue
Block a user