.Builder.Where(x => types.Contains(x.ContentType.Alias));
+ var result = repository.GetByQuery(query);
+
+ // Assert
+ Assert.That(result.Count(), Is.GreaterThanOrEqualTo(11));
+ }
+ }
+
[Test]
public void Can_Perform_GetPagedResultsByQuery_ForFirstPage_On_MediaRepository()
{
@@ -470,7 +526,7 @@ namespace Umbraco.Tests.Persistence.Repositories
Assert.That(result.First().Name, Is.EqualTo("Test File"));
}
}
-
+
[Test]
public void Can_Perform_GetPagedResultsByQuery_WithFilterMatchingAll_On_MediaRepository()
{
diff --git a/src/Umbraco.Tests/Services/MediaServiceTests.cs b/src/Umbraco.Tests/Services/MediaServiceTests.cs
index 8193df911c..82738a26f4 100644
--- a/src/Umbraco.Tests/Services/MediaServiceTests.cs
+++ b/src/Umbraco.Tests/Services/MediaServiceTests.cs
@@ -7,6 +7,7 @@ using Umbraco.Core;
using Umbraco.Core.Models;
using Umbraco.Core.Models.Rdbms;
using Umbraco.Core.Persistence;
+using Umbraco.Core.Persistence.DatabaseModelDefinitions;
using Umbraco.Core.Persistence.Repositories;
using Umbraco.Core.Persistence.UnitOfWork;
using Umbraco.Tests.TestHelpers;
@@ -30,6 +31,33 @@ namespace Umbraco.Tests.Services
base.TearDown();
}
+ [Test]
+ public void Get_Paged_Children_With_Media_Type_Filter()
+ {
+ var mediaService = ServiceContext.MediaService;
+ var mediaType1 = MockedContentTypes.CreateImageMediaType("Image2");
+ ServiceContext.ContentTypeService.Save(mediaType1);
+ var mediaType2 = MockedContentTypes.CreateImageMediaType("Image3");
+ ServiceContext.ContentTypeService.Save(mediaType2);
+
+ for (int i = 0; i < 10; i++)
+ {
+ var m1 = MockedMedia.CreateMediaImage(mediaType1, -1);
+ mediaService.Save(m1);
+ var m2 = MockedMedia.CreateMediaImage(mediaType2, -1);
+ mediaService.Save(m2);
+ }
+
+ long total;
+ var result = ServiceContext.MediaService.GetPagedChildren(-1, 0, 11, out total, "SortOrder", Direction.Ascending, true, null, new[] {mediaType1.Id, mediaType2.Id});
+ Assert.AreEqual(11, result.Count());
+ Assert.AreEqual(20, total);
+
+ result = ServiceContext.MediaService.GetPagedChildren(-1, 1, 11, out total, "SortOrder", Direction.Ascending, true, null, new[] { mediaType1.Id, mediaType2.Id });
+ Assert.AreEqual(9, result.Count());
+ Assert.AreEqual(20, total);
+ }
+
[Test]
public void Can_Move_Media()
{
diff --git a/src/Umbraco.Web.UI.Client/src/common/resources/media.resource.js b/src/Umbraco.Web.UI.Client/src/common/resources/media.resource.js
index c0aee7280d..c41b7e91c7 100644
--- a/src/Umbraco.Web.UI.Client/src/common/resources/media.resource.js
+++ b/src/Umbraco.Web.UI.Client/src/common/resources/media.resource.js
@@ -427,7 +427,9 @@ function mediaResource($q, $http, umbDataFormatter, umbRequestHelper) {
* Retrieves all media children with types used as folders.
* Uses the convention of looking for media items with mediaTypes ending in
* *Folder so will match "Folder", "bannerFolder", "secureFolder" etc,
- *
+ *
+ * NOTE: This will return a max of 500 folders, if more is required it needs to be paged
+ *
* ##usage
*
* mediaResource.getChildFolders(1234)
@@ -438,21 +440,22 @@ function mediaResource($q, $http, umbDataFormatter, umbRequestHelper) {
*
* @param {int} parentId Id of the media item to query for child folders
* @returns {Promise} resourcePromise object.
- * @deprecated This method is no longer used and shouldn't be because it performs poorly when there are a lot of media items
+ *
*/
getChildFolders: function (parentId) {
if (!parentId) {
parentId = -1;
}
+ //NOTE: This will return a max of 500 folders, if more is required it needs to be paged
return umbRequestHelper.resourcePromise(
$http.get(
umbRequestHelper.getApiUrl(
"mediaApiBaseUrl",
"GetChildFolders",
- [
- { id: parentId }
- ])),
+ {
+ id: parentId
+ })),
'Failed to retrieve child folders for media item ' + parentId);
},
diff --git a/src/Umbraco.Web.UI.Client/src/views/propertyeditors/listview/listview.controller.js b/src/Umbraco.Web.UI.Client/src/views/propertyeditors/listview/listview.controller.js
index 40ab5ce35f..f8887c6c44 100644
--- a/src/Umbraco.Web.UI.Client/src/views/propertyeditors/listview/listview.controller.js
+++ b/src/Umbraco.Web.UI.Client/src/views/propertyeditors/listview/listview.controller.js
@@ -1,4 +1,4 @@
-function listViewController($rootScope, $scope, $routeParams, $injector, $cookieStore, mediaTypeHelper, notificationsService, iconHelper, dialogService, editorState, localizationService, $location, appState, $timeout, $q, mediaResource, listViewHelper, userService, navigationService, treeService) {
+function listViewController($rootScope, $scope, $routeParams, $injector, $cookieStore, notificationsService, iconHelper, dialogService, editorState, localizationService, $location, appState, $timeout, $q, mediaResource, listViewHelper, userService, navigationService, treeService) {
//this is a quick check to see if we're in create mode, if so just exit - we cannot show children for content
// that isn't created yet, if we continue this will use the parent id in the route params which isn't what
@@ -53,7 +53,9 @@ function listViewController($rootScope, $scope, $routeParams, $injector, $cookie
$scope.isNew = false;
$scope.actionInProgress = false;
$scope.selection = [];
- $scope.folders = [];
+ $scope.folders = [];
+ //tracks if we've already loaded the folders for the current node
+ var foldersLoaded = false;
$scope.listViewResultSet = {
totalPages: 0,
items: []
@@ -261,25 +263,25 @@ function listViewController($rootScope, $scope, $routeParams, $injector, $cookie
$scope.actionInProgress = false;
$scope.listViewResultSet = data;
- //reset
- $scope.folders = [];
-
- //update all values for display
+ //update all values for display
if ($scope.listViewResultSet.items) {
_.each($scope.listViewResultSet.items, function (e, index) {
- setPropertyValues(e);
-
- //special case, we need to check if any of these types are folder types
- //and add them to the folders collection
- if ($scope.entityType === 'media') {
- if (mediaTypeHelper.isFolderType(e)) {
- $scope.folders.push(e);
- }
- }
+ setPropertyValues(e);
});
}
- $scope.viewLoaded = true;
+ if (!foldersLoaded && $scope.entityType === 'media') {
+ //The folders aren't loaded - we only need to do this once since we're never changing node ids
+ mediaResource.getChildFolders($scope.contentId)
+ .then(function (folders) {
+ $scope.folders = folders;
+ $scope.viewLoaded = true;
+ foldersLoaded = true;
+ });
+
+ } else {
+ $scope.viewLoaded = true;
+ }
//NOTE: This might occur if we are requesting a higher page number than what is actually available, for example
// if you have more than one page and you delete all items on the last page. In this case, we need to reset to the last
diff --git a/src/Umbraco.Web/Editors/MediaController.cs b/src/Umbraco.Web/Editors/MediaController.cs
index d00a26333e..2f3fe5bd94 100644
--- a/src/Umbraco.Web/Editors/MediaController.cs
+++ b/src/Umbraco.Web/Editors/MediaController.cs
@@ -167,18 +167,41 @@ namespace Umbraco.Web.Editors
[Obsolete("This is no longer used and shouldn't be because it performs poorly when there are a lot of media items")]
[FilterAllowedOutgoingMedia(typeof(IEnumerable>))]
public IEnumerable> GetChildFolders(int id = -1)
+ {
+ //we are only allowing a max of 500 to be returned here, if more is required it needs to be paged
+ var result = GetChildFolders(id, 1, 500);
+ return result.Items;
+ }
+
+ ///
+ /// Returns a paged result of media items known to be of a "Folder" type
+ ///
+ ///
+ ///
+ ///
+ ///
+ public PagedResult> GetChildFolders(int id, int pageNumber, int pageSize)
{
//Suggested convention for folder mediatypes - we can make this more or less complicated as long as we document it...
//if you create a media type, which has an alias that ends with ...Folder then its a folder: ex: "secureFolder", "bannerFolder", "Folder"
var folderTypes = Services.ContentTypeService
- .GetAllContentTypeAliases(Constants.ObjectTypes.MediaTypeGuid)
- .Where(x => x.EndsWith("Folder"));
-
- var children = (id < 0)
- ? Services.MediaService.GetRootMedia()
- : Services.MediaService.GetChildren(id);
+ .GetAllMediaTypes()
+ .Where(x => x.Alias.EndsWith("Folder"))
+ .Select(x => x.Id)
+ .ToArray();
- return children.Where(x => folderTypes.Contains(x.ContentType.Alias)).Select(Mapper.Map>);
+ if (folderTypes.Length == 0)
+ {
+ return new PagedResult>(0, pageNumber, pageSize);
+ }
+
+ long total;
+ var children = Services.MediaService.GetPagedChildren(id, pageNumber - 1, pageSize, out total, "Name", Direction.Ascending, true, null, folderTypes.ToArray());
+
+ return new PagedResult>(total, pageNumber, pageSize)
+ {
+ Items = children.Select(Mapper.Map>)
+ };
}
///