Skip to content

Commit

Permalink
Fixed a serialization issue with PermissionInfo
Browse files Browse the repository at this point in the history
This is a work in progress
  • Loading branch information
valadas committed Jan 29, 2024
1 parent b561caa commit 4e00a9b
Show file tree
Hide file tree
Showing 5 changed files with 212 additions and 43 deletions.
53 changes: 32 additions & 21 deletions DNN Platform/Library/Security/Permissions/PermissionInfo.cs
Original file line number Diff line number Diff line change
Expand Up @@ -18,28 +18,33 @@ namespace DotNetNuke.Security.Permissions
/// <summary>PermissionInfo provides the Entity Layer for Permissions.</summary>
[Serializable]
public class PermissionInfo : BaseEntityInfo, IPermissionDefinitionInfo
{
/// <inheritdoc cref="IPermissionDefinitionInfo.ModuleDefId" />
{
private int moduleDefId;
private int permissionId;

/// <inheritdoc cref="ModuleDefId" />
[XmlIgnore]
[JsonIgnore]
[Obsolete($"Deprecated in DotNetNuke 9.13.1. Use {nameof(IPermissionDefinitionInfo)}.{nameof(IPermissionDefinitionInfo.ModuleDefId)} instead. Scheduled for removal in v11.0.0.")]
[Obsolete($"Deprecated in DotNetNuke 9.13.1. Use {nameof(ModuleDefId)} instead. Scheduled for removal in v11.0.0.")]
[CLSCompliant(false)]
public int ModuleDefID
{
get => ((IPermissionDefinitionInfo)this).ModuleDefId;
set => ((IPermissionDefinitionInfo)this).ModuleDefId = value;
get => this.moduleDefId;
set => this.moduleDefId = value;
}

/// <inheritdoc />
[XmlElement("permissioncode")]
public string PermissionCode { get; set; }

/// <inheritdoc cref="IPermissionDefinitionInfo.PermissionID" />
[XmlElement("permissionid")]
[Obsolete($"Deprecated in DotNetNuke 9.13.1. Use {nameof(IPermissionDefinitionInfo)}.{nameof(IPermissionDefinitionInfo.PermissionId)} instead. Scheduled for removal in v11.0.0.")]
/// <inheritdoc cref="PermissionId" />
[XmlIgnore]
[Obsolete($"Deprecated in DotNetNuke 9.13.1. Use {nameof(PermissionId)} instead. Scheduled for removal in v11.0.0.")]
[CLSCompliant(false)]
public int PermissionID
{
get => ((IPermissionDefinitionInfo)this).PermissionId;
set => ((IPermissionDefinitionInfo)this).PermissionId = value;
get => this.permissionId;
set => this.permissionId = value;
}

/// <inheritdoc />
Expand All @@ -54,25 +59,31 @@ public int PermissionID
/// <inheritdoc />
[XmlIgnore]
[JsonIgnore]
int IPermissionDefinitionInfo.ModuleDefId { get; set; }
public int ModuleDefId
{
get => this.moduleDefId;
set => this.moduleDefId = value;
}

/// <inheritdoc />
[XmlIgnore]
[JsonIgnore]
int IPermissionDefinitionInfo.PermissionId { get; set; }
[XmlElement("permissionid")]
public int PermissionId
{
get => this.permissionId;
set => this.permissionId = value;
}

/// <summary>FillInternal fills a PermissionInfo from a Data Reader.</summary>
/// <param name="dr">The Data Reader to use.</param>
protected override void FillInternal(IDataReader dr)
{
base.FillInternal(dr);

var @this = (IPermissionDefinitionInfo)this;
@this.PermissionId = Null.SetNullInteger(dr["PermissionID"]);
@this.ModuleDefId = Null.SetNullInteger(dr["ModuleDefID"]);
@this.PermissionCode = Null.SetNullString(dr["PermissionCode"]);
@this.PermissionKey = Null.SetNullString(dr["PermissionKey"]);
@this.PermissionName = Null.SetNullString(dr["PermissionName"]);

this.permissionId = Null.SetNullInteger(dr["PermissionID"]);
this.moduleDefId = Null.SetNullInteger(dr["ModuleDefID"]);
this.PermissionCode = Null.SetNullString(dr["PermissionCode"]);
this.PermissionKey = Null.SetNullString(dr["PermissionKey"]);
this.PermissionName = Null.SetNullString(dr["PermissionName"]);
}
}
}
47 changes: 25 additions & 22 deletions DNN Platform/Library/Security/Permissions/PermissionInfoBase.cs
Original file line number Diff line number Diff line change
Expand Up @@ -76,19 +76,20 @@ public string DisplayName
}
}

/// <inheritdoc cref="IPermissionInfo.RoleId" />
[XmlElement("roleid")]
[Obsolete($"Deprecated in DotNetNuke 9.13.1. Use {nameof(IPermissionInfo)}.{nameof(IPermissionInfo.RoleId)} instead. Scheduled for removal in v11.0.0.")]
/// <inheritdoc cref="RoleId" />
[XmlIgnore]
[Obsolete($"Deprecated in DotNetNuke 9.13.1. Use {nameof(RoleId)} instead. Scheduled for removal in v11.0.0.")]
[CLSCompliant(false)]
public int RoleID
{
get
{
return ((IPermissionInfo)this).RoleId;
return this.roleId;
}

set
{
((IPermissionInfo)this).RoleId = value;
this.roleId = value;
}
}

Expand All @@ -107,19 +108,20 @@ public string RoleName
}
}

/// <inheritdoc cref="IPermissionInfo.UserId" />
[XmlElement("userid")]
[Obsolete($"Deprecated in DotNetNuke 9.13.1. Use {nameof(IPermissionInfo)}.{nameof(IPermissionInfo.UserId)} instead. Scheduled for removal in v11.0.0.")]
/// <inheritdoc cref="UserId"/>
[XmlIgnore]
[Obsolete($"Deprecated in DotNetNuke 9.13.1. Use {nameof(UserId)} instead. Scheduled for removal in v11.0.0.")]
[CLSCompliant(false)]
public int UserID
{
get
{
return ((IPermissionInfo)this).UserId;
return this.userId;
}

set
{
((IPermissionInfo)this).UserId = value;
this.userId = value;
}
}

Expand All @@ -139,14 +141,16 @@ public string Username
}

/// <inheritdoc />
int IPermissionInfo.RoleId
[XmlElement("roleid")]
public int RoleId
{
get => this.roleId;
set => this.roleId = value;
}

/// <inheritdoc />
int IPermissionInfo.UserId
[XmlElement("userid")]
public int UserId
{
get => this.userId;
set => this.userId = value;
Expand All @@ -159,22 +163,21 @@ protected override void FillInternal(IDataReader dr)
// Call the base classes fill method to populate base class properties
base.FillInternal(dr);

var @this = (IPermissionInfo)this;
@this.UserId = Null.SetNullInteger(dr["UserID"]);
@this.Username = Null.SetNullString(dr["Username"]);
@this.DisplayName = Null.SetNullString(dr["DisplayName"]);
if (@this.UserId == Null.NullInteger)
this.userId = Null.SetNullInteger(dr["UserID"]);
this.username = Null.SetNullString(dr["Username"]);
this.displayName = Null.SetNullString(dr["DisplayName"]);
if (this.userId == Null.NullInteger)
{
@this.RoleId = Null.SetNullInteger(dr["RoleID"]);
@this.RoleName = Null.SetNullString(dr["RoleName"]);
this.roleId = Null.SetNullInteger(dr["RoleID"]);
this.roleName = Null.SetNullString(dr["RoleName"]);
}
else
{
@this.RoleId = int.Parse(Globals.glbRoleNothing);
@this.RoleName = string.Empty;
this.roleId = int.Parse(Globals.glbRoleNothing);
this.roleName = string.Empty;
}

@this.AllowAccess = Null.SetNullBoolean(dr["AllowAccess"]);
this.allowAccess = Null.SetNullBoolean(dr["AllowAccess"]);
}
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -209,6 +209,8 @@
<Compile Include="Providers\Membership\MembershipProviderTests.cs" />
<Compile Include="Providers\Permissions\PermissionTests.cs" />
<Compile Include="RetryableActionTests.cs" />
<Compile Include="Security\Permissions\PermissionInfoBaseTests.cs" />
<Compile Include="Security\Permissions\PermissionInfoTests.cs" />
<Compile Include="Security\Permissions\PermissionProviderTests.cs" />
<Compile Include="Security\PortalSecurity\PortalSecurityTest.cs" />
<Compile Include="Services\ClientCapability\FacebookRequestControllerTests.cs" />
Expand Down
Original file line number Diff line number Diff line change
@@ -0,0 +1,45 @@
// Licensed to the .NET Foundation under one or more agreements.
// The .NET Foundation licenses this file to you under the MIT license.
// See the LICENSE file in the project root for more information

namespace DotNetNuke.Tests.Core.Security.Permissions
{
using DotNetNuke.Common.Utilities;
using DotNetNuke.Security.Permissions;
using NUnit.Framework;

[TestFixture]
public class PermissionInfoBaseTests
{
[Test]
public void SerializesXMLProperly()
{
// Arrange
var derived = new DerivedPermissionInfo
{
AllowAccess = true,
DisplayName = "Test Name",
RoleID = 123,
RoleName = "Test Role",
UserID = 234,
Username = "Test User",
};

// Act
var xml = XmlUtils.Serialize(derived);

// Assert
Assert.IsNotNull(xml);
Assert.True(xml.Contains("allowaccess"));
Assert.True(xml.Contains("displayname"));
Assert.True(xml.Contains("roleid"));
Assert.True(xml.Contains("rolename"));
Assert.True(xml.Contains("userid"));
Assert.True(xml.Contains("username"));
}
}

public class DerivedPermissionInfo : PermissionInfoBase
{
}
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,108 @@
// Licensed to the .NET Foundation under one or more agreements.
// The .NET Foundation licenses this file to you under the MIT license.
// See the LICENSE file in the project root for more information

namespace DotNetNuke.Tests.Core.Security.Permissions
{
using System;
using System.IO;
using System.Text;

using DotNetNuke.Abstractions.Security.Permissions;
using DotNetNuke.Common.Utilities;
using DotNetNuke.Security.Permissions;
using NUnit.Framework;

[TestFixture]
public class PermissionInfoTests
{
[Test]
public void SerializesJson_IncluddingObsoleteProperties()
{
// Arrange
var permissionInfo = new PermissionInfo
{
ModuleDefID = 123,
PermissionCode = "test",
PermissionID = 456,
PermissionKey = "testKey",
PermissionName = "testName",
};

// Act
var json = Json.Serialize(permissionInfo);

// Assert
Assert.NotNull(json);
Assert.False(json.Contains(nameof(permissionInfo.ModuleDefId)));
Assert.True(json.Contains(nameof(permissionInfo.PermissionCode)));
Assert.True(json.Contains(nameof(permissionInfo.PermissionID))); // old obsolete casing.
Assert.True(json.Contains(nameof(permissionInfo.PermissionId))); // new casing.
Assert.True(json.Contains(nameof(permissionInfo.PermissionKey)));
Assert.False(json.Contains(nameof(permissionInfo.PermissionName)));
}

[Test]
public void DeserializesJson_Properly()
{
// Arrange
var json = "{\"PermissionCode\":\"test\",\"PermissionID\":456,\"PermissionKey\":\"testKey\"}";

// Act
var permissionInfo = Json.Deserialize<PermissionInfo>(json);

// Assert
Assert.NotNull(permissionInfo);
Assert.AreEqual("test", permissionInfo.PermissionCode);
Assert.AreEqual(456, permissionInfo.PermissionID);
Assert.AreEqual(456, ((IPermissionDefinitionInfo)permissionInfo).PermissionId);
Assert.AreEqual("testKey", permissionInfo.PermissionKey);
}

[Test]
public void SerializesXml_IncludesObsoleteProperties()
{
// Arrange
var permissionInfo = new PermissionInfo
{
ModuleDefID = 123,
PermissionCode = "test",
PermissionID = 456,
PermissionKey = "testKey",
PermissionName = "testName",
};
// Act
var xml = XmlUtils.Serialize(permissionInfo);

// Assert
Assert.NotNull(xml);
Assert.False(xml.IndexOf("moduledefid", StringComparison.OrdinalIgnoreCase) >= 0);
Assert.True(xml.Contains("permissioncode"));
Assert.True(xml.Contains("permissionid"));
Assert.True(xml.Contains("permissionkey"));
Assert.False(xml.IndexOf("permissionname", StringComparison.OrdinalIgnoreCase) >= 0);
}

[Test]
public void Deserializes_Properly()
{
// Arrange
var xml = "<PermissionInfo><permissioncode>test</permissioncode><permissionid>456</permissionid><permissionkey>testKey</permissionkey></PermissionInfo>";
var stream = new MemoryStream();
var writer = new StreamWriter(stream, Encoding.UTF8);
writer.Write(xml);
writer.Flush();
stream.Position = 0;

// Act
var permissionInfo = (PermissionInfo)XmlUtils.Deserialize(stream, typeof(PermissionInfo));

// Assert
Assert.NotNull(permissionInfo);
Assert.AreEqual("test", permissionInfo.PermissionCode);
Assert.AreEqual(456, permissionInfo.PermissionID);
Assert.AreEqual(456, ((IPermissionDefinitionInfo)permissionInfo).PermissionId);
Assert.AreEqual("testKey", permissionInfo.PermissionKey);
}
}
}

0 comments on commit 4e00a9b

Please sign in to comment.