internal static PasswordRecord Load(this IPasswordRecord r, byte[] key) { var record = new PasswordRecord() { RecordKey = key, Uid = r.RecordUid, Shared = r.Shared, Owner = r.Owner, ClientModified = r.ClientModifiedTime != 0 ? DateTimeOffsetExtensions.FromUnixTimeMilliseconds(r.ClientModifiedTime) : DateTimeOffset.Now, }; var data = r.Data.Base64UrlDecode(); data = CryptoUtils.DecryptAesV1(data, key); using (var ms = new MemoryStream(data)) { var parsedData = (RecordData)DataSerializer.ReadObject(ms); record.Title = parsedData.title; record.Login = parsedData.secret1; record.Password = parsedData.secret2; record.Link = parsedData.link; record.Notes = parsedData.notes; if (parsedData.custom != null) { foreach (var cr in parsedData.custom) { record.Custom.Add(new CustomField { Name = cr.name, Value = cr.value, Type = cr.type }); } } } if (!string.IsNullOrEmpty(r.Extra)) { var extra = CryptoUtils.DecryptAesV1(r.Extra.Base64UrlDecode(), key); using (var ms = new MemoryStream(extra)) { var parsedExtra = (RecordExtra)ExtraSerializer.ReadObject(ms); if (parsedExtra.files != null && parsedExtra.files.Length > 0) { foreach (var file in parsedExtra.files) { var atta = new AttachmentFile { Id = file.id, Key = file.key, Name = file.name, Title = file.title ?? "", Type = file.type ?? "", Size = file.size ?? 0, LastModified = file.lastModified != null ? DateTimeOffsetExtensions.FromUnixTimeMilliseconds(file.lastModified.Value) : DateTimeOffset.Now }; if (file.thumbs != null) { atta.Thumbnails = file.thumbs .Select(t => new AttachmentFileThumb { Id = t.id, Type = t.type, Size = t.size ?? 0 }) .ToArray(); } record.Attachments.Add(atta); } } if (parsedExtra.fields != null) { foreach (var field in parsedExtra.fields) { var fld = new ExtraField(); foreach (var pair in field) { switch (pair.Key) { case "id": fld.Id = pair.Value.ToString(); break; case "field_type": fld.FieldType = pair.Value.ToString(); break; case "field_title": fld.FieldTitle = pair.Value.ToString(); break; default: fld.Custom[pair.Key] = pair.Value; break; } } record.ExtraFields.Add(fld); } } } } return(record); }
/// <summary> /// Encrypts and uploads file attachment. /// </summary> /// <param name="record">Keeper record.</param> /// <param name="uploadTask">Upload task</param> /// <returns>Awaitable task.</returns> /// <seealso cref="IVaultFileAttachment.UploadAttachment"/> public async Task UploadAttachment(PasswordRecord record, IAttachmentUploadTask uploadTask) { var fileStream = uploadTask.Stream; if (fileStream == null) { throw new KeeperInvalidParameter("Vault::UploadAttachment", "uploadTask", "GetStream()", "null"); } var thumbStream = uploadTask.Thumbnail?.Stream; var command = new RequestUploadCommand { FileCount = 1, ThumbnailCount = thumbStream != null ? 1 : 0 }; var rs = await Auth.ExecuteAuthCommand <RequestUploadCommand, RequestUploadResponse>(command); if (rs.FileUploads == null || rs.FileUploads.Length < 1) { throw new KeeperInvalidParameter("Vault::UploadAttachment", "request_upload", "file_uploads", "empty"); } var fileUpload = rs.FileUploads[0]; UploadParameters thumbUpload = null; if (rs.ThumbnailUploads != null && rs.ThumbnailUploads.Length > 0) { thumbUpload = rs.ThumbnailUploads[0]; } var key = CryptoUtils.GenerateEncryptionKey(); var atta = new AttachmentFile { Id = fileUpload.FileId, Name = uploadTask.Name, Title = uploadTask.Title, Key = key.Base64UrlEncode(), Type = uploadTask.MimeType, LastModified = DateTimeOffset.Now, }; var transform = new EncryptAesV1Transform(key); using (var cryptoStream = new CryptoStream(fileStream, transform, CryptoStreamMode.Read)) { await UploadSingleFile(fileUpload, cryptoStream); atta.Size = transform.EncryptedBytes; } if (thumbUpload != null && thumbStream != null) { try { transform = new EncryptAesV1Transform(key); using (var cryptoStream = new CryptoStream(thumbStream, transform, CryptoStreamMode.Read)) { await UploadSingleFile(thumbUpload, cryptoStream); } var thumbnail = new AttachmentFileThumb { Id = thumbUpload.FileId, Type = uploadTask.Thumbnail.MimeType, Size = uploadTask.Thumbnail.Size }; var ts = new[] { thumbnail }; atta.Thumbnails = atta.Thumbnails == null ? ts : atta.Thumbnails.Concat(ts).ToArray(); } catch (Exception e) { Trace.TraceError("Upload Thumbnail: {0}: \"{1}\"", e.GetType().Name, e.Message); } } record.Attachments.Add(atta); }