blob: 0304b9c6d7153d47e6e6ba31df2a909ae18e3855 [file]
// Copyright 2016 The LUCI Authors.
//
// Licensed under the Apache License, Version 2.0 (the "License");
// you may not use this file except in compliance with the License.
// You may obtain a copy of the License at
//
// http://www.apache.org/licenses/LICENSE-2.0
//
// Unless required by applicable law or agreed to in writing, software
// distributed under the License is distributed on an "AS IS" BASIS,
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
// See the License for the specific language governing permissions and
// limitations under the License.
package machinetoken
import (
"crypto/x509"
"math/big"
"testing"
"time"
"golang.org/x/net/context"
"github.com/luci/luci-go/common/clock/testclock"
"github.com/luci/luci-go/server/auth/signing"
"github.com/luci/luci-go/tokenserver/api"
"github.com/luci/luci-go/tokenserver/api/admin/v1"
. "github.com/luci/luci-go/common/testing/assertions"
. "github.com/smartystreets/goconvey/convey"
)
func TestMintParamsValidation(t *testing.T) {
Convey("with token params", t, func() {
params := MintParams{
FQDN: "host.domain",
Cert: &x509.Certificate{
SerialNumber: big.NewInt(12345),
},
Config: &admin.CertificateAuthorityConfig{
KnownDomains: []*admin.DomainConfig{
{
Domain: []string{"domain"},
MachineTokenLifetime: 3600,
},
},
},
}
Convey("good params", func() {
So(params.Validate(), ShouldBeNil)
})
Convey("good params with subdomain", func() {
params.FQDN = "host.subdomain.domain"
So(params.Validate(), ShouldBeNil)
})
Convey("bad FQDN case", func() {
params.FQDN = "HOST.domain"
So(params.Validate(), ShouldErrLike, "expecting FQDN in lowercase")
})
Convey("bad FQDN", func() {
params.FQDN = "host"
So(params.Validate(), ShouldErrLike, "not a valid FQDN")
})
Convey("not whitelisted", func() {
params.FQDN = "host.blah"
So(params.Validate(), ShouldErrLike, "not whitelisted in the config")
})
Convey("tokens are not allowed", func() {
params.Config.KnownDomains[0].MachineTokenLifetime = 0
So(params.Validate(), ShouldErrLike, "are not allowed")
})
Convey("bad SN", func() {
params.Cert.SerialNumber = big.NewInt(-1)
So(params.Validate(), ShouldErrLike, "invalid certificate serial number")
})
})
}
func TestMint(t *testing.T) {
Convey("with mock context", t, func() {
ctx := context.Background()
ctx, _ = testclock.UseTime(ctx, time.Date(2015, time.February, 3, 4, 5, 6, 7, time.UTC))
Convey("works", func() {
params := MintParams{
FQDN: "host.domain",
Cert: &x509.Certificate{
SerialNumber: big.NewInt(12345),
},
Config: &admin.CertificateAuthorityConfig{
KnownDomains: []*admin.DomainConfig{
{
Domain: []string{"domain"},
MachineTokenLifetime: 3600,
},
},
},
Signer: fakeSigner{},
}
body, token, err := Mint(ctx, &params)
So(err, ShouldBeNil)
So(body, ShouldResemble, &tokenserver.MachineTokenBody{
MachineFqdn: "host.domain",
IssuedBy: "token-server@example.com",
IssuedAt: 1422936306,
Lifetime: 3600,
CaId: 0,
CertSn: 12345,
})
So(token, ShouldEqual, "CjMKC2hvc3QuZG9tYWluEhh0b2tlbi1zZXJ2ZXJAZXhhbXB"+
"sZS5jb20Y8pHBpgUgkBwwuWASBmtleV9pZBoJc2lnbmF0dXJl")
})
})
}
type fakeSigner struct{}
func (fakeSigner) SignBytes(c context.Context, blob []byte) (keyID string, sig []byte, err error) {
return "key_id", []byte("signature"), nil
}
func (fakeSigner) Certificates(c context.Context) (*signing.PublicCertificates, error) {
panic("not implemented yet")
}
func (fakeSigner) ServiceInfo(c context.Context) (*signing.ServiceInfo, error) {
return &signing.ServiceInfo{
ServiceAccountName: "token-server@example.com",
}, nil
}