diff --git a/ccm-cms/src/main/java/com/arsdigita/cms/ui/folder/FolderBrowserController.java b/ccm-cms/src/main/java/com/arsdigita/cms/ui/folder/FolderBrowserController.java index 56dade1af..d22761ba6 100644 --- a/ccm-cms/src/main/java/com/arsdigita/cms/ui/folder/FolderBrowserController.java +++ b/ccm-cms/src/main/java/com/arsdigita/cms/ui/folder/FolderBrowserController.java @@ -670,13 +670,15 @@ public class FolderBrowserController { "No folder with ID %d found in database. " + "Where did that ID come form?", objectId))); - if (folder.getParentFolder() == null) { + final Optional parentFolder = folderManager.getParentFolder( + folder); + if (parentFolder.isPresent()) { return Optional.empty(); } else { return Optional.ofNullable(String.format( "%s%d", FOLDER_BROWSER_KEY_PREFIX_FOLDER, - folder.getParentFolder().getObjectId())); + parentFolder.get().getObjectId())); } } diff --git a/ccm-cms/src/main/java/com/arsdigita/cms/ui/folder/FolderManipulator.java b/ccm-cms/src/main/java/com/arsdigita/cms/ui/folder/FolderManipulator.java index 9bbda27fc..2380feb2c 100755 --- a/ccm-cms/src/main/java/com/arsdigita/cms/ui/folder/FolderManipulator.java +++ b/ccm-cms/src/main/java/com/arsdigita/cms/ui/folder/FolderManipulator.java @@ -73,6 +73,7 @@ import org.libreccm.categorization.Category; import org.libreccm.categorization.CategoryManager; import org.libreccm.cdi.utils.CdiUtil; import org.libreccm.core.CcmObject; +import org.libreccm.core.UnexpectedErrorException; import org.libreccm.security.PermissionChecker; import org.libreccm.security.Shiro; import org.librecms.CmsConstants; @@ -549,6 +550,8 @@ public class FolderManipulator extends SimpleContainer implements ContentItemManager.class); final FolderBrowserController controller = cdiUtil.findBean( FolderBrowserController.class); + final FolderManager folderManager = cdiUtil.findBean( + FolderManager.class); final PermissionChecker permissionChecker = cdiUtil.findBean( PermissionChecker.class); @@ -564,8 +567,44 @@ public class FolderManipulator extends SimpleContainer implements name = folder.getName(); //Check if folder or subfolder contains live items - if (isMove(state) && controller.hasLiveItems(folder)) { - addErrorMessage(data, "cms.ui.folder.item_is_live", name); + if (isMove(state)) { + final FolderManager.FolderIsMovable movable = folderManager + .folderIsMovable(folder, target); + switch (movable) { + case DIFFERENT_SECTIONS: + addErrorMessage(data, + "cms.ui.folder.different_sections", + name); + break; + case HAS_LIVE_ITEMS: + addErrorMessage(data, + "cms.ui.folder.item_is_live", + name); + break; + case DIFFERENT_TYPES: + addErrorMessage(data, + "cms.ui.folder.different_folder_types", + name); + break; + case IS_ROOT_FOLDER: + addErrorMessage(data, + "cms.ui.folder.is_root_folder", + name); + break; + case SAME_FOLDER: + addErrorMessage(data, + "cms.ui.folder.same_folder", + name); + break; + case YES: + //Nothing + break; + default: + throw new UnexpectedErrorException(String.format( + "Unknown state '%s' for '%s'.", + movable, + FolderManager.FolderIsMovable.class.getName())); + } } object = folder; diff --git a/ccm-cms/src/main/java/org/librecms/contentsection/Folder.java b/ccm-cms/src/main/java/org/librecms/contentsection/Folder.java index 0d81af839..7a1f35071 100644 --- a/ccm-cms/src/main/java/org/librecms/contentsection/Folder.java +++ b/ccm-cms/src/main/java/org/librecms/contentsection/Folder.java @@ -97,6 +97,14 @@ import static org.librecms.CmsConstants.*; // + "AND (LOWER(c.categorizedObject.displayName) LIKE :term " // + "OR LOWER(c.categorizedObject.name.value) LIKE :term)") // , + @NamedQuery( + name = "Folder.hasLiveItems", + query = "SELECT (CASE WHEN COUNT(i) > 0 THEN true ELSE false END) " + + "FROM ContentItem i JOIN i.categories c " + + "WHERE c.category = :folder " + + "AND i.version = org.librecms.contentsection.ContentItemVersion.LIVE" + ) + , @NamedQuery( name = "Folder.findObjects", query = "SELECT o FROM CcmObject o " @@ -109,8 +117,8 @@ import static org.librecms.CmsConstants.*; + "AND i.version = " + "org.librecms.contentsection.ContentItemVersion.DRAFT " + "AND (LOWER(i.displayName) LIKE LOWER(:term) " -// + "OR LOWER(i.name.values) LIKE LOWER(:term)" - + ")) " + // + "OR LOWER(i.name.values) LIKE LOWER(:term)" + + ")) " + "ORDER BY o.displayName" // query = "SELECT o FROM CcmObject o " // + "WHERE o IN (SELECT f FROM Folder f " @@ -140,8 +148,8 @@ import static org.librecms.CmsConstants.*; + "AND i.version = " + "org.librecms.contentsection.ContentItemVersion.DRAFT " + "AND (LOWER(i.displayName) LIKE LOWER(:term) " -// + "OR LOWER(i.name.values) LIKE LOWER(:term)" - + "))" + // + "OR LOWER(i.name.values) LIKE LOWER(:term)" + + "))" // query = "SELECT COUNT(o) FROM CcmObject o " // + "WHERE o IN (SELECT f FROM Folder f " // + "WHERE f.parentCategory = :parent " @@ -193,7 +201,7 @@ public class Folder extends Category implements Serializable { public Folder getParentFolder() { return (Folder) getParentCategory(); } - + /** * A convenient method for getting all sub folders of folder. * diff --git a/ccm-cms/src/main/java/org/librecms/contentsection/FolderManager.java b/ccm-cms/src/main/java/org/librecms/contentsection/FolderManager.java index c1df6d48e..395a21e7d 100644 --- a/ccm-cms/src/main/java/org/librecms/contentsection/FolderManager.java +++ b/ccm-cms/src/main/java/org/librecms/contentsection/FolderManager.java @@ -34,6 +34,9 @@ import java.util.stream.Collectors; import javax.enterprise.context.RequestScoped; import javax.inject.Inject; +import javax.persistence.EntityManager; +import javax.persistence.NoResultException; +import javax.persistence.TypedQuery; import javax.transaction.Transactional; /** @@ -43,16 +46,19 @@ import javax.transaction.Transactional; */ @RequestScoped public class FolderManager { - + + @Inject + private EntityManager entityManager; + @Inject private ConfigurationManager confManager; - + @Inject private FolderRepository folderRepo; - + @Inject private CategoryManager categoryManager; - + @Inject private ContentItemManager itemManager; @@ -110,22 +116,33 @@ public class FolderManager { */ HAS_LIVE_ITEMS } - + @Transactional(Transactional.TxType.REQUIRED) public Optional getParentFolder(final Folder folder) { - Objects.requireNonNull(folder); - final Optional theFolder = folderRepo.findById(folder. - getObjectId()); - if (!theFolder.isPresent()) { - throw new UnexpectedErrorException(String.format( - "The folder %s should be in the database but is not.", - Objects.toString(folder))); - } - final Category parentCategory = theFolder.get().getParentCategory(); - if (parentCategory == null) { - return Optional.empty(); - } else { +// Objects.requireNonNull(folder); +// final Optional theFolder = folderRepo.findById(folder. +// getObjectId()); +// if (!theFolder.isPresent()) { +// throw new UnexpectedErrorException(String.format( +// "The folder %s should be in the database but is not.", +// Objects.toString(folder))); +// } +// final Category parentCategory = theFolder.get().getParentCategory(); +// if (parentCategory == null) { +// return Optional.empty(); +// } else { +// return folderRepo.findById(parentCategory.getObjectId()); +// } + + final TypedQuery query = entityManager.createNamedQuery( + "Category.findParentCategory", Category.class); + query.setParameter("category", folder); + + try { + final Category parentCategory = query.getSingleResult(); return folderRepo.findById(parentCategory.getObjectId()); + } catch (NoResultException ex) { + return Optional.empty(); } } @@ -134,7 +151,7 @@ public class FolderManager { * and the content section to which the folder belongs are the same as for * the provided parent folder. * - * @param name The name of the new folder. + * @param name The name of the new folder. * @param parent The folder in which the new folder is generated. * * @return The new folder. @@ -143,17 +160,17 @@ public class FolderManager { public Folder createFolder(final String name, final Folder parent) { if (parent == null) { throw new IllegalArgumentException( - "Can't create a folder without a parent folder."); + "Can't create a folder without a parent folder."); } - + if (name == null || name.trim().isEmpty()) { throw new IllegalArgumentException( - "Can't create a folder with an empty name"); + "Can't create a folder with an empty name"); } - + final KernelConfig kernelConfig = confManager.findConfiguration( - KernelConfig.class); - + KernelConfig.class); + final Folder folder = new Folder(); folder.setName(name); folder.setDisplayName(name); @@ -161,30 +178,30 @@ public class FolderManager { folder.setSection(parent.getSection()); folder.setType(parent.getType()); folderRepo.save(folder); - + categoryManager.addSubCategoryToCategory(folder, parent); - + return folder; } - + public FolderIsDeletable folderIsDeletable(final Folder folder) { if (folder == null) { throw new IllegalArgumentException( - "Can't check if null is deletable."); + "Can't check if null is deletable."); } - + if (!folder.getSubCategories().isEmpty()) { return FolderIsDeletable.HAS_SUBCATEGORIES; } - + if (!folder.getObjects().isEmpty()) { return FolderIsDeletable.IS_NOT_EMPTY; } - + if (!getParentFolder(folder).isPresent()) { return FolderIsDeletable.IS_ROOT_FOLDER; } - + return FolderIsDeletable.YES; } @@ -198,7 +215,7 @@ public class FolderManager { if (folder == null) { throw new IllegalArgumentException("Can't delete folder null"); } - + final FolderIsDeletable status = folderIsDeletable(folder); switch (status) { case YES: @@ -206,20 +223,20 @@ public class FolderManager { break; case HAS_SUBCATEGORIES: throw new IllegalArgumentException(String.format( - "Can't delete folder \"%s\" because the folder is not empty", - getFolderPath(folder, true))); + "Can't delete folder \"%s\" because the folder is not empty", + getFolderPath(folder, true))); case IS_NOT_EMPTY: throw new IllegalArgumentException(String.format( - "Can't delete folder \"%s\" because the folder is not empty.", - getFolderPath(folder))); + "Can't delete folder \"%s\" because the folder is not empty.", + getFolderPath(folder))); case IS_ROOT_FOLDER: throw new IllegalArgumentException( - "The folder to delete is a root folder can can't be deleted."); + "The folder to delete is a root folder can can't be deleted."); default: throw new IllegalArgumentException(String.format( - "Unexpected return value from #folderIsDeletable: " - + "\"%s\".", - status.toString())); + "Unexpected return value from #folderIsDeletable: " + + "\"%s\".", + status.toString())); } } @@ -234,176 +251,140 @@ public class FolderManager { */ @Transactional(Transactional.TxType.REQUIRED) public void moveFolder(final Folder folder, final Folder target) { - + Objects.requireNonNull(folder, "Can't move folder null"); Objects.requireNonNull(target, "Can't move a folder to folder null"); - - final FolderIsMovable status = folderIsMovable(folder, target); + + final Folder movingFolder = folderRepo.findById(folder.getObjectId()) + .orElseThrow(() -> new IllegalArgumentException(String.format( + "No folder with ID %d in the database. Where did that ID come from?", + folder.getObjectId()))); + final Folder targetFolder = folderRepo.findById(target.getObjectId()) + .orElseThrow(() -> new IllegalArgumentException(String.format( + "No folder with ID %d in the database. Where did that ID come from?", + target.getObjectId()))); + + final FolderIsMovable status = folderIsMovable(movingFolder, + targetFolder); switch (status) { case YES: { - final Folder source = getParentFolder(folder).get(); - categoryManager.removeSubCategoryFromCategory(folder, source); - final boolean sameName = target.getSubCategories() - .stream() - .anyMatch(subCategory -> folder.getName().equals( - subCategory.getName())); + final Folder source = getParentFolder(movingFolder).get(); + categoryManager.removeSubCategoryFromCategory(movingFolder, + source); + final boolean sameName = targetFolder.getSubCategories() + .stream() + .anyMatch(subCategory -> movingFolder.getName().equals( + subCategory.getName())); if (sameName) { - final String name = String.format("%s_1", folder.getName()); - folder.setName(name); - folder.setDisplayName(name); - + final String name = String.format("%s_1", movingFolder + .getName()); + movingFolder.setName(name); + movingFolder.setDisplayName(name); + final KernelConfig kernelConfig = confManager. - findConfiguration( - KernelConfig.class); - folder.getTitle().addValue(kernelConfig.getDefaultLocale(), - name); + findConfiguration( + KernelConfig.class); + movingFolder.getTitle().addValue( + kernelConfig.getDefaultLocale(), name); } - categoryManager.addSubCategoryToCategory(folder, target); + categoryManager.addSubCategoryToCategory(movingFolder, + targetFolder); break; } case IS_ROOT_FOLDER: throw new IllegalArgumentException(String.format( - "The folder \"%s\" to move is a root folder can can't " - + "be moved.", - getFolderPath(folder))); + "The movingFolder \"%s\" to move is a root movingFolder can can't " + + "be moved.", + getFolderPath(movingFolder))); case SAME_FOLDER: throw new IllegalArgumentException( - "The folder to move and the target folder are the same " - + "folder."); + "The movingFolder to move and the targetFolder movingFolder are the same " + + "movingFolder."); case DIFFERENT_SECTIONS: throw new IllegalArgumentException(String.format( - "Folders can't be moved between content section. The " - + "folder \"%s\" to move belongs to section " - + "\"%s\", the target folder \"%s\" belongs to " - + "section \"%s\".", - getFolderPath(folder), - folder.getSection().getDisplayName(), - getFolderPath(target), - target.getSection().getDisplayName())); + "Folders can't be moved between content section. The " + + "movingFolder \"%s\" to move belongs to section " + + "\"%s\", the targetFolder movingFolder \"%s\" belongs to " + + "section \"%s\".", + getFolderPath(movingFolder), + movingFolder.getSection().getDisplayName(), + getFolderPath(targetFolder), + targetFolder.getSection().getDisplayName())); case DIFFERENT_TYPES: throw new IllegalArgumentException( - "The folder to move is a \"%s\"," - + "but the target folder is a \"%s\" folder."); + "The movingFolder to move is a \"%s\"," + + "but the targetFolder movingFolder is a \"%s\" movingFolder."); case HAS_LIVE_ITEMS: throw new IllegalArgumentException(String.format( - "Can't move folder \"%s\" because some items in the " - + "folder or its sub folder are live.", - getFolderPath(folder, true))); + "Can't move movingFolder \"%s\" because some items in the " + + "movingFolder or its sub movingFolder are live.", + getFolderPath(movingFolder, true))); default: throw new IllegalArgumentException(String.format( - "Unexpected return value from #folderIsMovable: %s", - status.toString())); + "Unexpected return value from #movingFolderIsMovable: %s", + status.toString())); } - -// if (folder.getParentFolder() -// == null) { -// throw new IllegalArgumentException(String.format( -// "The folder \"%s\" to move is a root folder can can't be moved.", -// getFolderPath(folder))); -// } -// -// if (folder.equals(target)) { -// throw new IllegalArgumentException( -// "The folder to move and the target folder are the same folder."); -// } -// -// if (!folder.getSection() -// .equals(target.getSection())) { -// throw new IllegalArgumentException(String.format( -// "Folders can't be moved between content section. The " -// + "folder \"%s\" to move belongs to section \"%s\", " -// + "the target folder \"%s\" belongs to section \"%s\".", -// getFolderPath(folder), -// folder.getSection().getDisplayName(), -// getFolderPath(target), -// target.getSection().getDisplayName())); -// } -// -// if (folder.getType() -// != target.getType()) { -// throw new IllegalArgumentException("The folder to move is a \"%s\"," -// + "but the target folder is a \"%s\" folder."); -// } -// -// if (liveItemsInFolder(folder)) { -// throw new IllegalArgumentException(String.format( -// "Can't move folder \"%s\" because some items in the folder or" -// + "its sub folder are live.", -// getFolderPath(folder, true))); -// } -// -// final Folder source = folder.getParentFolder(); -// -// categoryManager.removeSubCategoryFromCategory(folder, source); -// final boolean sameName = target.getSubCategories() -// .stream() -// .anyMatch(subCategory -> folder.getName().equals(subCategory -// .getName())); -// if (sameName) { -// final String name = String.format("%s_1", folder.getName()); -// folder.setName(name); -// folder.setDisplayName(name); -// -// final KernelConfig kernelConfig = confManager.findConfiguration( -// KernelConfig.class); -// folder.getTitle().addValue(kernelConfig.getDefaultLocale(), name); -// } -// -// categoryManager.addSubCategoryToCategory(folder, target); } - + + @Transactional(Transactional.TxType.REQUIRED) public FolderIsMovable folderIsMovable(final Folder folder, final Folder target) { - if (folder == null) { - throw new IllegalArgumentException("Can't check if null is movable."); - } - - if (target == null) { - throw new IllegalArgumentException( - "Can't check if a server can be moved to null."); - } - - if (!getParentFolder(folder).isPresent()) { + + Objects.requireNonNull(folder, + "Can't check if null is movable."); + Objects.requireNonNull(target, + "Can't check if a server can be moved to null."); + + final Folder movingFolder = folderRepo.findById(folder.getObjectId()) + .orElseThrow(() -> new IllegalArgumentException(String.format( + "No folder with ID %d in the datbase. Where did that ID come from?", + folder.getObjectId()))); + final Folder targetFolder = folderRepo.findById(target.getObjectId()) + .orElseThrow(() -> new IllegalArgumentException(String.format( + "No folder with ID %d in the datbase. Where did that ID come from?", + target.getObjectId()))); + + if (!getParentFolder(movingFolder).isPresent()) { return FolderIsMovable.IS_ROOT_FOLDER; } - - if (folder.equals(target)) { + + if (movingFolder.equals(targetFolder)) { return FolderIsMovable.SAME_FOLDER; } - - if (!folder.getSection().equals(target.getSection())) { + + if (!movingFolder.getSection().equals(targetFolder.getSection())) { return FolderIsMovable.DIFFERENT_SECTIONS; } - - if (folder.getType() != target.getType()) { + + if (movingFolder.getType() != targetFolder.getType()) { return FolderIsMovable.DIFFERENT_TYPES; } - - if (liveItemsInFolder(folder)) { + + if (liveItemsInFolder(movingFolder)) { return FolderIsMovable.HAS_LIVE_ITEMS; } - + return FolderIsMovable.YES; } - + @Transactional(Transactional.TxType.REQUIRED) public void copyFolder(final Folder folder, final Folder target) { - + Objects.requireNonNull(folder, "Can't move null to a folder."); Objects.requireNonNull(target, "Can't move a folder to null."); - + final Folder copy = createFolder(folder.getName(), target); final List items = folder.getObjects() - .stream() - .map(categorization -> categorization.getCategorizedObject()) - .filter(object -> object instanceof ContentItem) - .map(object -> (ContentItem) object) - .collect(Collectors.toList()); + .stream() + .map(categorization -> categorization.getCategorizedObject()) + .filter(object -> object instanceof ContentItem) + .map(object -> (ContentItem) object) + .collect(Collectors.toList()); for (final ContentItem item : items) { itemManager.copy(item, target); } - - for(final Folder subFolder : folder.getSubFolders()) { + + for (final Folder subFolder : folder.getSubFolders()) { copyFolder(subFolder, copy); } } @@ -415,20 +396,24 @@ public class FolderManager { * @param folder The folder to check for live items. * * @return {@code true} if there any live items in the folder or its sub - * folders, {@code false} if not. + * folders, {@code false} if not. */ private boolean liveItemsInFolder(final Folder folder) { - final boolean liveItemsInFolder = folder.getObjects() - .stream() - .map(categorization -> categorization.getCategorizedObject()) - .filter(object -> object instanceof ContentItem) - .map(object -> (ContentItem) object) - .anyMatch(item -> itemManager.isLive(item)); - +// final boolean liveItemsInFolder = folder.getObjects() +// .stream() +// .map(categorization -> categorization.getCategorizedObject()) +// .filter(object -> object instanceof ContentItem) +// .map(object -> (ContentItem) object) +// .anyMatch(item -> itemManager.isLive(item)); + final TypedQuery query = entityManager.createNamedQuery( + "Folder.hasLiveItems", Boolean.class); + query.setParameter("folder", folder); + final boolean liveItemsInFolder = query.getSingleResult(); + final boolean liveItemsInSubFolders = folder.getSubFolders() - .stream() - .anyMatch(subFolder -> liveItemsInFolder(subFolder)); - + .stream() + .anyMatch(subFolder -> liveItemsInFolder(subFolder)); + return liveItemsInFolder || liveItemsInSubFolders; } @@ -438,7 +423,7 @@ public class FolderManager { * @param folder The folder. * * @return The path of the folder as a UNIX-like path, but without the - * content section as prefix. + * content section as prefix. */ public String getFolderPath(final Folder folder) { return getFolderPath(folder, false); @@ -447,31 +432,31 @@ public class FolderManager { /** * Returns the path of folder. * - * @param folder The folder. + * @param folder The folder. * @param withContentSection Whether to include the content section in the - * path. + * path. * * @return The path of the folder as a UNIX-like path, optionally with the - * content section the folder belongs to as prefix.. + * content section the folder belongs to as prefix.. */ public String getFolderPath(final Folder folder, final boolean withContentSection) { if (folder == null) { throw new IllegalArgumentException("Can't generate a path for null."); } - + final List tokens = new ArrayList<>(); - + tokens.add(folder.getName()); Folder current = folder; while (getParentFolder(current).isPresent()) { current = getParentFolder(current).get(); tokens.add(current.getName()); } - + Collections.reverse(tokens); final String path = String.join("/", tokens); - + if (withContentSection) { final String sectionName = folder.getSection().getDisplayName(); return String.format("%s:/%s/", sectionName, path); @@ -489,12 +474,12 @@ public class FolderManager { */ @Transactional(Transactional.TxType.REQUIRED) public List getParentFolders(final Folder folder) { - + if (folder == null) { throw new IllegalArgumentException( - "Can't create a list of parent folder for folder null."); + "Can't create a list of parent folder for folder null."); } - + final List folders = new ArrayList<>(); if (getParentFolder(folder).isPresent()) { Optional currentFolder = getParentFolder(folder); @@ -503,9 +488,9 @@ public class FolderManager { currentFolder = getParentFolder(currentFolder.get()); } } - + Collections.reverse(folders); return folders; } - + } diff --git a/ccm-cms/src/main/resources/com/arsdigita/cms/ui/folder/CMSFolderResources.properties b/ccm-cms/src/main/resources/com/arsdigita/cms/ui/folder/CMSFolderResources.properties index 3889c119a..db6305e2a 100755 --- a/ccm-cms/src/main/resources/com/arsdigita/cms/ui/folder/CMSFolderResources.properties +++ b/ccm-cms/src/main/resources/com/arsdigita/cms/ui/folder/CMSFolderResources.properties @@ -77,3 +77,4 @@ cms.ui.folder.move.action=Move cms.ui.folder.copy.action=Copy cms.ui.folder.publish.action=(Re-)publish cms.ui.folder.unpublish.action=Unpublish +cms.ui.folder.same_folder=Folders are equal diff --git a/ccm-cms/src/main/resources/com/arsdigita/cms/ui/folder/CMSFolderResources_de.properties b/ccm-cms/src/main/resources/com/arsdigita/cms/ui/folder/CMSFolderResources_de.properties index 28ee56db9..ef78b895f 100755 --- a/ccm-cms/src/main/resources/com/arsdigita/cms/ui/folder/CMSFolderResources_de.properties +++ b/ccm-cms/src/main/resources/com/arsdigita/cms/ui/folder/CMSFolderResources_de.properties @@ -77,3 +77,4 @@ cms.ui.folder.move.action=Verschieben cms.ui.folder.copy.action=Kopieren cms.ui.folder.publish.action=(Re-)Publizieren cms.ui.folder.unpublish.action=Depublizieren +cms.ui.folder.same_folder=Folders are equal diff --git a/ccm-cms/src/main/resources/com/arsdigita/cms/ui/folder/CMSFolderResources_fr.properties b/ccm-cms/src/main/resources/com/arsdigita/cms/ui/folder/CMSFolderResources_fr.properties index 094cf3b85..a47657bbc 100755 --- a/ccm-cms/src/main/resources/com/arsdigita/cms/ui/folder/CMSFolderResources_fr.properties +++ b/ccm-cms/src/main/resources/com/arsdigita/cms/ui/folder/CMSFolderResources_fr.properties @@ -72,3 +72,4 @@ cms.ui.folder.move.action= cms.ui.folder.copy.action= cms.ui.folder.publish.action= cms.ui.folder.unpublish.action= +cms.ui.folder.same_folder=Der als Ziel gew\u00e4hlte Ordner ist der gleiche Ordner wie der zu verschiebene Ordner. diff --git a/ccm-core/src/main/java/org/libreccm/categorization/Category.java b/ccm-core/src/main/java/org/libreccm/categorization/Category.java index f9f7f8c4a..e5a659ffa 100644 --- a/ccm-core/src/main/java/org/libreccm/categorization/Category.java +++ b/ccm-core/src/main/java/org/libreccm/categorization/Category.java @@ -79,6 +79,10 @@ import javax.xml.bind.annotation.XmlRootElement; name = "Category.findByName", query = "SELECT c FROM Category c WHERE c.name = :name") , + @NamedQuery( + name = "Category.findParentCategory", + query = "SELECT c.parentCategory FROM Category c WHERE c = :category") + , @NamedQuery( name = "Category.countAssignedCategories", query = "SELECT COUNT(c) FROM Categorization c "