Creating a JWK server to servex keys in kubernetes

8/3/2021

I am trying to create a JWK server in a pod (on k8s) which would serve the keys when a request for a particular kid comes in. I create the JWK using the generate function

func (s *jwkServer) startJWKServer() {
    privateKey, err := rsa.GenerateKey(rand.Reader, 2048)
    if err != nil {
	    panic(err)
    }
    jwk := go_jose.JSONWebKey{
	    Key:                         privateKey,
	    KeyID:                       "rand_key_id",
	    Algorithm:                   "RSA256",
    }
    s.jwk = &jwk
}

func (s *jwkServer) ServeHTTP(response http.ResponseWriter, request *http.Request) {

    // Do some encoding and decoding to encapsulate into the response object
    return s.jwk
}

I used the above generated key to sign the JWT token. When the request for the above stated key comes in, the pod returns the key.

The problem here is that if the pod restarts before the request for the JWK comes in, then the key cannnot be found and this results in an error. How should such a scenario be handled ?

I thought about a couple of solutions here

Solution 1: Create the same key every time but then this would be a problem if someone gets access to the key.

Solution 2: A new JWK key is generated everytime the pod restarts but then I am concerned about the case where the pod restart happens a lot of times and then it adds latency to the code.

How should I handle the JWK server in kubernetes ?

-- The_Lost_Avatar
jwk
jwt
kubernetes

1 Answer

8/25/2021

Here is how we solved it

  1. Public key is persisted somewhere ( either DB or a PV or a vault)

  2. When the request comes in and the pod has not restarted, we would have the public key in memory, the server returns the key

  3. When the request comes in and the pod HAS restarted, we wont have the public key in memory. But we would still have it in our persistence layer, we would serve the public key from the persistence layer.

-- The_Lost_Avatar
Source: StackOverflow