diff --git a/src/Umbraco.Core/Models/EntityBase/Entity.cs b/src/Umbraco.Core/Models/EntityBase/Entity.cs
index 315e2697c0..1551f29f86 100644
--- a/src/Umbraco.Core/Models/EntityBase/Entity.cs
+++ b/src/Umbraco.Core/Models/EntityBase/Entity.cs
@@ -59,7 +59,7 @@ namespace Umbraco.Core.Models.EntityBase
/// The key is currectly used to store the Unique Id from the
/// umbracoNode table, which many of the entities are based on.
[DataMember]
- public Guid Key
+ public virtual Guid Key
{
get
{
diff --git a/src/Umbraco.Core/Models/PublicAccessEntry.cs b/src/Umbraco.Core/Models/PublicAccessEntry.cs
new file mode 100644
index 0000000000..948f33bc03
--- /dev/null
+++ b/src/Umbraco.Core/Models/PublicAccessEntry.cs
@@ -0,0 +1,177 @@
+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.EntityBase;
+
+namespace Umbraco.Core.Models
+{
+ [Serializable]
+ [DataContract(IsReference = true)]
+ public class PublicAccessEntry : Entity, IAggregateRoot
+ {
+ private readonly ObservableCollection _ruleCollection;
+ private Guid _protectedNodeId;
+ private Guid _noAccessNodeId;
+ private Guid _loginNodeId;
+ private readonly List _removedRules = new List();
+
+ public PublicAccessEntry(IContent protectedNode, IContent loginNode, IContent noAccessNode, IEnumerable ruleCollection)
+ {
+ LoginNodeId = loginNode.Key;
+ NoAccessNodeId = noAccessNode.Key;
+ _protectedNodeId = protectedNode.Key;
+
+ _ruleCollection = new ObservableCollection(ruleCollection);
+ _ruleCollection.CollectionChanged += _ruleCollection_CollectionChanged;
+ }
+
+ public PublicAccessEntry(Guid id, Guid protectedNodeId, Guid loginNodeId, Guid noAccessNodeId, IEnumerable ruleCollection)
+ {
+ Key = id;
+
+ LoginNodeId = loginNodeId;
+ NoAccessNodeId = noAccessNodeId;
+ _protectedNodeId = protectedNodeId;
+
+ _ruleCollection = new ObservableCollection(ruleCollection);
+ _ruleCollection.CollectionChanged += _ruleCollection_CollectionChanged;
+ }
+
+ void _ruleCollection_CollectionChanged(object sender, NotifyCollectionChangedEventArgs e)
+ {
+ OnPropertyChanged(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 PropertyInfo ProtectedNodeIdSelector = ExpressionHelper.GetPropertyInfo(x => x.ProtectedNodeId);
+ private static readonly PropertyInfo LoginNodeIdSelector = ExpressionHelper.GetPropertyInfo(x => x.LoginNodeId);
+ private static readonly PropertyInfo NoAccessNodeIdSelector = ExpressionHelper.GetPropertyInfo(x => x.NoAccessNodeId);
+ private static readonly PropertyInfo AllowedSectionsSelector = ExpressionHelper.GetPropertyInfo>(x => x.Rules);
+
+ internal IEnumerable RemovedRules
+ {
+ get { return _removedRules; }
+ }
+
+ public IEnumerable Rules
+ {
+ get { return _ruleCollection; }
+ }
+
+ public PublicAccessRule AddRule(string claim, string claimType)
+ {
+ var rule = new PublicAccessRule
+ {
+ AccessEntryId = Key,
+ Claim = claim,
+ ClaimType = claimType
+ };
+ _ruleCollection.Add(rule);
+ return rule;
+ }
+
+ public void RemoveRule(PublicAccessRule rule)
+ {
+ _ruleCollection.Remove(rule);
+ }
+
+ ///
+ /// Method to call on entity saved when first added
+ ///
+ internal override void AddingEntity()
+ {
+ if (Key == default(Guid))
+ {
+ Key = Guid.NewGuid();
+ }
+ base.AddingEntity();
+ }
+
+ [DataMember]
+ public sealed override Guid Key
+ {
+ get { return base.Key; }
+ set
+ {
+ base.Key = value;
+ HasIdentity = true;
+ }
+ }
+
+ [DataMember]
+ public Guid LoginNodeId
+ {
+ get { return _loginNodeId; }
+ set
+ {
+ SetPropertyValueAndDetectChanges(o =>
+ {
+ _loginNodeId = value;
+ return _loginNodeId;
+ }, _loginNodeId, LoginNodeIdSelector);
+ }
+ }
+
+ [DataMember]
+ public Guid NoAccessNodeId
+ {
+ get { return _noAccessNodeId; }
+ set
+ {
+ SetPropertyValueAndDetectChanges(o =>
+ {
+ _noAccessNodeId = value;
+ return _noAccessNodeId;
+ }, _noAccessNodeId, NoAccessNodeIdSelector);
+ }
+ }
+
+ [DataMember]
+ public Guid ProtectedNodeId
+ {
+ get { return _protectedNodeId; }
+ set
+ {
+ SetPropertyValueAndDetectChanges(o =>
+ {
+ _protectedNodeId = value;
+ return _protectedNodeId;
+ }, _protectedNodeId, ProtectedNodeIdSelector);
+ }
+ }
+
+ public override void ResetDirtyProperties(bool rememberPreviouslyChangedProperties)
+ {
+ _removedRules.Clear();
+ base.ResetDirtyProperties(rememberPreviouslyChangedProperties);
+ foreach (var publicAccessRule in _ruleCollection)
+ {
+ publicAccessRule.ResetDirtyProperties(rememberPreviouslyChangedProperties);
+ }
+ }
+ }
+}
\ No newline at end of file
diff --git a/src/Umbraco.Core/Models/PublicAccessRule.cs b/src/Umbraco.Core/Models/PublicAccessRule.cs
new file mode 100644
index 0000000000..aefa681794
--- /dev/null
+++ b/src/Umbraco.Core/Models/PublicAccessRule.cs
@@ -0,0 +1,81 @@
+using System;
+using System.Reflection;
+using System.Runtime.Serialization;
+using Umbraco.Core.Models.EntityBase;
+
+namespace Umbraco.Core.Models
+{
+ [Serializable]
+ [DataContract(IsReference = true)]
+ public class PublicAccessRule : Entity
+ {
+ private string _claim;
+ private string _claimType;
+
+ public PublicAccessRule(Guid id, Guid accessEntryId)
+ {
+ AccessEntryId = accessEntryId;
+ Key = id;
+ Id = Key.GetHashCode();
+ }
+
+ public PublicAccessRule()
+ {
+ }
+
+ private static readonly PropertyInfo ClaimSelector = ExpressionHelper.GetPropertyInfo(x => x.Claim);
+ private static readonly PropertyInfo ClaimTypeSelector = ExpressionHelper.GetPropertyInfo(x => x.ClaimType);
+
+ public sealed override Guid Key
+ {
+ get { return base.Key; }
+ set
+ {
+ base.Key = value;
+ HasIdentity = true;
+ }
+ }
+
+ public Guid AccessEntryId { get; internal set; }
+
+ ///
+ /// Method to call on entity saved when first added
+ ///
+ internal override void AddingEntity()
+ {
+ if (Key == default(Guid))
+ {
+ Key = Guid.NewGuid();
+ }
+ base.AddingEntity();
+ }
+
+ public string Claim
+ {
+ get { return _claim; }
+ set
+ {
+ SetPropertyValueAndDetectChanges(o =>
+ {
+ _claim = value;
+ return _claim;
+ }, _claim, ClaimSelector);
+ }
+ }
+
+ public string ClaimType
+ {
+ get { return _claimType; }
+ set
+ {
+ SetPropertyValueAndDetectChanges(o =>
+ {
+ _claimType = value;
+ return _claimType;
+ }, _claimType, ClaimTypeSelector);
+ }
+ }
+
+
+ }
+}
\ No newline at end of file
diff --git a/src/Umbraco.Core/Models/Rdbms/AccessDto.cs b/src/Umbraco.Core/Models/Rdbms/AccessDto.cs
index 486b755095..2c587946a1 100644
--- a/src/Umbraco.Core/Models/Rdbms/AccessDto.cs
+++ b/src/Umbraco.Core/Models/Rdbms/AccessDto.cs
@@ -1,27 +1,43 @@
-using Umbraco.Core.Persistence;
+using System;
+using System.Collections;
+using System.Collections.Generic;
+using System.Security.AccessControl;
+using Umbraco.Core.Persistence;
using Umbraco.Core.Persistence.DatabaseAnnotations;
namespace Umbraco.Core.Models.Rdbms
{
[TableName("umbracoAccess")]
- [PrimaryKey("id")]
+ [PrimaryKey("id", autoIncrement = false)]
[ExplicitColumns]
internal class AccessDto
{
[Column("id")]
- [PrimaryKeyColumn(Name = "PK_umbracoAccess")]
- public int Id { get; set; }
+ [PrimaryKeyColumn(Name = "PK_umbracoAccess", AutoIncrement = false)]
+ public Guid Id { get; set; }
[Column("nodeId")]
- [ForeignKey(typeof(NodeDto), Name = "FK_umbracoAccess_umbracoNode_id")]
- public int NodeId { get; set; }
+ [ForeignKey(typeof(NodeDto), Name = "FK_umbracoAccess_umbracoNode_uniqueID", Column = "uniqueID")]
+ [Index(IndexTypes.UniqueNonClustered, Name = "IX_umbracoAccess_nodeId")]
+ public Guid NodeId { get; set; }
[Column("loginNodeId")]
- [ForeignKey(typeof(NodeDto), Name = "FK_umbracoAccess_umbracoNode_id1")]
- public int LoginNodeId { get; set; }
+ [ForeignKey(typeof(NodeDto), Name = "FK_umbracoAccess_umbracoNode_uniqueID1", Column = "uniqueID")]
+ public Guid LoginNodeId { get; set; }
[Column("noAccessNodeId")]
- [ForeignKey(typeof(NodeDto), Name = "FK_umbracoAccess_umbracoNode_id2")]
- public int AccessDeniedNodeId { get; set; }
+ [ForeignKey(typeof(NodeDto), Name = "FK_umbracoAccess_umbracoNode_uniqueID2", Column = "uniqueID")]
+ public Guid AccessDeniedNodeId { get; set; }
+
+ [Column("createDate")]
+ [Constraint(Default = "getdate()")]
+ public DateTime CreateDate { get; set; }
+
+ [Column("updateDate")]
+ [Constraint(Default = "getdate()")]
+ public DateTime UpdateDate { get; set; }
+
+ [ResultColumn]
+ public List Rules { get; set; }
}
}
\ No newline at end of file
diff --git a/src/Umbraco.Core/Models/Rdbms/AccessRuleDto.cs b/src/Umbraco.Core/Models/Rdbms/AccessRuleDto.cs
index 6b006fabb7..4a8961c9dd 100644
--- a/src/Umbraco.Core/Models/Rdbms/AccessRuleDto.cs
+++ b/src/Umbraco.Core/Models/Rdbms/AccessRuleDto.cs
@@ -1,25 +1,34 @@
+using System;
using Umbraco.Core.Persistence;
using Umbraco.Core.Persistence.DatabaseAnnotations;
namespace Umbraco.Core.Models.Rdbms
{
[TableName("umbracoAccessRule")]
- [PrimaryKey("id")]
+ [PrimaryKey("id", autoIncrement = false)]
[ExplicitColumns]
internal class AccessRuleDto
{
[Column("id")]
- [PrimaryKeyColumn(Name = "PK_umbracoAccessRule")]
- public int Id { get; set; }
+ [PrimaryKeyColumn(Name = "PK_umbracoAccessRule", AutoIncrement = false)]
+ public Guid Id { get; set; }
[Column("accessId")]
[ForeignKey(typeof(AccessDto), Name = "FK_umbracoAccessRule_umbracoAccess_id")]
- public int AccessId { get; set; }
+ public Guid AccessId { get; set; }
[Column("claim")]
public string Claim { get; set; }
[Column("claimType")]
public string ClaimType { get; set; }
+
+ [Column("createDate")]
+ [Constraint(Default = "getdate()")]
+ public DateTime CreateDate { get; set; }
+
+ [Column("updateDate")]
+ [Constraint(Default = "getdate()")]
+ public DateTime UpdateDate { get; set; }
}
}
\ No newline at end of file
diff --git a/src/Umbraco.Core/Models/Rdbms/NodeDto.cs b/src/Umbraco.Core/Models/Rdbms/NodeDto.cs
index f9aadf4963..33c1a73059 100644
--- a/src/Umbraco.Core/Models/Rdbms/NodeDto.cs
+++ b/src/Umbraco.Core/Models/Rdbms/NodeDto.cs
@@ -40,9 +40,9 @@ namespace Umbraco.Core.Models.Rdbms
public int SortOrder { get; set; }
[Column("uniqueID")]
- [NullSetting(NullSetting = NullSettings.Null)]
- [Index(IndexTypes.NonClustered, Name = "IX_umbracoNodeUniqueID")]
- public Guid? UniqueId { get; set; }
+ [NullSetting(NullSetting = NullSettings.NotNull)]
+ [Index(IndexTypes.UniqueNonClustered, Name = "IX_umbracoNodeUniqueID")]
+ public Guid UniqueId { get; set; }
[Column("text")]
[NullSetting(NullSetting = NullSettings.Null)]
diff --git a/src/Umbraco.Core/Persistence/Factories/ContentFactory.cs b/src/Umbraco.Core/Persistence/Factories/ContentFactory.cs
index 0208a7a128..66dc6f64dc 100644
--- a/src/Umbraco.Core/Persistence/Factories/ContentFactory.cs
+++ b/src/Umbraco.Core/Persistence/Factories/ContentFactory.cs
@@ -32,10 +32,7 @@ namespace Umbraco.Core.Persistence.Factories
var content = new Content(dto.Text, dto.ContentVersionDto.ContentDto.NodeDto.ParentId, _contentType)
{
Id = _id,
- Key =
- dto.ContentVersionDto.ContentDto.NodeDto.UniqueId.HasValue
- ? dto.ContentVersionDto.ContentDto.NodeDto.UniqueId.Value
- : _id.ToGuid(),
+ Key = dto.ContentVersionDto.ContentDto.NodeDto.UniqueId,
Name = dto.Text,
NodeName = dto.ContentVersionDto.ContentDto.NodeDto.Text,
Path = dto.ContentVersionDto.ContentDto.NodeDto.Path,
diff --git a/src/Umbraco.Core/Persistence/Factories/ContentTypeFactory.cs b/src/Umbraco.Core/Persistence/Factories/ContentTypeFactory.cs
index 23c9270906..fdd2759d76 100644
--- a/src/Umbraco.Core/Persistence/Factories/ContentTypeFactory.cs
+++ b/src/Umbraco.Core/Persistence/Factories/ContentTypeFactory.cs
@@ -22,10 +22,7 @@ namespace Umbraco.Core.Persistence.Factories
var contentType = new ContentType(dto.ContentTypeDto.NodeDto.ParentId)
{
Id = dto.ContentTypeDto.NodeDto.NodeId,
- Key =
- dto.ContentTypeDto.NodeDto.UniqueId.HasValue
- ? dto.ContentTypeDto.NodeDto.UniqueId.Value
- : dto.ContentTypeDto.NodeDto.NodeId.ToGuid(),
+ Key = dto.ContentTypeDto.NodeDto.UniqueId,
Alias = dto.ContentTypeDto.Alias,
Name = dto.ContentTypeDto.NodeDto.Text,
Icon = dto.ContentTypeDto.Icon,
diff --git a/src/Umbraco.Core/Persistence/Factories/DataTypeDefinitionFactory.cs b/src/Umbraco.Core/Persistence/Factories/DataTypeDefinitionFactory.cs
index 7b57800277..6fd6500552 100644
--- a/src/Umbraco.Core/Persistence/Factories/DataTypeDefinitionFactory.cs
+++ b/src/Umbraco.Core/Persistence/Factories/DataTypeDefinitionFactory.cs
@@ -24,10 +24,7 @@ namespace Umbraco.Core.Persistence.Factories
CreateDate = dto.NodeDto.CreateDate,
DatabaseType = dto.DbType.EnumParse(true),
Id = dto.DataTypeId,
- Key =
- dto.NodeDto.UniqueId.HasValue
- ? dto.NodeDto.UniqueId.Value
- : dto.DataTypeId.ToGuid(),
+ Key = dto.NodeDto.UniqueId,
Level = dto.NodeDto.Level,
UpdateDate = dto.NodeDto.CreateDate,
Name = dto.NodeDto.Text,
diff --git a/src/Umbraco.Core/Persistence/Factories/MediaFactory.cs b/src/Umbraco.Core/Persistence/Factories/MediaFactory.cs
index cf285cbf66..2d8edcac52 100644
--- a/src/Umbraco.Core/Persistence/Factories/MediaFactory.cs
+++ b/src/Umbraco.Core/Persistence/Factories/MediaFactory.cs
@@ -32,10 +32,7 @@ namespace Umbraco.Core.Persistence.Factories
var media = new Models.Media(dto.ContentDto.NodeDto.Text, dto.ContentDto.NodeDto.ParentId, _contentType)
{
Id = _id,
- Key =
- dto.ContentDto.NodeDto.UniqueId.HasValue
- ? dto.ContentDto.NodeDto.UniqueId.Value
- : _id.ToGuid(),
+ Key = dto.ContentDto.NodeDto.UniqueId,
Path = dto.ContentDto.NodeDto.Path,
CreatorId = dto.ContentDto.NodeDto.UserId.Value,
Level = dto.ContentDto.NodeDto.Level,
diff --git a/src/Umbraco.Core/Persistence/Factories/MediaTypeFactory.cs b/src/Umbraco.Core/Persistence/Factories/MediaTypeFactory.cs
index b63512e1b6..98048cd3a7 100644
--- a/src/Umbraco.Core/Persistence/Factories/MediaTypeFactory.cs
+++ b/src/Umbraco.Core/Persistence/Factories/MediaTypeFactory.cs
@@ -21,10 +21,7 @@ namespace Umbraco.Core.Persistence.Factories
var contentType = new MediaType(dto.NodeDto.ParentId)
{
Id = dto.NodeDto.NodeId,
- Key =
- dto.NodeDto.UniqueId.HasValue
- ? dto.NodeDto.UniqueId.Value
- : dto.NodeDto.NodeId.ToGuid(),
+ Key = dto.NodeDto.UniqueId,
Alias = dto.Alias,
Name = dto.NodeDto.Text,
Icon = dto.Icon,
diff --git a/src/Umbraco.Core/Persistence/Factories/MemberFactory.cs b/src/Umbraco.Core/Persistence/Factories/MemberFactory.cs
index 42e09b2f9c..a35c472f24 100644
--- a/src/Umbraco.Core/Persistence/Factories/MemberFactory.cs
+++ b/src/Umbraco.Core/Persistence/Factories/MemberFactory.cs
@@ -35,10 +35,7 @@ namespace Umbraco.Core.Persistence.Factories
dto.Email,dto.LoginName,dto.Password, _contentType)
{
Id = _id,
- Key =
- dto.ContentVersionDto.ContentDto.NodeDto.UniqueId.HasValue
- ? dto.ContentVersionDto.ContentDto.NodeDto.UniqueId.Value
- : _id.ToGuid(),
+ Key = dto.ContentVersionDto.ContentDto.NodeDto.UniqueId,
Path = dto.ContentVersionDto.ContentDto.NodeDto.Path,
CreatorId = dto.ContentVersionDto.ContentDto.NodeDto.UserId.Value,
Level = dto.ContentVersionDto.ContentDto.NodeDto.Level,
diff --git a/src/Umbraco.Core/Persistence/Factories/MemberGroupFactory.cs b/src/Umbraco.Core/Persistence/Factories/MemberGroupFactory.cs
index 17dbba3001..9544d170e2 100644
--- a/src/Umbraco.Core/Persistence/Factories/MemberGroupFactory.cs
+++ b/src/Umbraco.Core/Persistence/Factories/MemberGroupFactory.cs
@@ -22,7 +22,7 @@ namespace Umbraco.Core.Persistence.Factories
{
CreateDate = dto.CreateDate,
Id = dto.NodeId,
- Key = dto.UniqueId.Value,
+ Key = dto.UniqueId,
Name = dto.Text
};
diff --git a/src/Umbraco.Core/Persistence/Factories/PublicAccessEntryFactory.cs b/src/Umbraco.Core/Persistence/Factories/PublicAccessEntryFactory.cs
new file mode 100644
index 0000000000..797914bce8
--- /dev/null
+++ b/src/Umbraco.Core/Persistence/Factories/PublicAccessEntryFactory.cs
@@ -0,0 +1,55 @@
+using System.Collections.Generic;
+using System.Linq;
+using Umbraco.Core.Models;
+using Umbraco.Core.Models.Rdbms;
+
+namespace Umbraco.Core.Persistence.Factories
+{
+ internal class PublicAccessEntryFactory
+ {
+ public PublicAccessEntry BuildEntity(AccessDto dto)
+ {
+ var entity = new PublicAccessEntry(dto.Id, dto.NodeId, dto.LoginNodeId, dto.AccessDeniedNodeId,
+ dto.Rules.Select(x => new PublicAccessRule(x.Id, x.AccessId)
+ {
+ Claim = x.Claim,
+ ClaimType = x.ClaimType,
+ CreateDate = x.CreateDate,
+ UpdateDate = x.UpdateDate
+ }))
+ {
+ CreateDate = dto.CreateDate,
+ UpdateDate = dto.UpdateDate
+ };
+
+ //on initial construction we don't want to have dirty properties tracked
+ // http://issues.umbraco.org/issue/U4-1946
+ entity.ResetDirtyProperties(false);
+ return entity;
+ }
+
+ public AccessDto BuildDto(PublicAccessEntry entity)
+ {
+ var dto = new AccessDto
+ {
+ Id = entity.Key,
+ AccessDeniedNodeId = entity.NoAccessNodeId,
+ LoginNodeId = entity.LoginNodeId,
+ NodeId = entity.ProtectedNodeId,
+ CreateDate = entity.CreateDate,
+ UpdateDate = entity.UpdateDate,
+ Rules = entity.Rules.Select(x => new AccessRuleDto
+ {
+ AccessId = x.AccessEntryId,
+ Id = x.Key,
+ Claim = x.Claim,
+ ClaimType = x.ClaimType,
+ CreateDate = x.CreateDate,
+ UpdateDate = x.UpdateDate
+ }).ToList()
+ };
+
+ return dto;
+ }
+ }
+}
\ No newline at end of file
diff --git a/src/Umbraco.Core/Persistence/Factories/TemplateFactory.cs b/src/Umbraco.Core/Persistence/Factories/TemplateFactory.cs
index 1124d2e9a8..1e59c8e920 100644
--- a/src/Umbraco.Core/Persistence/Factories/TemplateFactory.cs
+++ b/src/Umbraco.Core/Persistence/Factories/TemplateFactory.cs
@@ -39,7 +39,7 @@ namespace Umbraco.Core.Persistence.Factories
{
CreateDate = dto.NodeDto.CreateDate,
Id = dto.NodeId,
- Key = dto.NodeDto.UniqueId.Value,
+ Key = dto.NodeDto.UniqueId,
Path = dto.NodeDto.Path
};
diff --git a/src/Umbraco.Core/Persistence/Factories/UmbracoEntityFactory.cs b/src/Umbraco.Core/Persistence/Factories/UmbracoEntityFactory.cs
index 056d554d17..0494a25cfb 100644
--- a/src/Umbraco.Core/Persistence/Factories/UmbracoEntityFactory.cs
+++ b/src/Umbraco.Core/Persistence/Factories/UmbracoEntityFactory.cs
@@ -75,7 +75,7 @@ namespace Umbraco.Core.Persistence.Factories
CreateDate = dto.CreateDate,
CreatorId = dto.UserId.Value,
Id = dto.NodeId,
- Key = dto.UniqueId.Value,
+ Key = dto.UniqueId,
Level = dto.Level,
Name = dto.Text,
NodeObjectTypeId = dto.NodeObjectType.Value,
diff --git a/src/Umbraco.Core/Persistence/Migrations/Upgrades/TargetVersionSevenThreeZero/AddPublicAccessTables.cs b/src/Umbraco.Core/Persistence/Migrations/Upgrades/TargetVersionSevenThreeZero/AddPublicAccessTables.cs
index e2a5318051..0ab2e683b8 100644
--- a/src/Umbraco.Core/Persistence/Migrations/Upgrades/TargetVersionSevenThreeZero/AddPublicAccessTables.cs
+++ b/src/Umbraco.Core/Persistence/Migrations/Upgrades/TargetVersionSevenThreeZero/AddPublicAccessTables.cs
@@ -1,9 +1,10 @@
using System.Linq;
using Umbraco.Core.Configuration;
+using Umbraco.Core.Persistence.DatabaseModelDefinitions;
namespace Umbraco.Core.Persistence.Migrations.Upgrades.TargetVersionSevenThreeZero
{
- [Migration("7.3.0", 5, GlobalSettings.UmbracoMigrationName)]
+ [Migration("7.3.0", 6, GlobalSettings.UmbracoMigrationName)]
public class AddPublicAccessTables : MigrationBase
{
public override void Up()
@@ -13,20 +14,31 @@ namespace Umbraco.Core.Persistence.Migrations.Upgrades.TargetVersionSevenThreeZe
if (tables.InvariantContains("umbracoAccess")) return;
Create.Table("umbracoAccess")
- .WithColumn("id").AsInt32().NotNullable().Identity().PrimaryKey("PK_umbracoAccess")
- .WithColumn("nodeId").AsInt32().NotNullable().ForeignKey("FK_umbracoAccess_umbracoNode_id", "umbracoNode", "id")
- .WithColumn("loginNodeId").AsInt32().NotNullable().ForeignKey("FK_umbracoAccess_umbracoNode_id1", "umbracoNode", "id")
- .WithColumn("noAccessNodeId").AsInt32().NotNullable().ForeignKey("FK_umbracoAccess_umbracoNode_id2", "umbracoNode", "id");
+ .WithColumn("id").AsGuid().NotNullable().PrimaryKey("PK_umbracoAccess")
+ .WithColumn("nodeId").AsGuid().NotNullable().ForeignKey("FK_umbracoAccess_umbracoNode_id", "umbracoNode", "uniqueID")
+ .WithColumn("loginNodeId").AsGuid().NotNullable().ForeignKey("FK_umbracoAccess_umbracoNode_id1", "umbracoNode", "uniqueID")
+ .WithColumn("noAccessNodeId").AsGuid().NotNullable().ForeignKey("FK_umbracoAccess_umbracoNode_id2", "umbracoNode", "uniqueID")
+ .WithColumn("createDate").AsDateTime().NotNullable().WithDefault(SystemMethods.CurrentDateTime)
+ .WithColumn("updateDate").AsDateTime().NotNullable().WithDefault(SystemMethods.CurrentDateTime);
+
+ //unique constraint on node id = 1:1
+ Create.Index("IX_umbracoAccess_nodeId").OnTable("umbracoAccess").OnColumn("nodeId").Unique();
Create.Table("umbracoAccessRule")
- .WithColumn("id").AsInt32().NotNullable().Identity().PrimaryKey("PK_umbracoAccessRule")
- .WithColumn("accessId").AsInt32().NotNullable().ForeignKey("FK_umbracoAccessRule_umbracoAccess_id", "umbracoAccess", "id")
+ .WithColumn("id").AsGuid().NotNullable().PrimaryKey("PK_umbracoAccessRule")
+ .WithColumn("accessId").AsGuid().NotNullable().ForeignKey("FK_umbracoAccessRule_umbracoAccess_id", "umbracoAccess", "id")
.WithColumn("claim").AsString().NotNullable()
- .WithColumn("claimType").AsString().NotNullable();
+ .WithColumn("claimType").AsString().NotNullable()
+ .WithColumn("createDate").AsDateTime().NotNullable().WithDefault(SystemMethods.CurrentDateTime)
+ .WithColumn("updateDate").AsDateTime().NotNullable().WithDefault(SystemMethods.CurrentDateTime);
- //Create.PrimaryKey("PK_cmsContentType2ContentType")
- // .OnTable("cmsContentType2ContentType")
- // .Columns(new[] { "parentContentTypeId", "childContentTypeId" });
+ //unique constraint on node + claim + claim type
+ Create.Index("IX_umbracoAccessRule").OnTable("umbracoAccessRule")
+ .OnColumn("accessId").Ascending()
+ .OnColumn("claim").Ascending()
+ .OnColumn("claimType").Ascending()
+ .WithOptions()
+ .Unique();
}
public override void Down()
diff --git a/src/Umbraco.Core/Persistence/Migrations/Upgrades/TargetVersionSevenThreeZero/UpdateUniqueIdToHaveCorrectIndexType.cs b/src/Umbraco.Core/Persistence/Migrations/Upgrades/TargetVersionSevenThreeZero/UpdateUniqueIdToHaveCorrectIndexType.cs
new file mode 100644
index 0000000000..92876bbb4d
--- /dev/null
+++ b/src/Umbraco.Core/Persistence/Migrations/Upgrades/TargetVersionSevenThreeZero/UpdateUniqueIdToHaveCorrectIndexType.cs
@@ -0,0 +1,22 @@
+using Umbraco.Core.Configuration;
+
+namespace Umbraco.Core.Persistence.Migrations.Upgrades.TargetVersionSevenThreeZero
+{
+ [Migration("7.3.0", 5, GlobalSettings.UmbracoMigrationName)]
+ public class UpdateUniqueIdToHaveCorrectIndexType : MigrationBase
+ {
+ //see: http://issues.umbraco.org/issue/U4-6188, http://issues.umbraco.org/issue/U4-6187
+ public override void Up()
+ {
+ //must be non-nullable
+ Alter.Column("uniqueID").OnTable("umbracoNode").AsGuid().NotNullable();
+ //must be a uniqe index
+ Delete.Index("IX_umbracoNodeUniqueID").OnTable("umbracoNode");
+ Create.Index("IX_umbracoNode_uniqueID").OnTable("umbracoNode").OnColumn("uniqueID").Unique();
+ }
+
+ public override void Down()
+ {
+ }
+ }
+}
\ No newline at end of file
diff --git a/src/Umbraco.Core/Persistence/Relators/AccessRulesRelator.cs b/src/Umbraco.Core/Persistence/Relators/AccessRulesRelator.cs
new file mode 100644
index 0000000000..424c68a863
--- /dev/null
+++ b/src/Umbraco.Core/Persistence/Relators/AccessRulesRelator.cs
@@ -0,0 +1,43 @@
+using System.Collections.Generic;
+using Umbraco.Core.Models.Rdbms;
+
+namespace Umbraco.Core.Persistence.Relators
+{
+ internal class AccessRulesRelator
+ {
+ internal AccessDto Current;
+
+ internal AccessDto Map(AccessDto a, AccessRuleDto p)
+ {
+ // Terminating call. Since we can return null from this function
+ // we need to be ready for PetaPoco to callback later with null
+ // parameters
+ if (a == null)
+ return Current;
+
+ // Is this the same AccessDto as the current one we're processing
+ if (Current != null && Current.Id == a.Id)
+ {
+ // Yes, just add this AccessRuleDto to the current AccessDto's collection
+ Current.Rules.Add(p);
+
+ // Return null to indicate we're not done with this AccessDto yet
+ return null;
+ }
+
+ // This is a different AccessDto to the current one, or this is the
+ // first time through and we don't have a Tab yet
+
+ // Save the current AccessDto
+ var prev = Current;
+
+ // Setup the new current AccessDto
+ Current = a;
+ Current.Rules = new List();
+ Current.Rules.Add(p);
+
+ // Return the now populated previous AccessDto (or null if first time through)
+ return prev;
+ }
+ }
+}
\ No newline at end of file
diff --git a/src/Umbraco.Core/Persistence/Repositories/ContentRepository.cs b/src/Umbraco.Core/Persistence/Repositories/ContentRepository.cs
index 55ec8b3b25..3ac4f5f942 100644
--- a/src/Umbraco.Core/Persistence/Repositories/ContentRepository.cs
+++ b/src/Umbraco.Core/Persistence/Repositories/ContentRepository.cs
@@ -305,6 +305,24 @@ namespace Umbraco.Core.Persistence.Repositories
#region Unit of Work Implementation
+ protected override void PersistDeletedItem(IContent entity)
+ {
+ //We need to clear out all access rules but we need to do this in a manual way
+ var subQuery = new Sql()
+ .Select("umbracoAccessRule.accessId")
+ .From(SqlSyntax)
+ .InnerJoin(SqlSyntax)
+ .On(SqlSyntax, left => left.AccessId, right => right.Id)
+ .Where(dto => dto.NodeId == entity.Key);
+ Database.Execute(SqlSyntax.GetDeleteSubquery("umbracoAccessRule", "accessId", subQuery));
+ //Now delete everything from umbracoAccess, we are doing this manually because we have joined on GUIDs instead
+ // of integers since we'll be moving to GUID for v8 for everything
+ Database.Execute("DELETE FROM umbracoAccess WHERE nodeId = @Key", new {Key = entity.Key});
+
+ //now let the normal delete clauses take care of everything else
+ base.PersistDeletedItem(entity);
+ }
+
protected override void PersistNewItem(IContent entity)
{
((Content)entity).AddingEntity();
diff --git a/src/Umbraco.Core/Persistence/Repositories/Interfaces/IPublicAccessRepository.cs b/src/Umbraco.Core/Persistence/Repositories/Interfaces/IPublicAccessRepository.cs
new file mode 100644
index 0000000000..9ce00cc13a
--- /dev/null
+++ b/src/Umbraco.Core/Persistence/Repositories/Interfaces/IPublicAccessRepository.cs
@@ -0,0 +1,10 @@
+using System;
+using Umbraco.Core.Models;
+
+namespace Umbraco.Core.Persistence.Repositories
+{
+ public interface IPublicAccessRepository : IRepositoryQueryable
+ {
+
+ }
+}
\ No newline at end of file
diff --git a/src/Umbraco.Core/Persistence/Repositories/Interfaces/ITaskRepository.cs b/src/Umbraco.Core/Persistence/Repositories/Interfaces/ITaskRepository.cs
index d2b4770082..60f17c6de5 100644
--- a/src/Umbraco.Core/Persistence/Repositories/Interfaces/ITaskRepository.cs
+++ b/src/Umbraco.Core/Persistence/Repositories/Interfaces/ITaskRepository.cs
@@ -4,11 +4,6 @@ using Umbraco.Core.Models;
namespace Umbraco.Core.Persistence.Repositories
{
- public interface ITaskTypeRepository : IRepositoryQueryable
- {
-
- }
-
public interface ITaskRepository : IRepositoryQueryable
{
IEnumerable GetTasks(int? itemId = null, int? assignedUser = null, int? ownerUser = null, string taskTypeAlias = null, bool includeClosed = false);
diff --git a/src/Umbraco.Core/Persistence/Repositories/Interfaces/ITaskTypeRepository.cs b/src/Umbraco.Core/Persistence/Repositories/Interfaces/ITaskTypeRepository.cs
new file mode 100644
index 0000000000..ed35543ef6
--- /dev/null
+++ b/src/Umbraco.Core/Persistence/Repositories/Interfaces/ITaskTypeRepository.cs
@@ -0,0 +1,9 @@
+using Umbraco.Core.Models;
+
+namespace Umbraco.Core.Persistence.Repositories
+{
+ public interface ITaskTypeRepository : IRepositoryQueryable
+ {
+
+ }
+}
\ No newline at end of file
diff --git a/src/Umbraco.Core/Persistence/Repositories/PetaPocoRepositoryBase.cs b/src/Umbraco.Core/Persistence/Repositories/PetaPocoRepositoryBase.cs
index 872b7f1d14..fe363fea16 100644
--- a/src/Umbraco.Core/Persistence/Repositories/PetaPocoRepositoryBase.cs
+++ b/src/Umbraco.Core/Persistence/Repositories/PetaPocoRepositoryBase.cs
@@ -1,5 +1,6 @@
using System;
using System.Collections.Generic;
+using System.Data.SqlServerCe;
using Umbraco.Core.Logging;
using Umbraco.Core.Models.EntityBase;
@@ -72,8 +73,13 @@ namespace Umbraco.Core.Persistence.Repositories
var deletes = GetDeleteClauses();
foreach (var delete in deletes)
{
- Database.Execute(delete, new {Id = entity.Id});
+ Database.Execute(delete, new { Id = GetEntityId(entity) });
}
}
+
+ protected virtual TId GetEntityId(TEntity entity)
+ {
+ return (TId)(object)entity.Id;
+ }
}
}
\ No newline at end of file
diff --git a/src/Umbraco.Core/Persistence/Repositories/PublicAccessRepository.cs b/src/Umbraco.Core/Persistence/Repositories/PublicAccessRepository.cs
new file mode 100644
index 0000000000..e2c02523d9
--- /dev/null
+++ b/src/Umbraco.Core/Persistence/Repositories/PublicAccessRepository.cs
@@ -0,0 +1,153 @@
+using System;
+using System.Collections.Generic;
+using System.Linq;
+using Umbraco.Core.Logging;
+using Umbraco.Core.Models;
+using Umbraco.Core.Models.Rdbms;
+using Umbraco.Core.Persistence.Factories;
+using Umbraco.Core.Persistence.Querying;
+using Umbraco.Core.Persistence.Relators;
+using Umbraco.Core.Persistence.SqlSyntax;
+using Umbraco.Core.Persistence.UnitOfWork;
+
+namespace Umbraco.Core.Persistence.Repositories
+{
+ internal class PublicAccessRepository : PetaPocoRepositoryBase, IPublicAccessRepository
+ {
+ public PublicAccessRepository(IDatabaseUnitOfWork work, CacheHelper cache, ILogger logger, ISqlSyntaxProvider sqlSyntax)
+ : base(work, cache, logger, sqlSyntax)
+ {
+ }
+
+ protected override PublicAccessEntry PerformGet(Guid id)
+ {
+ var sql = GetBaseQuery(false);
+ sql.Where(GetBaseWhereClause(), new { Id = id });
+
+ var taskDto = Database.Fetch(new AccessRulesRelator().Map, sql).FirstOrDefault();
+ if (taskDto == null)
+ return null;
+
+ var factory = new PublicAccessEntryFactory();
+ var entity = factory.BuildEntity(taskDto);
+ return entity;
+ }
+
+ protected override IEnumerable PerformGetAll(params Guid[] ids)
+ {
+ var sql = GetBaseQuery(false);
+
+ if (ids.Any())
+ {
+ sql.Where("umbracoAccess.id IN (@ids)", new { ids = ids });
+ }
+
+ var factory = new PublicAccessEntryFactory();
+ var dtos = Database.Fetch(new AccessRulesRelator().Map, sql);
+ return dtos.Select(factory.BuildEntity);
+ }
+
+ protected override IEnumerable PerformGetByQuery(IQuery query)
+ {
+ var sqlClause = GetBaseQuery(false);
+ var translator = new SqlTranslator(sqlClause, query);
+ var sql = translator.Translate();
+
+ var factory = new PublicAccessEntryFactory();
+ var dtos = Database.Fetch(new AccessRulesRelator().Map, sql);
+ return dtos.Select(factory.BuildEntity);
+ }
+
+ protected override Sql GetBaseQuery(bool isCount)
+ {
+ var sql = new Sql();
+ sql.Select("*")
+ .From(SqlSyntax)
+ .InnerJoin(SqlSyntax)
+ .On(SqlSyntax, left => left.Id, right => right.AccessId);
+
+ return sql;
+ }
+
+ protected override string GetBaseWhereClause()
+ {
+ return "umbracoAccess.id = @Id";
+ }
+
+ protected override IEnumerable GetDeleteClauses()
+ {
+ var list = new List
+ {
+ "DELETE FROM umbracoAccessRule WHERE accessId = @Id",
+ "DELETE FROM umbracoAccess WHERE id = @Id"
+ };
+ return list;
+ }
+
+ protected override Guid NodeObjectTypeId
+ {
+ get { throw new NotImplementedException(); }
+ }
+
+ protected override void PersistNewItem(PublicAccessEntry entity)
+ {
+ entity.AddingEntity();
+ entity.Rules.ForEach(x => x.AddingEntity());
+
+ var factory = new PublicAccessEntryFactory();
+ var dto = factory.BuildDto(entity);
+
+ Database.Insert(dto);
+
+ foreach (var rule in dto.Rules)
+ {
+ rule.AccessId = entity.Key;
+ Database.Insert(rule);
+ }
+
+ entity.ResetDirtyProperties();
+ }
+
+ protected override void PersistUpdatedItem(PublicAccessEntry entity)
+ {
+ entity.UpdatingEntity();
+ entity.Rules.Where(x => x.HasIdentity).ForEach(x => x.UpdatingEntity());
+ entity.Rules.Where(x => x.HasIdentity == false).ForEach(x => x.AddingEntity());
+
+ var factory = new PublicAccessEntryFactory();
+ var dto = factory.BuildDto(entity);
+
+ Database.Update(dto);
+
+ foreach (var rule in entity.Rules)
+ {
+ if (rule.HasIdentity)
+ {
+ Database.Update(dto.Rules.Single(x => x.Id == rule.Key));
+ }
+ else
+ {
+ Database.Insert(new AccessRuleDto
+ {
+ AccessId = dto.NodeId,
+ Claim = rule.Claim,
+ ClaimType = rule.ClaimType,
+ CreateDate = rule.CreateDate,
+ UpdateDate = rule.UpdateDate
+ });
+ }
+ }
+ foreach (var removedRule in entity.RemovedRules)
+ {
+ Database.Delete("WHERE id=@Id", new {Id = removedRule});
+ }
+
+ entity.ResetDirtyProperties();
+ }
+
+ protected override Guid GetEntityId(PublicAccessEntry entity)
+ {
+ return entity.Key;
+ }
+ }
+}
\ No newline at end of file
diff --git a/src/Umbraco.Core/Umbraco.Core.csproj b/src/Umbraco.Core/Umbraco.Core.csproj
index b759c51634..ab9d578fbf 100644
--- a/src/Umbraco.Core/Umbraco.Core.csproj
+++ b/src/Umbraco.Core/Umbraco.Core.csproj
@@ -320,22 +320,30 @@
+
+
+
+
+
+
+
+
diff --git a/src/Umbraco.Tests/Persistence/Repositories/ContentRepositoryTest.cs b/src/Umbraco.Tests/Persistence/Repositories/ContentRepositoryTest.cs
index 2a65297864..f943f05de6 100644
--- a/src/Umbraco.Tests/Persistence/Repositories/ContentRepositoryTest.cs
+++ b/src/Umbraco.Tests/Persistence/Repositories/ContentRepositoryTest.cs
@@ -44,10 +44,10 @@ namespace Umbraco.Tests.Persistence.Repositories
private ContentRepository CreateRepository(IDatabaseUnitOfWork unitOfWork, out ContentTypeRepository contentTypeRepository)
{
- var templateRepository = new TemplateRepository(unitOfWork, CacheHelper.CreateDisabledCacheHelper(), Logger, SqlSyntax, Mock.Of(), Mock.Of(), Mock.Of());
- var tagRepository = new TagRepository(unitOfWork, CacheHelper.CreateDisabledCacheHelper(), Logger, SqlSyntax);
- contentTypeRepository = new ContentTypeRepository(unitOfWork, CacheHelper.CreateDisabledCacheHelper(), Logger, SqlSyntax, templateRepository);
- var repository = new ContentRepository(unitOfWork, CacheHelper.CreateDisabledCacheHelper(), Logger, SqlSyntax, contentTypeRepository, templateRepository, tagRepository);
+ var templateRepository = new TemplateRepository(unitOfWork, CacheHelper, Logger, SqlSyntax, Mock.Of(), Mock.Of(), Mock.Of());
+ var tagRepository = new TagRepository(unitOfWork, CacheHelper, Logger, SqlSyntax);
+ contentTypeRepository = new ContentTypeRepository(unitOfWork, CacheHelper, Logger, SqlSyntax, templateRepository);
+ var repository = new ContentRepository(unitOfWork, CacheHelper, Logger, SqlSyntax, contentTypeRepository, templateRepository, tagRepository);
return repository;
}
diff --git a/src/Umbraco.Tests/Persistence/Repositories/PublicAccessRepositoryTest.cs b/src/Umbraco.Tests/Persistence/Repositories/PublicAccessRepositoryTest.cs
new file mode 100644
index 0000000000..e42a21a115
--- /dev/null
+++ b/src/Umbraco.Tests/Persistence/Repositories/PublicAccessRepositoryTest.cs
@@ -0,0 +1,259 @@
+using System;
+using System.Collections;
+using System.Collections.Generic;
+using System.Linq;
+using System.Web.UI.WebControls;
+using Moq;
+using NUnit.Framework;
+using Umbraco.Core.Configuration.UmbracoSettings;
+using Umbraco.Core.IO;
+using Umbraco.Core.Models;
+using Umbraco.Core.Persistence.Repositories;
+using Umbraco.Core.Persistence.UnitOfWork;
+using Umbraco.Tests.TestHelpers;
+using Umbraco.Tests.TestHelpers.Entities;
+using Content = Umbraco.Core.Models.Content;
+
+namespace Umbraco.Tests.Persistence.Repositories
+{
+ [DatabaseTestBehavior(DatabaseBehavior.NewDbFileAndSchemaPerTest)]
+ [TestFixture]
+ public class PublicAccessRepositoryTest : BaseDatabaseFactoryTest
+ {
+ [Test]
+ public void Can_Delete()
+ {
+ var content = CreateTestData(3).ToArray();
+
+ var provider = new PetaPocoUnitOfWorkProvider(Logger);
+ var unitOfWork = provider.GetUnitOfWork();
+ using (var repo = new PublicAccessRepository(unitOfWork, CacheHelper, Logger, SqlSyntax))
+ {
+
+ var entry = new PublicAccessEntry(content[0], content[1], content[2], new[]
+ {
+ new PublicAccessRule
+ {
+ Claim = "test",
+ ClaimType = "RoleName"
+ },
+ });
+ repo.AddOrUpdate(entry);
+ unitOfWork.Commit();
+
+ repo.Delete(entry);
+ unitOfWork.Commit();
+
+ entry = repo.Get(entry.Key);
+ Assert.IsNull(entry);
+ }
+ }
+
+ [Test]
+ public void Can_Add()
+ {
+ var content = CreateTestData(3).ToArray();
+
+ var provider = new PetaPocoUnitOfWorkProvider(Logger);
+ var unitOfWork = provider.GetUnitOfWork();
+ using (var repo = new PublicAccessRepository(unitOfWork, CacheHelper, Logger, SqlSyntax))
+ {
+ var entry = new PublicAccessEntry(content[0], content[1], content[2], new[]
+ {
+ new PublicAccessRule
+ {
+ Claim = "test",
+ ClaimType = "RoleName"
+ },
+ });
+ repo.AddOrUpdate(entry);
+ unitOfWork.Commit();
+
+ var found = repo.GetAll().ToArray();
+
+ Assert.AreEqual(1, found.Count());
+ Assert.AreEqual(content[0].Key, found[0].ProtectedNodeId);
+ Assert.AreEqual(content[1].Key, found[0].LoginNodeId);
+ Assert.AreEqual(content[2].Key, found[0].NoAccessNodeId);
+ Assert.IsTrue(found[0].HasIdentity);
+ Assert.AreNotEqual(default(DateTime), found[0].CreateDate);
+ Assert.AreNotEqual(default(DateTime), found[0].UpdateDate);
+ Assert.AreEqual(1, found[0].Rules.Count());
+ Assert.AreEqual("test", found[0].Rules.First().Claim);
+ Assert.AreEqual("RoleName", found[0].Rules.First().ClaimType);
+ Assert.AreNotEqual(default(DateTime), found[0].Rules.First().CreateDate);
+ Assert.AreNotEqual(default(DateTime), found[0].Rules.First().UpdateDate);
+ Assert.IsTrue(found[0].Rules.First().HasIdentity);
+ }
+ }
+
+ [Test]
+ public void Can_Update()
+ {
+ var content = CreateTestData(3).ToArray();
+
+ var provider = new PetaPocoUnitOfWorkProvider(Logger);
+ var unitOfWork = provider.GetUnitOfWork();
+ using (var repo = new PublicAccessRepository(unitOfWork, CacheHelper, Logger, SqlSyntax))
+ {
+ var entry = new PublicAccessEntry(content[0], content[1], content[2], new[]
+ {
+ new PublicAccessRule
+ {
+ Claim = "test",
+ ClaimType = "RoleName"
+ },
+ });
+ repo.AddOrUpdate(entry);
+ unitOfWork.Commit();
+
+ //re-get
+ entry = repo.Get(entry.Key);
+
+ entry.Rules.First().Claim = "blah";
+ entry.Rules.First().ClaimType = "asdf";
+ repo.AddOrUpdate(entry);
+
+ unitOfWork.Commit();
+
+ //re-get
+ entry = repo.Get(entry.Key);
+
+ Assert.AreEqual("blah", entry.Rules.First().Claim);
+ Assert.AreEqual("asdf", entry.Rules.First().ClaimType);
+ }
+ }
+
+ [Test]
+ public void Get_By_Id()
+ {
+ var content = CreateTestData(3).ToArray();
+
+ var provider = new PetaPocoUnitOfWorkProvider(Logger);
+ var unitOfWork = provider.GetUnitOfWork();
+ using (var repo = new PublicAccessRepository(unitOfWork, CacheHelper, Logger, SqlSyntax))
+ {
+ var entry = new PublicAccessEntry(content[0], content[1], content[2], new[]
+ {
+ new PublicAccessRule
+ {
+ Claim = "test",
+ ClaimType = "RoleName"
+ },
+ });
+ repo.AddOrUpdate(entry);
+ unitOfWork.Commit();
+
+ //re-get
+ entry = repo.Get(entry.Key);
+
+ Assert.IsNotNull(entry);
+ }
+ }
+
+ [Test]
+ public void Get_All()
+ {
+ var content = CreateTestData(3).ToArray();
+
+ var provider = new PetaPocoUnitOfWorkProvider(Logger);
+ var unitOfWork = provider.GetUnitOfWork();
+ using (var repo = new PublicAccessRepository(unitOfWork, CacheHelper, Logger, SqlSyntax))
+ {
+ var entry1 = new PublicAccessEntry(content[0], content[1], content[2], new[]
+ {
+ new PublicAccessRule
+ {
+ Claim = "test",
+ ClaimType = "RoleName"
+ },
+ });
+ repo.AddOrUpdate(entry1);
+
+ var entry2 = new PublicAccessEntry(content[1], content[0], content[2], new[]
+ {
+ new PublicAccessRule
+ {
+ Claim = "test",
+ ClaimType = "RoleName"
+ },
+ });
+ repo.AddOrUpdate(entry2);
+
+ unitOfWork.Commit();
+
+ var found = repo.GetAll().ToArray();
+ Assert.AreEqual(2, found.Count());
+ }
+ }
+
+
+ [Test]
+ public void Get_All_With_Node_Id()
+ {
+ var content = CreateTestData(3).ToArray();
+
+ var provider = new PetaPocoUnitOfWorkProvider(Logger);
+ var unitOfWork = provider.GetUnitOfWork();
+ using (var repo = new PublicAccessRepository(unitOfWork, CacheHelper, Logger, SqlSyntax))
+ {
+ var entry1 = new PublicAccessEntry(content[0], content[1], content[2], new[]
+ {
+ new PublicAccessRule
+ {
+ Claim = "test",
+ ClaimType = "RoleName"
+ },
+ });
+ repo.AddOrUpdate(entry1);
+
+ var entry2 = new PublicAccessEntry(content[1], content[0], content[2], new[]
+ {
+ new PublicAccessRule
+ {
+ Claim = "test",
+ ClaimType = "RoleName"
+ },
+ });
+ repo.AddOrUpdate(entry2);
+
+ unitOfWork.Commit();
+
+ var found = repo.GetAll(entry1.Key).ToArray();
+ Assert.AreEqual(1, found.Count());
+ }
+ }
+
+ private ContentRepository CreateRepository(IDatabaseUnitOfWork unitOfWork, out ContentTypeRepository contentTypeRepository)
+ {
+ var templateRepository = new TemplateRepository(unitOfWork, CacheHelper, Logger, SqlSyntax, Mock.Of(), Mock.Of(), Mock.Of());
+ var tagRepository = new TagRepository(unitOfWork, CacheHelper, Logger, SqlSyntax);
+ contentTypeRepository = new ContentTypeRepository(unitOfWork, CacheHelper, Logger, SqlSyntax, templateRepository);
+ var repository = new ContentRepository(unitOfWork, CacheHelper, Logger, SqlSyntax, contentTypeRepository, templateRepository, tagRepository);
+ return repository;
+ }
+
+ private IEnumerable CreateTestData(int count)
+ {
+ var provider = new PetaPocoUnitOfWorkProvider(Logger);
+ var unitOfWork = provider.GetUnitOfWork();
+ ContentTypeRepository ctRepo;
+ using (var repo = CreateRepository(unitOfWork, out ctRepo))
+ {
+ var ct = MockedContentTypes.CreateBasicContentType("testing");
+ ctRepo.AddOrUpdate(ct);
+ unitOfWork.Commit();
+ var result = new List();
+ for (int i = 0; i < count; i++)
+ {
+ var c = new Content("test" + i, -1, ct);
+ repo.AddOrUpdate(c);
+ result.Add(c);
+ }
+ unitOfWork.Commit();
+
+ return result;
+ }
+ }
+ }
+}
\ No newline at end of file
diff --git a/src/Umbraco.Tests/Persistence/Repositories/TaskRepositoryTest.cs b/src/Umbraco.Tests/Persistence/Repositories/TaskRepositoryTest.cs
index 1477f62e9f..4a755de581 100644
--- a/src/Umbraco.Tests/Persistence/Repositories/TaskRepositoryTest.cs
+++ b/src/Umbraco.Tests/Persistence/Repositories/TaskRepositoryTest.cs
@@ -96,6 +96,10 @@ namespace Umbraco.Tests.Persistence.Repositories
task.Comment = "blah";
task.Closed = true;
+ unitOfWork.Commit();
+ //re-get
+ task = repo.Get(task.Id);
+
Assert.AreEqual(true, task.Closed);
Assert.AreEqual("blah", task.Comment);
}
diff --git a/src/Umbraco.Tests/Umbraco.Tests.csproj b/src/Umbraco.Tests/Umbraco.Tests.csproj
index 7d4fe26670..0600e0106d 100644
--- a/src/Umbraco.Tests/Umbraco.Tests.csproj
+++ b/src/Umbraco.Tests/Umbraco.Tests.csproj
@@ -176,6 +176,7 @@
+
diff --git a/src/Umbraco.Web.UI/config/ClientDependency.config b/src/Umbraco.Web.UI/config/ClientDependency.config
index 32b39b9d50..006dea76b0 100644
--- a/src/Umbraco.Web.UI/config/ClientDependency.config
+++ b/src/Umbraco.Web.UI/config/ClientDependency.config
@@ -10,7 +10,7 @@ NOTES:
* Compression/Combination/Minification is not enabled unless debug="false" is specified on the 'compiliation' element in the web.config
* A new version will invalidate both client and server cache and create new persisted files
-->
-
+