diff --git a/SignalServiceKit/src/Loki/API/Open Groups/PublicChatAPI.swift b/SignalServiceKit/src/Loki/API/Open Groups/PublicChatAPI.swift
index 09574bbe9..268175ba1 100644
--- a/SignalServiceKit/src/Loki/API/Open Groups/PublicChatAPI.swift	
+++ b/SignalServiceKit/src/Loki/API/Open Groups/PublicChatAPI.swift	
@@ -122,13 +122,16 @@ public final class PublicChatAPI : DotNetAPI {
                     return rawMessages.flatMap { message in
                         let isDeleted = (message["is_deleted"] as? Int == 1)
                         guard !isDeleted else { return nil }
+                        let dateFormatter = DateFormatter()
+                        dateFormatter.dateFormat = "yyyy-MM-dd'T'HH:mm:ss.SSSZ"
                         guard let annotations = message["annotations"] as? [JSON], let annotation = annotations.first(where: { $0["type"] as? String == publicChatMessageType }), let value = annotation["value"] as? JSON,
                             let serverID = message["id"] as? UInt64, let hexEncodedSignatureData = value["sig"] as? String, let signatureVersion = value["sigver"] as? UInt64,
                             let body = message["text"] as? String, let user = message["user"] as? JSON, let hexEncodedPublicKey = user["username"] as? String,
-                            let timestamp = value["timestamp"] as? UInt64 else {
+                            let timestamp = value["timestamp"] as? UInt64, let dateAsString = message["created_at"] as? String, let date = dateFormatter.date(from: dateAsString) else {
                                 print("[Loki] Couldn't parse message for public chat channel with ID: \(channel) on server: \(server) from: \(message).")
                                 return nil
                         }
+                        let servertTimestamp = UInt64(date.timeIntervalSince1970) * 1000
                         var profilePicture: PublicChatMessage.ProfilePicture? = nil
                         let displayName = user["name"] as? String ?? NSLocalizedString("Anonymous", comment: "")
                         if let userAnnotations = user["annotations"] as? [JSON], let profilePictureAnnotation = userAnnotations.first(where: { $0["type"] as? String == profilePictureType }),
@@ -168,7 +171,7 @@ public final class PublicChatAPI : DotNetAPI {
                                 width: width, height: height, caption: caption, url: url, linkPreviewURL: linkPreviewURL, linkPreviewTitle: linkPreviewTitle)
                         }
                         let result = PublicChatMessage(serverID: serverID, senderPublicKey: hexEncodedPublicKey, displayName: displayName, profilePicture: profilePicture,
-                            body: body, type: publicChatMessageType, timestamp: timestamp, quote: quote, attachments: attachments, signature: signature)
+                            body: body, type: publicChatMessageType, timestamp: timestamp, quote: quote, attachments: attachments, signature: signature, serverTimestamp: servertTimestamp)
                         guard result.hasValidSignature() else {
                             print("[Loki] Ignoring public chat message with invalid signature.")
                             return nil
@@ -182,7 +185,7 @@ public final class PublicChatAPI : DotNetAPI {
                             return nil
                         }
                         return result
-                    }.sorted { $0.timestamp < $1.timestamp }
+                    }.sorted { $0.serverTimestamp < $1.serverTimestamp}
                 }
             }
         }.handlingInvalidAuthTokenIfNeeded(for: server)
@@ -217,7 +220,7 @@ public final class PublicChatAPI : DotNetAPI {
                                 throw DotNetAPIError.parsingFailed
                             }
                             let timestamp = UInt64(date.timeIntervalSince1970) * 1000
-                            return PublicChatMessage(serverID: serverID, senderPublicKey: getUserHexEncodedPublicKey(), displayName: displayName, profilePicture: signedMessage.profilePicture, body: body, type: publicChatMessageType, timestamp: timestamp, quote: signedMessage.quote, attachments: signedMessage.attachments, signature: signedMessage.signature)
+                            return PublicChatMessage(serverID: serverID, senderPublicKey: getUserHexEncodedPublicKey(), displayName: displayName, profilePicture: signedMessage.profilePicture, body: body, type: publicChatMessageType, timestamp: timestamp, quote: signedMessage.quote, attachments: signedMessage.attachments, signature: signedMessage.signature, serverTimestamp: timestamp)
                         }
                     }
                 }.handlingInvalidAuthTokenIfNeeded(for: server)
diff --git a/SignalServiceKit/src/Loki/API/Open Groups/PublicChatMessage.swift b/SignalServiceKit/src/Loki/API/Open Groups/PublicChatMessage.swift
index 6445ebf03..780f1fa52 100644
--- a/SignalServiceKit/src/Loki/API/Open Groups/PublicChatMessage.swift	
+++ b/SignalServiceKit/src/Loki/API/Open Groups/PublicChatMessage.swift	
@@ -14,6 +14,9 @@ public final class PublicChatMessage : NSObject {
     public var attachments: [Attachment] = []
     public let signature: Signature?
     
+    // MARK: Server Timestamp (use for sorting)
+    public let serverTimestamp: UInt64
+    
     @objc(serverID)
     public var objc_serverID: UInt64 { return serverID ?? 0 }
     
@@ -72,7 +75,7 @@ public final class PublicChatMessage : NSObject {
     }
     
     // MARK: Initialization
-    public init(serverID: UInt64?, senderPublicKey: String, displayName: String, profilePicture: ProfilePicture?, body: String, type: String, timestamp: UInt64, quote: Quote?, attachments: [Attachment], signature: Signature?) {
+    public init(serverID: UInt64?, senderPublicKey: String, displayName: String, profilePicture: ProfilePicture?, body: String, type: String, timestamp: UInt64, quote: Quote?, attachments: [Attachment], signature: Signature?, serverTimestamp: UInt64) {
         self.serverID = serverID
         self.senderPublicKey = senderPublicKey
         self.displayName = displayName
@@ -83,10 +86,11 @@ public final class PublicChatMessage : NSObject {
         self.quote = quote
         self.attachments = attachments
         self.signature = signature
+        self.serverTimestamp = serverTimestamp
         super.init()
     }
     
-    @objc public convenience init(senderPublicKey: String, displayName: String, body: String, type: String, timestamp: UInt64, quotedMessageTimestamp: UInt64, quoteePublicKey: String?, quotedMessageBody: String?, quotedMessageServerID: UInt64, signatureData: Data?, signatureVersion: UInt64) {
+    @objc public convenience init(senderPublicKey: String, displayName: String, body: String, type: String, timestamp: UInt64, quotedMessageTimestamp: UInt64, quoteePublicKey: String?, quotedMessageBody: String?, quotedMessageServerID: UInt64, signatureData: Data?, signatureVersion: UInt64, serverTimestamp: UInt64) {
         let quote: Quote?
         if quotedMessageTimestamp != 0, let quoteeHexEncodedPublicKey = quoteePublicKey, let quotedMessageBody = quotedMessageBody {
             let quotedMessageServerID = (quotedMessageServerID != 0) ? quotedMessageServerID : nil
@@ -100,7 +104,7 @@ public final class PublicChatMessage : NSObject {
         } else {
             signature = nil
         }
-        self.init(serverID: nil, senderPublicKey: senderPublicKey, displayName: displayName, profilePicture: nil, body: body, type: type, timestamp: timestamp, quote: quote, attachments: [], signature: signature)
+        self.init(serverID: nil, senderPublicKey: senderPublicKey, displayName: displayName, profilePicture: nil, body: body, type: type, timestamp: timestamp, quote: quote, attachments: [], signature: signature, serverTimestamp: serverTimestamp)
     }
     
     // MARK: Crypto
@@ -115,7 +119,7 @@ public final class PublicChatMessage : NSObject {
             return nil
         }
         let signature = Signature(data: signatureData, version: signatureVersion)
-        return PublicChatMessage(serverID: serverID, senderPublicKey: senderPublicKey, displayName: displayName, profilePicture: profilePicture, body: body, type: type, timestamp: timestamp, quote: quote, attachments: attachments, signature: signature)
+        return PublicChatMessage(serverID: serverID, senderPublicKey: senderPublicKey, displayName: displayName, profilePicture: profilePicture, body: body, type: type, timestamp: timestamp, quote: quote, attachments: attachments, signature: signature, serverTimestamp: serverTimestamp)
     }
     
     internal func hasValidSignature() -> Bool {
diff --git a/SignalServiceKit/src/Loki/API/Open Groups/PublicChatPoller.swift b/SignalServiceKit/src/Loki/API/Open Groups/PublicChatPoller.swift
index 3e4efc7e1..5779c3e1d 100644
--- a/SignalServiceKit/src/Loki/API/Open Groups/PublicChatPoller.swift	
+++ b/SignalServiceKit/src/Loki/API/Open Groups/PublicChatPoller.swift	
@@ -75,7 +75,7 @@ public final class PublicChatPoller : NSObject {
                 }
                  */
                 // Sorting the messages by timestamp before importing them fixes an issue where messages that quote older messages can't find those older messages
-                messages.sorted { $0.timestamp < $1.timestamp }.forEach { message in
+                messages.sorted { $0.serverTimestamp < $1.serverTimestamp }.forEach { message in
                     var wasSentByCurrentUser = false
                     OWSPrimaryStorage.shared().dbReadConnection.read { transaction in
                         wasSentByCurrentUser = LokiDatabaseUtilities.isUserLinkedDevice(message.senderPublicKey, transaction: transaction)
diff --git a/SignalServiceKit/src/Messages/Interactions/TSInteraction.m b/SignalServiceKit/src/Messages/Interactions/TSInteraction.m
index 83af87902..07009a22c 100644
--- a/SignalServiceKit/src/Messages/Interactions/TSInteraction.m
+++ b/SignalServiceKit/src/Messages/Interactions/TSInteraction.m
@@ -5,6 +5,7 @@
 #import "TSInteraction.h"
 #import "TSDatabaseSecondaryIndexes.h"
 #import "TSThread.h"
+#import "TSGroupThread.h"
 #import <SessionCoreKit/NSDate+OWS.h>
 #import <SessionServiceKit/SessionServiceKit-Swift.h>
 
@@ -191,6 +192,18 @@ NSString *NSStringFromOWSInteractionType(OWSInteractionType value)
     // Loki: Sort the messages by the sender's timestamp (Signal uses sortId)
     uint64_t sortId1 = self.timestamp;
     uint64_t sortId2 = other.timestamp;
+    
+    // Loki: In open groups, we use the server time to sort the messages
+    //       SortId represents the order that a message is processed
+    //       Since we have sorted the messages in the poller using server time
+    //       SortId can represent the order by server time.
+    if (self.thread.isGroupThread) {
+        TSGroupThread *thread = (TSGroupThread *)self.thread;
+        if (thread.isPublicChat) {
+            sortId1 = self.sortId;
+            sortId2 = other.sortId;
+        }
+    }
 
     if (sortId1 > sortId2) {
         return NSOrderedDescending;
diff --git a/SignalServiceKit/src/Messages/OWSMessageSender.m b/SignalServiceKit/src/Messages/OWSMessageSender.m
index a5e64e1cb..f87c8ab6b 100644
--- a/SignalServiceKit/src/Messages/OWSMessageSender.m
+++ b/SignalServiceKit/src/Messages/OWSMessageSender.m
@@ -1043,7 +1043,7 @@ NSString *const OWSMessageSenderRateLimitedException = @"RateLimitedException";
         }
         NSString *body = (message.body != nil && message.body.length > 0) ? message.body : [NSString stringWithFormat:@"%@", @(message.timestamp)]; // Workaround for the fact that the back-end doesn't accept messages without a body
         LKPublicChatMessage *groupMessage = [[LKPublicChatMessage alloc] initWithSenderPublicKey:userPublicKey displayName:displayName body:body type:LKPublicChatAPI.publicChatMessageType
-         timestamp:message.timestamp quotedMessageTimestamp:quoteID quoteePublicKey:quoteePublicKey quotedMessageBody:quote.body quotedMessageServerID:quotedMessageServerID signatureData:nil signatureVersion:0];
+                                                                                       timestamp:message.timestamp quotedMessageTimestamp:quoteID quoteePublicKey:quoteePublicKey quotedMessageBody:quote.body quotedMessageServerID:quotedMessageServerID signatureData:nil signatureVersion:0 serverTimestamp:0];
         OWSLinkPreview *linkPreview = message.linkPreview;
         if (linkPreview != nil) {
             TSAttachmentStream *attachment = [TSAttachmentStream fetchObjectWithUniqueID:linkPreview.imageAttachmentId];