Skip to content

Commit b633f89

Browse files
agent: check ntf token status on registration (#1450)
* agent: check ntf token status on registration * remove check * update on check * refactor * version * fix * test, verify invalid * rename * increase delay * disable new tests in CI * fix --------- Co-authored-by: Evgeny Poberezkin <[email protected]>
1 parent 944a22a commit b633f89

File tree

4 files changed

+92
-27
lines changed

4 files changed

+92
-27
lines changed

simplexmq.cabal

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,7 +1,7 @@
11
cabal-version: 1.12
22

33
name: simplexmq
4-
version: 6.3.0.301
4+
version: 6.3.0.3
55
synopsis: SimpleXMQ message broker
66
description: This package includes <./docs/Simplex-Messaging-Server.html server>,
77
<./docs/Simplex-Messaging-Client.html client> and

src/Simplex/Messaging/Agent.hs

Lines changed: 19 additions & 11 deletions
Original file line numberDiff line numberDiff line change
@@ -1946,7 +1946,7 @@ registerNtfToken' c suppliedDeviceToken suppliedNtfMode =
19461946
-- possible improvement: add minimal time before repeat registration
19471947
(Just tknId, Nothing)
19481948
| savedDeviceToken == suppliedDeviceToken ->
1949-
when (ntfTknStatus == NTRegistered) (registerToken tkn) $> NTRegistered
1949+
registerToken tkn $> NTRegistered
19501950
| otherwise -> replaceToken tknId
19511951
(Just tknId, Just (NTAVerify code))
19521952
| savedDeviceToken == suppliedDeviceToken ->
@@ -1955,14 +1955,16 @@ registerNtfToken' c suppliedDeviceToken suppliedNtfMode =
19551955
(Just tknId, Just NTACheck)
19561956
| savedDeviceToken == suppliedDeviceToken -> do
19571957
ns <- asks ntfSupervisor
1958-
atomically $ nsUpdateToken ns tkn {ntfMode = suppliedNtfMode}
1959-
when (ntfTknStatus == NTActive) $ do
1960-
cron <- asks $ ntfCron . config
1961-
agentNtfEnableCron c tknId tkn cron
1962-
when (suppliedNtfMode == NMInstant) $ initializeNtfSubs c
1963-
when (suppliedNtfMode == NMPeriodic && savedNtfMode == NMInstant) $ deleteNtfSubs c NSCSmpDelete
1964-
-- possible improvement: get updated token status from the server, or maybe TCRON could return the current status
1965-
pure ntfTknStatus
1958+
let tkn' = tkn {ntfMode = suppliedNtfMode}
1959+
atomically $ nsUpdateToken ns tkn'
1960+
agentNtfCheckToken c tknId tkn' >>= \case
1961+
NTActive -> do
1962+
cron <- asks $ ntfCron . config
1963+
agentNtfEnableCron c tknId tkn cron
1964+
when (suppliedNtfMode == NMInstant) $ initializeNtfSubs c
1965+
when (suppliedNtfMode == NMPeriodic && savedNtfMode == NMInstant) $ deleteNtfSubs c NSCSmpDelete
1966+
t tkn' (NTActive, Just NTACheck) $ pure ()
1967+
status -> t tkn' (status, Nothing) $ pure ()
19661968
| otherwise -> replaceToken tknId
19671969
-- deprecated
19681970
(Just _tknId, Just NTADelete) -> deleteToken c tkn $> NTExpired
@@ -2029,9 +2031,15 @@ verifyNtfToken' c deviceToken nonce code =
20292031
checkNtfToken' :: AgentClient -> DeviceToken -> AM NtfTknStatus
20302032
checkNtfToken' c deviceToken =
20312033
withStore' c getSavedNtfToken >>= \case
2032-
Just tkn@NtfToken {deviceToken = savedDeviceToken, ntfTokenId = Just tknId} -> do
2034+
Just tkn@NtfToken {deviceToken = savedDeviceToken, ntfTokenId = Just tknId, ntfTknAction} -> do
20332035
when (deviceToken /= savedDeviceToken) . throwE $ CMD PROHIBITED "checkNtfToken: different token"
2034-
agentNtfCheckToken c tknId tkn
2036+
status <- agentNtfCheckToken c tknId tkn
2037+
let action = case status of
2038+
NTInvalid _ -> Nothing
2039+
NTExpired -> Nothing
2040+
_ -> ntfTknAction
2041+
withStore' c $ \db -> updateNtfToken db tkn status action
2042+
pure status
20352043
_ -> throwE $ CMD PROHIBITED "checkNtfToken: no token"
20362044

20372045
deleteNtfToken' :: AgentClient -> DeviceToken -> AM ()

src/Simplex/Messaging/Notifications/Server.hs

Lines changed: 9 additions & 13 deletions
Original file line numberDiff line numberDiff line change
@@ -436,19 +436,15 @@ ntfPush s@NtfPushServer {pushQ} = forever $ do
436436
liftIO $ logDebug $ "sending push notification to " <> T.pack (show pp)
437437
status <- readTVarIO tknStatus
438438
case ntf of
439-
PNVerification _ -> case status of
440-
NTInvalid _ -> logError $ "bad notification token status: " <> tshow status
441-
-- TODO nothing makes token "expired" on the server
442-
NTExpired -> logError $ "bad notification token status: " <> tshow status
443-
_ ->
444-
deliverNotification pp tkn ntf >>= \case
445-
Right _ -> do
446-
status_ <- atomically $ stateTVar tknStatus $ \case
447-
NTActive -> (Nothing, NTActive)
448-
NTConfirmed -> (Nothing, NTConfirmed)
449-
_ -> (Just NTConfirmed, NTConfirmed)
450-
forM_ status_ $ \status' -> withNtfLog $ \sl -> logTokenStatus sl ntfTknId status'
451-
_ -> pure ()
439+
PNVerification _ ->
440+
deliverNotification pp tkn ntf >>= \case
441+
Right _ -> do
442+
status_ <- atomically $ stateTVar tknStatus $ \case
443+
NTActive -> (Nothing, NTActive)
444+
NTConfirmed -> (Nothing, NTConfirmed)
445+
_ -> (Just NTConfirmed, NTConfirmed)
446+
forM_ status_ $ \status' -> withNtfLog $ \sl -> logTokenStatus sl ntfTknId status'
447+
_ -> pure ()
452448
PNCheckMessages -> checkActiveTkn status $ do
453449
void $ deliverNotification pp tkn ntf
454450
PNMessage {} -> checkActiveTkn status $ do

tests/AgentTests/NotificationTests.hs

Lines changed: 63 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -53,18 +53,21 @@ import Data.ByteString.Char8 (ByteString)
5353
import qualified Data.ByteString.Char8 as B
5454
import Data.List.NonEmpty (NonEmpty (..))
5555
import qualified Data.List.NonEmpty as L
56+
import Data.Text (Text)
57+
import qualified Data.Text as T
5658
import Data.Text.Encoding (encodeUtf8)
59+
import qualified Data.Text.IO as TIO
5760
import NtfClient
5861
import SMPAgentClient (agentCfg, initAgentServers, initAgentServers2, testDB, testDB2, testNtfServer, testNtfServer2)
59-
import SMPClient (cfg, cfgVPrev, testPort, testPort2, testStoreLogFile2, testStoreMsgsDir2, withSmpServer, withSmpServerConfigOn, withSmpServerStoreLogOn, withSmpServerStoreMsgLogOn)
62+
import SMPClient (cfg, cfgVPrev, testPort, testPort2, testStoreLogFile2, testStoreMsgsDir2, withSmpServer, withSmpServerConfigOn, withSmpServerStoreLogOn, withSmpServerStoreMsgLogOn, xit'')
6063
import Simplex.Messaging.Agent hiding (createConnection, joinConnection, sendMessage)
6164
import Simplex.Messaging.Agent.Client (ProtocolTestFailure (..), ProtocolTestStep (..), withStore')
6265
import Simplex.Messaging.Agent.Env.SQLite (AgentConfig, Env (..), InitialAgentServers)
6366
import Simplex.Messaging.Agent.Protocol hiding (CON, CONF, INFO, SENT)
6467
import Simplex.Messaging.Agent.Store.AgentStore (getSavedNtfToken)
6568
import Simplex.Messaging.Agent.Store.Common (withTransaction)
66-
import Simplex.Messaging.Agent.Store.Interface (closeDBStore, reopenDBStore)
6769
import qualified Simplex.Messaging.Agent.Store.DB as DB
70+
import Simplex.Messaging.Agent.Store.Interface (closeDBStore, reopenDBStore)
6871
import qualified Simplex.Messaging.Crypto as C
6972
import Simplex.Messaging.Encoding.String
7073
import Simplex.Messaging.Notifications.Protocol
@@ -117,6 +120,12 @@ notificationTests t = do
117120
it "should keep working with active token until replaced" $
118121
withAPNSMockServer $ \apns ->
119122
testNtfTokenChangeServers t apns
123+
xit'' "should re-register token in NTInvalid status after register attempt" $
124+
withAPNSMockServer $ \apns ->
125+
testNtfTokenReRegisterInvalid t apns
126+
xit'' "should re-register token in NTInvalid status after checking token" $
127+
withAPNSMockServer $ \apns ->
128+
testNtfTokenReRegisterInvalidOnCheck t apns
120129
describe "notification server tests" $ do
121130
it "should pass" $ testRunNTFServerTests t testNtfServer `shouldReturn` Nothing
122131
let srv1 = testNtfServer {keyHash = "1234"}
@@ -459,6 +468,58 @@ testNtfTokenChangeServers t apns =
459468
tkn <- registerTestToken a "qwer" NMInstant apns
460469
checkNtfToken a tkn >>= \r -> liftIO $ r `shouldBe` NTActive
461470

471+
testNtfTokenReRegisterInvalid :: ATransport -> APNSMockServer -> IO ()
472+
testNtfTokenReRegisterInvalid t apns = do
473+
tkn <- withNtfServerStoreLog t $ \_ -> do
474+
withAgent 1 agentCfg initAgentServers testDB $ \a -> runRight $ do
475+
tkn <- registerTestToken a "abcd" NMInstant apns
476+
NTActive <- checkNtfToken a tkn
477+
pure tkn
478+
479+
threadDelay 250000
480+
-- start server to compact
481+
withNtfServerStoreLog t $ \_ -> pure ()
482+
483+
threadDelay 250000
484+
replaceSubstringInFile ntfTestStoreLogFile "tokenStatus=ACTIVE" "tokenStatus=INVALID"
485+
486+
threadDelay 250000
487+
withNtfServerStoreLog t $ \_ -> do
488+
withAgent 1 agentCfg initAgentServers testDB $ \a -> runRight_ $ do
489+
NTInvalid Nothing <- registerNtfToken a tkn NMInstant
490+
tkn1 <- registerTestToken a "abcd" NMInstant apns
491+
NTActive <- checkNtfToken a tkn1
492+
pure ()
493+
494+
replaceSubstringInFile :: FilePath -> Text -> Text -> IO ()
495+
replaceSubstringInFile filePath oldText newText = do
496+
content <- TIO.readFile filePath
497+
let newContent = T.replace oldText newText content
498+
TIO.writeFile filePath newContent
499+
500+
testNtfTokenReRegisterInvalidOnCheck :: ATransport -> APNSMockServer -> IO ()
501+
testNtfTokenReRegisterInvalidOnCheck t apns = do
502+
tkn <- withNtfServerStoreLog t $ \_ -> do
503+
withAgent 1 agentCfg initAgentServers testDB $ \a -> runRight $ do
504+
tkn <- registerTestToken a "abcd" NMInstant apns
505+
NTActive <- checkNtfToken a tkn
506+
pure tkn
507+
508+
threadDelay 250000
509+
-- start server to compact
510+
withNtfServerStoreLog t $ \_ -> pure ()
511+
512+
threadDelay 250000
513+
replaceSubstringInFile ntfTestStoreLogFile "tokenStatus=ACTIVE" "tokenStatus=INVALID"
514+
515+
threadDelay 250000
516+
withNtfServerStoreLog t $ \_ -> do
517+
withAgent 1 agentCfg initAgentServers testDB $ \a -> runRight_ $ do
518+
NTInvalid Nothing <- checkNtfToken a tkn
519+
tkn1 <- registerTestToken a "abcd" NMInstant apns
520+
NTActive <- checkNtfToken a tkn1
521+
pure ()
522+
462523
testRunNTFServerTests :: ATransport -> NtfServer -> IO (Maybe ProtocolTestFailure)
463524
testRunNTFServerTests t srv =
464525
withNtfServerOn t ntfTestPort $

0 commit comments

Comments
 (0)