diff --git a/src/Vervis/Federation.hs b/src/Vervis/Federation.hs
index 085580f..51a9069 100644
--- a/src/Vervis/Federation.hs
+++ b/src/Vervis/Federation.hs
@@ -822,11 +822,12 @@ runDBExcept action = do
 deliverHttp
     :: (MonadSite m, SiteEnv m ~ App)
     => Doc Activity
+    -> Maybe LocalURI
     -> Text
     -> LocalURI
     -> m (Either APPostError (Response ()))
-deliverHttp doc h luInbox =
-    postActivity (l2f h luInbox) Nothing doc
+deliverHttp doc mfwd h luInbox =
+    postActivity (l2f h luInbox) (Left . l2f h <$> mfwd) doc
 
 isInstanceErrorHttp (InvalidUrlException _ _)    = False
 isInstanceErrorHttp (HttpExceptionRequest _ hec) =
@@ -934,7 +935,7 @@ handleOutboxNote host (Note mluNote luAttrib aud muParent muContext mpublished c
         Left (FedError t) -> throwE t
         Right r -> return r
     let handleDeliveryError e = logError $ "Outbox POST handler: delivery failed! " <> T.pack (displayException e)
-    lift $ forkHandler handleDeliveryError $ deliverRemoteHttp obid doc remotesHttp
+    lift $ forkHandler handleDeliveryError $ deliverRemoteHttp (furiHost uContext) obid doc remotesHttp
     return lmid
     where
     verifyNothing :: Monad m => Maybe a -> e -> ExceptT e m ()
@@ -1176,9 +1177,15 @@ handleOutboxNote host (Note mluNote luAttrib aud muParent muContext mpublished c
     fst3 :: (a, b, c) -> a
     fst3 (x, _, _) = x
 
+    fst4 :: (a, b, c, d) -> a
+    fst4 (x, _, _, _) = x
+
     thd3 :: (a, b, c) -> c
     thd3 (_, _, z) = z
 
+    fourth4 :: (a, b, c, d) -> d
+    fourth4 (_, _, _, w) = w
+
     -- Deliver to local recipients. For local users, find in DB and deliver.
     -- For local collections, expand them, deliver to local users, and return a
     -- list of remote actors found in them.
@@ -1187,7 +1194,7 @@ handleOutboxNote host (Note mluNote luAttrib aud muParent muContext mpublished c
         -> OutboxItemId
         -> [ShrIdent]
         -> Maybe (SharerId, FollowerSetId)
-        -> ExceptT Text AppDB [((InstanceId, Text), NonEmpty (RemoteActorId, LocalURI, Maybe UTCTime))]
+        -> ExceptT Text AppDB [((InstanceId, Text), NonEmpty (RemoteActorId, LocalURI, LocalURI, Maybe UTCTime))]
     deliverLocal pidAuthor obid recips mticket = do
         recipPids <- traverse getPersonId $ nub recips
         when (pidAuthor `elem` recipPids) $
@@ -1238,7 +1245,7 @@ handleOutboxNote host (Note mluNote luAttrib aud muParent muContext mpublished c
                           -- instances aren't repeated. Use a custom merge
                           -- where we can unionBy or LO.unionBy whenever both
                           -- lists have the same instance.
-                        , map (second $ NE.nubBy ((==) `on` fst3)) $ mergeConcat teamRemotes fsRemotes
+                        , map (second $ NE.nubBy ((==) `on` fst4)) $ mergeConcat teamRemotes fsRemotes
                         )
         lift $ for_ (union recipPids morePids) $ \ pid -> insert_ $ InboxItemLocal pid obid
         return remotes
@@ -1258,11 +1265,11 @@ handleOutboxNote host (Note mluNote luAttrib aud muParent muContext mpublished c
             case id_ of
                 Left pid -> return pid
                 Right _gid -> throwE "Local Note addresses a local group"
-        groupRemotes :: [(InstanceId, Text, RemoteActorId, LocalURI, Maybe UTCTime)] -> [((InstanceId, Text), NonEmpty (RemoteActorId, LocalURI, Maybe UTCTime))]
+        groupRemotes :: [(InstanceId, Text, RemoteActorId, LocalURI, LocalURI, Maybe UTCTime)] -> [((InstanceId, Text), NonEmpty (RemoteActorId, LocalURI, LocalURI, Maybe UTCTime))]
         groupRemotes = groupWithExtractBy ((==) `on` fst) fst snd . map toTuples
             where
-            toTuples (iid, h, rsid, lu, ms) = ((iid, h), (rsid, lu, ms))
-        getTicketTeam :: SharerId -> AppDB ([PersonId], [((InstanceId, Text), NonEmpty (RemoteActorId, LocalURI, Maybe UTCTime))])
+            toTuples (iid, h, rsid, luA, luI, ms) = ((iid, h), (rsid, luA, luI, ms))
+        getTicketTeam :: SharerId -> AppDB ([PersonId], [((InstanceId, Text), NonEmpty (RemoteActorId, LocalURI, LocalURI, Maybe UTCTime))])
         getTicketTeam sid = do
             id_ <- getPersonOrGroupId sid
             (,[]) <$> case id_ of
@@ -1270,7 +1277,7 @@ handleOutboxNote host (Note mluNote luAttrib aud muParent muContext mpublished c
                 Right gid ->
                     map (groupMemberPerson . entityVal) <$>
                         selectList [GroupMemberGroup ==. gid] []
-        getFollowers :: FollowerSetId -> AppDB ([PersonId], [((InstanceId, Text), NonEmpty (RemoteActorId, LocalURI, Maybe UTCTime))])
+        getFollowers :: FollowerSetId -> AppDB ([PersonId], [((InstanceId, Text), NonEmpty (RemoteActorId, LocalURI, LocalURI, Maybe UTCTime))])
         getFollowers fsid = do
             local <- selectList [FollowTarget ==. fsid] []
             remote <- E.select $ E.from $ \ (rf `E.InnerJoin` rs `E.InnerJoin` i) -> do
@@ -1282,14 +1289,15 @@ handleOutboxNote host (Note mluNote luAttrib aud muParent muContext mpublished c
                     ( i E.^. InstanceId
                     , i E.^. InstanceHost
                     , rs E.^. RemoteActorId
+                    , rs E.^. RemoteActorIdent
                     , rs E.^. RemoteActorInbox
                     , rs E.^. RemoteActorErrorSince
                     )
             return
                 ( map (followPerson . entityVal) local
                 , groupRemotes $
-                    map (\ (E.Value iid, E.Value h, E.Value rsid, E.Value luInbox, E.Value msince) ->
-                            (iid, h, rsid, luInbox, msince)
+                    map (\ (E.Value iid, E.Value h, E.Value rsid, E.Value luActor, E.Value luInbox, E.Value msince) ->
+                            (iid, h, rsid, luActor, luInbox, msince)
                         )
                         remote
                 )
@@ -1312,9 +1320,9 @@ handleOutboxNote host (Note mluNote luAttrib aud muParent muContext mpublished c
     deliverRemoteDB
         :: OutboxItemId
         -> [FedURI]
-        -> [((InstanceId, Text), NonEmpty (RemoteActorId, LocalURI, Maybe UTCTime))]
+        -> [((InstanceId, Text), NonEmpty (RemoteActorId, LocalURI, LocalURI, Maybe UTCTime))]
         -> AppDB
-            ( [((InstanceId, Text), NonEmpty (RemoteActorId, LocalURI, DeliveryId))]
+            ( [((InstanceId, Text), NonEmpty (RemoteActorId, LocalURI, LocalURI, DeliveryId))]
             , [((InstanceId, Text), NonEmpty (UnfetchedRemoteActorId, LocalURI, UnlinkedDeliveryId))]
             , [((InstanceId, Text), NonEmpty (UnfetchedRemoteActorId, LocalURI, UnlinkedDeliveryId))]
             )
@@ -1334,7 +1342,7 @@ handleOutboxNote host (Note mluNote luAttrib aud muParent muContext mpublished c
                                 Nothing -> Left lu
                                 Just e ->
                                     Right $ case e of
-                                        Left (Entity raid ra) -> Left (raid, remoteActorInbox ra, remoteActorErrorSince ra)
+                                        Left (Entity raid ra) -> Left (raid, remoteActorIdent ra, remoteActorInbox ra, remoteActorErrorSince ra)
                                         Right (Entity uraid ura) -> Right (uraid, unfetchedRemoteActorIdent ura, unfetchedRemoteActorSince ura)
                     let (unknown, newKnown) = partitionEithers $ NE.toList es
                         (fetched, unfetched) = partitionEithers newKnown
@@ -1343,9 +1351,9 @@ handleOutboxNote host (Note mluNote luAttrib aud muParent muContext mpublished c
             unfetched = mapMaybe (\ (i, (_, uf, _)) -> (i,) <$> uf) recips'
             stillUnknown = mapMaybe (\ (i, (_, _, uk)) -> (i,) <$> uk) recips'
             -- TODO see the earlier TODO about merge, it applies here too
-            allFetched = map (second $ NE.nubBy ((==) `on` fst3)) $ mergeConcat known moreKnown
+            allFetched = map (second $ NE.nubBy ((==) `on` fst4)) $ mergeConcat known moreKnown
         fetchedDeliv <- for allFetched $ \ (i, rs) ->
-            (i,) <$> insertMany' (\ (raid, _, msince) -> Delivery raid obid $ isNothing msince) rs
+            (i,) <$> insertMany' (\ (raid, _, _, msince) -> Delivery raid obid $ isNothing msince) rs
         unfetchedDeliv <- for unfetched $ \ (i, rs) ->
             (i,) <$> insertMany' (\ (uraid, _, msince) -> UnlinkedDelivery uraid obid $ isNothing msince) rs
         unknownDeliv <- for stillUnknown $ \ (i, lus) -> do
@@ -1353,8 +1361,8 @@ handleOutboxNote host (Note mluNote luAttrib aud muParent muContext mpublished c
             rs <- insertMany' (\ lu -> UnfetchedRemoteActor (fst i) lu Nothing) lus
             (i,) <$> insertMany' (\ (_, uraid) -> UnlinkedDelivery uraid obid True) rs
         return
-            ( takeNoError fetchedDeliv
-            , takeNoError unfetchedDeliv
+            ( takeNoError4 fetchedDeliv
+            , takeNoError3 unfetchedDeliv
             , map
                 (second $ NE.map $ \ ((lu, ak), dlk) -> (ak, lu, dlk))
                 unknownDeliv
@@ -1370,21 +1378,28 @@ handleOutboxNote host (Note mluNote luAttrib aud muParent muContext mpublished c
                     Just y' | length x == length y' -> NE.zip x y'
                     _ -> error "insertMany' returned different length!"
 
-        takeNoError = mapMaybe $ \ (i, rs) -> (i,) <$> nonEmpty (mapMaybe noError $ NE.toList rs)
+        takeNoError noError = mapMaybe $ \ (i, rs) -> (i,) <$> nonEmpty (mapMaybe noError $ NE.toList rs)
+        takeNoError3 = takeNoError noError
             where
             noError ((ak, lu, Nothing), dlk) = Just (ak, lu, dlk)
             noError ((_ , _ , Just _ ), _  ) = Nothing
+        takeNoError4 = takeNoError noError
+            where
+            noError ((ak, luA, luI, Nothing), dlk) = Just (ak, luA, luI, dlk)
+            noError ((_ , _  , _  , Just _ ), _  ) = Nothing
 
     deliverRemoteHttp
-        :: OutboxItemId
+        :: Text
+        -> OutboxItemId
         -> Doc Activity
-        -> ( [((InstanceId, Text), NonEmpty (RemoteActorId, LocalURI, DeliveryId))]
+        -> ( [((InstanceId, Text), NonEmpty (RemoteActorId, LocalURI, LocalURI, DeliveryId))]
            , [((InstanceId, Text), NonEmpty (UnfetchedRemoteActorId, LocalURI, UnlinkedDeliveryId))]
            , [((InstanceId, Text), NonEmpty (UnfetchedRemoteActorId, LocalURI, UnlinkedDeliveryId))]
            )
         -> Handler ()
-    deliverRemoteHttp obid doc (fetched, unfetched, unknown) = do
-        let deliver = deliverHttp doc
+    deliverRemoteHttp hContext obid doc (fetched, unfetched, unknown) = do
+        let deliver fwd h =
+                deliverHttp doc (if h == hContext then Just fwd else Nothing) h
         now <- liftIO getCurrentTime
         traverse_ (fork . deliverFetched deliver now) fetched
         traverse_ (fork . deliverUnfetched deliver now) unfetched
@@ -1392,8 +1407,8 @@ handleOutboxNote host (Note mluNote luAttrib aud muParent muContext mpublished c
         where
         fork = forkHandler $ \ e -> logError $ "Outbox POST handler: delivery failed! " <> T.pack (displayException e)
         deliverFetched deliver now ((_, h), recips@(r :| rs)) = do
-            let (raid, luInbox, dlid) = r
-            e <- deliver h luInbox
+            let (raid, luActor, luInbox, dlid) = r
+            e <- deliver luActor h luInbox
             let e' = case e of
                         Left err ->
                             if isInstanceErrorP err
@@ -1403,8 +1418,8 @@ handleOutboxNote host (Note mluNote luAttrib aud muParent muContext mpublished c
             case e' of
                 Nothing -> runDB $ do
                     let recips' = NE.toList recips
-                    updateWhere [RemoteActorId <-. map fst3 recips', RemoteActorErrorSince ==. Nothing] [RemoteActorErrorSince =. Just now]
-                    updateWhere [DeliveryId <-. map thd3 recips'] [DeliveryRunning =. False]
+                    updateWhere [RemoteActorId <-. map fst4 recips', RemoteActorErrorSince ==. Nothing] [RemoteActorErrorSince =. Just now]
+                    updateWhere [DeliveryId <-. map fourth4 recips'] [DeliveryRunning =. False]
                 Just success -> do
                     runDB $
                         if success
@@ -1412,9 +1427,9 @@ handleOutboxNote host (Note mluNote luAttrib aud muParent muContext mpublished c
                             else do
                                 updateWhere [RemoteActorId ==. raid, RemoteActorErrorSince ==. Nothing] [RemoteActorErrorSince =. Just now]
                                 update dlid [DeliveryRunning =. False]
-                    for_ rs $ \ (raid, luInbox, dlid) ->
+                    for_ rs $ \ (raid, luActor, luInbox, dlid) ->
                         fork $ do
-                            e <- deliver h luInbox
+                            e <- deliver luActor h luInbox
                             runDB $
                                 case e of
                                     Left _err -> do
@@ -1442,7 +1457,7 @@ handleOutboxNote host (Note mluNote luAttrib aud muParent muContext mpublished c
                             e <- fetchRemoteActor iid h luActor
                             case e of
                                 Right (Right (Entity raid ra)) -> do
-                                    e' <- deliver h $ remoteActorInbox ra
+                                    e' <- deliver luActor h $ remoteActorInbox ra
                                     runDB $
                                         case e' of
                                             Left _ -> do
@@ -1458,7 +1473,7 @@ handleOutboxNote host (Note mluNote luAttrib aud muParent muContext mpublished c
                             updateWhere [UnfetchedRemoteActorId ==. uraid, UnfetchedRemoteActorSince ==. Nothing] [UnfetchedRemoteActorSince =. Just now]
                             update udlid [UnlinkedDeliveryRunning =. False]
                         Just (Entity raid ra) -> do
-                            e'' <- deliver h $ remoteActorInbox ra
+                            e'' <- deliver luActor h $ remoteActorInbox ra
                             runDB $
                                 case e'' of
                                     Left _ -> do
@@ -1586,7 +1601,7 @@ retryOutboxDelivery = do
     deliverLinked deliver now ((_, h), recips) = do
         waitsR <- for recips $ \ ((raid, inbox), delivs) -> fork $ do
             waitsD <- for delivs $ \ (dlid, doc) -> fork $ do
-                e <- deliver doc h inbox
+                e <- deliver doc Nothing h inbox
                 case e of
                     Left _err -> return False
                     Right _resp -> do
@@ -1610,7 +1625,7 @@ retryOutboxDelivery = do
             case e of
                 Right (Right (Entity raid ra)) -> do
                     waitsD <- for delivs $ \ (udlid, obid, doc) -> fork $ do
-                        e' <- deliver doc h $ remoteActorInbox ra
+                        e' <- deliver doc Nothing h $ remoteActorInbox ra
                         case e' of
                             Left _err -> do
                                 runSiteDB $ do