Update config shape
This commit is contained in:
parent
b8d1f58f21
commit
912893b70c
|
@ -120,17 +120,7 @@ func NewInternalAPI(
|
||||||
|
|
||||||
js, nats := base.NATS.Prepare(base.ProcessContext, &cfg.Matrix.JetStream)
|
js, nats := base.NATS.Prepare(base.ProcessContext, &cfg.Matrix.JetStream)
|
||||||
|
|
||||||
signingInfo := map[gomatrixserverlib.ServerName]*queue.SigningInfo{}
|
signingInfo := base.Cfg.Global.SigningIdentities()
|
||||||
for _, serverName := range append(
|
|
||||||
[]gomatrixserverlib.ServerName{base.Cfg.Global.ServerName},
|
|
||||||
base.Cfg.Global.SecondaryServerNames...,
|
|
||||||
) {
|
|
||||||
signingInfo[serverName] = &queue.SigningInfo{
|
|
||||||
KeyID: cfg.Matrix.KeyID,
|
|
||||||
PrivateKey: cfg.Matrix.PrivateKey,
|
|
||||||
ServerName: serverName,
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
queues := queue.NewOutgoingQueues(
|
queues := queue.NewOutgoingQueues(
|
||||||
federationDB, base.ProcessContext,
|
federationDB, base.ProcessContext,
|
||||||
|
|
|
@ -50,7 +50,7 @@ type destinationQueue struct {
|
||||||
queues *OutgoingQueues
|
queues *OutgoingQueues
|
||||||
db storage.Database
|
db storage.Database
|
||||||
process *process.ProcessContext
|
process *process.ProcessContext
|
||||||
signing map[gomatrixserverlib.ServerName]*SigningInfo
|
signing map[gomatrixserverlib.ServerName]*gomatrixserverlib.SigningIdentity
|
||||||
rsAPI api.FederationRoomserverAPI
|
rsAPI api.FederationRoomserverAPI
|
||||||
client fedapi.FederationClient // federation client
|
client fedapi.FederationClient // federation client
|
||||||
origin gomatrixserverlib.ServerName // origin of requests
|
origin gomatrixserverlib.ServerName // origin of requests
|
||||||
|
|
|
@ -15,7 +15,6 @@
|
||||||
package queue
|
package queue
|
||||||
|
|
||||||
import (
|
import (
|
||||||
"crypto/ed25519"
|
|
||||||
"encoding/json"
|
"encoding/json"
|
||||||
"fmt"
|
"fmt"
|
||||||
"sync"
|
"sync"
|
||||||
|
@ -46,7 +45,7 @@ type OutgoingQueues struct {
|
||||||
origin gomatrixserverlib.ServerName
|
origin gomatrixserverlib.ServerName
|
||||||
client fedapi.FederationClient
|
client fedapi.FederationClient
|
||||||
statistics *statistics.Statistics
|
statistics *statistics.Statistics
|
||||||
signing map[gomatrixserverlib.ServerName]*SigningInfo
|
signing map[gomatrixserverlib.ServerName]*gomatrixserverlib.SigningIdentity
|
||||||
queuesMutex sync.Mutex // protects the below
|
queuesMutex sync.Mutex // protects the below
|
||||||
queues map[gomatrixserverlib.ServerName]*destinationQueue
|
queues map[gomatrixserverlib.ServerName]*destinationQueue
|
||||||
}
|
}
|
||||||
|
@ -91,7 +90,7 @@ func NewOutgoingQueues(
|
||||||
client fedapi.FederationClient,
|
client fedapi.FederationClient,
|
||||||
rsAPI api.FederationRoomserverAPI,
|
rsAPI api.FederationRoomserverAPI,
|
||||||
statistics *statistics.Statistics,
|
statistics *statistics.Statistics,
|
||||||
signing map[gomatrixserverlib.ServerName]*SigningInfo,
|
signing []*gomatrixserverlib.SigningIdentity,
|
||||||
) *OutgoingQueues {
|
) *OutgoingQueues {
|
||||||
queues := &OutgoingQueues{
|
queues := &OutgoingQueues{
|
||||||
disabled: disabled,
|
disabled: disabled,
|
||||||
|
@ -101,9 +100,12 @@ func NewOutgoingQueues(
|
||||||
origin: origin,
|
origin: origin,
|
||||||
client: client,
|
client: client,
|
||||||
statistics: statistics,
|
statistics: statistics,
|
||||||
signing: signing,
|
signing: map[gomatrixserverlib.ServerName]*gomatrixserverlib.SigningIdentity{},
|
||||||
queues: map[gomatrixserverlib.ServerName]*destinationQueue{},
|
queues: map[gomatrixserverlib.ServerName]*destinationQueue{},
|
||||||
}
|
}
|
||||||
|
for _, identity := range signing {
|
||||||
|
queues.signing[identity.ServerName] = identity
|
||||||
|
}
|
||||||
// Look up which servers we have pending items for and then rehydrate those queues.
|
// Look up which servers we have pending items for and then rehydrate those queues.
|
||||||
if !disabled {
|
if !disabled {
|
||||||
serverNames := map[gomatrixserverlib.ServerName]struct{}{}
|
serverNames := map[gomatrixserverlib.ServerName]struct{}{}
|
||||||
|
@ -135,14 +137,6 @@ func NewOutgoingQueues(
|
||||||
return queues
|
return queues
|
||||||
}
|
}
|
||||||
|
|
||||||
// TODO: Move this somewhere useful for other components as we often need to ferry these 3 variables
|
|
||||||
// around together
|
|
||||||
type SigningInfo struct {
|
|
||||||
ServerName gomatrixserverlib.ServerName
|
|
||||||
KeyID gomatrixserverlib.KeyID
|
|
||||||
PrivateKey ed25519.PrivateKey
|
|
||||||
}
|
|
||||||
|
|
||||||
type queuedPDU struct {
|
type queuedPDU struct {
|
||||||
receipt *shared.Receipt
|
receipt *shared.Receipt
|
||||||
pdu *gomatrixserverlib.HeaderedEvent
|
pdu *gomatrixserverlib.HeaderedEvent
|
||||||
|
|
|
@ -350,8 +350,8 @@ func testSetup(failuresUntilBlacklist uint32, shouldTxSucceed bool, t *testing.T
|
||||||
}
|
}
|
||||||
rs := &stubFederationRoomServerAPI{}
|
rs := &stubFederationRoomServerAPI{}
|
||||||
stats := statistics.NewStatistics(db, failuresUntilBlacklist)
|
stats := statistics.NewStatistics(db, failuresUntilBlacklist)
|
||||||
signingInfo := map[gomatrixserverlib.ServerName]*SigningInfo{
|
signingInfo := []*gomatrixserverlib.SigningIdentity{
|
||||||
"localhost": {
|
{
|
||||||
KeyID: "ed21019:auto",
|
KeyID: "ed21019:auto",
|
||||||
PrivateKey: test.PrivateKeyA,
|
PrivateKey: test.PrivateKeyA,
|
||||||
ServerName: "localhost",
|
ServerName: "localhost",
|
||||||
|
|
|
@ -136,30 +136,36 @@ func ClaimOneTimeKeys(
|
||||||
// LocalKeys returns the local keys for the server.
|
// LocalKeys returns the local keys for the server.
|
||||||
// See https://matrix.org/docs/spec/server_server/unstable.html#publishing-keys
|
// See https://matrix.org/docs/spec/server_server/unstable.html#publishing-keys
|
||||||
func LocalKeys(cfg *config.FederationAPI, serverName gomatrixserverlib.ServerName) util.JSONResponse {
|
func LocalKeys(cfg *config.FederationAPI, serverName gomatrixserverlib.ServerName) util.JSONResponse {
|
||||||
keys, err := localKeys(cfg, serverName, time.Now().Add(cfg.Matrix.KeyValidityPeriod))
|
keys, err := localKeys(cfg, serverName)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return util.ErrorResponse(err)
|
return util.ErrorResponse(err)
|
||||||
}
|
}
|
||||||
return util.JSONResponse{Code: http.StatusOK, JSON: keys}
|
return util.JSONResponse{Code: http.StatusOK, JSON: keys}
|
||||||
}
|
}
|
||||||
|
|
||||||
func localKeys(cfg *config.FederationAPI, serverName gomatrixserverlib.ServerName, validUntil time.Time) (*gomatrixserverlib.ServerKeys, error) {
|
func localKeys(cfg *config.FederationAPI, serverName gomatrixserverlib.ServerName) (*gomatrixserverlib.ServerKeys, error) {
|
||||||
var keys gomatrixserverlib.ServerKeys
|
var keys gomatrixserverlib.ServerKeys
|
||||||
if !cfg.Matrix.IsLocalServerName(serverName) {
|
if !cfg.Matrix.IsLocalServerName(serverName) {
|
||||||
return nil, fmt.Errorf("server name not known")
|
return nil, fmt.Errorf("server name not known")
|
||||||
}
|
}
|
||||||
|
|
||||||
keys.ServerName = serverName
|
var virtualHost *config.VirtualHost
|
||||||
keys.ValidUntilTS = gomatrixserverlib.AsTimestamp(validUntil)
|
for _, v := range cfg.Matrix.VirtualHosts {
|
||||||
|
if v.ServerName != serverName {
|
||||||
|
continue
|
||||||
|
}
|
||||||
|
virtualHost = v
|
||||||
|
}
|
||||||
|
|
||||||
|
if virtualHost == nil {
|
||||||
publicKey := cfg.Matrix.PrivateKey.Public().(ed25519.PublicKey)
|
publicKey := cfg.Matrix.PrivateKey.Public().(ed25519.PublicKey)
|
||||||
|
keys.ServerName = cfg.Matrix.ServerName
|
||||||
|
keys.ValidUntilTS = gomatrixserverlib.AsTimestamp(time.Now().Add(cfg.Matrix.KeyValidityPeriod))
|
||||||
keys.VerifyKeys = map[gomatrixserverlib.KeyID]gomatrixserverlib.VerifyKey{
|
keys.VerifyKeys = map[gomatrixserverlib.KeyID]gomatrixserverlib.VerifyKey{
|
||||||
cfg.Matrix.KeyID: {
|
cfg.Matrix.KeyID: {
|
||||||
Key: gomatrixserverlib.Base64Bytes(publicKey),
|
Key: gomatrixserverlib.Base64Bytes(publicKey),
|
||||||
},
|
},
|
||||||
}
|
}
|
||||||
|
|
||||||
keys.OldVerifyKeys = map[gomatrixserverlib.KeyID]gomatrixserverlib.OldVerifyKey{}
|
keys.OldVerifyKeys = map[gomatrixserverlib.KeyID]gomatrixserverlib.OldVerifyKey{}
|
||||||
for _, oldVerifyKey := range cfg.Matrix.OldVerifyKeys {
|
for _, oldVerifyKey := range cfg.Matrix.OldVerifyKeys {
|
||||||
keys.OldVerifyKeys[oldVerifyKey.KeyID] = gomatrixserverlib.OldVerifyKey{
|
keys.OldVerifyKeys[oldVerifyKey.KeyID] = gomatrixserverlib.OldVerifyKey{
|
||||||
|
@ -169,6 +175,18 @@ func localKeys(cfg *config.FederationAPI, serverName gomatrixserverlib.ServerNam
|
||||||
ExpiredTS: oldVerifyKey.ExpiredAt,
|
ExpiredTS: oldVerifyKey.ExpiredAt,
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
} else {
|
||||||
|
publicKey := virtualHost.PrivateKey.Public().(ed25519.PublicKey)
|
||||||
|
keys.ServerName = virtualHost.ServerName
|
||||||
|
keys.ValidUntilTS = gomatrixserverlib.AsTimestamp(time.Now().Add(virtualHost.KeyValidityPeriod))
|
||||||
|
keys.VerifyKeys = map[gomatrixserverlib.KeyID]gomatrixserverlib.VerifyKey{
|
||||||
|
virtualHost.KeyID: {
|
||||||
|
Key: gomatrixserverlib.Base64Bytes(publicKey),
|
||||||
|
},
|
||||||
|
}
|
||||||
|
// TODO: Virtual hosts probably want to be able to specify old signing
|
||||||
|
// keys too, just in case
|
||||||
|
}
|
||||||
|
|
||||||
toSign, err := json.Marshal(keys.ServerKeyFields)
|
toSign, err := json.Marshal(keys.ServerKeyFields)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
|
@ -213,7 +231,7 @@ func NotaryKeys(
|
||||||
for serverName, kidToCriteria := range req.ServerKeys {
|
for serverName, kidToCriteria := range req.ServerKeys {
|
||||||
var keyList []gomatrixserverlib.ServerKeys
|
var keyList []gomatrixserverlib.ServerKeys
|
||||||
if serverName == cfg.Matrix.ServerName {
|
if serverName == cfg.Matrix.ServerName {
|
||||||
if k, err := localKeys(cfg, serverName, time.Now().Add(cfg.Matrix.KeyValidityPeriod)); err == nil {
|
if k, err := localKeys(cfg, serverName); err == nil {
|
||||||
keyList = append(keyList, *k)
|
keyList = append(keyList, *k)
|
||||||
} else {
|
} else {
|
||||||
return util.ErrorResponse(err)
|
return util.ErrorResponse(err)
|
||||||
|
|
|
@ -364,19 +364,7 @@ func (b *BaseDendrite) CreateClient() *gomatrixserverlib.Client {
|
||||||
// CreateFederationClient creates a new federation client. Should only be called
|
// CreateFederationClient creates a new federation client. Should only be called
|
||||||
// once per component.
|
// once per component.
|
||||||
func (b *BaseDendrite) CreateFederationClient() *gomatrixserverlib.FederationClient {
|
func (b *BaseDendrite) CreateFederationClient() *gomatrixserverlib.FederationClient {
|
||||||
identities := make([]*gomatrixserverlib.SigningIdentity, 0, 1+len(b.Cfg.Global.SecondaryServerNames))
|
identities := b.Cfg.Global.SigningIdentities()
|
||||||
identities = append(identities, &gomatrixserverlib.SigningIdentity{
|
|
||||||
ServerName: b.Cfg.Global.ServerName,
|
|
||||||
KeyID: b.Cfg.Global.KeyID,
|
|
||||||
PrivateKey: b.Cfg.Global.PrivateKey,
|
|
||||||
})
|
|
||||||
for _, serverName := range b.Cfg.Global.SecondaryServerNames {
|
|
||||||
identities = append(identities, &gomatrixserverlib.SigningIdentity{
|
|
||||||
ServerName: serverName,
|
|
||||||
KeyID: b.Cfg.Global.KeyID, // TODO: Per-virtual host key
|
|
||||||
PrivateKey: b.Cfg.Global.PrivateKey, // TODO: Per-virtual host key
|
|
||||||
})
|
|
||||||
}
|
|
||||||
if b.Cfg.Global.DisableFederation {
|
if b.Cfg.Global.DisableFederation {
|
||||||
return gomatrixserverlib.NewFederationClient(
|
return gomatrixserverlib.NewFederationClient(
|
||||||
identities, gomatrixserverlib.WithTransport(noOpHTTPTransport),
|
identities, gomatrixserverlib.WithTransport(noOpHTTPTransport),
|
||||||
|
|
|
@ -231,6 +231,21 @@ func loadConfig(
|
||||||
return nil, err
|
return nil, err
|
||||||
}
|
}
|
||||||
|
|
||||||
|
for _, v := range c.Global.VirtualHosts {
|
||||||
|
if v.KeyValidityPeriod == 0 {
|
||||||
|
v.KeyValidityPeriod = c.Global.KeyValidityPeriod
|
||||||
|
}
|
||||||
|
if v.PrivateKeyPath == "" {
|
||||||
|
v.KeyID = c.Global.KeyID
|
||||||
|
v.PrivateKey = c.Global.PrivateKey
|
||||||
|
continue
|
||||||
|
}
|
||||||
|
privateKeyPath := absPath(basePath, v.PrivateKeyPath)
|
||||||
|
if v.KeyID, v.PrivateKey, err = LoadMatrixKey(privateKeyPath, readFile); err != nil {
|
||||||
|
return nil, err
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
for _, key := range c.Global.OldVerifyKeys {
|
for _, key := range c.Global.OldVerifyKeys {
|
||||||
switch {
|
switch {
|
||||||
case key.PrivateKeyPath != "":
|
case key.PrivateKeyPath != "":
|
||||||
|
|
|
@ -16,7 +16,7 @@ type Global struct {
|
||||||
ServerName gomatrixserverlib.ServerName `yaml:"server_name"`
|
ServerName gomatrixserverlib.ServerName `yaml:"server_name"`
|
||||||
|
|
||||||
// The secondary server names, used for virtual hosting.
|
// The secondary server names, used for virtual hosting.
|
||||||
SecondaryServerNames []gomatrixserverlib.ServerName `yaml:"secondary_server_names"`
|
VirtualHosts []*VirtualHost `yaml:"virtual_hosts"`
|
||||||
|
|
||||||
// Path to the private key which will be used to sign requests and events.
|
// Path to the private key which will be used to sign requests and events.
|
||||||
PrivateKeyPath Path `yaml:"private_key"`
|
PrivateKeyPath Path `yaml:"private_key"`
|
||||||
|
@ -128,8 +128,8 @@ func (c *Global) IsLocalServerName(serverName gomatrixserverlib.ServerName) bool
|
||||||
if c.ServerName == serverName {
|
if c.ServerName == serverName {
|
||||||
return true
|
return true
|
||||||
}
|
}
|
||||||
for _, secondaryName := range c.SecondaryServerNames {
|
for _, v := range c.VirtualHosts {
|
||||||
if secondaryName == serverName {
|
if v.ServerName == serverName {
|
||||||
return true
|
return true
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -148,22 +148,49 @@ func (c *Global) SplitLocalID(sigil byte, id string) (string, gomatrixserverlib.
|
||||||
}
|
}
|
||||||
|
|
||||||
func (c *Global) SigningIdentities() []*gomatrixserverlib.SigningIdentity {
|
func (c *Global) SigningIdentities() []*gomatrixserverlib.SigningIdentity {
|
||||||
identities := make([]*gomatrixserverlib.SigningIdentity, 0, len(c.SecondaryServerNames)+1)
|
identities := make([]*gomatrixserverlib.SigningIdentity, 0, len(c.VirtualHosts)+1)
|
||||||
identities = append(identities, &gomatrixserverlib.SigningIdentity{
|
identities = append(identities, &gomatrixserverlib.SigningIdentity{
|
||||||
ServerName: c.ServerName,
|
ServerName: c.ServerName,
|
||||||
KeyID: c.KeyID,
|
KeyID: c.KeyID,
|
||||||
PrivateKey: c.PrivateKey,
|
PrivateKey: c.PrivateKey,
|
||||||
})
|
})
|
||||||
for _, serverName := range c.SecondaryServerNames {
|
for _, v := range c.VirtualHosts {
|
||||||
identities = append(identities, &gomatrixserverlib.SigningIdentity{
|
identities = append(identities, v.SigningIdentity())
|
||||||
ServerName: serverName,
|
|
||||||
KeyID: c.KeyID,
|
|
||||||
PrivateKey: c.PrivateKey,
|
|
||||||
})
|
|
||||||
}
|
}
|
||||||
return identities
|
return identities
|
||||||
}
|
}
|
||||||
|
|
||||||
|
type VirtualHost struct {
|
||||||
|
// The server name of the virtual host.
|
||||||
|
ServerName gomatrixserverlib.ServerName `yaml:"server_name"`
|
||||||
|
|
||||||
|
// The key ID of the private key. If not specified, the default global key ID
|
||||||
|
// will be used instead.
|
||||||
|
KeyID gomatrixserverlib.KeyID `yaml:"key_id"`
|
||||||
|
|
||||||
|
// Path to the private key. If not specified, the default global private key
|
||||||
|
// will be used instead.
|
||||||
|
PrivateKeyPath Path `yaml:"private_key"`
|
||||||
|
|
||||||
|
// The private key itself.
|
||||||
|
PrivateKey ed25519.PrivateKey `yaml:"-"`
|
||||||
|
|
||||||
|
// How long a remote server can cache our server key for before requesting it again.
|
||||||
|
// Increasing this number will reduce the number of requests made by remote servers
|
||||||
|
// for our key, but increases the period a compromised key will be considered valid
|
||||||
|
// by remote servers.
|
||||||
|
// Defaults to 24 hours.
|
||||||
|
KeyValidityPeriod time.Duration `yaml:"key_validity_period"`
|
||||||
|
}
|
||||||
|
|
||||||
|
func (v *VirtualHost) SigningIdentity() *gomatrixserverlib.SigningIdentity {
|
||||||
|
return &gomatrixserverlib.SigningIdentity{
|
||||||
|
ServerName: v.ServerName,
|
||||||
|
KeyID: v.KeyID,
|
||||||
|
PrivateKey: v.PrivateKey,
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
type OldVerifyKeys struct {
|
type OldVerifyKeys struct {
|
||||||
// Path to the private key.
|
// Path to the private key.
|
||||||
PrivateKeyPath Path `yaml:"private_key"`
|
PrivateKeyPath Path `yaml:"private_key"`
|
||||||
|
|
Loading…
Reference in a new issue