status-go/protocol/activity_center.go
frank f04a9a8726
feat(sync)!: leftovers work for sync fallback (#5794)
* feat(sync)!: remove compatibility with v2.29

* feat(sync)_: add AC notifications when initiating the sync fallback

Needed for https://github.com/status-im/status-desktop/issues/15750

Adds an AC notification when the syncing fails and the user is prompted to use a seed phrase instead.
There is one notification for the initiator (created) and one for the old account (received).
Once the flow is completed, ie the receiver presses Enable and sync,  the notifications are deleted

* test_: update test

* fix_: lint issue

* chore_: ignore tmp file generated by make lint-fix

* chore_: rename EnableAndSyncInstallation to EnableInstallationAndSync

* chore_: address review feedback

* chore_: revert changes to .gitignore

* fix_: simplify code

* fix_: keep old API

---------

Co-authored-by: Jonathan Rainville <rainville.jonathan@gmail.com>
2024-09-19 16:17:46 +08:00

167 lines
6.5 KiB
Go

package protocol
import (
"crypto/ecdsa"
"errors"
"github.com/status-im/status-go/eth-node/types"
"github.com/status-im/status-go/protocol/common"
"github.com/status-im/status-go/protocol/verification"
"github.com/status-im/status-go/services/wallet/thirdparty"
)
// The activity center is a place where we store incoming notifications before
// they are shown to the users as new chats, in order to mitigate the impact of spam
// on the messenger
type ActivityCenterType int
const (
ActivityCenterNotificationNoType ActivityCenterType = iota
ActivityCenterNotificationTypeNewOneToOne
ActivityCenterNotificationTypeNewPrivateGroupChat
ActivityCenterNotificationTypeMention
ActivityCenterNotificationTypeReply
ActivityCenterNotificationTypeContactRequest
ActivityCenterNotificationTypeCommunityInvitation
ActivityCenterNotificationTypeCommunityRequest
ActivityCenterNotificationTypeCommunityMembershipRequest
ActivityCenterNotificationTypeCommunityKicked
ActivityCenterNotificationTypeContactVerification
ActivityCenterNotificationTypeContactRemoved
ActivityCenterNotificationTypeNewKeypairAddedToPairedDevice
ActivityCenterNotificationTypeOwnerTokenReceived
ActivityCenterNotificationTypeOwnershipReceived
ActivityCenterNotificationTypeOwnershipLost
ActivityCenterNotificationTypeSetSignerFailed
ActivityCenterNotificationTypeSetSignerDeclined
ActivityCenterNotificationTypeShareAccounts
ActivityCenterNotificationTypeCommunityTokenReceived
ActivityCenterNotificationTypeFirstCommunityTokenReceived
ActivityCenterNotificationTypeCommunityBanned
ActivityCenterNotificationTypeCommunityUnbanned
ActivityCenterNotificationTypeNewInstallationReceived
ActivityCenterNotificationTypeNewInstallationCreated
)
type ActivityCenterMembershipStatus int
const (
ActivityCenterMembershipStatusIdle ActivityCenterMembershipStatus = iota
ActivityCenterMembershipStatusPending
ActivityCenterMembershipStatusAccepted
ActivityCenterMembershipStatusDeclined
ActivityCenterMembershipStatusAcceptedPending
ActivityCenterMembershipStatusDeclinedPending
ActivityCenterMembershipOwnershipChanged
)
type ActivityCenterQueryParamsRead uint
const (
ActivityCenterQueryParamsReadRead = iota + 1
ActivityCenterQueryParamsReadUnread
ActivityCenterQueryParamsReadAll
)
var ErrInvalidActivityCenterNotification = errors.New("invalid activity center notification")
type ActivityTokenData struct {
ChainID uint64 `json:"chainId,omitempty"`
CollectibleID thirdparty.CollectibleUniqueID `json:"collectibleId,omitempty"`
TxHash string `json:"txHash,omitempty"`
WalletAddress string `json:"walletAddress,omitempty"`
IsFirst bool `json:"isFirst,omitempty"`
// Community data
CommunityID string `json:"communityId,omitempty"`
// Token data
Amount string `json:"amount,omitempty"`
Name string `json:"name,omitempty"`
Symbol string `json:"symbol,omitempty"`
ImageURL string `json:"imageUrl,omitempty"`
TokenType int `json:"tokenType,omitempty"`
}
type ActivityCenterNotification struct {
ID types.HexBytes `json:"id"`
ChatID string `json:"chatId"`
CommunityID string `json:"communityId"`
MembershipStatus ActivityCenterMembershipStatus `json:"membershipStatus"`
Name string `json:"name"`
Author string `json:"author"`
InstallationID string `json:"installationId"`
Type ActivityCenterType `json:"type"`
LastMessage *common.Message `json:"lastMessage"`
Message *common.Message `json:"message"`
ReplyMessage *common.Message `json:"replyMessage"`
Timestamp uint64 `json:"timestamp"`
Read bool `json:"read"`
Dismissed bool `json:"dismissed"`
Deleted bool `json:"deleted"`
Accepted bool `json:"accepted"`
ContactVerificationStatus verification.RequestStatus `json:"contactVerificationStatus"`
TokenData *ActivityTokenData `json:"tokenData"`
//Used for synchronization. Each update should increment the UpdatedAt.
//The value should represent the time when the update occurred.
UpdatedAt uint64 `json:"updatedAt"`
AlbumMessages []*common.Message `json:"albumMessages"`
}
func (n *ActivityCenterNotification) IncrementUpdatedAt(timesource common.TimeSource) {
tNow := timesource.GetCurrentTime()
// If updatead at is greater or equal than time now, we bump it
if n.UpdatedAt >= tNow {
n.UpdatedAt++
} else {
n.UpdatedAt = tNow
}
}
type ActivityCenterNotificationsRequest struct {
Cursor string `json:"cursor"`
Limit uint64 `json:"limit"`
ActivityTypes []ActivityCenterType `json:"activityTypes"`
ReadType ActivityCenterQueryParamsRead `json:"readType"`
}
type ActivityCenterCountRequest struct {
ActivityTypes []ActivityCenterType `json:"activityTypes"`
ReadType ActivityCenterQueryParamsRead `json:"readType"`
}
type ActivityCenterPaginationResponse struct {
Cursor string `json:"cursor"`
Notifications []*ActivityCenterNotification `json:"notifications"`
}
type ActivityCenterCountResponse = map[ActivityCenterType]uint64
type ActivityCenterState struct {
HasSeen bool `json:"hasSeen"`
UpdatedAt uint64 `json:"updatedAt"`
}
func (n *ActivityCenterNotification) Valid() error {
if len(n.ID) == 0 || n.Type == 0 || n.Timestamp == 0 {
return ErrInvalidActivityCenterNotification
}
return nil
}
func showMentionOrReplyActivityCenterNotification(publicKey ecdsa.PublicKey, message *common.Message, chat *Chat, responseTo *common.Message) (bool, ActivityCenterType) {
if chat == nil || !chat.Active || (!chat.CommunityChat() && !chat.PrivateGroupChat()) || chat.Muted {
return false, ActivityCenterNotificationNoType
}
if message.Mentioned {
return true, ActivityCenterNotificationTypeMention
}
publicKeyString := common.PubkeyToHex(&publicKey)
if responseTo != nil && responseTo.From == publicKeyString {
return true, ActivityCenterNotificationTypeReply
}
return false, ActivityCenterNotificationNoType
}