예제 #1
0
        private static void ProcessSubFolders(this Vault vault, SyncDownResponse rs)
        {
            var comparers  = new Comparers();
            var folderList = new SortedSet <IFolderNode>(vault.userFolders.Values, comparers);
            var recordList = new SortedSet <IRecordNode>(vault.userFolderRecords ?? Enumerable.Empty <IRecordNode>(), comparers);

            if (rs.userFoldersRemoved != null)
            {
                foreach (var ufr in rs.userFoldersRemoved)
                {
                    folderList.RemoveWhere(x => x.FolderUid == ufr.folderUid);
                    recordList.RemoveWhere(x => x.FolderUid == ufr.folderUid);
                }
            }

            if (rs.sharedFolderFolderRemoved != null)
            {
                foreach (var sffr in rs.sharedFolderFolderRemoved)
                {
                    folderList.RemoveWhere(x => x.FolderUid == sffr.folderUid);
                    recordList.RemoveWhere(x => x.FolderUid == sffr.folderUid);
                }
            }

            if (rs.userFolderSharedFoldersRemoved != null)
            {
                foreach (var ufsfr in rs.userFolderSharedFoldersRemoved)
                {
                    folderList.RemoveWhere(x => x.FolderUid == ufsfr.folderUid);
                    recordList.RemoveWhere(x => x.FolderUid == ufsfr.folderUid);
                }
            }

            if (rs.userFoldersRemovedRecords != null)
            {
                foreach (var uffr in rs.userFoldersRemovedRecords)
                {
                    recordList.Remove(uffr);
                }
            }

            if (rs.sharedFolderFolderRecordsRemoved != null)
            {
                foreach (var sffrr in rs.sharedFolderFolderRecordsRemoved)
                {
                    recordList.Remove(sffrr);
                }
            }

            if (rs.userFolders != null)
            {
                foreach (var uf in rs.userFolders)
                {
                    var encryptedKey = uf.userFolderKey.Base64UrlDecode();
                    uf.unencryptedFolderKey = uf.keyType == 2
                        ? CryptoUtils.DecryptRsa(encryptedKey, vault.Auth.PrivateKey)
                        : CryptoUtils.DecryptAesV1(encryptedKey, vault.Auth.DataKey);
                    folderList.Remove(uf);
                    folderList.Add(uf);
                }
            }

            if (rs.sharedFolderFolders != null)
            {
                foreach (var sff in rs.sharedFolderFolders)
                {
                    if (vault.sharedFolders.TryGetValue(sff.sharedFolderUid, out SyncDownSharedFolder sf))
                    {
                        var encryptedKey = sff.sharedFolderFolderKey.Base64UrlDecode();
                        sff.unencryptedFolderKey = CryptoUtils.DecryptAesV1(encryptedKey, sf.unencryptedSharedFolderKey);
                        folderList.Remove(sff);
                        folderList.Add(sff);
                    }
                    else
                    {
                        Trace.TraceError("Sync_Down: shared_folder_folders: Shared Folder UID {0} not found", sff.sharedFolderUid);
                    }
                }
            }

            if (rs.userFolderSharedFolders != null)
            {
                foreach (var ufsf in rs.userFolderSharedFolders)
                {
                    folderList.Remove(ufsf);
                    folderList.Add(ufsf);
                }
            }

            if (rs.userFolderRecords != null)
            {
                foreach (var ufr in rs.userFolderRecords)
                {
                    recordList.Add(ufr);
                }
            }

            if (rs.sharedFolderFolderRecords != null)
            {
                foreach (var sffr in rs.sharedFolderFolderRecords)
                {
                    recordList.Add(sffr);
                }
            }

            var toDelete = new HashSet <string>();

            foreach (var folder in vault.keeperFolders.Values)
            {
                toDelete.Add(folder.FolderUid);
                folder.Children.Clear();
                folder.Records.Clear();
            }
            foreach (var folder in folderList)
            {
                if (vault.keeperFolders.TryGetValue(folder.FolderUid, out FolderNode node))
                {
                    toDelete.Remove(folder.FolderUid);
                    node.Children.Clear();
                    node.Records.Clear();
                    node.Name = null;
                }
                else
                {
                    node = new FolderNode
                    {
                        FolderType = folder.Type,
                        FolderUid  = folder.FolderUid
                    };
                    vault.keeperFolders.Add(folder.FolderUid, node);
                }
                node.ParentUid = folder.ParentUid;

                byte[] unencrypted_data = null;
                switch (folder.Type)
                {
                case FolderType.UserFolder:
                    if (folder is SyncDownUserFolder uf)
                    {
                        unencrypted_data = CryptoUtils.DecryptAesV1(uf.data.Base64UrlDecode(), uf.unencryptedFolderKey);
                    }
                    else
                    {
                        Trace.TraceError("Folder UID {0} expected to be User-Folder", folder.FolderUid);
                    }
                    break;

                case FolderType.SharedFolderForder:
                    if (folder is SyncDownSharedFolderFolder sff)
                    {
                        unencrypted_data = CryptoUtils.DecryptAesV1(sff.data.Base64UrlDecode(), sff.unencryptedFolderKey);
                    }
                    else
                    {
                        Trace.TraceError("Folder UID {0} expected to be Shared-Folder-Folder", folder.FolderUid);
                    }
                    break;

                case FolderType.SharedFolder:
                    if (vault.sharedFolders.TryGetValue(folder.FolderUid, out SyncDownSharedFolder sf))
                    {
                        node.Name = Encoding.UTF8.GetString(CryptoUtils.DecryptAesV1(sf.name.Base64UrlDecode(), sf.unencryptedSharedFolderKey));
                    }
                    else
                    {
                        Trace.TraceError("Folder UID {0} expected to be Shared-Folder", folder.FolderUid);
                    }
                    break;
                }
                if (unencrypted_data != null)
                {
                    var serializer = new DataContractJsonSerializer(typeof(FolderData));
                    using (var stream = new MemoryStream(unencrypted_data))
                    {
                        var folderData = serializer.ReadObject(stream) as FolderData;
                        node.Name = folderData.name;
                    }
                }
                if (string.IsNullOrEmpty(node.Name))
                {
                    node.Name = node.FolderUid;
                }
            }
            foreach (var uid in toDelete)
            {
                vault.keeperFolders.Remove(uid);
            }
            vault.Root.Children.Clear();
            vault.Root.Records.Clear();

            foreach (var node in vault.keeperFolders.Values)
            {
                if (string.IsNullOrEmpty(node.ParentUid))
                {
                    vault.Root.Children.Add(node.FolderUid);
                }
                else
                {
                    if (vault.keeperFolders.TryGetValue(node.ParentUid, out FolderNode parent))
                    {
                        parent.Children.Add(node.FolderUid);
                    }
                    else
                    {
                        Trace.TraceError("Folder UID {0} was lost", node.FolderUid);
                    }
                }
            }

            foreach (var record in recordList)
            {
                if (string.IsNullOrEmpty(record.FolderUid))
                {
                    vault.Root.Records.Add(record.RecordUid);
                }
                else
                {
                    if (vault.keeperFolders.TryGetValue(record.FolderUid, out FolderNode node))
                    {
                        node.Records.Add(record.RecordUid);
                    }
                    else
                    {
                        Trace.TraceError("Folder UID {0} was lost", node.FolderUid);
                        vault.Root.Records.Add(record.RecordUid);
                    }
                }
            }

            vault.userFolders.Clear();
            foreach (var folder in folderList)
            {
                vault.userFolders.Add(folder.FolderUid, folder);
            }
            vault.userFolderRecords = recordList.ToList();
        }
예제 #2
0
 public bool TryGetFolder(string folderUid, out FolderNode node)
 {
     return(keeperFolders.TryGetValue(folderUid, out node));
 }