Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Rls/v1.2.1 #235

Merged
merged 7 commits into from
Sep 2, 2024
Merged
Show file tree
Hide file tree
Changes from 6 commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
Original file line number Diff line number Diff line change
@@ -1,5 +1,3 @@
using System.Collections.Immutable;

using CMS.Base;
using CMS.MediaLibrary;

Expand Down Expand Up @@ -46,27 +44,42 @@ public async Task<CommandResult> Handle(MigrateMediaLibrariesCommand request, Ca
var skippedMediaLibraries = new HashSet<Guid>();
var unsuitableMediaLibraries =
modelFacade.Select("""
SELECT LibraryName, STRING_AGG(CAST(LibraryGUID AS NVARCHAR(max)), '|') as [LibraryGUIDs]
FROM Media_Library
GROUP BY LibraryName
HAVING COUNT(*) > 1
SELECT LibraryName, LibraryGUID FROM Media_Library [ML]
WHERE EXISTS(
SELECT 1
FROM Media_Library [MLI]
WHERE MLI.LibraryName = ML.LibraryName
GROUP BY LibraryName
HAVING COUNT(*) > 1
)
""",
(reader, _) => new { LibraryName = reader.Unbox<string>("LibraryName"), LibraryGuids = reader.Unbox<string?>("LibraryGUIDs")?.Split('|').Select(Guid.Parse).ToImmutableList() ?? [] });
(reader, _) => new
{
LibraryName = reader.Unbox<string>("LibraryName"),
LibraryGuid = reader.Unbox<Guid?>("LibraryGUID")
});

foreach (var mlg in unsuitableMediaLibraries)
var groupedMls = unsuitableMediaLibraries
.GroupBy(x => x.LibraryName)
.Select(x => new { LibraryGuids = x.Select(y => y.LibraryGuid).ToArray(), LibraryName = x.Key });

foreach (var mlg in groupedMls)
{
logger.LogError(
"Media libraries with LibraryGuid ({LibraryGuids}) have same LibraryName '{LibraryName}', due to removal of sites and media library globalization it is required to set unique LibraryName and LibraryFolder",
string.Join(",", mlg.LibraryGuids), mlg.LibraryName);

foreach (var libraryGuid in mlg.LibraryGuids)
{
skippedMediaLibraries.Add(libraryGuid);
if (libraryGuid is { } lg)
{
skippedMediaLibraries.Add(lg);

protocol.Append(HandbookReferences.NotCurrentlySupportedSkip()
.WithMessage($"Media library '{mlg.LibraryName}' with LibraryGuid '{libraryGuid}' doesn't satisfy unique LibraryName and LibraryFolder condition for migration")
.WithData(new { LibraryGuid = libraryGuid, mlg.LibraryName })
);
protocol.Append(HandbookReferences.NotCurrentlySupportedSkip()
.WithMessage($"Media library '{mlg.LibraryName}' with LibraryGuid '{libraryGuid}' doesn't satisfy unique LibraryName and LibraryFolder condition for migration")
.WithData(new { LibraryGuid = libraryGuid, mlg.LibraryName })
);
}
}
}

Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -90,9 +90,10 @@ public async Task<CommandResult> Handle(MigratePagesCommand request, Cancellatio
.SelectWhere<ICmsDocument>("DocumentNodeID = @nodeId", new SqlParameter("nodeId", ksNode.NodeID))
.ToList();

if (nodeLinkedNode != null)
bool isLinkedNode = nodeLinkedNode != null;
if (isLinkedNode)
{
if (nodeLinkedNode.NodeSiteID != ksNode.NodeSiteID)
if (nodeLinkedNode?.NodeSiteID != ksNode.NodeSiteID)
{
// skip & write to protocol
logger.LogWarning("Linked node with NodeGuid {NodeGuid} is linked from different site - unable to migrate", ksTreeOriginal.NodeGUID);
Expand Down Expand Up @@ -153,7 +154,8 @@ public async Task<CommandResult> Handle(MigratePagesCommand request, Cancellatio
CmsTreeK13 node => node with { NodeLinkedNodeID = null, NodeLinkedNodeSiteID = null },
_ => ksNode
};
logger.LogTrace("Linked node with NodeGuid {NodeGuid} was materialized", ksNode.NodeGUID);

logger.LogWarning("Linked node with NodeGuid {NodeGuid} was materialized (Xperience by Kentico doesn't support links), it no longer serves as link to original document. This affect also routing, this document will have own link generated from node alias path", ksNode.NodeGUID);
}
}

Expand Down Expand Up @@ -254,7 +256,8 @@ await MigratePageUrlPaths(
commonDataInfos,
migratedDocument,
ksNode,
migratedDocument.DocumentCulture
migratedDocument.DocumentCulture,
isLinkedNode
);

existingDocumentLanguages.Add(languageGuid);
Expand All @@ -271,7 +274,8 @@ await MigratePageUrlPaths(
commonDataInfos,
null,
ksNode,
culture.ContentLanguageName
culture.ContentLanguageName,
isLinkedNode
);
}

Expand Down Expand Up @@ -335,7 +339,7 @@ private static void AsserVersionStatusRule(List<ContentItemCommonDataInfo> commo
}

private async Task MigratePageUrlPaths(Guid webPageItemGuid, int webPageItemId, Guid webSiteChannelGuid, Guid languageGuid,
List<ContentItemCommonDataInfo> contentItemCommonDataInfos, ICmsDocument? ksDocument, ICmsTree ksTree, string documentCulture)
List<ContentItemCommonDataInfo> contentItemCommonDataInfos, ICmsDocument? ksDocument, ICmsTree ksTree, string documentCulture, bool isLinkedNode)
{
var existingPaths = WebPageUrlPathInfo.Provider.Get()
.WhereEquals(nameof(WebPageUrlPathInfo.WebPageUrlPathWebPageItemID), webPageItemId)
Expand Down Expand Up @@ -413,8 +417,8 @@ private async Task MigratePageUrlPaths(Guid webPageItemGuid, int webPageItemId,
var webPageUrlPath = new WebPageUrlPathModel
{
WebPageUrlPathGUID = contentItemCommonDataInfo.ContentItemCommonDataVersionStatus == VersionStatus.Draft
? GuidHelper.CreateWebPageUrlPathGuid($"{ksDocument!.DocumentGUID}|{documentCulture}|{ksTree.NodeAliasPath}|DRAFT")
: GuidHelper.CreateWebPageUrlPathGuid($"{ksDocument!.DocumentGUID}|{ksTree.NodeAliasPath}"),
? GuidHelper.CreateWebPageUrlPathGuid($"{ksDocument!.DocumentGUID}|{documentCulture}|{ksTree.NodeAliasPath}|DRAFT|{ksTree.NodeID}")
: GuidHelper.CreateWebPageUrlPathGuid($"{ksDocument!.DocumentGUID}|{ksTree.NodeAliasPath}|{ksTree.NodeID}"),
WebPageUrlPath = ksTree.NodeAliasPath, //ksPath.PageUrlPathUrlPath,
// WebPageUrlPathHash = ksPath.PageUrlPathUrlPathHash,
WebPageUrlPathWebPageItemGuid = webPageItemGuid,
Expand Down Expand Up @@ -457,17 +461,16 @@ private async Task MigratePageUrlPaths(Guid webPageItemGuid, int webPageItemId,

string urlPath = (ksDocument switch
{
CmsDocumentK11 doc => doc.DocumentUrlPath,
CmsDocumentK12 doc => doc.DocumentUrlPath,
CmsDocumentK11 doc => isLinkedNode ? $"{languageInfo.ContentLanguageName}{ksTree.NodeAliasPath}" : doc.DocumentUrlPath,
CmsDocumentK12 doc => isLinkedNode ? $"{languageInfo.ContentLanguageName}{ksTree.NodeAliasPath}" : doc.DocumentUrlPath,
null => $"{languageInfo.ContentLanguageName}{ksTree.NodeAliasPath}",
_ => null
}).NullIf(string.Empty) ?? ksTree.NodeAliasPath;
}).NullIf(string.Empty) ?? $"{ksTree.NodeAliasPath}";

var webPageUrlPath = new WebPageUrlPathModel
{
WebPageUrlPathGUID = GuidHelper.CreateWebPageUrlPathGuid($"{urlPath}|{documentCulture}|{webSiteChannel.WebsiteChannelGUID}"),
WebPageUrlPathGUID = GuidHelper.CreateWebPageUrlPathGuid($"{urlPath}|{documentCulture}|{webSiteChannel.WebsiteChannelGUID}|{ksTree.NodeID}"),
WebPageUrlPath = urlPath,
// WebPageUrlPathHash = kx13PageUrlPath.PageUrlPathUrlPathHash,
WebPageUrlPathWebPageItemGuid = webPageItemGuid,
WebPageUrlPathWebsiteChannelGuid = webSiteChannelGuid,
WebPageUrlPathContentLanguageGuid = languageGuid,
Expand Down Expand Up @@ -496,7 +499,7 @@ private async Task CreateDefaultPageUrlAsync(Guid webPageItemGuid, Guid webSiteC

var webPageUrlPath = new WebPageUrlPathModel
{
WebPageUrlPathGUID = GuidHelper.CreateWebPageUrlPathGuid($"{urlPath}|{documentCulture}|{webSiteChannel.WebsiteChannelGUID}"),
WebPageUrlPathGUID = GuidHelper.CreateWebPageUrlPathGuid($"{urlPath}|{documentCulture}|{webSiteChannel.WebsiteChannelGUID}|{ksTree.NodeID}"),
WebPageUrlPath = urlPath,
WebPageUrlPathWebPageItemGuid = webPageItemGuid,
WebPageUrlPathWebsiteChannelGuid = webSiteChannelGuid,
Expand Down
Original file line number Diff line number Diff line change
@@ -1,3 +1,4 @@
using System.Text.RegularExpressions;
using CMS.MediaLibrary;

using Microsoft.Extensions.Logging;
Expand All @@ -17,10 +18,11 @@ public class MediaLibraryInfoMapper(ILogger<MediaLibraryInfoMapper> logger, Prim
protected override MediaLibraryInfo? CreateNewInstance(MediaLibraryInfoMapperSource source, MappingHelper mappingHelper, AddFailure addFailure) =>
MediaLibraryInfo.New();

private static readonly Regex allowedCharactersForLibraryName = new Regex(@"[^a-zA-Z0-9_]", RegexOptions.Compiled | RegexOptions.Singleline);
protected override MediaLibraryInfo MapInternal(MediaLibraryInfoMapperSource s, MediaLibraryInfo target, bool newInstance, MappingHelper mappingHelper, AddFailure addFailure)
{
var (ksLibrary, ksSite) = s;

string ksSiteNameSafe = allowedCharactersForLibraryName.Replace(ksSite.SiteName, "_");
// Sets the library properties
target.LibraryDisplayName = ksLibrary.LibraryDisplayName;
target.LibraryName = ksLibrary.LibraryName;
Expand All @@ -30,9 +32,9 @@ protected override MediaLibraryInfo MapInternal(MediaLibraryInfoMapperSource s,
target.LibraryDisplayName = ksLibrary.LibraryDisplayName;
target.LibraryDescription = ksLibrary.LibraryDescription;

if (!target.LibraryFolder.StartsWith($"{ksSite.SiteName}_", StringComparison.InvariantCultureIgnoreCase))
if (!target.LibraryFolder.StartsWith($"{ksSiteNameSafe}_", StringComparison.InvariantCultureIgnoreCase))
{
target.LibraryFolder = $"{ksSite.SiteName}_{ksLibrary.LibraryFolder}";
target.LibraryFolder = $"{ksSiteNameSafe}_{ksLibrary.LibraryFolder}";
}

target.LibraryLastModified = mappingHelper.Require(ksLibrary.LibraryLastModified, nameof(ksLibrary.LibraryLastModified));
Expand Down
55 changes: 33 additions & 22 deletions KVA/Migration.Toolkit.Source/Services/SpoiledGuidContext.cs
Original file line number Diff line number Diff line change
Expand Up @@ -24,38 +24,49 @@ public class SpoiledGuidContext(ModelFacade modelFacade, ILogger<SpoiledGuidCont

internal IDictionary<Guid, ImmutableList<SpoiledDocumentGuidInfo>> SpoiledDocumentGuids =>
spoiledDocumentGuids ??= modelFacade.Select("""
SELECT DocumentGUID, STRING_AGG(CONCAT(NodeSiteID, '-', NodeID), '|') [SiteID-NodeID]
SELECT DocumentGUID, NodeSiteID, NodeID
FROM View_CMS_Tree_Joined TJ
GROUP BY DocumentGUID
HAVING COUNT(DocumentID) > 1
WHERE EXISTS(
SELECT 1
FROM View_CMS_Tree_Joined TJI
WHERE TJI.DocumentGUID = TJ.DocumentGUID
GROUP BY DocumentGUID
HAVING COUNT(DocumentID) > 1
)
""",
(reader, version) => new { DocumentGUID = reader.Unbox<Guid>("DocumentGuid"), Info = reader.Unbox<string>("SiteID-NodeID") })
.ToFrozenDictionary(
x => x.DocumentGUID,
x => x.Info.Split('|').Select(i =>
(reader, version) => new
{
string[] spl = i.Split('-');

return new SpoiledDocumentGuidInfo(int.Parse(spl[0]), int.Parse(spl[1]));
}).ToImmutableList()
DocumentGUID = reader.Unbox<Guid>("DocumentGUID"),
NodeID = reader.Unbox<int>("NodeID"),
NodeSiteID = reader.Unbox<int>("NodeSiteID"),
})
.GroupBy(x => x.DocumentGUID)
.ToFrozenDictionary(
x => x.Key,
x => x.Select(i => new SpoiledDocumentGuidInfo(i.NodeSiteID, i.NodeID)).ToImmutableList()
);

internal IDictionary<Guid, ImmutableList<SpoiledNodeGuidInfo>> SpoiledNodeGuids =>
spoiledNodeGuids ??= modelFacade.Select("""
SELECT NodeGUID, STRING_AGG(NodeSiteID, '|') [SiteID]
SELECT NodeGUID, NodeSiteID
FROM View_CMS_Tree_Joined TJ
GROUP BY NodeGUID
HAVING COUNT(NodeGUID) > 1
WHERE EXISTS (
SELECT 1
FROM View_CMS_Tree_Joined TJI
WHERE TJI.NodeGUID = TJ.NodeGUID
GROUP BY NodeGUID
HAVING COUNT(NodeGUID) > 1
)
""",
(reader, version) => new { DocumentGUID = reader.Unbox<Guid>("NodeGUID"), Info = reader.Unbox<string>("SiteID") })
.ToFrozenDictionary(
x => x.DocumentGUID,
x => x.Info.Split('|').Select(i =>
(reader, version) => new
{
string[] spl = i.Split('-');

return new SpoiledNodeGuidInfo(int.Parse(spl[0]));
}).ToImmutableList()
NodeGUID = reader.Unbox<Guid>("NodeGUID"),
NodeSiteID = reader.Unbox<int>("NodeSiteID")
})
.GroupBy(x => x.NodeGUID)
.ToFrozenDictionary(
x => x.Key,
x => x.Select(i => new SpoiledNodeGuidInfo(i.NodeSiteID)).ToImmutableList()
);

public Guid EnsureDocumentGuid(Guid documentGuid, int siteId, int nodeId, int documentId)
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -13,7 +13,7 @@
using Migration.Toolkit.Core.K11.Mappers;
using Migration.Toolkit.K11;
using Migration.Toolkit.K11.Models;
using Migration.Toolkit.KXP.Api.Auxiliary;
using Migration.Toolkit.KXP.Api.Enums;

namespace Migration.Toolkit.Core.K11.Handlers;

Expand All @@ -37,7 +37,7 @@ public async Task<CommandResult> Handle(MigrateMembersCommand request, Cancellat

var k11CmsUsers = k11Context.CmsUsers
.Include(u => u.CmsUserSettingUserSettingsUserNavigation)
.Where(u => UserHelper.PrivilegeLevelsMigratedAsMemberUser.Contains(u.UserPrivilegeLevel))
.Where(u => u.UserPrivilegeLevel == (int)UserPrivilegeLevelEnum.None)
;

foreach (var k11User in k11CmsUsers)
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -12,7 +12,6 @@
using Migration.Toolkit.Core.K11.Contexts;
using Migration.Toolkit.K11;
using Migration.Toolkit.K11.Models;
using Migration.Toolkit.KXP.Api.Auxiliary;
using Migration.Toolkit.KXP.Api.Enums;

namespace Migration.Toolkit.Core.K11.Handlers;
Expand All @@ -38,7 +37,7 @@ public async Task<CommandResult> Handle(MigrateUsersCommand request, Cancellatio
await using var k11Context = await k11ContextFactory.CreateDbContextAsync(cancellationToken);

var k11CmsUsers = k11Context.CmsUsers
.Where(u => UserHelper.PrivilegeLevelsMigratedAsAdminUser.Contains(u.UserPrivilegeLevel))
.Where(u => u.UserPrivilegeLevel == (int)UserPrivilegeLevelEnum.Admin || u.UserPrivilegeLevel == (int)UserPrivilegeLevelEnum.Editor || u.UserPrivilegeLevel == (int)UserPrivilegeLevelEnum.GlobalAdmin)
;

foreach (var k11User in k11CmsUsers)
Expand Down Expand Up @@ -127,7 +126,7 @@ private async Task MigrateUserCmsRoles(K11Context k11Context, CancellationToken
{
var groupedRoles = k11Context.CmsRoles
.Where(r =>
r.CmsUserRoles.Any(ur => UserHelper.PrivilegeLevelsMigratedAsAdminUser.Contains(ur.User.UserPrivilegeLevel))
r.CmsUserRoles.Any(ur => ur.User.UserPrivilegeLevel == (int)UserPrivilegeLevelEnum.Editor || ur.User.UserPrivilegeLevel == (int)UserPrivilegeLevelEnum.Admin || ur.User.UserPrivilegeLevel == (int)UserPrivilegeLevelEnum.GlobalAdmin)
)
.GroupBy(x => x.RoleName)
.AsNoTracking();
Expand Down Expand Up @@ -157,7 +156,7 @@ Roles with RoleGuid ({RoleGuids}) have same RoleName '{RoleName}', due to remova

var k11CmsRoles = k11Context.CmsRoles
.Where(r =>
r.CmsUserRoles.Any(ur => UserHelper.PrivilegeLevelsMigratedAsAdminUser.Contains(ur.User.UserPrivilegeLevel))
r.CmsUserRoles.Any(ur => ur.User.UserPrivilegeLevel == (int)UserPrivilegeLevelEnum.Editor || ur.User.UserPrivilegeLevel == (int)UserPrivilegeLevelEnum.Admin || ur.User.UserPrivilegeLevel == (int)UserPrivilegeLevelEnum.GlobalAdmin)
)
.AsNoTracking()
.AsAsyncEnumerable();
Expand Down Expand Up @@ -215,8 +214,9 @@ private async Task MigrateUserRole(int k11RoleId)
var k11Context = await k11ContextFactory.CreateDbContextAsync();
var k11UserRoles = k11Context.CmsUserRoles
.Where(ur =>
ur.RoleId == k11RoleId &&
UserHelper.PrivilegeLevelsMigratedAsAdminUser.Contains(ur.User.UserPrivilegeLevel)
ur.RoleId == k11RoleId && (
ur.User.UserPrivilegeLevel == (int)UserPrivilegeLevelEnum.Editor || ur.User.UserPrivilegeLevel == (int)UserPrivilegeLevelEnum.Admin || ur.User.UserPrivilegeLevel == (int)UserPrivilegeLevelEnum.GlobalAdmin
)
)
.AsNoTracking()
.AsAsyncEnumerable();
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -14,7 +14,6 @@
using Migration.Toolkit.Core.KX12.Contexts;
using Migration.Toolkit.Core.KX12.Mappers;
using Migration.Toolkit.KX12.Context;
using Migration.Toolkit.KXP.Api.Auxiliary;
using Migration.Toolkit.KXP.Api.Enums;

namespace Migration.Toolkit.Core.KX12.Handlers;
Expand All @@ -39,7 +38,7 @@ public async Task<CommandResult> Handle(MigrateMembersCommand request, Cancellat

var k12CmsUsers = kx12Context.CmsUsers
.Include(u => u.CmsUserSettingUserSettingsUserNavigation)
.Where(u => UserHelper.PrivilegeLevelsMigratedAsMemberUser.Contains(u.UserPrivilegeLevel))
.Where(u => u.UserPrivilegeLevel == (int)UserPrivilegeLevelEnum.None)
;

foreach (var k12User in k12CmsUsers)
Expand Down
Loading
Loading