Split up boulder-config.json (RA) (#1974)

Part of #1962
This commit is contained in:
Ben Irving 2016-06-29 13:43:55 -07:00 committed by Jacob Hoffman-Andrews
parent 0ab507339b
commit c4f7fb580d
7 changed files with 266 additions and 169 deletions

View File

@ -1,7 +1,9 @@
package main
import (
"flag"
"fmt"
"os"
"time"
"github.com/jmhodges/clock"
@ -10,7 +12,6 @@ import (
"github.com/letsencrypt/boulder/cmd"
"github.com/letsencrypt/boulder/core"
bgrpc "github.com/letsencrypt/boulder/grpc"
blog "github.com/letsencrypt/boulder/log"
"github.com/letsencrypt/boulder/metrics"
"github.com/letsencrypt/boulder/policy"
"github.com/letsencrypt/boulder/ra"
@ -19,79 +20,149 @@ import (
const clientName = "RA"
func main() {
app := cmd.NewAppShell("boulder-ra", "Handles service orchestration")
app.Action = func(c cmd.Config, stats metrics.Statter, logger blog.Logger) {
// Validate PA config and set defaults if needed
cmd.FailOnError(c.PA.CheckChallenges(), "Invalid PA configuration")
type config struct {
RA struct {
cmd.ServiceConfig
cmd.HostnamePolicyConfig
go cmd.DebugServer(c.RA.DebugAddr)
RateLimitPoliciesFilename string
pa, err := policy.New(c.PA.Challenges)
cmd.FailOnError(err, "Couldn't create PA")
MaxConcurrentRPCServerRequests int64
if c.RA.HostnamePolicyFile == "" {
cmd.FailOnError(fmt.Errorf("HostnamePolicyFile must be provided."), "")
}
err = pa.SetHostnamePolicyFile(c.RA.HostnamePolicyFile)
cmd.FailOnError(err, "Couldn't load hostname policy file")
MaxContactsPerRegistration int
go cmd.ProfileCmd("RA", stats)
// UseIsSafeDomain determines whether to call VA.IsSafeDomain
UseIsSafeDomain bool // TODO: remove after va IsSafeDomain deploy
amqpConf := c.RA.AMQP
var vac core.ValidationAuthority
if c.RA.VAService != nil {
conn, err := bgrpc.ClientSetup(c.RA.VAService)
cmd.FailOnError(err, "Unable to create VA client")
vac = bgrpc.NewValidationAuthorityGRPCClient(conn)
} else {
vac, err = rpc.NewValidationAuthorityClient(clientName, amqpConf, stats)
cmd.FailOnError(err, "Unable to create VA client")
}
// The number of times to try a DNS query (that has a temporary error)
// before giving up. May be short-circuited by deadlines. A zero value
// will be turned into 1.
DNSTries int
cac, err := rpc.NewCertificateAuthorityClient(clientName, amqpConf, stats)
cmd.FailOnError(err, "Unable to create CA client")
VAService *cmd.GRPCClientConfig
sac, err := rpc.NewStorageAuthorityClient(clientName, amqpConf, stats)
cmd.FailOnError(err, "Unable to create SA client")
MaxNames int
DoNotForceCN bool
rai := ra.NewRegistrationAuthorityImpl(clock.Default(), logger, stats,
c.RA.MaxContactsPerRegistration, c.KeyPolicy(),
c.RA.MaxNames, c.RA.DoNotForceCN, c.RA.ReuseValidAuthz)
policyErr := rai.SetRateLimitPoliciesFile(c.RA.RateLimitPoliciesFilename)
cmd.FailOnError(policyErr, "Couldn't load rate limit policies file")
rai.PA = pa
raDNSTimeout, err := time.ParseDuration(c.Common.DNSTimeout)
cmd.FailOnError(err, "Couldn't parse RA DNS timeout")
scoped := metrics.NewStatsdScope(stats, "RA", "DNS")
dnsTries := c.RA.DNSTries
if dnsTries < 1 {
dnsTries = 1
}
if !c.Common.DNSAllowLoopbackAddresses {
rai.DNSResolver = bdns.NewDNSResolverImpl(
raDNSTimeout,
[]string{c.Common.DNSResolver},
nil,
scoped,
clock.Default(),
dnsTries)
} else {
rai.DNSResolver = bdns.NewTestDNSResolverImpl(raDNSTimeout, []string{c.Common.DNSResolver}, scoped, clock.Default(), dnsTries)
}
rai.VA = vac
rai.CA = cac
rai.SA = sac
ras, err := rpc.NewAmqpRPCServer(amqpConf, c.RA.MaxConcurrentRPCServerRequests, stats, logger)
cmd.FailOnError(err, "Unable to create RA RPC server")
err = rpc.NewRegistrationAuthorityServer(ras, rai, logger)
cmd.FailOnError(err, "Unable to setup RA RPC server")
err = ras.Start(amqpConf)
cmd.FailOnError(err, "Unable to run RA RPC server")
// Controls behaviour of the RA when asked to create a new authz for
// a name/regID that already has a valid authz. False preserves historic
// behaviour and ignores the existing authz and creates a new one. True
// instructs the RA to reuse the previously created authz in lieu of
// creating another.
ReuseValidAuthz bool
}
app.Run()
*cmd.AllowedSigningAlgos
PA cmd.PAConfig
cmd.StatsdConfig
cmd.SyslogConfig
Common struct {
DNSResolver string
DNSTimeout string
DNSAllowLoopbackAddresses bool
}
}
func main() {
configFile := flag.String("config", "", "File path to the configuration file for this service")
flag.Parse()
if *configFile == "" {
flag.Usage()
os.Exit(1)
}
var c config
err := cmd.ReadJSONFile(*configFile, &c)
cmd.FailOnError(err, "Reading JSON config file into config structure")
go cmd.DebugServer(c.RA.DebugAddr)
stats, logger := cmd.StatsAndLogging(c.StatsdConfig, c.SyslogConfig)
defer logger.AuditPanic()
logger.Info(cmd.VersionString(clientName))
// Validate PA config and set defaults if needed
cmd.FailOnError(c.PA.CheckChallenges(), "Invalid PA configuration")
pa, err := policy.New(c.PA.Challenges)
cmd.FailOnError(err, "Couldn't create PA")
if c.RA.HostnamePolicyFile == "" {
cmd.FailOnError(fmt.Errorf("HostnamePolicyFile must be provided."), "")
}
err = pa.SetHostnamePolicyFile(c.RA.HostnamePolicyFile)
cmd.FailOnError(err, "Couldn't load hostname policy file")
go cmd.ProfileCmd("RA", stats)
amqpConf := c.RA.AMQP
var vac core.ValidationAuthority
if c.RA.VAService != nil {
conn, err := bgrpc.ClientSetup(c.RA.VAService)
cmd.FailOnError(err, "Unable to create VA client")
vac = bgrpc.NewValidationAuthorityGRPCClient(conn)
} else {
vac, err = rpc.NewValidationAuthorityClient(clientName, amqpConf, stats)
cmd.FailOnError(err, "Unable to create VA client")
}
cac, err := rpc.NewCertificateAuthorityClient(clientName, amqpConf, stats)
cmd.FailOnError(err, "Unable to create CA client")
sac, err := rpc.NewStorageAuthorityClient(clientName, amqpConf, stats)
cmd.FailOnError(err, "Unable to create SA client")
rai := ra.NewRegistrationAuthorityImpl(
clock.Default(),
logger,
stats,
c.RA.MaxContactsPerRegistration,
c.AllowedSigningAlgos.KeyPolicy(),
c.RA.MaxNames,
c.RA.DoNotForceCN,
c.RA.ReuseValidAuthz)
policyErr := rai.SetRateLimitPoliciesFile(c.RA.RateLimitPoliciesFilename)
cmd.FailOnError(policyErr, "Couldn't load rate limit policies file")
rai.PA = pa
raDNSTimeout, err := time.ParseDuration(c.Common.DNSTimeout)
cmd.FailOnError(err, "Couldn't parse RA DNS timeout")
scoped := metrics.NewStatsdScope(stats, "RA", "DNS")
dnsTries := c.RA.DNSTries
if dnsTries < 1 {
dnsTries = 1
}
if !c.Common.DNSAllowLoopbackAddresses {
rai.DNSResolver = bdns.NewDNSResolverImpl(
raDNSTimeout,
[]string{c.Common.DNSResolver},
nil,
scoped,
clock.Default(),
dnsTries)
} else {
rai.DNSResolver = bdns.NewTestDNSResolverImpl(
raDNSTimeout,
[]string{c.Common.DNSResolver},
scoped,
clock.Default(),
dnsTries)
}
rai.VA = vac
rai.CA = cac
rai.SA = sac
ras, err := rpc.NewAmqpRPCServer(amqpConf, c.RA.MaxConcurrentRPCServerRequests, stats, logger)
cmd.FailOnError(err, "Unable to create RA RPC server")
err = rpc.NewRegistrationAuthorityServer(ras, rai, logger)
cmd.FailOnError(err, "Unable to setup RA RPC server")
err = ras.Start(amqpConf)
cmd.FailOnError(err, "Unable to run RA RPC server")
}

View File

@ -27,37 +27,6 @@ type Config struct {
CA CAConfig
RA struct {
ServiceConfig
HostnamePolicyConfig
RateLimitPoliciesFilename string
MaxConcurrentRPCServerRequests int64
MaxContactsPerRegistration int
// UseIsSafeDomain determines whether to call VA.IsSafeDomain
UseIsSafeDomain bool // TODO(jmhodges): remove after va IsSafeDomain deploy
// The number of times to try a DNS query (that has a temporary error)
// before giving up. May be short-circuited by deadlines. A zero value
// will be turned into 1.
DNSTries int
VAService *GRPCClientConfig
MaxNames int
DoNotForceCN bool
// Controls behaviour of the RA when asked to create a new authz for
// a name/regID that already has a valid authz. False preserves historic
// behaviour and ignores the existing authz and creates a new one. True
// instructs the RA to reuse the previously created authz in lieu of
// creating another.
ReuseValidAuthz bool
}
SA struct {
ServiceConfig
DBConfig

View File

@ -100,12 +100,6 @@ func (as *AppShell) Run() {
config.CA.AMQP.ServiceQueue = config.AMQP.CA.Server
}
}
if config.RA.AMQP == nil {
config.RA.AMQP = config.AMQP
if config.RA.AMQP != nil && config.AMQP.RA != nil {
config.RA.AMQP.ServiceQueue = config.AMQP.RA.Server
}
}
if config.SA.AMQP == nil {
config.SA.AMQP = config.AMQP
if config.SA.AMQP != nil && config.AMQP.SA != nil {

View File

@ -137,43 +137,6 @@
}
},
"ra": {
"rateLimitPoliciesFilename": "test/rate-limit-policies.yml",
"maxConcurrentRPCServerRequests": 16,
"maxContactsPerRegistration": 100,
"dnsTries": 3,
"debugAddr": "localhost:8002",
"hostnamePolicyFile": "test/hostname-policy.json",
"maxNames": 1000,
"doNotForceCN": true,
"reuseValidAuthz": true,
"vaService": {
"serverAddresses": ["boulder:9092"],
"serverIssuerPath": "test/grpc-creds/ca.pem",
"clientCertificatePath": "test/grpc-creds/client.pem",
"clientKeyPath": "test/grpc-creds/key.pem",
"timeout": "90s"
},
"amqp": {
"serverURLFile": "test/secrets/amqp_url",
"insecure": true,
"serviceQueue": "RA.server",
"VA": {
"server": "VA.server",
"rpcTimeout": "60s"
},
"SA": {
"server": "SA.server",
"rpcTimeout": "15s"
},
"CA": {
"server": "CA.server",
"rpcTimeout": "15s"
}
}
},
"sa": {
"dbConnectFile": "test/secrets/sa_dburl",
"maxDBConns": 10,

View File

@ -135,35 +135,6 @@
}
},
"ra": {
"rateLimitPoliciesFilename": "test/rate-limit-policies.yml",
"maxConcurrentRPCServerRequests": 16,
"maxContactsPerRegistration": 100,
"dnsTries": 3,
"debugAddr": "localhost:8002",
"hostnamePolicyFile": "test/hostname-policy.json",
"maxNames": 1000,
"doNotForceCN": true,
"amqp": {
"serverURLFile": "test/secrets/amqp_url",
"insecure": true,
"serviceQueue": "RA.server",
"VA": {
"server": "VA.server",
"rpcTimeout": "60s"
},
"SA": {
"server": "SA.server",
"rpcTimeout": "15s"
},
"CA": {
"server": "CA.server",
"rpcTimeout": "15s"
}
}
},
"sa": {
"dbConnectFile": "test/secrets/sa_dburl",
"maxDBConns": 10,

68
test/config-next/ra.json Normal file
View File

@ -0,0 +1,68 @@
{
"ra": {
"rateLimitPoliciesFilename": "test/rate-limit-policies.yml",
"maxConcurrentRPCServerRequests": 16,
"maxContactsPerRegistration": 100,
"dnsTries": 3,
"debugAddr": "localhost:8002",
"hostnamePolicyFile": "test/hostname-policy.json",
"maxNames": 1000,
"doNotForceCN": true,
"reuseValidAuthz": true,
"vaService": {
"serverAddresses": ["boulder:9092"],
"serverIssuerPath": "test/grpc-creds/ca.pem",
"clientCertificatePath": "test/grpc-creds/client.pem",
"clientKeyPath": "test/grpc-creds/key.pem",
"timeout": "90s"
},
"amqp": {
"serverURLFile": "test/secrets/amqp_url",
"insecure": true,
"serviceQueue": "RA.server",
"VA": {
"server": "VA.server",
"rpcTimeout": "60s"
},
"SA": {
"server": "SA.server",
"rpcTimeout": "15s"
},
"CA": {
"server": "CA.server",
"rpcTimeout": "15s"
}
}
},
"allowedSigningAlgos": {
"rsa": true,
"ecdsanistp256": true,
"ecdsanistp384": true,
"ecdsanistp521": false
},
"pa": {
"challenges": {
"http-01": true,
"tls-sni-01": true,
"dns-01": true
}
},
"statsd": {
"server": "localhost:8125",
"prefix": "Boulder"
},
"syslog": {
"stdoutlevel": 6,
"sysloglevel": 4
},
"common": {
"dnsResolver": "127.0.0.1:8053",
"dnsTimeout": "10s",
"dnsAllowLoopbackAddresses": true
}
}

61
test/config/ra.json Normal file
View File

@ -0,0 +1,61 @@
{
"ra": {
"rateLimitPoliciesFilename": "test/rate-limit-policies.yml",
"maxConcurrentRPCServerRequests": 16,
"maxContactsPerRegistration": 100,
"dnsTries": 3,
"debugAddr": "localhost:8002",
"hostnamePolicyFile": "test/hostname-policy.json",
"maxNames": 1000,
"doNotForceCN": true,
"amqp": {
"serverURLFile": "test/secrets/amqp_url",
"insecure": true,
"serviceQueue": "RA.server",
"VA": {
"server": "VA.server",
"rpcTimeout": "60s"
},
"SA": {
"server": "SA.server",
"rpcTimeout": "15s"
},
"CA": {
"server": "CA.server",
"rpcTimeout": "15s"
}
}
},
"allowedSigningAlgos": {
"rsa": true,
"ecdsanistp256": true,
"ecdsanistp384": true,
"ecdsanistp521": false
},
"pa": {
"challenges": {
"http-01": true,
"tls-sni-01": true,
"dns-01": true
}
},
"statsd": {
"server": "localhost:8125",
"prefix": "Boulder"
},
"syslog": {
"network": "",
"server": "",
"stdoutlevel": 6
},
"common": {
"dnsResolver": "127.0.0.1:8053",
"dnsTimeout": "10s",
"dnsAllowLoopbackAddresses": true
}
}