using System; using System.Collections.Generic; using System.Collections.ObjectModel; using System.Collections.Specialized; using System.Linq; using System.Reflection; using System.Runtime.Serialization; using Umbraco.Core.Models.Entities; namespace Umbraco.Core.Models { [Serializable] [DataContract(IsReference = true)] public class PublicAccessEntry : EntityBase { private readonly ObservableCollection _ruleCollection; private int _protectedNodeId; private int _noAccessNodeId; private int _loginNodeId; private readonly List _removedRules = new List(); public PublicAccessEntry(IContent protectedNode, IContent loginNode, IContent noAccessNode, IEnumerable ruleCollection) { LoginNodeId = loginNode.Id; NoAccessNodeId = noAccessNode.Id; _protectedNodeId = protectedNode.Id; _ruleCollection = new ObservableCollection(ruleCollection); _ruleCollection.CollectionChanged += _ruleCollection_CollectionChanged; foreach (var rule in _ruleCollection) rule.AccessEntryId = Key; } public PublicAccessEntry(Guid id, int protectedNodeId, int loginNodeId, int noAccessNodeId, IEnumerable ruleCollection) { Key = id; Id = Key.GetHashCode(); LoginNodeId = loginNodeId; NoAccessNodeId = noAccessNodeId; _protectedNodeId = protectedNodeId; _ruleCollection = new ObservableCollection(ruleCollection); _ruleCollection.CollectionChanged += _ruleCollection_CollectionChanged; foreach (var rule in _ruleCollection) rule.AccessEntryId = Key; } void _ruleCollection_CollectionChanged(object sender, NotifyCollectionChangedEventArgs e) { OnPropertyChanged(Ps.Value.AllowedSectionsSelector); //if (e.Action == NotifyCollectionChangedAction.Add) //{ // var item = e.NewItems.Cast().First(); // if (_addedSections.Contains(item) == false) // { // _addedSections.Add(item); // } //} if (e.Action == NotifyCollectionChangedAction.Remove) { var item = e.OldItems.Cast().First(); if (_removedRules.Contains(item.Key) == false) { _removedRules.Add(item.Key); } } } private static readonly Lazy Ps = new Lazy(); private class PropertySelectors { public readonly PropertyInfo ProtectedNodeIdSelector = ExpressionHelper.GetPropertyInfo(x => x.ProtectedNodeId); public readonly PropertyInfo LoginNodeIdSelector = ExpressionHelper.GetPropertyInfo(x => x.LoginNodeId); public readonly PropertyInfo NoAccessNodeIdSelector = ExpressionHelper.GetPropertyInfo(x => x.NoAccessNodeId); public readonly PropertyInfo AllowedSectionsSelector = ExpressionHelper.GetPropertyInfo>(x => x.Rules); } internal IEnumerable RemovedRules { get { return _removedRules; } } public IEnumerable Rules { get { return _ruleCollection; } } public PublicAccessRule AddRule(string ruleValue, string ruleType) { var rule = new PublicAccessRule { AccessEntryId = Key, RuleValue = ruleValue, RuleType = ruleType }; _ruleCollection.Add(rule); return rule; } public void RemoveRule(PublicAccessRule rule) { _ruleCollection.Remove(rule); } public void ClearRules() { _ruleCollection.Clear(); } internal void ClearRemovedRules() { _removedRules.Clear(); } [DataMember] public int LoginNodeId { get { return _loginNodeId; } set { SetPropertyValueAndDetectChanges(value, ref _loginNodeId, Ps.Value.LoginNodeIdSelector); } } [DataMember] public int NoAccessNodeId { get { return _noAccessNodeId; } set { SetPropertyValueAndDetectChanges(value, ref _noAccessNodeId, Ps.Value.NoAccessNodeIdSelector); } } [DataMember] public int ProtectedNodeId { get { return _protectedNodeId; } set { SetPropertyValueAndDetectChanges(value, ref _protectedNodeId, Ps.Value.ProtectedNodeIdSelector); } } public override void ResetDirtyProperties(bool rememberDirty) { _removedRules.Clear(); base.ResetDirtyProperties(rememberDirty); foreach (var publicAccessRule in _ruleCollection) { publicAccessRule.ResetDirtyProperties(rememberDirty); } } } }