Files
status-go/internal/protocol/messenger_sync_settings.go
Igor Sirotin f3e4363808 refactor: move protocol to internal/protocol
Part of the Go project layout migration, item 27.

Pure move plus import-path rewrite across 502 files. No API or behaviour
change. `internal/` keeps the messaging application logic unimportable
from outside the module, which is what the issue asks for -- status-go is
consumed through the C-bindings in mobile/, not as a Go library.

Things that had to follow the move, beyond the Go imports:

- tools/generate-handlers/template.txt. messenger_handlers.go is
  generated, and the template hard-codes the imports it emits, so the
  generated file kept importing protocol/common and failed typecheck.
- .gitignore. The ignore rule for that generated file was pinned to the
  old path; without moving it, a 1486-line generated file starts being
  tracked.
- Makefile: the logosstorage and torrent test targets (both the archive
  packages and ./protocol itself), the archive README, migration-protocol.
- scripts/run_unit_tests.sh, which names the protocol package explicitly
  to shard its tests.
- scripts/cleanup_generated_files.sh and .golangci.yml.

scripts/migration_check.sh also needed a fix that is not specific to this
move: it validated every file the branch touched under a migration dir
against the timestamp naming rule, and a directory rename makes every
migration in it look newly added. It now excludes renames, so moving a
migration is not mistaken for adding one.

refs #7067
2026-08-21 10:11:05 +02:00

149 lines
4.3 KiB
Go

package protocol
import (
"context"
errorsLib "errors"
"go.uber.org/zap"
"github.com/status-im/status-go/internal/db/multiaccounts/settings"
"github.com/status-im/status-go/internal/panics"
"github.com/status-im/status-go/internal/protocol/common"
"github.com/status-im/status-go/internal/protocol/protobuf"
)
// syncSettings syncs all settings that are syncable
func (m *Messenger) prepareSyncSettingsMessages(currentClock uint64, prepareForBackup bool) (resultRaw []*common.RawMessage, resultSync []*protobuf.SyncSetting, errorResult error) {
var errors []error
s, err := m.settings.GetSettings()
if err != nil {
errorResult = err
return
}
logger := m.logger.Named("prepareSyncSettings")
// Do not use the network clock, use the db value
_, chat := m.getLastClockWithRelatedChat()
for _, sf := range settings.SettingFieldRegister {
if sf.CanSync(settings.FromStruct) {
// DisplayName is backed up via `protobuf.BackedUpProfile` message.
if prepareForBackup && sf.SyncProtobufFactory().SyncSettingProtobufType() == protobuf.SyncSetting_DISPLAY_NAME {
continue
}
// Pull clock from the db
clock, err := m.settings.GetSettingLastSynced(sf)
if err != nil {
logger.Error("m.settings.GetSettingLastSynced", zap.Error(err), zap.String("SettingField", sf.GetDBName()))
errorResult = err
return
}
if clock == 0 {
clock = currentClock
}
// Build protobuf
rm, sm, err := sf.SyncProtobufFactory().FromStruct()(s, clock, chat.ID)
if err != nil {
// Collect errors to give other sync messages a chance to send
logger.Error("SyncProtobufFactory.Struct", zap.Error(err))
errors = append(errors, err)
}
resultRaw = append(resultRaw, rm)
resultSync = append(resultSync, sm)
}
}
errorResult = errorsLib.Join(errors...)
return
}
func (m *Messenger) syncSettings(rawMessageHandler RawMessageHandler) error {
logger := m.logger.Named("syncSettings")
clock, _ := m.getLastClockWithRelatedChat()
rawMessages, _, err := m.prepareSyncSettingsMessages(clock, false)
if err != nil {
return err
}
for _, rm := range rawMessages {
_, err := rawMessageHandler(context.Background(), *rm)
if err != nil {
logger.Error("dispatchMessage", zap.Error(err))
return err
}
logger.Debug("dispatchMessage success", zap.Any("rm", rm))
}
return nil
}
// startSyncSettingsLoop watches the m.settings.SyncQueue and sends a sync message in response to a settings update
func (m *Messenger) startSyncSettingsLoop() {
go func() {
defer panics.LogOnPanic()
logger := m.logger.Named("SyncSettingsLoop")
for {
select {
case s := <-m.settings.GetSyncQueue():
if s.CanSync(settings.FromInterface) {
logger.Debug("setting for sync received from settings.SyncQueue")
clock, chat := m.getLastClockWithRelatedChat()
// Only the messenger has access to the clock, so set the settings sync clock here.
err := m.settings.SetSettingLastSynced(s.SettingField, clock)
if err != nil {
logger.Error("m.settings.SetSettingLastSynced", zap.Error(err))
break
}
rm, _, err := s.SyncProtobufFactory().FromInterface()(s.Value, clock, chat.ID)
if err != nil {
logger.Error("SyncProtobufFactory().FromInterface", zap.Error(err), zap.String("SyncSettingField", s.GetDBName()))
break
}
_, err = m.dispatchMessage(context.Background(), *rm)
if err != nil {
logger.Error("dispatchMessage", zap.Error(err))
break
}
logger.Debug("message dispatched")
}
case <-m.quit:
return
}
}
}()
}
func (m *Messenger) startSettingsChangesLoop() {
channel := m.settings.SubscribeToChanges()
go func() {
defer panics.LogOnPanic()
for {
select {
case s := <-channel:
switch s.GetReactName() {
case settings.DisplayName.GetReactName():
m.selfContact.DisplayName = s.Value.(string)
m.publishSelfContactSubscriptions(&SelfContactChangeEvent{DisplayNameChanged: true})
case settings.PreferredName.GetReactName():
m.selfContact.EnsName = s.Value.(string)
m.publishSelfContactSubscriptions(&SelfContactChangeEvent{PreferredNameChanged: true})
case settings.Bio.GetReactName():
m.selfContact.Bio = s.Value.(string)
m.publishSelfContactSubscriptions(&SelfContactChangeEvent{BioChanged: true})
}
case <-m.quit:
return
}
}
}()
}