Merge pull request #1613 from umbraco/temp-U4-7833
U4-7833 Changing doc type results in invalid cache, lucene indexes, e…
This commit is contained in:
@@ -326,7 +326,7 @@ namespace Umbraco.Core.Models
|
||||
}
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// <summary>
|
||||
/// A boolean flag indicating if a property type has been removed from this instance.
|
||||
/// </summary>
|
||||
/// <remarks>
|
||||
|
||||
@@ -32,7 +32,7 @@ namespace Umbraco.Web.Cache
|
||||
/// </summary>
|
||||
/// <param name="json"></param>
|
||||
/// <returns></returns>
|
||||
private static JsonPayload[] DeserializeFromJsonPayload(string json)
|
||||
internal static JsonPayload[] DeserializeFromJsonPayload(string json)
|
||||
{
|
||||
var serializer = new JavaScriptSerializer();
|
||||
var jsonObject = serializer.Deserialize<JsonPayload[]>(json);
|
||||
@@ -45,30 +45,28 @@ namespace Umbraco.Web.Cache
|
||||
/// <param name="contentType"></param>
|
||||
/// <param name="isDeleted">if the item was deleted</param>
|
||||
/// <returns></returns>
|
||||
private static JsonPayload FromContentType(IContentTypeBase contentType, bool isDeleted = false)
|
||||
internal static JsonPayload FromContentType(IContentTypeBase contentType, bool isDeleted = false)
|
||||
{
|
||||
var payload = new JsonPayload
|
||||
{
|
||||
Alias = contentType.Alias,
|
||||
Id = contentType.Id,
|
||||
PropertyTypeIds = contentType.PropertyTypes.Select(x => x.Id).ToArray(),
|
||||
//either IContentType or IMediaType or IMemberType
|
||||
Type = (contentType is IContentType)
|
||||
? typeof(IContentType).Name
|
||||
: (contentType is IMediaType)
|
||||
{
|
||||
Alias = contentType.Alias,
|
||||
Id = contentType.Id,
|
||||
PropertyTypeIds = contentType.PropertyTypes.Select(x => x.Id).ToArray(),
|
||||
//either IContentType or IMediaType or IMemberType
|
||||
Type = (contentType is IContentType)
|
||||
? typeof(IContentType).Name
|
||||
: (contentType is IMediaType)
|
||||
? typeof(IMediaType).Name
|
||||
: typeof(IMemberType).Name,
|
||||
DescendantPayloads = contentType.Descendants().Select(x => FromContentType(x)).ToArray(),
|
||||
WasDeleted = isDeleted
|
||||
};
|
||||
//here we need to check if the alias of the content type changed or if one of the properties was removed.
|
||||
var dirty = contentType as IRememberBeingDirty;
|
||||
if (dirty != null)
|
||||
{
|
||||
payload.PropertyRemoved = dirty.WasPropertyDirty("HasPropertyTypeBeenRemoved");
|
||||
payload.AliasChanged = dirty.WasPropertyDirty("Alias");
|
||||
payload.IsNew = dirty.WasPropertyDirty("HasIdentity");
|
||||
}
|
||||
DescendantPayloads = contentType.Descendants().Select(x => FromContentType(x)).ToArray(),
|
||||
WasDeleted = isDeleted,
|
||||
PropertyRemoved = contentType.WasPropertyDirty("HasPropertyTypeBeenRemoved"),
|
||||
AliasChanged = contentType.WasPropertyDirty("Alias"),
|
||||
PropertyTypeAliasChanged = contentType.PropertyTypes.Any(x => x.WasPropertyDirty("Alias")),
|
||||
IsNew = contentType.WasPropertyDirty("HasIdentity")
|
||||
};
|
||||
|
||||
|
||||
return payload;
|
||||
}
|
||||
|
||||
@@ -90,7 +88,7 @@ namespace Umbraco.Web.Cache
|
||||
|
||||
#region Sub classes
|
||||
|
||||
private class JsonPayload
|
||||
internal class JsonPayload
|
||||
{
|
||||
public JsonPayload()
|
||||
{
|
||||
@@ -103,6 +101,7 @@ namespace Umbraco.Web.Cache
|
||||
public string Type { get; set; }
|
||||
public bool AliasChanged { get; set; }
|
||||
public bool PropertyRemoved { get; set; }
|
||||
public bool PropertyTypeAliasChanged { get; set; }
|
||||
public JsonPayload[] DescendantPayloads { get; set; }
|
||||
public bool WasDeleted { get; set; }
|
||||
public bool IsNew { get; set; }
|
||||
@@ -190,21 +189,21 @@ namespace Umbraco.Web.Cache
|
||||
ApplicationContext.Current.ApplicationCache.RuntimeCache.ClearCacheByKeySearch(CacheKeys.IdToKeyCacheKey);
|
||||
ApplicationContext.Current.ApplicationCache.RuntimeCache.ClearCacheByKeySearch(CacheKeys.KeyToIdCacheKey);
|
||||
|
||||
payloads.ForEach(payload =>
|
||||
foreach (var payload in payloads)
|
||||
{
|
||||
//clear the cache for each item
|
||||
ClearContentTypeCache(payload);
|
||||
|
||||
//we only need to do this for IContentType NOT for IMediaType, we don't want to refresh the whole cache.
|
||||
//if the item was deleted or the alias changed or property removed then we need to refresh the content.
|
||||
//and, don't refresh the cache if it is new.
|
||||
if (payload.Type == typeof(IContentType).Name
|
||||
&& payload.IsNew == false
|
||||
&& (payload.WasDeleted || payload.AliasChanged || payload.PropertyRemoved || payload.PropertyTypeAliasChanged))
|
||||
{
|
||||
//clear the cache for each item
|
||||
ClearContentTypeCache(payload);
|
||||
|
||||
//we only need to do this for IContentType NOT for IMediaType, we don't want to refresh the whole cache.
|
||||
//if the item was deleted or the alias changed or property removed then we need to refresh the content.
|
||||
//and, don't refresh the cache if it is new.
|
||||
if (payload.Type == typeof(IContentType).Name
|
||||
&& !payload.IsNew
|
||||
&& (payload.WasDeleted || payload.AliasChanged || payload.PropertyRemoved))
|
||||
{
|
||||
needsContentRefresh = true;
|
||||
}
|
||||
});
|
||||
needsContentRefresh = true;
|
||||
}
|
||||
}
|
||||
|
||||
//need to refresh the xml content cache if required
|
||||
if (needsContentRefresh)
|
||||
@@ -237,7 +236,7 @@ namespace Umbraco.Web.Cache
|
||||
//cache if only a media type has changed.
|
||||
//we don't want to update the routes cache if all of the content types here are new.
|
||||
if (payloads.Any(x => x.Type == typeof(IContentType).Name)
|
||||
&& !payloads.All(x => x.IsNew)) //if they are all new then don't proceed
|
||||
&& payloads.All(x => x.IsNew) == false) //if they are all new then don't proceed
|
||||
{
|
||||
// SD: we need to clear the routes cache here!
|
||||
//
|
||||
|
||||
@@ -1,4 +1,5 @@
|
||||
using System;
|
||||
using System.Collections.Generic;
|
||||
using System.Globalization;
|
||||
using System.Linq;
|
||||
using System.Xml;
|
||||
@@ -67,12 +68,12 @@ namespace Umbraco.Web.Search
|
||||
|
||||
/// <summary>
|
||||
/// This is used to refresh content indexers IndexData based on the DataService whenever a content type is changed since
|
||||
/// properties may have been added/removed
|
||||
/// properties may have been added/removed, then we need to re-index any required data if aliases have been changed
|
||||
/// </summary>
|
||||
/// <param name="sender"></param>
|
||||
/// <param name="e"></param>
|
||||
/// <remarks>
|
||||
/// See: http://issues.umbraco.org/issue/U4-4798
|
||||
/// See: http://issues.umbraco.org/issue/U4-4798, http://issues.umbraco.org/issue/U4-7833
|
||||
/// </remarks>
|
||||
static void ContentTypeCacheRefresherCacheUpdated(ContentTypeCacheRefresher sender, CacheRefresherEventArgs e)
|
||||
{
|
||||
@@ -81,6 +82,79 @@ namespace Umbraco.Web.Search
|
||||
{
|
||||
provider.RefreshIndexerDataFromDataService();
|
||||
}
|
||||
|
||||
if (e.MessageType == MessageType.RefreshByJson)
|
||||
{
|
||||
var contentTypesChanged = new HashSet<string>();
|
||||
var mediaTypesChanged = new HashSet<string>();
|
||||
var memberTypesChanged = new HashSet<string>();
|
||||
|
||||
var payloads = ContentTypeCacheRefresher.DeserializeFromJsonPayload(e.MessageObject.ToString());
|
||||
foreach (var payload in payloads)
|
||||
{
|
||||
if (payload.IsNew == false
|
||||
&& (payload.WasDeleted || payload.AliasChanged || payload.PropertyRemoved || payload.PropertyTypeAliasChanged))
|
||||
{
|
||||
//if we get here it means that some aliases have changed and the indexes for those particular doc types will need to be updated
|
||||
if (payload.Type == typeof(IContentType).Name)
|
||||
{
|
||||
//if it is content
|
||||
contentTypesChanged.Add(payload.Alias);
|
||||
}
|
||||
else if (payload.Type == typeof(IMediaType).Name)
|
||||
{
|
||||
//if it is media
|
||||
mediaTypesChanged.Add(payload.Alias);
|
||||
}
|
||||
else if (payload.Type == typeof(IMemberType).Name)
|
||||
{
|
||||
//if it is members
|
||||
memberTypesChanged.Add(payload.Alias);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
//TODO: We need to update Examine to support re-indexing multiple items at once instead of one by one which will speed up
|
||||
// the re-indexing process, we don't want to revert to rebuilding the whole thing!
|
||||
|
||||
if (contentTypesChanged.Count > 0)
|
||||
{
|
||||
foreach (var alias in contentTypesChanged)
|
||||
{
|
||||
var ctType = ApplicationContext.Current.Services.ContentTypeService.GetContentType(alias);
|
||||
var contentItems = ApplicationContext.Current.Services.ContentService.GetContentOfContentType(ctType.Id);
|
||||
foreach (var contentItem in contentItems)
|
||||
{
|
||||
ReIndexForContent(contentItem, contentItem.HasPublishedVersion && contentItem.Trashed == false);
|
||||
}
|
||||
}
|
||||
}
|
||||
if (mediaTypesChanged.Count > 0)
|
||||
{
|
||||
foreach (var alias in mediaTypesChanged)
|
||||
{
|
||||
var ctType = ApplicationContext.Current.Services.ContentTypeService.GetMediaType(alias);
|
||||
var mediaItems = ApplicationContext.Current.Services.MediaService.GetMediaOfMediaType(ctType.Id);
|
||||
foreach (var mediaItem in mediaItems)
|
||||
{
|
||||
ReIndexForMedia(mediaItem, mediaItem.Trashed == false);
|
||||
}
|
||||
}
|
||||
}
|
||||
if (memberTypesChanged.Count > 0)
|
||||
{
|
||||
foreach (var alias in memberTypesChanged)
|
||||
{
|
||||
var ctType = ApplicationContext.Current.Services.MemberTypeService.Get(alias);
|
||||
var memberItems = ApplicationContext.Current.Services.MemberService.GetMembersByMemberType(ctType.Id);
|
||||
foreach (var memberItem in memberItems)
|
||||
{
|
||||
ReIndexForMember(memberItem);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
static void MemberCacheRefresherCacheUpdated(MemberCacheRefresher sender, CacheRefresherEventArgs e)
|
||||
@@ -432,7 +506,7 @@ namespace Umbraco.Web.Search
|
||||
//add an icon attribute to get indexed
|
||||
xml.Add(new XAttribute("icon", sender.ContentType.Icon));
|
||||
|
||||
ExamineManager.Instance.ReIndexNode(
|
||||
ExamineManager.Instance.ReIndexNode(
|
||||
xml, IndexTypes.Content,
|
||||
ExamineManager.Instance.IndexProviderCollection.OfType<BaseUmbracoIndexer>()
|
||||
|
||||
|
||||
Reference in New Issue
Block a user