Notify user when the device is missing (#1298)
* Notify user when the device is missing * Update services/shhext/chat/encryption.go Co-Authored-By: cammellos <andrea.maria.piana@gmail.com>
This commit is contained in:
parent
49cfcd3e24
commit
afc3017e07
|
@ -98,7 +98,7 @@ pipeline {
|
||||||
usernameVariable: 'GITHUB_USER',
|
usernameVariable: 'GITHUB_USER',
|
||||||
passwordVariable: 'GITHUB_TOKEN'
|
passwordVariable: 'GITHUB_TOKEN'
|
||||||
]]) {
|
]]) {
|
||||||
sh "yes | make release release_branch=${lib.gitBranch()}"
|
sh "yes | make release RELEASE_BRANCH=${lib.gitBranch()}"
|
||||||
}
|
}
|
||||||
sh 'make clean-release'
|
sh 'make clean-release'
|
||||||
}
|
}
|
||||||
|
|
|
@ -416,11 +416,9 @@ func (api *PublicAPI) processPFSMessage(msg *whisper.Message) error {
|
||||||
|
|
||||||
response, err := api.service.protocol.HandleMessage(privateKey, publicKey, msg.Payload)
|
response, err := api.service.protocol.HandleMessage(privateKey, publicKey, msg.Payload)
|
||||||
|
|
||||||
handler := EnvelopeSignalHandler{}
|
|
||||||
|
|
||||||
// Notify that someone tried to contact us using an invalid bundle
|
// Notify that someone tried to contact us using an invalid bundle
|
||||||
if err == chat.ErrSessionNotFound {
|
if err == chat.ErrDeviceNotFound && privateKey.PublicKey != *publicKey {
|
||||||
api.log.Warn("Session not found, sending signal", "err", err)
|
api.log.Warn("Device not found, sending signal", "err", err)
|
||||||
keyString := fmt.Sprintf("0x%x", crypto.FromECDSAPub(publicKey))
|
keyString := fmt.Sprintf("0x%x", crypto.FromECDSAPub(publicKey))
|
||||||
handler := EnvelopeSignalHandler{}
|
handler := EnvelopeSignalHandler{}
|
||||||
handler.DecryptMessageFailed(keyString)
|
handler.DecryptMessageFailed(keyString)
|
||||||
|
@ -432,14 +430,7 @@ func (api *PublicAPI) processPFSMessage(msg *whisper.Message) error {
|
||||||
}
|
}
|
||||||
|
|
||||||
// Add unencrypted payload
|
// Add unencrypted payload
|
||||||
msg.Payload = response.Message
|
msg.Payload = response
|
||||||
|
|
||||||
// Notify of added bundles
|
|
||||||
if response.AddedBundles != nil {
|
|
||||||
for _, bundle := range response.AddedBundles {
|
|
||||||
handler.BundleAdded(bundle[0], bundle[1])
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
return nil
|
return nil
|
||||||
}
|
}
|
||||||
|
|
|
@ -18,6 +18,7 @@ import (
|
||||||
)
|
)
|
||||||
|
|
||||||
var ErrSessionNotFound = errors.New("session not found")
|
var ErrSessionNotFound = errors.New("session not found")
|
||||||
|
var ErrDeviceNotFound = errors.New("device not found")
|
||||||
|
|
||||||
// If we have no bundles, we use a constant so that the message can reach any device.
|
// If we have no bundles, we use a constant so that the message can reach any device.
|
||||||
const noInstallationID = "none"
|
const noInstallationID = "none"
|
||||||
|
@ -53,7 +54,7 @@ func DefaultEncryptionServiceConfig(installationID string) EncryptionServiceConf
|
||||||
MaxSkip: 1000,
|
MaxSkip: 1000,
|
||||||
MaxKeep: 3000,
|
MaxKeep: 3000,
|
||||||
MaxMessageKeysPerSession: 2000,
|
MaxMessageKeysPerSession: 2000,
|
||||||
BundleRefreshInterval: 14 * 24 * 60 * 60 * 1000,
|
BundleRefreshInterval: 6 * 60 * 60 * 1000,
|
||||||
InstallationID: installationID,
|
InstallationID: installationID,
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -238,8 +239,8 @@ func (s *EncryptionService) DecryptPayload(myIdentityKey *ecdsa.PrivateKey, thei
|
||||||
}
|
}
|
||||||
|
|
||||||
// We should not be sending a signal if it's coming from us, as we receive our own messages
|
// We should not be sending a signal if it's coming from us, as we receive our own messages
|
||||||
if msg == nil {
|
if msg == nil && *theirIdentityKey != myIdentityKey.PublicKey {
|
||||||
return nil, ErrSessionNotFound
|
return nil, ErrDeviceNotFound
|
||||||
}
|
}
|
||||||
payload := msg.GetPayload()
|
payload := msg.GetPayload()
|
||||||
|
|
||||||
|
|
|
@ -770,6 +770,39 @@ func (s *EncryptionServiceTestSuite) TestBundleNotExisting() {
|
||||||
s.Equal(ErrSessionNotFound, err)
|
s.Equal(ErrSessionNotFound, err)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// Device is not included in the bundle
|
||||||
|
func (s *EncryptionServiceTestSuite) TestDeviceNotIncluded() {
|
||||||
|
bobDevice2InstallationID := "bob2"
|
||||||
|
|
||||||
|
bobKey, err := crypto.GenerateKey()
|
||||||
|
s.Require().NoError(err)
|
||||||
|
|
||||||
|
aliceKey, err := crypto.GenerateKey()
|
||||||
|
s.Require().NoError(err)
|
||||||
|
|
||||||
|
// Create a bundle without saving it
|
||||||
|
bobBundleContainer, err := NewBundleContainer(bobKey, bobDevice2InstallationID)
|
||||||
|
s.Require().NoError(err)
|
||||||
|
|
||||||
|
err = SignBundle(bobKey, bobBundleContainer)
|
||||||
|
s.Require().NoError(err)
|
||||||
|
|
||||||
|
bobBundle := bobBundleContainer.GetBundle()
|
||||||
|
|
||||||
|
// We add bob bundle
|
||||||
|
_, err = s.alice.ProcessPublicBundle(aliceKey, bobBundle)
|
||||||
|
s.Require().NoError(err)
|
||||||
|
|
||||||
|
// Alice sends a message
|
||||||
|
aliceMessage, err := s.alice.EncryptPayload(&bobKey.PublicKey, aliceKey, []byte("does not matter"))
|
||||||
|
s.Require().NoError(err)
|
||||||
|
|
||||||
|
// Bob receives the message, and returns a bundlenotfound error
|
||||||
|
_, err = s.bob.DecryptPayload(bobKey, &aliceKey.PublicKey, aliceInstallationID, aliceMessage)
|
||||||
|
s.Require().Error(err)
|
||||||
|
s.Equal(ErrDeviceNotFound, err)
|
||||||
|
}
|
||||||
|
|
||||||
// A new bundle has been received
|
// A new bundle has been received
|
||||||
func (s *EncryptionServiceTestSuite) TestRefreshedBundle() {
|
func (s *EncryptionServiceTestSuite) TestRefreshedBundle() {
|
||||||
|
|
||||||
|
|
|
@ -11,19 +11,16 @@ import (
|
||||||
type ProtocolService struct {
|
type ProtocolService struct {
|
||||||
log log.Logger
|
log log.Logger
|
||||||
encryption *EncryptionService
|
encryption *EncryptionService
|
||||||
|
addedBundlesHandler func([]IdentityAndIDPair)
|
||||||
Enabled bool
|
Enabled bool
|
||||||
}
|
}
|
||||||
|
|
||||||
type HandleMessageResponse struct {
|
|
||||||
AddedBundles []IdentityAndIDPair
|
|
||||||
Message []byte
|
|
||||||
}
|
|
||||||
|
|
||||||
// NewProtocolService creates a new ProtocolService instance
|
// NewProtocolService creates a new ProtocolService instance
|
||||||
func NewProtocolService(encryption *EncryptionService) *ProtocolService {
|
func NewProtocolService(encryption *EncryptionService, addedBundlesHandler func([]IdentityAndIDPair)) *ProtocolService {
|
||||||
return &ProtocolService{
|
return &ProtocolService{
|
||||||
log: log.New("package", "status-go/services/sshext.chat"),
|
log: log.New("package", "status-go/services/sshext.chat"),
|
||||||
encryption: encryption,
|
encryption: encryption,
|
||||||
|
addedBundlesHandler: addedBundlesHandler,
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -126,13 +123,11 @@ func (p *ProtocolService) DisableInstallation(myIdentityKey *ecdsa.PublicKey, in
|
||||||
}
|
}
|
||||||
|
|
||||||
// HandleMessage unmarshals a message and processes it, decrypting it if it is a 1:1 message.
|
// HandleMessage unmarshals a message and processes it, decrypting it if it is a 1:1 message.
|
||||||
func (p *ProtocolService) HandleMessage(myIdentityKey *ecdsa.PrivateKey, theirPublicKey *ecdsa.PublicKey, payload []byte) (*HandleMessageResponse, error) {
|
func (p *ProtocolService) HandleMessage(myIdentityKey *ecdsa.PrivateKey, theirPublicKey *ecdsa.PublicKey, payload []byte) ([]byte, error) {
|
||||||
if p.encryption == nil {
|
if p.encryption == nil {
|
||||||
return nil, errors.New("encryption service not initialized")
|
return nil, errors.New("encryption service not initialized")
|
||||||
}
|
}
|
||||||
|
|
||||||
response := &HandleMessageResponse{}
|
|
||||||
|
|
||||||
// Unmarshal message
|
// Unmarshal message
|
||||||
protocolMessage := &ProtocolMessage{}
|
protocolMessage := &ProtocolMessage{}
|
||||||
|
|
||||||
|
@ -147,14 +142,14 @@ func (p *ProtocolService) HandleMessage(myIdentityKey *ecdsa.PrivateKey, theirPu
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return nil, err
|
return nil, err
|
||||||
}
|
}
|
||||||
response.AddedBundles = addedBundles
|
|
||||||
|
p.addedBundlesHandler(addedBundles)
|
||||||
}
|
}
|
||||||
|
|
||||||
// Check if it's a public message
|
// Check if it's a public message
|
||||||
if publicMessage := protocolMessage.GetPublicMessage(); publicMessage != nil {
|
if publicMessage := protocolMessage.GetPublicMessage(); publicMessage != nil {
|
||||||
response.Message = publicMessage
|
|
||||||
// Nothing to do, as already in cleartext
|
// Nothing to do, as already in cleartext
|
||||||
return response, nil
|
return publicMessage, nil
|
||||||
}
|
}
|
||||||
|
|
||||||
// Decrypt message
|
// Decrypt message
|
||||||
|
@ -163,9 +158,8 @@ func (p *ProtocolService) HandleMessage(myIdentityKey *ecdsa.PrivateKey, theirPu
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return nil, err
|
return nil, err
|
||||||
}
|
}
|
||||||
response.Message = message
|
|
||||||
|
|
||||||
return response, nil
|
return message, nil
|
||||||
}
|
}
|
||||||
|
|
||||||
// Return error
|
// Return error
|
||||||
|
|
|
@ -38,8 +38,10 @@ func (s *ProtocolServiceTestSuite) SetupTest() {
|
||||||
panic(err)
|
panic(err)
|
||||||
}
|
}
|
||||||
|
|
||||||
s.alice = NewProtocolService(NewEncryptionService(alicePersistence, DefaultEncryptionServiceConfig("1")))
|
addedBundlesHandler := func(addedBundles []IdentityAndIDPair) {}
|
||||||
s.bob = NewProtocolService(NewEncryptionService(bobPersistence, DefaultEncryptionServiceConfig("2")))
|
|
||||||
|
s.alice = NewProtocolService(NewEncryptionService(alicePersistence, DefaultEncryptionServiceConfig("1")), addedBundlesHandler)
|
||||||
|
s.bob = NewProtocolService(NewEncryptionService(bobPersistence, DefaultEncryptionServiceConfig("2")), addedBundlesHandler)
|
||||||
}
|
}
|
||||||
|
|
||||||
func (s *ProtocolServiceTestSuite) TestBuildDirectMessage() {
|
func (s *ProtocolServiceTestSuite) TestBuildDirectMessage() {
|
||||||
|
@ -102,9 +104,8 @@ func (s *ProtocolServiceTestSuite) TestBuildAndReadDirectMessage() {
|
||||||
s.NoError(err)
|
s.NoError(err)
|
||||||
|
|
||||||
// Bob is able to decrypt the message
|
// Bob is able to decrypt the message
|
||||||
response, err := s.bob.HandleMessage(bobKey, &aliceKey.PublicKey, marshaledMsg[&bobKey.PublicKey])
|
unmarshaledMsg, err := s.bob.HandleMessage(bobKey, &aliceKey.PublicKey, marshaledMsg[&bobKey.PublicKey])
|
||||||
s.NoError(err)
|
s.NoError(err)
|
||||||
unmarshaledMsg := response.Message
|
|
||||||
|
|
||||||
s.NotNil(unmarshaledMsg)
|
s.NotNil(unmarshaledMsg)
|
||||||
|
|
||||||
|
|
|
@ -118,7 +118,15 @@ func (s *Service) InitProtocol(address string, password string) error {
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return err
|
return err
|
||||||
}
|
}
|
||||||
s.protocol = chat.NewProtocolService(chat.NewEncryptionService(persistence, chat.DefaultEncryptionServiceConfig(s.installationID)))
|
|
||||||
|
addedBundlesHandler := func(addedBundles []chat.IdentityAndIDPair) {
|
||||||
|
handler := EnvelopeSignalHandler{}
|
||||||
|
for _, bundle := range addedBundles {
|
||||||
|
handler.BundleAdded(bundle[0], bundle[1])
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
s.protocol = chat.NewProtocolService(chat.NewEncryptionService(persistence, chat.DefaultEncryptionServiceConfig(s.installationID)), addedBundlesHandler)
|
||||||
|
|
||||||
return nil
|
return nil
|
||||||
}
|
}
|
||||||
|
|
Loading…
Reference in New Issue