Merge remote-tracking branch 'origin/main' into sync-tests

# Conflicts:
#	commonspace/object/tree/synctree/synctree_test.go
#	commonspace/objectsync/objectsync.go
#	commonspace/objectsync/syncclient.go
This commit is contained in:
mcrakhman 2023-04-19 10:13:37 +02:00
commit 73201843e5
No known key found for this signature in database
GPG Key ID: DED12CFEF5B8396B
44 changed files with 2854 additions and 838 deletions

View File

@ -1,6 +1,9 @@
package logger package logger
import ( import (
"fmt"
"strings"
"go.uber.org/zap" "go.uber.org/zap"
"go.uber.org/zap/zapcore" "go.uber.org/zap/zapcore"
@ -15,14 +18,19 @@ const (
JSONOutput JSONOutput
) )
type NamedLevel struct {
Name string `yaml:"name"`
Level string `yaml:"level"`
}
type Config struct { type Config struct {
Production bool `yaml:"production"` Production bool `yaml:"production"`
DefaultLevel string `yaml:"defaultLevel"` DefaultLevel string `yaml:"defaultLevel"`
NamedLevels map[string]string `yaml:"namedLevels"` Levels []NamedLevel `yaml:"levels"` // first match will be used
AddOutputPaths []string `yaml:"outputPaths"` AddOutputPaths []string `yaml:"outputPaths"`
DisableStdErr bool `yaml:"disableStdErr"` DisableStdErr bool `yaml:"disableStdErr"`
Format LogFormat `yaml:"format"` Format LogFormat `yaml:"format"`
ZapConfig *zap.Config `yaml:"-"` // optional, if set it will be used instead of other config options ZapConfig *zap.Config `yaml:"-"` // optional, if set it will be used instead of other config options
} }
func (l Config) ApplyGlobal() { func (l Config) ApplyGlobal() {
@ -68,20 +76,49 @@ func (l Config) ApplyGlobal() {
conf.Level = defaultLevel conf.Level = defaultLevel
} }
} }
var lvl = make(map[string]zap.AtomicLevel) for _, v := range l.Levels {
for k, v := range l.NamedLevels { if lev, err := zap.ParseAtomicLevel(v.Level); err == nil {
if lev, err := zap.ParseAtomicLevel(v); err == nil {
lvl[k] = lev
// we need to have a minimum level of all named loggers for the main logger // we need to have a minimum level of all named loggers for the main logger
if lev.Level() < conf.Level.Level() { if lev.Level() < conf.Level.Level() {
conf.Level.SetLevel(lev.Level()) conf.Level.SetLevel(lev.Level())
} }
} }
} }
lg, err := conf.Build() lg, err := conf.Build()
if err != nil { if err != nil {
Default().Fatal("can't build logger", zap.Error(err)) Default().Fatal("can't build logger", zap.Error(err))
} }
SetDefault(lg) SetDefault(lg)
SetNamedLevels(lvl) SetNamedLevels(l.Levels)
}
// LevelsFromStr parses a string of the form "name1=DEBUG;prefix*=WARN;*=ERROR" into a slice of NamedLevel
// it may be useful to parse the log level from the OS env var
func LevelsFromStr(s string) (levels []NamedLevel) {
for _, kv := range strings.Split(s, ";") {
strings.TrimSpace(kv)
parts := strings.Split(kv, "=")
var key, value string
if len(parts) == 1 {
key = "*"
value = parts[0]
_, err := zap.ParseAtomicLevel(value)
if err != nil {
fmt.Printf("Can't parse log level %s: %s\n", parts[0], err.Error())
continue
}
levels = append(levels, NamedLevel{Name: key, Level: value})
} else if len(parts) == 2 {
key = parts[0]
value = parts[1]
}
_, err := zap.ParseAtomicLevel(value)
if err != nil {
fmt.Printf("Can't parse log level %s: %s\n", parts[0], err.Error())
continue
}
levels = append(levels, NamedLevel{Name: key, Level: value})
}
return levels
} }

View File

@ -11,12 +11,17 @@ var (
mu sync.Mutex mu sync.Mutex
logger *zap.Logger logger *zap.Logger
loggerConfig zap.Config loggerConfig zap.Config
namedLevels = make(map[string]zap.AtomicLevel) namedLevels []namedLevel
namedGlobs = make(map[string]glob.Glob) namedGlobs = make(map[string]glob.Glob)
namedLoggers = make(map[string]CtxLogger) namedLoggers = make(map[string]CtxLogger)
namedSugarLoggers = make(map[string]*zap.SugaredLogger) namedSugarLoggers = make(map[string]*zap.SugaredLogger)
) )
type namedLevel struct {
name string
level zap.AtomicLevel
}
func init() { func init() {
loggerConfig = zap.NewDevelopmentConfig() loggerConfig = zap.NewDevelopmentConfig()
logger, _ = loggerConfig.Build() logger, _ = loggerConfig.Build()
@ -35,18 +40,23 @@ func SetDefault(l *zap.Logger) {
// it also supports glob patterns for names, like "app*" // it also supports glob patterns for names, like "app*"
// can be racy in case there are existing named loggers // can be racy in case there are existing named loggers
// so consider to call only once at the beginning // so consider to call only once at the beginning
func SetNamedLevels(l map[string]zap.AtomicLevel) { func SetNamedLevels(nls []NamedLevel) {
mu.Lock() mu.Lock()
defer mu.Unlock() defer mu.Unlock()
namedLevels = l namedLevels = namedLevels[:0]
var minLevel = logger.Level() var minLevel = logger.Level()
for k, l := range namedLevels { for _, nl := range nls {
g, err := glob.Compile(k) l, err := zap.ParseAtomicLevel(nl.Level)
if err == nil { if err != nil {
namedGlobs[k] = g continue
} }
namedLevels[k] = l namedLevels = append(namedLevels, namedLevel{name: nl.Name, level: l})
g, err := glob.Compile(nl.Name)
if err == nil {
namedGlobs[nl.Name] = g
}
if l.Level() < minLevel { if l.Level() < minLevel {
minLevel = l.Level() minLevel = l.Level()
} }
@ -81,23 +91,18 @@ func Default() *zap.Logger {
return logger return logger
} }
// getLevel returns the level for the given name
// it return the first matching name or glob pattern whatever comes first
func getLevel(name string) zap.AtomicLevel { func getLevel(name string) zap.AtomicLevel {
level, ok := namedLevels[name] for _, nl := range namedLevels {
if !ok { if nl.name == name {
var found bool return nl.level
for globName, glob := range namedGlobs {
if glob.Match(name) {
found = true
level, _ = namedLevels[globName]
// no need to check ok, because we know that globName exists
break
}
} }
if !found { if g, ok := namedGlobs[nl.name]; ok && g.Match(name) {
level = loggerConfig.Level return nl.level
} }
} }
return level return zap.NewAtomicLevelAt(logger.Level())
} }
func NewNamed(name string, fields ...zap.Field) CtxLogger { func NewNamed(name string, fields ...zap.Field) CtxLogger {

150
app/logger/log_test.go Normal file
View File

@ -0,0 +1,150 @@
package logger
import (
"reflect"
"testing"
"go.uber.org/zap"
)
func Test_getLevel1(t *testing.T) {
SetNamedLevels([]NamedLevel{
{Name: "app", Level: "debug"},
{Name: "app*", Level: "info"},
{Name: "app.sub", Level: "warn"},
{Name: "*", Level: "fatal"},
})
tests := []struct {
name string
want zap.AtomicLevel
}{
{
name: "app",
want: zap.NewAtomicLevelAt(zap.DebugLevel),
},
{
name: "app.aaa",
want: zap.NewAtomicLevelAt(zap.InfoLevel),
},
{
name: "app.sub",
want: zap.NewAtomicLevelAt(zap.InfoLevel),
},
{
name: "random",
want: zap.NewAtomicLevelAt(zap.FatalLevel),
},
}
for _, tt := range tests {
t.Run(tt.name, func(t *testing.T) {
if got := getLevel(tt.name); !reflect.DeepEqual(got, tt.want) {
t.Errorf("getLevel() = %v, want %v", got, tt.want)
}
})
}
}
func Test_getLevel2(t *testing.T) {
SetNamedLevels([]NamedLevel{
{Name: "*", Level: "ERROR"},
{Name: "app", Level: "info"},
{Name: "app.sub", Level: "warn"},
{Name: "*", Level: "fatal"},
})
tests := []struct {
name string
want zap.AtomicLevel
}{
{
name: "app",
want: zap.NewAtomicLevelAt(zap.ErrorLevel),
},
{
name: "app.aaa",
want: zap.NewAtomicLevelAt(zap.ErrorLevel),
},
{
name: "app.sub",
want: zap.NewAtomicLevelAt(zap.ErrorLevel),
},
{
name: "random",
want: zap.NewAtomicLevelAt(zap.ErrorLevel),
},
}
for _, tt := range tests {
t.Run(tt.name, func(t *testing.T) {
if got := getLevel(tt.name); !reflect.DeepEqual(got, tt.want) {
t.Errorf("getLevel() = %v, want %v", got, tt.want)
}
})
}
}
func Test_getLevel3(t *testing.T) {
SetNamedLevels([]NamedLevel{
{Name: "app", Level: "info"},
{Name: "*.sub", Level: "warn"},
{Name: "*", Level: "fatal"},
})
tests := []struct {
name string
want zap.AtomicLevel
}{
{
name: "app",
want: zap.NewAtomicLevelAt(zap.InfoLevel),
},
{
name: "app.sub",
want: zap.NewAtomicLevelAt(zap.WarnLevel),
},
{
name: "random",
want: zap.NewAtomicLevelAt(zap.FatalLevel),
},
}
for _, tt := range tests {
t.Run(tt.name, func(t *testing.T) {
if got := getLevel(tt.name); !reflect.DeepEqual(got, tt.want) {
t.Errorf("getLevel() = %v, want %v", got, tt.want)
}
})
}
}
func Test_getLevel4(t *testing.T) {
SetNamedLevels([]NamedLevel{
{Name: "*", Level: "invalid"},
{Name: "app", Level: "info"},
{Name: "b", Level: "invalid"},
})
tests := []struct {
name string
want zap.AtomicLevel
}{
{
name: "app",
want: zap.NewAtomicLevelAt(zap.InfoLevel),
},
{
name: "app.sub",
want: zap.NewAtomicLevelAt(logger.Level()),
},
{
name: "b",
want: zap.NewAtomicLevelAt(logger.Level()),
},
}
for _, tt := range tests {
t.Run(tt.name, func(t *testing.T) {
if got := getLevel(tt.name); !reflect.DeepEqual(got, tt.want) {
t.Errorf("getLevel() = %v, want %v", got, tt.want)
}
})
}
}

View File

@ -298,94 +298,6 @@ func (m *BlockPushResponse) XXX_DiscardUnknown() {
var xxx_messageInfo_BlockPushResponse proto.InternalMessageInfo var xxx_messageInfo_BlockPushResponse proto.InternalMessageInfo
type BlocksDeleteRequest struct {
SpaceId string `protobuf:"bytes,1,opt,name=spaceId,proto3" json:"spaceId,omitempty"`
Cids [][]byte `protobuf:"bytes,2,rep,name=cids,proto3" json:"cids,omitempty"`
}
func (m *BlocksDeleteRequest) Reset() { *m = BlocksDeleteRequest{} }
func (m *BlocksDeleteRequest) String() string { return proto.CompactTextString(m) }
func (*BlocksDeleteRequest) ProtoMessage() {}
func (*BlocksDeleteRequest) Descriptor() ([]byte, []int) {
return fileDescriptor_fd665a7e11c833d5, []int{4}
}
func (m *BlocksDeleteRequest) XXX_Unmarshal(b []byte) error {
return m.Unmarshal(b)
}
func (m *BlocksDeleteRequest) XXX_Marshal(b []byte, deterministic bool) ([]byte, error) {
if deterministic {
return xxx_messageInfo_BlocksDeleteRequest.Marshal(b, m, deterministic)
} else {
b = b[:cap(b)]
n, err := m.MarshalToSizedBuffer(b)
if err != nil {
return nil, err
}
return b[:n], nil
}
}
func (m *BlocksDeleteRequest) XXX_Merge(src proto.Message) {
xxx_messageInfo_BlocksDeleteRequest.Merge(m, src)
}
func (m *BlocksDeleteRequest) XXX_Size() int {
return m.Size()
}
func (m *BlocksDeleteRequest) XXX_DiscardUnknown() {
xxx_messageInfo_BlocksDeleteRequest.DiscardUnknown(m)
}
var xxx_messageInfo_BlocksDeleteRequest proto.InternalMessageInfo
func (m *BlocksDeleteRequest) GetSpaceId() string {
if m != nil {
return m.SpaceId
}
return ""
}
func (m *BlocksDeleteRequest) GetCids() [][]byte {
if m != nil {
return m.Cids
}
return nil
}
type BlocksDeleteResponse struct {
}
func (m *BlocksDeleteResponse) Reset() { *m = BlocksDeleteResponse{} }
func (m *BlocksDeleteResponse) String() string { return proto.CompactTextString(m) }
func (*BlocksDeleteResponse) ProtoMessage() {}
func (*BlocksDeleteResponse) Descriptor() ([]byte, []int) {
return fileDescriptor_fd665a7e11c833d5, []int{5}
}
func (m *BlocksDeleteResponse) XXX_Unmarshal(b []byte) error {
return m.Unmarshal(b)
}
func (m *BlocksDeleteResponse) XXX_Marshal(b []byte, deterministic bool) ([]byte, error) {
if deterministic {
return xxx_messageInfo_BlocksDeleteResponse.Marshal(b, m, deterministic)
} else {
b = b[:cap(b)]
n, err := m.MarshalToSizedBuffer(b)
if err != nil {
return nil, err
}
return b[:n], nil
}
}
func (m *BlocksDeleteResponse) XXX_Merge(src proto.Message) {
xxx_messageInfo_BlocksDeleteResponse.Merge(m, src)
}
func (m *BlocksDeleteResponse) XXX_Size() int {
return m.Size()
}
func (m *BlocksDeleteResponse) XXX_DiscardUnknown() {
xxx_messageInfo_BlocksDeleteResponse.DiscardUnknown(m)
}
var xxx_messageInfo_BlocksDeleteResponse proto.InternalMessageInfo
type BlocksCheckRequest struct { type BlocksCheckRequest struct {
SpaceId string `protobuf:"bytes,1,opt,name=spaceId,proto3" json:"spaceId,omitempty"` SpaceId string `protobuf:"bytes,1,opt,name=spaceId,proto3" json:"spaceId,omitempty"`
Cids [][]byte `protobuf:"bytes,2,rep,name=cids,proto3" json:"cids,omitempty"` Cids [][]byte `protobuf:"bytes,2,rep,name=cids,proto3" json:"cids,omitempty"`
@ -395,7 +307,7 @@ func (m *BlocksCheckRequest) Reset() { *m = BlocksCheckRequest{} }
func (m *BlocksCheckRequest) String() string { return proto.CompactTextString(m) } func (m *BlocksCheckRequest) String() string { return proto.CompactTextString(m) }
func (*BlocksCheckRequest) ProtoMessage() {} func (*BlocksCheckRequest) ProtoMessage() {}
func (*BlocksCheckRequest) Descriptor() ([]byte, []int) { func (*BlocksCheckRequest) Descriptor() ([]byte, []int) {
return fileDescriptor_fd665a7e11c833d5, []int{6} return fileDescriptor_fd665a7e11c833d5, []int{4}
} }
func (m *BlocksCheckRequest) XXX_Unmarshal(b []byte) error { func (m *BlocksCheckRequest) XXX_Unmarshal(b []byte) error {
return m.Unmarshal(b) return m.Unmarshal(b)
@ -446,7 +358,7 @@ func (m *BlocksCheckResponse) Reset() { *m = BlocksCheckResponse{} }
func (m *BlocksCheckResponse) String() string { return proto.CompactTextString(m) } func (m *BlocksCheckResponse) String() string { return proto.CompactTextString(m) }
func (*BlocksCheckResponse) ProtoMessage() {} func (*BlocksCheckResponse) ProtoMessage() {}
func (*BlocksCheckResponse) Descriptor() ([]byte, []int) { func (*BlocksCheckResponse) Descriptor() ([]byte, []int) {
return fileDescriptor_fd665a7e11c833d5, []int{7} return fileDescriptor_fd665a7e11c833d5, []int{5}
} }
func (m *BlocksCheckResponse) XXX_Unmarshal(b []byte) error { func (m *BlocksCheckResponse) XXX_Unmarshal(b []byte) error {
return m.Unmarshal(b) return m.Unmarshal(b)
@ -491,7 +403,7 @@ func (m *BlockAvailability) Reset() { *m = BlockAvailability{} }
func (m *BlockAvailability) String() string { return proto.CompactTextString(m) } func (m *BlockAvailability) String() string { return proto.CompactTextString(m) }
func (*BlockAvailability) ProtoMessage() {} func (*BlockAvailability) ProtoMessage() {}
func (*BlockAvailability) Descriptor() ([]byte, []int) { func (*BlockAvailability) Descriptor() ([]byte, []int) {
return fileDescriptor_fd665a7e11c833d5, []int{8} return fileDescriptor_fd665a7e11c833d5, []int{6}
} }
func (m *BlockAvailability) XXX_Unmarshal(b []byte) error { func (m *BlockAvailability) XXX_Unmarshal(b []byte) error {
return m.Unmarshal(b) return m.Unmarshal(b)
@ -544,7 +456,7 @@ func (m *BlocksBindRequest) Reset() { *m = BlocksBindRequest{} }
func (m *BlocksBindRequest) String() string { return proto.CompactTextString(m) } func (m *BlocksBindRequest) String() string { return proto.CompactTextString(m) }
func (*BlocksBindRequest) ProtoMessage() {} func (*BlocksBindRequest) ProtoMessage() {}
func (*BlocksBindRequest) Descriptor() ([]byte, []int) { func (*BlocksBindRequest) Descriptor() ([]byte, []int) {
return fileDescriptor_fd665a7e11c833d5, []int{9} return fileDescriptor_fd665a7e11c833d5, []int{7}
} }
func (m *BlocksBindRequest) XXX_Unmarshal(b []byte) error { func (m *BlocksBindRequest) XXX_Unmarshal(b []byte) error {
return m.Unmarshal(b) return m.Unmarshal(b)
@ -601,7 +513,7 @@ func (m *BlocksBindResponse) Reset() { *m = BlocksBindResponse{} }
func (m *BlocksBindResponse) String() string { return proto.CompactTextString(m) } func (m *BlocksBindResponse) String() string { return proto.CompactTextString(m) }
func (*BlocksBindResponse) ProtoMessage() {} func (*BlocksBindResponse) ProtoMessage() {}
func (*BlocksBindResponse) Descriptor() ([]byte, []int) { func (*BlocksBindResponse) Descriptor() ([]byte, []int) {
return fileDescriptor_fd665a7e11c833d5, []int{10} return fileDescriptor_fd665a7e11c833d5, []int{8}
} }
func (m *BlocksBindResponse) XXX_Unmarshal(b []byte) error { func (m *BlocksBindResponse) XXX_Unmarshal(b []byte) error {
return m.Unmarshal(b) return m.Unmarshal(b)
@ -639,7 +551,7 @@ func (m *FilesDeleteRequest) Reset() { *m = FilesDeleteRequest{} }
func (m *FilesDeleteRequest) String() string { return proto.CompactTextString(m) } func (m *FilesDeleteRequest) String() string { return proto.CompactTextString(m) }
func (*FilesDeleteRequest) ProtoMessage() {} func (*FilesDeleteRequest) ProtoMessage() {}
func (*FilesDeleteRequest) Descriptor() ([]byte, []int) { func (*FilesDeleteRequest) Descriptor() ([]byte, []int) {
return fileDescriptor_fd665a7e11c833d5, []int{11} return fileDescriptor_fd665a7e11c833d5, []int{9}
} }
func (m *FilesDeleteRequest) XXX_Unmarshal(b []byte) error { func (m *FilesDeleteRequest) XXX_Unmarshal(b []byte) error {
return m.Unmarshal(b) return m.Unmarshal(b)
@ -689,7 +601,7 @@ func (m *FilesDeleteResponse) Reset() { *m = FilesDeleteResponse{} }
func (m *FilesDeleteResponse) String() string { return proto.CompactTextString(m) } func (m *FilesDeleteResponse) String() string { return proto.CompactTextString(m) }
func (*FilesDeleteResponse) ProtoMessage() {} func (*FilesDeleteResponse) ProtoMessage() {}
func (*FilesDeleteResponse) Descriptor() ([]byte, []int) { func (*FilesDeleteResponse) Descriptor() ([]byte, []int) {
return fileDescriptor_fd665a7e11c833d5, []int{12} return fileDescriptor_fd665a7e11c833d5, []int{10}
} }
func (m *FilesDeleteResponse) XXX_Unmarshal(b []byte) error { func (m *FilesDeleteResponse) XXX_Unmarshal(b []byte) error {
return m.Unmarshal(b) return m.Unmarshal(b)
@ -727,7 +639,7 @@ func (m *FilesInfoRequest) Reset() { *m = FilesInfoRequest{} }
func (m *FilesInfoRequest) String() string { return proto.CompactTextString(m) } func (m *FilesInfoRequest) String() string { return proto.CompactTextString(m) }
func (*FilesInfoRequest) ProtoMessage() {} func (*FilesInfoRequest) ProtoMessage() {}
func (*FilesInfoRequest) Descriptor() ([]byte, []int) { func (*FilesInfoRequest) Descriptor() ([]byte, []int) {
return fileDescriptor_fd665a7e11c833d5, []int{13} return fileDescriptor_fd665a7e11c833d5, []int{11}
} }
func (m *FilesInfoRequest) XXX_Unmarshal(b []byte) error { func (m *FilesInfoRequest) XXX_Unmarshal(b []byte) error {
return m.Unmarshal(b) return m.Unmarshal(b)
@ -778,7 +690,7 @@ func (m *FilesInfoResponse) Reset() { *m = FilesInfoResponse{} }
func (m *FilesInfoResponse) String() string { return proto.CompactTextString(m) } func (m *FilesInfoResponse) String() string { return proto.CompactTextString(m) }
func (*FilesInfoResponse) ProtoMessage() {} func (*FilesInfoResponse) ProtoMessage() {}
func (*FilesInfoResponse) Descriptor() ([]byte, []int) { func (*FilesInfoResponse) Descriptor() ([]byte, []int) {
return fileDescriptor_fd665a7e11c833d5, []int{14} return fileDescriptor_fd665a7e11c833d5, []int{12}
} }
func (m *FilesInfoResponse) XXX_Unmarshal(b []byte) error { func (m *FilesInfoResponse) XXX_Unmarshal(b []byte) error {
return m.Unmarshal(b) return m.Unmarshal(b)
@ -824,7 +736,7 @@ func (m *FileInfo) Reset() { *m = FileInfo{} }
func (m *FileInfo) String() string { return proto.CompactTextString(m) } func (m *FileInfo) String() string { return proto.CompactTextString(m) }
func (*FileInfo) ProtoMessage() {} func (*FileInfo) ProtoMessage() {}
func (*FileInfo) Descriptor() ([]byte, []int) { func (*FileInfo) Descriptor() ([]byte, []int) {
return fileDescriptor_fd665a7e11c833d5, []int{15} return fileDescriptor_fd665a7e11c833d5, []int{13}
} }
func (m *FileInfo) XXX_Unmarshal(b []byte) error { func (m *FileInfo) XXX_Unmarshal(b []byte) error {
return m.Unmarshal(b) return m.Unmarshal(b)
@ -881,7 +793,7 @@ func (m *CheckRequest) Reset() { *m = CheckRequest{} }
func (m *CheckRequest) String() string { return proto.CompactTextString(m) } func (m *CheckRequest) String() string { return proto.CompactTextString(m) }
func (*CheckRequest) ProtoMessage() {} func (*CheckRequest) ProtoMessage() {}
func (*CheckRequest) Descriptor() ([]byte, []int) { func (*CheckRequest) Descriptor() ([]byte, []int) {
return fileDescriptor_fd665a7e11c833d5, []int{16} return fileDescriptor_fd665a7e11c833d5, []int{14}
} }
func (m *CheckRequest) XXX_Unmarshal(b []byte) error { func (m *CheckRequest) XXX_Unmarshal(b []byte) error {
return m.Unmarshal(b) return m.Unmarshal(b)
@ -919,7 +831,7 @@ func (m *CheckResponse) Reset() { *m = CheckResponse{} }
func (m *CheckResponse) String() string { return proto.CompactTextString(m) } func (m *CheckResponse) String() string { return proto.CompactTextString(m) }
func (*CheckResponse) ProtoMessage() {} func (*CheckResponse) ProtoMessage() {}
func (*CheckResponse) Descriptor() ([]byte, []int) { func (*CheckResponse) Descriptor() ([]byte, []int) {
return fileDescriptor_fd665a7e11c833d5, []int{17} return fileDescriptor_fd665a7e11c833d5, []int{15}
} }
func (m *CheckResponse) XXX_Unmarshal(b []byte) error { func (m *CheckResponse) XXX_Unmarshal(b []byte) error {
return m.Unmarshal(b) return m.Unmarshal(b)
@ -970,7 +882,7 @@ func (m *SpaceInfoRequest) Reset() { *m = SpaceInfoRequest{} }
func (m *SpaceInfoRequest) String() string { return proto.CompactTextString(m) } func (m *SpaceInfoRequest) String() string { return proto.CompactTextString(m) }
func (*SpaceInfoRequest) ProtoMessage() {} func (*SpaceInfoRequest) ProtoMessage() {}
func (*SpaceInfoRequest) Descriptor() ([]byte, []int) { func (*SpaceInfoRequest) Descriptor() ([]byte, []int) {
return fileDescriptor_fd665a7e11c833d5, []int{18} return fileDescriptor_fd665a7e11c833d5, []int{16}
} }
func (m *SpaceInfoRequest) XXX_Unmarshal(b []byte) error { func (m *SpaceInfoRequest) XXX_Unmarshal(b []byte) error {
return m.Unmarshal(b) return m.Unmarshal(b)
@ -1017,7 +929,7 @@ func (m *SpaceInfoResponse) Reset() { *m = SpaceInfoResponse{} }
func (m *SpaceInfoResponse) String() string { return proto.CompactTextString(m) } func (m *SpaceInfoResponse) String() string { return proto.CompactTextString(m) }
func (*SpaceInfoResponse) ProtoMessage() {} func (*SpaceInfoResponse) ProtoMessage() {}
func (*SpaceInfoResponse) Descriptor() ([]byte, []int) { func (*SpaceInfoResponse) Descriptor() ([]byte, []int) {
return fileDescriptor_fd665a7e11c833d5, []int{19} return fileDescriptor_fd665a7e11c833d5, []int{17}
} }
func (m *SpaceInfoResponse) XXX_Unmarshal(b []byte) error { func (m *SpaceInfoResponse) XXX_Unmarshal(b []byte) error {
return m.Unmarshal(b) return m.Unmarshal(b)
@ -1081,8 +993,6 @@ func init() {
proto.RegisterType((*BlockGetResponse)(nil), "filesync.BlockGetResponse") proto.RegisterType((*BlockGetResponse)(nil), "filesync.BlockGetResponse")
proto.RegisterType((*BlockPushRequest)(nil), "filesync.BlockPushRequest") proto.RegisterType((*BlockPushRequest)(nil), "filesync.BlockPushRequest")
proto.RegisterType((*BlockPushResponse)(nil), "filesync.BlockPushResponse") proto.RegisterType((*BlockPushResponse)(nil), "filesync.BlockPushResponse")
proto.RegisterType((*BlocksDeleteRequest)(nil), "filesync.BlocksDeleteRequest")
proto.RegisterType((*BlocksDeleteResponse)(nil), "filesync.BlocksDeleteResponse")
proto.RegisterType((*BlocksCheckRequest)(nil), "filesync.BlocksCheckRequest") proto.RegisterType((*BlocksCheckRequest)(nil), "filesync.BlocksCheckRequest")
proto.RegisterType((*BlocksCheckResponse)(nil), "filesync.BlocksCheckResponse") proto.RegisterType((*BlocksCheckResponse)(nil), "filesync.BlocksCheckResponse")
proto.RegisterType((*BlockAvailability)(nil), "filesync.BlockAvailability") proto.RegisterType((*BlockAvailability)(nil), "filesync.BlockAvailability")
@ -1104,59 +1014,58 @@ func init() {
} }
var fileDescriptor_fd665a7e11c833d5 = []byte{ var fileDescriptor_fd665a7e11c833d5 = []byte{
// 817 bytes of a gzipped FileDescriptorProto // 805 bytes of a gzipped FileDescriptorProto
0x1f, 0x8b, 0x08, 0x00, 0x00, 0x00, 0x00, 0x00, 0x02, 0xff, 0xa4, 0x56, 0x4f, 0x53, 0xfb, 0x44, 0x1f, 0x8b, 0x08, 0x00, 0x00, 0x00, 0x00, 0x00, 0x02, 0xff, 0xa4, 0x56, 0xcd, 0x52, 0xeb, 0x36,
0x18, 0x6e, 0xda, 0xfc, 0x4a, 0xf3, 0x96, 0x42, 0xba, 0x40, 0xad, 0xa5, 0x66, 0x3a, 0x39, 0x38, 0x14, 0x8e, 0x13, 0x13, 0xe2, 0x13, 0x02, 0x8e, 0xf8, 0x69, 0x1a, 0x52, 0x4f, 0xc6, 0x8b, 0x0e,
0x0c, 0xe3, 0x14, 0x07, 0x3d, 0x70, 0xf1, 0x40, 0x4b, 0x0b, 0x15, 0x07, 0x35, 0x8c, 0xc3, 0xa8, 0xc3, 0x74, 0x42, 0x87, 0x76, 0xc1, 0xa6, 0x0b, 0x12, 0x12, 0x48, 0xe9, 0xd0, 0xd6, 0x4c, 0x87,
0x17, 0xd3, 0x64, 0x0b, 0x91, 0x90, 0xad, 0xd9, 0xad, 0x52, 0x3f, 0x82, 0x27, 0xfd, 0x32, 0x7e, 0x69, 0xbb, 0xa9, 0x63, 0x2b, 0xe0, 0x62, 0xac, 0xd4, 0x52, 0x5a, 0xd2, 0x47, 0xe8, 0xaa, 0x7d,
0x06, 0x8e, 0x1c, 0x3d, 0x3a, 0xf0, 0x45, 0x9c, 0xdd, 0x6c, 0x9a, 0xed, 0x1f, 0x07, 0xc4, 0x4b, 0x99, 0x3e, 0x03, 0x4b, 0x96, 0x77, 0x79, 0x07, 0x5e, 0xe4, 0x8e, 0x64, 0x39, 0x56, 0x7e, 0xee,
0xd8, 0x3c, 0xfb, 0xbe, 0xef, 0xf3, 0xee, 0xf3, 0x66, 0x1f, 0x0a, 0x1f, 0x7a, 0xe4, 0xee, 0x8e, 0x70, 0x7f, 0x36, 0x8e, 0xf4, 0xe9, 0x9c, 0xf3, 0x1d, 0x7d, 0x92, 0xbe, 0x09, 0x7c, 0xee, 0x91,
0x44, 0xa3, 0x20, 0xc4, 0x07, 0xfc, 0x31, 0x8e, 0x09, 0x23, 0x07, 0xe2, 0x49, 0x05, 0xd0, 0x16, 0xbb, 0x3b, 0x12, 0x0d, 0x83, 0x10, 0x1f, 0xf0, 0xcf, 0x28, 0x26, 0x8c, 0x1c, 0x88, 0x2f, 0x15,
0x6b, 0x54, 0xe2, 0x6b, 0x3a, 0x8d, 0x3c, 0xfb, 0x33, 0xd8, 0xec, 0x84, 0xc4, 0xbb, 0x3d, 0xc5, 0x40, 0x4b, 0x8c, 0x51, 0x89, 0x8f, 0xe9, 0x24, 0xf2, 0xec, 0x6f, 0x60, 0xa3, 0x1d, 0x12, 0xef,
0xcc, 0xc1, 0x3f, 0x4d, 0x30, 0x65, 0xa8, 0x0e, 0x6b, 0x74, 0xec, 0x7a, 0x78, 0xe0, 0xd7, 0xb5, 0xf6, 0x14, 0x33, 0x07, 0xff, 0x31, 0xc6, 0x94, 0xa1, 0x1a, 0xac, 0xd2, 0x91, 0xeb, 0xe1, 0xbe,
0x96, 0xb6, 0x67, 0x38, 0xe9, 0x2b, 0x32, 0xa1, 0xe0, 0x05, 0x7e, 0x3d, 0xdf, 0xd2, 0xf6, 0xd6, 0x5f, 0xd3, 0x9a, 0xda, 0x9e, 0xe1, 0xa4, 0x53, 0x64, 0x42, 0xc1, 0x0b, 0xfc, 0x5a, 0xbe, 0xa9,
0x1d, 0xbe, 0xb4, 0x8f, 0xc0, 0xcc, 0xd2, 0xe9, 0x98, 0x44, 0x14, 0xa7, 0x51, 0xda, 0x2c, 0x0a, 0xed, 0xad, 0x39, 0x7c, 0x68, 0x1f, 0x81, 0x99, 0xa5, 0xd3, 0x11, 0x89, 0x28, 0x4e, 0xa3, 0xb4,
0x21, 0xd0, 0x7d, 0x97, 0xb9, 0x32, 0x51, 0xac, 0xed, 0x1f, 0x65, 0xe6, 0x57, 0x13, 0x7a, 0xf3, 0x69, 0x14, 0x42, 0xa0, 0xfb, 0x2e, 0x73, 0x65, 0xa2, 0x18, 0xdb, 0xbf, 0xcb, 0xcc, 0x1f, 0xc6,
0x32, 0x73, 0x0d, 0x8a, 0xbc, 0xe5, 0x41, 0x42, 0x6e, 0x38, 0xf2, 0x2d, 0xe5, 0x2a, 0x2c, 0x73, 0xf4, 0xe6, 0x65, 0xe6, 0x1d, 0x28, 0xf2, 0x96, 0xfb, 0x09, 0xb9, 0xe1, 0xc8, 0x59, 0xca, 0x55,
0xe9, 0x0a, 0xd7, 0x16, 0x54, 0x15, 0xae, 0xa4, 0x4d, 0xbb, 0x0b, 0x5b, 0x02, 0xa4, 0x27, 0x38, 0x58, 0xe4, 0xd2, 0x15, 0xae, 0x4d, 0xa8, 0x2a, 0x5c, 0x49, 0x9b, 0x76, 0x1b, 0x90, 0x00, 0x69,
0xc4, 0x0c, 0xbf, 0xdc, 0x03, 0x02, 0xdd, 0x0b, 0x7c, 0x5a, 0xcf, 0xb7, 0x0a, 0xbc, 0x32, 0x5f, 0xe7, 0x06, 0x7b, 0xb7, 0x2f, 0xb7, 0x80, 0x40, 0xf7, 0x02, 0x9f, 0xd6, 0xf2, 0xcd, 0x02, 0x2f,
0xdb, 0x35, 0xd8, 0x9e, 0x2f, 0x22, 0x8b, 0x77, 0x00, 0x25, 0x78, 0xf7, 0x06, 0x7b, 0xb7, 0x6f, 0xcc, 0xc7, 0xf6, 0x00, 0x36, 0x67, 0x6a, 0x48, 0x05, 0xce, 0x01, 0x0d, 0x04, 0x7c, 0xfc, 0xa7,
0xab, 0x3d, 0x4c, 0x1b, 0x94, 0x35, 0xa4, 0xbc, 0xe7, 0x80, 0x86, 0x02, 0x3e, 0xfe, 0xd9, 0x0d, 0x1b, 0x84, 0xee, 0x20, 0x08, 0x03, 0x36, 0xa9, 0x69, 0xcd, 0xc2, 0x5e, 0xf9, 0x70, 0xb7, 0x95,
0x42, 0x77, 0x18, 0x84, 0x01, 0x9b, 0xd6, 0xb5, 0x56, 0x61, 0xaf, 0x7c, 0xb8, 0xdb, 0x4e, 0x07, 0x6a, 0xdf, 0x12, 0xa9, 0x6a, 0x88, 0xb3, 0x24, 0xcd, 0xfe, 0x55, 0x36, 0xaf, 0x82, 0x4b, 0x34,
0xdb, 0x16, 0xa9, 0x6a, 0x88, 0xb3, 0x22, 0xcd, 0xfe, 0x5e, 0x2a, 0xa3, 0x82, 0x2b, 0x06, 0xf8, 0xfe, 0x1a, 0x8a, 0x94, 0xb9, 0x6c, 0x4c, 0x85, 0x42, 0xeb, 0x87, 0x8d, 0x8c, 0x47, 0xcd, 0xbc,
0x29, 0x14, 0x29, 0x73, 0xd9, 0x84, 0x0a, 0xf9, 0x37, 0x0e, 0x9b, 0x19, 0x8f, 0x9a, 0x79, 0x29, 0x14, 0x31, 0x8e, 0x8c, 0xb5, 0x7f, 0x96, 0xc5, 0x69, 0x3b, 0x88, 0xfc, 0x0f, 0x3f, 0x86, 0x54,
0x62, 0x1c, 0x19, 0x6b, 0x7f, 0x2b, 0x8b, 0xd3, 0x4e, 0x10, 0xf9, 0x6f, 0x9f, 0x71, 0xaa, 0x4d, 0x9b, 0x82, 0xa2, 0xcd, 0x56, 0xaa, 0x6f, 0x52, 0x5a, 0xaa, 0x7e, 0x06, 0xa8, 0xc7, 0xfb, 0x3a,
0x41, 0xd1, 0x66, 0x3b, 0xd5, 0x37, 0x29, 0x2d, 0x55, 0x3f, 0x03, 0xd4, 0xe7, 0x7d, 0xbd, 0x76, 0xc1, 0x21, 0x66, 0xf8, 0x65, 0xc6, 0x1a, 0xac, 0x26, 0x1c, 0x89, 0xf0, 0x86, 0x93, 0x4e, 0xed,
0xa2, 0x75, 0x58, 0x4b, 0x38, 0x12, 0xe1, 0x0d, 0x27, 0x7d, 0xb5, 0x77, 0x60, 0x6b, 0xae, 0x92, 0x6d, 0xd8, 0x9c, 0xa9, 0x24, 0x09, 0x7a, 0x60, 0x0a, 0xb8, 0x1f, 0x0d, 0xc9, 0xc7, 0x94, 0xef,
0x24, 0xe8, 0x83, 0x29, 0xe0, 0x41, 0x34, 0x22, 0xff, 0xa7, 0x7c, 0x0f, 0xaa, 0x4a, 0x1d, 0x39, 0x42, 0x55, 0xa9, 0x23, 0x0f, 0xf6, 0x4b, 0x30, 0x86, 0x29, 0x28, 0xcf, 0x13, 0x65, 0x3a, 0xf3,
0xd8, 0x8f, 0xc1, 0x18, 0xa5, 0xa0, 0x9c, 0x27, 0xca, 0x74, 0xe6, 0xf1, 0x22, 0x3c, 0x0b, 0xb2, 0x78, 0x11, 0x9e, 0x05, 0xd9, 0xbf, 0x41, 0x29, 0x85, 0x15, 0xf5, 0xb4, 0x19, 0xf5, 0x2c, 0x80,
0x7f, 0x80, 0x52, 0x0a, 0x2b, 0xea, 0x69, 0x73, 0xea, 0x59, 0x00, 0x13, 0xea, 0x5e, 0xe3, 0xce, 0x31, 0x75, 0xaf, 0x71, 0x7b, 0xc2, 0x70, 0x72, 0x7c, 0xba, 0xa3, 0x20, 0xa8, 0x01, 0x06, 0x57,
0x94, 0xe1, 0x64, 0x7c, 0xba, 0xa3, 0x20, 0xa8, 0x09, 0x06, 0x57, 0xb4, 0x4b, 0x26, 0x11, 0x13, 0xb4, 0x43, 0xc6, 0x11, 0x13, 0x57, 0xbd, 0xe2, 0x64, 0x80, 0xbd, 0x0e, 0x6b, 0xea, 0x0d, 0xb6,
0xf7, 0xa8, 0xe2, 0x64, 0x80, 0xbd, 0x01, 0xeb, 0xea, 0x17, 0x6c, 0x9f, 0x43, 0x65, 0xfe, 0x6b, 0xcf, 0xa1, 0x32, 0x7b, 0x1b, 0xeb, 0x50, 0x92, 0xdb, 0xa5, 0xa2, 0x67, 0xc3, 0x99, 0xce, 0x39,
0x6c, 0x40, 0x49, 0x1e, 0x97, 0x8a, 0x9e, 0x0d, 0x67, 0xf6, 0xce, 0xa9, 0xdd, 0x30, 0x24, 0xbf, 0xb5, 0x1b, 0x86, 0xe4, 0xaf, 0xab, 0x38, 0x60, 0x58, 0x50, 0x97, 0x1c, 0x05, 0xb1, 0xbf, 0x00,
0x5c, 0xc5, 0x01, 0xc3, 0x82, 0xba, 0xe4, 0x28, 0x88, 0xfd, 0x11, 0x98, 0x97, 0x22, 0xf6, 0x35, 0xf3, 0x52, 0xc4, 0xbe, 0x8b, 0x9a, 0xf6, 0x7f, 0x1a, 0x54, 0x95, 0x70, 0xc9, 0x6f, 0x01, 0x84,
0x6a, 0xda, 0x7f, 0x68, 0x50, 0x55, 0xc2, 0x25, 0xbf, 0x05, 0x10, 0x06, 0x77, 0x01, 0x4b, 0x8e, 0xc1, 0x5d, 0xc0, 0x92, 0xed, 0x69, 0xc9, 0xf6, 0x32, 0xe4, 0xfd, 0xb7, 0xaf, 0x2b, 0xdb, 0xe7,
0xa7, 0x25, 0xc7, 0xcb, 0x90, 0xff, 0x7e, 0x7c, 0x5d, 0x39, 0x3e, 0xcf, 0x16, 0x6a, 0x27, 0xdb, 0xd9, 0x42, 0xed, 0x64, 0x59, 0x4f, 0xb2, 0x33, 0x64, 0xff, 0x1f, 0x0d, 0x4a, 0xdd, 0x38, 0xee,
0x7a, 0x92, 0x9d, 0x21, 0xfb, 0xbf, 0x69, 0x50, 0xea, 0xc5, 0x71, 0x97, 0xf8, 0x98, 0xa2, 0x0d, 0x10, 0x1f, 0x53, 0xb4, 0x0e, 0xf0, 0x53, 0x84, 0xef, 0x47, 0xd8, 0x63, 0xd8, 0x37, 0x73, 0x68,
0x80, 0x6f, 0x22, 0x7c, 0x3f, 0xc6, 0x1e, 0xc3, 0xbe, 0x99, 0x43, 0x9b, 0x50, 0xee, 0x0e, 0x4e, 0x03, 0xca, 0x9d, 0xfe, 0xc9, 0x05, 0x61, 0x3d, 0x32, 0x8e, 0x7c, 0x53, 0x43, 0x15, 0x30, 0x7a,
0x2e, 0x08, 0xeb, 0x93, 0x49, 0xe4, 0x9b, 0x1a, 0xaa, 0x80, 0xd1, 0x27, 0xf1, 0x30, 0xf0, 0x7d, 0x24, 0x1e, 0x04, 0xbe, 0x8f, 0x23, 0x33, 0x8f, 0x76, 0x00, 0x89, 0xfd, 0x7c, 0xc7, 0xbb, 0xed,
0x1c, 0x99, 0x79, 0x54, 0x03, 0x24, 0xce, 0xf3, 0x05, 0xef, 0xb6, 0x77, 0xef, 0x61, 0xec, 0x63, 0xde, 0x7b, 0x18, 0xfb, 0xd8, 0x37, 0x0b, 0x68, 0x1b, 0xaa, 0x3f, 0x8e, 0x71, 0x3c, 0xb9, 0x0c,
0xdf, 0x2c, 0xa0, 0x1d, 0xa8, 0x7e, 0x3d, 0xc1, 0xf1, 0xf4, 0x32, 0xf8, 0x15, 0xcf, 0x60, 0x9d, 0xfe, 0xc6, 0x53, 0x58, 0xe7, 0xd9, 0x57, 0x31, 0x89, 0xae, 0xcf, 0x5c, 0x7a, 0x63, 0xae, 0x20,
0x67, 0x5f, 0xc5, 0x24, 0xba, 0x3e, 0x73, 0xe9, 0x8d, 0xf9, 0x0e, 0x99, 0x50, 0xee, 0xc5, 0x31, 0x13, 0xca, 0xdd, 0x38, 0x26, 0xf1, 0xf7, 0xc3, 0x21, 0xc5, 0xcc, 0x7c, 0xd0, 0xf6, 0xdb, 0x80,
0x89, 0xbf, 0x1c, 0x8d, 0x28, 0x66, 0xe6, 0x83, 0xb6, 0xdf, 0x01, 0xb4, 0x7c, 0x19, 0x79, 0xda, 0x16, 0x1f, 0x23, 0x4f, 0xbb, 0x20, 0xac, 0x7b, 0x1f, 0x50, 0x46, 0xcd, 0x1c, 0x02, 0x28, 0xca,
0x05, 0x61, 0xbd, 0xfb, 0x80, 0x32, 0x6a, 0xe6, 0x10, 0x40, 0x51, 0xae, 0x35, 0x54, 0x85, 0x4a, 0xb1, 0x86, 0xaa, 0x50, 0x49, 0xc6, 0xfd, 0x48, 0x34, 0x62, 0xe6, 0x0f, 0xff, 0xd7, 0x41, 0xe7,
0xb2, 0x1e, 0x44, 0xa2, 0x11, 0x33, 0x7f, 0xf8, 0xa7, 0x0e, 0x3a, 0xff, 0xa4, 0xd0, 0x31, 0x94, 0x57, 0x0a, 0x1d, 0x43, 0x29, 0xf5, 0x5e, 0xf4, 0xe9, 0x9c, 0xab, 0x64, 0x76, 0x5e, 0xaf, 0x2f,
0x52, 0x63, 0x47, 0xef, 0x2f, 0xb8, 0x4a, 0xf6, 0xbf, 0xa2, 0xd1, 0x58, 0xb5, 0x25, 0x47, 0x73, 0x5b, 0x92, 0x47, 0x73, 0x02, 0xc6, 0xd4, 0x18, 0xd1, 0x7c, 0xa0, 0xe2, 0xcc, 0xf5, 0xdd, 0xa5,
0x02, 0xc6, 0xcc, 0x75, 0xd1, 0x62, 0xa0, 0x62, 0xfb, 0x8d, 0xdd, 0x95, 0x7b, 0xb2, 0xca, 0xe7, 0x6b, 0xb2, 0xca, 0xb7, 0x50, 0x56, 0x5c, 0x10, 0x35, 0xe6, 0x62, 0x67, 0x0c, 0xb6, 0xfe, 0xd9,
0x50, 0x56, 0x5c, 0x10, 0x35, 0x17, 0x62, 0xe7, 0x0c, 0xb6, 0xf1, 0xc1, 0xbf, 0xec, 0xca, 0x5a, 0x5b, 0x56, 0x65, 0xad, 0x53, 0x80, 0xcc, 0x35, 0xd0, 0x3c, 0xad, 0x6a, 0x53, 0xf5, 0xc6, 0xf2,
0xa7, 0x00, 0x99, 0x6b, 0xa0, 0x45, 0x5a, 0xd5, 0xa6, 0x1a, 0xcd, 0xd5, 0x9b, 0x59, 0x53, 0x8a, 0xc5, 0xac, 0x29, 0xc5, 0x1e, 0xd4, 0xa6, 0x16, 0xfd, 0x47, 0x6d, 0x6a, 0x89, 0xa7, 0x70, 0x99,
0x3d, 0xa8, 0x4d, 0x2d, 0xfb, 0x8f, 0xda, 0xd4, 0x0a, 0x4f, 0xe1, 0x32, 0xcd, 0xbc, 0x40, 0x95, 0xa6, 0x5e, 0xa0, 0xca, 0x34, 0x6f, 0x34, 0xaa, 0x4c, 0x8b, 0xe6, 0x71, 0x04, 0x2b, 0x89, 0x40,
0x69, 0xd1, 0x68, 0x54, 0x99, 0x96, 0xcd, 0xe3, 0x08, 0xde, 0x25, 0x02, 0xd5, 0xb2, 0xa8, 0x39, 0x3b, 0x59, 0xd4, 0x8c, 0x34, 0x9f, 0x2c, 0xe0, 0x19, 0xff, 0xf4, 0x59, 0xa9, 0xfc, 0xf3, 0x4f,
0x69, 0xde, 0x5b, 0xc2, 0x33, 0xfe, 0xd9, 0xb5, 0x52, 0xf9, 0x17, 0xaf, 0xa6, 0xca, 0xbf, 0x74, 0x53, 0xe5, 0x5f, 0x78, 0x87, 0xed, 0xd6, 0xc3, 0x93, 0xa5, 0x3d, 0x3e, 0x59, 0xda, 0xeb, 0x27,
0x0f, 0x3b, 0xed, 0x87, 0x27, 0x4b, 0x7b, 0x7c, 0xb2, 0xb4, 0xbf, 0x9f, 0x2c, 0xed, 0xf7, 0x67, 0x4b, 0xfb, 0xf7, 0xd9, 0xca, 0x3d, 0x3e, 0x5b, 0xb9, 0x57, 0xcf, 0x56, 0xee, 0x97, 0xad, 0x65,
0x2b, 0xf7, 0xf8, 0x6c, 0xe5, 0xfe, 0x7a, 0xb6, 0x72, 0xdf, 0x6d, 0xaf, 0xfa, 0x4d, 0x32, 0x2c, 0x7f, 0x1b, 0x06, 0x45, 0xf1, 0xf3, 0xd5, 0x9b, 0x00, 0x00, 0x00, 0xff, 0xff, 0x45, 0x87, 0x27,
0x8a, 0x3f, 0x9f, 0xfc, 0x13, 0x00, 0x00, 0xff, 0xff, 0x26, 0x23, 0x7f, 0x83, 0xb2, 0x08, 0x00, 0x98, 0x55, 0x08, 0x00, 0x00,
0x00,
} }
func (m *BlockGetRequest) Marshal() (dAtA []byte, err error) { func (m *BlockGetRequest) Marshal() (dAtA []byte, err error) {
@ -1307,68 +1216,6 @@ func (m *BlockPushResponse) MarshalToSizedBuffer(dAtA []byte) (int, error) {
return len(dAtA) - i, nil return len(dAtA) - i, nil
} }
func (m *BlocksDeleteRequest) Marshal() (dAtA []byte, err error) {
size := m.Size()
dAtA = make([]byte, size)
n, err := m.MarshalToSizedBuffer(dAtA[:size])
if err != nil {
return nil, err
}
return dAtA[:n], nil
}
func (m *BlocksDeleteRequest) MarshalTo(dAtA []byte) (int, error) {
size := m.Size()
return m.MarshalToSizedBuffer(dAtA[:size])
}
func (m *BlocksDeleteRequest) MarshalToSizedBuffer(dAtA []byte) (int, error) {
i := len(dAtA)
_ = i
var l int
_ = l
if len(m.Cids) > 0 {
for iNdEx := len(m.Cids) - 1; iNdEx >= 0; iNdEx-- {
i -= len(m.Cids[iNdEx])
copy(dAtA[i:], m.Cids[iNdEx])
i = encodeVarintFile(dAtA, i, uint64(len(m.Cids[iNdEx])))
i--
dAtA[i] = 0x12
}
}
if len(m.SpaceId) > 0 {
i -= len(m.SpaceId)
copy(dAtA[i:], m.SpaceId)
i = encodeVarintFile(dAtA, i, uint64(len(m.SpaceId)))
i--
dAtA[i] = 0xa
}
return len(dAtA) - i, nil
}
func (m *BlocksDeleteResponse) Marshal() (dAtA []byte, err error) {
size := m.Size()
dAtA = make([]byte, size)
n, err := m.MarshalToSizedBuffer(dAtA[:size])
if err != nil {
return nil, err
}
return dAtA[:n], nil
}
func (m *BlocksDeleteResponse) MarshalTo(dAtA []byte) (int, error) {
size := m.Size()
return m.MarshalToSizedBuffer(dAtA[:size])
}
func (m *BlocksDeleteResponse) MarshalToSizedBuffer(dAtA []byte) (int, error) {
i := len(dAtA)
_ = i
var l int
_ = l
return len(dAtA) - i, nil
}
func (m *BlocksCheckRequest) Marshal() (dAtA []byte, err error) { func (m *BlocksCheckRequest) Marshal() (dAtA []byte, err error) {
size := m.Size() size := m.Size()
dAtA = make([]byte, size) dAtA = make([]byte, size)
@ -1944,34 +1791,6 @@ func (m *BlockPushResponse) Size() (n int) {
return n return n
} }
func (m *BlocksDeleteRequest) Size() (n int) {
if m == nil {
return 0
}
var l int
_ = l
l = len(m.SpaceId)
if l > 0 {
n += 1 + l + sovFile(uint64(l))
}
if len(m.Cids) > 0 {
for _, b := range m.Cids {
l = len(b)
n += 1 + l + sovFile(uint64(l))
}
}
return n
}
func (m *BlocksDeleteResponse) Size() (n int) {
if m == nil {
return 0
}
var l int
_ = l
return n
}
func (m *BlocksCheckRequest) Size() (n int) { func (m *BlocksCheckRequest) Size() (n int) {
if m == nil { if m == nil {
return 0 return 0
@ -2668,170 +2487,6 @@ func (m *BlockPushResponse) Unmarshal(dAtA []byte) error {
} }
return nil return nil
} }
func (m *BlocksDeleteRequest) Unmarshal(dAtA []byte) error {
l := len(dAtA)
iNdEx := 0
for iNdEx < l {
preIndex := iNdEx
var wire uint64
for shift := uint(0); ; shift += 7 {
if shift >= 64 {
return ErrIntOverflowFile
}
if iNdEx >= l {
return io.ErrUnexpectedEOF
}
b := dAtA[iNdEx]
iNdEx++
wire |= uint64(b&0x7F) << shift
if b < 0x80 {
break
}
}
fieldNum := int32(wire >> 3)
wireType := int(wire & 0x7)
if wireType == 4 {
return fmt.Errorf("proto: BlocksDeleteRequest: wiretype end group for non-group")
}
if fieldNum <= 0 {
return fmt.Errorf("proto: BlocksDeleteRequest: illegal tag %d (wire type %d)", fieldNum, wire)
}
switch fieldNum {
case 1:
if wireType != 2 {
return fmt.Errorf("proto: wrong wireType = %d for field SpaceId", wireType)
}
var stringLen uint64
for shift := uint(0); ; shift += 7 {
if shift >= 64 {
return ErrIntOverflowFile
}
if iNdEx >= l {
return io.ErrUnexpectedEOF
}
b := dAtA[iNdEx]
iNdEx++
stringLen |= uint64(b&0x7F) << shift
if b < 0x80 {
break
}
}
intStringLen := int(stringLen)
if intStringLen < 0 {
return ErrInvalidLengthFile
}
postIndex := iNdEx + intStringLen
if postIndex < 0 {
return ErrInvalidLengthFile
}
if postIndex > l {
return io.ErrUnexpectedEOF
}
m.SpaceId = string(dAtA[iNdEx:postIndex])
iNdEx = postIndex
case 2:
if wireType != 2 {
return fmt.Errorf("proto: wrong wireType = %d for field Cids", wireType)
}
var byteLen int
for shift := uint(0); ; shift += 7 {
if shift >= 64 {
return ErrIntOverflowFile
}
if iNdEx >= l {
return io.ErrUnexpectedEOF
}
b := dAtA[iNdEx]
iNdEx++
byteLen |= int(b&0x7F) << shift
if b < 0x80 {
break
}
}
if byteLen < 0 {
return ErrInvalidLengthFile
}
postIndex := iNdEx + byteLen
if postIndex < 0 {
return ErrInvalidLengthFile
}
if postIndex > l {
return io.ErrUnexpectedEOF
}
m.Cids = append(m.Cids, make([]byte, postIndex-iNdEx))
copy(m.Cids[len(m.Cids)-1], dAtA[iNdEx:postIndex])
iNdEx = postIndex
default:
iNdEx = preIndex
skippy, err := skipFile(dAtA[iNdEx:])
if err != nil {
return err
}
if (skippy < 0) || (iNdEx+skippy) < 0 {
return ErrInvalidLengthFile
}
if (iNdEx + skippy) > l {
return io.ErrUnexpectedEOF
}
iNdEx += skippy
}
}
if iNdEx > l {
return io.ErrUnexpectedEOF
}
return nil
}
func (m *BlocksDeleteResponse) Unmarshal(dAtA []byte) error {
l := len(dAtA)
iNdEx := 0
for iNdEx < l {
preIndex := iNdEx
var wire uint64
for shift := uint(0); ; shift += 7 {
if shift >= 64 {
return ErrIntOverflowFile
}
if iNdEx >= l {
return io.ErrUnexpectedEOF
}
b := dAtA[iNdEx]
iNdEx++
wire |= uint64(b&0x7F) << shift
if b < 0x80 {
break
}
}
fieldNum := int32(wire >> 3)
wireType := int(wire & 0x7)
if wireType == 4 {
return fmt.Errorf("proto: BlocksDeleteResponse: wiretype end group for non-group")
}
if fieldNum <= 0 {
return fmt.Errorf("proto: BlocksDeleteResponse: illegal tag %d (wire type %d)", fieldNum, wire)
}
switch fieldNum {
default:
iNdEx = preIndex
skippy, err := skipFile(dAtA[iNdEx:])
if err != nil {
return err
}
if (skippy < 0) || (iNdEx+skippy) < 0 {
return ErrInvalidLengthFile
}
if (iNdEx + skippy) > l {
return io.ErrUnexpectedEOF
}
iNdEx += skippy
}
}
if iNdEx > l {
return io.ErrUnexpectedEOF
}
return nil
}
func (m *BlocksCheckRequest) Unmarshal(dAtA []byte) error { func (m *BlocksCheckRequest) Unmarshal(dAtA []byte) error {
l := len(dAtA) l := len(dAtA)
iNdEx := 0 iNdEx := 0

View File

@ -51,13 +51,6 @@ message BlockPushRequest {
message BlockPushResponse {} message BlockPushResponse {}
message BlocksDeleteRequest {
string spaceId = 1;
repeated bytes cids = 2;
}
message BlocksDeleteResponse {}
message BlocksCheckRequest { message BlocksCheckRequest {
string spaceId = 1; string spaceId = 1;

View File

@ -46,7 +46,7 @@ type headSync struct {
diff ldiff.Diff diff ldiff.Diff
log logger.CtxLogger log logger.CtxLogger
syncer DiffSyncer syncer DiffSyncer
configuration nodeconf.Configuration configuration nodeconf.NodeConf
spaceIsDeleted *atomic.Bool spaceIsDeleted *atomic.Bool
syncPeriod int syncPeriod int
@ -56,7 +56,7 @@ func NewHeadSync(
spaceId string, spaceId string,
spaceIsDeleted *atomic.Bool, spaceIsDeleted *atomic.Bool,
syncPeriod int, syncPeriod int,
configuration nodeconf.Configuration, configuration nodeconf.NodeConf,
storage spacestorage.SpaceStorage, storage spacestorage.SpaceStorage,
peerManager peermanager.PeerManager, peerManager peermanager.PeerManager,
cache treemanager.TreeManager, cache treemanager.TreeManager,

View File

@ -41,6 +41,10 @@ func (m mockPubKey) Account() string {
return mockKeyValue return mockKeyValue
} }
func (m mockPubKey) Network() string {
return mockKeyValue
}
func (m mockPubKey) PeerId() string { func (m mockPubKey) PeerId() string {
return mockKeyValue return mockKeyValue
} }

View File

@ -64,16 +64,20 @@ func TestRandomMerge(t *testing.T) {
rnd = rand.New(rand.NewSource(time.Now().Unix())) rnd = rand.New(rand.NewSource(time.Now().Unix()))
levels = 20 levels = 20
perLevel = 20 perLevel = 20
rounds = 10
) )
testTreeMerge(t, levels, perLevel, func() bool { for i := 0; i < rounds; i++ {
return true testTreeMerge(t, levels, perLevel, func() bool {
}) return true
testTreeMerge(t, levels, perLevel, func() bool { })
return false testTreeMerge(t, levels, perLevel, func() bool {
}) return false
testTreeMerge(t, levels, perLevel, func() bool { })
return rnd.Intn(10) > 8 testTreeMerge(t, levels, perLevel, func() bool {
}) return rnd.Intn(10) > 8
})
levels += 2
}
} }
func testTreeMerge(t *testing.T, levels, perlevel int, isSnapshot func() bool) { func testTreeMerge(t *testing.T, levels, perlevel int, isSnapshot func() bool) {
@ -113,7 +117,7 @@ func testTreeMerge(t *testing.T, levels, perlevel int, isSnapshot func() bool) {
NewHeads: initialRes.heads, NewHeads: initialRes.heads,
RawChanges: initialRes.changes, RawChanges: initialRes.changes,
}) })
time.Sleep(100 * time.Millisecond) time.Sleep(50 * time.Millisecond)
firstHeads := fx.handlers["peer1"].tree().Heads() firstHeads := fx.handlers["peer1"].tree().Heads()
secondHeads := fx.handlers["peer2"].tree().Heads() secondHeads := fx.handlers["peer2"].tree().Heads()
require.True(t, slice.UnsortedEquals(firstHeads, secondHeads)) require.True(t, slice.UnsortedEquals(firstHeads, secondHeads))
@ -139,7 +143,7 @@ func testTreeMerge(t *testing.T, levels, perlevel int, isSnapshot func() bool) {
NewHeads: peer2Res.heads, NewHeads: peer2Res.heads,
RawChanges: peer2Res.changes, RawChanges: peer2Res.changes,
}) })
time.Sleep(100 * time.Millisecond) time.Sleep(50 * time.Millisecond)
fx.stop() fx.stop()
firstTree := fx.handlers["peer1"].tree() firstTree := fx.handlers["peer1"].tree()
secondTree := fx.handlers["peer2"].tree() secondTree := fx.handlers["peer2"].tree()

View File

@ -64,7 +64,7 @@ type ResponsiblePeersGetter interface {
type BuildDeps struct { type BuildDeps struct {
SpaceId string SpaceId string
ObjectSync objectsync.ObjectSync ObjectSync objectsync.ObjectSync
Configuration nodeconf.Configuration Configuration nodeconf.NodeConf
HeadNotifiable HeadNotifiable HeadNotifiable HeadNotifiable
Listener updatelistener.UpdateListener Listener updatelistener.UpdateListener
AclList list.AclList AclList list.AclList

View File

@ -34,8 +34,8 @@ func (s syncTreeMatcher) String() string {
return "" return ""
} }
func syncClientFuncCreator(client objectsync.SyncClient) func(spaceId string, factory objectsync.RequestFactory, objectSync objectsync.ObjectSync, configuration nodeconf.Configuration) objectsync.SyncClient { func syncClientFuncCreator(client objectsync.SyncClient) func(spaceId string, factory objectsync.RequestFactory, objectSync objectsync.ObjectSync, configuration nodeconf.NodeConf) objectsync.SyncClient {
return func(spaceId string, factory objectsync.RequestFactory, objectSync objectsync.ObjectSync, configuration nodeconf.Configuration) objectsync.SyncClient { return func(spaceId string, factory objectsync.RequestFactory, objectSync objectsync.ObjectSync, configuration nodeconf.NodeConf) objectsync.SyncClient {
return client return client
} }
} }

View File

@ -35,7 +35,7 @@ type objectSync struct {
messagePool MessagePool messagePool MessagePool
syncClient SyncClient syncClient SyncClient
objectGetter syncobjectgetter.SyncObjectGetter objectGetter syncobjectgetter.SyncObjectGetter
configuration nodeconf.Configuration configuration nodeconf.NodeConf
spaceStorage spacestorage.SpaceStorage spaceStorage spacestorage.SpaceStorage
syncCtx context.Context syncCtx context.Context
@ -46,7 +46,7 @@ type objectSync struct {
func NewObjectSync( func NewObjectSync(
spaceId string, spaceId string,
spaceIsDeleted *atomic.Bool, spaceIsDeleted *atomic.Bool,
configuration nodeconf.Configuration, configuration nodeconf.NodeConf,
peerManager peermanager.PeerManager, peerManager peermanager.PeerManager,
objectGetter syncobjectgetter.SyncObjectGetter, objectGetter syncobjectgetter.SyncObjectGetter,
storage spacestorage.SpaceStorage) ObjectSync { storage spacestorage.SpaceStorage) ObjectSync {

View File

@ -49,7 +49,7 @@ type Deps struct {
Account accountservice.Service Account accountservice.Service
TreeManager treemanager.TreeManager TreeManager treemanager.TreeManager
Store spacestorage.SpaceStorage Store spacestorage.SpaceStorage
Configuration nodeconf.Configuration Configuration nodeconf.NodeConf
DeletionState settingsstate.ObjectDeletionState DeletionState settingsstate.ObjectDeletionState
Provider SpaceIdsProvider Provider SpaceIdsProvider
OnSpaceDelete func() OnSpaceDelete func()

View File

@ -121,7 +121,7 @@ type space struct {
treeManager *commonGetter treeManager *commonGetter
account accountservice.Service account accountservice.Service
aclList *syncacl.SyncAcl aclList *syncacl.SyncAcl
configuration nodeconf.Configuration configuration nodeconf.NodeConf
settingsObject settings.SettingsObject settingsObject settings.SettingsObject
peerManager peermanager.PeerManager peerManager peermanager.PeerManager
treeBuilder objecttree.BuildObjectTreeFunc treeBuilder objecttree.BuildObjectTreeFunc

View File

@ -136,7 +136,7 @@ func (s *spaceService) NewSpace(ctx context.Context, id string) (Space, error) {
} }
} }
lastConfiguration := s.configurationService.GetLast() lastConfiguration := s.configurationService
var ( var (
spaceIsClosed = &atomic.Bool{} spaceIsClosed = &atomic.Bool{}
spaceIsDeleted = &atomic.Bool{} spaceIsDeleted = &atomic.Bool{}
@ -210,7 +210,7 @@ func (s *spaceService) addSpaceStorage(ctx context.Context, spaceDescription Spa
func (s *spaceService) getSpaceStorageFromRemote(ctx context.Context, id string) (st spacestorage.SpaceStorage, err error) { func (s *spaceService) getSpaceStorageFromRemote(ctx context.Context, id string) (st spacestorage.SpaceStorage, err error) {
var p peer.Peer var p peer.Peer
lastConfiguration := s.configurationService.GetLast() lastConfiguration := s.configurationService
// we can't connect to client if it is a node // we can't connect to client if it is a node
if lastConfiguration.IsResponsible(id) { if lastConfiguration.IsResponsible(id) {
err = spacesyncproto.ErrSpaceMissing err = spacesyncproto.ErrSpaceMissing

View File

@ -4,6 +4,7 @@ package spacestorage
import ( import (
"context" "context"
"errors" "errors"
"fmt"
"github.com/anytypeio/any-sync/app" "github.com/anytypeio/any-sync/app"
"github.com/anytypeio/any-sync/commonspace/object/acl/aclrecordproto" "github.com/anytypeio/any-sync/commonspace/object/acl/aclrecordproto"
"github.com/anytypeio/any-sync/commonspace/object/acl/liststorage" "github.com/anytypeio/any-sync/commonspace/object/acl/liststorage"
@ -14,6 +15,7 @@ import (
"github.com/anytypeio/any-sync/util/cidutil" "github.com/anytypeio/any-sync/util/cidutil"
"github.com/anytypeio/any-sync/util/crypto" "github.com/anytypeio/any-sync/util/crypto"
"github.com/gogo/protobuf/proto" "github.com/gogo/protobuf/proto"
"strconv"
"strings" "strings"
) )
@ -66,10 +68,144 @@ type SpaceStorageProvider interface {
} }
func ValidateSpaceStorageCreatePayload(payload SpaceStorageCreatePayload) (err error) { func ValidateSpaceStorageCreatePayload(payload SpaceStorageCreatePayload) (err error) {
// TODO: add proper validation err = validateCreateSpaceHeaderPayload(payload.SpaceHeaderWithId)
return nil if err != nil {
return
}
aclSpaceId, err := validateCreateSpaceAclPayload(payload.AclWithId)
if err != nil {
return
}
aclHeadId, settingsSpaceId, err := validateCreateSpaceSettingsPayload(payload.SpaceSettingsWithId)
if err != nil {
return
}
if aclSpaceId != payload.SpaceHeaderWithId.Id || aclSpaceId != settingsSpaceId {
err = ErrIncorrectSpaceHeader
return
}
if aclHeadId != payload.AclWithId.Id {
err = ErrIncorrectSpaceHeader
return
}
return
} }
func validateCreateSpaceHeaderPayload(rawHeaderWithId *spacesyncproto.RawSpaceHeaderWithId) (err error) {
var rawSpaceHeader spacesyncproto.RawSpaceHeader
err = proto.Unmarshal(rawHeaderWithId.RawHeader, &rawSpaceHeader)
if err != nil {
return
}
var header spacesyncproto.SpaceHeader
err = proto.Unmarshal(rawSpaceHeader.SpaceHeader, &header)
if err != nil {
return
}
split := strings.Split(rawHeaderWithId.Id, ".")
if len(split) != 2 {
return ErrIncorrectSpaceHeader
}
if !cidutil.VerifyCid(rawHeaderWithId.RawHeader, split[0]) {
err = objecttree.ErrIncorrectCid
return
}
payloadIdentity, err := crypto.UnmarshalEd25519PublicKeyProto(header.Identity)
if err != nil {
return
}
res, err := payloadIdentity.Verify(rawSpaceHeader.SpaceHeader, rawSpaceHeader.Signature)
if err != nil || !res {
err = ErrIncorrectSpaceHeader
return
}
id, err := cidutil.NewCidFromBytes(rawHeaderWithId.RawHeader)
if err != nil {
return
}
requiredSpaceId := fmt.Sprintf("%s.%s", id, strconv.FormatUint(header.ReplicationKey, 36))
if requiredSpaceId != rawHeaderWithId.Id {
err = ErrIncorrectSpaceHeader
return
}
return
}
func validateCreateSpaceAclPayload(rawWithId *aclrecordproto.RawAclRecordWithId) (spaceId string, err error) {
if !cidutil.VerifyCid(rawWithId.Payload, rawWithId.Id) {
err = objecttree.ErrIncorrectCid
return
}
var rawAcl aclrecordproto.RawAclRecord
err = proto.Unmarshal(rawWithId.Payload, &rawAcl)
if err != nil {
return
}
var aclRoot aclrecordproto.AclRoot
err = proto.Unmarshal(rawAcl.Payload, &aclRoot)
if err != nil {
return
}
payloadIdentity, err := crypto.UnmarshalEd25519PublicKeyProto(aclRoot.Identity)
if err != nil {
return
}
res, err := payloadIdentity.Verify(rawAcl.Payload, rawAcl.Signature)
if err != nil || !res {
err = ErrIncorrectSpaceHeader
return
}
masterKey, err := crypto.UnmarshalEd25519PublicKeyProto(aclRoot.MasterKey)
if err != nil {
return
}
rawIdentity, err := payloadIdentity.Raw()
if err != nil {
return
}
res, err = masterKey.Verify(rawIdentity, aclRoot.IdentitySignature)
if err != nil || !res {
err = ErrIncorrectSpaceHeader
return
}
spaceId = aclRoot.SpaceId
return
}
func validateCreateSpaceSettingsPayload(rawWithId *treechangeproto.RawTreeChangeWithId) (aclHeadId string, spaceId string, err error) {
var raw treechangeproto.RawTreeChange
err = proto.Unmarshal(rawWithId.RawChange, &raw)
if err != nil {
return
}
var rootChange treechangeproto.RootChange
err = proto.Unmarshal(raw.Payload, &rootChange)
if err != nil {
return
}
payloadIdentity, err := crypto.UnmarshalEd25519PublicKeyProto(rootChange.Identity)
if err != nil {
return
}
res, err := payloadIdentity.Verify(raw.Payload, raw.Signature)
if err != nil || !res {
err = ErrIncorrectSpaceHeader
return
}
id, err := cidutil.NewCidFromBytes(rawWithId.RawChange)
if id != rawWithId.Id {
err = ErrIncorrectSpaceHeader
return
}
spaceId = rootChange.SpaceId
aclHeadId = rootChange.AclHeadId
return
}
// ValidateSpaceHeader Used in coordinator
func ValidateSpaceHeader(spaceId string, header []byte, identity crypto.PubKey) (err error) { func ValidateSpaceHeader(spaceId string, header []byte, identity crypto.PubKey) (err error) {
split := strings.Split(spaceId, ".") split := strings.Split(spaceId, ".")
if len(split) != 2 { if len(split) != 2 {

View File

@ -0,0 +1,655 @@
package spacestorage
import (
"crypto/rand"
"fmt"
"github.com/anytypeio/any-sync/commonspace/object/accountdata"
"github.com/anytypeio/any-sync/commonspace/object/acl/aclrecordproto"
"github.com/anytypeio/any-sync/commonspace/object/tree/objecttree"
"github.com/anytypeio/any-sync/commonspace/object/tree/treechangeproto"
"github.com/anytypeio/any-sync/commonspace/spacesyncproto"
"github.com/anytypeio/any-sync/util/cidutil"
"github.com/anytypeio/any-sync/util/crypto"
"github.com/stretchr/testify/assert"
"github.com/stretchr/testify/require"
rand2 "golang.org/x/exp/rand"
"strconv"
"testing"
"time"
)
func TestSuccessHeaderPayloadForSpaceCreate(t *testing.T) {
accountKeys, err := accountdata.NewRandom()
require.NoError(t, err)
_, rawHeaderWithId, err := rawHeaderWithId(accountKeys)
require.NoError(t, err)
err = validateCreateSpaceHeaderPayload(rawHeaderWithId)
require.NoError(t, err)
}
func TestFailedHeaderPayloadForSpaceCreate_InvalidFormatSpaceId(t *testing.T) {
accountKeys, err := accountdata.NewRandom()
require.NoError(t, err)
identity, err := accountKeys.SignKey.GetPublic().Marshall()
require.NoError(t, err)
spaceHeaderSeed := make([]byte, 32)
_, err = rand.Read(spaceHeaderSeed)
require.NoError(t, err)
spaceHeaderPayload := make([]byte, 32)
_, err = rand.Read(spaceHeaderPayload)
require.NoError(t, err)
replicationKey := rand2.Uint64()
header := &spacesyncproto.SpaceHeader{
Identity: identity,
Timestamp: time.Now().Unix(),
SpaceType: "SpaceType",
ReplicationKey: replicationKey,
Seed: spaceHeaderSeed,
SpaceHeaderPayload: spaceHeaderPayload,
}
marhalled, err := header.Marshal()
require.NoError(t, err)
signature, err := accountKeys.SignKey.Sign(marhalled)
require.NoError(t, err)
rawHeader := &spacesyncproto.RawSpaceHeader{
SpaceHeader: marhalled,
Signature: signature,
}
marhalledRawHeader, err := rawHeader.Marshal()
require.NoError(t, err)
id, err := cidutil.NewCidFromBytes(marhalled)
require.NoError(t, err)
spaceId := fmt.Sprintf("%s%s", id, strconv.FormatUint(replicationKey, 36))
rawHeaderWithId := &spacesyncproto.RawSpaceHeaderWithId{
RawHeader: marhalledRawHeader,
Id: spaceId,
}
err = validateCreateSpaceHeaderPayload(rawHeaderWithId)
assert.EqualErrorf(t, err, ErrIncorrectSpaceHeader.Error(), "Error should be: %v, got: %v", ErrIncorrectSpaceHeader, err)
}
func TestFailedHeaderPayloadForSpaceCreate_CidIsWrong(t *testing.T) {
accountKeys, err := accountdata.NewRandom()
require.NoError(t, err)
identity, err := accountKeys.SignKey.GetPublic().Marshall()
require.NoError(t, err)
spaceHeaderSeed := make([]byte, 32)
_, err = rand.Read(spaceHeaderSeed)
require.NoError(t, err)
spaceHeaderPayload := make([]byte, 32)
_, err = rand.Read(spaceHeaderPayload)
require.NoError(t, err)
replicationKey := rand2.Uint64()
header := &spacesyncproto.SpaceHeader{
Identity: identity,
Timestamp: time.Now().Unix(),
SpaceType: "SpaceType",
ReplicationKey: replicationKey,
Seed: spaceHeaderSeed,
SpaceHeaderPayload: spaceHeaderPayload,
}
marhalled, err := header.Marshal()
require.NoError(t, err)
signature, err := accountKeys.SignKey.Sign(marhalled)
require.NoError(t, err)
rawHeader := &spacesyncproto.RawSpaceHeader{
SpaceHeader: marhalled,
Signature: signature,
}
marhalledRawHeader, err := rawHeader.Marshal()
require.NoError(t, err)
id := "faisdfjpiocpoakopkop34"
spaceId := fmt.Sprintf("%s.%s", id, strconv.FormatUint(replicationKey, 36))
rawHeaderWithId := &spacesyncproto.RawSpaceHeaderWithId{
RawHeader: marhalledRawHeader,
Id: spaceId,
}
err = validateCreateSpaceHeaderPayload(rawHeaderWithId)
assert.EqualErrorf(t, err, objecttree.ErrIncorrectCid.Error(), "Error should be: %v, got: %v", objecttree.ErrIncorrectCid, err)
}
func TestFailedHeaderPayloadForSpaceCreate_SignedWithAnotherIdentity(t *testing.T) {
accountKeys, err := accountdata.NewRandom()
require.NoError(t, err)
identity, err := accountKeys.SignKey.GetPublic().Marshall()
require.NoError(t, err)
spaceHeaderSeed := make([]byte, 32)
_, err = rand.Read(spaceHeaderSeed)
require.NoError(t, err)
spaceHeaderPayload := make([]byte, 32)
_, err = rand.Read(spaceHeaderPayload)
require.NoError(t, err)
replicationKey := rand2.Uint64()
header := &spacesyncproto.SpaceHeader{
Identity: identity,
Timestamp: time.Now().Unix(),
SpaceType: "SpaceType",
ReplicationKey: replicationKey,
Seed: spaceHeaderSeed,
SpaceHeaderPayload: spaceHeaderPayload,
}
marhalled, err := header.Marshal()
require.NoError(t, err)
anotherAccountKeys, err := accountdata.NewRandom()
signature, err := anotherAccountKeys.SignKey.Sign(marhalled)
require.NoError(t, err)
rawHeader := &spacesyncproto.RawSpaceHeader{
SpaceHeader: marhalled,
Signature: signature,
}
marhalledRawHeader, err := rawHeader.Marshal()
require.NoError(t, err)
id := "faisdfjpiocpoakopkop34"
spaceId := fmt.Sprintf("%s.%s", id, strconv.FormatUint(replicationKey, 36))
rawHeaderWithId := &spacesyncproto.RawSpaceHeaderWithId{
RawHeader: marhalledRawHeader,
Id: spaceId,
}
err = validateCreateSpaceHeaderPayload(rawHeaderWithId)
assert.EqualErrorf(t, err, objecttree.ErrIncorrectCid.Error(), "Error should be: %v, got: %v", objecttree.ErrIncorrectCid, err)
}
func TestSuccessAclPayloadSpace(t *testing.T) {
accountKeys, err := accountdata.NewRandom()
spaceId := "AnySpaceId"
_, rawWithId, err := rawAclWithId(accountKeys, spaceId)
require.NoError(t, err)
validationSpaceId, err := validateCreateSpaceAclPayload(rawWithId)
require.Equal(t, validationSpaceId, spaceId)
require.NoError(t, err)
}
func TestFailAclPayloadSpace_IncorrectCid(t *testing.T) {
accountKeys, err := accountdata.NewRandom()
require.NoError(t, err)
identity, err := accountKeys.SignKey.GetPublic().Marshall()
require.NoError(t, err)
readKeyBytes := make([]byte, 32)
_, err = rand.Read(readKeyBytes)
require.NoError(t, err)
readKey, err := accountKeys.SignKey.GetPublic().Encrypt(readKeyBytes)
require.NoError(t, err)
masterKey, _, err := crypto.GenerateRandomEd25519KeyPair()
require.NoError(t, err)
rawIdentity, err := accountKeys.SignKey.GetPublic().Raw()
require.NoError(t, err)
identitySignature, err := masterKey.Sign(rawIdentity)
require.NoError(t, err)
rawMasterKey, err := masterKey.GetPublic().Marshall()
require.NoError(t, err)
aclRoot := aclrecordproto.AclRoot{
Identity: identity,
MasterKey: rawMasterKey,
SpaceId: "SpaceId",
EncryptedReadKey: readKey,
Timestamp: time.Now().Unix(),
IdentitySignature: identitySignature,
}
marshalled, err := aclRoot.Marshal()
require.NoError(t, err)
signature, err := accountKeys.SignKey.Sign(marshalled)
rawAclRecord := &aclrecordproto.RawAclRecord{
Payload: marshalled,
Signature: signature,
}
marshalledRaw, err := rawAclRecord.Marshal()
require.NoError(t, err)
aclHeadId := "rand"
rawWithId := &aclrecordproto.RawAclRecordWithId{
Payload: marshalledRaw,
Id: aclHeadId,
}
_, err = validateCreateSpaceAclPayload(rawWithId)
assert.EqualErrorf(t, err, objecttree.ErrIncorrectCid.Error(), "Error should be: %v, got: %v", objecttree.ErrIncorrectCid, err)
}
func TestFailedAclPayloadSpace_IncorrectSignature(t *testing.T) {
accountKeys, err := accountdata.NewRandom()
require.NoError(t, err)
readKeyBytes := make([]byte, 32)
_, err = rand.Read(readKeyBytes)
require.NoError(t, err)
readKey, err := accountKeys.SignKey.GetPublic().Encrypt(readKeyBytes)
require.NoError(t, err)
masterKey, _, err := crypto.GenerateRandomEd25519KeyPair()
require.NoError(t, err)
rawIdentity, err := accountKeys.SignKey.GetPublic().Raw()
require.NoError(t, err)
identity, err := accountKeys.SignKey.GetPublic().Marshall()
identitySignature, err := masterKey.Sign(rawIdentity)
require.NoError(t, err)
rawMasterKey, err := masterKey.GetPublic().Raw()
require.NoError(t, err)
aclRoot := aclrecordproto.AclRoot{
Identity: identity,
MasterKey: rawMasterKey,
SpaceId: "SpaceId",
EncryptedReadKey: readKey,
Timestamp: time.Now().Unix(),
IdentitySignature: identitySignature,
}
marshalled, err := aclRoot.Marshal()
require.NoError(t, err)
rawAclRecord := &aclrecordproto.RawAclRecord{
Payload: marshalled,
Signature: marshalled,
}
marshalledRaw, err := rawAclRecord.Marshal()
require.NoError(t, err)
aclHeadId, err := cidutil.NewCidFromBytes(marshalledRaw)
require.NoError(t, err)
rawWithId := &aclrecordproto.RawAclRecordWithId{
Payload: marshalledRaw,
Id: aclHeadId,
}
_, err = validateCreateSpaceAclPayload(rawWithId)
assert.NotNil(t, err)
assert.EqualErrorf(t, err, ErrIncorrectSpaceHeader.Error(), "Error should be: %v, got: %v", ErrIncorrectSpaceHeader, err)
}
func TestFailedAclPayloadSpace_IncorrectIdentitySignature(t *testing.T) {
spaceId := "AnySpaceId"
accountKeys, err := accountdata.NewRandom()
require.NoError(t, err)
readKeyBytes := make([]byte, 32)
_, err = rand.Read(readKeyBytes)
if err != nil {
return
}
readKey, err := accountKeys.SignKey.GetPublic().Encrypt(readKeyBytes)
if err != nil {
return
}
masterKey, _, err := crypto.GenerateRandomEd25519KeyPair()
if err != nil {
return
}
masterPubKey := masterKey.GetPublic()
identity, err := accountKeys.SignKey.GetPublic().Marshall()
if err != nil {
return
}
rawMasterKey, err := masterPubKey.Marshall()
if err != nil {
return
}
aclRoot := aclrecordproto.AclRoot{
Identity: identity,
MasterKey: rawMasterKey,
SpaceId: spaceId,
EncryptedReadKey: readKey,
Timestamp: time.Now().Unix(),
IdentitySignature: identity,
}
marshalled, err := aclRoot.Marshal()
if err != nil {
return
}
signature, err := accountKeys.SignKey.Sign(marshalled)
rawAclRecord := &aclrecordproto.RawAclRecord{
Payload: marshalled,
Signature: signature,
}
marshalledRaw, err := rawAclRecord.Marshal()
if err != nil {
return
}
aclHeadId, err := cidutil.NewCidFromBytes(marshalledRaw)
if err != nil {
return
}
rawWithId := &aclrecordproto.RawAclRecordWithId{
Payload: marshalledRaw,
Id: aclHeadId,
}
_, err = validateCreateSpaceAclPayload(rawWithId)
assert.EqualErrorf(t, err, ErrIncorrectSpaceHeader.Error(), "Error should be: %v, got: %v", ErrIncorrectSpaceHeader, err)
}
func TestSuccessSettingsPayloadSpace(t *testing.T) {
accountKeys, err := accountdata.NewRandom()
require.NoError(t, err)
identity, err := accountKeys.SignKey.GetPublic().Marshall()
require.NoError(t, err)
spaceSettingsSeed := make([]byte, 32)
_, err = rand.Read(spaceSettingsSeed)
require.NoError(t, err)
changePayload := make([]byte, 32)
_, err = rand.Read(changePayload)
require.NoError(t, err)
spaceId := "SpaceId"
rootChange := &treechangeproto.RootChange{
AclHeadId: "AclHeadId",
SpaceId: spaceId,
ChangeType: "ChangeType",
Timestamp: time.Now().Unix(),
Seed: spaceSettingsSeed,
Identity: identity,
ChangePayload: changePayload,
}
marshalledChange, err := rootChange.Marshal()
require.NoError(t, err)
signature, err := accountKeys.SignKey.Sign(marshalledChange)
require.NoError(t, err)
raw := &treechangeproto.RawTreeChange{
Payload: marshalledChange,
Signature: signature,
}
marshalledRawChange, err := raw.Marshal()
id, err := cidutil.NewCidFromBytes(marshalledRawChange)
require.NoError(t, err)
rawIdChange := &treechangeproto.RawTreeChangeWithId{
RawChange: marshalledRawChange,
Id: id,
}
_, validationSpaceId, err := validateCreateSpaceSettingsPayload(rawIdChange)
require.Equal(t, validationSpaceId, spaceId)
require.NoError(t, err)
}
func TestFailSettingsPayloadSpace_InvalidSignature(t *testing.T) {
accountKeys, err := accountdata.NewRandom()
require.NoError(t, err)
identity, err := accountKeys.SignKey.GetPublic().Marshall()
require.NoError(t, err)
spaceSettingsSeed := make([]byte, 32)
_, err = rand.Read(spaceSettingsSeed)
require.NoError(t, err)
changePayload := make([]byte, 32)
_, err = rand.Read(changePayload)
require.NoError(t, err)
rootChange := &treechangeproto.RootChange{
AclHeadId: "AclHeadId",
SpaceId: "SpaceId",
ChangeType: "ChangeType",
Timestamp: time.Now().Unix(),
Seed: spaceSettingsSeed,
Identity: identity,
ChangePayload: changePayload,
}
marshalledChange, err := rootChange.Marshal()
require.NoError(t, err)
raw := &treechangeproto.RawTreeChange{
Payload: marshalledChange,
Signature: marshalledChange,
}
marshalledRawChange, err := raw.Marshal()
id, err := cidutil.NewCidFromBytes(marshalledRawChange)
require.NoError(t, err)
rawIdChange := &treechangeproto.RawTreeChangeWithId{
RawChange: marshalledRawChange,
Id: id,
}
_, _, err = validateCreateSpaceSettingsPayload(rawIdChange)
assert.EqualErrorf(t, err, ErrIncorrectSpaceHeader.Error(), "Error should be: %v, got: %v", ErrIncorrectSpaceHeader, err)
}
func TestFailSettingsPayloadSpace_InvalidCid(t *testing.T) {
accountKeys, err := accountdata.NewRandom()
require.NoError(t, err)
identity, err := accountKeys.SignKey.GetPublic().Marshall()
require.NoError(t, err)
spaceSettingsSeed := make([]byte, 32)
_, err = rand.Read(spaceSettingsSeed)
require.NoError(t, err)
changePayload := make([]byte, 32)
_, err = rand.Read(changePayload)
require.NoError(t, err)
rootChange := &treechangeproto.RootChange{
AclHeadId: "AclHeadId",
SpaceId: "SpaceId",
ChangeType: "ChangeType",
Timestamp: time.Now().Unix(),
Seed: spaceSettingsSeed,
Identity: identity,
ChangePayload: changePayload,
}
marshalledChange, err := rootChange.Marshal()
require.NoError(t, err)
signature, err := accountKeys.SignKey.Sign(marshalledChange)
require.NoError(t, err)
raw := &treechangeproto.RawTreeChange{
Payload: marshalledChange,
Signature: signature,
}
marshalledRawChange, err := raw.Marshal()
id := "id"
require.NoError(t, err)
rawIdChange := &treechangeproto.RawTreeChangeWithId{
RawChange: marshalledRawChange,
Id: id,
}
_, _, err = validateCreateSpaceSettingsPayload(rawIdChange)
assert.EqualErrorf(t, err, ErrIncorrectSpaceHeader.Error(), "Error should be: %v, got: %v", ErrIncorrectSpaceHeader, err)
}
func TestSuccessSameIds(t *testing.T) {
accountKeys, err := accountdata.NewRandom()
require.NoError(t, err)
spaceId, rawHeaderWithId, err := rawHeaderWithId(accountKeys)
require.NoError(t, err)
aclHeadId, rawAclWithId, err := rawAclWithId(accountKeys, spaceId)
require.NoError(t, err)
rawSettingsPayload, err := rawSettingsPayload(accountKeys, spaceId, aclHeadId)
spacePayload := SpaceStorageCreatePayload{
AclWithId: rawAclWithId,
SpaceHeaderWithId: rawHeaderWithId,
SpaceSettingsWithId: rawSettingsPayload,
}
err = ValidateSpaceStorageCreatePayload(spacePayload)
require.NoError(t, err)
}
func TestFailWithAclWrongSpaceId(t *testing.T) {
accountKeys, err := accountdata.NewRandom()
require.NoError(t, err)
spaceId, rawHeaderWithId, err := rawHeaderWithId(accountKeys)
require.NoError(t, err)
aclHeadId, rawAclWithId, err := rawAclWithId(accountKeys, "spaceId")
require.NoError(t, err)
rawSettingsPayload, err := rawSettingsPayload(accountKeys, spaceId, aclHeadId)
spacePayload := SpaceStorageCreatePayload{
AclWithId: rawAclWithId,
SpaceHeaderWithId: rawHeaderWithId,
SpaceSettingsWithId: rawSettingsPayload,
}
err = ValidateSpaceStorageCreatePayload(spacePayload)
assert.EqualErrorf(t, err, ErrIncorrectSpaceHeader.Error(), "Error should be: %v, got: %v", ErrIncorrectSpaceHeader, err)
}
func TestFailWithSettingsWrongSpaceId(t *testing.T) {
accountKeys, err := accountdata.NewRandom()
require.NoError(t, err)
spaceId, rawHeaderWithId, err := rawHeaderWithId(accountKeys)
require.NoError(t, err)
aclHeadId, rawAclWithId, err := rawAclWithId(accountKeys, spaceId)
require.NoError(t, err)
rawSettingsPayload, err := rawSettingsPayload(accountKeys, "spaceId", aclHeadId)
spacePayload := SpaceStorageCreatePayload{
AclWithId: rawAclWithId,
SpaceHeaderWithId: rawHeaderWithId,
SpaceSettingsWithId: rawSettingsPayload,
}
err = ValidateSpaceStorageCreatePayload(spacePayload)
assert.EqualErrorf(t, err, ErrIncorrectSpaceHeader.Error(), "Error should be: %v, got: %v", ErrIncorrectSpaceHeader, err)
}
func TestFailWithWrongAclHeadIdInSettingsPayload(t *testing.T) {
accountKeys, err := accountdata.NewRandom()
require.NoError(t, err)
spaceId, rawHeaderWithId, err := rawHeaderWithId(accountKeys)
require.NoError(t, err)
_, rawAclWithId, err := rawAclWithId(accountKeys, spaceId)
require.NoError(t, err)
rawSettingsPayload, err := rawSettingsPayload(accountKeys, spaceId, "aclHeadId")
spacePayload := SpaceStorageCreatePayload{
AclWithId: rawAclWithId,
SpaceHeaderWithId: rawHeaderWithId,
SpaceSettingsWithId: rawSettingsPayload,
}
err = ValidateSpaceStorageCreatePayload(spacePayload)
assert.EqualErrorf(t, err, ErrIncorrectSpaceHeader.Error(), "Error should be: %v, got: %v", ErrIncorrectSpaceHeader, err)
}
func rawSettingsPayload(accountKeys *accountdata.AccountKeys, spaceId, aclHeadId string) (rawIdChange *treechangeproto.RawTreeChangeWithId, err error) {
identity, err := accountKeys.SignKey.GetPublic().Marshall()
if err != nil {
return
}
spaceSettingsSeed := make([]byte, 32)
_, err = rand.Read(spaceSettingsSeed)
if err != nil {
return
}
changePayload := make([]byte, 32)
_, err = rand.Read(changePayload)
if err != nil {
return
}
rootChange := &treechangeproto.RootChange{
AclHeadId: aclHeadId,
SpaceId: spaceId,
ChangeType: "ChangeType",
Timestamp: time.Now().Unix(),
Seed: spaceSettingsSeed,
Identity: identity,
ChangePayload: changePayload,
}
marshalledChange, err := rootChange.Marshal()
if err != nil {
return
}
signature, err := accountKeys.SignKey.Sign(marshalledChange)
if err != nil {
return
}
raw := &treechangeproto.RawTreeChange{
Payload: marshalledChange,
Signature: signature,
}
marshalledRawChange, err := raw.Marshal()
id, err := cidutil.NewCidFromBytes(marshalledRawChange)
if err != nil {
return
}
rawIdChange = &treechangeproto.RawTreeChangeWithId{
RawChange: marshalledRawChange,
Id: id,
}
return
}
func rawAclWithId(accountKeys *accountdata.AccountKeys, spaceId string) (aclHeadId string, rawWithId *aclrecordproto.RawAclRecordWithId, err error) {
readKeyBytes := make([]byte, 32)
_, err = rand.Read(readKeyBytes)
if err != nil {
return
}
readKey, err := accountKeys.SignKey.GetPublic().Encrypt(readKeyBytes)
if err != nil {
return
}
masterKey, _, err := crypto.GenerateRandomEd25519KeyPair()
identity, err := accountKeys.SignKey.GetPublic().Marshall()
if err != nil {
return
}
masterPubKey := masterKey.GetPublic()
rawIdentity, err := accountKeys.SignKey.GetPublic().Raw()
if err != nil {
return
}
identitySignature, err := masterKey.Sign(rawIdentity)
if err != nil {
return
}
rawMasterKey, err := masterPubKey.Marshall()
if err != nil {
return
}
aclRoot := aclrecordproto.AclRoot{
Identity: identity,
MasterKey: rawMasterKey,
SpaceId: spaceId,
EncryptedReadKey: readKey,
Timestamp: time.Now().Unix(),
IdentitySignature: identitySignature,
}
marshalled, err := aclRoot.Marshal()
if err != nil {
return
}
signature, err := accountKeys.SignKey.Sign(marshalled)
rawAclRecord := &aclrecordproto.RawAclRecord{
Payload: marshalled,
Signature: signature,
}
marshalledRaw, err := rawAclRecord.Marshal()
if err != nil {
return
}
aclHeadId, err = cidutil.NewCidFromBytes(marshalledRaw)
if err != nil {
return
}
rawWithId = &aclrecordproto.RawAclRecordWithId{
Payload: marshalledRaw,
Id: aclHeadId,
}
return
}
func rawHeaderWithId(accountKeys *accountdata.AccountKeys) (spaceId string, rawWithId *spacesyncproto.RawSpaceHeaderWithId, err error) {
identity, err := accountKeys.SignKey.GetPublic().Marshall()
if err != nil {
return
}
spaceHeaderSeed := make([]byte, 32)
_, err = rand.Read(spaceHeaderSeed)
if err != nil {
return
}
spaceHeaderPayload := make([]byte, 32)
_, err = rand.Read(spaceHeaderPayload)
if err != nil {
return
}
replicationKey := rand2.Uint64()
header := &spacesyncproto.SpaceHeader{
Identity: identity,
Timestamp: time.Now().Unix(),
SpaceType: "SpaceType",
ReplicationKey: replicationKey,
Seed: spaceHeaderSeed,
SpaceHeaderPayload: spaceHeaderPayload,
}
marhalled, err := header.Marshal()
if err != nil {
return
}
signature, err := accountKeys.SignKey.Sign(marhalled)
if err != nil {
return
}
rawHeader := &spacesyncproto.RawSpaceHeader{
SpaceHeader: marhalled,
Signature: signature,
}
marhalledRawHeader, err := rawHeader.Marshal()
if err != nil {
return
}
id, err := cidutil.NewCidFromBytes(marhalledRawHeader)
if err != nil {
return
}
spaceId = fmt.Sprintf("%s.%s", id, strconv.FormatUint(replicationKey, 36))
rawWithId = &spacesyncproto.RawSpaceHeaderWithId{
RawHeader: marhalledRawHeader,
Id: spaceId,
}
return
}

View File

@ -72,7 +72,7 @@ type treeStatus struct {
type syncStatusProvider struct { type syncStatusProvider struct {
sync.Mutex sync.Mutex
configuration nodeconf.Configuration configuration nodeconf.NodeConf
periodicSync periodicsync.PeriodicSync periodicSync periodicsync.PeriodicSync
updateReceiver UpdateReceiver updateReceiver UpdateReceiver
storage spacestorage.SpaceStorage storage spacestorage.SpaceStorage
@ -92,11 +92,11 @@ type syncStatusProvider struct {
type SyncStatusDeps struct { type SyncStatusDeps struct {
UpdateIntervalSecs int UpdateIntervalSecs int
UpdateTimeout time.Duration UpdateTimeout time.Duration
Configuration nodeconf.Configuration Configuration nodeconf.NodeConf
Storage spacestorage.SpaceStorage Storage spacestorage.SpaceStorage
} }
func DefaultDeps(configuration nodeconf.Configuration, store spacestorage.SpaceStorage) SyncStatusDeps { func DefaultDeps(configuration nodeconf.NodeConf, store spacestorage.SpaceStorage) SyncStatusDeps {
return SyncStatusDeps{ return SyncStatusDeps{
UpdateIntervalSecs: syncUpdateInterval, UpdateIntervalSecs: syncUpdateInterval,
UpdateTimeout: syncTimeout, UpdateTimeout: syncTimeout,

View File

@ -23,6 +23,7 @@ type CoordinatorClient interface {
StatusCheck(ctx context.Context, spaceId string) (status *coordinatorproto.SpaceStatusPayload, err error) StatusCheck(ctx context.Context, spaceId string) (status *coordinatorproto.SpaceStatusPayload, err error)
SpaceSign(ctx context.Context, payload SpaceSignPayload) (receipt *coordinatorproto.SpaceReceiptWithSignature, err error) SpaceSign(ctx context.Context, payload SpaceSignPayload) (receipt *coordinatorproto.SpaceReceiptWithSignature, err error)
FileLimitCheck(ctx context.Context, spaceId string, identity []byte) (limit uint64, err error) FileLimitCheck(ctx context.Context, spaceId string, identity []byte) (limit uint64, err error)
NetworkConfiguration(ctx context.Context, currentId string) (*coordinatorproto.NetworkConfigurationResponse, error)
app.Component app.Component
} }
@ -128,8 +129,23 @@ func (c *coordinatorClient) FileLimitCheck(ctx context.Context, spaceId string,
return resp.Limit, nil return resp.Limit, nil
} }
func (c *coordinatorClient) NetworkConfiguration(ctx context.Context, currentId string) (resp *coordinatorproto.NetworkConfigurationResponse, err error) {
cl, err := c.client(ctx)
if err != nil {
return
}
resp, err = cl.NetworkConfiguration(ctx, &coordinatorproto.NetworkConfigurationRequest{
CurrentId: currentId,
})
if err != nil {
err = rpcerr.Unwrap(err)
return
}
return
}
func (c *coordinatorClient) client(ctx context.Context) (coordinatorproto.DRPCCoordinatorClient, error) { func (c *coordinatorClient) client(ctx context.Context) (coordinatorproto.DRPCCoordinatorClient, error) {
p, err := c.pool.GetOneOf(ctx, c.nodeConf.GetLast().CoordinatorPeers()) p, err := c.pool.GetOneOf(ctx, c.nodeConf.CoordinatorPeers())
if err != nil { if err != nil {
return nil, err return nil, err
} }

View File

@ -96,6 +96,21 @@ func (mr *MockCoordinatorClientMockRecorder) Name() *gomock.Call {
return mr.mock.ctrl.RecordCallWithMethodType(mr.mock, "Name", reflect.TypeOf((*MockCoordinatorClient)(nil).Name)) return mr.mock.ctrl.RecordCallWithMethodType(mr.mock, "Name", reflect.TypeOf((*MockCoordinatorClient)(nil).Name))
} }
// NetworkConfiguration mocks base method.
func (m *MockCoordinatorClient) NetworkConfiguration(arg0 context.Context, arg1 string) (*coordinatorproto.NetworkConfigurationResponse, error) {
m.ctrl.T.Helper()
ret := m.ctrl.Call(m, "NetworkConfiguration", arg0, arg1)
ret0, _ := ret[0].(*coordinatorproto.NetworkConfigurationResponse)
ret1, _ := ret[1].(error)
return ret0, ret1
}
// NetworkConfiguration indicates an expected call of NetworkConfiguration.
func (mr *MockCoordinatorClientMockRecorder) NetworkConfiguration(arg0, arg1 interface{}) *gomock.Call {
mr.mock.ctrl.T.Helper()
return mr.mock.ctrl.RecordCallWithMethodType(mr.mock, "NetworkConfiguration", reflect.TypeOf((*MockCoordinatorClient)(nil).NetworkConfiguration), arg0, arg1)
}
// SpaceSign mocks base method. // SpaceSign mocks base method.
func (m *MockCoordinatorClient) SpaceSign(arg0 context.Context, arg1 coordinatorclient.SpaceSignPayload) (*coordinatorproto.SpaceReceiptWithSignature, error) { func (m *MockCoordinatorClient) SpaceSign(arg0 context.Context, arg1 coordinatorclient.SpaceSignPayload) (*coordinatorproto.SpaceReceiptWithSignature, error) {
m.ctrl.T.Helper() m.ctrl.T.Helper()

File diff suppressed because it is too large Load Diff

View File

@ -44,6 +44,7 @@ type DRPCCoordinatorClient interface {
FileLimitCheck(ctx context.Context, in *FileLimitCheckRequest) (*FileLimitCheckResponse, error) FileLimitCheck(ctx context.Context, in *FileLimitCheckRequest) (*FileLimitCheckResponse, error)
SpaceStatusCheck(ctx context.Context, in *SpaceStatusCheckRequest) (*SpaceStatusCheckResponse, error) SpaceStatusCheck(ctx context.Context, in *SpaceStatusCheckRequest) (*SpaceStatusCheckResponse, error)
SpaceStatusChange(ctx context.Context, in *SpaceStatusChangeRequest) (*SpaceStatusChangeResponse, error) SpaceStatusChange(ctx context.Context, in *SpaceStatusChangeRequest) (*SpaceStatusChangeResponse, error)
NetworkConfiguration(ctx context.Context, in *NetworkConfigurationRequest) (*NetworkConfigurationResponse, error)
} }
type drpcCoordinatorClient struct { type drpcCoordinatorClient struct {
@ -92,11 +93,21 @@ func (c *drpcCoordinatorClient) SpaceStatusChange(ctx context.Context, in *Space
return out, nil return out, nil
} }
func (c *drpcCoordinatorClient) NetworkConfiguration(ctx context.Context, in *NetworkConfigurationRequest) (*NetworkConfigurationResponse, error) {
out := new(NetworkConfigurationResponse)
err := c.cc.Invoke(ctx, "/coordinator.Coordinator/NetworkConfiguration", drpcEncoding_File_coordinator_coordinatorproto_protos_coordinator_proto{}, in, out)
if err != nil {
return nil, err
}
return out, nil
}
type DRPCCoordinatorServer interface { type DRPCCoordinatorServer interface {
SpaceSign(context.Context, *SpaceSignRequest) (*SpaceSignResponse, error) SpaceSign(context.Context, *SpaceSignRequest) (*SpaceSignResponse, error)
FileLimitCheck(context.Context, *FileLimitCheckRequest) (*FileLimitCheckResponse, error) FileLimitCheck(context.Context, *FileLimitCheckRequest) (*FileLimitCheckResponse, error)
SpaceStatusCheck(context.Context, *SpaceStatusCheckRequest) (*SpaceStatusCheckResponse, error) SpaceStatusCheck(context.Context, *SpaceStatusCheckRequest) (*SpaceStatusCheckResponse, error)
SpaceStatusChange(context.Context, *SpaceStatusChangeRequest) (*SpaceStatusChangeResponse, error) SpaceStatusChange(context.Context, *SpaceStatusChangeRequest) (*SpaceStatusChangeResponse, error)
NetworkConfiguration(context.Context, *NetworkConfigurationRequest) (*NetworkConfigurationResponse, error)
} }
type DRPCCoordinatorUnimplementedServer struct{} type DRPCCoordinatorUnimplementedServer struct{}
@ -117,9 +128,13 @@ func (s *DRPCCoordinatorUnimplementedServer) SpaceStatusChange(context.Context,
return nil, drpcerr.WithCode(errors.New("Unimplemented"), drpcerr.Unimplemented) return nil, drpcerr.WithCode(errors.New("Unimplemented"), drpcerr.Unimplemented)
} }
func (s *DRPCCoordinatorUnimplementedServer) NetworkConfiguration(context.Context, *NetworkConfigurationRequest) (*NetworkConfigurationResponse, error) {
return nil, drpcerr.WithCode(errors.New("Unimplemented"), drpcerr.Unimplemented)
}
type DRPCCoordinatorDescription struct{} type DRPCCoordinatorDescription struct{}
func (DRPCCoordinatorDescription) NumMethods() int { return 4 } func (DRPCCoordinatorDescription) NumMethods() int { return 5 }
func (DRPCCoordinatorDescription) Method(n int) (string, drpc.Encoding, drpc.Receiver, interface{}, bool) { func (DRPCCoordinatorDescription) Method(n int) (string, drpc.Encoding, drpc.Receiver, interface{}, bool) {
switch n { switch n {
@ -159,6 +174,15 @@ func (DRPCCoordinatorDescription) Method(n int) (string, drpc.Encoding, drpc.Rec
in1.(*SpaceStatusChangeRequest), in1.(*SpaceStatusChangeRequest),
) )
}, DRPCCoordinatorServer.SpaceStatusChange, true }, DRPCCoordinatorServer.SpaceStatusChange, true
case 4:
return "/coordinator.Coordinator/NetworkConfiguration", drpcEncoding_File_coordinator_coordinatorproto_protos_coordinator_proto{},
func(srv interface{}, ctx context.Context, in1, in2 interface{}) (drpc.Message, error) {
return srv.(DRPCCoordinatorServer).
NetworkConfiguration(
ctx,
in1.(*NetworkConfigurationRequest),
)
}, DRPCCoordinatorServer.NetworkConfiguration, true
default: default:
return "", nil, nil, nil, false return "", nil, nil, nil, false
} }
@ -231,3 +255,19 @@ func (x *drpcCoordinator_SpaceStatusChangeStream) SendAndClose(m *SpaceStatusCha
} }
return x.CloseSend() return x.CloseSend()
} }
type DRPCCoordinator_NetworkConfigurationStream interface {
drpc.Stream
SendAndClose(*NetworkConfigurationResponse) error
}
type drpcCoordinator_NetworkConfigurationStream struct {
drpc.Stream
}
func (x *drpcCoordinator_NetworkConfigurationStream) SendAndClose(m *NetworkConfigurationResponse) error {
if err := x.MsgSend(m, drpcEncoding_File_coordinator_coordinatorproto_protos_coordinator_proto{}); err != nil {
return err
}
return x.CloseSend()
}

View File

@ -18,6 +18,9 @@ service Coordinator {
// SpaceStatusChange changes the status of space // SpaceStatusChange changes the status of space
rpc SpaceStatusChange(SpaceStatusChangeRequest) returns (SpaceStatusChangeResponse); rpc SpaceStatusChange(SpaceStatusChangeRequest) returns (SpaceStatusChangeResponse);
// NetworkConfiguration retrieves the latest network configuration
rpc NetworkConfiguration(NetworkConfigurationRequest) returns (NetworkConfigurationResponse);
} }
message SpaceSignRequest { message SpaceSignRequest {
@ -109,3 +112,42 @@ message SpaceStatusChangeRequest {
message SpaceStatusChangeResponse { message SpaceStatusChangeResponse {
SpaceStatusPayload payload = 1; SpaceStatusPayload payload = 1;
} }
// NetworkConfigurationRequest contains currenId of the client configuration, it can be empty
message NetworkConfigurationRequest {
// currenId of the client configuration
// if the currentId is equal to the latest configuration id then the response will not contain a nodes list
string currentId = 1;
}
// NetworkConfigurationResponse contains list of nodes
message NetworkConfigurationResponse {
// id of current configuration
string configurationId = 1;
// network id
string networkId = 2;
// nodes list - it will be empty if the client's currentId is equal configurationId
repeated Node nodes = 3;
// unix timestamp of the creation time of configuration
uint64 creationTimeUnix = 4;
}
// NodeType determines the type of API that a node supports
enum NodeType {
// TreeAPI supports space/tree sync api
TreeAPI = 0;
// FileAPI support file api
FileAPI = 1;
// CoordinatorAPI supports coordinator api
CoordinatorAPI = 2;
}
// Node describes one node in the network
message Node {
// peerId - it's a peer identifier (libp2p format string) so it's an encoded publicKey
string peerId = 1;
// list of node addresses
repeated string addresses = 2;
// list of supported APIs
repeated NodeType types = 3;
}

View File

@ -0,0 +1,68 @@
package nodeconfsource
import (
"context"
"github.com/anytypeio/any-sync/app"
"github.com/anytypeio/any-sync/coordinator/coordinatorclient"
"github.com/anytypeio/any-sync/coordinator/coordinatorproto"
"github.com/anytypeio/any-sync/nodeconf"
"time"
)
type NodeConfSource interface {
app.Component
nodeconf.Source
}
func New() NodeConfSource {
return new(nodeConfSource)
}
type nodeConfSource struct {
cl coordinatorclient.CoordinatorClient
}
func (n *nodeConfSource) Init(a *app.App) (err error) {
n.cl = a.MustComponent(coordinatorclient.CName).(coordinatorclient.CoordinatorClient)
return nil
}
func (n *nodeConfSource) Name() (name string) {
return nodeconf.CNameSource
}
func (n *nodeConfSource) GetLast(ctx context.Context, currentId string) (c nodeconf.Configuration, err error) {
res, err := n.cl.NetworkConfiguration(ctx, currentId)
if err != nil {
return
}
if res.ConfigurationId == currentId {
err = nodeconf.ErrConfigurationNotChanged
return
}
nodes := make([]nodeconf.Node, len(res.Nodes))
for i, node := range res.Nodes {
types := make([]nodeconf.NodeType, 0, len(node.Types))
for _, nt := range node.Types {
switch nt {
case coordinatorproto.NodeType_FileAPI:
types = append(types, nodeconf.NodeTypeFile)
case coordinatorproto.NodeType_CoordinatorAPI:
types = append(types, nodeconf.NodeTypeCoordinator)
case coordinatorproto.NodeType_TreeAPI:
types = append(types, nodeconf.NodeTypeTree)
}
}
nodes[i] = nodeconf.Node{
PeerId: node.PeerId,
Addresses: node.Addresses,
Types: types,
}
}
return nodeconf.Configuration{
Id: res.ConfigurationId,
NetworkId: res.NetworkId,
Nodes: nodes,
CreationTime: time.Unix(int64(res.CreationTimeUnix), 0),
}, nil
}

24
go.mod
View File

@ -23,11 +23,11 @@ require (
github.com/ipfs/go-ipld-format v0.4.0 github.com/ipfs/go-ipld-format v0.4.0
github.com/ipfs/go-merkledag v0.10.0 github.com/ipfs/go-merkledag v0.10.0
github.com/ipfs/go-unixfs v0.4.5 github.com/ipfs/go-unixfs v0.4.5
github.com/libp2p/go-libp2p v0.24.1 github.com/libp2p/go-libp2p v0.25.1
github.com/mr-tron/base58 v1.2.0 github.com/mr-tron/base58 v1.2.0
github.com/multiformats/go-multibase v0.2.0 github.com/multiformats/go-multibase v0.2.0
github.com/multiformats/go-multihash v0.2.1 github.com/multiformats/go-multihash v0.2.1
github.com/prometheus/client_golang v1.14.0 github.com/prometheus/client_golang v1.15.0
github.com/stretchr/testify v1.8.2 github.com/stretchr/testify v1.8.2
github.com/tyler-smith/go-bip39 v1.1.0 github.com/tyler-smith/go-bip39 v1.1.0
github.com/zeebo/blake3 v0.2.3 github.com/zeebo/blake3 v0.2.3
@ -41,7 +41,7 @@ require (
) )
require ( require (
github.com/alecthomas/units v0.0.0-20210927113745-59d0afb8317a // indirect github.com/alecthomas/units v0.0.0-20211218093645-b94a6e3cc137 // indirect
github.com/beorn7/perks v1.0.1 // indirect github.com/beorn7/perks v1.0.1 // indirect
github.com/cespare/xxhash/v2 v2.2.0 // indirect github.com/cespare/xxhash/v2 v2.2.0 // indirect
github.com/crackcomm/go-gitignore v0.0.0-20170627025303-887ab5e44cc3 // indirect github.com/crackcomm/go-gitignore v0.0.0-20170627025303-887ab5e44cc3 // indirect
@ -52,18 +52,19 @@ require (
github.com/go-logr/logr v1.2.3 // indirect github.com/go-logr/logr v1.2.3 // indirect
github.com/go-logr/stdr v1.2.2 // indirect github.com/go-logr/stdr v1.2.2 // indirect
github.com/golang/freetype v0.0.0-20170609003504-e2365dfdc4a0 // indirect github.com/golang/freetype v0.0.0-20170609003504-e2365dfdc4a0 // indirect
github.com/golang/protobuf v1.5.2 // indirect github.com/golang/protobuf v1.5.3 // indirect
github.com/google/uuid v1.3.0 // indirect github.com/google/uuid v1.3.0 // indirect
github.com/hashicorp/golang-lru v0.5.4 // indirect github.com/hashicorp/golang-lru v0.5.4 // indirect
github.com/ipfs/bbloom v0.0.4 // indirect github.com/ipfs/bbloom v0.0.4 // indirect
github.com/ipfs/go-bitfield v1.1.0 // indirect github.com/ipfs/go-bitfield v1.1.0 // indirect
github.com/ipfs/go-datastore v0.6.0 // indirect github.com/ipfs/go-datastore v0.6.0 // indirect
github.com/ipfs/go-ipfs-ds-help v1.1.0 // indirect github.com/ipfs/go-ipfs-ds-help v1.1.0 // indirect
github.com/ipfs/go-ipfs-files v0.2.0 // indirect github.com/ipfs/go-ipfs-files v0.3.0 // indirect
github.com/ipfs/go-ipfs-posinfo v0.0.1 // indirect github.com/ipfs/go-ipfs-posinfo v0.0.1 // indirect
github.com/ipfs/go-ipfs-util v0.0.2 // indirect github.com/ipfs/go-ipfs-util v0.0.2 // indirect
github.com/ipfs/go-ipld-cbor v0.0.6 // indirect github.com/ipfs/go-ipld-cbor v0.0.6 // indirect
github.com/ipfs/go-ipld-legacy v0.1.1 // indirect github.com/ipfs/go-ipld-legacy v0.1.1 // indirect
github.com/ipfs/go-libipfs v0.7.0 // indirect
github.com/ipfs/go-log v1.0.5 // indirect github.com/ipfs/go-log v1.0.5 // indirect
github.com/ipfs/go-log/v2 v2.5.1 // indirect github.com/ipfs/go-log/v2 v2.5.1 // indirect
github.com/ipfs/go-metrics-interface v0.0.1 // indirect github.com/ipfs/go-metrics-interface v0.0.1 // indirect
@ -72,29 +73,26 @@ require (
github.com/ipld/go-ipld-prime v0.20.0 // indirect github.com/ipld/go-ipld-prime v0.20.0 // indirect
github.com/jbenet/go-temp-err-catcher v0.1.0 // indirect github.com/jbenet/go-temp-err-catcher v0.1.0 // indirect
github.com/jbenet/goprocess v0.1.4 // indirect github.com/jbenet/goprocess v0.1.4 // indirect
github.com/klauspost/cpuid/v2 v2.2.2 // indirect github.com/klauspost/cpuid/v2 v2.2.3 // indirect
github.com/libp2p/go-buffer-pool v0.1.0 // indirect github.com/libp2p/go-buffer-pool v0.1.0 // indirect
github.com/libp2p/go-openssl v0.1.0 // indirect
github.com/mattn/go-isatty v0.0.17 // indirect github.com/mattn/go-isatty v0.0.17 // indirect
github.com/mattn/go-pointer v0.0.1 // indirect
github.com/matttproud/golang_protobuf_extensions v1.0.4 // indirect github.com/matttproud/golang_protobuf_extensions v1.0.4 // indirect
github.com/minio/sha256-simd v1.0.0 // indirect github.com/minio/sha256-simd v1.0.0 // indirect
github.com/multiformats/go-base32 v0.1.0 // indirect github.com/multiformats/go-base32 v0.1.0 // indirect
github.com/multiformats/go-base36 v0.2.0 // indirect github.com/multiformats/go-base36 v0.2.0 // indirect
github.com/multiformats/go-multiaddr v0.8.0 // indirect github.com/multiformats/go-multiaddr v0.8.0 // indirect
github.com/multiformats/go-multicodec v0.8.0 // indirect github.com/multiformats/go-multicodec v0.8.0 // indirect
github.com/multiformats/go-multistream v0.3.3 // indirect github.com/multiformats/go-multistream v0.4.1 // indirect
github.com/multiformats/go-varint v0.0.7 // indirect github.com/multiformats/go-varint v0.0.7 // indirect
github.com/opentracing/opentracing-go v1.2.0 // indirect github.com/opentracing/opentracing-go v1.2.0 // indirect
github.com/pkg/errors v0.9.1 // indirect github.com/pkg/errors v0.9.1 // indirect
github.com/pmezard/go-difflib v1.0.0 // indirect github.com/pmezard/go-difflib v1.0.0 // indirect
github.com/polydawn/refmt v0.89.0 // indirect github.com/polydawn/refmt v0.89.0 // indirect
github.com/prometheus/client_model v0.3.0 // indirect github.com/prometheus/client_model v0.3.0 // indirect
github.com/prometheus/common v0.39.0 // indirect github.com/prometheus/common v0.42.0 // indirect
github.com/prometheus/procfs v0.9.0 // indirect github.com/prometheus/procfs v0.9.0 // indirect
github.com/spacemonkeygo/spacelog v0.0.0-20180420211403-2296661a0572 // indirect
github.com/spaolacci/murmur3 v1.1.0 // indirect github.com/spaolacci/murmur3 v1.1.0 // indirect
github.com/whyrusleeping/cbor-gen v0.0.0-20221220214510-0333c149dec0 // indirect github.com/whyrusleeping/cbor-gen v0.0.0-20230126041949-52956bd4c9aa // indirect
github.com/whyrusleeping/chunker v0.0.0-20181014151217-fe64bd25879f // indirect github.com/whyrusleeping/chunker v0.0.0-20181014151217-fe64bd25879f // indirect
go.opentelemetry.io/otel v1.11.2 // indirect go.opentelemetry.io/otel v1.11.2 // indirect
go.opentelemetry.io/otel/trace v1.11.2 // indirect go.opentelemetry.io/otel/trace v1.11.2 // indirect
@ -104,7 +102,7 @@ require (
golang.org/x/sync v0.1.0 // indirect golang.org/x/sync v0.1.0 // indirect
golang.org/x/sys v0.7.0 // indirect golang.org/x/sys v0.7.0 // indirect
golang.org/x/xerrors v0.0.0-20220907171357-04be3eba64a2 // indirect golang.org/x/xerrors v0.0.0-20220907171357-04be3eba64a2 // indirect
google.golang.org/protobuf v1.28.1 // indirect google.golang.org/protobuf v1.30.0 // indirect
gopkg.in/yaml.v3 v3.0.1 // indirect gopkg.in/yaml.v3 v3.0.1 // indirect
lukechampine.com/blake3 v1.1.7 // indirect lukechampine.com/blake3 v1.1.7 // indirect
) )

54
go.sum
View File

@ -3,8 +3,8 @@ filippo.io/edwards25519 v1.0.0/go.mod h1:N1IkdkCkiLB6tki+MYJoSx2JTY9NUlxZE7eHn5E
github.com/BurntSushi/toml v0.3.1/go.mod h1:xHWCNGjB5oqiDr8zfno3MHue2Ht5sIBksp03qcyfWMU= github.com/BurntSushi/toml v0.3.1/go.mod h1:xHWCNGjB5oqiDr8zfno3MHue2Ht5sIBksp03qcyfWMU=
github.com/OneOfOne/xxhash v1.2.2 h1:KMrpdQIwFcEqXDklaen+P1axHaj9BSKzvpUUfnHldSE= github.com/OneOfOne/xxhash v1.2.2 h1:KMrpdQIwFcEqXDklaen+P1axHaj9BSKzvpUUfnHldSE=
github.com/OneOfOne/xxhash v1.2.2/go.mod h1:HSdplMjZKSmBqAxg5vPj2TmRDmfkzw+cTzAElWljhcU= github.com/OneOfOne/xxhash v1.2.2/go.mod h1:HSdplMjZKSmBqAxg5vPj2TmRDmfkzw+cTzAElWljhcU=
github.com/alecthomas/units v0.0.0-20210927113745-59d0afb8317a h1:E/8AP5dFtMhl5KPJz66Kt9G0n+7Sn41Fy1wv9/jHOrc= github.com/alecthomas/units v0.0.0-20211218093645-b94a6e3cc137 h1:s6gZFSlWYmbqAuRjVTiNNhvNRfY2Wxp9nhfyel4rklc=
github.com/alecthomas/units v0.0.0-20210927113745-59d0afb8317a/go.mod h1:OMCwj8VM1Kc9e19TLln2VL61YJF0x1XFtfdL4JdbSyE= github.com/alecthomas/units v0.0.0-20211218093645-b94a6e3cc137/go.mod h1:OMCwj8VM1Kc9e19TLln2VL61YJF0x1XFtfdL4JdbSyE=
github.com/anytypeio/go-chash v0.1.0 h1:nYCMh13SEai/7cXRUoKfU27uASj7XEF6NhvY6hFMKY8= github.com/anytypeio/go-chash v0.1.0 h1:nYCMh13SEai/7cXRUoKfU27uASj7XEF6NhvY6hFMKY8=
github.com/anytypeio/go-chash v0.1.0/go.mod h1:Q7XiggkMrThRFAwYSItzLOT9OPC8a497SLZtgmJtC/I= github.com/anytypeio/go-chash v0.1.0/go.mod h1:Q7XiggkMrThRFAwYSItzLOT9OPC8a497SLZtgmJtC/I=
github.com/anytypeio/go-slip10 v0.0.0-20200330112030-a352ca8495e4 h1:jB5Ke7NVoW52i65PtLFBr5Q5k6RskIY8L70pgnBcnWo= github.com/anytypeio/go-slip10 v0.0.0-20200330112030-a352ca8495e4 h1:jB5Ke7NVoW52i65PtLFBr5Q5k6RskIY8L70pgnBcnWo=
@ -58,8 +58,8 @@ github.com/golang/mock v1.6.0/go.mod h1:p6yTPP+5HYm5mzsMV8JkE6ZKdX+/wYM6Hr+Licev
github.com/golang/protobuf v1.2.0/go.mod h1:6lQm79b+lXiMfvg/cZm0SGofjICqVBUtrP5yJMmIC1U= github.com/golang/protobuf v1.2.0/go.mod h1:6lQm79b+lXiMfvg/cZm0SGofjICqVBUtrP5yJMmIC1U=
github.com/golang/protobuf v1.3.5/go.mod h1:6O5/vntMXwX2lRkT1hjjk0nAC1IDOTvTlVgjlRvqsdk= github.com/golang/protobuf v1.3.5/go.mod h1:6O5/vntMXwX2lRkT1hjjk0nAC1IDOTvTlVgjlRvqsdk=
github.com/golang/protobuf v1.5.0/go.mod h1:FsONVRAS9T7sI+LIUmWTfcYkHO4aIWwzhcaSAoJOfIk= github.com/golang/protobuf v1.5.0/go.mod h1:FsONVRAS9T7sI+LIUmWTfcYkHO4aIWwzhcaSAoJOfIk=
github.com/golang/protobuf v1.5.2 h1:ROPKBNFfQgOUMifHyP+KYbvpjbdoFNs+aK7DXlji0Tw= github.com/golang/protobuf v1.5.3 h1:KhyjKVUg7Usr/dYsdSqoFveMYd5ko72D+zANwlG1mmg=
github.com/golang/protobuf v1.5.2/go.mod h1:XVQd3VNwM+JqD3oG2Ue2ip4fOMUkwXdXDdiuN0vRsmY= github.com/golang/protobuf v1.5.3/go.mod h1:XVQd3VNwM+JqD3oG2Ue2ip4fOMUkwXdXDdiuN0vRsmY=
github.com/google/go-cmp v0.4.0/go.mod h1:v8dTdLbMG2kIc/vJvl+f65V22dbkXbowE6jgT/gNBxE= github.com/google/go-cmp v0.4.0/go.mod h1:v8dTdLbMG2kIc/vJvl+f65V22dbkXbowE6jgT/gNBxE=
github.com/google/go-cmp v0.5.4/go.mod h1:v8dTdLbMG2kIc/vJvl+f65V22dbkXbowE6jgT/gNBxE= github.com/google/go-cmp v0.5.4/go.mod h1:v8dTdLbMG2kIc/vJvl+f65V22dbkXbowE6jgT/gNBxE=
github.com/google/go-cmp v0.5.5/go.mod h1:v8dTdLbMG2kIc/vJvl+f65V22dbkXbowE6jgT/gNBxE= github.com/google/go-cmp v0.5.5/go.mod h1:v8dTdLbMG2kIc/vJvl+f65V22dbkXbowE6jgT/gNBxE=
@ -117,11 +117,11 @@ github.com/ipfs/go-ipfs-ds-help v1.1.0/go.mod h1:YR5+6EaebOhfcqVCyqemItCLthrpVNo
github.com/ipfs/go-ipfs-exchange-interface v0.2.0 h1:8lMSJmKogZYNo2jjhUs0izT+dck05pqUw4mWNW9Pw6Y= github.com/ipfs/go-ipfs-exchange-interface v0.2.0 h1:8lMSJmKogZYNo2jjhUs0izT+dck05pqUw4mWNW9Pw6Y=
github.com/ipfs/go-ipfs-exchange-interface v0.2.0/go.mod h1:z6+RhJuDQbqKguVyslSOuVDhqF9JtTrO3eptSAiW2/Y= github.com/ipfs/go-ipfs-exchange-interface v0.2.0/go.mod h1:z6+RhJuDQbqKguVyslSOuVDhqF9JtTrO3eptSAiW2/Y=
github.com/ipfs/go-ipfs-exchange-offline v0.3.0 h1:c/Dg8GDPzixGd0MC8Jh6mjOwU57uYokgWRFidfvEkuA= github.com/ipfs/go-ipfs-exchange-offline v0.3.0 h1:c/Dg8GDPzixGd0MC8Jh6mjOwU57uYokgWRFidfvEkuA=
github.com/ipfs/go-ipfs-files v0.2.0 h1:z6MCYHQSZpDWpUSK59Kf0ajP1fi4gLCf6fIulVsp8A8= github.com/ipfs/go-ipfs-files v0.3.0 h1:fallckyc5PYjuMEitPNrjRfpwl7YFt69heCOUhsbGxQ=
github.com/ipfs/go-ipfs-files v0.2.0/go.mod h1:vT7uaQfIsprKktzbTPLnIsd+NGw9ZbYwSq0g3N74u0M= github.com/ipfs/go-ipfs-files v0.3.0/go.mod h1:xAUtYMwB+iu/dtf6+muHNSFQCJG2dSiStR2P6sn9tIM=
github.com/ipfs/go-ipfs-posinfo v0.0.1 h1:Esoxj+1JgSjX0+ylc0hUmJCOv6V2vFoZiETLR6OtpRs= github.com/ipfs/go-ipfs-posinfo v0.0.1 h1:Esoxj+1JgSjX0+ylc0hUmJCOv6V2vFoZiETLR6OtpRs=
github.com/ipfs/go-ipfs-posinfo v0.0.1/go.mod h1:SwyeVP+jCwiDu0C313l/8jg6ZxM0qqtlt2a0vILTc1A= github.com/ipfs/go-ipfs-posinfo v0.0.1/go.mod h1:SwyeVP+jCwiDu0C313l/8jg6ZxM0qqtlt2a0vILTc1A=
github.com/ipfs/go-ipfs-pq v0.0.2 h1:e1vOOW6MuOwG2lqxcLA+wEn93i/9laCY8sXAw76jFOY= github.com/ipfs/go-ipfs-pq v0.0.3 h1:YpoHVJB+jzK15mr/xsWC574tyDLkezVrDNeaalQBsTE=
github.com/ipfs/go-ipfs-routing v0.3.0 h1:9W/W3N+g+y4ZDeffSgqhgo7BsBSJwPMcyssET9OWevc= github.com/ipfs/go-ipfs-routing v0.3.0 h1:9W/W3N+g+y4ZDeffSgqhgo7BsBSJwPMcyssET9OWevc=
github.com/ipfs/go-ipfs-util v0.0.1/go.mod h1:spsl5z8KUnrve+73pOhSVZND1SIxPW5RyBCNzQxlJBc= github.com/ipfs/go-ipfs-util v0.0.1/go.mod h1:spsl5z8KUnrve+73pOhSVZND1SIxPW5RyBCNzQxlJBc=
github.com/ipfs/go-ipfs-util v0.0.2 h1:59Sswnk1MFaiq+VcaknX7aYEyGyGDAA73ilhEK2POp8= github.com/ipfs/go-ipfs-util v0.0.2 h1:59Sswnk1MFaiq+VcaknX7aYEyGyGDAA73ilhEK2POp8=
@ -134,6 +134,8 @@ github.com/ipfs/go-ipld-format v0.4.0 h1:yqJSaJftjmjc9jEOFYlpkwOLVKv68OD27jFLlSg
github.com/ipfs/go-ipld-format v0.4.0/go.mod h1:co/SdBE8h99968X0hViiw1MNlh6fvxxnHpvVLnH7jSM= github.com/ipfs/go-ipld-format v0.4.0/go.mod h1:co/SdBE8h99968X0hViiw1MNlh6fvxxnHpvVLnH7jSM=
github.com/ipfs/go-ipld-legacy v0.1.1 h1:BvD8PEuqwBHLTKqlGFTHSwrwFOMkVESEvwIYwR2cdcc= github.com/ipfs/go-ipld-legacy v0.1.1 h1:BvD8PEuqwBHLTKqlGFTHSwrwFOMkVESEvwIYwR2cdcc=
github.com/ipfs/go-ipld-legacy v0.1.1/go.mod h1:8AyKFCjgRPsQFf15ZQgDB8Din4DML/fOmKZkkFkrIEg= github.com/ipfs/go-ipld-legacy v0.1.1/go.mod h1:8AyKFCjgRPsQFf15ZQgDB8Din4DML/fOmKZkkFkrIEg=
github.com/ipfs/go-libipfs v0.7.0 h1:Mi54WJTODaOL2/ZSm5loi3SwI3jI2OuFWUrQIkJ5cpM=
github.com/ipfs/go-libipfs v0.7.0/go.mod h1:KsIf/03CqhICzyRGyGo68tooiBE2iFbI/rXW7FhAYr0=
github.com/ipfs/go-log v0.0.1/go.mod h1:kL1d2/hzSpI0thNYjiKfjanbVNU+IIGA/WnNESY9leM= github.com/ipfs/go-log v0.0.1/go.mod h1:kL1d2/hzSpI0thNYjiKfjanbVNU+IIGA/WnNESY9leM=
github.com/ipfs/go-log v1.0.5 h1:2dOuUCB1Z7uoczMWgAyDck5JLb72zHzrMnGnCNNbvY8= github.com/ipfs/go-log v1.0.5 h1:2dOuUCB1Z7uoczMWgAyDck5JLb72zHzrMnGnCNNbvY8=
github.com/ipfs/go-log v1.0.5/go.mod h1:j0b8ZoR+7+R99LD9jZ6+AJsrzkPbSXbZfGakb5JPtIo= github.com/ipfs/go-log v1.0.5/go.mod h1:j0b8ZoR+7+R99LD9jZ6+AJsrzkPbSXbZfGakb5JPtIo=
@ -144,7 +146,7 @@ github.com/ipfs/go-merkledag v0.10.0 h1:IUQhj/kzTZfam4e+LnaEpoiZ9vZF6ldimVlby+6O
github.com/ipfs/go-merkledag v0.10.0/go.mod h1:zkVav8KiYlmbzUzNM6kENzkdP5+qR7+2mCwxkQ6GIj8= github.com/ipfs/go-merkledag v0.10.0/go.mod h1:zkVav8KiYlmbzUzNM6kENzkdP5+qR7+2mCwxkQ6GIj8=
github.com/ipfs/go-metrics-interface v0.0.1 h1:j+cpbjYvu4R8zbleSs36gvB7jR+wsL2fGD6n0jO4kdg= github.com/ipfs/go-metrics-interface v0.0.1 h1:j+cpbjYvu4R8zbleSs36gvB7jR+wsL2fGD6n0jO4kdg=
github.com/ipfs/go-metrics-interface v0.0.1/go.mod h1:6s6euYU4zowdslK0GKHmqaIZ3j/b/tL7HTWtJ4VPgWY= github.com/ipfs/go-metrics-interface v0.0.1/go.mod h1:6s6euYU4zowdslK0GKHmqaIZ3j/b/tL7HTWtJ4VPgWY=
github.com/ipfs/go-peertaskqueue v0.8.0 h1:JyNO144tfu9bx6Hpo119zvbEL9iQ760FHOiJYsUjqaU= github.com/ipfs/go-peertaskqueue v0.8.1 h1:YhxAs1+wxb5jk7RvS0LHdyiILpNmRIRnZVztekOF0pg=
github.com/ipfs/go-unixfs v0.4.5 h1:wj8JhxvV1G6CD7swACwSKYa+NgtdWC1RUit+gFnymDU= github.com/ipfs/go-unixfs v0.4.5 h1:wj8JhxvV1G6CD7swACwSKYa+NgtdWC1RUit+gFnymDU=
github.com/ipfs/go-unixfs v0.4.5/go.mod h1:BIznJNvt/gEx/ooRMI4Us9K8+qeGO7vx1ohnbk8gjFg= github.com/ipfs/go-unixfs v0.4.5/go.mod h1:BIznJNvt/gEx/ooRMI4Us9K8+qeGO7vx1ohnbk8gjFg=
github.com/ipfs/go-verifcid v0.0.2 h1:XPnUv0XmdH+ZIhLGKg6U2vaPaRDXb9urMyNVCE7uvTs= github.com/ipfs/go-verifcid v0.0.2 h1:XPnUv0XmdH+ZIhLGKg6U2vaPaRDXb9urMyNVCE7uvTs=
@ -169,8 +171,8 @@ github.com/kisielk/gotool v1.0.0/go.mod h1:XhKaO+MFFWcvkIS/tQcRk01m1F5IRFswLeQ+o
github.com/klauspost/cpuid/v2 v2.0.4/go.mod h1:FInQzS24/EEf25PyTYn52gqo7WaD8xa0213Md/qVLRg= github.com/klauspost/cpuid/v2 v2.0.4/go.mod h1:FInQzS24/EEf25PyTYn52gqo7WaD8xa0213Md/qVLRg=
github.com/klauspost/cpuid/v2 v2.0.9/go.mod h1:FInQzS24/EEf25PyTYn52gqo7WaD8xa0213Md/qVLRg= github.com/klauspost/cpuid/v2 v2.0.9/go.mod h1:FInQzS24/EEf25PyTYn52gqo7WaD8xa0213Md/qVLRg=
github.com/klauspost/cpuid/v2 v2.0.12/go.mod h1:g2LTdtYhdyuGPqyWyv7qRAmj1WBqxuObKfj5c0PQa7c= github.com/klauspost/cpuid/v2 v2.0.12/go.mod h1:g2LTdtYhdyuGPqyWyv7qRAmj1WBqxuObKfj5c0PQa7c=
github.com/klauspost/cpuid/v2 v2.2.2 h1:xPMwiykqNK9VK0NYC3+jTMYv9I6Vl3YdjZgPZKG3zO0= github.com/klauspost/cpuid/v2 v2.2.3 h1:sxCkb+qR91z4vsqw4vGGZlDgPz3G7gjaLyK3V8y70BU=
github.com/klauspost/cpuid/v2 v2.2.2/go.mod h1:RVVoqg1df56z8g3pUjL/3lE5UfnlrJX8tyFgg4nqhuY= github.com/klauspost/cpuid/v2 v2.2.3/go.mod h1:RVVoqg1df56z8g3pUjL/3lE5UfnlrJX8tyFgg4nqhuY=
github.com/koron/go-ssdp v0.0.3 h1:JivLMY45N76b4p/vsWGOKewBQu6uf39y8l+AQ7sDKx8= github.com/koron/go-ssdp v0.0.3 h1:JivLMY45N76b4p/vsWGOKewBQu6uf39y8l+AQ7sDKx8=
github.com/kr/pretty v0.1.0/go.mod h1:dAy3ld7l9f0ibDNOQOHHMYYIIbhfbHSm3C4ZsoJORNo= github.com/kr/pretty v0.1.0/go.mod h1:dAy3ld7l9f0ibDNOQOHHMYYIIbhfbHSm3C4ZsoJORNo=
github.com/kr/pretty v0.2.0/go.mod h1:ipq/a2n7PKx3OHsz4KJII5eveXtPO4qwEXGdVfWzfnI= github.com/kr/pretty v0.2.0/go.mod h1:ipq/a2n7PKx3OHsz4KJII5eveXtPO4qwEXGdVfWzfnI=
@ -183,24 +185,20 @@ github.com/libp2p/go-buffer-pool v0.0.2/go.mod h1:MvaB6xw5vOrDl8rYZGLFdKAuk/hRoR
github.com/libp2p/go-buffer-pool v0.1.0 h1:oK4mSFcQz7cTQIfqbe4MIj9gLW+mnanjyFtc6cdF0Y8= github.com/libp2p/go-buffer-pool v0.1.0 h1:oK4mSFcQz7cTQIfqbe4MIj9gLW+mnanjyFtc6cdF0Y8=
github.com/libp2p/go-buffer-pool v0.1.0/go.mod h1:N+vh8gMqimBzdKkSMVuydVDq+UV5QTWy5HSiZacSbPg= github.com/libp2p/go-buffer-pool v0.1.0/go.mod h1:N+vh8gMqimBzdKkSMVuydVDq+UV5QTWy5HSiZacSbPg=
github.com/libp2p/go-cidranger v1.1.0 h1:ewPN8EZ0dd1LSnrtuwd4709PXVcITVeuwbag38yPW7c= github.com/libp2p/go-cidranger v1.1.0 h1:ewPN8EZ0dd1LSnrtuwd4709PXVcITVeuwbag38yPW7c=
github.com/libp2p/go-libp2p v0.24.1 h1:+lS4fqj7RF9egcPq9Yo3iqdRTcDMApzoBbQMhxtwOVw= github.com/libp2p/go-libp2p v0.25.1 h1:YK+YDCHpYyTvitKWVxa5PfElgIpOONU01X5UcLEwJGA=
github.com/libp2p/go-libp2p v0.24.1/go.mod h1:5LJqbrqFsUzWrq70JHCYqjATlX4ey8Klpct3OEe8hSI= github.com/libp2p/go-libp2p v0.25.1/go.mod h1:xnK9/1d9+jeQCVvi/f1g12KqtVi/jP/SijtKV1hML3g=
github.com/libp2p/go-libp2p-asn-util v0.2.0 h1:rg3+Os8jbnO5DxkC7K/Utdi+DkY3q/d1/1q+8WeNAsw= github.com/libp2p/go-libp2p-asn-util v0.2.0 h1:rg3+Os8jbnO5DxkC7K/Utdi+DkY3q/d1/1q+8WeNAsw=
github.com/libp2p/go-libp2p-record v0.2.0 h1:oiNUOCWno2BFuxt3my4i1frNrt7PerzB3queqa1NkQ0= github.com/libp2p/go-libp2p-record v0.2.0 h1:oiNUOCWno2BFuxt3my4i1frNrt7PerzB3queqa1NkQ0=
github.com/libp2p/go-libp2p-testing v0.12.0 h1:EPvBb4kKMWO29qP4mZGyhVzUyR25dvfUIK5WDu6iPUA= github.com/libp2p/go-libp2p-testing v0.12.0 h1:EPvBb4kKMWO29qP4mZGyhVzUyR25dvfUIK5WDu6iPUA=
github.com/libp2p/go-msgio v0.2.0 h1:W6shmB+FeynDrUVl2dgFQvzfBZcXiyqY4VmpQLu9FqU= github.com/libp2p/go-msgio v0.3.0 h1:mf3Z8B1xcFN314sWX+2vOTShIE0Mmn2TXn3YCUQGNj0=
github.com/libp2p/go-nat v0.1.0 h1:MfVsH6DLcpa04Xr+p8hmVRG4juse0s3J8HyNWYHffXg= github.com/libp2p/go-nat v0.1.0 h1:MfVsH6DLcpa04Xr+p8hmVRG4juse0s3J8HyNWYHffXg=
github.com/libp2p/go-netroute v0.2.1 h1:V8kVrpD8GK0Riv15/7VN6RbUQ3URNZVosw7H2v9tksU= github.com/libp2p/go-netroute v0.2.1 h1:V8kVrpD8GK0Riv15/7VN6RbUQ3URNZVosw7H2v9tksU=
github.com/libp2p/go-openssl v0.1.0 h1:LBkKEcUv6vtZIQLVTegAil8jbNpJErQ9AnT+bWV+Ooo=
github.com/libp2p/go-openssl v0.1.0/go.mod h1:OiOxwPpL3n4xlenjx2h7AwSGaFSC/KZvf6gNdOBQMtc=
github.com/libp2p/go-yamux/v4 v4.0.0 h1:+Y80dV2Yx/kv7Y7JKu0LECyVdMXm1VUoko+VQ9rBfZQ= github.com/libp2p/go-yamux/v4 v4.0.0 h1:+Y80dV2Yx/kv7Y7JKu0LECyVdMXm1VUoko+VQ9rBfZQ=
github.com/mattn/go-colorable v0.1.1/go.mod h1:FuOcm+DKB9mbwrcAfNl7/TZVBZ6rcnceauSikq3lYCQ= github.com/mattn/go-colorable v0.1.1/go.mod h1:FuOcm+DKB9mbwrcAfNl7/TZVBZ6rcnceauSikq3lYCQ=
github.com/mattn/go-isatty v0.0.5/go.mod h1:Iq45c/XA43vh69/j3iqttzPXn0bhXyGjM0Hdxcsrc5s= github.com/mattn/go-isatty v0.0.5/go.mod h1:Iq45c/XA43vh69/j3iqttzPXn0bhXyGjM0Hdxcsrc5s=
github.com/mattn/go-isatty v0.0.14/go.mod h1:7GGIvUiUoEMVVmxf/4nioHXj79iQHKdU27kJ6hsGG94= github.com/mattn/go-isatty v0.0.14/go.mod h1:7GGIvUiUoEMVVmxf/4nioHXj79iQHKdU27kJ6hsGG94=
github.com/mattn/go-isatty v0.0.17 h1:BTarxUcIeDqL27Mc+vyvdWYSL28zpIhv3RoTdsLMPng= github.com/mattn/go-isatty v0.0.17 h1:BTarxUcIeDqL27Mc+vyvdWYSL28zpIhv3RoTdsLMPng=
github.com/mattn/go-isatty v0.0.17/go.mod h1:kYGgaQfpe5nmfYZH+SKPsOc2e4SrIfOl2e/yFXSvRLM= github.com/mattn/go-isatty v0.0.17/go.mod h1:kYGgaQfpe5nmfYZH+SKPsOc2e4SrIfOl2e/yFXSvRLM=
github.com/mattn/go-pointer v0.0.1 h1:n+XhsuGeVO6MEAp7xyEukFINEa+Quek5psIR/ylA6o0=
github.com/mattn/go-pointer v0.0.1/go.mod h1:2zXcozF6qYGgmsG+SeTZz3oAbFLdD3OWqnUbNvJZAlc=
github.com/matttproud/golang_protobuf_extensions v1.0.4 h1:mmDVorXM7PCGKw94cs5zkfA9PSy5pEvNWRP0ET0TIVo= github.com/matttproud/golang_protobuf_extensions v1.0.4 h1:mmDVorXM7PCGKw94cs5zkfA9PSy5pEvNWRP0ET0TIVo=
github.com/matttproud/golang_protobuf_extensions v1.0.4/go.mod h1:BSXmuO+STAnVfrANrmjBb36TMTDstsz7MSK+HVaYKv4= github.com/matttproud/golang_protobuf_extensions v1.0.4/go.mod h1:BSXmuO+STAnVfrANrmjBb36TMTDstsz7MSK+HVaYKv4=
github.com/miekg/dns v1.1.50 h1:DQUfb9uc6smULcREF09Uc+/Gd46YWqJd5DbpPE9xkcA= github.com/miekg/dns v1.1.50 h1:DQUfb9uc6smULcREF09Uc+/Gd46YWqJd5DbpPE9xkcA=
@ -237,8 +235,8 @@ github.com/multiformats/go-multihash v0.0.14/go.mod h1:VdAWLKTwram9oKAatUcLxBNUj
github.com/multiformats/go-multihash v0.0.15/go.mod h1:D6aZrWNLFTV/ynMpKsNtB40mJzmCl4jb1alC0OvHiHg= github.com/multiformats/go-multihash v0.0.15/go.mod h1:D6aZrWNLFTV/ynMpKsNtB40mJzmCl4jb1alC0OvHiHg=
github.com/multiformats/go-multihash v0.2.1 h1:aem8ZT0VA2nCHHk7bPJ1BjUbHNciqZC/d16Vve9l108= github.com/multiformats/go-multihash v0.2.1 h1:aem8ZT0VA2nCHHk7bPJ1BjUbHNciqZC/d16Vve9l108=
github.com/multiformats/go-multihash v0.2.1/go.mod h1:WxoMcYG85AZVQUyRyo9s4wULvW5qrI9vb2Lt6evduFc= github.com/multiformats/go-multihash v0.2.1/go.mod h1:WxoMcYG85AZVQUyRyo9s4wULvW5qrI9vb2Lt6evduFc=
github.com/multiformats/go-multistream v0.3.3 h1:d5PZpjwRgVlbwfdTDjife7XszfZd8KYWfROYFlGcR8o= github.com/multiformats/go-multistream v0.4.1 h1:rFy0Iiyn3YT0asivDUIR05leAdwZq3de4741sbiSdfo=
github.com/multiformats/go-multistream v0.3.3/go.mod h1:ODRoqamLUsETKS9BNcII4gcRsJBU5VAwRIv7O39cEXg= github.com/multiformats/go-multistream v0.4.1/go.mod h1:Mz5eykRVAjJWckE2U78c6xqdtyNUEhKSM0Lwar2p77Q=
github.com/multiformats/go-varint v0.0.5/go.mod h1:3Ls8CIEsrijN6+B7PbrXRPxHRPuXSrVKRY101jdMZYE= github.com/multiformats/go-varint v0.0.5/go.mod h1:3Ls8CIEsrijN6+B7PbrXRPxHRPuXSrVKRY101jdMZYE=
github.com/multiformats/go-varint v0.0.6/go.mod h1:3Ls8CIEsrijN6+B7PbrXRPxHRPuXSrVKRY101jdMZYE= github.com/multiformats/go-varint v0.0.6/go.mod h1:3Ls8CIEsrijN6+B7PbrXRPxHRPuXSrVKRY101jdMZYE=
github.com/multiformats/go-varint v0.0.7 h1:sWSGR+f/eu5ABZA2ZpYKBILXTTs9JWpdEM/nEGOHFS8= github.com/multiformats/go-varint v0.0.7 h1:sWSGR+f/eu5ABZA2ZpYKBILXTTs9JWpdEM/nEGOHFS8=
@ -256,12 +254,12 @@ github.com/polydawn/refmt v0.0.0-20190221155625-df39d6c2d992/go.mod h1:uIp+gprXx
github.com/polydawn/refmt v0.0.0-20190807091052-3d65705ee9f1/go.mod h1:uIp+gprXxxrWSjjklXD+mN4wed/tMfjMMmN/9+JsA9o= github.com/polydawn/refmt v0.0.0-20190807091052-3d65705ee9f1/go.mod h1:uIp+gprXxxrWSjjklXD+mN4wed/tMfjMMmN/9+JsA9o=
github.com/polydawn/refmt v0.89.0 h1:ADJTApkvkeBZsN0tBTx8QjpD9JkmxbKp0cxfr9qszm4= github.com/polydawn/refmt v0.89.0 h1:ADJTApkvkeBZsN0tBTx8QjpD9JkmxbKp0cxfr9qszm4=
github.com/polydawn/refmt v0.89.0/go.mod h1:/zvteZs/GwLtCgZ4BL6CBsk9IKIlexP43ObX9AxTqTw= github.com/polydawn/refmt v0.89.0/go.mod h1:/zvteZs/GwLtCgZ4BL6CBsk9IKIlexP43ObX9AxTqTw=
github.com/prometheus/client_golang v1.14.0 h1:nJdhIvne2eSX/XRAFV9PcvFFRbrjbcTUj0VP62TMhnw= github.com/prometheus/client_golang v1.15.0 h1:5fCgGYogn0hFdhyhLbw7hEsWxufKtY9klyvdNfFlFhM=
github.com/prometheus/client_golang v1.14.0/go.mod h1:8vpkKitgIVNcqrRBWh1C4TIUQgYNtG/XQE4E/Zae36Y= github.com/prometheus/client_golang v1.15.0/go.mod h1:e9yaBhRPU2pPNsZwE+JdQl0KEt1N9XgF6zxWmaC0xOk=
github.com/prometheus/client_model v0.3.0 h1:UBgGFHqYdG/TPFD1B1ogZywDqEkwp3fBMvqdiQ7Xew4= github.com/prometheus/client_model v0.3.0 h1:UBgGFHqYdG/TPFD1B1ogZywDqEkwp3fBMvqdiQ7Xew4=
github.com/prometheus/client_model v0.3.0/go.mod h1:LDGWKZIo7rky3hgvBe+caln+Dr3dPggB5dvjtD7w9+w= github.com/prometheus/client_model v0.3.0/go.mod h1:LDGWKZIo7rky3hgvBe+caln+Dr3dPggB5dvjtD7w9+w=
github.com/prometheus/common v0.39.0 h1:oOyhkDq05hPZKItWVBkJ6g6AtGxi+fy7F4JvUV8uhsI= github.com/prometheus/common v0.42.0 h1:EKsfXEYo4JpWMHH5cg+KOUWeuJSov1Id8zGR8eeI1YM=
github.com/prometheus/common v0.39.0/go.mod h1:6XBZ7lYdLCbkAVhwRsWTZn+IN5AB9F/NXd5w0BbEX0Y= github.com/prometheus/common v0.42.0/go.mod h1:xBwqVerjNdUDjgODMpudtOMwlOwf2SaTr1yjz4b7Zbc=
github.com/prometheus/procfs v0.9.0 h1:wzCHvIvM5SxWqYvwgVL7yJY8Lz3PKn49KQtpgMYJfhI= github.com/prometheus/procfs v0.9.0 h1:wzCHvIvM5SxWqYvwgVL7yJY8Lz3PKn49KQtpgMYJfhI=
github.com/prometheus/procfs v0.9.0/go.mod h1:+pB4zwohETzFnmlpe6yd2lSc+0/46IYZRB/chUwxUZY= github.com/prometheus/procfs v0.9.0/go.mod h1:+pB4zwohETzFnmlpe6yd2lSc+0/46IYZRB/chUwxUZY=
github.com/rogpeppe/go-internal v1.3.0/go.mod h1:M8bDsm7K2OlrFYOpmOWEs/qY81heoFRclV5y23lUDJ4= github.com/rogpeppe/go-internal v1.3.0/go.mod h1:M8bDsm7K2OlrFYOpmOWEs/qY81heoFRclV5y23lUDJ4=
@ -275,8 +273,6 @@ github.com/smartystreets/goconvey v0.0.0-20190222223459-a17d461953aa/go.mod h1:2
github.com/smartystreets/goconvey v1.6.4/go.mod h1:syvi0/a8iFYH4r/RixwvyeAJjdLS9QV7WQ/tjFTllLA= github.com/smartystreets/goconvey v1.6.4/go.mod h1:syvi0/a8iFYH4r/RixwvyeAJjdLS9QV7WQ/tjFTllLA=
github.com/smartystreets/goconvey v1.7.2 h1:9RBaZCeXEQ3UselpuwUQHltGVXvdwm6cv1hgR6gDIPg= github.com/smartystreets/goconvey v1.7.2 h1:9RBaZCeXEQ3UselpuwUQHltGVXvdwm6cv1hgR6gDIPg=
github.com/smartystreets/goconvey v1.7.2/go.mod h1:Vw0tHAZW6lzCRk3xgdin6fKYcG+G3Pg9vgXWeJpQFMM= github.com/smartystreets/goconvey v1.7.2/go.mod h1:Vw0tHAZW6lzCRk3xgdin6fKYcG+G3Pg9vgXWeJpQFMM=
github.com/spacemonkeygo/spacelog v0.0.0-20180420211403-2296661a0572 h1:RC6RW7j+1+HkWaX/Yh71Ee5ZHaHYt7ZP4sQgUrm6cDU=
github.com/spacemonkeygo/spacelog v0.0.0-20180420211403-2296661a0572/go.mod h1:w0SWMsp6j9O/dk4/ZpIhL+3CkG8ofA2vuv7k+ltqUMc=
github.com/spaolacci/murmur3 v0.0.0-20180118202830-f09979ecbc72/go.mod h1:JwIasOWyU6f++ZhiEuf87xNszmSA2myDM2Kzu9HwQUA= github.com/spaolacci/murmur3 v0.0.0-20180118202830-f09979ecbc72/go.mod h1:JwIasOWyU6f++ZhiEuf87xNszmSA2myDM2Kzu9HwQUA=
github.com/spaolacci/murmur3 v1.1.0 h1:7c1g84S4BPRrfL5Xrdp6fOJ206sU9y293DDHaoy0bLI= github.com/spaolacci/murmur3 v1.1.0 h1:7c1g84S4BPRrfL5Xrdp6fOJ206sU9y293DDHaoy0bLI=
github.com/spaolacci/murmur3 v1.1.0/go.mod h1:JwIasOWyU6f++ZhiEuf87xNszmSA2myDM2Kzu9HwQUA= github.com/spaolacci/murmur3 v1.1.0/go.mod h1:JwIasOWyU6f++ZhiEuf87xNszmSA2myDM2Kzu9HwQUA=
@ -299,8 +295,8 @@ github.com/warpfork/go-wish v0.0.0-20200122115046-b9ea61034e4a/go.mod h1:x6AKhvS
github.com/warpfork/go-wish v0.0.0-20220906213052-39a1cc7a02d0 h1:GDDkbFiaK8jsSDJfjId/PEGEShv6ugrt4kYsC5UIDaQ= github.com/warpfork/go-wish v0.0.0-20220906213052-39a1cc7a02d0 h1:GDDkbFiaK8jsSDJfjId/PEGEShv6ugrt4kYsC5UIDaQ=
github.com/warpfork/go-wish v0.0.0-20220906213052-39a1cc7a02d0/go.mod h1:x6AKhvSSexNrVSrViXSHUEbICjmGXhtgABaHIySUSGw= github.com/warpfork/go-wish v0.0.0-20220906213052-39a1cc7a02d0/go.mod h1:x6AKhvSSexNrVSrViXSHUEbICjmGXhtgABaHIySUSGw=
github.com/whyrusleeping/cbor-gen v0.0.0-20200123233031-1cdf64d27158/go.mod h1:Xj/M2wWU+QdTdRbu/L/1dIZY8/Wb2K9pAhtroQuxJJI= github.com/whyrusleeping/cbor-gen v0.0.0-20200123233031-1cdf64d27158/go.mod h1:Xj/M2wWU+QdTdRbu/L/1dIZY8/Wb2K9pAhtroQuxJJI=
github.com/whyrusleeping/cbor-gen v0.0.0-20221220214510-0333c149dec0 h1:obKzQ1ey5AJg5NKjgtTo/CKwLImVP4ETLRcsmzFJ4Qw= github.com/whyrusleeping/cbor-gen v0.0.0-20230126041949-52956bd4c9aa h1:EyA027ZAkuaCLoxVX4r1TZMPy1d31fM6hbfQ4OU4I5o=
github.com/whyrusleeping/cbor-gen v0.0.0-20221220214510-0333c149dec0/go.mod h1:fgkXqYy7bV2cFeIEOkVTZS/WjXARfBqSH6Q2qHL33hQ= github.com/whyrusleeping/cbor-gen v0.0.0-20230126041949-52956bd4c9aa/go.mod h1:fgkXqYy7bV2cFeIEOkVTZS/WjXARfBqSH6Q2qHL33hQ=
github.com/whyrusleeping/chunker v0.0.0-20181014151217-fe64bd25879f h1:jQa4QT2UP9WYv2nzyawpKMOCl+Z/jW7djv2/J50lj9E= github.com/whyrusleeping/chunker v0.0.0-20181014151217-fe64bd25879f h1:jQa4QT2UP9WYv2nzyawpKMOCl+Z/jW7djv2/J50lj9E=
github.com/whyrusleeping/chunker v0.0.0-20181014151217-fe64bd25879f/go.mod h1:p9UJB6dDgdPgMJZs7UjUOdulKyRr9fqkS+6JKAInPy8= github.com/whyrusleeping/chunker v0.0.0-20181014151217-fe64bd25879f/go.mod h1:p9UJB6dDgdPgMJZs7UjUOdulKyRr9fqkS+6JKAInPy8=
github.com/whyrusleeping/go-logging v0.0.0-20170515211332-0457bb6b88fc/go.mod h1:bopw91TMyo8J3tvftk8xmU2kPmlrt4nScJQZU2hE5EM= github.com/whyrusleeping/go-logging v0.0.0-20170515211332-0457bb6b88fc/go.mod h1:bopw91TMyo8J3tvftk8xmU2kPmlrt4nScJQZU2hE5EM=
@ -430,8 +426,8 @@ golang.org/x/xerrors v0.0.0-20220907171357-04be3eba64a2 h1:H2TDz8ibqkAF6YGhCdN3j
golang.org/x/xerrors v0.0.0-20220907171357-04be3eba64a2/go.mod h1:K8+ghG5WaK9qNqU5K3HdILfMLy1f3aNYFI/wnl100a8= golang.org/x/xerrors v0.0.0-20220907171357-04be3eba64a2/go.mod h1:K8+ghG5WaK9qNqU5K3HdILfMLy1f3aNYFI/wnl100a8=
google.golang.org/protobuf v1.26.0-rc.1/go.mod h1:jlhhOSvTdKEhbULTjvd4ARK9grFBp09yW+WbY/TyQbw= google.golang.org/protobuf v1.26.0-rc.1/go.mod h1:jlhhOSvTdKEhbULTjvd4ARK9grFBp09yW+WbY/TyQbw=
google.golang.org/protobuf v1.26.0/go.mod h1:9q0QmTI4eRPtz6boOQmLYwt+qCgq0jsYwAQnmE0givc= google.golang.org/protobuf v1.26.0/go.mod h1:9q0QmTI4eRPtz6boOQmLYwt+qCgq0jsYwAQnmE0givc=
google.golang.org/protobuf v1.28.1 h1:d0NfwRgPtno5B1Wa6L2DAG+KivqkdutMf1UhdNx175w= google.golang.org/protobuf v1.30.0 h1:kPPoIgf3TsEvrm0PFe15JQ+570QVxYzEvvHqChK+cng=
google.golang.org/protobuf v1.28.1/go.mod h1:HV8QOd/L58Z+nl8r43ehVNZIU/HEI6OcFqwMG9pJV4I= google.golang.org/protobuf v1.30.0/go.mod h1:HV8QOd/L58Z+nl8r43ehVNZIU/HEI6OcFqwMG9pJV4I=
gopkg.in/check.v1 v0.0.0-20161208181325-20d25e280405/go.mod h1:Co6ibVJAznAaIkqp8huTwlJQCZ016jof/cbN4VW5Yz0= gopkg.in/check.v1 v0.0.0-20161208181325-20d25e280405/go.mod h1:Co6ibVJAznAaIkqp8huTwlJQCZ016jof/cbN4VW5Yz0=
gopkg.in/check.v1 v1.0.0-20180628173108-788fd7840127/go.mod h1:Co6ibVJAznAaIkqp8huTwlJQCZ016jof/cbN4VW5Yz0= gopkg.in/check.v1 v1.0.0-20180628173108-788fd7840127/go.mod h1:Co6ibVJAznAaIkqp8huTwlJQCZ016jof/cbN4VW5Yz0=
gopkg.in/check.v1 v1.0.0-20190902080502-41f04d3bba15/go.mod h1:Co6ibVJAznAaIkqp8huTwlJQCZ016jof/cbN4VW5Yz0= gopkg.in/check.v1 v1.0.0-20190902080502-41f04d3bba15/go.mod h1:Co6ibVJAznAaIkqp8huTwlJQCZ016jof/cbN4VW5Yz0=

View File

@ -42,6 +42,7 @@ type Dialer interface {
type dialer struct { type dialer struct {
transport secureservice.SecureService transport secureservice.SecureService
config net2.Config config net2.Config
nodeConf nodeconf.NodeConf
peerAddrs map[string][]string peerAddrs map[string][]string
mu sync.RWMutex mu sync.RWMutex
@ -49,7 +50,7 @@ type dialer struct {
func (d *dialer) Init(a *app.App) (err error) { func (d *dialer) Init(a *app.App) (err error) {
d.transport = a.MustComponent(secureservice.CName).(secureservice.SecureService) d.transport = a.MustComponent(secureservice.CName).(secureservice.SecureService)
d.peerAddrs = a.MustComponent(nodeconf.CName).(nodeconf.Service).GetLast().Addresses() d.nodeConf = a.MustComponent(nodeconf.CName).(nodeconf.NodeConf)
d.config = a.MustComponent("config").(net2.ConfigGetter).GetNet() d.config = a.MustComponent("config").(net2.ConfigGetter).GetNet()
return return
} }
@ -73,6 +74,17 @@ func (d *dialer) SetPeerAddrs(peerId string, addrs []string) {
d.peerAddrs[peerId] = addrs d.peerAddrs[peerId] = addrs
} }
func (d *dialer) getPeerAddrs(peerId string) ([]string, error) {
if addrs, ok := d.nodeConf.PeerAddresses(peerId); ok {
return addrs, nil
}
addrs, ok := d.peerAddrs[peerId]
if !ok || len(addrs) == 0 {
return nil, ErrArrdsNotFound
}
return addrs, nil
}
func (d *dialer) Dial(ctx context.Context, peerId string) (p peer.Peer, err error) { func (d *dialer) Dial(ctx context.Context, peerId string) (p peer.Peer, err error) {
var ctxCancel context.CancelFunc var ctxCancel context.CancelFunc
ctx, ctxCancel = context.WithTimeout(ctx, time.Second*10) ctx, ctxCancel = context.WithTimeout(ctx, time.Second*10)
@ -80,10 +92,11 @@ func (d *dialer) Dial(ctx context.Context, peerId string) (p peer.Peer, err erro
d.mu.RLock() d.mu.RLock()
defer d.mu.RUnlock() defer d.mu.RUnlock()
addrs, ok := d.peerAddrs[peerId] addrs, err := d.getPeerAddrs(peerId)
if !ok || len(addrs) == 0 { if err != nil {
return nil, ErrArrdsNotFound return
} }
var ( var (
conn drpc.Conn conn drpc.Conn
sc sec.SecureConn sc sec.SecureConn

View File

@ -6,6 +6,7 @@ import (
"github.com/anytypeio/any-sync/app/ocache" "github.com/anytypeio/any-sync/app/ocache"
"github.com/anytypeio/any-sync/net/dialer" "github.com/anytypeio/any-sync/net/dialer"
"github.com/anytypeio/any-sync/net/peer" "github.com/anytypeio/any-sync/net/peer"
"go.uber.org/zap"
"math/rand" "math/rand"
) )
@ -78,6 +79,8 @@ func (p *pool) GetOneOf(ctx context.Context, peerIds []string) (peer.Peer, error
for _, peerId := range peerIds { for _, peerId := range peerIds {
if v, err := p.cache.Get(ctx, peerId); err == nil { if v, err := p.cache.Get(ctx, peerId); err == nil {
return v.(peer.Peer), nil return v.(peer.Peer), nil
} else {
log.Debug("unable to connect", zap.String("peerId", peerId), zap.Error(err))
} }
} }
return nil, ErrUnableToConnect return nil, ErrUnableToConnect
@ -92,6 +95,8 @@ func (p *pool) DialOneOf(ctx context.Context, peerIds []string) (peer.Peer, erro
for _, peerId := range peerIds { for _, peerId := range peerIds {
if v, err := p.dialer.Dial(ctx, peerId); err == nil { if v, err := p.dialer.Dial(ctx, peerId); err == nil {
return v.(peer.Peer), nil return v.(peer.Peer), nil
} else {
log.Debug("unable to connect", zap.String("peerId", peerId), zap.Error(err))
} }
} }
return nil, ErrUnableToConnect return nil, ErrUnableToConnect

View File

@ -70,7 +70,7 @@ func (s *secureService) Init(a *app.App) (err error) {
s.nodeconf = a.MustComponent(nodeconf.CName).(nodeconf.Service) s.nodeconf = a.MustComponent(nodeconf.CName).(nodeconf.Service)
s.inboundChecker = s.noVerifyChecker s.inboundChecker = s.noVerifyChecker
confTypes := s.nodeconf.GetLast().NodeTypes(account.Account().PeerId) confTypes := s.nodeconf.NodeTypes(account.Account().PeerId)
if len(confTypes) > 0 { if len(confTypes) > 0 {
// require identity verification if we are node // require identity verification if we are node
s.inboundChecker = s.peerSignVerifier s.inboundChecker = s.peerSignVerifier
@ -116,7 +116,7 @@ func (s *secureService) SecureOutbound(ctx context.Context, conn net.Conn) (sec.
return nil, HandshakeError{err: err, remoteAddr: conn.RemoteAddr().String()} return nil, HandshakeError{err: err, remoteAddr: conn.RemoteAddr().String()}
} }
peerId := sc.RemotePeer().String() peerId := sc.RemotePeer().String()
confTypes := s.nodeconf.GetLast().NodeTypes(peerId) confTypes := s.nodeconf.NodeTypes(peerId)
var checker handshake.CredentialChecker var checker handshake.CredentialChecker
if len(confTypes) > 0 { if len(confTypes) > 0 {
checker = s.peerSignVerifier checker = s.peerSignVerifier

View File

@ -6,7 +6,9 @@ import (
"github.com/anytypeio/any-sync/app" "github.com/anytypeio/any-sync/app"
"github.com/anytypeio/any-sync/net/peer" "github.com/anytypeio/any-sync/net/peer"
"github.com/anytypeio/any-sync/nodeconf" "github.com/anytypeio/any-sync/nodeconf"
"github.com/anytypeio/any-sync/nodeconf/mock_nodeconf"
"github.com/anytypeio/any-sync/testutil/testnodeconf" "github.com/anytypeio/any-sync/testutil/testnodeconf"
"github.com/golang/mock/gomock"
"github.com/stretchr/testify/assert" "github.com/stretchr/testify/assert"
"github.com/stretchr/testify/require" "github.com/stretchr/testify/require"
"net" "net"
@ -19,7 +21,6 @@ func TestHandshake(t *testing.T) {
nc := testnodeconf.GenNodeConfig(2) nc := testnodeconf.GenNodeConfig(2)
fxS := newFixture(t, nc, nc.GetAccountService(0)) fxS := newFixture(t, nc, nc.GetAccountService(0))
defer fxS.Finish(t) defer fxS.Finish(t)
sc, cc := net.Pipe() sc, cc := net.Pipe()
type acceptRes struct { type acceptRes struct {
@ -53,20 +54,28 @@ func TestHandshake(t *testing.T) {
func newFixture(t *testing.T, nc *testnodeconf.Config, acc accountservice.Service) *fixture { func newFixture(t *testing.T, nc *testnodeconf.Config, acc accountservice.Service) *fixture {
fx := &fixture{ fx := &fixture{
ctrl: gomock.NewController(t),
secureService: New().(*secureService), secureService: New().(*secureService),
acc: acc, acc: acc,
a: new(app.App), a: new(app.App),
} }
fx.mockNodeConf = mock_nodeconf.NewMockService(fx.ctrl)
fx.a.Register(fx.acc).Register(nc).Register(nodeconf.New()).Register(fx.secureService) fx.mockNodeConf.EXPECT().Init(gomock.Any())
fx.mockNodeConf.EXPECT().Name().Return(nodeconf.CName).AnyTimes()
fx.mockNodeConf.EXPECT().Run(ctx)
fx.mockNodeConf.EXPECT().Close(ctx)
fx.mockNodeConf.EXPECT().NodeTypes(gomock.Any()).Return([]nodeconf.NodeType{nodeconf.NodeTypeTree}).AnyTimes()
fx.a.Register(fx.acc).Register(nc).Register(fx.mockNodeConf).Register(fx.secureService)
require.NoError(t, fx.a.Start(ctx)) require.NoError(t, fx.a.Start(ctx))
return fx return fx
} }
type fixture struct { type fixture struct {
*secureService *secureService
a *app.App a *app.App
acc accountservice.Service acc accountservice.Service
ctrl *gomock.Controller
mockNodeConf *mock_nodeconf.MockService
} }
func (fx *fixture) Finish(t *testing.T) { func (fx *fixture) Finish(t *testing.T) {

View File

@ -1,5 +1,18 @@
package nodeconf package nodeconf
import (
"errors"
"time"
)
type ConfigGetter interface {
GetNodeConf() Configuration
}
var (
ErrConfigurationNotFound = errors.New("node nodeConf not found")
)
type NodeType string type NodeType string
const ( const (
@ -10,17 +23,21 @@ const (
NodeTypeCoordinator NodeType = "coordinator" NodeTypeCoordinator NodeType = "coordinator"
) )
type configGetter interface { type Node struct {
GetNodes() []NodeConfig PeerId string `yaml:"peerId" bson:"peerId"`
Addresses []string `yaml:"addresses" bson:"addresses"`
Types []NodeType `yaml:"types,omitempty" bson:"types"`
} }
type NodeConfig struct { func (n Node) Id() string {
PeerId string `yaml:"peerId"` return n.PeerId
Addresses []string `yaml:"address"`
Types []NodeType `yaml:"types,omitempty"`
} }
func (n NodeConfig) HasType(t NodeType) bool { func (n Node) Capacity() float64 {
return 1
}
func (n Node) HasType(t NodeType) bool {
for _, nt := range n.Types { for _, nt := range n.Types {
if nt == t { if nt == t {
return true return true
@ -28,3 +45,10 @@ func (n NodeConfig) HasType(t NodeType) bool {
} }
return false return false
} }
type Configuration struct {
Id string `yaml:"id"`
NetworkId string `yaml:"networkId"`
Nodes []Node `yaml:"nodes"`
CreationTime time.Time `yaml:"creationTime"`
}

View File

@ -1,10 +1,11 @@
// Code generated by MockGen. DO NOT EDIT. // Code generated by MockGen. DO NOT EDIT.
// Source: github.com/anytypeio/any-sync/nodeconf (interfaces: Service,Configuration) // Source: github.com/anytypeio/any-sync/nodeconf (interfaces: Service)
// Package mock_nodeconf is a generated GoMock package. // Package mock_nodeconf is a generated GoMock package.
package mock_nodeconf package mock_nodeconf
import ( import (
context "context"
reflect "reflect" reflect "reflect"
app "github.com/anytypeio/any-sync/app" app "github.com/anytypeio/any-sync/app"
@ -36,32 +37,102 @@ func (m *MockService) EXPECT() *MockServiceMockRecorder {
return m.recorder return m.recorder
} }
// GetById mocks base method. // CHash mocks base method.
func (m *MockService) GetById(arg0 string) nodeconf.Configuration { func (m *MockService) CHash() chash.CHash {
m.ctrl.T.Helper() m.ctrl.T.Helper()
ret := m.ctrl.Call(m, "GetById", arg0) ret := m.ctrl.Call(m, "CHash")
ret0, _ := ret[0].(chash.CHash)
return ret0
}
// CHash indicates an expected call of CHash.
func (mr *MockServiceMockRecorder) CHash() *gomock.Call {
mr.mock.ctrl.T.Helper()
return mr.mock.ctrl.RecordCallWithMethodType(mr.mock, "CHash", reflect.TypeOf((*MockService)(nil).CHash))
}
// Close mocks base method.
func (m *MockService) Close(arg0 context.Context) error {
m.ctrl.T.Helper()
ret := m.ctrl.Call(m, "Close", arg0)
ret0, _ := ret[0].(error)
return ret0
}
// Close indicates an expected call of Close.
func (mr *MockServiceMockRecorder) Close(arg0 interface{}) *gomock.Call {
mr.mock.ctrl.T.Helper()
return mr.mock.ctrl.RecordCallWithMethodType(mr.mock, "Close", reflect.TypeOf((*MockService)(nil).Close), arg0)
}
// Configuration mocks base method.
func (m *MockService) Configuration() nodeconf.Configuration {
m.ctrl.T.Helper()
ret := m.ctrl.Call(m, "Configuration")
ret0, _ := ret[0].(nodeconf.Configuration) ret0, _ := ret[0].(nodeconf.Configuration)
return ret0 return ret0
} }
// GetById indicates an expected call of GetById. // Configuration indicates an expected call of Configuration.
func (mr *MockServiceMockRecorder) GetById(arg0 interface{}) *gomock.Call { func (mr *MockServiceMockRecorder) Configuration() *gomock.Call {
mr.mock.ctrl.T.Helper() mr.mock.ctrl.T.Helper()
return mr.mock.ctrl.RecordCallWithMethodType(mr.mock, "GetById", reflect.TypeOf((*MockService)(nil).GetById), arg0) return mr.mock.ctrl.RecordCallWithMethodType(mr.mock, "Configuration", reflect.TypeOf((*MockService)(nil).Configuration))
} }
// GetLast mocks base method. // ConsensusPeers mocks base method.
func (m *MockService) GetLast() nodeconf.Configuration { func (m *MockService) ConsensusPeers() []string {
m.ctrl.T.Helper() m.ctrl.T.Helper()
ret := m.ctrl.Call(m, "GetLast") ret := m.ctrl.Call(m, "ConsensusPeers")
ret0, _ := ret[0].(nodeconf.Configuration) ret0, _ := ret[0].([]string)
return ret0 return ret0
} }
// GetLast indicates an expected call of GetLast. // ConsensusPeers indicates an expected call of ConsensusPeers.
func (mr *MockServiceMockRecorder) GetLast() *gomock.Call { func (mr *MockServiceMockRecorder) ConsensusPeers() *gomock.Call {
mr.mock.ctrl.T.Helper() mr.mock.ctrl.T.Helper()
return mr.mock.ctrl.RecordCallWithMethodType(mr.mock, "GetLast", reflect.TypeOf((*MockService)(nil).GetLast)) return mr.mock.ctrl.RecordCallWithMethodType(mr.mock, "ConsensusPeers", reflect.TypeOf((*MockService)(nil).ConsensusPeers))
}
// CoordinatorPeers mocks base method.
func (m *MockService) CoordinatorPeers() []string {
m.ctrl.T.Helper()
ret := m.ctrl.Call(m, "CoordinatorPeers")
ret0, _ := ret[0].([]string)
return ret0
}
// CoordinatorPeers indicates an expected call of CoordinatorPeers.
func (mr *MockServiceMockRecorder) CoordinatorPeers() *gomock.Call {
mr.mock.ctrl.T.Helper()
return mr.mock.ctrl.RecordCallWithMethodType(mr.mock, "CoordinatorPeers", reflect.TypeOf((*MockService)(nil).CoordinatorPeers))
}
// FilePeers mocks base method.
func (m *MockService) FilePeers() []string {
m.ctrl.T.Helper()
ret := m.ctrl.Call(m, "FilePeers")
ret0, _ := ret[0].([]string)
return ret0
}
// FilePeers indicates an expected call of FilePeers.
func (mr *MockServiceMockRecorder) FilePeers() *gomock.Call {
mr.mock.ctrl.T.Helper()
return mr.mock.ctrl.RecordCallWithMethodType(mr.mock, "FilePeers", reflect.TypeOf((*MockService)(nil).FilePeers))
}
// Id mocks base method.
func (m *MockService) Id() string {
m.ctrl.T.Helper()
ret := m.ctrl.Call(m, "Id")
ret0, _ := ret[0].(string)
return ret0
}
// Id indicates an expected call of Id.
func (mr *MockServiceMockRecorder) Id() *gomock.Call {
mr.mock.ctrl.T.Helper()
return mr.mock.ctrl.RecordCallWithMethodType(mr.mock, "Id", reflect.TypeOf((*MockService)(nil).Id))
} }
// Init mocks base method. // Init mocks base method.
@ -78,6 +149,20 @@ func (mr *MockServiceMockRecorder) Init(arg0 interface{}) *gomock.Call {
return mr.mock.ctrl.RecordCallWithMethodType(mr.mock, "Init", reflect.TypeOf((*MockService)(nil).Init), arg0) return mr.mock.ctrl.RecordCallWithMethodType(mr.mock, "Init", reflect.TypeOf((*MockService)(nil).Init), arg0)
} }
// IsResponsible mocks base method.
func (m *MockService) IsResponsible(arg0 string) bool {
m.ctrl.T.Helper()
ret := m.ctrl.Call(m, "IsResponsible", arg0)
ret0, _ := ret[0].(bool)
return ret0
}
// IsResponsible indicates an expected call of IsResponsible.
func (mr *MockServiceMockRecorder) IsResponsible(arg0 interface{}) *gomock.Call {
mr.mock.ctrl.T.Helper()
return mr.mock.ctrl.RecordCallWithMethodType(mr.mock, "IsResponsible", reflect.TypeOf((*MockService)(nil).IsResponsible), arg0)
}
// Name mocks base method. // Name mocks base method.
func (m *MockService) Name() string { func (m *MockService) Name() string {
m.ctrl.T.Helper() m.ctrl.T.Helper()
@ -92,129 +177,8 @@ func (mr *MockServiceMockRecorder) Name() *gomock.Call {
return mr.mock.ctrl.RecordCallWithMethodType(mr.mock, "Name", reflect.TypeOf((*MockService)(nil).Name)) return mr.mock.ctrl.RecordCallWithMethodType(mr.mock, "Name", reflect.TypeOf((*MockService)(nil).Name))
} }
// MockConfiguration is a mock of Configuration interface.
type MockConfiguration struct {
ctrl *gomock.Controller
recorder *MockConfigurationMockRecorder
}
// MockConfigurationMockRecorder is the mock recorder for MockConfiguration.
type MockConfigurationMockRecorder struct {
mock *MockConfiguration
}
// NewMockConfiguration creates a new mock instance.
func NewMockConfiguration(ctrl *gomock.Controller) *MockConfiguration {
mock := &MockConfiguration{ctrl: ctrl}
mock.recorder = &MockConfigurationMockRecorder{mock}
return mock
}
// EXPECT returns an object that allows the caller to indicate expected use.
func (m *MockConfiguration) EXPECT() *MockConfigurationMockRecorder {
return m.recorder
}
// Addresses mocks base method.
func (m *MockConfiguration) Addresses() map[string][]string {
m.ctrl.T.Helper()
ret := m.ctrl.Call(m, "Addresses")
ret0, _ := ret[0].(map[string][]string)
return ret0
}
// Addresses indicates an expected call of Addresses.
func (mr *MockConfigurationMockRecorder) Addresses() *gomock.Call {
mr.mock.ctrl.T.Helper()
return mr.mock.ctrl.RecordCallWithMethodType(mr.mock, "Addresses", reflect.TypeOf((*MockConfiguration)(nil).Addresses))
}
// CHash mocks base method.
func (m *MockConfiguration) CHash() chash.CHash {
m.ctrl.T.Helper()
ret := m.ctrl.Call(m, "CHash")
ret0, _ := ret[0].(chash.CHash)
return ret0
}
// CHash indicates an expected call of CHash.
func (mr *MockConfigurationMockRecorder) CHash() *gomock.Call {
mr.mock.ctrl.T.Helper()
return mr.mock.ctrl.RecordCallWithMethodType(mr.mock, "CHash", reflect.TypeOf((*MockConfiguration)(nil).CHash))
}
// ConsensusPeers mocks base method.
func (m *MockConfiguration) ConsensusPeers() []string {
m.ctrl.T.Helper()
ret := m.ctrl.Call(m, "ConsensusPeers")
ret0, _ := ret[0].([]string)
return ret0
}
// ConsensusPeers indicates an expected call of ConsensusPeers.
func (mr *MockConfigurationMockRecorder) ConsensusPeers() *gomock.Call {
mr.mock.ctrl.T.Helper()
return mr.mock.ctrl.RecordCallWithMethodType(mr.mock, "ConsensusPeers", reflect.TypeOf((*MockConfiguration)(nil).ConsensusPeers))
}
// CoordinatorPeers mocks base method.
func (m *MockConfiguration) CoordinatorPeers() []string {
m.ctrl.T.Helper()
ret := m.ctrl.Call(m, "CoordinatorPeers")
ret0, _ := ret[0].([]string)
return ret0
}
// CoordinatorPeers indicates an expected call of CoordinatorPeers.
func (mr *MockConfigurationMockRecorder) CoordinatorPeers() *gomock.Call {
mr.mock.ctrl.T.Helper()
return mr.mock.ctrl.RecordCallWithMethodType(mr.mock, "CoordinatorPeers", reflect.TypeOf((*MockConfiguration)(nil).CoordinatorPeers))
}
// FilePeers mocks base method.
func (m *MockConfiguration) FilePeers() []string {
m.ctrl.T.Helper()
ret := m.ctrl.Call(m, "FilePeers")
ret0, _ := ret[0].([]string)
return ret0
}
// FilePeers indicates an expected call of FilePeers.
func (mr *MockConfigurationMockRecorder) FilePeers() *gomock.Call {
mr.mock.ctrl.T.Helper()
return mr.mock.ctrl.RecordCallWithMethodType(mr.mock, "FilePeers", reflect.TypeOf((*MockConfiguration)(nil).FilePeers))
}
// Id mocks base method.
func (m *MockConfiguration) Id() string {
m.ctrl.T.Helper()
ret := m.ctrl.Call(m, "Id")
ret0, _ := ret[0].(string)
return ret0
}
// Id indicates an expected call of Id.
func (mr *MockConfigurationMockRecorder) Id() *gomock.Call {
mr.mock.ctrl.T.Helper()
return mr.mock.ctrl.RecordCallWithMethodType(mr.mock, "Id", reflect.TypeOf((*MockConfiguration)(nil).Id))
}
// IsResponsible mocks base method.
func (m *MockConfiguration) IsResponsible(arg0 string) bool {
m.ctrl.T.Helper()
ret := m.ctrl.Call(m, "IsResponsible", arg0)
ret0, _ := ret[0].(bool)
return ret0
}
// IsResponsible indicates an expected call of IsResponsible.
func (mr *MockConfigurationMockRecorder) IsResponsible(arg0 interface{}) *gomock.Call {
mr.mock.ctrl.T.Helper()
return mr.mock.ctrl.RecordCallWithMethodType(mr.mock, "IsResponsible", reflect.TypeOf((*MockConfiguration)(nil).IsResponsible), arg0)
}
// NodeIds mocks base method. // NodeIds mocks base method.
func (m *MockConfiguration) NodeIds(arg0 string) []string { func (m *MockService) NodeIds(arg0 string) []string {
m.ctrl.T.Helper() m.ctrl.T.Helper()
ret := m.ctrl.Call(m, "NodeIds", arg0) ret := m.ctrl.Call(m, "NodeIds", arg0)
ret0, _ := ret[0].([]string) ret0, _ := ret[0].([]string)
@ -222,13 +186,13 @@ func (m *MockConfiguration) NodeIds(arg0 string) []string {
} }
// NodeIds indicates an expected call of NodeIds. // NodeIds indicates an expected call of NodeIds.
func (mr *MockConfigurationMockRecorder) NodeIds(arg0 interface{}) *gomock.Call { func (mr *MockServiceMockRecorder) NodeIds(arg0 interface{}) *gomock.Call {
mr.mock.ctrl.T.Helper() mr.mock.ctrl.T.Helper()
return mr.mock.ctrl.RecordCallWithMethodType(mr.mock, "NodeIds", reflect.TypeOf((*MockConfiguration)(nil).NodeIds), arg0) return mr.mock.ctrl.RecordCallWithMethodType(mr.mock, "NodeIds", reflect.TypeOf((*MockService)(nil).NodeIds), arg0)
} }
// NodeTypes mocks base method. // NodeTypes mocks base method.
func (m *MockConfiguration) NodeTypes(arg0 string) []nodeconf.NodeType { func (m *MockService) NodeTypes(arg0 string) []nodeconf.NodeType {
m.ctrl.T.Helper() m.ctrl.T.Helper()
ret := m.ctrl.Call(m, "NodeTypes", arg0) ret := m.ctrl.Call(m, "NodeTypes", arg0)
ret0, _ := ret[0].([]nodeconf.NodeType) ret0, _ := ret[0].([]nodeconf.NodeType)
@ -236,13 +200,13 @@ func (m *MockConfiguration) NodeTypes(arg0 string) []nodeconf.NodeType {
} }
// NodeTypes indicates an expected call of NodeTypes. // NodeTypes indicates an expected call of NodeTypes.
func (mr *MockConfigurationMockRecorder) NodeTypes(arg0 interface{}) *gomock.Call { func (mr *MockServiceMockRecorder) NodeTypes(arg0 interface{}) *gomock.Call {
mr.mock.ctrl.T.Helper() mr.mock.ctrl.T.Helper()
return mr.mock.ctrl.RecordCallWithMethodType(mr.mock, "NodeTypes", reflect.TypeOf((*MockConfiguration)(nil).NodeTypes), arg0) return mr.mock.ctrl.RecordCallWithMethodType(mr.mock, "NodeTypes", reflect.TypeOf((*MockService)(nil).NodeTypes), arg0)
} }
// Partition mocks base method. // Partition mocks base method.
func (m *MockConfiguration) Partition(arg0 string) int { func (m *MockService) Partition(arg0 string) int {
m.ctrl.T.Helper() m.ctrl.T.Helper()
ret := m.ctrl.Call(m, "Partition", arg0) ret := m.ctrl.Call(m, "Partition", arg0)
ret0, _ := ret[0].(int) ret0, _ := ret[0].(int)
@ -250,7 +214,36 @@ func (m *MockConfiguration) Partition(arg0 string) int {
} }
// Partition indicates an expected call of Partition. // Partition indicates an expected call of Partition.
func (mr *MockConfigurationMockRecorder) Partition(arg0 interface{}) *gomock.Call { func (mr *MockServiceMockRecorder) Partition(arg0 interface{}) *gomock.Call {
mr.mock.ctrl.T.Helper() mr.mock.ctrl.T.Helper()
return mr.mock.ctrl.RecordCallWithMethodType(mr.mock, "Partition", reflect.TypeOf((*MockConfiguration)(nil).Partition), arg0) return mr.mock.ctrl.RecordCallWithMethodType(mr.mock, "Partition", reflect.TypeOf((*MockService)(nil).Partition), arg0)
}
// PeerAddresses mocks base method.
func (m *MockService) PeerAddresses(arg0 string) ([]string, bool) {
m.ctrl.T.Helper()
ret := m.ctrl.Call(m, "PeerAddresses", arg0)
ret0, _ := ret[0].([]string)
ret1, _ := ret[1].(bool)
return ret0, ret1
}
// PeerAddresses indicates an expected call of PeerAddresses.
func (mr *MockServiceMockRecorder) PeerAddresses(arg0 interface{}) *gomock.Call {
mr.mock.ctrl.T.Helper()
return mr.mock.ctrl.RecordCallWithMethodType(mr.mock, "PeerAddresses", reflect.TypeOf((*MockService)(nil).PeerAddresses), arg0)
}
// Run mocks base method.
func (m *MockService) Run(arg0 context.Context) error {
m.ctrl.T.Helper()
ret := m.ctrl.Call(m, "Run", arg0)
ret0, _ := ret[0].(error)
return ret0
}
// Run indicates an expected call of Run.
func (mr *MockServiceMockRecorder) Run(arg0 interface{}) *gomock.Call {
mr.mock.ctrl.T.Helper()
return mr.mock.ctrl.RecordCallWithMethodType(mr.mock, "Run", reflect.TypeOf((*MockService)(nil).Run), arg0)
} }

View File

@ -1,4 +1,4 @@
//go:generate mockgen -destination mock_nodeconf/mock_nodeconf.go github.com/anytypeio/any-sync/nodeconf Service,Configuration //go:generate mockgen -destination mock_nodeconf/mock_nodeconf.go github.com/anytypeio/any-sync/nodeconf Service
package nodeconf package nodeconf
import ( import (
@ -6,9 +6,11 @@ import (
"strings" "strings"
) )
type Configuration interface { type NodeConf interface {
// Id returns current nodeconf id // Id returns current nodeconf id
Id() string Id() string
// Configuration returns configuration struct
Configuration() Configuration
// NodeIds returns list of peerId for given spaceId // NodeIds returns list of peerId for given spaceId
NodeIds(spaceId string) []string NodeIds(spaceId string) []string
// IsResponsible checks if current account responsible for given spaceId // IsResponsible checks if current account responsible for given spaceId
@ -19,8 +21,8 @@ type Configuration interface {
ConsensusPeers() []string ConsensusPeers() []string
// CoordinatorPeers returns list of coordinator nodes // CoordinatorPeers returns list of coordinator nodes
CoordinatorPeers() []string CoordinatorPeers() []string
// Addresses returns map[peerId][]addr with connection addresses for all known nodes // PeerAddresses returns peer addresses by peer id
Addresses() map[string][]string PeerAddresses(peerId string) (addrs []string, ok bool)
// CHash returns nodes consistent table // CHash returns nodes consistent table
CHash() chash.CHash CHash() chash.CHash
// Partition returns partition number by spaceId // Partition returns partition number by spaceId
@ -29,21 +31,27 @@ type Configuration interface {
NodeTypes(nodeId string) []NodeType NodeTypes(nodeId string) []NodeType
} }
type configuration struct { type nodeConf struct {
id string id string
accountId string accountId string
filePeers []string filePeers []string
consensusPeers []string consensusPeers []string
coordinatorPeers []string coordinatorPeers []string
chash chash.CHash chash chash.CHash
allMembers []NodeConfig allMembers []Node
c Configuration
addrs map[string][]string
} }
func (c *configuration) Id() string { func (c *nodeConf) Id() string {
return c.id return c.id
} }
func (c *configuration) NodeIds(spaceId string) []string { func (c *nodeConf) Configuration() Configuration {
return c.c
}
func (c *nodeConf) NodeIds(spaceId string) []string {
members := c.chash.GetMembers(ReplKey(spaceId)) members := c.chash.GetMembers(ReplKey(spaceId))
res := make([]string, 0, len(members)) res := make([]string, 0, len(members))
for _, m := range members { for _, m := range members {
@ -54,7 +62,7 @@ func (c *configuration) NodeIds(spaceId string) []string {
return res return res
} }
func (c *configuration) IsResponsible(spaceId string) bool { func (c *nodeConf) IsResponsible(spaceId string) bool {
for _, m := range c.chash.GetMembers(ReplKey(spaceId)) { for _, m := range c.chash.GetMembers(ReplKey(spaceId)) {
if m.Id() == c.accountId { if m.Id() == c.accountId {
return true return true
@ -63,35 +71,32 @@ func (c *configuration) IsResponsible(spaceId string) bool {
return false return false
} }
func (c *configuration) FilePeers() []string { func (c *nodeConf) FilePeers() []string {
return c.filePeers return c.filePeers
} }
func (c *configuration) ConsensusPeers() []string { func (c *nodeConf) ConsensusPeers() []string {
return c.consensusPeers return c.consensusPeers
} }
func (c *configuration) CoordinatorPeers() []string { func (c *nodeConf) CoordinatorPeers() []string {
return c.coordinatorPeers return c.coordinatorPeers
} }
func (c *configuration) Addresses() map[string][]string { func (c *nodeConf) PeerAddresses(peerId string) (addrs []string, ok bool) {
res := make(map[string][]string) addrs, ok = c.addrs[peerId]
for _, m := range c.allMembers { return
res[m.PeerId] = m.Addresses
}
return res
} }
func (c *configuration) CHash() chash.CHash { func (c *nodeConf) CHash() chash.CHash {
return c.chash return c.chash
} }
func (c *configuration) Partition(spaceId string) (part int) { func (c *nodeConf) Partition(spaceId string) (part int) {
return c.chash.GetPartition(ReplKey(spaceId)) return c.chash.GetPartition(ReplKey(spaceId))
} }
func (c *configuration) NodeTypes(nodeId string) []NodeType { func (c *nodeConf) NodeTypes(nodeId string) []NodeType {
for _, m := range c.allMembers { for _, m := range c.allMembers {
if m.PeerId == nodeId { if m.PeerId == nodeId {
return m.Types return m.Types

View File

@ -21,7 +21,7 @@ func TestConfiguration_NodeIds(t *testing.T) {
ReplicationFactor: ReplicationFactor, ReplicationFactor: ReplicationFactor,
}) })
require.NoError(t, err) require.NoError(t, err)
conf := &configuration{ conf := &nodeConf{
id: "last", id: "last",
accountId: "1", accountId: "1",
chash: ch, chash: ch,

View File

@ -0,0 +1,65 @@
package nodeconfstore
import (
"context"
"github.com/anytypeio/any-sync/app"
"github.com/anytypeio/any-sync/nodeconf"
"gopkg.in/yaml.v3"
"os"
"path/filepath"
"sync"
)
func New() NodeConfStore {
return new(nodeConfStore)
}
type NodeConfStore interface {
app.Component
nodeconf.Store
}
type nodeConfStore struct {
path string
mu sync.Mutex
}
type configGetter interface {
GetNodeConfStorePath() string
}
func (n *nodeConfStore) Init(a *app.App) (err error) {
n.path = a.MustComponent("config").(configGetter).GetNodeConfStorePath()
if e := os.Mkdir(n.path, 0755); e != nil && !os.IsExist(e) {
return e
}
return
}
func (n *nodeConfStore) Name() (name string) {
return nodeconf.CNameStore
}
func (n *nodeConfStore) GetLast(ctx context.Context, netId string) (c nodeconf.Configuration, err error) {
n.mu.Lock()
defer n.mu.Unlock()
path := filepath.Join(n.path, netId+".yml")
data, err := os.ReadFile(path)
if os.IsNotExist(err) {
err = nodeconf.ErrConfigurationNotFound
return
}
err = yaml.Unmarshal(data, &c)
return
}
func (n *nodeConfStore) SaveLast(ctx context.Context, c nodeconf.Configuration) (err error) {
n.mu.Lock()
defer n.mu.Unlock()
path := filepath.Join(n.path, c.NetworkId+".yml")
data, err := yaml.Marshal(c)
if err != nil {
return
}
return os.WriteFile(path, data, 0755)
}

View File

@ -0,0 +1,87 @@
package nodeconfstore
import (
"context"
"github.com/anytypeio/any-sync/app"
"github.com/anytypeio/any-sync/nodeconf"
"github.com/stretchr/testify/assert"
"github.com/stretchr/testify/require"
"os"
"path/filepath"
"testing"
"time"
)
var ctx = context.Background()
func TestNodeConfStore_GetLast(t *testing.T) {
t.Run("not found", func(t *testing.T) {
fx := newFixture(t)
defer fx.finish(t)
_, err := fx.GetLast(ctx, "123")
assert.EqualError(t, err, nodeconf.ErrConfigurationNotFound.Error())
})
t.Run("success", func(t *testing.T) {
fx := newFixture(t)
defer fx.finish(t)
c := nodeconf.Configuration{
Id: "123",
NetworkId: "456",
Nodes: []nodeconf.Node{
{
PeerId: "peerId",
Addresses: []string{"addr1", "addr2"},
Types: []nodeconf.NodeType{nodeconf.NodeTypeTree, nodeconf.NodeTypeCoordinator},
},
},
CreationTime: time.Now().Round(time.Second),
}
require.NoError(t, fx.SaveLast(ctx, c))
res, err := fx.GetLast(ctx, "456")
require.NoError(t, err)
assert.Equal(t, c.CreationTime.Unix(), res.CreationTime.Unix())
c.CreationTime = res.CreationTime
assert.Equal(t, c, res)
})
}
type fixture struct {
NodeConfStore
tmpPath string
a *app.App
}
func newFixture(t *testing.T) *fixture {
fx := &fixture{
NodeConfStore: New(),
a: new(app.App),
}
var err error
fx.tmpPath, err = os.MkdirTemp("", "")
require.NoError(t, err)
fx.a.Register(config{path: fx.tmpPath}).Register(fx.NodeConfStore)
require.NoError(t, fx.a.Start(ctx))
return fx
}
func (fx *fixture) finish(t *testing.T) {
defer os.RemoveAll(fx.tmpPath)
require.NoError(t, fx.a.Close(ctx))
}
type config struct {
path string
}
func (c config) GetNodeConfStorePath() string {
return filepath.Join(c.path, "nodeconf")
}
func (c config) Init(a *app.App) (err error) {
return
}
func (c config) Name() (name string) {
return "config"
}

View File

@ -1,12 +1,14 @@
package nodeconf package nodeconf
import ( import (
"context"
commonaccount "github.com/anytypeio/any-sync/accountservice" commonaccount "github.com/anytypeio/any-sync/accountservice"
"github.com/anytypeio/any-sync/app" "github.com/anytypeio/any-sync/app"
"github.com/anytypeio/any-sync/app/logger" "github.com/anytypeio/any-sync/app/logger"
"github.com/anytypeio/any-sync/util/crypto" "github.com/anytypeio/any-sync/util/periodicsync"
"github.com/anytypeio/go-chash" "github.com/anytypeio/go-chash"
"github.com/libp2p/go-libp2p/core/peer" "go.uber.org/zap"
"sync"
) )
const CName = "common.nodeconf" const CName = "common.nodeconf"
@ -23,109 +25,182 @@ func New() Service {
} }
type Service interface { type Service interface {
GetLast() Configuration NodeConf
GetById(id string) Configuration app.ComponentRunnable
app.Component
} }
type service struct { type service struct {
accountId string accountId string
last Configuration config Configuration
} source Source
store Store
type Node struct { last NodeConf
Addresses []string mu sync.RWMutex
PeerId string sync periodicsync.PeriodicSync
SigningKey crypto.PubKey
}
func (n *Node) Id() string {
return n.PeerId
}
func (n *Node) Capacity() float64 {
return 1
} }
func (s *service) Init(a *app.App) (err error) { func (s *service) Init(a *app.App) (err error) {
nodesConf := a.MustComponent("config").(configGetter).GetNodes() s.config = a.MustComponent("config").(ConfigGetter).GetNodeConf()
s.accountId = a.MustComponent(commonaccount.CName).(commonaccount.Service).Account().PeerId s.accountId = a.MustComponent(commonaccount.CName).(commonaccount.Service).Account().PeerId
s.source = a.MustComponent(CNameSource).(Source)
fileConfig := &configuration{ s.store = a.MustComponent(CNameStore).(Store)
id: "config", lastStored, err := s.store.GetLast(context.Background(), s.config.NetworkId)
accountId: s.accountId, if err == ErrConfigurationNotFound {
lastStored = s.config
err = nil
} }
if fileConfig.chash, err = chash.New(chash.Config{ s.sync = periodicsync.NewPeriodicSync(600, 0, func(ctx context.Context) (err error) {
PartitionCount: PartitionCount, err = s.updateConfiguration(ctx)
ReplicationFactor: ReplicationFactor, if err != nil {
}); err != nil { if err == ErrConfigurationNotChanged {
return err = nil
}
members := make([]chash.Member, 0, len(nodesConf))
for _, n := range nodesConf {
if n.HasType(NodeTypeTree) {
var member *Node
member, err = nodeFromConfigNode(n)
if err != nil {
return
} }
members = append(members, member)
} }
if n.HasType(NodeTypeConsensus) {
fileConfig.consensusPeers = append(fileConfig.consensusPeers, n.PeerId)
}
if n.HasType(NodeTypeFile) {
fileConfig.filePeers = append(fileConfig.filePeers, n.PeerId)
}
if n.HasType(NodeTypeCoordinator) {
fileConfig.coordinatorPeers = append(fileConfig.coordinatorPeers, n.PeerId)
}
fileConfig.allMembers = append(fileConfig.allMembers, n)
}
if err = fileConfig.chash.AddMembers(members...); err != nil {
return return
} }, log)
s.last = fileConfig return s.setLastConfiguration(lastStored)
return
} }
func (s *service) Name() (name string) { func (s *service) Name() (name string) {
return CName return CName
} }
func (s *service) GetLast() Configuration { func (s *service) Run(_ context.Context) (err error) {
return s.last s.sync.Run()
return
} }
func (s *service) GetById(id string) Configuration { func (s *service) updateConfiguration(ctx context.Context) (err error) {
//TODO implement me last, err := s.source.GetLast(ctx, s.Configuration().Id)
panic("implement me") if err != nil {
return
}
if err = s.store.SaveLast(ctx, last); err != nil {
return
}
return s.setLastConfiguration(last)
} }
func nodeFromConfigNode(n NodeConfig) (*Node, error) { func (s *service) setLastConfiguration(c Configuration) (err error) {
p, err := peer.Decode(n.PeerId) s.mu.Lock()
if err != nil { defer s.mu.Unlock()
return nil, err if s.last != nil && s.last.Id() == c.Id {
} return
ic, err := p.ExtractPublicKey()
if err != nil {
return nil, err
} }
icRaw, err := ic.Raw() nc := &nodeConf{
if err != nil { id: c.Id,
return nil, err c: c,
accountId: s.accountId,
addrs: map[string][]string{},
}
if nc.chash, err = chash.New(chash.Config{
PartitionCount: PartitionCount,
ReplicationFactor: ReplicationFactor,
}); err != nil {
return
} }
sigPubKey, err := crypto.UnmarshalEd25519PublicKey(icRaw) members := make([]chash.Member, 0, len(c.Nodes))
if err != nil { for _, n := range c.Nodes {
return nil, err if n.HasType(NodeTypeTree) {
members = append(members, n)
}
if n.HasType(NodeTypeConsensus) {
nc.consensusPeers = append(nc.consensusPeers, n.PeerId)
}
if n.HasType(NodeTypeFile) {
nc.filePeers = append(nc.filePeers, n.PeerId)
}
if n.HasType(NodeTypeCoordinator) {
nc.coordinatorPeers = append(nc.coordinatorPeers, n.PeerId)
}
nc.allMembers = append(nc.allMembers, n)
nc.addrs[n.PeerId] = n.Addresses
} }
if err = nc.chash.AddMembers(members...); err != nil {
return &Node{ return
Addresses: n.Addresses, }
PeerId: n.PeerId, var beforeId = ""
SigningKey: sigPubKey, if s.last != nil {
}, nil beforeId = s.last.Id()
}
if s.last != nil {
log.Info("net configuration changed", zap.String("before", beforeId), zap.String("after", nc.Id()))
} else {
log.Info("net configuration applied", zap.String("netId", nc.Configuration().NetworkId), zap.String("id", nc.Id()))
}
s.last = nc
return
}
func (s *service) Id() string {
s.mu.RLock()
defer s.mu.RUnlock()
return s.last.Id()
}
func (s *service) Configuration() Configuration {
s.mu.RLock()
defer s.mu.RUnlock()
return s.last.Configuration()
}
func (s *service) NodeIds(spaceId string) []string {
s.mu.RLock()
defer s.mu.RUnlock()
return s.last.NodeIds(spaceId)
}
func (s *service) IsResponsible(spaceId string) bool {
s.mu.RLock()
defer s.mu.RUnlock()
return s.last.IsResponsible(spaceId)
}
func (s *service) FilePeers() []string {
s.mu.RLock()
defer s.mu.RUnlock()
return s.last.FilePeers()
}
func (s *service) ConsensusPeers() []string {
s.mu.RLock()
defer s.mu.RUnlock()
return s.last.ConsensusPeers()
}
func (s *service) CoordinatorPeers() []string {
s.mu.RLock()
defer s.mu.RUnlock()
return s.last.CoordinatorPeers()
}
func (s *service) PeerAddresses(peerId string) ([]string, bool) {
s.mu.RLock()
defer s.mu.RUnlock()
return s.last.PeerAddresses(peerId)
}
func (s *service) CHash() chash.CHash {
s.mu.RLock()
defer s.mu.RUnlock()
return s.last.CHash()
}
func (s *service) Partition(spaceId string) (part int) {
s.mu.RLock()
defer s.mu.RUnlock()
return s.last.Partition(spaceId)
}
func (s *service) NodeTypes(nodeId string) []NodeType {
s.mu.RLock()
defer s.mu.RUnlock()
return s.last.NodeTypes(nodeId)
}
func (s *service) Close(ctx context.Context) (err error) {
s.sync.Close()
return
} }

16
nodeconf/source.go Normal file
View File

@ -0,0 +1,16 @@
package nodeconf
import (
"context"
"errors"
)
const CNameSource = "common.nodeconf.source"
var (
ErrConfigurationNotChanged = errors.New("configuration not changed")
)
type Source interface {
GetLast(ctx context.Context, currentId string) (c Configuration, err error)
}

10
nodeconf/store.go Normal file
View File

@ -0,0 +1,10 @@
package nodeconf
import "context"
const CNameStore = "common.nodeconf.store"
type Store interface {
GetLast(ctx context.Context, netId string) (c Configuration, err error)
SaveLast(ctx context.Context, c Configuration) (err error)
}

View File

@ -47,8 +47,8 @@ func (s *AccountTestService) Account() *accountdata.AccountKeys {
return s.acc return s.acc
} }
func (s *AccountTestService) NodeConf(addrs []string) nodeconf.NodeConfig { func (s *AccountTestService) NodeConf(addrs []string) nodeconf.Node {
return nodeconf.NodeConfig{ return nodeconf.Node{
PeerId: s.acc.PeerId, PeerId: s.acc.PeerId,
Addresses: addrs, Addresses: addrs,
Types: []nodeconf.NodeType{nodeconf.NodeTypeTree}, Types: []nodeconf.NodeType{nodeconf.NodeTypeTree},

View File

@ -17,21 +17,25 @@ func GenNodeConfig(num int) (conf *Config) {
if err := ac.Init(nil); err != nil { if err := ac.Init(nil); err != nil {
panic(err) panic(err)
} }
conf.nodes = append(conf.nodes, ac.NodeConf(nil)) conf.nodes.Nodes = append(conf.nodes.Nodes, ac.NodeConf(nil))
conf.configs = append(conf.configs, ac) conf.configs = append(conf.configs, ac)
} }
return conf return conf
} }
type Config struct { type Config struct {
nodes []nodeconf.NodeConfig nodes nodeconf.Configuration
configs []*accounttest.AccountTestService configs []*accounttest.AccountTestService
} }
func (c *Config) Init(a *app.App) (err error) { return } func (c *Config) Init(a *app.App) (err error) { return }
func (c *Config) Name() string { return "config" } func (c *Config) Name() string { return "config" }
func (c *Config) GetNodes() []nodeconf.NodeConfig { func (c *Config) GetNodesConfId() string {
return "test"
}
func (c *Config) GetNodeConf() nodeconf.Configuration {
return c.nodes return c.nodes
} }

View File

@ -158,6 +158,11 @@ func (k *Ed25519PubKey) Account() string {
return res return res
} }
func (k *Ed25519PubKey) Network() string {
res, _ := strkey.Encode(strkey.NetworkAddressVersionByte, k.pubKey)
return res
}
// PeerId returns string representation of key for peer id // PeerId returns string representation of key for peer id
func (k *Ed25519PubKey) PeerId() string { func (k *Ed25519PubKey) PeerId() string {
peerId, _ := IdFromSigningPubKey(k) peerId, _ := IdFromSigningPubKey(k)

View File

@ -47,6 +47,8 @@ type PubKey interface {
Storage() []byte Storage() []byte
// Account returns string representation for anytype account // Account returns string representation for anytype account
Account() string Account() string
// Network returns string representation for anytype network
Network() string
// PeerId returns string representation for peer id // PeerId returns string representation for peer id
PeerId() string PeerId() string
// LibP2P returns libp2p model // LibP2P returns libp2p model

View File

@ -0,0 +1,16 @@
package strkey
import (
"github.com/stretchr/testify/assert"
"github.com/stretchr/testify/require"
"testing"
)
func TestDecode(t *testing.T) {
key := "ABCw4rFBR7qU2HGzHwnKLYo9mMRcjGhFK28gSy58RKc5feqz"
res, err := Decode(AccountAddressVersionByte, key)
require.NoError(t, err)
str, err := Encode(AccountAddressVersionByte, res)
require.NoError(t, err)
assert.Equal(t, key, str)
}

View File

@ -4,4 +4,5 @@ const (
AccountAddressVersionByte VersionByte = 0x5b // Base58-encodes to 'A...' AccountAddressVersionByte VersionByte = 0x5b // Base58-encodes to 'A...'
AccountSeedVersionByte VersionByte = 0xff // Base58-encodes to 'S...' AccountSeedVersionByte VersionByte = 0xff // Base58-encodes to 'S...'
DeviceSeedVersionByte VersionByte = 0x7d // Base58-encodes to 'D...' DeviceSeedVersionByte VersionByte = 0x7d // Base58-encodes to 'D...'
NetworkAddressVersionByte VersionByte = 0xd3 // Base58-encodes to `N...`
) )