root / trunk / Pithos.Client.WPF / FileProperties / ConflictResolver.cs @ 368e06fd
History | View | Annotate | Download (5.2 kB)
1 |
using System; |
---|---|
2 |
using System.Collections.Generic; |
3 |
using System.ComponentModel.Composition; |
4 |
using System.Linq; |
5 |
using System.Text; |
6 |
using Caliburn.Micro; |
7 |
using Pithos.Core; |
8 |
using Pithos.Core.Agents; |
9 |
using Pithos.Interfaces; |
10 |
using Pithos.Network; |
11 |
|
12 |
namespace Pithos.Client.WPF.FileProperties |
13 |
{ |
14 |
[Export(typeof(IConflictResolver))] |
15 |
public class ConflictResolver : IConflictResolver |
16 |
{ |
17 |
[Import] |
18 |
public IStatusKeeper StatusAgent { get; set; } |
19 |
|
20 |
[Import] |
21 |
public ShellViewModel Shell { get; set; } |
22 |
|
23 |
[Import] |
24 |
public NetworkAgent NetworkAgent { get; set; } |
25 |
|
26 |
public void Resolve(IEnumerable<ConflictFile> conflicts) |
27 |
{ |
28 |
KeepServer(conflicts.Where(c => c.Action == ConflictAction.KeepServer)); |
29 |
KeepLocal(conflicts.Where(c => c.Action == ConflictAction.KeepLocal)); |
30 |
//KeepBoth(conflicts.Where(c => c.Action == ConflictAction.KeepBoth)); |
31 |
ClearLocal(conflicts.Where(c => c.Action == ConflictAction.ClearLocal)); |
32 |
} |
33 |
|
34 |
|
35 |
//Clearing the local state means that we clear the conflict state of the local file. |
36 |
//This is needed to clear wrong conflicts |
37 |
private void ClearLocal(IEnumerable<ConflictFile> conflicts) |
38 |
{ |
39 |
//This can be done simply by changing the local Filestate status to normal |
40 |
conflicts.Apply(clear => |
41 |
StatusAgent.SetFileState(clear.FilePath, FileStatus.Unchanged, FileOverlayStatus.Normal, "")); |
42 |
|
43 |
} |
44 |
|
45 |
|
46 |
//Keeping the server version means that we need to |
47 |
//download the server's version of the file. |
48 |
private void KeepServer(IEnumerable<ConflictFile> conflicts) |
49 |
{ |
50 |
|
51 |
//This can be done either by scheduling the appropriate action, ignoring the hash |
52 |
//Or directly downloading the file. |
53 |
|
54 |
//This can be done either by scheduling the appropriate action, ignoring the hash |
55 |
//Or directly uploading the file. |
56 |
var monitors = Shell.Monitors.Select(m => m.Value); |
57 |
|
58 |
//Files that were not deleted |
59 |
var filesToDelete= from conflict in conflicts |
60 |
where conflict.State.OverlayStatus == FileOverlayStatus.Deleted |
61 |
let info=FileInfoExtensions.FromPath(conflict.FilePath) |
62 |
where info.Exists |
63 |
select info; |
64 |
filesToDelete.Apply(f=> |
65 |
{ |
66 |
f.Delete(); |
67 |
StatusAgent.ClearFileStatus(f.FullName); |
68 |
}); |
69 |
|
70 |
//Files that were not deleted |
71 |
var downloadActions = from conflict in conflicts |
72 |
where conflict.State.OverlayStatus != FileOverlayStatus.Deleted |
73 |
let monitor=monitors.First(m=> conflict.FilePath.StartsWith(m.Account.AccountPath, StringComparison.InvariantCultureIgnoreCase)) |
74 |
let account = monitor.Account |
75 |
let info = monitor.GetObjectInfo(conflict.FilePath) |
76 |
select new CloudDownloadAction(account, info, "Resolver"); |
77 |
|
78 |
downloadActions.Apply(action=> StatusAgent.SetFileState(action.FileState.FilePath,FileStatus.Unchanged,FileOverlayStatus.Normal,"Resolve by downloading")); |
79 |
downloadActions.Apply(NetworkAgent.Post); |
80 |
|
81 |
} |
82 |
|
83 |
//Keeping the server version means that we need to |
84 |
//upload the local version of the file to the server |
85 |
private void KeepLocal(IEnumerable<ConflictFile> conflicts) |
86 |
{ |
87 |
|
88 |
var accounts = (from monitor in Shell.Monitors |
89 |
select monitor.Value.Account).ToList(); |
90 |
|
91 |
//This can be done either by scheduling the appropriate action, ignoring the hash |
92 |
//Or directly uploading the file. |
93 |
var actions = from conflict in conflicts |
94 |
let account = accounts.First(acc => conflict.FilePath.StartsWith(acc.AccountPath, StringComparison.InvariantCultureIgnoreCase)) |
95 |
let info = FileInfoExtensions.FromPath(conflict.FilePath) |
96 |
select new CloudUploadAction(account, info, conflict.State, |
97 |
account.BlockSize, account.BlockHash,"Resolver"); |
98 |
|
99 |
actions.Apply(action => StatusAgent.SetFileState(action.FileState.FilePath, FileStatus.Modified, FileOverlayStatus.Normal, "Resolve by downloading")); |
100 |
actions.Apply(NetworkAgent.Post); |
101 |
} |
102 |
|
103 |
//Keeping both versions means that we need to copy one of them |
104 |
//somewhere and keep the other |
105 |
private void KeepBoth(IEnumerable<ConflictFile> conflicts) |
106 |
{ |
107 |
//We can copy the rename the local file to another name and download the server file |
108 |
//Or rename the server file and upload the local file |
109 |
|
110 |
//Downloading the server file is probably much faster with ADSL connections |
111 |
|
112 |
//We could probably use the local file as a source of blocks to download fewer data, |
113 |
//We create a hashmap of the local file, download the differences from the server |
114 |
//and merge common and changed blocks to create the new file. |
115 |
} |
116 |
} |
117 |
} |