mirror of
https://github.com/strukturag/nextcloud-spreed-signaling
synced 2024-05-04 23:03:09 +02:00
Return dedicated error if proxy receives token that is not valid yet.
This can happen for example if the times of the machines running the signaling server and proxy don't match.
This commit is contained in:
parent
fde95ddc93
commit
5101b16df3
|
@ -73,6 +73,7 @@ var (
|
|||
TimeoutCreatingSubscriber = signaling.NewError("timeout", "Timeout creating subscriber.")
|
||||
TokenAuthFailed = signaling.NewError("auth_failed", "The token could not be authenticated.")
|
||||
TokenExpired = signaling.NewError("token_expired", "The token is expired.")
|
||||
TokenNotValidYet = signaling.NewError("token_not_valid_yet", "The token is not valid yet.")
|
||||
UnknownClient = signaling.NewError("unknown_client", "Unknown client id given.")
|
||||
UnsupportedCommand = signaling.NewError("bad_request", "Unsupported command received.")
|
||||
UnsupportedMessage = signaling.NewError("bad_request", "Unsupported message received.")
|
||||
|
@ -865,8 +866,15 @@ func (s *ProxyServer) NewSession(hello *signaling.HelloProxyClientMessage) (*Pro
|
|||
reason = "unsupported-issuer"
|
||||
return nil, fmt.Errorf("No key found for issuer")
|
||||
}
|
||||
|
||||
return tokenKey.key, nil
|
||||
})
|
||||
if err, ok := err.(*jwt.ValidationError); ok {
|
||||
if err.Errors&jwt.ValidationErrorIssuedAt == jwt.ValidationErrorIssuedAt {
|
||||
statsTokenErrorsTotal.WithLabelValues("not-valid-yet").Inc()
|
||||
return nil, TokenNotValidYet
|
||||
}
|
||||
}
|
||||
if err != nil {
|
||||
statsTokenErrorsTotal.WithLabelValues(reason).Inc()
|
||||
return nil, TokenAuthFailed
|
||||
|
|
127
proxy/proxy_server_test.go
Normal file
127
proxy/proxy_server_test.go
Normal file
|
@ -0,0 +1,127 @@
|
|||
/**
|
||||
* Standalone signaling server for the Nextcloud Spreed app.
|
||||
* Copyright (C) 2022 struktur AG
|
||||
*
|
||||
* @author Joachim Bauch <bauch@struktur.de>
|
||||
*
|
||||
* @license GNU AGPL version 3 or any later version
|
||||
*
|
||||
* This program is free software: you can redistribute it and/or modify
|
||||
* it under the terms of the GNU Affero General Public License as published by
|
||||
* the Free Software Foundation, either version 3 of the License, or
|
||||
* (at your option) any later version.
|
||||
*
|
||||
* This program is distributed in the hope that it will be useful,
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
* GNU Affero General Public License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU Affero General Public License
|
||||
* along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
package main
|
||||
|
||||
import (
|
||||
"crypto/rand"
|
||||
"crypto/rsa"
|
||||
"crypto/x509"
|
||||
"encoding/pem"
|
||||
"io/ioutil"
|
||||
"os"
|
||||
"testing"
|
||||
"time"
|
||||
|
||||
"github.com/dlintw/goconf"
|
||||
"github.com/golang-jwt/jwt"
|
||||
"github.com/gorilla/mux"
|
||||
signaling "github.com/strukturag/nextcloud-spreed-signaling"
|
||||
)
|
||||
|
||||
const (
|
||||
KeypairSizeForTest = 2048
|
||||
TokenIdForTest = "foo"
|
||||
)
|
||||
|
||||
func newProxyServerForTest(t *testing.T) (*ProxyServer, *rsa.PrivateKey, func()) {
|
||||
tempdir, err := ioutil.TempDir("", "test")
|
||||
if err != nil {
|
||||
t.Fatalf("could not create temporary folder: %s", err)
|
||||
}
|
||||
var server *ProxyServer
|
||||
shutdown := func() {
|
||||
if server != nil {
|
||||
server.Stop()
|
||||
}
|
||||
os.RemoveAll(tempdir)
|
||||
}
|
||||
|
||||
r := mux.NewRouter()
|
||||
key, err := rsa.GenerateKey(rand.Reader, KeypairSizeForTest)
|
||||
if err != nil {
|
||||
t.Fatalf("could not generate key: %s", err)
|
||||
}
|
||||
priv := &pem.Block{
|
||||
Type: "RSA PRIVATE KEY",
|
||||
Bytes: x509.MarshalPKCS1PrivateKey(key),
|
||||
}
|
||||
privkey, err := ioutil.TempFile(tempdir, "privkey*.pem")
|
||||
if err != nil {
|
||||
t.Fatalf("could not create temporary file for private key: %s", err)
|
||||
}
|
||||
if err := pem.Encode(privkey, priv); err != nil {
|
||||
t.Fatalf("could not encode private key: %s", err)
|
||||
}
|
||||
|
||||
pubData, err := x509.MarshalPKIXPublicKey(&key.PublicKey)
|
||||
if err != nil {
|
||||
t.Fatalf("could not marshal public key: %s", err)
|
||||
}
|
||||
pub := &pem.Block{
|
||||
Type: "RSA PUBLIC KEY",
|
||||
Bytes: pubData,
|
||||
}
|
||||
pubkey, err := ioutil.TempFile(tempdir, "pubkey*.pem")
|
||||
if err != nil {
|
||||
t.Fatalf("could not create temporary file for public key: %s", err)
|
||||
}
|
||||
if err := pem.Encode(pubkey, pub); err != nil {
|
||||
t.Fatalf("could not encode public key: %s", err)
|
||||
}
|
||||
|
||||
config := goconf.NewConfigFile()
|
||||
config.AddOption("tokens", TokenIdForTest, pubkey.Name())
|
||||
|
||||
if server, err = NewProxyServer(r, "0.0", config); err != nil {
|
||||
t.Fatalf("could not create server: %s", err)
|
||||
}
|
||||
return server, key, shutdown
|
||||
}
|
||||
|
||||
func TestTokenInFuture(t *testing.T) {
|
||||
server, key, shutdown := newProxyServerForTest(t)
|
||||
defer shutdown()
|
||||
|
||||
claims := &signaling.TokenClaims{
|
||||
StandardClaims: jwt.StandardClaims{
|
||||
IssuedAt: time.Now().Add(time.Hour).Unix(),
|
||||
Issuer: TokenIdForTest,
|
||||
},
|
||||
}
|
||||
token := jwt.NewWithClaims(jwt.SigningMethodRS256, claims)
|
||||
tokenString, err := token.SignedString(key)
|
||||
if err != nil {
|
||||
t.Fatalf("could not create token: %s", err)
|
||||
}
|
||||
|
||||
hello := &signaling.HelloProxyClientMessage{
|
||||
Version: "1.0",
|
||||
Token: tokenString,
|
||||
}
|
||||
session, err := server.NewSession(hello)
|
||||
if session != nil {
|
||||
defer session.Close()
|
||||
t.Errorf("should not have created session")
|
||||
} else if err != TokenNotValidYet {
|
||||
t.Errorf("could have failed with TokenNotValidYet, got %s", err)
|
||||
}
|
||||
}
|
Loading…
Reference in a new issue