Skip to content

Commit e7e2860

Browse files
committed
parameterize type for link data by connection type
1 parent d348462 commit e7e2860

6 files changed

Lines changed: 159 additions & 90 deletions

File tree

src/Simplex/Messaging/Agent.hs

Lines changed: 9 additions & 10 deletions
Original file line numberDiff line numberDiff line change
@@ -379,7 +379,7 @@ deleteContactShortLink c = withAgentEnv c . deleteContactShortLink' c
379379
{-# INLINE deleteContactShortLink #-}
380380

381381
-- | Get and verify data from short link. For 1-time invitations it preserves the key to allow retries
382-
getConnShortLink :: AgentClient -> UserId -> ConnShortLink c -> AE (Maybe (ConnectionRequestUri c), ConnInfo)
382+
getConnShortLink :: AgentClient -> UserId -> ConnShortLink c -> AE (ConnectionRequestUri c, ConnInfo)
383383
getConnShortLink c = withAgentEnv c .: getConnShortLink' c
384384
{-# INLINE getConnShortLink #-}
385385

@@ -838,7 +838,7 @@ setContactShortLink' c connId userData =
838838
SomeConn _ (ContactConnection _ rq) -> do
839839
(lnkId, linkKey, d) <- prepareLinkData rq
840840
addQueueLink c rq lnkId d
841-
pure $ CSLContact (qServer rq) CCTContact linkKey
841+
pure $ CSLContact CCTContact (qServer rq) linkKey
842842
_ -> throwE $ CMD PROHIBITED "setContactShortLink: not contact address"
843843
where
844844
prepareLinkData :: RcvQueue -> AM (SMP.LinkId, LinkKey, QueueLinkData)
@@ -870,7 +870,7 @@ deleteContactShortLink' c connId =
870870
_ -> throwE $ CMD PROHIBITED "deleteContactShortLink: not contact address"
871871

872872
-- TODO [short links] remove 1-time invitation data and link ID from the server after the message is sent.
873-
getConnShortLink' :: forall c. AgentClient -> UserId -> ConnShortLink c -> AM (Maybe (ConnectionRequestUri c), ConnInfo)
873+
getConnShortLink' :: forall c. AgentClient -> UserId -> ConnShortLink c -> AM (ConnectionRequestUri c, ConnInfo)
874874
getConnShortLink' c userId = \case
875875
CSLInvitation srv linkId linkKey -> do
876876
g <- asks random
@@ -886,17 +886,16 @@ getConnShortLink' c userId = \case
886886
ld@(sndId, _) <- secureGetQueueLink c userId invLink
887887
withStore' c $ \db -> setInvShortLinkSndId db invLink sndId
888888
decryptData srv linkKey k ld
889-
CSLContact srv _ linkKey -> do
889+
CSLContact _ srv linkKey -> do
890890
let (linkId, k) = SL.contactShortLinkKdf linkKey
891891
ld <- getQueueLink c userId srv linkId
892892
decryptData srv linkKey k ld
893893
where
894-
decryptData :: ConnectionModeI c => SMPServer -> LinkKey -> C.SbKey -> (SMP.SenderId, QueueLinkData) -> AM (Maybe (ConnectionRequestUri c), ConnInfo)
894+
decryptData :: ConnectionModeI c => SMPServer -> LinkKey -> C.SbKey -> (SMP.SenderId, QueueLinkData) -> AM (ConnectionRequestUri c, ConnInfo)
895895
decryptData srv linkKey k (sndId, d) = do
896-
r@(cReq_, _) <- liftEither $ SL.decryptLinkData @c linkKey k d
897-
forM_ cReq_ $ \cReq ->
898-
unless ((srv, sndId) `sameQAddress` qAddress (connReqQueue cReq)) $
899-
throwE $ AGENT $ A_LINK "different address"
896+
r@(cReq, _) <- liftEither $ SL.decryptLinkData @c linkKey k d
897+
unless ((srv, sndId) `sameQAddress` qAddress (connReqQueue cReq)) $
898+
throwE $ AGENT $ A_LINK "different address"
900899
pure r
901900

902901
deleteLocalInvShortLink' :: AgentClient -> ConnShortLink 'CMInvitation -> AM ()
@@ -979,7 +978,7 @@ newRcvConnSrv c userId connId enableNtfs cMode userData_ clientData pqInitKeys s
979978
Just ShortLinkCreds {shortLinkId, shortLinkKey}
980979
| qUri == qUri' ->
981980
let link = case cReq of
982-
CRContactUri _ -> CSLContact srv CCTContact shortLinkKey
981+
CRContactUri _ -> CSLContact CCTContact srv shortLinkKey
983982
CRInvitationUri {} -> CSLInvitation srv shortLinkId shortLinkKey
984983
in pure $ CCLink cReq (Just link)
985984
| otherwise -> throwE $ INTERNAL "different rcv queue address"

src/Simplex/Messaging/Agent/Protocol.hs

Lines changed: 100 additions & 37 deletions
Original file line numberDiff line numberDiff line change
@@ -109,7 +109,7 @@ module Simplex.Messaging.Agent.Protocol
109109
CRClientData,
110110
ServiceScheme,
111111
FixedLinkData (..),
112-
UserLinkData (..),
112+
ConnLinkData (..),
113113
OwnerAuth (..),
114114
OwnerId,
115115
ConnectionLink (..),
@@ -156,6 +156,7 @@ module Simplex.Messaging.Agent.Protocol
156156
updateSMPServerHosts,
157157
shortenShortLink,
158158
restoreShortLink,
159+
linkUserData,
159160
)
160161
where
161162

@@ -167,7 +168,7 @@ import qualified Data.Attoparsec.ByteString.Char8 as A
167168
import qualified Data.ByteString.Base64.URL as B64
168169
import Data.ByteString.Char8 (ByteString)
169170
import qualified Data.ByteString.Char8 as B
170-
import Data.Char (isDigit)
171+
import Data.Char (isDigit, toLower, toUpper)
171172
import Data.Foldable (find)
172173
import Data.Functor (($>))
173174
import Data.Int (Int64)
@@ -1349,7 +1350,7 @@ deriving instance Show AConnectionRequestUri
13491350

13501351
data ConnShortLink (m :: ConnectionMode) where
13511352
CSLInvitation :: SMPServer -> SMP.LinkId -> LinkKey -> ConnShortLink 'CMInvitation
1352-
CSLContact :: SMPServer -> ContactConnType -> LinkKey -> ConnShortLink 'CMContact
1353+
CSLContact :: ContactConnType -> SMPServer -> LinkKey -> ConnShortLink 'CMContact
13531354

13541355
deriving instance Eq (ConnShortLink m)
13551356

@@ -1369,7 +1370,7 @@ instance ConnectionModeI c => ToField (ConnShortLink c) where toField = toField
13691370

13701371
instance (Typeable c, ConnectionModeI c) => FromField (ConnShortLink c) where fromField = blobFieldDecoder strDecode
13711372

1372-
data ContactConnType = CCTContact | CCTGroup deriving (Eq, Show)
1373+
data ContactConnType = CCTContact | CCTChannel | CCTGroup deriving (Eq, Show)
13731374

13741375
data AConnShortLink = forall m. ConnectionModeI m => ACSL (SConnectionMode m) (ConnShortLink m)
13751376

@@ -1406,50 +1407,84 @@ instance ConnectionModeI m => FromJSON (ConnectionLink m) where
14061407

14071408
instance ConnectionModeI m => StrEncoding (ConnShortLink m) where
14081409
strEncode = \case
1409-
CSLInvitation srv (SMP.EntityId lnkId) (LinkKey k) -> encLink srv (lnkId <> k) "i"
1410-
CSLContact srv ct (LinkKey k) -> encLink srv k $ case ct of CCTContact -> "c"; CCTGroup -> "g"
1410+
CSLInvitation srv (SMP.EntityId lnkId) (LinkKey k) -> encLink srv (lnkId <> k) 'i'
1411+
CSLContact ct srv (LinkKey k) -> encLink srv k $ toLower $ ctTypeChar ct
14111412
where
14121413
encLink (SMPServer (h :| hs) port (C.KeyHash kh)) linkUri linkType =
1413-
"https://" <> strEncode h <> port' <> "/" <> linkType <> "#" <> khStr <> hosts <> B64.encodeUnpadded linkUri
1414+
B.concat ["https://", strEncode h, port', "/", B.singleton linkType, "#", khStr, hosts, B64.encodeUnpadded linkUri]
14141415
where
14151416
port' = if null port then "" else B.pack (':' : port)
14161417
hosts = if null hs then "" else strEncode (TransportHosts_ hs) <> "/"
14171418
khStr = if B.null kh then "" else B64.encodeUnpadded kh <> "@"
1418-
strP = do
1419-
ACSL m l <- strP
1420-
case testEquality m $ sConnectionMode @m of
1421-
Just Refl -> pure l
1422-
_ -> fail "bad short link mode"
1419+
strP = (\(ACSL _ l) -> checkConnMode l) <$?> strP
1420+
{-# INLINE strP #-}
14231421

14241422
instance StrEncoding AConnShortLink where
14251423
strEncode (ACSL _ l) = strEncode l
1424+
{-# INLINE strEncode #-}
14261425
strP = do
14271426
h <- "https://" *> strP
14281427
port <- A.char ':' *> (B.unpack <$> A.takeWhile1 isDigit) <|> pure ""
1429-
linkType <- A.char '/' *> A.anyChar
1428+
contactType <- A.char '/' *> contactTypeP
14301429
keyHash <- optional (A.char '/') *> A.char '#' *> (strP <* A.char '@' <|> pure (C.KeyHash ""))
14311430
TransportHosts_ hs <- strP <* "/" <|> pure (TransportHosts_ [])
14321431
linkUri <- strP
14331432
let srv = SMPServer (h :| hs) port keyHash
1434-
case linkType of
1435-
'i'
1433+
case contactType of
1434+
Nothing
14361435
| B.length linkUri == 56 ->
14371436
let (lnkId, k) = B.splitAt 24 linkUri
14381437
in pure $ ACSL SCMInvitation $ CSLInvitation srv (SMP.EntityId lnkId) (LinkKey k)
14391438
| otherwise -> fail "bad ConnShortLink: incorrect linkID and key length"
1440-
'c' -> contactP srv CCTContact linkUri
1441-
'g' -> contactP srv CCTGroup linkUri
1442-
_ -> fail "bad ConnShortLink: unknown link type"
1439+
Just ct
1440+
| B.length linkUri == 32 -> pure $ ACSL SCMContact $ CSLContact ct srv (LinkKey linkUri)
1441+
| otherwise -> fail "bad ConnShortLink: incorrect key length"
14431442
where
1444-
contactP srv ct k
1445-
| B.length k == 32 = pure $ ACSL SCMContact $ CSLContact srv ct (LinkKey k)
1446-
| otherwise = fail "bad ConnShortLink: incorrect key length"
1443+
contactTypeP = do
1444+
Just <$> (A.anyChar >>= ctTypeP . toUpper)
1445+
<|> A.char 'i' $> Nothing
1446+
<|> fail "unknown link type"
1447+
1448+
instance ConnectionModeI m => Encoding (ConnShortLink m) where
1449+
smpEncode = \case
1450+
CSLInvitation srv lnkId (LinkKey k) -> smpEncode (CMInvitation, srv, lnkId, k)
1451+
CSLContact ct srv (LinkKey k) -> smpEncode (CMContact, ctTypeChar ct, srv, k)
1452+
smpP = (\(ACSL _ l) -> checkConnMode l) <$?> smpP
1453+
{-# INLINE smpP #-}
1454+
1455+
instance Encoding AConnShortLink where
1456+
smpEncode (ACSL _ l) = smpEncode l
1457+
{-# INLINE smpEncode #-}
1458+
smpP =
1459+
smpP >>= \case
1460+
CMInvitation -> do
1461+
(srv, lnkId, k) <- smpP
1462+
pure $ ACSL SCMInvitation $ CSLInvitation srv lnkId (LinkKey k)
1463+
CMContact -> do
1464+
ct <- ctTypeP =<< A.anyChar
1465+
(srv, k) <- smpP
1466+
pure $ ACSL SCMContact $ CSLContact ct srv (LinkKey k)
1467+
1468+
ctTypeP :: Char -> Parser ContactConnType
1469+
ctTypeP = \case
1470+
'A' -> pure CCTContact
1471+
'C' -> pure CCTChannel
1472+
'G' -> pure CCTGroup
1473+
_ -> fail "unknown contact address type"
1474+
{-# INLINE ctTypeP #-}
1475+
1476+
ctTypeChar :: ContactConnType -> Char
1477+
ctTypeChar = \case
1478+
CCTContact -> 'A'
1479+
CCTChannel -> 'C'
1480+
CCTGroup -> 'G'
1481+
{-# INLINE ctTypeChar #-}
14471482

14481483
-- the servers passed to this function should be all preset servers, not servers configured by the user.
14491484
shortenShortLink :: NonEmpty SMPServer -> ConnShortLink m -> ConnShortLink m
14501485
shortenShortLink presetSrvs = \case
14511486
CSLInvitation srv lnkId linkKey -> CSLInvitation (shortServer srv) lnkId linkKey
1452-
CSLContact srv ct linkKey -> CSLContact (shortServer srv) ct linkKey
1487+
CSLContact ct srv linkKey -> CSLContact ct (shortServer srv) linkKey
14531488
where
14541489
shortServer srv@(SMPServer hs@(h :| _) p kh) =
14551490
if isPresetServer then SMPServer [h] "" (C.KeyHash "") else srv
@@ -1465,7 +1500,7 @@ shortenShortLink presetSrvs = \case
14651500
restoreShortLink :: NonEmpty SMPServer -> ConnShortLink m -> ConnShortLink m
14661501
restoreShortLink presetSrvs = \case
14671502
CSLInvitation srv lnkId linkKey -> CSLInvitation (fullServer srv) lnkId linkKey
1468-
CSLContact srv ct linkKey -> CSLContact (fullServer srv) ct linkKey
1503+
CSLContact ct srv linkKey -> CSLContact ct (fullServer srv) linkKey
14691504
where
14701505
fullServer = \case
14711506
s@(SMPServer [_] "" (C.KeyHash "")) -> fromMaybe s $ findPresetServer s presetSrvs
@@ -1500,14 +1535,28 @@ type CRClientData = Text
15001535
data FixedLinkData c = FixedLinkData
15011536
{ agentVRange :: VersionRangeSMPA,
15021537
rootKey :: C.PublicKeyEd25519,
1503-
connReq :: Maybe (ConnectionRequestUri c)
1538+
connReq :: ConnectionRequestUri c
15041539
}
15051540

1506-
data UserLinkData = UserLinkData
1507-
{ agentVRange :: VersionRangeSMPA,
1508-
owners :: [OwnerAuth],
1509-
userData :: ConnInfo
1510-
}
1541+
data ConnLinkData c where
1542+
InvitationLinkData :: VersionRangeSMPA -> ConnInfo -> ConnLinkData 'CMInvitation
1543+
ContactLinkData ::
1544+
{ agentVRange :: VersionRangeSMPA,
1545+
-- direct connection via connReq in fixed data is allowed.
1546+
direct :: Bool,
1547+
-- additional owner keys to sign changes of mutable data.
1548+
owners :: [OwnerAuth],
1549+
-- alternative addresses of chat relays that receive requests for this contact address.
1550+
relays :: [ConnShortLink 'CMContact],
1551+
userData :: ConnInfo
1552+
} -> ConnLinkData 'CMContact
1553+
1554+
data AConnLinkData = forall m. ConnectionModeI m => ACLD (SConnectionMode m) (ConnLinkData m)
1555+
1556+
linkUserData :: ConnLinkData c -> ConnInfo
1557+
linkUserData = \case
1558+
InvitationLinkData _ d -> d
1559+
ContactLinkData {userData} -> userData
15111560

15121561
type OwnerId = ByteString
15131562

@@ -1540,14 +1589,28 @@ instance ConnectionModeI c => Encoding (FixedLinkData c) where
15401589
(agentVRange, rootKey, connReq) <- smpP
15411590
pure FixedLinkData {agentVRange, rootKey, connReq}
15421591

1543-
instance Encoding UserLinkData where
1544-
smpEncode UserLinkData {agentVRange, owners, userData} =
1545-
smpEncode agentVRange <> smpEncodeList owners <> smpEncode (Large userData)
1546-
smpP = do
1547-
agentVRange <- smpP
1548-
owners <- smpListP
1549-
Large userData <- smpP
1550-
pure UserLinkData {agentVRange, owners, userData}
1592+
instance ConnectionModeI c => Encoding (ConnLinkData c) where
1593+
smpEncode = \case
1594+
InvitationLinkData vr userData -> smpEncode (CMInvitation, vr, userData)
1595+
ContactLinkData {agentVRange, direct, owners, relays, userData} ->
1596+
B.concat [smpEncode (CMContact, agentVRange, direct), smpEncodeList owners, smpEncodeList relays, smpEncode userData]
1597+
smpP = (\(ACLD _ d) -> checkConnMode d) <$?> smpP
1598+
{-# INLINE smpP #-}
1599+
1600+
instance Encoding AConnLinkData where
1601+
smpEncode (ACLD _ d) = smpEncode d
1602+
{-# INLINE smpEncode #-}
1603+
smpP =
1604+
smpP >>= \case
1605+
CMInvitation -> do
1606+
(vr, userData) <- smpP
1607+
pure $ ACLD SCMInvitation $ InvitationLinkData vr userData
1608+
CMContact -> do
1609+
(agentVRange, direct) <- smpP
1610+
owners <- smpListP
1611+
relays <- smpListP
1612+
userData <- smpP
1613+
pure $ ACLD SCMContact ContactLinkData {agentVRange, direct, owners, relays, userData}
15511614

15521615
-- | SMP queue status.
15531616
data QueueStatus

src/Simplex/Messaging/Crypto/ShortLink.hs

Lines changed: 18 additions & 11 deletions
Original file line numberDiff line numberDiff line change
@@ -1,10 +1,12 @@
11
{-# LANGUAGE DataKinds #-}
22
{-# LANGUAGE DuplicateRecordFields #-}
3+
{-# LANGUAGE GADTs #-}
34
{-# LANGUAGE MultiWayIf #-}
45
{-# LANGUAGE NamedFieldPuns #-}
56
{-# LANGUAGE OverloadedStrings #-}
67
{-# LANGUAGE ScopedTypeVariables #-}
78
{-# LANGUAGE TupleSections #-}
9+
{-# LANGUAGE TypeApplications #-}
810

911
module Simplex.Messaging.Crypto.ShortLink
1012
( contactShortLinkKdf,
@@ -46,15 +48,20 @@ contactShortLinkKdf (LinkKey k) =
4648
invShortLinkKdf :: LinkKey -> C.SbKey
4749
invShortLinkKdf (LinkKey k) = C.unsafeSbKey $ C.hkdf "" k "SimpleXInvLink" 32
4850

49-
encodeSignLinkData :: ConnectionModeI c => C.KeyPair 'C.Ed25519 -> VersionRangeSMPA -> ConnectionRequestUri c -> ConnInfo -> (LinkKey, (ByteString, ByteString))
51+
encodeSignLinkData :: forall c. ConnectionModeI c => C.KeyPair 'C.Ed25519 -> VersionRangeSMPA -> ConnectionRequestUri c -> ConnInfo -> (LinkKey, (ByteString, ByteString))
5052
encodeSignLinkData (rootKey, pk) agentVRange connReq userData =
51-
let fd = smpEncode FixedLinkData {agentVRange, rootKey, connReq = Just connReq}
52-
ud = smpEncode UserLinkData {agentVRange, owners = [], userData}
53-
in (LinkKey (C.sha3_256 fd), (encodeSign pk fd, encodeSign pk ud))
53+
let fd = smpEncode FixedLinkData {agentVRange, rootKey, connReq}
54+
md = smpEncode $ connLinkData @c agentVRange userData
55+
in (LinkKey (C.sha3_256 fd), (encodeSign pk fd, encodeSign pk md))
5456

5557
encodeSignUserData :: C.PrivateKeyEd25519 -> VersionRangeSMPA -> ConnInfo -> ByteString
5658
encodeSignUserData pk agentVRange userData =
57-
encodeSign pk $ smpEncode UserLinkData {agentVRange, owners = [], userData}
59+
encodeSign pk $ smpEncode $ connLinkData @'CMContact agentVRange userData
60+
61+
connLinkData :: forall c. ConnectionModeI c => VersionRangeSMPA -> ConnInfo -> ConnLinkData c
62+
connLinkData agentVRange userData = case sConnectionMode @c of
63+
SCMInvitation -> InvitationLinkData agentVRange userData
64+
SCMContact -> ContactLinkData {agentVRange, direct = True, owners = [], relays = [], userData}
5865

5966
encodeSign :: C.PrivateKeyEd25519 -> ByteString -> ByteString
6067
encodeSign pk s = smpEncode (C.sign' pk s) <> s
@@ -73,17 +80,17 @@ encryptData g k len s = do
7380
ct <- liftEitherWith cryptoError $ C.sbEncrypt k nonce s len
7481
pure $ EncDataBytes $ smpEncode nonce <> ct
7582

76-
decryptLinkData :: ConnectionModeI c => LinkKey -> C.SbKey -> QueueLinkData -> Either AgentErrorType (Maybe (ConnectionRequestUri c), ConnInfo)
77-
decryptLinkData linkKey k (encFD, encUD) = do
83+
decryptLinkData :: forall c. ConnectionModeI c => LinkKey -> C.SbKey -> QueueLinkData -> Either AgentErrorType (ConnectionRequestUri c, ConnInfo)
84+
decryptLinkData linkKey k (encFD, encMD) = do
7885
(sig1, fd) <- decrypt encFD
79-
(sig2, ud) <- decrypt encUD
86+
(sig2, md) <- decrypt encMD
8087
FixedLinkData {rootKey, connReq} <- decode fd
81-
UserLinkData {userData} <- decode ud
88+
md' <- decode @(ConnLinkData c) md
8289
if
8390
| LinkKey (C.sha3_256 fd) /= linkKey -> linkErr "link data hash"
8491
| not (C.verify' rootKey sig1 fd) -> linkErr "link data signature"
85-
| not (C.verify' rootKey sig2 ud) -> linkErr "user data signature"
86-
| otherwise -> Right (connReq, userData)
92+
| not (C.verify' rootKey sig2 md) -> linkErr "user data signature"
93+
| otherwise -> Right (connReq, linkUserData md')
8794
where
8895
decrypt (EncDataBytes d) = do
8996
(nonce, Tail ct) <- decode d

tests/AgentTests/ConnectionRequestTests.hs

Lines changed: 13 additions & 13 deletions
Original file line numberDiff line numberDiff line change
@@ -279,22 +279,22 @@ connectionRequestTests =
279279
smpEncodingTest contactAddressV2
280280
smpEncodingTest contactAddressClientData
281281
it "should serialize / parse short links" $ do
282-
CSLContact srv CCTContact (LinkKey "0123456789abcdef0123456789abcdef") #==# "https://smp.simplex.im:5223/c#1234-w@jjbyvoemxysm7qxap7m5d5m35jzv5qq6gnlv7s4rsn7tdwwmuqciwpid.onion/MDEyMzQ1Njc4OWFiY2RlZjAxMjM0NTY3ODlhYmNkZWY"
283-
CSLContact srv CCTGroup (LinkKey "0123456789abcdef0123456789abcdef") #==# "https://smp.simplex.im:5223/g#1234-w@jjbyvoemxysm7qxap7m5d5m35jzv5qq6gnlv7s4rsn7tdwwmuqciwpid.onion/MDEyMzQ1Njc4OWFiY2RlZjAxMjM0NTY3ODlhYmNkZWY"
284-
CSLContact shortSrv CCTContact (LinkKey "0123456789abcdef0123456789abcdef") #==# "https://smp.simplex.im/c#MDEyMzQ1Njc4OWFiY2RlZjAxMjM0NTY3ODlhYmNkZWY"
282+
CSLContact CCTContact srv (LinkKey "0123456789abcdef0123456789abcdef") #==# "https://smp.simplex.im:5223/a#1234-w@jjbyvoemxysm7qxap7m5d5m35jzv5qq6gnlv7s4rsn7tdwwmuqciwpid.onion/MDEyMzQ1Njc4OWFiY2RlZjAxMjM0NTY3ODlhYmNkZWY"
283+
CSLContact CCTGroup srv (LinkKey "0123456789abcdef0123456789abcdef") #==# "https://smp.simplex.im:5223/g#1234-w@jjbyvoemxysm7qxap7m5d5m35jzv5qq6gnlv7s4rsn7tdwwmuqciwpid.onion/MDEyMzQ1Njc4OWFiY2RlZjAxMjM0NTY3ODlhYmNkZWY"
284+
CSLContact CCTContact shortSrv (LinkKey "0123456789abcdef0123456789abcdef") #==# "https://smp.simplex.im/a#MDEyMzQ1Njc4OWFiY2RlZjAxMjM0NTY3ODlhYmNkZWY"
285285
CSLInvitation srv (EntityId "0123456789abcdef01234567") (LinkKey "0123456789abcdef0123456789abcdef") #==# "https://smp.simplex.im:5223/i#1234-w@jjbyvoemxysm7qxap7m5d5m35jzv5qq6gnlv7s4rsn7tdwwmuqciwpid.onion/MDEyMzQ1Njc4OWFiY2RlZjAxMjM0NTY3MDEyMzQ1Njc4OWFiY2RlZjAxMjM0NTY3ODlhYmNkZWY"
286286
CSLInvitation shortSrv (EntityId "0123456789abcdef01234567") (LinkKey "0123456789abcdef0123456789abcdef") #==# "https://smp.simplex.im/i#MDEyMzQ1Njc4OWFiY2RlZjAxMjM0NTY3MDEyMzQ1Njc4OWFiY2RlZjAxMjM0NTY3ODlhYmNkZWY"
287287
it "should shorten / restore short links" $ do
288-
shortenShortLink [srv] (CSLContact srv CCTContact (LinkKey "0123456789abcdef0123456789abcdef"))
289-
`shouldBe` CSLContact shortSrv CCTContact (LinkKey "0123456789abcdef0123456789abcdef")
290-
shortenShortLink [srv] (CSLContact srv2 CCTContact (LinkKey "0123456789abcdef0123456789abcdef"))
291-
`shouldBe` CSLContact srv2 CCTContact (LinkKey "0123456789abcdef0123456789abcdef")
292-
restoreShortLink [srv] (CSLContact shortSrv CCTContact (LinkKey "0123456789abcdef0123456789abcdef"))
293-
`shouldBe` CSLContact srv CCTContact (LinkKey "0123456789abcdef0123456789abcdef")
294-
restoreShortLink [srv2] (CSLContact shortSrv CCTContact (LinkKey "0123456789abcdef0123456789abcdef"))
295-
`shouldBe` CSLContact shortSrv CCTContact (LinkKey "0123456789abcdef0123456789abcdef")
296-
restoreShortLink [srv] (CSLContact srv2 CCTContact (LinkKey "0123456789abcdef0123456789abcdef"))
297-
`shouldBe` CSLContact srv2 CCTContact (LinkKey "0123456789abcdef0123456789abcdef")
288+
shortenShortLink [srv] (CSLContact CCTContact srv (LinkKey "0123456789abcdef0123456789abcdef"))
289+
`shouldBe` CSLContact CCTContact shortSrv (LinkKey "0123456789abcdef0123456789abcdef")
290+
shortenShortLink [srv] (CSLContact CCTContact srv2 (LinkKey "0123456789abcdef0123456789abcdef"))
291+
`shouldBe` CSLContact CCTContact srv2 (LinkKey "0123456789abcdef0123456789abcdef")
292+
restoreShortLink [srv] (CSLContact CCTContact shortSrv (LinkKey "0123456789abcdef0123456789abcdef"))
293+
`shouldBe` CSLContact CCTContact srv (LinkKey "0123456789abcdef0123456789abcdef")
294+
restoreShortLink [srv2] (CSLContact CCTContact shortSrv (LinkKey "0123456789abcdef0123456789abcdef"))
295+
`shouldBe` CSLContact CCTContact shortSrv (LinkKey "0123456789abcdef0123456789abcdef")
296+
restoreShortLink [srv] (CSLContact CCTContact srv2 (LinkKey "0123456789abcdef0123456789abcdef"))
297+
`shouldBe` CSLContact CCTContact srv2 (LinkKey "0123456789abcdef0123456789abcdef")
298298
where
299299
smpEncodingTest a = smpDecode (smpEncode a) `shouldBe` Right a
300300

0 commit comments

Comments
 (0)