...
1 package notmain
2
3 import (
4 "context"
5 "flag"
6 "fmt"
7 "os"
8 "runtime"
9
10 ct "github.com/google/certificate-transparency-go"
11
12 "github.com/letsencrypt/boulder/cmd"
13 "github.com/letsencrypt/boulder/features"
14 bgrpc "github.com/letsencrypt/boulder/grpc"
15 "github.com/letsencrypt/boulder/issuance"
16 "github.com/letsencrypt/boulder/publisher"
17 pubpb "github.com/letsencrypt/boulder/publisher/proto"
18 )
19
20 type Config struct {
21 Publisher struct {
22 cmd.ServiceConfig
23 Features map[string]bool
24
25
26
27
28 BlockProfileRate int
29 UserAgent string
30
31
32
33
34 Chains [][]string `validate:"min=1,dive,min=2,dive,required"`
35 }
36
37 Syslog cmd.SyslogConfig
38 OpenTelemetry cmd.OpenTelemetryConfig
39 }
40
41 func main() {
42 grpcAddr := flag.String("addr", "", "gRPC listen address override")
43 debugAddr := flag.String("debug-addr", "", "Debug server address override")
44 configFile := flag.String("config", "", "File path to the configuration file for this service")
45 flag.Parse()
46 if *configFile == "" {
47 flag.Usage()
48 os.Exit(1)
49 }
50
51 var c Config
52 err := cmd.ReadConfigFile(*configFile, &c)
53 cmd.FailOnError(err, "Reading JSON config file into config structure")
54 err = features.Set(c.Publisher.Features)
55 cmd.FailOnError(err, "Failed to set feature flags")
56
57 runtime.SetBlockProfileRate(c.Publisher.BlockProfileRate)
58
59 if *grpcAddr != "" {
60 c.Publisher.GRPC.Address = *grpcAddr
61 }
62 if *debugAddr != "" {
63 c.Publisher.DebugAddr = *debugAddr
64 }
65 if c.Publisher.UserAgent == "" {
66 c.Publisher.UserAgent = "certificate-transparency-go/1.0"
67 }
68 scope, logger, oTelShutdown := cmd.StatsAndLogging(c.Syslog, c.OpenTelemetry, c.Publisher.DebugAddr)
69 defer oTelShutdown(context.Background())
70 logger.Info(cmd.VersionString())
71
72 if c.Publisher.Chains == nil {
73 logger.AuditErr("No chain files provided")
74 os.Exit(1)
75 }
76
77 bundles := make(map[issuance.IssuerNameID][]ct.ASN1Cert)
78 for _, files := range c.Publisher.Chains {
79 chain, err := issuance.LoadChain(files)
80 cmd.FailOnError(err, "failed to load chain.")
81 issuer := chain[0]
82 id := issuer.NameID()
83 if _, exists := bundles[id]; exists {
84 cmd.Fail(fmt.Sprintf("Got multiple chains configured for issuer %q", issuer.Subject.CommonName))
85 }
86 bundles[id] = publisher.GetCTBundleForChain(chain)
87 }
88
89 tlsConfig, err := c.Publisher.TLS.Load(scope)
90 cmd.FailOnError(err, "TLS config")
91
92 clk := cmd.Clock()
93
94 pubi := publisher.New(bundles, c.Publisher.UserAgent, logger, scope)
95
96 start, err := bgrpc.NewServer(c.Publisher.GRPC, logger).Add(
97 &pubpb.Publisher_ServiceDesc, pubi).Build(tlsConfig, scope, clk)
98 cmd.FailOnError(err, "Unable to setup Publisher gRPC server")
99
100 cmd.FailOnError(start(), "Publisher gRPC service failed")
101 }
102
103 func init() {
104 cmd.RegisterCommand("boulder-publisher", main, &cmd.ConfigValidator{Config: &Config{}})
105 }
106
View as plain text