newline battles continue
This commit is contained in:
10
vendor/go.mongodb.org/mongo-driver/x/mongo/driver/description/description.go
generated
vendored
Executable file
10
vendor/go.mongodb.org/mongo-driver/x/mongo/driver/description/description.go
generated
vendored
Executable file
@@ -0,0 +1,10 @@
|
||||
// Copyright (C) MongoDB, Inc. 2017-present.
|
||||
//
|
||||
// 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
|
||||
|
||||
package description // import "go.mongodb.org/mongo-driver/x/mongo/driver/description"
|
||||
|
||||
// Unknown is an unknown server or topology kind.
|
||||
const Unknown = 0
|
||||
36
vendor/go.mongodb.org/mongo-driver/x/mongo/driver/description/feature.go
generated
vendored
Executable file
36
vendor/go.mongodb.org/mongo-driver/x/mongo/driver/description/feature.go
generated
vendored
Executable file
@@ -0,0 +1,36 @@
|
||||
// Copyright (C) MongoDB, Inc. 2017-present.
|
||||
//
|
||||
// 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
|
||||
|
||||
package description
|
||||
|
||||
import (
|
||||
"fmt"
|
||||
)
|
||||
|
||||
// MaxStalenessSupported returns an error if the given server version
|
||||
// does not support max staleness.
|
||||
func MaxStalenessSupported(wireVersion *VersionRange) error {
|
||||
if wireVersion != nil && wireVersion.Max < 5 {
|
||||
return fmt.Errorf("max staleness is only supported for servers 3.4 or newer")
|
||||
}
|
||||
|
||||
return nil
|
||||
}
|
||||
|
||||
// ScramSHA1Supported returns an error if the given server version
|
||||
// does not support scram-sha-1.
|
||||
func ScramSHA1Supported(wireVersion *VersionRange) error {
|
||||
if wireVersion != nil && wireVersion.Max < 3 {
|
||||
return fmt.Errorf("SCRAM-SHA-1 is only supported for servers 3.0 or newer")
|
||||
}
|
||||
|
||||
return nil
|
||||
}
|
||||
|
||||
// SessionsSupported returns true of the given server version indicates that it supports sessions.
|
||||
func SessionsSupported(wireVersion *VersionRange) bool {
|
||||
return wireVersion != nil && wireVersion.Max >= 6
|
||||
}
|
||||
154
vendor/go.mongodb.org/mongo-driver/x/mongo/driver/description/server.go
generated
vendored
Executable file
154
vendor/go.mongodb.org/mongo-driver/x/mongo/driver/description/server.go
generated
vendored
Executable file
@@ -0,0 +1,154 @@
|
||||
// Copyright (C) MongoDB, Inc. 2017-present.
|
||||
//
|
||||
// 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
|
||||
|
||||
package description
|
||||
|
||||
import (
|
||||
"fmt"
|
||||
"time"
|
||||
|
||||
"go.mongodb.org/mongo-driver/bson/primitive"
|
||||
"go.mongodb.org/mongo-driver/tag"
|
||||
"go.mongodb.org/mongo-driver/x/mongo/driver/address"
|
||||
"go.mongodb.org/mongo-driver/x/network/result"
|
||||
)
|
||||
|
||||
// UnsetRTT is the unset value for a round trip time.
|
||||
const UnsetRTT = -1 * time.Millisecond
|
||||
|
||||
// SelectedServer represents a selected server that is a member of a topology.
|
||||
type SelectedServer struct {
|
||||
Server
|
||||
Kind TopologyKind
|
||||
}
|
||||
|
||||
// Server represents a description of a server. This is created from an isMaster
|
||||
// command.
|
||||
type Server struct {
|
||||
Addr address.Address
|
||||
|
||||
AverageRTT time.Duration
|
||||
AverageRTTSet bool
|
||||
Compression []string // compression methods returned by server
|
||||
CanonicalAddr address.Address
|
||||
ElectionID primitive.ObjectID
|
||||
HeartbeatInterval time.Duration
|
||||
LastError error
|
||||
LastUpdateTime time.Time
|
||||
LastWriteTime time.Time
|
||||
MaxBatchCount uint32
|
||||
MaxDocumentSize uint32
|
||||
MaxMessageSize uint32
|
||||
Members []address.Address
|
||||
ReadOnly bool
|
||||
SessionTimeoutMinutes uint32
|
||||
SetName string
|
||||
SetVersion uint32
|
||||
Tags tag.Set
|
||||
Kind ServerKind
|
||||
WireVersion *VersionRange
|
||||
|
||||
SaslSupportedMechs []string // user-specific from server handshake
|
||||
}
|
||||
|
||||
// NewServer creates a new server description from the given parameters.
|
||||
func NewServer(addr address.Address, isMaster result.IsMaster) Server {
|
||||
i := Server{
|
||||
Addr: addr,
|
||||
|
||||
CanonicalAddr: address.Address(isMaster.Me).Canonicalize(),
|
||||
Compression: isMaster.Compression,
|
||||
ElectionID: isMaster.ElectionID,
|
||||
LastUpdateTime: time.Now().UTC(),
|
||||
LastWriteTime: isMaster.LastWriteTimestamp,
|
||||
MaxBatchCount: isMaster.MaxWriteBatchSize,
|
||||
MaxDocumentSize: isMaster.MaxBSONObjectSize,
|
||||
MaxMessageSize: isMaster.MaxMessageSizeBytes,
|
||||
SaslSupportedMechs: isMaster.SaslSupportedMechs,
|
||||
SessionTimeoutMinutes: isMaster.LogicalSessionTimeoutMinutes,
|
||||
SetName: isMaster.SetName,
|
||||
SetVersion: isMaster.SetVersion,
|
||||
Tags: tag.NewTagSetFromMap(isMaster.Tags),
|
||||
}
|
||||
|
||||
if i.CanonicalAddr == "" {
|
||||
i.CanonicalAddr = addr
|
||||
}
|
||||
|
||||
if isMaster.OK != 1 {
|
||||
i.LastError = fmt.Errorf("not ok")
|
||||
return i
|
||||
}
|
||||
|
||||
for _, host := range isMaster.Hosts {
|
||||
i.Members = append(i.Members, address.Address(host).Canonicalize())
|
||||
}
|
||||
|
||||
for _, passive := range isMaster.Passives {
|
||||
i.Members = append(i.Members, address.Address(passive).Canonicalize())
|
||||
}
|
||||
|
||||
for _, arbiter := range isMaster.Arbiters {
|
||||
i.Members = append(i.Members, address.Address(arbiter).Canonicalize())
|
||||
}
|
||||
|
||||
i.Kind = Standalone
|
||||
|
||||
if isMaster.IsReplicaSet {
|
||||
i.Kind = RSGhost
|
||||
} else if isMaster.SetName != "" {
|
||||
if isMaster.IsMaster {
|
||||
i.Kind = RSPrimary
|
||||
} else if isMaster.Hidden {
|
||||
i.Kind = RSMember
|
||||
} else if isMaster.Secondary {
|
||||
i.Kind = RSSecondary
|
||||
} else if isMaster.ArbiterOnly {
|
||||
i.Kind = RSArbiter
|
||||
} else {
|
||||
i.Kind = RSMember
|
||||
}
|
||||
} else if isMaster.Msg == "isdbgrid" {
|
||||
i.Kind = Mongos
|
||||
}
|
||||
|
||||
i.WireVersion = &VersionRange{
|
||||
Min: isMaster.MinWireVersion,
|
||||
Max: isMaster.MaxWireVersion,
|
||||
}
|
||||
|
||||
return i
|
||||
}
|
||||
|
||||
// SetAverageRTT sets the average round trip time for this server description.
|
||||
func (s Server) SetAverageRTT(rtt time.Duration) Server {
|
||||
s.AverageRTT = rtt
|
||||
if rtt == UnsetRTT {
|
||||
s.AverageRTTSet = false
|
||||
} else {
|
||||
s.AverageRTTSet = true
|
||||
}
|
||||
|
||||
return s
|
||||
}
|
||||
|
||||
// DataBearing returns true if the server is a data bearing server.
|
||||
func (s Server) DataBearing() bool {
|
||||
return s.Kind == RSPrimary ||
|
||||
s.Kind == RSSecondary ||
|
||||
s.Kind == Mongos ||
|
||||
s.Kind == Standalone
|
||||
}
|
||||
|
||||
// SelectServer selects this server if it is in the list of given candidates.
|
||||
func (s Server) SelectServer(_ Topology, candidates []Server) ([]Server, error) {
|
||||
for _, candidate := range candidates {
|
||||
if candidate.Addr == s.Addr {
|
||||
return []Server{candidate}, nil
|
||||
}
|
||||
}
|
||||
return nil, nil
|
||||
}
|
||||
43
vendor/go.mongodb.org/mongo-driver/x/mongo/driver/description/server_kind.go
generated
vendored
Executable file
43
vendor/go.mongodb.org/mongo-driver/x/mongo/driver/description/server_kind.go
generated
vendored
Executable file
@@ -0,0 +1,43 @@
|
||||
// Copyright (C) MongoDB, Inc. 2017-present.
|
||||
//
|
||||
// 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
|
||||
|
||||
package description
|
||||
|
||||
// ServerKind represents the type of a server.
|
||||
type ServerKind uint32
|
||||
|
||||
// These constants are the possible types of servers.
|
||||
const (
|
||||
Standalone ServerKind = 1
|
||||
RSMember ServerKind = 2
|
||||
RSPrimary ServerKind = 4 + RSMember
|
||||
RSSecondary ServerKind = 8 + RSMember
|
||||
RSArbiter ServerKind = 16 + RSMember
|
||||
RSGhost ServerKind = 32 + RSMember
|
||||
Mongos ServerKind = 256
|
||||
)
|
||||
|
||||
// String implements the fmt.Stringer interface.
|
||||
func (kind ServerKind) String() string {
|
||||
switch kind {
|
||||
case Standalone:
|
||||
return "Standalone"
|
||||
case RSMember:
|
||||
return "RSOther"
|
||||
case RSPrimary:
|
||||
return "RSPrimary"
|
||||
case RSSecondary:
|
||||
return "RSSecondary"
|
||||
case RSArbiter:
|
||||
return "RSArbiter"
|
||||
case RSGhost:
|
||||
return "RSGhost"
|
||||
case Mongos:
|
||||
return "Mongos"
|
||||
}
|
||||
|
||||
return "Unknown"
|
||||
}
|
||||
279
vendor/go.mongodb.org/mongo-driver/x/mongo/driver/description/server_selector.go
generated
vendored
Executable file
279
vendor/go.mongodb.org/mongo-driver/x/mongo/driver/description/server_selector.go
generated
vendored
Executable file
@@ -0,0 +1,279 @@
|
||||
// Copyright (C) MongoDB, Inc. 2017-present.
|
||||
//
|
||||
// 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
|
||||
|
||||
package description
|
||||
|
||||
import (
|
||||
"fmt"
|
||||
"math"
|
||||
"time"
|
||||
|
||||
"go.mongodb.org/mongo-driver/mongo/readpref"
|
||||
"go.mongodb.org/mongo-driver/tag"
|
||||
)
|
||||
|
||||
// ServerSelector is an interface implemented by types that can select a server given a
|
||||
// topology description.
|
||||
type ServerSelector interface {
|
||||
SelectServer(Topology, []Server) ([]Server, error)
|
||||
}
|
||||
|
||||
// ServerSelectorFunc is a function that can be used as a ServerSelector.
|
||||
type ServerSelectorFunc func(Topology, []Server) ([]Server, error)
|
||||
|
||||
// SelectServer implements the ServerSelector interface.
|
||||
func (ssf ServerSelectorFunc) SelectServer(t Topology, s []Server) ([]Server, error) {
|
||||
return ssf(t, s)
|
||||
}
|
||||
|
||||
type compositeSelector struct {
|
||||
selectors []ServerSelector
|
||||
}
|
||||
|
||||
// CompositeSelector combines multiple selectors into a single selector.
|
||||
func CompositeSelector(selectors []ServerSelector) ServerSelector {
|
||||
return &compositeSelector{selectors: selectors}
|
||||
}
|
||||
|
||||
func (cs *compositeSelector) SelectServer(t Topology, candidates []Server) ([]Server, error) {
|
||||
var err error
|
||||
for _, sel := range cs.selectors {
|
||||
candidates, err = sel.SelectServer(t, candidates)
|
||||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
}
|
||||
return candidates, nil
|
||||
}
|
||||
|
||||
type latencySelector struct {
|
||||
latency time.Duration
|
||||
}
|
||||
|
||||
// LatencySelector creates a ServerSelector which selects servers based on their latency.
|
||||
func LatencySelector(latency time.Duration) ServerSelector {
|
||||
return &latencySelector{latency: latency}
|
||||
}
|
||||
|
||||
func (ls *latencySelector) SelectServer(t Topology, candidates []Server) ([]Server, error) {
|
||||
if ls.latency < 0 {
|
||||
return candidates, nil
|
||||
}
|
||||
|
||||
switch len(candidates) {
|
||||
case 0, 1:
|
||||
return candidates, nil
|
||||
default:
|
||||
min := time.Duration(math.MaxInt64)
|
||||
for _, candidate := range candidates {
|
||||
if candidate.AverageRTTSet {
|
||||
if candidate.AverageRTT < min {
|
||||
min = candidate.AverageRTT
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
if min == math.MaxInt64 {
|
||||
return candidates, nil
|
||||
}
|
||||
|
||||
max := min + ls.latency
|
||||
|
||||
var result []Server
|
||||
for _, candidate := range candidates {
|
||||
if candidate.AverageRTTSet {
|
||||
if candidate.AverageRTT <= max {
|
||||
result = append(result, candidate)
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
return result, nil
|
||||
}
|
||||
}
|
||||
|
||||
// WriteSelector selects all the writable servers.
|
||||
func WriteSelector() ServerSelector {
|
||||
return ServerSelectorFunc(func(t Topology, candidates []Server) ([]Server, error) {
|
||||
switch t.Kind {
|
||||
case Single:
|
||||
return candidates, nil
|
||||
default:
|
||||
result := []Server{}
|
||||
for _, candidate := range candidates {
|
||||
switch candidate.Kind {
|
||||
case Mongos, RSPrimary, Standalone:
|
||||
result = append(result, candidate)
|
||||
}
|
||||
}
|
||||
return result, nil
|
||||
}
|
||||
})
|
||||
}
|
||||
|
||||
// ReadPrefSelector selects servers based on the provided read preference.
|
||||
func ReadPrefSelector(rp *readpref.ReadPref) ServerSelector {
|
||||
return ServerSelectorFunc(func(t Topology, candidates []Server) ([]Server, error) {
|
||||
if _, set := rp.MaxStaleness(); set {
|
||||
for _, s := range candidates {
|
||||
if s.Kind != Unknown {
|
||||
if err := MaxStalenessSupported(s.WireVersion); err != nil {
|
||||
return nil, err
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
switch t.Kind {
|
||||
case Single:
|
||||
return candidates, nil
|
||||
case ReplicaSetNoPrimary, ReplicaSetWithPrimary:
|
||||
return selectForReplicaSet(rp, t, candidates)
|
||||
case Sharded:
|
||||
return selectByKind(candidates, Mongos), nil
|
||||
}
|
||||
|
||||
return nil, nil
|
||||
})
|
||||
}
|
||||
|
||||
func selectForReplicaSet(rp *readpref.ReadPref, t Topology, candidates []Server) ([]Server, error) {
|
||||
if err := verifyMaxStaleness(rp, t); err != nil {
|
||||
return nil, err
|
||||
}
|
||||
|
||||
switch rp.Mode() {
|
||||
case readpref.PrimaryMode:
|
||||
return selectByKind(candidates, RSPrimary), nil
|
||||
case readpref.PrimaryPreferredMode:
|
||||
selected := selectByKind(candidates, RSPrimary)
|
||||
|
||||
if len(selected) == 0 {
|
||||
selected = selectSecondaries(rp, candidates)
|
||||
return selectByTagSet(selected, rp.TagSets()), nil
|
||||
}
|
||||
|
||||
return selected, nil
|
||||
case readpref.SecondaryPreferredMode:
|
||||
selected := selectSecondaries(rp, candidates)
|
||||
selected = selectByTagSet(selected, rp.TagSets())
|
||||
if len(selected) > 0 {
|
||||
return selected, nil
|
||||
}
|
||||
return selectByKind(candidates, RSPrimary), nil
|
||||
case readpref.SecondaryMode:
|
||||
selected := selectSecondaries(rp, candidates)
|
||||
return selectByTagSet(selected, rp.TagSets()), nil
|
||||
case readpref.NearestMode:
|
||||
selected := selectByKind(candidates, RSPrimary)
|
||||
selected = append(selected, selectSecondaries(rp, candidates)...)
|
||||
return selectByTagSet(selected, rp.TagSets()), nil
|
||||
}
|
||||
|
||||
return nil, fmt.Errorf("unsupported mode: %d", rp.Mode())
|
||||
}
|
||||
|
||||
func selectSecondaries(rp *readpref.ReadPref, candidates []Server) []Server {
|
||||
secondaries := selectByKind(candidates, RSSecondary)
|
||||
if len(secondaries) == 0 {
|
||||
return secondaries
|
||||
}
|
||||
if maxStaleness, set := rp.MaxStaleness(); set {
|
||||
primaries := selectByKind(candidates, RSPrimary)
|
||||
if len(primaries) == 0 {
|
||||
baseTime := secondaries[0].LastWriteTime
|
||||
for i := 1; i < len(secondaries); i++ {
|
||||
if secondaries[i].LastWriteTime.After(baseTime) {
|
||||
baseTime = secondaries[i].LastWriteTime
|
||||
}
|
||||
}
|
||||
|
||||
var selected []Server
|
||||
for _, secondary := range secondaries {
|
||||
estimatedStaleness := baseTime.Sub(secondary.LastWriteTime) + secondary.HeartbeatInterval
|
||||
if estimatedStaleness <= maxStaleness {
|
||||
selected = append(selected, secondary)
|
||||
}
|
||||
}
|
||||
|
||||
return selected
|
||||
}
|
||||
|
||||
primary := primaries[0]
|
||||
|
||||
var selected []Server
|
||||
for _, secondary := range secondaries {
|
||||
estimatedStaleness := secondary.LastUpdateTime.Sub(secondary.LastWriteTime) - primary.LastUpdateTime.Sub(primary.LastWriteTime) + secondary.HeartbeatInterval
|
||||
if estimatedStaleness <= maxStaleness {
|
||||
selected = append(selected, secondary)
|
||||
}
|
||||
}
|
||||
return selected
|
||||
}
|
||||
|
||||
return secondaries
|
||||
}
|
||||
|
||||
func selectByTagSet(candidates []Server, tagSets []tag.Set) []Server {
|
||||
if len(tagSets) == 0 {
|
||||
return candidates
|
||||
}
|
||||
|
||||
for _, ts := range tagSets {
|
||||
var results []Server
|
||||
for _, s := range candidates {
|
||||
if len(s.Tags) > 0 && s.Tags.ContainsAll(ts) {
|
||||
results = append(results, s)
|
||||
}
|
||||
}
|
||||
|
||||
if len(results) > 0 {
|
||||
return results
|
||||
}
|
||||
}
|
||||
|
||||
return []Server{}
|
||||
}
|
||||
|
||||
func selectByKind(candidates []Server, kind ServerKind) []Server {
|
||||
var result []Server
|
||||
for _, s := range candidates {
|
||||
if s.Kind == kind {
|
||||
result = append(result, s)
|
||||
}
|
||||
}
|
||||
|
||||
return result
|
||||
}
|
||||
|
||||
func verifyMaxStaleness(rp *readpref.ReadPref, t Topology) error {
|
||||
maxStaleness, set := rp.MaxStaleness()
|
||||
if !set {
|
||||
return nil
|
||||
}
|
||||
|
||||
if maxStaleness < 90*time.Second {
|
||||
return fmt.Errorf("max staleness (%s) must be greater than or equal to 90s", maxStaleness)
|
||||
}
|
||||
|
||||
if len(t.Servers) < 1 {
|
||||
// Maybe we should return an error here instead?
|
||||
return nil
|
||||
}
|
||||
|
||||
// we'll assume all candidates have the same heartbeat interval.
|
||||
s := t.Servers[0]
|
||||
idleWritePeriod := 10 * time.Second
|
||||
|
||||
if maxStaleness < s.HeartbeatInterval+idleWritePeriod {
|
||||
return fmt.Errorf(
|
||||
"max staleness (%s) must be greater than or equal to the heartbeat interval (%s) plus idle write period (%s)",
|
||||
maxStaleness, s.HeartbeatInterval, idleWritePeriod,
|
||||
)
|
||||
}
|
||||
|
||||
return nil
|
||||
}
|
||||
136
vendor/go.mongodb.org/mongo-driver/x/mongo/driver/description/topology.go
generated
vendored
Executable file
136
vendor/go.mongodb.org/mongo-driver/x/mongo/driver/description/topology.go
generated
vendored
Executable file
@@ -0,0 +1,136 @@
|
||||
// Copyright (C) MongoDB, Inc. 2017-present.
|
||||
//
|
||||
// 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
|
||||
|
||||
package description
|
||||
|
||||
import (
|
||||
"sort"
|
||||
"strings"
|
||||
|
||||
"go.mongodb.org/mongo-driver/x/mongo/driver/address"
|
||||
)
|
||||
|
||||
// Topology represents a description of a mongodb topology
|
||||
type Topology struct {
|
||||
Servers []Server
|
||||
Kind TopologyKind
|
||||
SessionTimeoutMinutes uint32
|
||||
}
|
||||
|
||||
// Server returns the server for the given address. Returns false if the server
|
||||
// could not be found.
|
||||
func (t Topology) Server(addr address.Address) (Server, bool) {
|
||||
for _, server := range t.Servers {
|
||||
if server.Addr.String() == addr.String() {
|
||||
return server, true
|
||||
}
|
||||
}
|
||||
return Server{}, false
|
||||
}
|
||||
|
||||
// TopologyDiff is the difference between two different topology descriptions.
|
||||
type TopologyDiff struct {
|
||||
Added []Server
|
||||
Removed []Server
|
||||
}
|
||||
|
||||
// DiffTopology compares the two topology descriptions and returns the difference.
|
||||
func DiffTopology(old, new Topology) TopologyDiff {
|
||||
var diff TopologyDiff
|
||||
|
||||
// TODO: do this without sorting...
|
||||
oldServers := serverSorter(old.Servers)
|
||||
newServers := serverSorter(new.Servers)
|
||||
|
||||
sort.Sort(oldServers)
|
||||
sort.Sort(newServers)
|
||||
|
||||
i := 0
|
||||
j := 0
|
||||
for {
|
||||
if i < len(oldServers) && j < len(newServers) {
|
||||
comp := strings.Compare(oldServers[i].Addr.String(), newServers[j].Addr.String())
|
||||
switch comp {
|
||||
case 1:
|
||||
//left is bigger than
|
||||
diff.Added = append(diff.Added, newServers[j])
|
||||
j++
|
||||
case -1:
|
||||
// right is bigger
|
||||
diff.Removed = append(diff.Removed, oldServers[i])
|
||||
i++
|
||||
case 0:
|
||||
i++
|
||||
j++
|
||||
}
|
||||
} else if i < len(oldServers) {
|
||||
diff.Removed = append(diff.Removed, oldServers[i])
|
||||
i++
|
||||
} else if j < len(newServers) {
|
||||
diff.Added = append(diff.Added, newServers[j])
|
||||
j++
|
||||
} else {
|
||||
break
|
||||
}
|
||||
}
|
||||
|
||||
return diff
|
||||
}
|
||||
|
||||
// HostlistDiff is the difference between a topology and a host list.
|
||||
type HostlistDiff struct {
|
||||
Added []string
|
||||
Removed []string
|
||||
}
|
||||
|
||||
// DiffHostlist compares the topology description and host list and returns the difference.
|
||||
func (t Topology) DiffHostlist(hostlist []string) HostlistDiff {
|
||||
var diff HostlistDiff
|
||||
|
||||
oldServers := serverSorter(t.Servers)
|
||||
sort.Sort(oldServers)
|
||||
sort.Strings(hostlist)
|
||||
|
||||
i := 0
|
||||
j := 0
|
||||
for {
|
||||
if i < len(oldServers) && j < len(hostlist) {
|
||||
oldServer := oldServers[i].Addr.String()
|
||||
comp := strings.Compare(oldServer, hostlist[j])
|
||||
switch comp {
|
||||
case 1:
|
||||
// oldServers[i] is bigger
|
||||
diff.Added = append(diff.Added, hostlist[j])
|
||||
j++
|
||||
case -1:
|
||||
// hostlist[j] is bigger
|
||||
diff.Removed = append(diff.Removed, oldServer)
|
||||
i++
|
||||
case 0:
|
||||
i++
|
||||
j++
|
||||
}
|
||||
} else if i < len(oldServers) {
|
||||
diff.Removed = append(diff.Removed, oldServers[i].Addr.String())
|
||||
i++
|
||||
} else if j < len(hostlist) {
|
||||
diff.Added = append(diff.Added, hostlist[j])
|
||||
j++
|
||||
} else {
|
||||
break
|
||||
}
|
||||
}
|
||||
|
||||
return diff
|
||||
}
|
||||
|
||||
type serverSorter []Server
|
||||
|
||||
func (ss serverSorter) Len() int { return len(ss) }
|
||||
func (ss serverSorter) Swap(i, j int) { ss[i], ss[j] = ss[j], ss[i] }
|
||||
func (ss serverSorter) Less(i, j int) bool {
|
||||
return strings.Compare(ss[i].Addr.String(), ss[j].Addr.String()) < 0
|
||||
}
|
||||
37
vendor/go.mongodb.org/mongo-driver/x/mongo/driver/description/topology_kind.go
generated
vendored
Executable file
37
vendor/go.mongodb.org/mongo-driver/x/mongo/driver/description/topology_kind.go
generated
vendored
Executable file
@@ -0,0 +1,37 @@
|
||||
// Copyright (C) MongoDB, Inc. 2017-present.
|
||||
//
|
||||
// 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
|
||||
|
||||
package description
|
||||
|
||||
// TopologyKind represents a specific topology configuration.
|
||||
type TopologyKind uint32
|
||||
|
||||
// These constants are the available topology configurations.
|
||||
const (
|
||||
Single TopologyKind = 1
|
||||
ReplicaSet TopologyKind = 2
|
||||
ReplicaSetNoPrimary TopologyKind = 4 + ReplicaSet
|
||||
ReplicaSetWithPrimary TopologyKind = 8 + ReplicaSet
|
||||
Sharded TopologyKind = 256
|
||||
)
|
||||
|
||||
// String implements the fmt.Stringer interface.
|
||||
func (kind TopologyKind) String() string {
|
||||
switch kind {
|
||||
case Single:
|
||||
return "Single"
|
||||
case ReplicaSet:
|
||||
return "ReplicaSet"
|
||||
case ReplicaSetNoPrimary:
|
||||
return "ReplicaSetNoPrimary"
|
||||
case ReplicaSetWithPrimary:
|
||||
return "ReplicaSetWithPrimary"
|
||||
case Sharded:
|
||||
return "Sharded"
|
||||
}
|
||||
|
||||
return "Unknown"
|
||||
}
|
||||
44
vendor/go.mongodb.org/mongo-driver/x/mongo/driver/description/version.go
generated
vendored
Executable file
44
vendor/go.mongodb.org/mongo-driver/x/mongo/driver/description/version.go
generated
vendored
Executable file
@@ -0,0 +1,44 @@
|
||||
// Copyright (C) MongoDB, Inc. 2017-present.
|
||||
//
|
||||
// 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
|
||||
|
||||
package description
|
||||
|
||||
import "strconv"
|
||||
|
||||
// Version represents a software version.
|
||||
type Version struct {
|
||||
Desc string
|
||||
Parts []uint8
|
||||
}
|
||||
|
||||
// AtLeast ensures that the version is at least as large as the "other" version.
|
||||
func (v Version) AtLeast(other ...uint8) bool {
|
||||
for i := range other {
|
||||
if i == len(v.Parts) {
|
||||
return false
|
||||
}
|
||||
if v.Parts[i] < other[i] {
|
||||
return false
|
||||
}
|
||||
}
|
||||
return true
|
||||
}
|
||||
|
||||
// String provides the string represtation of the Version.
|
||||
func (v Version) String() string {
|
||||
if v.Desc == "" {
|
||||
var s string
|
||||
for i, p := range v.Parts {
|
||||
if i != 0 {
|
||||
s += "."
|
||||
}
|
||||
s += strconv.Itoa(int(p))
|
||||
}
|
||||
return s
|
||||
}
|
||||
|
||||
return v.Desc
|
||||
}
|
||||
31
vendor/go.mongodb.org/mongo-driver/x/mongo/driver/description/version_range.go
generated
vendored
Executable file
31
vendor/go.mongodb.org/mongo-driver/x/mongo/driver/description/version_range.go
generated
vendored
Executable file
@@ -0,0 +1,31 @@
|
||||
// Copyright (C) MongoDB, Inc. 2017-present.
|
||||
//
|
||||
// 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
|
||||
|
||||
package description
|
||||
|
||||
import "fmt"
|
||||
|
||||
// VersionRange represents a range of versions.
|
||||
type VersionRange struct {
|
||||
Min int32
|
||||
Max int32
|
||||
}
|
||||
|
||||
// NewVersionRange creates a new VersionRange given a min and a max.
|
||||
func NewVersionRange(min, max int32) VersionRange {
|
||||
return VersionRange{Min: min, Max: max}
|
||||
}
|
||||
|
||||
// Includes returns a bool indicating whether the supplied integer is included
|
||||
// in the range.
|
||||
func (vr VersionRange) Includes(v int32) bool {
|
||||
return v >= vr.Min && v <= vr.Max
|
||||
}
|
||||
|
||||
// String implements the fmt.Stringer interface.
|
||||
func (vr VersionRange) String() string {
|
||||
return fmt.Sprintf("[%d, %d]", vr.Min, vr.Max)
|
||||
}
|
||||
Reference in New Issue
Block a user