diff --git a/src/SQLCE4Umbraco/SqlCE4Umbraco.csproj b/src/SQLCE4Umbraco/SqlCE4Umbraco.csproj
index 2f2bb5866d..454a6cf2ce 100644
--- a/src/SQLCE4Umbraco/SqlCE4Umbraco.csproj
+++ b/src/SQLCE4Umbraco/SqlCE4Umbraco.csproj
@@ -49,11 +49,9 @@
..\packages\SqlServerCE.4.0.0.1\lib\System.Data.SqlServerCe.dll
- True..\packages\SqlServerCE.4.0.0.1\lib\System.Data.SqlServerCe.Entity.dll
- True
diff --git a/src/Umbraco.Core/Logging/RollingFileCleanupAppender.cs b/src/Umbraco.Core/Logging/RollingFileCleanupAppender.cs
new file mode 100644
index 0000000000..6be2552296
--- /dev/null
+++ b/src/Umbraco.Core/Logging/RollingFileCleanupAppender.cs
@@ -0,0 +1,95 @@
+using System;
+using System.IO;
+using log4net.Appender;
+using log4net.Util;
+
+namespace Umbraco.Core.Logging
+{
+ ///
+ /// This class will do the exact same thing as the RollingFileAppender that comes from log4net
+ /// With the extension, that it is able to do automatic cleanup of the logfiles in the directory where logging happens
+ ///
+ /// By specifying the properties MaxLogFileDays and BaseFilePattern, the files will automaticly get deleted when
+ /// the logger is configured(typically when the app starts). To utilize this appender swap out the type of the rollingFile appender
+ /// that ships with Umbraco, to be Umbraco.Core.Logging.RollingFileCleanupAppender, and add the maxLogFileDays and baseFilePattern elements
+ /// to the configuration i.e.:
+ ///
+ ///
+ ///
+ ///
+ ///
+ ///
+ ///
+ ///
+ ///
+ ///
+ ///
+ ///
+ ///
+ ///
+ ///
+ ///
+ ///
+ ///
+ ///
+ ///
+ public class RollingFileCleanupAppender : RollingFileAppender
+ {
+ public int MaxLogFileDays { get; set; }
+ public string BaseFilePattern { get; set; }
+
+ ///
+ /// This override will delete logs older than the specified amount of days
+ ///
+ ///
+ ///
+ protected override void OpenFile(string fileName, bool append)
+ {
+ bool cleanup = true;
+ // Validate settings and input
+ if (MaxLogFileDays <= 0)
+ {
+ LogLog.Warn(typeof(RollingFileCleanupAppender), "Parameter 'MaxLogFileDays' needs to be a positive integer, aborting cleanup");
+ cleanup = false;
+ }
+
+ if (string.IsNullOrWhiteSpace(BaseFilePattern))
+ {
+ LogLog.Warn(typeof(RollingFileCleanupAppender), "Parameter 'BaseFilePattern' is empty, aborting cleanup");
+ cleanup = false;
+ }
+ // grab the directory we are logging to, as this is were we will search for older logfiles
+ var logFolder = Path.GetDirectoryName(fileName);
+ if (Directory.Exists(logFolder) == false)
+ {
+ LogLog.Warn(typeof(RollingFileCleanupAppender), string.Format("Directory '{0}' for logfiles does not exist, aborting cleanup", logFolder));
+ cleanup = false;
+ }
+ // If everything is validated, we can do the actual cleanup
+ if (cleanup)
+ {
+ Cleanup(logFolder);
+ }
+
+ base.OpenFile(fileName, append);
+ }
+
+ private void Cleanup(string directoryPath)
+ {
+ // only take files that matches the pattern we are using i.e. UmbracoTraceLog.*.txt.*
+ string[] logFiles = Directory.GetFiles(directoryPath, BaseFilePattern);
+ LogLog.Debug(typeof(RollingFileCleanupAppender), string.Format("Found {0} files that matches the baseFilePattern: '{1}'", logFiles.Length, BaseFilePattern));
+
+ foreach (var logFile in logFiles)
+ {
+ DateTime lastAccessTime = System.IO.File.GetLastWriteTimeUtc(logFile);
+ // take the value from the config file
+ if (lastAccessTime < DateTime.Now.AddDays(-MaxLogFileDays))
+ {
+ LogLog.Debug(typeof(RollingFileCleanupAppender), string.Format("Deleting file {0} as its lastAccessTime is older than {1} days speficied by MaxLogFileDays", logFile, MaxLogFileDays));
+ base.DeleteFile(logFile);
+ }
+ }
+ }
+ }
+}
diff --git a/src/Umbraco.Core/Services/ContentTypeService.cs b/src/Umbraco.Core/Services/ContentTypeService.cs
index 7de374b140..61a34ce5f8 100644
--- a/src/Umbraco.Core/Services/ContentTypeService.cs
+++ b/src/Umbraco.Core/Services/ContentTypeService.cs
@@ -377,7 +377,7 @@ namespace Umbraco.Core.Services
repo.Delete(container);
uow.Commit();
deleteEventArgs.CanCancel = false;
- uow.Events.Dispatch(DeletedMediaTypeContainer, this, deleteEventArgs);
+ uow.Events.Dispatch(DeletedMediaTypeContainer, this, deleteEventArgs, "DeletedMediaTypeContainer");
return OperationStatus.Success(evtMsgs);
//TODO: Audit trail ?
diff --git a/src/Umbraco.Core/UdiEntityType.cs b/src/Umbraco.Core/UdiEntityType.cs
index b33e9c2ad7..8213edbfc1 100644
--- a/src/Umbraco.Core/UdiEntityType.cs
+++ b/src/Umbraco.Core/UdiEntityType.cs
@@ -118,7 +118,7 @@ namespace Umbraco.Core
case UmbracoObjectTypes.Document:
return Document;
case UmbracoObjectTypes.DocumentBlueprint:
- return DocumentBlueprint;
+ return DocumentBluePrint;
case UmbracoObjectTypes.Media:
return Media;
case UmbracoObjectTypes.Member:
@@ -163,7 +163,7 @@ namespace Umbraco.Core
{
case Document:
return UmbracoObjectTypes.Document;
- case DocumentBlueprint:
+ case DocumentBluePrint:
return UmbracoObjectTypes.DocumentBlueprint;
case Media:
return UmbracoObjectTypes.Media;
diff --git a/src/Umbraco.Core/Umbraco.Core.csproj b/src/Umbraco.Core/Umbraco.Core.csproj
index c2d90cb383..345ee8da8d 100644
--- a/src/Umbraco.Core/Umbraco.Core.csproj
+++ b/src/Umbraco.Core/Umbraco.Core.csproj
@@ -39,18 +39,15 @@
..\packages\AutoMapper.3.3.1\lib\net40\AutoMapper.dll
- True..\packages\AutoMapper.3.3.1\lib\net40\AutoMapper.Net4.dll
- True..\packages\ClientDependency.1.9.2\lib\net45\ClientDependency.Core.dll..\packages\HtmlAgilityPack.1.4.9.5\lib\Net45\HtmlAgilityPack.dll
- True..\packages\ImageProcessor.2.5.6\lib\net45\ImageProcessor.dll
@@ -63,11 +60,9 @@
..\packages\Microsoft.AspNet.Identity.Core.2.2.1\lib\net45\Microsoft.AspNet.Identity.Core.dll
- True..\packages\Microsoft.AspNet.Identity.Owin.2.2.1\lib\net45\Microsoft.AspNet.Identity.Owin.dll
- True..\packages\Microsoft.Owin.3.1.0\lib\net45\Microsoft.Owin.dll
@@ -83,17 +78,16 @@
..\packages\MiniProfiler.2.1.0\lib\net40\MiniProfiler.dll
- True..\packages\MySql.Data.6.9.9\lib\net45\MySql.Data.dll
+ True..\packages\Newtonsoft.Json.10.0.2\lib\net45\Newtonsoft.Json.dll..\packages\Owin.1.0\lib\net40\Owin.dll
- True..\packages\semver.1.1.2\lib\net45\Semver.dll
@@ -105,11 +99,9 @@
..\packages\SqlServerCE.4.0.0.1\lib\System.Data.SqlServerCe.dll
- True..\packages\SqlServerCE.4.0.0.1\lib\System.Data.SqlServerCe.Entity.dll
- True
@@ -368,6 +360,7 @@
+
diff --git a/src/Umbraco.Tests.Benchmarks/Umbraco.Tests.Benchmarks.csproj b/src/Umbraco.Tests.Benchmarks/Umbraco.Tests.Benchmarks.csproj
index 64fef90ffa..6cad6893f5 100644
--- a/src/Umbraco.Tests.Benchmarks/Umbraco.Tests.Benchmarks.csproj
+++ b/src/Umbraco.Tests.Benchmarks/Umbraco.Tests.Benchmarks.csproj
@@ -40,34 +40,27 @@
..\packages\BenchmarkDotNet.0.9.9\lib\net45\BenchmarkDotNet.dll
- True..\packages\BenchmarkDotNet.Core.0.9.9\lib\net45\BenchmarkDotNet.Core.dll
- True..\packages\BenchmarkDotNet.Diagnostics.Windows.0.9.9\lib\net45\BenchmarkDotNet.Diagnostics.Windows.dll
- True..\packages\BenchmarkDotNet.Toolchains.Roslyn.0.9.9\lib\net45\BenchmarkDotNet.Toolchains.Roslyn.dll
- True..\packages\Castle.Core.4.0.0\lib\net45\Castle.Core.dll..\packages\Microsoft.CodeAnalysis.Common.1.3.2\lib\net45\Microsoft.CodeAnalysis.dll
- True..\packages\Microsoft.CodeAnalysis.CSharp.1.3.2\lib\net45\Microsoft.CodeAnalysis.CSharp.dll
- True..\packages\Microsoft.Diagnostics.Tracing.TraceEvent.1.0.41\lib\net40\Microsoft.Diagnostics.Tracing.TraceEvent.dll
- True..\packages\Moq.4.1.1309.0919\lib\net40\Moq.dll
@@ -75,27 +68,22 @@
..\packages\System.Collections.Immutable.1.2.0\lib\portable-net45+win8+wp8+wpa81\System.Collections.Immutable.dll
- True..\packages\SqlServerCE.4.0.0.1\lib\System.Data.SqlServerCe.dll
- True..\packages\SqlServerCE.4.0.0.1\lib\System.Data.SqlServerCe.Entity.dll
- True..\packages\System.Reflection.Metadata.1.3.0\lib\portable-net45+win8\System.Reflection.Metadata.dll
- True..\packages\System.Threading.Tasks.Extensions.4.0.0\lib\portable-net45+win8+wp8+wpa81\System.Threading.Tasks.Extensions.dll
- True
@@ -116,6 +104,7 @@
+
@@ -132,8 +121,8 @@
-
-
+
+
diff --git a/src/Umbraco.Tests/Umbraco.Tests.csproj b/src/Umbraco.Tests/Umbraco.Tests.csproj
index f669416643..db0b5c7c85 100644
--- a/src/Umbraco.Tests/Umbraco.Tests.csproj
+++ b/src/Umbraco.Tests/Umbraco.Tests.csproj
@@ -62,8 +62,8 @@
..\packages\Castle.Core.4.0.0\lib\net45\Castle.Core.dll
-
- ..\packages\Examine.0.1.88\lib\net45\Examine.dll
+
+ ..\packages\Examine.0.1.89-beta05\lib\net45\Examine.dll..\packages\SharpZipLib.0.86.0\lib\20\ICSharpCode.SharpZipLib.dll
diff --git a/src/Umbraco.Tests/packages.config b/src/Umbraco.Tests/packages.config
index 921ac155c7..6075f6da6d 100644
--- a/src/Umbraco.Tests/packages.config
+++ b/src/Umbraco.Tests/packages.config
@@ -2,7 +2,7 @@
-
+
diff --git a/src/Umbraco.Web.UI.Client/src/common/directives/components/grid/grid.rte.directive.js b/src/Umbraco.Web.UI.Client/src/common/directives/components/grid/grid.rte.directive.js
index e3a50b482c..0b2853a174 100644
--- a/src/Umbraco.Web.UI.Client/src/common/directives/components/grid/grid.rte.directive.js
+++ b/src/Umbraco.Web.UI.Client/src/common/directives/components/grid/grid.rte.directive.js
@@ -366,6 +366,9 @@ angular.module("umbraco.directives")
// element might still be there even after the modal has been hidden.
scope.$on('$destroy', function () {
unsubscribe();
+ if (tinyMceEditor !== undefined && tinyMceEditor != null) {
+ tinyMceEditor.destroy()
+ }
});
});
diff --git a/src/Umbraco.Web.UI.Client/src/views/common/overlays/embed/embed.html b/src/Umbraco.Web.UI.Client/src/views/common/overlays/embed/embed.html
index 8c2e5d6bc6..6a829e6be4 100644
--- a/src/Umbraco.Web.UI.Client/src/views/common/overlays/embed/embed.html
+++ b/src/Umbraco.Web.UI.Client/src/views/common/overlays/embed/embed.html
@@ -2,7 +2,7 @@
-
+
@@ -12,15 +12,15 @@
-
+
-
+
-
+
diff --git a/src/Umbraco.Web.UI.Client/src/views/propertyeditors/rte/rte.controller.js b/src/Umbraco.Web.UI.Client/src/views/propertyeditors/rte/rte.controller.js
index d17310d65a..a11a4dae9f 100644
--- a/src/Umbraco.Web.UI.Client/src/views/propertyeditors/rte/rte.controller.js
+++ b/src/Umbraco.Web.UI.Client/src/views/propertyeditors/rte/rte.controller.js
@@ -374,6 +374,9 @@ angular.module("umbraco")
// element might still be there even after the modal has been hidden.
$scope.$on('$destroy', function () {
unsubscribe();
+ if (tinyMceEditor !== undefined && tinyMceEditor != null) {
+ tinyMceEditor.destroy()
+ }
});
});
});
diff --git a/src/Umbraco.Web.UI/Umbraco.Web.UI.csproj b/src/Umbraco.Web.UI/Umbraco.Web.UI.csproj
index 6f96590bf2..4b35b30753 100644
--- a/src/Umbraco.Web.UI/Umbraco.Web.UI.csproj
+++ b/src/Umbraco.Web.UI/Umbraco.Web.UI.csproj
@@ -127,11 +127,10 @@
..\packages\dotless.1.5.2\lib\dotless.Core.dll
-
- ..\packages\Examine.0.1.88\lib\net45\Examine.dll
+
+ ..\packages\Examine.0.1.89-beta05\lib\net45\Examine.dll
- False..\packages\SharpZipLib.0.86.0\lib\20\ICSharpCode.SharpZipLib.dll
@@ -144,7 +143,6 @@
..\packages\log4net.2.0.8\lib\net45-full\log4net.dll
- False..\packages\Lucene.Net.2.9.4.1\lib\net40\Lucene.Net.dll
diff --git a/src/Umbraco.Web.UI/Umbraco/config/lang/nb.xml b/src/Umbraco.Web.UI/Umbraco/config/lang/nb.xml
index 06c8eb017f..a7cc7cad39 100644
--- a/src/Umbraco.Web.UI/Umbraco/config/lang/nb.xml
+++ b/src/Umbraco.Web.UI/Umbraco/config/lang/nb.xml
@@ -422,7 +422,7 @@
Hvilken side skal vises etter at skjemaet er sendtStørrelseSorter
- Submit
+ SendTypeSøk...Opp
@@ -439,6 +439,17 @@
JaMappeSøkeresultater
+ Sorter
+ Avslutt sortering
+ Eksempel
+ Bytt passord
+ til
+ Listevisning
+ Lagrer...
+ nåværende
+ Innbygging
+ Hent
+ valgtBakgrunnsfarge
diff --git a/src/Umbraco.Web.UI/packages.config b/src/Umbraco.Web.UI/packages.config
index 13b0d501eb..783b4eaa18 100644
--- a/src/Umbraco.Web.UI/packages.config
+++ b/src/Umbraco.Web.UI/packages.config
@@ -4,7 +4,7 @@
-
+
diff --git a/src/Umbraco.Web.UI/umbraco/config/lang/da.xml b/src/Umbraco.Web.UI/umbraco/config/lang/da.xml
index 76989945e0..1c1f03f140 100644
--- a/src/Umbraco.Web.UI/umbraco/config/lang/da.xml
+++ b/src/Umbraco.Web.UI/umbraco/config/lang/da.xml
@@ -590,7 +590,6 @@
SortérStatusIndsend
-
TypeSkriv for at søge...Op
@@ -616,6 +615,7 @@
Gemmer...nuværendeIndlejring
+ Hentvalgt
diff --git a/src/Umbraco.Web.UI/umbraco/config/lang/en.xml b/src/Umbraco.Web.UI/umbraco/config/lang/en.xml
index 0674e81066..c0ba47e470 100644
--- a/src/Umbraco.Web.UI/umbraco/config/lang/en.xml
+++ b/src/Umbraco.Web.UI/umbraco/config/lang/en.xml
@@ -638,6 +638,7 @@
Saving...currentEmbed
+ Retrieveselected
diff --git a/src/Umbraco.Web.UI/umbraco/config/lang/en_us.xml b/src/Umbraco.Web.UI/umbraco/config/lang/en_us.xml
index b765116090..777e5ee378 100644
--- a/src/Umbraco.Web.UI/umbraco/config/lang/en_us.xml
+++ b/src/Umbraco.Web.UI/umbraco/config/lang/en_us.xml
@@ -649,6 +649,7 @@
Saving...currentEmbed
+ Retrieveselected
diff --git a/src/Umbraco.Web.UI/umbraco/config/lang/sv.xml b/src/Umbraco.Web.UI/umbraco/config/lang/sv.xml
index 2fae24db21..aad6f440f9 100644
--- a/src/Umbraco.Web.UI/umbraco/config/lang/sv.xml
+++ b/src/Umbraco.Web.UI/umbraco/config/lang/sv.xml
@@ -411,7 +411,7 @@
Vilken sida skall visas när formuläret är skickatStorlekSortera
- Submit
+ SkickaSkrivSkriv för att söka...Upp
@@ -426,8 +426,17 @@
BreddTitta påJa
- Reorder
- I am done reordering
+ Sortera
+ Avsluta sortering
+ Förhandsvisning
+ Ändra lösenord
+ till
+ Listvy
+ Sparar...
+ nuvarande
+ Inbäddning
+ Hämta
+ valgtBakgrundsfärg
diff --git a/src/Umbraco.Web/Editors/MemberController.cs b/src/Umbraco.Web/Editors/MemberController.cs
index 5e246c0d59..5921b9c61c 100644
--- a/src/Umbraco.Web/Editors/MemberController.cs
+++ b/src/Umbraco.Web/Editors/MemberController.cs
@@ -555,7 +555,7 @@ namespace Umbraco.Web.Editors
var builtInAliases = Constants.Conventions.Member.GetStandardPropertyTypeStubs().Select(x => x.Key).ToArray();
foreach (var p in contentItem.PersistedContent.Properties)
{
- var valueMapped = currProps.SingleOrDefault(x => x.Alias == p.Alias);
+ var valueMapped = currProps.FirstOrDefault(x => x.Alias == p.Alias);
if (builtInAliases.Contains(p.Alias) == false && valueMapped != null)
{
p.Value = valueMapped.Value;
diff --git a/src/Umbraco.Web/ExamineStartup.cs b/src/Umbraco.Web/ExamineStartup.cs
new file mode 100644
index 0000000000..e149caabb3
--- /dev/null
+++ b/src/Umbraco.Web/ExamineStartup.cs
@@ -0,0 +1,176 @@
+using System.Collections.Generic;
+using System.Linq;
+using Examine;
+using Examine.Config;
+using Examine.LuceneEngine;
+using Examine.LuceneEngine.Providers;
+using Examine.Providers;
+using Lucene.Net.Index;
+using Lucene.Net.Store;
+using Umbraco.Core;
+using Umbraco.Core.Logging;
+using UmbracoExamine;
+
+namespace Umbraco.Web
+{
+ ///
+ /// Used to configure Examine during startup for the web application
+ ///
+ internal class ExamineStartup
+ {
+ private readonly List _indexesToRebuild = new List();
+ private readonly ApplicationContext _appCtx;
+ private readonly ProfilingLogger _profilingLogger;
+
+ //this is used if we are not the MainDom, in which case we need to ensure that if indexes need rebuilding that this
+ //doesn't occur since that should only occur when we are MainDom
+ private bool _disableExamineIndexing = false;
+
+ public ExamineStartup(ApplicationContext appCtx)
+ {
+ _appCtx = appCtx;
+ _profilingLogger = appCtx.ProfilingLogger;
+ }
+
+ ///
+ /// Called during the initialize operation of the boot manager process
+ ///
+ public void Initialize()
+ {
+ //We want to manage Examine's appdomain shutdown sequence ourselves so first we'll disable Examine's default behavior
+ //and then we'll use MainDom to control Examine's shutdown
+ ExamineManager.DisableDefaultHostingEnvironmentRegistration();
+
+ //we want to tell examine to use a different fs lock instead of the default NativeFSFileLock which could cause problems if the appdomain
+ //terminates and in some rare cases would only allow unlocking of the file if IIS is forcefully terminated. Instead we'll rely on the simplefslock
+ //which simply checks the existence of the lock file
+ DirectoryTracker.DefaultLockFactory = d =>
+ {
+ var simpleFsLockFactory = new NoPrefixSimpleFsLockFactory(d);
+ return simpleFsLockFactory;
+ };
+
+ //This is basically a hack for this item: http://issues.umbraco.org/issue/U4-5976
+ // when Examine initializes it will try to rebuild if the indexes are empty, however in many cases not all of Examine's
+ // event handlers will be assigned during bootup when the rebuilding starts which is a problem. So with the examine 0.1.58.2941 build
+ // it has an event we can subscribe to in order to cancel this rebuilding process, but what we'll do is cancel it and postpone the rebuilding until the
+ // boot process has completed. It's a hack but it works.
+ ExamineManager.Instance.BuildingEmptyIndexOnStartup += OnInstanceOnBuildingEmptyIndexOnStartup;
+
+ //let's deal with shutting down Examine with MainDom
+ var examineShutdownRegistered = _appCtx.MainDom.Register(() =>
+ {
+ using (_profilingLogger.TraceDuration("Examine shutting down"))
+ {
+ //Due to the way Examine's own IRegisteredObject works, we'll first run it with immediate=false and then true so that
+ //it's correct subroutines are executed (otherwise we'd have to run this logic manually ourselves)
+ ExamineManager.Instance.Stop(false);
+ ExamineManager.Instance.Stop(true);
+ }
+ });
+ if (examineShutdownRegistered)
+ {
+ _profilingLogger.Logger.Debug("Examine shutdown registered with MainDom");
+ }
+ else
+ {
+ _profilingLogger.Logger.Debug("Examine shutdown not registered, this appdomain is not the MainDom");
+
+ //if we could not register the shutdown examine ourselves, it means we are not maindom! in this case all of examine should be disabled
+ //from indexing anything on startup!!
+ _disableExamineIndexing = true;
+ Suspendable.ExamineEvents.SuspendIndexers();
+ }
+ }
+
+ ///
+ /// Called during the Complete operation of the boot manager process
+ ///
+ public void Complete()
+ {
+ //We now need to disable waiting for indexing for Examine so that the appdomain is shutdown immediately and doesn't wait for pending
+ //indexing operations. We used to wait for indexing operations to complete but this can cause more problems than that is worth because
+ //that could end up halting shutdown for a very long time causing overlapping appdomains and many other problems.
+ foreach (var luceneIndexer in ExamineManager.Instance.IndexProviderCollection.OfType())
+ {
+ luceneIndexer.WaitForIndexQueueOnShutdown = false;
+ }
+
+ //Ok, now that everything is complete we'll check if we've stored any references to index that need rebuilding and run them
+ // (see the initialize method for notes) - we'll ensure we remove the event handler too in case examine manager doesn't actually
+ // initialize during startup, in which case we want it to rebuild the indexes itself.
+ ExamineManager.Instance.BuildingEmptyIndexOnStartup -= OnInstanceOnBuildingEmptyIndexOnStartup;
+
+ //don't do anything if we have disabled this
+ if (_disableExamineIndexing == false)
+ {
+ foreach (var indexer in _indexesToRebuild)
+ {
+ indexer.RebuildIndex();
+ }
+ }
+ }
+
+ ///
+ /// Called to perform the rebuilding indexes on startup if the indexes don't exist
+ ///
+ public void RebuildIndexes()
+ {
+ //don't do anything if we have disabled this
+ if (_disableExamineIndexing) return;
+
+ //If the developer has explicitly opted out of rebuilding indexes on startup then we
+ // should adhere to that and not do it, this means that if they are load balancing things will be
+ // out of sync if they are auto-scaling but there's not much we can do about that.
+ if (ExamineSettings.Instance.RebuildOnAppStart == false) return;
+
+ foreach (var indexer in GetIndexesForColdBoot())
+ {
+ indexer.RebuildIndex();
+ }
+ }
+
+ ///
+ /// The method used to create indexes on a cold boot
+ ///
+ ///
+ /// A cold boot is when the server determines it will not (or cannot) process instructions in the cache table and
+ /// will rebuild it's own caches itself.
+ ///
+ public IEnumerable GetIndexesForColdBoot()
+ {
+ // NOTE: This is IMPORTANT! ... we don't want to rebuild any index that is already flagged to be re-indexed
+ // on startup based on our _indexesToRebuild variable and how Examine auto-rebuilds when indexes are empty.
+ // This callback is used above for the DatabaseServerMessenger startup options.
+
+ // all indexes
+ IEnumerable indexes = ExamineManager.Instance.IndexProviderCollection;
+
+ // except those that are already flagged
+ // and are processed in Complete()
+ if (_indexesToRebuild.Any())
+ indexes = indexes.Except(_indexesToRebuild);
+
+ // return
+ foreach (var index in indexes)
+ yield return index;
+ }
+
+ private void OnInstanceOnBuildingEmptyIndexOnStartup(object sender, BuildingEmptyIndexOnStartupEventArgs args)
+ {
+ //store the indexer that needs rebuilding because it's empty for when the boot process
+ // is complete and cancel this current event so the rebuild process doesn't start right now.
+ args.Cancel = true;
+ _indexesToRebuild.Add((BaseIndexProvider)args.Indexer);
+
+ //check if the index is rebuilding due to an error and log it
+ if (args.IsHealthy == false)
+ {
+ var baseIndex = args.Indexer as BaseIndexProvider;
+ var name = baseIndex != null ? baseIndex.Name : "[UKNOWN]";
+
+ _profilingLogger.Logger.Error(string.Format("The index {0} is rebuilding due to being unreadable/corrupt", name), args.UnhealthyException);
+ }
+ }
+ }
+}
\ No newline at end of file
diff --git a/src/Umbraco.Web/Scheduling/ScheduledPublishing.cs b/src/Umbraco.Web/Scheduling/ScheduledPublishing.cs
index 919a531549..52cca003b7 100644
--- a/src/Umbraco.Web/Scheduling/ScheduledPublishing.cs
+++ b/src/Umbraco.Web/Scheduling/ScheduledPublishing.cs
@@ -86,7 +86,16 @@ namespace Umbraco.Web.Scheduling
finally
{
if (tempContext != null)
+ {
+ // because we created an http context and assigned it to UmbracoContext,
+ // the batched messenger does batch instructions, but since there is no
+ // request, we need to explicitely tell it to flush the batch of instrs.
+ var batchedMessenger = ServerMessengerResolver.Current.Messenger as BatchedDatabaseServerMessenger;
+ if (batchedMessenger != null)
+ batchedMessenger.FlushBatch();
+
tempContext.Dispose(); // nulls the ThreadStatic context
+ }
}
return true; // repeat
diff --git a/src/Umbraco.Web/Umbraco.Web.csproj b/src/Umbraco.Web/Umbraco.Web.csproj
index 82bc790eb0..99a1582f19 100644
--- a/src/Umbraco.Web/Umbraco.Web.csproj
+++ b/src/Umbraco.Web/Umbraco.Web.csproj
@@ -112,8 +112,8 @@
..\packages\dotless.1.5.2\lib\dotless.Core.dll
-
- ..\packages\Examine.0.1.88\lib\net45\Examine.dll
+
+ ..\packages\Examine.0.1.89-beta05\lib\net45\Examine.dll..\packages\HtmlAgilityPack.1.4.9.5\lib\Net45\HtmlAgilityPack.dll
@@ -121,11 +121,9 @@
..\packages\SharpZipLib.0.86.0\lib\20\ICSharpCode.SharpZipLib.dll
- True..\packages\Lucene.Net.2.9.4.1\lib\net40\Lucene.Net.dll
- True..\packages\Markdown.1.14.7\lib\net45\MarkdownSharp.dll
@@ -335,6 +333,7 @@
+
diff --git a/src/Umbraco.Web/WebApi/Binders/MemberBinder.cs b/src/Umbraco.Web/WebApi/Binders/MemberBinder.cs
index 49669fd427..7a1913ce1a 100644
--- a/src/Umbraco.Web/WebApi/Binders/MemberBinder.cs
+++ b/src/Umbraco.Web/WebApi/Binders/MemberBinder.cs
@@ -97,17 +97,8 @@ namespace Umbraco.Web.WebApi.Binders
if (member == null)
{
throw new InvalidOperationException("Could not find member with key " + key);
- }
+ }
- var standardProps = Constants.Conventions.Member.GetStandardPropertyTypeStubs();
-
- //remove all membership properties, these values are set with the membership provider.
- var exclude = standardProps.Select(x => x.Value.Alias).ToArray();
-
- foreach (var remove in exclude)
- {
- member.Properties.Remove(remove);
- }
return member;
}
diff --git a/src/Umbraco.Web/WebBootManager.cs b/src/Umbraco.Web/WebBootManager.cs
index 2f6b81820f..c38540b6a2 100644
--- a/src/Umbraco.Web/WebBootManager.cs
+++ b/src/Umbraco.Web/WebBootManager.cs
@@ -3,7 +3,6 @@ using System.Collections.Generic;
using System.Collections.Specialized;
using System.Configuration;
using System.Linq;
-using System.Reflection;
using System.Web;
using System.Web.Configuration;
using System.Web.Http;
@@ -11,10 +10,7 @@ using System.Web.Http.Dispatcher;
using System.Web.Mvc;
using System.Web.Routing;
using ClientDependency.Core.Config;
-using Examine;
-using Examine.Config;
using Examine.Providers;
-using umbraco;
using Umbraco.Core;
using Umbraco.Core.Configuration;
using Umbraco.Core.Dictionary;
@@ -27,25 +23,18 @@ using Umbraco.Core.PropertyEditors.ValueConverters;
using Umbraco.Core.Sync;
using Umbraco.Web.Dictionary;
using Umbraco.Web.Install;
-using Umbraco.Web.Macros;
using Umbraco.Web.Media;
using Umbraco.Web.Media.ThumbnailProviders;
-using Umbraco.Web.Models;
using Umbraco.Web.Mvc;
-using Umbraco.Web.PropertyEditors;
-using Umbraco.Web.PropertyEditors.ValueConverters;
using Umbraco.Web.PublishedCache;
using Umbraco.Web.Routing;
using Umbraco.Web.Security;
-using Umbraco.Web.Scheduling;
using Umbraco.Web.UI.JavaScript;
using Umbraco.Web.WebApi;
-using umbraco.BusinessLogic;
using Umbraco.Core.Cache;
using Umbraco.Core.Events;
using Umbraco.Core.Persistence;
using Umbraco.Core.Persistence.UnitOfWork;
-using Umbraco.Core.Publishing;
using Umbraco.Core.Scoping;
using Umbraco.Core.Services;
using Umbraco.Web.Editors;
@@ -64,8 +53,9 @@ namespace Umbraco.Web
public class WebBootManager : CoreBootManager
{
private readonly bool _isForTesting;
- //NOTE: see the Initialize method for what this is used for
- private static readonly List IndexesToRebuild = new List();
+
+ //needs to be static because we have the public static method GetIndexesForColdBoot
+ private static ExamineStartup _examineStartup;
public WebBootManager(UmbracoApplicationBase umbracoApplication)
: base(umbracoApplication)
@@ -109,15 +99,11 @@ namespace Umbraco.Web
///
public override IBootManager Initialize()
{
- //This is basically a hack for this item: http://issues.umbraco.org/issue/U4-5976
- // when Examine initializes it will try to rebuild if the indexes are empty, however in many cases not all of Examine's
- // event handlers will be assigned during bootup when the rebuilding starts which is a problem. So with the examine 0.1.58.2941 build
- // it has an event we can subscribe to in order to cancel this rebuilding process, but what we'll do is cancel it and postpone the rebuilding until the
- // boot process has completed. It's a hack but it works.
- ExamineManager.Instance.BuildingEmptyIndexOnStartup += OnInstanceOnBuildingEmptyIndexOnStartup;
-
base.Initialize();
+ _examineStartup = new ExamineStartup(ApplicationContext);
+ _examineStartup.Initialize();
+
// Backwards compatibility - set the path and URL type for ClientDependency 1.5.1 [LK]
ClientDependency.Core.CompositeFiles.Providers.XmlFileMapper.FileMapVirtualFolder = "~/App_Data/TEMP/ClientDependency";
ClientDependency.Core.CompositeFiles.Providers.BaseCompositeFileProcessingProvider.UrlTypeDefault = ClientDependency.Core.CompositeFiles.Providers.CompositeUrlType.Base64QueryStrings;
@@ -214,25 +200,15 @@ namespace Umbraco.Web
//Now, startup all of our legacy startup handler
ApplicationEventsResolver.Current.InstantiateLegacyStartupHandlers();
- //Ok, now that everything is complete we'll check if we've stored any references to index that need rebuilding and run them
- // (see the initialize method for notes) - we'll ensure we remove the event handler too in case examine manager doesn't actually
- // initialize during startup, in which case we want it to rebuild the indexes itself.
- ExamineManager.Instance.BuildingEmptyIndexOnStartup -= OnInstanceOnBuildingEmptyIndexOnStartup;
- if (IndexesToRebuild.Any())
- {
- foreach (var indexer in IndexesToRebuild)
- {
- indexer.RebuildIndex();
- }
- }
+ _examineStartup.Complete();
//Now ensure webapi is initialized after everything
GlobalConfiguration.Configuration.EnsureInitialized();
-
+
return this;
}
-
+
internal static void ConfigureGlobalFilters()
{
@@ -377,11 +353,11 @@ namespace Umbraco.Web
{
base.InitializeResolvers();
- SearchableTreeResolver.Current = new SearchableTreeResolver(ServiceProvider, LoggerResolver.Current.Logger, ApplicationContext.Services.ApplicationTreeService, () => PluginManager.ResolveSearchableTrees());
+ SearchableTreeResolver.Current = new SearchableTreeResolver(ServiceProvider, LoggerResolver.Current.Logger, ApplicationContext.Services.ApplicationTreeService, () => PluginManager.ResolveSearchableTrees());
XsltExtensionsResolver.Current = new XsltExtensionsResolver(ServiceProvider, LoggerResolver.Current.Logger, () => PluginManager.ResolveXsltExtensions());
- EditorValidationResolver.Current= new EditorValidationResolver(ServiceProvider, LoggerResolver.Current.Logger, () => PluginManager.ResolveTypes());
+ EditorValidationResolver.Current = new EditorValidationResolver(ServiceProvider, LoggerResolver.Current.Logger, () => PluginManager.ResolveTypes());
//set the default RenderMvcController
DefaultRenderMvcControllerResolver.Current = new DefaultRenderMvcControllerResolver(typeof(RenderMvcController));
@@ -421,23 +397,6 @@ namespace Umbraco.Web
}
else
{
-
- //We are using a custom action here so we can check the examine settings value first, we don't want to
- // put that check into the CreateIndexesOnColdBoot method because developers may choose to use this
- // method directly and they will be in charge of this check if they need it
- Action rebuildIndexes = () =>
- {
- //If the developer has explicitly opted out of rebuilding indexes on startup then we
- // should adhere to that and not do it, this means that if they are load balancing things will be
- // out of sync if they are auto-scaling but there's not much we can do about that.
- if (ExamineSettings.Instance.RebuildOnAppStart == false) return;
-
- foreach (var indexer in GetIndexesForColdBoot())
- {
- indexer.RebuildIndex();
- }
- };
-
ServerMessengerResolver.Current.SetServerMessenger(new BatchedDatabaseServerMessenger(
ApplicationContext,
true,
@@ -453,7 +412,7 @@ namespace Umbraco.Web
//rebuild indexes if the server is not synced
// NOTE: This will rebuild ALL indexes including the members, if developers want to target specific
// indexes then they can adjust this logic themselves.
- rebuildIndexes
+ () => _examineStartup.RebuildIndexes()
}
}));
}
@@ -489,9 +448,9 @@ namespace Umbraco.Web
// add all known factories, devs can then modify this list on application
// startup either by binding to events or in their own global.asax
new[]
- {
- typeof (RenderControllerFactory)
- });
+ {
+ typeof (RenderControllerFactory)
+ });
UrlProviderResolver.Current = new UrlProviderResolver(
ServiceProvider, LoggerResolver.Current.Logger,
@@ -559,42 +518,11 @@ namespace Umbraco.Web
///
/// A cold boot is when the server determines it will not (or cannot) process instructions in the cache table and
/// will rebuild it's own caches itself.
+ /// TODO: Does this method need to exist? Is it used publicly elsewhere (i.e. outside of core?)
///
public static IEnumerable GetIndexesForColdBoot()
{
- // NOTE: This is IMPORTANT! ... we don't want to rebuild any index that is already flagged to be re-indexed
- // on startup based on our _indexesToRebuild variable and how Examine auto-rebuilds when indexes are empty.
- // This callback is used above for the DatabaseServerMessenger startup options.
-
- // all indexes
- IEnumerable indexes = ExamineManager.Instance.IndexProviderCollection;
-
- // except those that are already flagged
- // and are processed in Complete()
- if (IndexesToRebuild.Any())
- indexes = indexes.Except(IndexesToRebuild);
-
- // return
- foreach (var index in indexes)
- yield return index;
- }
-
-
- private void OnInstanceOnBuildingEmptyIndexOnStartup(object sender, BuildingEmptyIndexOnStartupEventArgs args)
- {
- //store the indexer that needs rebuilding because it's empty for when the boot process
- // is complete and cancel this current event so the rebuild process doesn't start right now.
- args.Cancel = true;
- IndexesToRebuild.Add((BaseIndexProvider)args.Indexer);
-
- //check if the index is rebuilding due to an error and log it
- if (args.IsHealthy == false)
- {
- var baseIndex = args.Indexer as BaseIndexProvider;
- var name = baseIndex != null ? baseIndex.Name : "[UKNOWN]";
-
- ProfilingLogger.Logger.Error(string.Format("The index {0} is rebuilding due to being unreadable/corrupt", name), args.UnhealthyException);
- }
+ return _examineStartup.GetIndexesForColdBoot();
}
}
}
diff --git a/src/Umbraco.Web/WebServices/ExamineManagementApiController.cs b/src/Umbraco.Web/WebServices/ExamineManagementApiController.cs
index ca49f7a9f7..1218ddc2da 100644
--- a/src/Umbraco.Web/WebServices/ExamineManagementApiController.cs
+++ b/src/Umbraco.Web/WebServices/ExamineManagementApiController.cs
@@ -8,7 +8,9 @@ using Examine;
using Examine.LuceneEngine;
using Examine.LuceneEngine.Providers;
using Examine.Providers;
+using Lucene.Net.Index;
using Lucene.Net.Search;
+using Lucene.Net.Store;
using Umbraco.Core;
using Umbraco.Core.Logging;
using Umbraco.Web.Search;
@@ -189,20 +191,39 @@ namespace Umbraco.Web.WebServices
{
indexer.RebuildIndex();
}
+ catch (LockObtainFailedException)
+ {
+ //this will occur if the index is locked (which it should defo not be!) so in this case we'll forcibly unlock it and try again
+
+ try
+ {
+ IndexWriter.Unlock(indexer.GetLuceneDirectory());
+ indexer.RebuildIndex();
+ }
+ catch (Exception e)
+ {
+ return HandleException(e, indexer);
+ }
+ }
catch (Exception ex)
{
- //ensure it's not listening
- indexer.IndexOperationComplete -= Indexer_IndexOperationComplete;
- LogHelper.Error("An error occurred rebuilding index", ex);
- var response = Request.CreateResponse(HttpStatusCode.Conflict);
- response.Content = new StringContent(string.Format("The index could not be rebuilt at this time, most likely there is another thread currently writing to the index. Error: {0}", ex));
- response.ReasonPhrase = "Could Not Rebuild";
- return response;
+ return HandleException(ex, indexer);
}
}
return msg;
}
+ private HttpResponseMessage HandleException(Exception ex, LuceneIndexer indexer)
+ {
+ //ensure it's not listening
+ indexer.IndexOperationComplete -= Indexer_IndexOperationComplete;
+ LogHelper.Error("An error occurred rebuilding index", ex);
+ var response = Request.CreateResponse(HttpStatusCode.Conflict);
+ response.Content = new StringContent(string.Format("The index could not be rebuilt at this time, most likely there is another thread currently writing to the index. Error: {0}", ex));
+ response.ReasonPhrase = "Could Not Rebuild";
+ return response;
+ }
+
//static listener so it's not GC'd
private static void Indexer_IndexOperationComplete(object sender, EventArgs e)
{
diff --git a/src/Umbraco.Web/packages.config b/src/Umbraco.Web/packages.config
index 88482b4022..66a5495249 100644
--- a/src/Umbraco.Web/packages.config
+++ b/src/Umbraco.Web/packages.config
@@ -3,7 +3,7 @@
-
+
diff --git a/src/UmbracoExamine/BaseUmbracoIndexer.cs b/src/UmbracoExamine/BaseUmbracoIndexer.cs
index 1d87b0dfff..bd480b88f1 100644
--- a/src/UmbracoExamine/BaseUmbracoIndexer.cs
+++ b/src/UmbracoExamine/BaseUmbracoIndexer.cs
@@ -150,7 +150,7 @@ namespace UmbracoExamine
{
//By default, we will be using the UmbracoDataService
//generally this would only need to be set differently for unit testing
- DataService = new UmbracoDataService();
+ DataService = CreateDefaultUmbracoDataService();
}
DataService.LogService.LogLevel = LoggingLevel.Normal;
@@ -206,10 +206,15 @@ namespace UmbracoExamine
}
}
- }
-
+ }
+
#endregion
+ protected virtual IDataService CreateDefaultUmbracoDataService()
+ {
+ return new UmbracoDataService();
+ }
+
///
/// Used to aquire the internal searcher
///
diff --git a/src/UmbracoExamine/Config/IndexSetExtensions.cs b/src/UmbracoExamine/Config/IndexSetExtensions.cs
index f4bd2e24b2..9c087694b7 100644
--- a/src/UmbracoExamine/Config/IndexSetExtensions.cs
+++ b/src/UmbracoExamine/Config/IndexSetExtensions.cs
@@ -13,10 +13,12 @@ namespace UmbracoExamine.Config
///
public static class IndexSetExtensions
{
- internal static IIndexCriteria ToIndexCriteria(this IndexSet set, IDataService svc,
- StaticFieldCollection indexFieldPolicies)
+ internal static IIndexCriteria ToIndexCriteria(this IndexSet set,
+ IDataService svc,
+ StaticFieldCollection indexFieldPolicies,
+ IEnumerable additionalUserFields = null)
{
- return new LazyIndexCriteria(set, svc, indexFieldPolicies);
+ return new LazyIndexCriteria(set, svc, indexFieldPolicies, additionalUserFields);
}
///
diff --git a/src/UmbracoExamine/Config/LazyIndexCriteria.cs b/src/UmbracoExamine/Config/LazyIndexCriteria.cs
index ee58431930..7f7a9510f1 100644
--- a/src/UmbracoExamine/Config/LazyIndexCriteria.cs
+++ b/src/UmbracoExamine/Config/LazyIndexCriteria.cs
@@ -12,7 +12,8 @@ namespace UmbracoExamine.Config
public LazyIndexCriteria(
IndexSet set,
IDataService svc,
- StaticFieldCollection indexFieldPolicies)
+ StaticFieldCollection indexFieldPolicies,
+ IEnumerable additionalUserFields = null)
{
if (set == null) throw new ArgumentNullException("set");
if (indexFieldPolicies == null) throw new ArgumentNullException("indexFieldPolicies");
@@ -21,7 +22,7 @@ namespace UmbracoExamine.Config
_lazyCriteria = new Lazy(() =>
{
var attributeFields = set.IndexAttributeFields.Cast().ToArray();
- var userFields = set.IndexUserFields.Cast().ToArray();
+ var userFields = set.IndexUserFields.Cast().ToList();
var includeNodeTypes = set.IncludeNodeTypes.Cast().Select(x => x.Name).ToArray();
var excludeNodeTypes = set.ExcludeNodeTypes.Cast().Select(x => x.Name).ToArray();
var parentId = set.IndexParentId;
@@ -44,7 +45,7 @@ namespace UmbracoExamine.Config
}
fields.Add(field);
}
- userFields = fields.ToArray();
+ userFields = fields.ToList();
}
//if there are no attribute fields defined, we'll populate them from the data source (include them all)
@@ -68,6 +69,19 @@ namespace UmbracoExamine.Config
attributeFields = fields.ToArray();
}
+ //merge in the additional user fields if any are defined
+ if (additionalUserFields != null)
+ {
+ foreach (var field in additionalUserFields)
+ {
+ var f = field; //copy local
+ if (userFields.Any(x => x.Name == f.Name) == false)
+ {
+ userFields.Add(f);
+ }
+ }
+
+ }
return new IndexCriteria(
attributeFields,
diff --git a/src/UmbracoExamine/DataServices/UmbracoContentService.cs b/src/UmbracoExamine/DataServices/UmbracoContentService.cs
index b52f60a2f2..5dcaabe09b 100644
--- a/src/UmbracoExamine/DataServices/UmbracoContentService.cs
+++ b/src/UmbracoExamine/DataServices/UmbracoContentService.cs
@@ -13,7 +13,7 @@ namespace UmbracoExamine.DataServices
{
public class UmbracoContentService : IContentService
{
- private readonly ApplicationContext _applicationContext;
+ protected ApplicationContext ApplicationContext { get; private set; }
public UmbracoContentService()
: this(ApplicationContext.Current)
@@ -21,7 +21,7 @@ namespace UmbracoExamine.DataServices
public UmbracoContentService(ApplicationContext applicationContext)
{
- _applicationContext = applicationContext;
+ ApplicationContext = applicationContext;
}
///
@@ -60,11 +60,11 @@ namespace UmbracoExamine.DataServices
using (var scope = ApplicationContext.Current.ScopeProvider.CreateScope())
{
var xmlContent = XDocument.Parse("");
- var rootContent = _applicationContext.Services.ContentService.GetRootContent();
+ var rootContent = ApplicationContext.Services.ContentService.GetRootContent();
foreach (var c in rootContent)
{
// not sure this uses the database, but better be save
- xmlContent.Root.Add(c.ToDeepXml(_applicationContext.Services.PackagingService));
+ xmlContent.Root.Add(c.ToDeepXml(ApplicationContext.Services.PackagingService));
}
var result = ((IEnumerable)xmlContent.XPathEvaluate(xpath)).Cast();
scope.Complete();
@@ -82,7 +82,7 @@ namespace UmbracoExamine.DataServices
{
using (var scope = ApplicationContext.Current.ScopeProvider.CreateScope())
{
- var ret = _applicationContext.Services.PublicAccessService.IsProtected(path.EnsureEndsWith("," + nodeId));
+ var ret = ApplicationContext.Services.PublicAccessService.IsProtected(path.EnsureEndsWith("," + nodeId));
scope.Complete();
return ret;
}
@@ -93,14 +93,26 @@ namespace UmbracoExamine.DataServices
///
///
- public IEnumerable GetAllUserPropertyNames()
+ public virtual IEnumerable GetAllUserPropertyNames()
{
using (var scope = ApplicationContext.Current.ScopeProvider.CreateScope())
{
try
- {
- var result = _applicationContext.DatabaseContext.Database.Fetch("select distinct alias from cmsPropertyType order by alias");
- scope.Complete();
+ {
+ //only return the property type aliases for media and content
+
+ var result = ApplicationContext.DatabaseContext.Database.Fetch(
+ @"select distinct cmsPropertyType.alias from cmsPropertyType
+ inner join cmsContentType on cmsContentType.nodeId = cmsPropertyType.contentTypeId
+ inner join umbracoNode on umbracoNode.id = cmsContentType.nodeId
+ where umbracoNode.nodeObjectType = @contentNodeObjectType OR umbracoNode.nodeObjectType = @mediaNodeObjectType
+ order by alias", new
+ {
+ contentNodeObjectType = Constants.ObjectTypes.DocumentType,
+ mediaNodeObjectType = Constants.ObjectTypes.MediaType
+ });
+
+ scope.Complete();
return result;
}
catch (Exception ex)
diff --git a/src/UmbracoExamine/DataServices/UmbracoMemberContentService.cs b/src/UmbracoExamine/DataServices/UmbracoMemberContentService.cs
new file mode 100644
index 0000000000..2112e686a6
--- /dev/null
+++ b/src/UmbracoExamine/DataServices/UmbracoMemberContentService.cs
@@ -0,0 +1,37 @@
+using System;
+using System.Collections.Generic;
+using System.Linq;
+using Umbraco.Core;
+using Umbraco.Core.Logging;
+
+namespace UmbracoExamine.DataServices
+{
+ public class UmbracoMemberContentService : UmbracoContentService
+ {
+ public override IEnumerable GetAllUserPropertyNames()
+ {
+ using (var scope = ApplicationContext.Current.ScopeProvider.CreateScope())
+ {
+ try
+ {
+ //only return the property type aliases for members
+
+ var result = ApplicationContext.DatabaseContext.Database.Fetch(
+ @"select distinct cmsPropertyType.alias from cmsPropertyType
+ inner join cmsContentType on cmsContentType.nodeId = cmsPropertyType.contentTypeId
+ inner join umbracoNode on umbracoNode.id = cmsContentType.nodeId
+ where umbracoNode.nodeObjectType = @nodeObjectType
+ order by alias", new {nodeObjectType = Constants.ObjectTypes.MemberType});
+
+ scope.Complete();
+ return result;
+ }
+ catch (Exception ex)
+ {
+ LogHelper.Error("EXCEPTION OCCURRED reading GetAllUserPropertyNames", ex);
+ return Enumerable.Empty();
+ }
+ }
+ }
+ }
+}
\ No newline at end of file
diff --git a/src/UmbracoExamine/DataServices/UmbracoMemberDataService.cs b/src/UmbracoExamine/DataServices/UmbracoMemberDataService.cs
new file mode 100644
index 0000000000..44aa2815fa
--- /dev/null
+++ b/src/UmbracoExamine/DataServices/UmbracoMemberDataService.cs
@@ -0,0 +1,10 @@
+namespace UmbracoExamine.DataServices
+{
+ public class UmbracoMemberDataService : UmbracoDataService
+ {
+ public UmbracoMemberDataService()
+ {
+ ContentService = new UmbracoMemberContentService();
+ }
+ }
+}
\ No newline at end of file
diff --git a/src/UmbracoExamine/NoPrefixSimpleFsLockFactory.cs b/src/UmbracoExamine/NoPrefixSimpleFsLockFactory.cs
new file mode 100644
index 0000000000..ac4210bcc0
--- /dev/null
+++ b/src/UmbracoExamine/NoPrefixSimpleFsLockFactory.cs
@@ -0,0 +1,26 @@
+using System.IO;
+using Examine;
+using Examine.LuceneEngine;
+using Lucene.Net.Store;
+
+namespace UmbracoExamine
+{
+ ///
+ /// A custom that ensures a prefixless lock prefix
+ ///
+ ///
+ /// This is a work around for the Lucene APIs. By default Lucene will use a null prefix however when we set a custom
+ /// lock factory the null prefix is overwritten.
+ ///
+ public class NoPrefixSimpleFsLockFactory : SimpleFSLockFactory
+ {
+ public NoPrefixSimpleFsLockFactory(DirectoryInfo lockDir) : base(lockDir)
+ {
+ }
+
+ public override void SetLockPrefix(string lockPrefix)
+ {
+ base.SetLockPrefix(null);
+ }
+ }
+}
\ No newline at end of file
diff --git a/src/UmbracoExamine/UmbracoContentIndexer.cs b/src/UmbracoExamine/UmbracoContentIndexer.cs
index 2a2e2ce98c..649c18df47 100644
--- a/src/UmbracoExamine/UmbracoContentIndexer.cs
+++ b/src/UmbracoExamine/UmbracoContentIndexer.cs
@@ -410,7 +410,11 @@ namespace UmbracoExamine
{
if (SupportedTypes.Contains(type) == false)
return;
-
+
+ //if the app is shutting down do not continue
+ if (IsCancellationRequested)
+ return;
+
var pageIndex = 0;
DataService.LogService.AddInfoLog(-1, string.Format("PerformIndexAll - Start data queries - {0}", type));
@@ -530,7 +534,7 @@ namespace UmbracoExamine
content, notPublished).WhereNotNull(), type);
pageIndex++;
- } while (currentPageSize == PageSize);
+ } while (currentPageSize == PageSize && IsCancellationRequested == false); //do not continue if app is shutting down
}
break;
@@ -628,7 +632,7 @@ namespace UmbracoExamine
AddNodesToIndex(xElements, type);
pageIndex++;
- } while (more);
+ } while (more && IsCancellationRequested == false); //don't continue if the app is shutting down
}
internal static IEnumerable GetSerializedContent(
diff --git a/src/UmbracoExamine/UmbracoExamine.csproj b/src/UmbracoExamine/UmbracoExamine.csproj
index f3dd301a8c..2c46c156ef 100644
--- a/src/UmbracoExamine/UmbracoExamine.csproj
+++ b/src/UmbracoExamine/UmbracoExamine.csproj
@@ -82,15 +82,14 @@
..\Solution Items\TheFARM-Public.snk
-
- ..\packages\Examine.0.1.88\lib\net45\Examine.dll
+
+ ..\packages\Examine.0.1.89-beta05\lib\net45\Examine.dll..\packages\SharpZipLib.0.86.0\lib\20\ICSharpCode.SharpZipLib.dll..\packages\Lucene.Net.2.9.4.1\lib\net40\Lucene.Net.dll
- True
@@ -118,6 +117,8 @@
+
+
@@ -133,6 +134,7 @@
+
diff --git a/src/UmbracoExamine/UmbracoMemberIndexer.cs b/src/UmbracoExamine/UmbracoMemberIndexer.cs
index 1a3c9befd2..f3ee7a4a89 100644
--- a/src/UmbracoExamine/UmbracoMemberIndexer.cs
+++ b/src/UmbracoExamine/UmbracoMemberIndexer.cs
@@ -19,6 +19,8 @@ using Lucene.Net.Analysis;
namespace UmbracoExamine
{
+
+
///
/// Custom indexer for members
///
@@ -101,6 +103,11 @@ namespace UmbracoExamine
_memberTypeService = memberTypeService;
}
+ protected override IDataService CreateDefaultUmbracoDataService()
+ {
+ return new UmbracoMemberDataService();
+ }
+
///
/// Ensures that the'_searchEmail' is added to the user fields so that it is indexed - without having to modify the config
///
@@ -108,34 +115,26 @@ namespace UmbracoExamine
///
protected override IIndexCriteria GetIndexerData(IndexSet indexSet)
{
- var indexerData = base.GetIndexerData(indexSet);
-
if (CanInitialize())
{
- //If the fields are missing a custom _searchEmail, then add it
-
- if (indexerData.UserFields.Any(x => x.Name == "_searchEmail") == false)
+ //Add a custom _searchEmail to the index criteria no matter what is in config
+ var field = new IndexField { Name = "_searchEmail" };
+ StaticField policy;
+ if (IndexFieldPolicies.TryGetValue("_searchEmail", out policy))
{
- var field = new IndexField { Name = "_searchEmail" };
-
- StaticField policy;
- if (IndexFieldPolicies.TryGetValue("_searchEmail", out policy))
- {
- field.Type = policy.Type;
- field.EnableSorting = policy.EnableSorting;
- }
-
- return new IndexCriteria(
- indexerData.StandardFields,
- indexerData.UserFields.Concat(new[] { field }),
- indexerData.IncludeNodeTypes,
- indexerData.ExcludeNodeTypes,
- indexerData.ParentNodeId
- );
+ field.Type = policy.Type;
+ field.EnableSorting = policy.EnableSorting;
}
- }
- return indexerData;
+ return indexSet.ToIndexCriteria(DataService, IndexFieldPolicies,
+ //add additional explicit fields
+ new []{field});
+ }
+ else
+ {
+ return base.GetIndexerData(indexSet);
+ }
+
}
///
@@ -198,7 +197,7 @@ namespace UmbracoExamine
AddNodesToIndex(GetSerializedMembers(members), type);
pageIndex++;
- } while (members.Length == pageSize);
+ } while (members.Length == pageSize && IsCancellationRequested == false); //don't continue if the app is shutting down
}
}
else
@@ -212,7 +211,7 @@ namespace UmbracoExamine
AddNodesToIndex(GetSerializedMembers(members), type);
pageIndex++;
- } while (members.Length == pageSize);
+ } while (members.Length == pageSize && IsCancellationRequested == false); //don't continue if the app is shutting down
}
}
}
@@ -233,8 +232,8 @@ namespace UmbracoExamine
protected override XDocument GetXDocument(string xPath, string type)
{
throw new NotSupportedException();
- }
-
+ }
+
///
/// Add the special __key and _searchEmail fields
///
diff --git a/src/UmbracoExamine/packages.config b/src/UmbracoExamine/packages.config
index 40bdd28e84..74b8cbb907 100644
--- a/src/UmbracoExamine/packages.config
+++ b/src/UmbracoExamine/packages.config
@@ -1,6 +1,6 @@
-
+
\ No newline at end of file
diff --git a/src/umbraco.MacroEngines/packages.config b/src/umbraco.MacroEngines/packages.config
index 6aadcba8d4..14c21a4bd4 100644
--- a/src/umbraco.MacroEngines/packages.config
+++ b/src/umbraco.MacroEngines/packages.config
@@ -1,6 +1,6 @@
-
+
diff --git a/src/umbraco.MacroEngines/umbraco.MacroEngines.csproj b/src/umbraco.MacroEngines/umbraco.MacroEngines.csproj
index 46c2b1ed2c..bde18c31dd 100644
--- a/src/umbraco.MacroEngines/umbraco.MacroEngines.csproj
+++ b/src/umbraco.MacroEngines/umbraco.MacroEngines.csproj
@@ -45,8 +45,8 @@
false
-
- ..\packages\Examine.0.1.88\lib\net45\Examine.dll
+
+ ..\packages\Examine.0.1.89-beta05\lib\net45\Examine.dll..\packages\HtmlAgilityPack.1.4.9.5\lib\Net45\HtmlAgilityPack.dll
@@ -57,7 +57,6 @@
..\packages\Lucene.Net.2.9.4.1\lib\net40\Lucene.Net.dll
- True..\packages\Microsoft.Web.Infrastructure.1.0.0.0\lib\net40\Microsoft.Web.Infrastructure.dll
diff --git a/src/umbraco.businesslogic/umbraco.businesslogic.csproj b/src/umbraco.businesslogic/umbraco.businesslogic.csproj
index bbc98ca0c7..cb1e47eaf8 100644
--- a/src/umbraco.businesslogic/umbraco.businesslogic.csproj
+++ b/src/umbraco.businesslogic/umbraco.businesslogic.csproj
@@ -108,11 +108,9 @@
..\packages\AutoMapper.3.3.1\lib\net40\AutoMapper.dll
- True..\packages\AutoMapper.3.3.1\lib\net40\AutoMapper.Net4.dll
- True..\packages\Microsoft.AspNet.Identity.Core.2.2.1\lib\net45\Microsoft.AspNet.Identity.Core.dll
@@ -122,11 +120,9 @@
..\packages\Microsoft.Web.Infrastructure.1.0.0.0\lib\net40\Microsoft.Web.Infrastructure.dll
- True..\packages\Owin.1.0\lib\net40\Owin.dll
- True
@@ -145,27 +141,21 @@
..\packages\Microsoft.AspNet.WebPages.3.2.3\lib\net45\System.Web.Helpers.dll
- True..\packages\Microsoft.AspNet.Mvc.5.2.3\lib\net45\System.Web.Mvc.dll
- True..\packages\Microsoft.AspNet.Razor.3.2.3\lib\net45\System.Web.Razor.dll
- True..\packages\Microsoft.AspNet.WebPages.3.2.3\lib\net45\System.Web.WebPages.dll
- True..\packages\Microsoft.AspNet.WebPages.3.2.3\lib\net45\System.Web.WebPages.Deployment.dll
- True..\packages\Microsoft.AspNet.WebPages.3.2.3\lib\net45\System.Web.WebPages.Razor.dll
- TrueSystem.XML
diff --git a/src/umbraco.cms/umbraco.cms.csproj b/src/umbraco.cms/umbraco.cms.csproj
index 792279ad10..2b81d1fe92 100644
--- a/src/umbraco.cms/umbraco.cms.csproj
+++ b/src/umbraco.cms/umbraco.cms.csproj
@@ -108,11 +108,9 @@
..\packages\ClientDependency.1.9.2\lib\net45\ClientDependency.Core.dll
- True..\packages\HtmlAgilityPack.1.4.9.5\lib\Net45\HtmlAgilityPack.dll
- True
@@ -166,7 +164,6 @@
..\packages\Tidy.Net.1.0.0\lib\TidyNet.dll
- True
diff --git a/src/umbraco.controls/umbraco.controls.csproj b/src/umbraco.controls/umbraco.controls.csproj
index e458a56213..c562fa35d1 100644
--- a/src/umbraco.controls/umbraco.controls.csproj
+++ b/src/umbraco.controls/umbraco.controls.csproj
@@ -70,7 +70,6 @@
..\packages\ClientDependency.1.9.2\lib\net45\ClientDependency.Core.dll
- True
diff --git a/src/umbraco.datalayer/umbraco.datalayer.csproj b/src/umbraco.datalayer/umbraco.datalayer.csproj
index e0fd450022..de34a0cfbb 100644
--- a/src/umbraco.datalayer/umbraco.datalayer.csproj
+++ b/src/umbraco.datalayer/umbraco.datalayer.csproj
@@ -70,10 +70,10 @@
..\packages\Microsoft.ApplicationBlocks.Data.1.0.1559.20655\lib\Microsoft.ApplicationBlocks.Data.dll
- True..\packages\MySql.Data.6.9.9\lib\net45\MySql.Data.dll
+ True
diff --git a/src/umbraco.editorControls/umbraco.editorControls.csproj b/src/umbraco.editorControls/umbraco.editorControls.csproj
index 5950ac9719..602187e55a 100644
--- a/src/umbraco.editorControls/umbraco.editorControls.csproj
+++ b/src/umbraco.editorControls/umbraco.editorControls.csproj
@@ -116,7 +116,6 @@
..\packages\ClientDependency.1.9.2\lib\net45\ClientDependency.Core.dll
- TrueSystem