Statistics
| Branch: | Revision:

root / trunk / Pithos.Core / Agents / SnapshotDifferencer.cs @ 99e6329f

History | View | Annotate | Download (5.8 kB)

1 255f5f86 Panagiotis Kanavos
#region
2 255f5f86 Panagiotis Kanavos
/* -----------------------------------------------------------------------
3 255f5f86 Panagiotis Kanavos
 * <copyright file="SnapshotDifferencer.cs" company="GRNet">
4 255f5f86 Panagiotis Kanavos
 * 
5 255f5f86 Panagiotis Kanavos
 * Copyright 2011-2012 GRNET S.A. All rights reserved.
6 255f5f86 Panagiotis Kanavos
 *
7 255f5f86 Panagiotis Kanavos
 * Redistribution and use in source and binary forms, with or
8 255f5f86 Panagiotis Kanavos
 * without modification, are permitted provided that the following
9 255f5f86 Panagiotis Kanavos
 * conditions are met:
10 255f5f86 Panagiotis Kanavos
 *
11 255f5f86 Panagiotis Kanavos
 *   1. Redistributions of source code must retain the above
12 255f5f86 Panagiotis Kanavos
 *      copyright notice, this list of conditions and the following
13 255f5f86 Panagiotis Kanavos
 *      disclaimer.
14 255f5f86 Panagiotis Kanavos
 *
15 255f5f86 Panagiotis Kanavos
 *   2. Redistributions in binary form must reproduce the above
16 255f5f86 Panagiotis Kanavos
 *      copyright notice, this list of conditions and the following
17 255f5f86 Panagiotis Kanavos
 *      disclaimer in the documentation and/or other materials
18 255f5f86 Panagiotis Kanavos
 *      provided with the distribution.
19 255f5f86 Panagiotis Kanavos
 *
20 255f5f86 Panagiotis Kanavos
 *
21 255f5f86 Panagiotis Kanavos
 * THIS SOFTWARE IS PROVIDED BY GRNET S.A. ``AS IS'' AND ANY EXPRESS
22 255f5f86 Panagiotis Kanavos
 * OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
23 255f5f86 Panagiotis Kanavos
 * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
24 255f5f86 Panagiotis Kanavos
 * PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL GRNET S.A OR
25 255f5f86 Panagiotis Kanavos
 * CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
26 255f5f86 Panagiotis Kanavos
 * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
27 255f5f86 Panagiotis Kanavos
 * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF
28 255f5f86 Panagiotis Kanavos
 * USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED
29 255f5f86 Panagiotis Kanavos
 * AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
30 255f5f86 Panagiotis Kanavos
 * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN
31 255f5f86 Panagiotis Kanavos
 * ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
32 255f5f86 Panagiotis Kanavos
 * POSSIBILITY OF SUCH DAMAGE.
33 255f5f86 Panagiotis Kanavos
 *
34 255f5f86 Panagiotis Kanavos
 * The views and conclusions contained in the software and
35 255f5f86 Panagiotis Kanavos
 * documentation are those of the authors and should not be
36 255f5f86 Panagiotis Kanavos
 * interpreted as representing official policies, either expressed
37 255f5f86 Panagiotis Kanavos
 * or implied, of GRNET S.A.
38 255f5f86 Panagiotis Kanavos
 * </copyright>
39 255f5f86 Panagiotis Kanavos
 * -----------------------------------------------------------------------
40 255f5f86 Panagiotis Kanavos
 */
41 255f5f86 Panagiotis Kanavos
#endregion
42 7f0e1c1e Panagiotis Kanavos
using System.Collections.Concurrent;
43 039d89ea Panagiotis Kanavos
using Pithos.Interfaces;
44 a0622735 Panagiotis Kanavos
using Pithos.Network;
45 039d89ea Panagiotis Kanavos
46 039d89ea Panagiotis Kanavos
namespace Pithos.Core.Agents
47 039d89ea Panagiotis Kanavos
{
48 039d89ea Panagiotis Kanavos
    using System;
49 039d89ea Panagiotis Kanavos
    using System.Collections.Generic;
50 039d89ea Panagiotis Kanavos
    using System.Linq;
51 039d89ea Panagiotis Kanavos
    using System.Text;
52 039d89ea Panagiotis Kanavos
53 039d89ea Panagiotis Kanavos
    /// <summary>
54 039d89ea Panagiotis Kanavos
    /// TODO: Update summary.
55 039d89ea Panagiotis Kanavos
    /// </summary>
56 039d89ea Panagiotis Kanavos
    public class SnapshotDifferencer
57 039d89ea Panagiotis Kanavos
    {
58 039d89ea Panagiotis Kanavos
        private IEnumerable<ObjectInfo> _previous;
59 039d89ea Panagiotis Kanavos
        private IEnumerable<ObjectInfo> _current;
60 039d89ea Panagiotis Kanavos
        private static ObjectInfo[] _empty = new ObjectInfo[0];
61 039d89ea Panagiotis Kanavos
        private ObjectInfoComparer _comparer = new ObjectInfoComparer();
62 039d89ea Panagiotis Kanavos
63 039d89ea Panagiotis Kanavos
        public SnapshotDifferencer()
64 039d89ea Panagiotis Kanavos
        {
65 039d89ea Panagiotis Kanavos
            _previous = new List<ObjectInfo>();
66 039d89ea Panagiotis Kanavos
            _current= new List<ObjectInfo>();
67 039d89ea Panagiotis Kanavos
        }
68 039d89ea Panagiotis Kanavos
69 039d89ea Panagiotis Kanavos
70 039d89ea Panagiotis Kanavos
        public SnapshotDifferencer(IEnumerable<ObjectInfo> previous,IEnumerable<ObjectInfo> current  )
71 039d89ea Panagiotis Kanavos
        {
72 039d89ea Panagiotis Kanavos
            _previous = previous ?? new List<ObjectInfo>();
73 039d89ea Panagiotis Kanavos
            _current= current ?? new List<ObjectInfo>();
74 039d89ea Panagiotis Kanavos
        }
75 039d89ea Panagiotis Kanavos
        public SnapshotDifferencer Post(IEnumerable<ObjectInfo> list)
76 039d89ea Panagiotis Kanavos
        {
77 422c9598 Panagiotis Kanavos
            _previous = _current;
78 99e6329f Panagiotis Kanavos
            if (list == null)
79 99e6329f Panagiotis Kanavos
            {
80 99e6329f Panagiotis Kanavos
                _current = new List<ObjectInfo>();
81 99e6329f Panagiotis Kanavos
                return this;
82 99e6329f Panagiotis Kanavos
            }
83 99e6329f Panagiotis Kanavos
84 99e6329f Panagiotis Kanavos
            //Replace any NoModification entries with previous values that have
85 99e6329f Panagiotis Kanavos
            //the same account, container and possibly, folder
86 99e6329f Panagiotis Kanavos
            _current=list.Replace(
87 99e6329f Panagiotis Kanavos
                info => info is NoModificationInfo, 
88 99e6329f Panagiotis Kanavos
                noMod => from info in _previous
89 99e6329f Panagiotis Kanavos
                        where 
90 99e6329f Panagiotis Kanavos
                            info.Account==noMod.Account 
91 99e6329f Panagiotis Kanavos
                            && info.Container==noMod.Container 
92 99e6329f Panagiotis Kanavos
                            //If the NoModification specifies a folder, use it to match items below this folder
93 99e6329f Panagiotis Kanavos
                            && (noMod.Name==null || info.Name.StartsWith(noMod.Name))
94 99e6329f Panagiotis Kanavos
                        select info);
95 99e6329f Panagiotis Kanavos
96 422c9598 Panagiotis Kanavos
            return this;
97 039d89ea Panagiotis Kanavos
        }
98 039d89ea Panagiotis Kanavos
        
99 039d89ea Panagiotis Kanavos
        public IEnumerable<ObjectInfo> Deleted
100 039d89ea Panagiotis Kanavos
        {
101 039d89ea Panagiotis Kanavos
            get { return _previous.Except(_current,_comparer); }
102 039d89ea Panagiotis Kanavos
        }
103 039d89ea Panagiotis Kanavos
        public IEnumerable<ObjectInfo> Created
104 039d89ea Panagiotis Kanavos
        {
105 039d89ea Panagiotis Kanavos
            get { return _current.Except(_previous,_comparer); }
106 039d89ea Panagiotis Kanavos
        }
107 039d89ea Panagiotis Kanavos
        public IEnumerable<ObjectInfo> Changed
108 039d89ea Panagiotis Kanavos
        {
109 039d89ea Panagiotis Kanavos
            get
110 039d89ea Panagiotis Kanavos
            {
111 039d89ea Panagiotis Kanavos
                var changes = from newItem in _current 
112 039d89ea Panagiotis Kanavos
                              let oldItem=_previous.FirstOrDefault(old=>_comparer.Equals(old,newItem))
113 039d89ea Panagiotis Kanavos
                              where oldItem !=null &&
114 039d89ea Panagiotis Kanavos
                                    newItem.Hash != oldItem.Hash
115 039d89ea Panagiotis Kanavos
                              select newItem;
116 039d89ea Panagiotis Kanavos
                return changes;
117 039d89ea Panagiotis Kanavos
            }
118 039d89ea Panagiotis Kanavos
        }
119 039d89ea Panagiotis Kanavos
        public IEnumerable<ObjectInfo> Unchanged
120 039d89ea Panagiotis Kanavos
        {
121 039d89ea Panagiotis Kanavos
            get
122 039d89ea Panagiotis Kanavos
            {
123 039d89ea Panagiotis Kanavos
                var unChanged = from newItem in _current
124 039d89ea Panagiotis Kanavos
                              let oldItem = _previous.FirstOrDefault(old => _comparer.Equals(old, newItem))
125 039d89ea Panagiotis Kanavos
                              where oldItem != null &&
126 039d89ea Panagiotis Kanavos
                                    newItem.Hash == oldItem.Hash
127 039d89ea Panagiotis Kanavos
                              select newItem;
128 039d89ea Panagiotis Kanavos
                return unChanged;
129 039d89ea Panagiotis Kanavos
            }
130 039d89ea Panagiotis Kanavos
        }
131 039d89ea Panagiotis Kanavos
    }
132 a0622735 Panagiotis Kanavos
133 a0622735 Panagiotis Kanavos
    public class AccountsDifferencer
134 a0622735 Panagiotis Kanavos
    {
135 7f0e1c1e Panagiotis Kanavos
        ConcurrentDictionary<string, SnapshotDifferencer> _differencers = new ConcurrentDictionary<string, SnapshotDifferencer>();
136 a0622735 Panagiotis Kanavos
137 7f0e1c1e Panagiotis Kanavos
        public ConcurrentDictionary<string, SnapshotDifferencer> Differencers { get { return _differencers; } }
138 a0622735 Panagiotis Kanavos
139 a0622735 Panagiotis Kanavos
        public SnapshotDifferencer PostSnapshot(AccountInfo accountInfo, List<ObjectInfo> cleanRemotes)
140 a0622735 Panagiotis Kanavos
        {
141 a0622735 Panagiotis Kanavos
            SnapshotDifferencer differencer;
142 a0622735 Panagiotis Kanavos
            if (!_differencers.TryGetValue(accountInfo.UserName, out differencer))
143 a0622735 Panagiotis Kanavos
            {
144 a0622735 Panagiotis Kanavos
                differencer = new SnapshotDifferencer();
145 a0622735 Panagiotis Kanavos
                _differencers[accountInfo.UserName] = differencer;
146 a0622735 Panagiotis Kanavos
            }
147 a0622735 Panagiotis Kanavos
            differencer.Post(cleanRemotes);
148 a0622735 Panagiotis Kanavos
            return differencer;
149 a0622735 Panagiotis Kanavos
        }
150 a0622735 Panagiotis Kanavos
151 a0622735 Panagiotis Kanavos
    }
152 039d89ea Panagiotis Kanavos
}