コード例 #1
0
ファイル: DB.cs プロジェクト: pawelsudo1/Signal-Windows
        public static SignalGroup InsertOrUpdateGroupLocked(string groupId, string displayname, string avatarfile, bool canReceive, long timestamp, MainPageViewModel mpvm)
        {
            SignalGroup dbgroup;
            bool        is_new = false;

            lock (DBLock)
            {
                using (var ctx = new SignalDBContext())
                {
                    dbgroup = ctx.Groups
                              .Where(g => g.ThreadId == groupId)
                              .Include(g => g.GroupMemberships)
                              .ThenInclude(gm => gm.Contact)
                              .SingleOrDefault();
                    if (dbgroup == null)
                    {
                        is_new  = true;
                        dbgroup = new SignalGroup()
                        {
                            ThreadId            = groupId,
                            ThreadDisplayName   = displayname,
                            LastActiveTimestamp = timestamp,
                            AvatarFile          = avatarfile,
                            UnreadCount         = 0,
                            CanReceive          = canReceive,
                            GroupMemberships    = new List <GroupMembership>()
                        };
                        ctx.Add(dbgroup);
                    }
                    else
                    {
                        dbgroup.ThreadDisplayName   = displayname;
                        dbgroup.LastActiveTimestamp = timestamp;
                        dbgroup.AvatarFile          = avatarfile;
                        dbgroup.CanReceive          = true;
                    }
                    ctx.SaveChanges();
                }
                if (is_new)
                {
                    Windows.ApplicationModel.Core.CoreApplication.MainView.CoreWindow.Dispatcher.RunAsync(Windows.UI.Core.CoreDispatcherPriority.Normal, () =>
                    {
                        mpvm.AddThread(dbgroup);
                    }).AsTask().Wait();
                }
                else
                {
                    Windows.ApplicationModel.Core.CoreApplication.MainView.CoreWindow.Dispatcher.RunAsync(Windows.UI.Core.CoreDispatcherPriority.Normal, () =>
                    {
                        mpvm.UIUpdateThread(dbgroup);
                    }).AsTask().Wait();
                }
            }
            return(dbgroup);
        }
コード例 #2
0
 public static void DeleteAttachment(SignalAttachment attachment)
 {
     lock (DBLock)
     {
         using (var ctx = new SignalDBContext())
         {
             ctx.Remove(attachment);
             ctx.SaveChanges();
         }
     }
 }
コード例 #3
0
 private static SignalConversation GetSignalConversationByThreadId(SignalDBContext ctx, string id)
 {
     if (!id.EndsWith("="))
     {
         return(GetSignalContactByThreadId(ctx, id));
     }
     else
     {
         return(GetSignalGroupByThreadId(ctx, id));
     }
 }
コード例 #4
0
 public static void SaveMessageLocked(SignalMessage message)
 {
     lock (DBLock)
     {
         using (var ctx = new SignalDBContext())
         {
             SaveMessage(ctx, message);
             ctx.SaveChanges();
         }
     }
 }
コード例 #5
0
ファイル: DB.cs プロジェクト: pawelsudo1/Signal-Windows
 public static void UpdateAttachmentLocked(SignalAttachment sa)
 {
     lock (DBLock)
     {
         using (var ctx = new SignalDBContext())
         {
             ctx.Attachments.Update(sa);
             ctx.SaveChanges();
         }
     }
 }
コード例 #6
0
 public static SignalAttachment GetAttachmentByGuidNameLocked(string guid)
 {
     lock (DBLock)
     {
         using (var ctx = new SignalDBContext())
         {
             return(ctx.Attachments
                    .Where(a => a.Guid == guid)
                    .FirstOrDefault());
         }
     }
 }
コード例 #7
0
 public static void UpdateMessageExpiresAt(SignalMessage message)
 {
     lock (DBLock)
     {
         using (var ctx = new SignalDBContext())
         {
             var m = ctx.Messages.Single(t => t.Id == message.Id);
             m.ExpiresAt = message.ExpiresAt;
             ctx.SaveChanges();
         }
     }
 }
コード例 #8
0
ファイル: DB.cs プロジェクト: pawelsudo1/Signal-Windows
 public static void FailAllPendingMessages()
 {
     lock (DBLock)
     {
         using (var ctx = new SignalDBContext())
         {
             var messages = ctx.Messages
                            .Where(m => m.Direction == SignalMessageDirection.Outgoing && m.Status == SignalMessageStatus.Pending).ToList();
             messages.ForEach(m => m.Status = SignalMessageStatus.Failed_Unknown);
             ctx.SaveChanges();
         }
     }
 }
コード例 #9
0
 internal static void UpdateAttachmentStatus(SignalAttachment attachment)
 {
     lock (DBLock)
     {
         using (var ctx = new SignalDBContext())
         {
             var savedAttachment = ctx.Attachments
                                   .Where(a => a.Id == attachment.Id)
                                   .First();
             savedAttachment.Status = attachment.Status;
             ctx.SaveChanges();
         }
     }
 }
コード例 #10
0
 public static void UpdateExpiresInLocked(SignalConversation thread)
 {
     lock (DBLock)
     {
         using (var ctx = new SignalDBContext())
         {
             var dbConversation = GetSignalConversationByThreadId(ctx, thread.ThreadId);
             if (dbConversation != null)
             {
                 dbConversation.ExpiresInSeconds = thread.ExpiresInSeconds;
                 ctx.SaveChanges();
             }
         }
     }
 }
コード例 #11
0
ファイル: DB.cs プロジェクト: pawelsudo1/Signal-Windows
 public static List <SignalContact> GetAllContactsLocked()
 {
     lock (DBLock)
     {
         using (var ctx = new SignalDBContext())
         {
             return(ctx.Contacts
                    .OrderByDescending(c => c.LastActiveTimestamp)
                    .Include(g => g.LastMessage)
                    .ThenInclude(m => m.Content)
                    .AsNoTracking()
                    .ToList());
         }
     }
 }
コード例 #12
0
ファイル: DB.cs プロジェクト: pawelsudo1/Signal-Windows
        public static void Migrate()
        {
            lock (DBLock)
            {
                using (var ctx = new SignalDBContext())
                {
                    ctx.Database.Migrate();

                    /*
                     * var serviceProvider = ctx.GetInfrastructure<IServiceProvider>();
                     * var loggerFactory = serviceProvider.GetService<ILoggerFactory>();
                     * loggerFactory.AddProvider(new SqlLoggerProvider());
                     */
                }
            }
        }
コード例 #13
0
 /// <summary>
 /// Gets messages older than the given timestamp.
 /// </summary>
 /// <param name="timestamp">Timestamp in millis</param>
 /// <returns>Expired messages</returns>
 public static List <SignalMessage> GetExpiredMessages(long timestampMillis)
 {
     lock (DBLock)
     {
         using (var ctx = new SignalDBContext())
         {
             var messages = ctx.Messages
                            .Where(m => m.ExpiresAt > 0)
                            .Where(m => m.ExpiresAt < timestampMillis)
                            .Include(m => m.Attachments)
                            .Include(m => m.Content)
                            .AsNoTracking()
                            .ToList();
             return(messages);
         }
     }
 }
コード例 #14
0
ファイル: DB.cs プロジェクト: pawelsudo1/Signal-Windows
 public static List <SignalGroup> GetAllGroupsLocked()
 {
     lock (DBLock)
     {
         using (var ctx = new SignalDBContext())
         {
             return(ctx.Groups
                    .OrderByDescending(g => g.LastActiveTimestamp)
                    .Include(g => g.GroupMemberships)
                    .ThenInclude(gm => gm.Contact)
                    .Include(g => g.LastMessage)
                    .ThenInclude(m => m.Content)
                    .AsNoTracking()
                    .ToList());
         }
     }
 }
コード例 #15
0
 public static void InsertOrUpdateConversationLocked(SignalConversation conversation)
 {
     lock (DBLock)
     {
         using (var ctx = new SignalDBContext())
         {
             if (conversation is SignalContact contact)
             {
                 var c = ctx.Contacts.SingleOrDefault(b => b.ThreadId == conversation.ThreadId);
                 if (c == null)
                 {
                     ctx.Contacts.Add(contact);
                 }
                 else
                 {
                     c.Color             = contact.Color;
                     c.ThreadId          = conversation.ThreadId;
                     c.ThreadDisplayName = conversation.ThreadDisplayName;
                     c.CanReceive        = conversation.CanReceive;
                     c.AvatarFile        = conversation.AvatarFile;
                     c.Draft             = conversation.Draft;
                     c.UnreadCount       = conversation.UnreadCount;
                 }
             }
             else if (conversation is SignalGroup group)
             {
                 var c = ctx.Groups.SingleOrDefault(b => b.ThreadId == conversation.ThreadId);
                 if (c == null)
                 {
                     ctx.Groups.Add(group);
                 }
                 else
                 {
                     c.ThreadId          = conversation.ThreadId;
                     c.ThreadDisplayName = conversation.ThreadDisplayName;
                     c.CanReceive        = conversation.CanReceive;
                     c.AvatarFile        = conversation.AvatarFile;
                     c.Draft             = conversation.Draft;
                     c.UnreadCount       = conversation.UnreadCount;
                 }
             }
             ctx.SaveChanges();
         }
     }
 }
コード例 #16
0
ファイル: DB.cs プロジェクト: pawelsudo1/Signal-Windows
 public static void InsertOrUpdateGroupMembershipLocked(long groupid, long memberid)
 {
     lock (DBLock)
     {
         using (var ctx = new SignalDBContext())
         {
             var old = ctx.GroupMemberships.Where(g => g.GroupId == groupid && g.ContactId == memberid).SingleOrDefault();
             if (old == null)
             {
                 ctx.GroupMemberships.Add(new GroupMembership()
                 {
                     ContactId = memberid,
                     GroupId   = groupid
                 });
                 ctx.SaveChanges();
             }
         }
     }
 }
コード例 #17
0
ファイル: DB.cs プロジェクト: pawelsudo1/Signal-Windows
        public static void InsertOrUpdateContactLocked(SignalContact contact, MainPageViewModel mpvm)
        {
            bool is_new = false;

            lock (DBLock)
            {
                using (var ctx = new SignalDBContext())
                {
                    var c = ctx.Contacts.SingleOrDefault(b => b.ThreadId == contact.ThreadId);
                    if (c == null)
                    {
                        is_new = true;
                        ctx.Contacts.Add(contact);
                    }
                    else
                    {
                        c.Color             = contact.Color;
                        c.ThreadId          = contact.ThreadId;
                        c.ThreadDisplayName = contact.ThreadDisplayName;
                        c.CanReceive        = contact.CanReceive;
                        c.AvatarFile        = contact.AvatarFile;
                        c.Draft             = contact.Draft;
                        c.UnreadCount       = contact.UnreadCount;
                    }
                    ctx.SaveChanges();
                }
                if (is_new)
                {
                    Windows.ApplicationModel.Core.CoreApplication.MainView.CoreWindow.Dispatcher.RunAsync(Windows.UI.Core.CoreDispatcherPriority.Normal, () =>
                    {
                        mpvm.AddThread(contact);
                    }).AsTask().Wait();
                }
                else
                {
                    Windows.ApplicationModel.Core.CoreApplication.MainView.CoreWindow.Dispatcher.RunAsync(Windows.UI.Core.CoreDispatcherPriority.Normal, () =>
                    {
                        mpvm.UIUpdateThread(contact);
                    }).AsTask().Wait();
                }
            }
        }
コード例 #18
0
        public static SignalGroup InsertOrUpdateGroupLocked(string groupId, string displayname, string avatarfile, bool canReceive, long timestamp)
        {
            SignalGroup dbgroup;

            lock (DBLock)
            {
                using (var ctx = new SignalDBContext())
                {
                    dbgroup = ctx.Groups
                              .Where(g => g.ThreadId == groupId)
                              .Include(g => g.GroupMemberships)
                              .ThenInclude(gm => gm.Contact)
                              .SingleOrDefault();
                    if (dbgroup == null)
                    {
                        dbgroup = new SignalGroup()
                        {
                            ThreadId            = groupId,
                            ThreadDisplayName   = displayname,
                            LastActiveTimestamp = timestamp,
                            AvatarFile          = avatarfile,
                            UnreadCount         = 0,
                            CanReceive          = canReceive,
                            GroupMemberships    = new List <GroupMembership>()
                        };
                        ctx.Add(dbgroup);
                    }
                    else
                    {
                        dbgroup.ThreadDisplayName   = displayname;
                        dbgroup.LastActiveTimestamp = timestamp;
                        dbgroup.AvatarFile          = avatarfile;
                        dbgroup.CanReceive          = true;
                    }
                    ctx.SaveChanges();
                }
            }
            return(dbgroup);
        }
コード例 #19
0
ファイル: DB.cs プロジェクト: pawelsudo1/Signal-Windows
        public static void IncreaseReceiptCountLocked(SignalServiceEnvelope envelope, MainPageViewModel mpvm)
        {
            SignalMessage m;
            bool          set_mark = false;

            lock (DBLock)
            {
                using (var ctx = new SignalDBContext())
                {
                    m = ctx.Messages.SingleOrDefault(t => t.ComposedTimestamp == envelope.getTimestamp());
                    if (m != null)
                    {
                        m.Receipts++;
                        if (m.Status == SignalMessageStatus.Confirmed)
                        {
                            m.Status = SignalMessageStatus.Received;
                            set_mark = true;
                        }
                    }
                    else
                    {
                        ctx.EarlyReceipts.Add(new SignalEarlyReceipt()
                        {
                            DeviceId  = (uint)envelope.getSourceDevice(),
                            Timestamp = envelope.getTimestamp(),
                            Username  = envelope.getSource()
                        });
                    }
                    ctx.SaveChanges();
                }
            }
            if (set_mark)
            {
                Windows.ApplicationModel.Core.CoreApplication.MainView.CoreWindow.Dispatcher.RunAsync(Windows.UI.Core.CoreDispatcherPriority.Normal, () =>
                {
                    mpvm.UIUpdateMessageBox(m);
                }).AsTask().Wait();
            }
        }
コード例 #20
0
ファイル: DB.cs プロジェクト: pawelsudo1/Signal-Windows
        public static SignalContact GetOrCreateContactLocked(string username, long timestamp, MainPageViewModel mpvm)
        {
            SignalContact contact;
            bool          is_new = false;

            lock (DBLock)
            {
                using (var ctx = new SignalDBContext())
                {
                    contact = ctx.Contacts
                              .Where(c => c.ThreadId == username)
                              .SingleOrDefault();
                    if (contact == null)
                    {
                        is_new  = true;
                        contact = new SignalContact()
                        {
                            ThreadId            = username,
                            ThreadDisplayName   = username,
                            CanReceive          = true,
                            LastActiveTimestamp = timestamp,
                            Color = Utils.Colors[Utils.CalculateDefaultColorIndex(username)]
                        };
                        ctx.Contacts.Add(contact);
                        ctx.SaveChanges();
                    }
                }
                if (is_new)
                {
                    Windows.ApplicationModel.Core.CoreApplication.MainView.CoreWindow.Dispatcher.RunAsync(Windows.UI.Core.CoreDispatcherPriority.Normal, () =>
                    {
                        mpvm.AddThread(contact);
                    }).AsTask().Wait();
                }
            }
            return(contact);
        }
コード例 #21
0
        private static SignalConversation SaveMessage(SignalDBContext ctx, SignalMessage message)
        {
            if (message.Direction == SignalMessageDirection.Synced)
            {
                var receipts = ctx.EarlyReceipts
                               .Where(er => er.Timestamp == message.ComposedTimestamp)
                               .ToList();

                message.Receipts = (uint)receipts.Count;
                ctx.EarlyReceipts.RemoveRange(receipts);
                if (message.Receipts > 0)
                {
                    message.Status = SignalMessageStatus.Received;
                }
            }
            if (message.Author != null)
            {
                message.Author = GetSignalContactByThreadId(ctx, message.Author.ThreadId);
            }
            SignalConversation conversation = GetSignalConversationByThreadId(ctx, message.ThreadId);

            conversation.LastActiveTimestamp = message.ComposedTimestamp;
            conversation.LastMessage         = message;
            conversation.MessagesCount      += 1;
            if (message.Author == null)
            {
                conversation.UnreadCount          = 0;
                conversation.LastSeenMessageIndex = conversation.MessagesCount;
            }
            else
            {
                conversation.UnreadCount += 1;
            }
            ctx.Messages.Add(message);
            return(conversation);
        }
コード例 #22
0
        public static IEnumerable <SignalMessage> GetMessagesLocked(SignalConversation thread, int startIndex, int count)
        {
            Logger.LogTrace("GetMessagesLocked() skip {0} take {1}", startIndex, count);
            var messages = new List <SignalMessage>();

            lock (DBLock)
            {
                using (var ctx = new SignalDBContext())
                {
                    messages = ctx.Messages
                               .Where(m => m.ThreadId == thread.ThreadId)
                               .Include(m => m.Content)
                               .Include(m => m.Author)
                               .Include(m => m.Attachments)
                               .OrderBy(m => m.Id)
                               .Skip(startIndex)
                               .AsNoTracking()
                               .Take(count)
                               .ToList();
                }
            }
            Logger.LogTrace($"GetMessagesLocked() returning {messages.Count} messages");
            return(messages);
        }
コード例 #23
0
ファイル: DB.cs プロジェクト: pawelsudo1/Signal-Windows
        public static void SaveMessageLocked(SignalMessage message)
        {
            lock (DBLock)
            {
                using (var ctx = new SignalDBContext())
                {
                    long timestamp;
                    if (message.Direction == SignalMessageDirection.Synced)
                    {
                        var receipts = ctx.EarlyReceipts
                                       .Where(er => er.Timestamp == message.ComposedTimestamp)
                                       .ToList();

                        message.Receipts = (uint)receipts.Count;
                        ctx.EarlyReceipts.RemoveRange(receipts);
                        if (message.Receipts > 0)
                        {
                            message.Status = SignalMessageStatus.Received;
                        }
                    }
                    if (message.Author != null)
                    {
                        timestamp      = message.ReceivedTimestamp;
                        message.Author = ctx.Contacts.Where(a => a.Id == message.Author.Id).Single();
                    }
                    else
                    {
                        timestamp = message.ComposedTimestamp;
                    }
                    if (!message.ThreadId.EndsWith("="))
                    {
                        var contact = ctx.Contacts
                                      .Where(c => c.ThreadId == message.ThreadId)
                                      .Single();
                        contact.LastActiveTimestamp = timestamp;
                        contact.LastMessage         = message;
                        contact.MessagesCount      += 1;
                        if (message.Author == null)
                        {
                            contact.UnreadCount          = 0;
                            contact.LastSeenMessageIndex = contact.MessagesCount;
                        }
                        else
                        {
                            contact.UnreadCount += 1;
                        }
                    }
                    else
                    {
                        var group = ctx.Groups
                                    .Where(c => c.ThreadId == message.ThreadId)
                                    .Single();
                        message.ExpiresAt         = group.ExpiresInSeconds;
                        group.LastActiveTimestamp = timestamp;
                        group.LastMessage         = message;
                        group.MessagesCount      += 1;
                        if (message.Author == null)
                        {
                            group.UnreadCount          = 0;
                            group.LastSeenMessageIndex = group.MessagesCount;
                        }
                        else
                        {
                            group.UnreadCount += 1;
                        }
                    }
                    ctx.Messages.Add(message);
                    ctx.SaveChanges();
                }
            }
        }
コード例 #24
0
ファイル: DB.cs プロジェクト: pawelsudo1/Signal-Windows
        public static LinkedList <SignalMessage> InsertIdentityChangedMessages(string number)
        {
            long now = Util.CurrentTimeMillis();
            LinkedList <SignalMessage> messages = new LinkedList <SignalMessage>();

            lock (DBLock)
            {
                using (var ctx = new SignalDBContext())
                {
                    SignalContact contact = ctx.Contacts
                                            .Where(c => c.ThreadId == number)
                                            .SingleOrDefault();
                    if (contact != null)
                    {
                        string        str = $"Your safety numbers with {contact.ThreadDisplayName} have changed.";
                        SignalMessage msg = new SignalMessage()
                        {
                            Author            = contact,
                            ComposedTimestamp = now,
                            ReceivedTimestamp = now,
                            Direction         = SignalMessageDirection.Incoming,
                            Type     = SignalMessageType.IdentityKeyChange,
                            ThreadId = contact.ThreadId,
                            Content  = new SignalMessageContent()
                            {
                                Content = str
                            }
                        };
                        contact.LastMessage    = msg;
                        contact.MessagesCount += 1;
                        ctx.Messages.Add(msg);
                        messages.AddLast(msg);
                        var groups = ctx.GroupMemberships
                                     .Where(gm => gm.ContactId == contact.Id)
                                     .Include(gm => gm.Group);
                        foreach (var gm in groups)
                        {
                            msg = new SignalMessage()
                            {
                                Author            = contact,
                                ComposedTimestamp = now,
                                ReceivedTimestamp = now,
                                Direction         = SignalMessageDirection.Incoming,
                                Type     = SignalMessageType.IdentityKeyChange,
                                ThreadId = gm.Group.ThreadId,
                                Content  = new SignalMessageContent()
                                {
                                    Content = str
                                }
                            };
                            gm.Group.LastMessage    = msg;
                            gm.Group.MessagesCount += 1;
                            ctx.Messages.Add(msg);
                            messages.AddLast(msg);
                        }
                    }
                    else
                    {
                        Debug.WriteLine("InsertIdentityChangedMessages for non-existing contact!");
                    }
                    ctx.SaveChanges();
                }
            }
            return(messages);
        }
コード例 #25
0
 private static SignalGroup GetSignalGroupByThreadId(SignalDBContext ctx, string id)
 {
     return(ctx.Groups
            .Where(c => c.ThreadId == id)
            .SingleOrDefault());
 }
コード例 #26
0
 internal static SignalContact GetSignalContactByThreadId(SignalDBContext ctx, string id)
 {
     return(ctx.Contacts
            .Where(c => c.ThreadId == id)
            .SingleOrDefault());
 }