CCM NG/ccm-cms: Finding invalid targets for copying/moving items/folders.
git-svn-id: https://svn.libreccm.org/ccm/ccm_ng@4612 8810af33-2d31-482b-a856-94f89814c4dfpull/2/head
parent
d5a0f86a8f
commit
a24ff55996
|
|
@ -43,6 +43,7 @@ import java.util.Collections;
|
||||||
import java.util.List;
|
import java.util.List;
|
||||||
import java.util.Locale;
|
import java.util.Locale;
|
||||||
import java.util.Objects;
|
import java.util.Objects;
|
||||||
|
import java.util.Optional;
|
||||||
|
|
||||||
import java.util.stream.Collectors;
|
import java.util.stream.Collectors;
|
||||||
|
|
||||||
|
|
@ -60,6 +61,8 @@ import javax.persistence.TypedQuery;
|
||||||
import javax.persistence.criteria.Order;
|
import javax.persistence.criteria.Order;
|
||||||
import javax.persistence.criteria.Path;
|
import javax.persistence.criteria.Path;
|
||||||
|
|
||||||
|
import static org.librecms.CmsConstants.*;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* The {@code FolderBrowserController} wraps all database operations (queries)
|
* The {@code FolderBrowserController} wraps all database operations (queries)
|
||||||
* required by the {@link FolderBrowser}, the
|
* required by the {@link FolderBrowser}, the
|
||||||
|
|
@ -112,7 +115,7 @@ public class FolderBrowserController {
|
||||||
@PostConstruct
|
@PostConstruct
|
||||||
private void init() {
|
private void init() {
|
||||||
final KernelConfig kernelConfig = confManager.findConfiguration(
|
final KernelConfig kernelConfig = confManager.findConfiguration(
|
||||||
KernelConfig.class);
|
KernelConfig.class);
|
||||||
defaultLocale = kernelConfig.getDefaultLocale();
|
defaultLocale = kernelConfig.getDefaultLocale();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
@ -122,7 +125,7 @@ public class FolderBrowserController {
|
||||||
* @param folder The folder.
|
* @param folder The folder.
|
||||||
*
|
*
|
||||||
* @return The number of objects (subfolders and content items) in the
|
* @return The number of objects (subfolders and content items) in the
|
||||||
* provided {@code folder}.
|
* provided {@code folder}.
|
||||||
*/
|
*/
|
||||||
public long countObjects(final Folder folder) {
|
public long countObjects(final Folder folder) {
|
||||||
return countObjects(folder, "%");
|
return countObjects(folder, "%");
|
||||||
|
|
@ -132,12 +135,11 @@ public class FolderBrowserController {
|
||||||
* Count all objects (subfolders and content items) in the provided folder
|
* Count all objects (subfolders and content items) in the provided folder
|
||||||
* which match the provided filter term.
|
* which match the provided filter term.
|
||||||
*
|
*
|
||||||
* @param folder The folder.
|
* @param folder The folder.
|
||||||
* @param filterTerm The filter term.
|
* @param filterTerm The filter term.
|
||||||
*
|
*
|
||||||
* @return The number of objects (subfolders and content items) in the
|
* @return The number of objects (subfolders and content items) in the
|
||||||
* provided {@code folder} which match the provided
|
* provided {@code folder} which match the provided {@code filterTerm}.
|
||||||
* {@code filterTerm}.
|
|
||||||
*/
|
*/
|
||||||
public long countObjects(final Folder folder,
|
public long countObjects(final Folder folder,
|
||||||
final String filterTerm) {
|
final String filterTerm) {
|
||||||
|
|
@ -171,8 +173,8 @@ public class FolderBrowserController {
|
||||||
criteriaQuery = criteriaQuery.where(from.in(subFolders));
|
criteriaQuery = criteriaQuery.where(from.in(subFolders));
|
||||||
} else {
|
} else {
|
||||||
criteriaQuery = criteriaQuery.where(builder.or(
|
criteriaQuery = criteriaQuery.where(builder.or(
|
||||||
from.in(subFolders),
|
from.in(subFolders),
|
||||||
from.in(items)));
|
from.in(items)));
|
||||||
}
|
}
|
||||||
|
|
||||||
return entityManager.createQuery(criteriaQuery).getSingleResult();
|
return entityManager.createQuery(criteriaQuery).getSingleResult();
|
||||||
|
|
@ -182,13 +184,13 @@ public class FolderBrowserController {
|
||||||
* Create {@link FolderBrowserTableRow} objects for all objects in the
|
* Create {@link FolderBrowserTableRow} objects for all objects in the
|
||||||
* provided folder.
|
* provided folder.
|
||||||
*
|
*
|
||||||
* @param folder The folder which contains the objects.
|
* @param folder The folder which contains the objects.
|
||||||
* @param orderBy The field used to order the objects.
|
* @param orderBy The field used to order the objects.
|
||||||
* @param orderDirection The direction for ordering the objects.
|
* @param orderDirection The direction for ordering the objects.
|
||||||
*
|
*
|
||||||
* @return A list with {@link FolderBrowserTableRow} objects for each object
|
* @return A list with {@link FolderBrowserTableRow} objects for each object
|
||||||
* in the provided {@code folder} ordered by the provided field and
|
* in the provided {@code folder} ordered by the provided field and in the
|
||||||
* in the provided direction.
|
* provided direction.
|
||||||
*/
|
*/
|
||||||
@Transactional(Transactional.TxType.REQUIRED)
|
@Transactional(Transactional.TxType.REQUIRED)
|
||||||
List<FolderBrowserTableRow> getObjectRows(final Folder folder,
|
List<FolderBrowserTableRow> getObjectRows(final Folder folder,
|
||||||
|
|
@ -201,15 +203,15 @@ public class FolderBrowserController {
|
||||||
* Create {@link FolderBrowserTableRow} objects for all objects in the
|
* Create {@link FolderBrowserTableRow} objects for all objects in the
|
||||||
* provided folder which match provided filter term.
|
* provided folder which match provided filter term.
|
||||||
*
|
*
|
||||||
* @param folder The folder which contains the objects.
|
* @param folder The folder which contains the objects.
|
||||||
* @param filterTerm The filter term.
|
* @param filterTerm The filter term.
|
||||||
* @param orderBy The field used to order the objects.
|
* @param orderBy The field used to order the objects.
|
||||||
* @param orderDirection The direction for ordering the objects.
|
* @param orderDirection The direction for ordering the objects.
|
||||||
*
|
*
|
||||||
* @return A list with {@link FolderBrowserTableRow} objects for each object
|
* @return A list with {@link FolderBrowserTableRow} objects for each object
|
||||||
* in the provided {@code folder} which matches the provided
|
* in the provided {@code folder} which matches the provided
|
||||||
* {@code filterTerm}, ordered by the provided field and in the
|
* {@code filterTerm}, ordered by the provided field and in the provided
|
||||||
* provided direction.
|
* direction.
|
||||||
*/
|
*/
|
||||||
@Transactional(Transactional.TxType.REQUIRED)
|
@Transactional(Transactional.TxType.REQUIRED)
|
||||||
List<FolderBrowserTableRow> getObjectRows(final Folder folder,
|
List<FolderBrowserTableRow> getObjectRows(final Folder folder,
|
||||||
|
|
@ -229,17 +231,17 @@ public class FolderBrowserController {
|
||||||
* provided folder which are in the range provided by {@code firstResult}
|
* provided folder which are in the range provided by {@code firstResult}
|
||||||
* and {@code maxResult}
|
* and {@code maxResult}
|
||||||
*
|
*
|
||||||
* @param folder The folder which contains the objects.
|
* @param folder The folder which contains the objects.
|
||||||
* @param orderBy The field used to order the objects.
|
* @param orderBy The field used to order the objects.
|
||||||
* @param orderDirection The direction for ordering the objects.
|
* @param orderDirection The direction for ordering the objects.
|
||||||
* @param firstResult The index of the first object to use.
|
* @param firstResult The index of the first object to use.
|
||||||
* @param maxResults The maximum number of objects to retrieve.
|
* @param maxResults The maximum number of objects to retrieve.
|
||||||
*
|
*
|
||||||
* @return A list with {@link FolderBrowserTableRow} objects for each object
|
* @return A list with {@link FolderBrowserTableRow} objects for each object
|
||||||
* in the provided {@code folder} ordered by the provided field and
|
* in the provided {@code folder} ordered by the provided field and in the
|
||||||
* in the provided direction. The list will start with the object
|
* provided direction. The list will start with the object with index
|
||||||
* with index provided as {@code firstResult} and contain at most
|
* provided as {@code firstResult} and contain at most {@code maxResults}
|
||||||
* {@code maxResults} items.
|
* items.
|
||||||
*/
|
*/
|
||||||
@Transactional(Transactional.TxType.REQUIRED)
|
@Transactional(Transactional.TxType.REQUIRED)
|
||||||
List<FolderBrowserTableRow> getObjectRows(final Folder folder,
|
List<FolderBrowserTableRow> getObjectRows(final Folder folder,
|
||||||
|
|
@ -260,19 +262,18 @@ public class FolderBrowserController {
|
||||||
* provided folder which match the provided filter term and which are in the
|
* provided folder which match the provided filter term and which are in the
|
||||||
* range provided by {@code firstResult} and {@code maxResult}
|
* range provided by {@code firstResult} and {@code maxResult}
|
||||||
*
|
*
|
||||||
* @param folder The folder which contains the objects.
|
* @param folder The folder which contains the objects.
|
||||||
* @param filterTerm The filter term.
|
* @param filterTerm The filter term.
|
||||||
* @param orderBy The field used to order the objects.
|
* @param orderBy The field used to order the objects.
|
||||||
* @param orderDirection The direction for ordering the objects.
|
* @param orderDirection The direction for ordering the objects.
|
||||||
* @param firstResult The index of the first object to use.
|
* @param firstResult The index of the first object to use.
|
||||||
* @param maxResults The maximum number of objects to retrieve.
|
* @param maxResults The maximum number of objects to retrieve.
|
||||||
*
|
*
|
||||||
* @return A list with {@link FolderBrowserTableRow} objects for each object
|
* @return A list with {@link FolderBrowserTableRow} objects for each object
|
||||||
* in the provided {@code folder} which matches the provided
|
* in the provided {@code folder} which matches the provided
|
||||||
* {@code filterTerm}, ordered by the provided field and in the
|
* {@code filterTerm}, ordered by the provided field and in the provided
|
||||||
* provided direction. The list will start with the object with
|
* direction. The list will start with the object with index provided as
|
||||||
* index provided as {@code firstResult} and contain at most
|
* {@code firstResult} and contain at most {@code maxResults} items.
|
||||||
* {@code maxResults} items.
|
|
||||||
*/
|
*/
|
||||||
@Transactional(Transactional.TxType.REQUIRED)
|
@Transactional(Transactional.TxType.REQUIRED)
|
||||||
List<FolderBrowserTableRow> getObjectRows(final Folder folder,
|
List<FolderBrowserTableRow> getObjectRows(final Folder folder,
|
||||||
|
|
@ -288,8 +289,8 @@ public class FolderBrowserController {
|
||||||
firstResult,
|
firstResult,
|
||||||
maxResults);
|
maxResults);
|
||||||
final List<FolderBrowserTableRow> subFolderRows = subFolders.stream()
|
final List<FolderBrowserTableRow> subFolderRows = subFolders.stream()
|
||||||
.map(subFolder -> buildRow(subFolder))
|
.map(subFolder -> buildRow(subFolder))
|
||||||
.collect(Collectors.toList());
|
.collect(Collectors.toList());
|
||||||
|
|
||||||
if (subFolders.size() > maxResults) {
|
if (subFolders.size() > maxResults) {
|
||||||
return subFolderRows;
|
return subFolderRows;
|
||||||
|
|
@ -304,8 +305,8 @@ public class FolderBrowserController {
|
||||||
firstItem,
|
firstItem,
|
||||||
maxItems);
|
maxItems);
|
||||||
final List<FolderBrowserTableRow> itemRows = items.stream()
|
final List<FolderBrowserTableRow> itemRows = items.stream()
|
||||||
.map(item -> buildRow(item))
|
.map(item -> buildRow(item))
|
||||||
.collect(Collectors.toList());
|
.collect(Collectors.toList());
|
||||||
|
|
||||||
final ArrayList<FolderBrowserTableRow> rows = new ArrayList<>();
|
final ArrayList<FolderBrowserTableRow> rows = new ArrayList<>();
|
||||||
rows.addAll(subFolderRows);
|
rows.addAll(subFolderRows);
|
||||||
|
|
@ -320,10 +321,10 @@ public class FolderBrowserController {
|
||||||
* {@link Folder}.
|
* {@link Folder}.
|
||||||
*
|
*
|
||||||
* @param folder The {@link Folder} to use for building the
|
* @param folder The {@link Folder} to use for building the
|
||||||
* {@link FolderBrowserTableRow}.
|
* {@link FolderBrowserTableRow}.
|
||||||
*
|
*
|
||||||
* @return A {@link FolderBrowserTableRow} containing the data needed by the
|
* @return A {@link FolderBrowserTableRow} containing the data needed by the
|
||||||
* {@link FolderBrowser} to display the provided {@code folder}.
|
* {@link FolderBrowser} to display the provided {@code folder}.
|
||||||
*/
|
*/
|
||||||
private FolderBrowserTableRow buildRow(final Folder folder) {
|
private FolderBrowserTableRow buildRow(final Folder folder) {
|
||||||
|
|
||||||
|
|
@ -334,15 +335,15 @@ public class FolderBrowserController {
|
||||||
row.setName(folder.getName());
|
row.setName(folder.getName());
|
||||||
row.setLanguages(Collections.emptyList());
|
row.setLanguages(Collections.emptyList());
|
||||||
if (folder.getTitle().hasValue(globalizationHelper
|
if (folder.getTitle().hasValue(globalizationHelper
|
||||||
.getNegotiatedLocale())) {
|
.getNegotiatedLocale())) {
|
||||||
row.setTitle(folder.getTitle().getValue(globalizationHelper
|
row.setTitle(folder.getTitle().getValue(globalizationHelper
|
||||||
.getNegotiatedLocale()));
|
.getNegotiatedLocale()));
|
||||||
} else {
|
} else {
|
||||||
row.setTitle(folder.getTitle().getValue(defaultLocale));
|
row.setTitle(folder.getTitle().getValue(defaultLocale));
|
||||||
}
|
}
|
||||||
row.setFolder(true);
|
row.setFolder(true);
|
||||||
row.setDeletable(!categoryManager.hasSubCategories(folder)
|
row.setDeletable(!categoryManager.hasSubCategories(folder)
|
||||||
&& !categoryManager.hasObjects(folder));
|
&& !categoryManager.hasObjects(folder));
|
||||||
|
|
||||||
return row;
|
return row;
|
||||||
}
|
}
|
||||||
|
|
@ -352,10 +353,10 @@ public class FolderBrowserController {
|
||||||
* {@link ContentItem}.
|
* {@link ContentItem}.
|
||||||
*
|
*
|
||||||
* @param item The {@link ContentItem} to use for building the
|
* @param item The {@link ContentItem} to use for building the
|
||||||
* {@link FolderBrowserTableRow}.
|
* {@link FolderBrowserTableRow}.
|
||||||
*
|
*
|
||||||
* @return A {@link FolderBrowserTableRow} containing the data needed by the
|
* @return A {@link FolderBrowserTableRow} containing the data needed by the
|
||||||
* {@link FolderBrowser} to display the provided {@code item}.
|
* {@link FolderBrowser} to display the provided {@code item}.
|
||||||
*/
|
*/
|
||||||
private FolderBrowserTableRow buildRow(final ContentItem item) {
|
private FolderBrowserTableRow buildRow(final ContentItem item) {
|
||||||
|
|
||||||
|
|
@ -365,20 +366,20 @@ public class FolderBrowserController {
|
||||||
row.setObjectUuid(item.getItemUuid());
|
row.setObjectUuid(item.getItemUuid());
|
||||||
row.setName(item.getName().getValue(defaultLocale));
|
row.setName(item.getName().getValue(defaultLocale));
|
||||||
final List<Locale> languages = new ArrayList<>(itemL10NManager
|
final List<Locale> languages = new ArrayList<>(itemL10NManager
|
||||||
.availableLanguages(item));
|
.availableLanguages(item));
|
||||||
languages.sort((lang1, lang2) -> lang1.toString().compareTo(
|
languages.sort((lang1, lang2) -> lang1.toString().compareTo(
|
||||||
lang2.toString()));
|
lang2.toString()));
|
||||||
row.setLanguages(languages);
|
row.setLanguages(languages);
|
||||||
if (item.getTitle().hasValue(globalizationHelper
|
if (item.getTitle().hasValue(globalizationHelper
|
||||||
.getNegotiatedLocale())) {
|
.getNegotiatedLocale())) {
|
||||||
row.setTitle(item.getTitle().getValue(globalizationHelper
|
row.setTitle(item.getTitle().getValue(globalizationHelper
|
||||||
.getNegotiatedLocale()));
|
.getNegotiatedLocale()));
|
||||||
} else {
|
} else {
|
||||||
row.setTitle(item.getTitle().getValue(defaultLocale));
|
row.setTitle(item.getTitle().getValue(defaultLocale));
|
||||||
}
|
}
|
||||||
final ContentType type = item.getContentType();
|
final ContentType type = item.getContentType();
|
||||||
final ContentTypeInfo typeInfo = typesManager.getContentTypeInfo(
|
final ContentTypeInfo typeInfo = typesManager.getContentTypeInfo(
|
||||||
type);
|
type);
|
||||||
row.setTypeLabelBundle(typeInfo.getLabelBundle());
|
row.setTypeLabelBundle(typeInfo.getLabelBundle());
|
||||||
row.setTypeLabelKey(typeInfo.getLabelKey());
|
row.setTypeLabelKey(typeInfo.getLabelKey());
|
||||||
|
|
||||||
|
|
@ -404,21 +405,21 @@ public class FolderBrowserController {
|
||||||
|
|
||||||
if (objectId.startsWith("folder-")) {
|
if (objectId.startsWith("folder-")) {
|
||||||
final long folderId = Long.parseLong(
|
final long folderId = Long.parseLong(
|
||||||
objectId.substring("folder-".length()));
|
objectId.substring("folder-".length()));
|
||||||
|
|
||||||
folderRepo
|
folderRepo
|
||||||
.findById(folderId)
|
.findById(folderId)
|
||||||
.ifPresent(folderRepo::delete);
|
.ifPresent(folderRepo::delete);
|
||||||
} else if (objectId.startsWith("item-")) {
|
} else if (objectId.startsWith("item-")) {
|
||||||
final long itemId = Long.parseLong(
|
final long itemId = Long.parseLong(
|
||||||
objectId.substring("item-".length()));
|
objectId.substring("item-".length()));
|
||||||
|
|
||||||
itemRepo
|
itemRepo
|
||||||
.findById(itemId)
|
.findById(itemId)
|
||||||
.ifPresent(itemRepo::delete);
|
.ifPresent(itemRepo::delete);
|
||||||
} else {
|
} else {
|
||||||
throw new IllegalArgumentException(
|
throw new IllegalArgumentException(
|
||||||
"The objectId is expected to start with 'folder-' or 'item.'.");
|
"The objectId is expected to start with 'folder-' or 'item.'.");
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
@ -434,21 +435,20 @@ public class FolderBrowserController {
|
||||||
* name in ascending and descending order depending on the value of
|
* name in ascending and descending order depending on the value of
|
||||||
* {@code orderDirection}.
|
* {@code orderDirection}.
|
||||||
*
|
*
|
||||||
* @param folder The folder which contains the subfolders.
|
* @param folder The folder which contains the subfolders.
|
||||||
* @param filterTerm The filter term.
|
* @param filterTerm The filter term.
|
||||||
* @param orderBy Field to use for ordering. If the value is negative
|
* @param orderBy Field to use for ordering. If the value is negative the
|
||||||
* the parameter is ignored.
|
* parameter is ignored.
|
||||||
* @param orderDirection Direction for ordering. If the value is negative
|
* @param orderDirection Direction for ordering. If the value is negative
|
||||||
* the parameter is ignored.
|
* the parameter is ignored.
|
||||||
* @param firstResult Index of the first result to retrieve.
|
* @param firstResult Index of the first result to retrieve.
|
||||||
* @param maxResults Maxium number of results to retrieve.
|
* @param maxResults Maxium number of results to retrieve.
|
||||||
*
|
*
|
||||||
*
|
*
|
||||||
* @return A list of the subfolders of the provided {@code folder} which
|
* @return A list of the subfolders of the provided {@code folder} which
|
||||||
* match the provided {@code filterTerm}. The list is ordered as
|
* match the provided {@code filterTerm}. The list is ordered as described
|
||||||
* described above. The list will contain at most {@code maxResults}
|
* above. The list will contain at most {@code maxResults} starting with the
|
||||||
* starting with the result with the index provided as
|
* result with the index provided as {@code firstResult}.
|
||||||
* {@code firstResult}.
|
|
||||||
*/
|
*/
|
||||||
private List<Folder> findSubFolders(final Folder folder,
|
private List<Folder> findSubFolders(final Folder folder,
|
||||||
final String filterTerm,
|
final String filterTerm,
|
||||||
|
|
@ -457,26 +457,27 @@ public class FolderBrowserController {
|
||||||
final int firstResult,
|
final int firstResult,
|
||||||
final int maxResults) {
|
final int maxResults) {
|
||||||
final CriteriaBuilder builder = entityManager
|
final CriteriaBuilder builder = entityManager
|
||||||
.getCriteriaBuilder();
|
.getCriteriaBuilder();
|
||||||
|
|
||||||
final CriteriaQuery<Folder> criteria = builder.createQuery(
|
final CriteriaQuery<Folder> criteria = builder.createQuery(
|
||||||
Folder.class);
|
Folder.class);
|
||||||
final Root<Folder> from = criteria.from(Folder.class);
|
final Root<Folder> from = criteria.from(Folder.class);
|
||||||
|
|
||||||
final Order order;
|
final Order order;
|
||||||
if (FolderBrowser.SORT_KEY_NAME.equals(orderBy)
|
if (FolderBrowser.SORT_KEY_NAME.equals(orderBy)
|
||||||
&& FolderBrowser.SORT_ACTION_DOWN.equals(orderDirection)) {
|
&& FolderBrowser.SORT_ACTION_DOWN.equals(orderDirection)) {
|
||||||
order = builder.desc(from.get("name"));
|
order = builder.desc(from.get("name"));
|
||||||
} else {
|
} else {
|
||||||
order = builder.asc(from.get("name"));
|
order = builder.asc(from.get("name"));
|
||||||
}
|
}
|
||||||
|
|
||||||
final TypedQuery<Folder> query = entityManager.createQuery(
|
final TypedQuery<Folder> query = entityManager.createQuery(
|
||||||
criteria.where(builder.and(
|
criteria.where(builder.and(
|
||||||
builder.equal(from.get("parentCategory"), folder),
|
builder.equal(from.get("parentCategory"), folder),
|
||||||
builder
|
builder
|
||||||
.like(builder.lower(from.get("name")), filterTerm)))
|
.like(builder.lower(from.get("name")),
|
||||||
.orderBy(order));
|
filterTerm)))
|
||||||
|
.orderBy(order));
|
||||||
|
|
||||||
if (firstResult >= 0) {
|
if (firstResult >= 0) {
|
||||||
query.setFirstResult(firstResult);
|
query.setFirstResult(firstResult);
|
||||||
|
|
@ -491,22 +492,21 @@ public class FolderBrowserController {
|
||||||
/**
|
/**
|
||||||
* Retrieves all items of a folder matching the provided filter term.
|
* Retrieves all items of a folder matching the provided filter term.
|
||||||
*
|
*
|
||||||
* @param folder The folder which contains the subfolders.
|
* @param folder The folder which contains the subfolders.
|
||||||
* @param filterTerm The filter term.
|
* @param filterTerm The filter term.
|
||||||
* @param orderBy Field to use for ordering. If the value is negative
|
* @param orderBy Field to use for ordering. If the value is negative the
|
||||||
* the parameter is ignored.
|
* parameter is ignored.
|
||||||
* @param orderDirection Direction for ordering. If the value is negative
|
* @param orderDirection Direction for ordering. If the value is negative
|
||||||
* the parameter is ignored.
|
* the parameter is ignored.
|
||||||
* @param firstResult Index of the first result to retrieve.
|
* @param firstResult Index of the first result to retrieve.
|
||||||
* @param maxResults Maxium number of results to retrieve.
|
* @param maxResults Maxium number of results to retrieve.
|
||||||
*
|
*
|
||||||
*
|
*
|
||||||
* @return A list of the subfolders of the provided {@code folder} which
|
* @return A list of the subfolders of the provided {@code folder} which
|
||||||
* match the provided {@code filterTerm}. The list is ordered the
|
* match the provided {@code filterTerm}. The list is ordered the field
|
||||||
* field provided as {@code orderBy} in the direction provided by
|
* provided as {@code orderBy} in the direction provided by
|
||||||
* {@code orderDirection}. The list will contain at most
|
* {@code orderDirection}. The list will contain at most {@code maxResults}
|
||||||
* {@code maxResults} starting with the result with the index
|
* starting with the result with the index provided as {@code firstResult}.
|
||||||
* provided as {@code firstResult}.
|
|
||||||
*/
|
*/
|
||||||
private List<ContentItem> findItemsInFolder(final Folder folder,
|
private List<ContentItem> findItemsInFolder(final Folder folder,
|
||||||
final String filterTerm,
|
final String filterTerm,
|
||||||
|
|
@ -516,13 +516,13 @@ public class FolderBrowserController {
|
||||||
final int maxResults) {
|
final int maxResults) {
|
||||||
|
|
||||||
final CriteriaBuilder builder = entityManager
|
final CriteriaBuilder builder = entityManager
|
||||||
.getCriteriaBuilder();
|
.getCriteriaBuilder();
|
||||||
|
|
||||||
final CriteriaQuery<ContentItem> criteria = builder.createQuery(
|
final CriteriaQuery<ContentItem> criteria = builder.createQuery(
|
||||||
ContentItem.class);
|
ContentItem.class);
|
||||||
final Root<ContentItem> fromItem = criteria.from(ContentItem.class);
|
final Root<ContentItem> fromItem = criteria.from(ContentItem.class);
|
||||||
final Join<ContentItem, Categorization> join = fromItem.join(
|
final Join<ContentItem, Categorization> join = fromItem.join(
|
||||||
"categories");
|
"categories");
|
||||||
|
|
||||||
final Path<?> orderPath;
|
final Path<?> orderPath;
|
||||||
switch (orderBy) {
|
switch (orderBy) {
|
||||||
|
|
@ -548,16 +548,16 @@ public class FolderBrowserController {
|
||||||
}
|
}
|
||||||
|
|
||||||
final TypedQuery<ContentItem> query = entityManager.createQuery(criteria
|
final TypedQuery<ContentItem> query = entityManager.createQuery(criteria
|
||||||
.select(fromItem)
|
.select(fromItem)
|
||||||
.where(builder.and(
|
.where(builder.and(
|
||||||
builder.equal(join.get("category"), folder),
|
builder.equal(join.get("category"), folder),
|
||||||
builder.equal(join.get("type"),
|
builder.equal(join.get("type"),
|
||||||
CmsConstants.CATEGORIZATION_TYPE_FOLDER),
|
CmsConstants.CATEGORIZATION_TYPE_FOLDER),
|
||||||
builder.equal(fromItem.get("version"),
|
builder.equal(fromItem.get("version"),
|
||||||
ContentItemVersion.DRAFT),
|
ContentItemVersion.DRAFT),
|
||||||
builder.like(fromItem.get("displayName"),
|
builder.like(fromItem.get("displayName"),
|
||||||
filterTerm)))
|
filterTerm)))
|
||||||
.orderBy(order));
|
.orderBy(order));
|
||||||
|
|
||||||
if (firstResult >= 0) {
|
if (firstResult >= 0) {
|
||||||
query.setFirstResult(firstResult);
|
query.setFirstResult(firstResult);
|
||||||
|
|
@ -575,7 +575,7 @@ public class FolderBrowserController {
|
||||||
* @param folder The folder to check for live items.
|
* @param folder The folder to check for live items.
|
||||||
*
|
*
|
||||||
* @return {@code true} if the {@code folder} or on of its subfolders
|
* @return {@code true} if the {@code folder} or on of its subfolders
|
||||||
* contains at least one live item, {@code false} otherwise.
|
* contains at least one live item, {@code false} otherwise.
|
||||||
*/
|
*/
|
||||||
@Transactional(Transactional.TxType.REQUIRED)
|
@Transactional(Transactional.TxType.REQUIRED)
|
||||||
public boolean hasLiveItems(final Folder folder) {
|
public boolean hasLiveItems(final Folder folder) {
|
||||||
|
|
@ -585,25 +585,132 @@ public class FolderBrowserController {
|
||||||
|
|
||||||
//Ensure that we use an non detached entity.
|
//Ensure that we use an non detached entity.
|
||||||
final Folder theFolder = folderRepo.findById(folder.getObjectId())
|
final Folder theFolder = folderRepo.findById(folder.getObjectId())
|
||||||
.orElseThrow(() -> new IllegalArgumentException(String.format(
|
.orElseThrow(() -> new IllegalArgumentException(String.format(
|
||||||
"No folder with id %s in the database. Where did that ID come from?",
|
"No folder with id %s in the database. Where did that ID come from?",
|
||||||
folder.getObjectId())));
|
folder.getObjectId())));
|
||||||
|
|
||||||
final boolean hasLiveItem = theFolder.getObjects()
|
final boolean hasLiveItem = theFolder.getObjects()
|
||||||
.stream()
|
.stream()
|
||||||
.map(categorization -> categorization.getCategorizedObject())
|
.map(categorization -> categorization.getCategorizedObject())
|
||||||
.filter(object -> object instanceof ContentItem)
|
.filter(object -> object instanceof ContentItem)
|
||||||
.map(object -> (ContentItem) object)
|
.map(object -> (ContentItem) object)
|
||||||
.filter(item -> itemManager.isLive(item))
|
.filter(item -> itemManager.isLive(item))
|
||||||
.anyMatch(item -> itemManager.isLive(item));
|
.anyMatch(item -> itemManager.isLive(item));
|
||||||
|
|
||||||
if (hasLiveItem) {
|
if (hasLiveItem) {
|
||||||
return true;
|
return true;
|
||||||
} else {
|
} else {
|
||||||
return theFolder.getSubFolders()
|
return theFolder.getSubFolders()
|
||||||
.stream()
|
.stream()
|
||||||
.anyMatch(currentFolder -> hasLiveItems(currentFolder));
|
.anyMatch(currentFolder -> hasLiveItems(currentFolder));
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Get the IDs of the folders invalid for copy/move actions.
|
||||||
|
*
|
||||||
|
* @param sources
|
||||||
|
* @return
|
||||||
|
*/
|
||||||
|
@Transactional(Transactional.TxType.REQUIRED)
|
||||||
|
public List<String> createInvalidTargetsList(final List<String> sources) {
|
||||||
|
|
||||||
|
Objects.requireNonNull(sources);
|
||||||
|
|
||||||
|
final List<String> sourceFolderIds = sources
|
||||||
|
.stream()
|
||||||
|
.filter(source -> source.startsWith(
|
||||||
|
FOLDER_BROWSER_KEY_PREFIX_FOLDER))
|
||||||
|
.collect(Collectors.toList());
|
||||||
|
final List<String> parentFolderIds = sourceFolderIds
|
||||||
|
.stream()
|
||||||
|
.map(sourceFolderId -> findParentFolderId(sourceFolderId))
|
||||||
|
.filter(Optional::isPresent)
|
||||||
|
.map(Optional::get)
|
||||||
|
.collect(Collectors.toList());
|
||||||
|
final List<List<String>> subFolderIds = sourceFolderIds
|
||||||
|
.stream()
|
||||||
|
.map(sourceFolderId -> findSubFolderIds(sourceFolderId))
|
||||||
|
.collect(Collectors.toList());
|
||||||
|
|
||||||
|
final List<String> invalidTargetIds = new ArrayList<>();
|
||||||
|
invalidTargetIds.addAll(sourceFolderIds);
|
||||||
|
invalidTargetIds.addAll(parentFolderIds);
|
||||||
|
for(final List<String> subFolderIdList : subFolderIds) {
|
||||||
|
invalidTargetIds.addAll(subFolderIdList);
|
||||||
|
}
|
||||||
|
|
||||||
|
return invalidTargetIds;
|
||||||
|
}
|
||||||
|
|
||||||
|
private Optional<String> findParentFolderId(final String folderId) {
|
||||||
|
|
||||||
|
Objects.requireNonNull(folderId);
|
||||||
|
|
||||||
|
if (!folderId.startsWith(FOLDER_BROWSER_KEY_PREFIX_FOLDER)) {
|
||||||
|
throw new IllegalArgumentException(String.format(
|
||||||
|
"Provided string '%s' is not an ID of a folder.",
|
||||||
|
folderId));
|
||||||
|
}
|
||||||
|
|
||||||
|
final long objectId = Long.parseLong(folderId.substring(
|
||||||
|
FOLDER_BROWSER_KEY_PREFIX_FOLDER.length()));
|
||||||
|
final Folder folder = folderRepo.findById(objectId)
|
||||||
|
.orElseThrow(() -> new IllegalArgumentException(String.format(
|
||||||
|
"No folder with ID %d found in database. "
|
||||||
|
+ "Where did that ID come form?",
|
||||||
|
objectId)));
|
||||||
|
if (folder.getParentFolder() == null) {
|
||||||
|
return Optional.empty();
|
||||||
|
} else {
|
||||||
|
return Optional.ofNullable(String.format(
|
||||||
|
"%s%d",
|
||||||
|
FOLDER_BROWSER_KEY_PREFIX_FOLDER,
|
||||||
|
folder.getParentFolder().getObjectId()));
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
private List<String> findSubFolderIds(final String folderId) {
|
||||||
|
|
||||||
|
Objects.requireNonNull(folderId);
|
||||||
|
|
||||||
|
if (!folderId.startsWith(FOLDER_BROWSER_KEY_PREFIX_FOLDER)) {
|
||||||
|
throw new IllegalArgumentException(String.format(
|
||||||
|
"Provided string '%s' is not the ID of a folder.",
|
||||||
|
folderId));
|
||||||
|
}
|
||||||
|
|
||||||
|
final long objectId = Long.parseLong(folderId.substring(
|
||||||
|
FOLDER_BROWSER_KEY_PREFIX_FOLDER.length()));
|
||||||
|
final Folder folder = folderRepo.findById(objectId)
|
||||||
|
.orElseThrow(() -> new IllegalArgumentException(String.format(
|
||||||
|
"No folder with ID %d found in database. "
|
||||||
|
+ "Where did that ID come form?",
|
||||||
|
objectId)));
|
||||||
|
return findSubFolders(folder)
|
||||||
|
.stream()
|
||||||
|
.map(subFolder -> String.format("%s%d",
|
||||||
|
FOLDER_BROWSER_KEY_PREFIX_FOLDER,
|
||||||
|
subFolder.getObjectId()))
|
||||||
|
.collect(Collectors.toList());
|
||||||
|
}
|
||||||
|
|
||||||
|
private List<Folder> findSubFolders(final Folder folder) {
|
||||||
|
|
||||||
|
Objects.requireNonNull(folder);
|
||||||
|
|
||||||
|
if (folder.getSubFolders() == null
|
||||||
|
|| folder.getSubFolders().isEmpty()) {
|
||||||
|
return Collections.emptyList();
|
||||||
|
}
|
||||||
|
|
||||||
|
final List<Folder> subFolders = new ArrayList<>();
|
||||||
|
for(final Folder subFolder : folder.getSubFolders()) {
|
||||||
|
subFolders.add(subFolder);
|
||||||
|
subFolders.addAll(findSubFolders(subFolder));
|
||||||
|
}
|
||||||
|
|
||||||
|
return subFolders;
|
||||||
|
}
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
|
||||||
|
|
@ -55,7 +55,6 @@ import com.arsdigita.bebop.form.SingleSelect;
|
||||||
import com.arsdigita.bebop.form.Submit;
|
import com.arsdigita.bebop.form.Submit;
|
||||||
import com.arsdigita.bebop.form.TextField;
|
import com.arsdigita.bebop.form.TextField;
|
||||||
import com.arsdigita.bebop.parameters.ArrayParameter;
|
import com.arsdigita.bebop.parameters.ArrayParameter;
|
||||||
import com.arsdigita.bebop.parameters.LongParameter;
|
|
||||||
import com.arsdigita.bebop.parameters.StringParameter;
|
import com.arsdigita.bebop.parameters.StringParameter;
|
||||||
import com.arsdigita.bebop.table.TableCellRenderer;
|
import com.arsdigita.bebop.table.TableCellRenderer;
|
||||||
import com.arsdigita.bebop.table.TableColumn;
|
import com.arsdigita.bebop.table.TableColumn;
|
||||||
|
|
@ -67,6 +66,8 @@ import org.apache.logging.log4j.LogManager;
|
||||||
import org.apache.logging.log4j.Logger;
|
import org.apache.logging.log4j.Logger;
|
||||||
|
|
||||||
import java.util.ArrayList;
|
import java.util.ArrayList;
|
||||||
|
import java.util.Arrays;
|
||||||
|
import java.util.List;
|
||||||
|
|
||||||
import org.arsdigita.cms.CMSConfig;
|
import org.arsdigita.cms.CMSConfig;
|
||||||
import org.libreccm.categorization.Category;
|
import org.libreccm.categorization.Category;
|
||||||
|
|
@ -92,14 +93,14 @@ import java.util.Objects;
|
||||||
*/
|
*/
|
||||||
@SuppressWarnings("PMD.BeanMembersShouldSerialize")
|
@SuppressWarnings("PMD.BeanMembersShouldSerialize")
|
||||||
public class FolderManipulator extends SimpleContainer implements
|
public class FolderManipulator extends SimpleContainer implements
|
||||||
//FormProcessListener,
|
//FormProcessListener,
|
||||||
//FormValidationListener,
|
//FormValidationListener,
|
||||||
//FormSubmissionListener,
|
//FormSubmissionListener,
|
||||||
Resettable {
|
Resettable {
|
||||||
|
|
||||||
//public static final String RESOURCE_BUNDLE = "com.arsdigita.cms.ui.folder.CMSFolderResources";
|
//public static final String RESOURCE_BUNDLE = "com.arsdigita.cms.ui.folder.CMSFolderResources";
|
||||||
private static final Logger LOGGER = LogManager.getLogger(
|
private static final Logger LOGGER = LogManager.getLogger(
|
||||||
FolderManipulator.class);
|
FolderManipulator.class);
|
||||||
|
|
||||||
private static final String ATOZ_FILTER_PARAM = "aToZfilter";
|
private static final String ATOZ_FILTER_PARAM = "aToZfilter";
|
||||||
private static final String ACTION_PARAM = "act";
|
private static final String ACTION_PARAM = "act";
|
||||||
|
|
@ -112,9 +113,9 @@ public class FolderManipulator extends SimpleContainer implements
|
||||||
//private static final String UNPUBLISH = "UnPublish";
|
//private static final String UNPUBLISH = "UnPublish";
|
||||||
|
|
||||||
private final ArrayParameter sourcesParam = new ArrayParameter(
|
private final ArrayParameter sourcesParam = new ArrayParameter(
|
||||||
new StringParameter(SOURCES_PARAM));
|
new StringParameter(SOURCES_PARAM));
|
||||||
private final StringParameter actionParam
|
private final StringParameter actionParam
|
||||||
= new StringParameter(ACTION_PARAM);
|
= new StringParameter(ACTION_PARAM);
|
||||||
;
|
;
|
||||||
/**
|
/**
|
||||||
* The folder in which the source items live.
|
* The folder in which the source items live.
|
||||||
|
|
@ -126,9 +127,9 @@ public class FolderManipulator extends SimpleContainer implements
|
||||||
|
|
||||||
private FilterForm filterForm;
|
private FilterForm filterForm;
|
||||||
private final StringParameter atozFilterParam = new StringParameter(
|
private final StringParameter atozFilterParam = new StringParameter(
|
||||||
ATOZ_FILTER_PARAM);
|
ATOZ_FILTER_PARAM);
|
||||||
private final StringParameter filterParam
|
private final StringParameter filterParam
|
||||||
= new StringParameter(FILTER_PARAM);
|
= new StringParameter(FILTER_PARAM);
|
||||||
|
|
||||||
public FolderManipulator(final FolderSelectionModel folderModel) {
|
public FolderManipulator(final FolderSelectionModel folderModel) {
|
||||||
|
|
||||||
|
|
@ -142,9 +143,9 @@ public class FolderManipulator extends SimpleContainer implements
|
||||||
|
|
||||||
targetSelector.addProcessListener(new TargetSelectorProcessListener());
|
targetSelector.addProcessListener(new TargetSelectorProcessListener());
|
||||||
targetSelector.addValidationListener(
|
targetSelector.addValidationListener(
|
||||||
new TargetSelectorValidationListener());
|
new TargetSelectorValidationListener());
|
||||||
targetSelector.addSubmissionListener(
|
targetSelector.addSubmissionListener(
|
||||||
new TargetSelectorSubmissionListener());
|
new TargetSelectorSubmissionListener());
|
||||||
add(targetSelector);
|
add(targetSelector);
|
||||||
|
|
||||||
//publishDialog.addProcessListener(new PublishDialogProcessListener());
|
//publishDialog.addProcessListener(new PublishDialogProcessListener());
|
||||||
|
|
@ -423,7 +424,7 @@ public class FolderManipulator extends SimpleContainer implements
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public void process(final FormSectionEvent event)
|
public void process(final FormSectionEvent event)
|
||||||
throws FormProcessException {
|
throws FormProcessException {
|
||||||
|
|
||||||
final PageState state = event.getPageState();
|
final PageState state = event.getPageState();
|
||||||
|
|
||||||
|
|
@ -442,7 +443,7 @@ public class FolderManipulator extends SimpleContainer implements
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public void process(final FormSectionEvent event) throws
|
public void process(final FormSectionEvent event) throws
|
||||||
FormProcessException {
|
FormProcessException {
|
||||||
|
|
||||||
final PageState state = event.getPageState();
|
final PageState state = event.getPageState();
|
||||||
|
|
||||||
|
|
@ -498,7 +499,7 @@ public class FolderManipulator extends SimpleContainer implements
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public void validate(final FormSectionEvent event) throws
|
public void validate(final FormSectionEvent event) throws
|
||||||
FormProcessException {
|
FormProcessException {
|
||||||
|
|
||||||
final PageState state = event.getPageState();
|
final PageState state = event.getPageState();
|
||||||
final FormData data = event.getFormData();
|
final FormData data = event.getFormData();
|
||||||
|
|
@ -512,7 +513,7 @@ public class FolderManipulator extends SimpleContainer implements
|
||||||
}
|
}
|
||||||
|
|
||||||
private class TargetSelectorValidationListener implements
|
private class TargetSelectorValidationListener implements
|
||||||
FormValidationListener {
|
FormValidationListener {
|
||||||
|
|
||||||
public TargetSelectorValidationListener() {
|
public TargetSelectorValidationListener() {
|
||||||
//Nothing
|
//Nothing
|
||||||
|
|
@ -520,7 +521,7 @@ public class FolderManipulator extends SimpleContainer implements
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public void validate(final FormSectionEvent event) throws
|
public void validate(final FormSectionEvent event) throws
|
||||||
FormProcessException {
|
FormProcessException {
|
||||||
|
|
||||||
final PageState state = event.getPageState();
|
final PageState state = event.getPageState();
|
||||||
|
|
||||||
|
|
@ -532,25 +533,25 @@ public class FolderManipulator extends SimpleContainer implements
|
||||||
final FormData data = event.getFormData();
|
final FormData data = event.getFormData();
|
||||||
if (target == null) {
|
if (target == null) {
|
||||||
data.addError(new GlobalizedMessage(
|
data.addError(new GlobalizedMessage(
|
||||||
"cms.ui.folder.need_select_target_folder",
|
"cms.ui.folder.need_select_target_folder",
|
||||||
CmsConstants.CMS_FOLDER_BUNDLE));
|
CmsConstants.CMS_FOLDER_BUNDLE));
|
||||||
//If the target is null, we can skip the rest of the checks
|
//If the target is null, we can skip the rest of the checks
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
if (target.equals(sourceFolderModel.getSelectedObject(state))) {
|
if (target.equals(sourceFolderModel.getSelectedObject(state))) {
|
||||||
data.addError(new GlobalizedMessage(
|
data.addError(new GlobalizedMessage(
|
||||||
"cms.ui.folder.not_within_same_folder",
|
"cms.ui.folder.not_within_same_folder",
|
||||||
CmsConstants.CMS_FOLDER_BUNDLE));
|
CmsConstants.CMS_FOLDER_BUNDLE));
|
||||||
}
|
}
|
||||||
|
|
||||||
// check create item permission
|
// check create item permission
|
||||||
final CdiUtil cdiUtil = CdiUtil.createCdiUtil();
|
final CdiUtil cdiUtil = CdiUtil.createCdiUtil();
|
||||||
final Shiro shiro = cdiUtil.findBean(Shiro.class);
|
final Shiro shiro = cdiUtil.findBean(Shiro.class);
|
||||||
final PermissionChecker permissionChecker = cdiUtil.findBean(
|
final PermissionChecker permissionChecker = cdiUtil.findBean(
|
||||||
PermissionChecker.class);
|
PermissionChecker.class);
|
||||||
if (!permissionChecker.isPermitted(
|
if (!permissionChecker.isPermitted(
|
||||||
ItemPrivileges.CREATE_NEW, target)) {
|
ItemPrivileges.CREATE_NEW, target)) {
|
||||||
data.addError("cms.ui.folder.no_permission_for_item",
|
data.addError("cms.ui.folder.no_permission_for_item",
|
||||||
CmsConstants.CMS_FOLDER_BUNDLE);
|
CmsConstants.CMS_FOLDER_BUNDLE);
|
||||||
}
|
}
|
||||||
|
|
@ -572,24 +573,24 @@ public class FolderManipulator extends SimpleContainer implements
|
||||||
|
|
||||||
final CdiUtil cdiUtil = CdiUtil.createCdiUtil();
|
final CdiUtil cdiUtil = CdiUtil.createCdiUtil();
|
||||||
final FolderRepository folderRepo = cdiUtil.findBean(
|
final FolderRepository folderRepo = cdiUtil.findBean(
|
||||||
FolderRepository.class);
|
FolderRepository.class);
|
||||||
final ContentItemRepository itemRepo = cdiUtil.findBean(
|
final ContentItemRepository itemRepo = cdiUtil.findBean(
|
||||||
ContentItemRepository.class);
|
ContentItemRepository.class);
|
||||||
final ContentItemManager itemManager = cdiUtil.findBean(
|
final ContentItemManager itemManager = cdiUtil.findBean(
|
||||||
ContentItemManager.class);
|
ContentItemManager.class);
|
||||||
final FolderBrowserController controller = cdiUtil.findBean(
|
final FolderBrowserController controller = cdiUtil.findBean(
|
||||||
FolderBrowserController.class);
|
FolderBrowserController.class);
|
||||||
final PermissionChecker permissionChecker = cdiUtil.findBean(
|
final PermissionChecker permissionChecker = cdiUtil.findBean(
|
||||||
PermissionChecker.class);
|
PermissionChecker.class);
|
||||||
|
|
||||||
final CcmObject object;
|
final CcmObject object;
|
||||||
final String name;
|
final String name;
|
||||||
if (objectId.startsWith("folder--")) {
|
if (objectId.startsWith("folder--")) {
|
||||||
final long folderId = Long.parseLong(objectId.substring(
|
final long folderId = Long.parseLong(objectId.substring(
|
||||||
"folder--".length()));
|
"folder--".length()));
|
||||||
final Folder folder = folderRepo.findById(folderId).orElseThrow(
|
final Folder folder = folderRepo.findById(folderId).orElseThrow(
|
||||||
() -> new IllegalArgumentException(String.format(
|
() -> new IllegalArgumentException(String.format(
|
||||||
"No folder with id %d in database.", folderId)));
|
"No folder with id %d in database.", folderId)));
|
||||||
|
|
||||||
name = folder.getName();
|
name = folder.getName();
|
||||||
|
|
||||||
|
|
@ -602,10 +603,11 @@ public class FolderManipulator extends SimpleContainer implements
|
||||||
|
|
||||||
} else if (objectId.startsWith("item--")) {
|
} else if (objectId.startsWith("item--")) {
|
||||||
final long itemId = Long.parseLong(objectId.substring(
|
final long itemId = Long.parseLong(objectId.substring(
|
||||||
"item--".length()));
|
"item--".length()));
|
||||||
final ContentItem item = itemRepo.findById(itemId).orElseThrow(
|
final ContentItem item = itemRepo.findById(itemId).orElseThrow(
|
||||||
() -> new IllegalArgumentException(String.format(
|
() -> new IllegalArgumentException(String.format(
|
||||||
"No content item with id %d in database.", itemId)));
|
"No content item with id %d in database.",
|
||||||
|
itemId)));
|
||||||
|
|
||||||
name = item.getDisplayName();
|
name = item.getDisplayName();
|
||||||
|
|
||||||
|
|
@ -616,9 +618,9 @@ public class FolderManipulator extends SimpleContainer implements
|
||||||
object = item;
|
object = item;
|
||||||
} else {
|
} else {
|
||||||
throw new IllegalArgumentException(String.format(
|
throw new IllegalArgumentException(String.format(
|
||||||
"Provided objectId '%s' does not start with 'folder--' "
|
"Provided objectId '%s' does not start with 'folder--' "
|
||||||
+ "or 'item--'.",
|
+ "or 'item--'.",
|
||||||
objectId));
|
objectId));
|
||||||
}
|
}
|
||||||
|
|
||||||
final long count = controller.countObjects(target, name);
|
final long count = controller.countObjects(target, name);
|
||||||
|
|
@ -630,7 +632,7 @@ public class FolderManipulator extends SimpleContainer implements
|
||||||
|
|
||||||
if (!(permissionChecker.isPermitted(
|
if (!(permissionChecker.isPermitted(
|
||||||
ItemPrivileges.DELETE, object))
|
ItemPrivileges.DELETE, object))
|
||||||
&& isMove(state)) {
|
&& isMove(state)) {
|
||||||
addErrorMessage(data,
|
addErrorMessage(data,
|
||||||
"cms.ui.folder.no_permission_for_item",
|
"cms.ui.folder.no_permission_for_item",
|
||||||
object.getDisplayName());
|
object.getDisplayName());
|
||||||
|
|
@ -659,7 +661,7 @@ public class FolderManipulator extends SimpleContainer implements
|
||||||
// }
|
// }
|
||||||
// }
|
// }
|
||||||
private class TargetSelectorSubmissionListener implements
|
private class TargetSelectorSubmissionListener implements
|
||||||
FormSubmissionListener {
|
FormSubmissionListener {
|
||||||
|
|
||||||
public TargetSelectorSubmissionListener() {
|
public TargetSelectorSubmissionListener() {
|
||||||
//Nothing
|
//Nothing
|
||||||
|
|
@ -667,15 +669,15 @@ public class FolderManipulator extends SimpleContainer implements
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public void submitted(final FormSectionEvent event) throws
|
public void submitted(final FormSectionEvent event) throws
|
||||||
FormProcessException {
|
FormProcessException {
|
||||||
|
|
||||||
final PageState state = event.getPageState();
|
final PageState state = event.getPageState();
|
||||||
|
|
||||||
if (targetSelector.isCancelled(state)) {
|
if (targetSelector.isCancelled(state)) {
|
||||||
reset(state);
|
reset(state);
|
||||||
throw new FormProcessException(new GlobalizedMessage(
|
throw new FormProcessException(new GlobalizedMessage(
|
||||||
"cms.ui.folder.cancelled",
|
"cms.ui.folder.cancelled",
|
||||||
CmsConstants.CMS_FOLDER_BUNDLE));
|
CmsConstants.CMS_FOLDER_BUNDLE));
|
||||||
}
|
}
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
@ -719,25 +721,25 @@ public class FolderManipulator extends SimpleContainer implements
|
||||||
final Label label = (Label) event.getTarget();
|
final Label label = (Label) event.getTarget();
|
||||||
final int numberOfItems = getSources(state).length;
|
final int numberOfItems = getSources(state).length;
|
||||||
final Category folder = (Category) sourceFolderModel.
|
final Category folder = (Category) sourceFolderModel.
|
||||||
getSelectedObject(state);
|
getSelectedObject(state);
|
||||||
final CdiUtil cdiUtil = CdiUtil.createCdiUtil();
|
final CdiUtil cdiUtil = CdiUtil.createCdiUtil();
|
||||||
final CategoryManager categoryManager = cdiUtil.
|
final CategoryManager categoryManager = cdiUtil.
|
||||||
findBean(CategoryManager.class);
|
findBean(CategoryManager.class);
|
||||||
|
|
||||||
if (isMove(state)) {
|
if (isMove(state)) {
|
||||||
|
|
||||||
label.setLabel(new GlobalizedMessage(
|
label.setLabel(new GlobalizedMessage(
|
||||||
"cms.ui.folder.move",
|
"cms.ui.folder.move",
|
||||||
CmsConstants.CMS_FOLDER_BUNDLE,
|
CmsConstants.CMS_FOLDER_BUNDLE,
|
||||||
new Object[]{numberOfItems,
|
new Object[]{numberOfItems,
|
||||||
categoryManager.getCategoryPath(
|
categoryManager.getCategoryPath(
|
||||||
folder)}));
|
folder)}));
|
||||||
} else if (isCopy(state)) {
|
} else if (isCopy(state)) {
|
||||||
label.setLabel(new GlobalizedMessage(
|
label.setLabel(new GlobalizedMessage(
|
||||||
"cms.ui.folder.copy",
|
"cms.ui.folder.copy",
|
||||||
new Object[]{numberOfItems,
|
new Object[]{numberOfItems,
|
||||||
categoryManager.getCategoryPath(
|
categoryManager.getCategoryPath(
|
||||||
folder)}));
|
folder)}));
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
@ -761,13 +763,13 @@ public class FolderManipulator extends SimpleContainer implements
|
||||||
// Set things up the first time the selector gets visible
|
// Set things up the first time the selector gets visible
|
||||||
public void expose(final PageState state) {
|
public void expose(final PageState state) {
|
||||||
final Category folder = (Category) sourceFolderModel.
|
final Category folder = (Category) sourceFolderModel.
|
||||||
getSelectedObject(
|
getSelectedObject(
|
||||||
state);
|
state);
|
||||||
targetModel.clearSelection(state);
|
targetModel.clearSelection(state);
|
||||||
if (folder != null) {
|
if (folder != null) {
|
||||||
final CdiUtil cdiUtil = CdiUtil.createCdiUtil();
|
final CdiUtil cdiUtil = CdiUtil.createCdiUtil();
|
||||||
final ContentItemManager itemManager = cdiUtil.findBean(
|
final ContentItemManager itemManager = cdiUtil.findBean(
|
||||||
ContentItemManager.class);
|
ContentItemManager.class);
|
||||||
|
|
||||||
//ToDo
|
//ToDo
|
||||||
// final ItemCollection items = folder.getPathInfo(true);
|
// final ItemCollection items = folder.getPathInfo(true);
|
||||||
|
|
@ -864,15 +866,15 @@ public class FolderManipulator extends SimpleContainer implements
|
||||||
// folderBrowser.setFilterForm(filterForm);
|
// folderBrowser.setFilterForm(filterForm);
|
||||||
folderBrowser.setFolderManipulator(FolderManipulator.this);
|
folderBrowser.setFolderManipulator(FolderManipulator.this);
|
||||||
paginator = new Paginator(
|
paginator = new Paginator(
|
||||||
new FolderBrowserPaginationModelBuilder(folderBrowser),
|
new FolderBrowserPaginationModelBuilder(folderBrowser),
|
||||||
CMSConfig.getConfig().getFolderBrowseListSize());
|
CMSConfig.getConfig().getFolderBrowseListSize());
|
||||||
folderBrowser.setPaginator(paginator);
|
folderBrowser.setPaginator(paginator);
|
||||||
panel.add(paginator);
|
panel.add(paginator);
|
||||||
panel.add(folderBrowser);
|
panel.add(folderBrowser);
|
||||||
|
|
||||||
LOGGER.debug("Adding filter form...");
|
LOGGER.debug("Adding filter form...");
|
||||||
filterForm = new FilterForm(new FolderBrowserFilterFormModelBuilder(
|
filterForm = new FilterForm(new FolderBrowserFilterFormModelBuilder(
|
||||||
folderBrowser));
|
folderBrowser));
|
||||||
FolderManipulator.this.add(filterForm);
|
FolderManipulator.this.add(filterForm);
|
||||||
|
|
||||||
checkboxGroup = new CheckboxGroup(sourcesParam);
|
checkboxGroup = new CheckboxGroup(sourcesParam);
|
||||||
|
|
@ -884,19 +886,19 @@ public class FolderManipulator extends SimpleContainer implements
|
||||||
group.addAction(container);
|
group.addAction(container);
|
||||||
|
|
||||||
container.add(new Label(new GlobalizedMessage(
|
container.add(new Label(new GlobalizedMessage(
|
||||||
"cms.ui.folder.edit_selection",
|
"cms.ui.folder.edit_selection",
|
||||||
CmsConstants.CMS_FOLDER_BUNDLE)));
|
CmsConstants.CMS_FOLDER_BUNDLE)));
|
||||||
actionSelect = new SingleSelect(actionParam);
|
actionSelect = new SingleSelect(actionParam);
|
||||||
actionSelect.addOption(
|
actionSelect.addOption(
|
||||||
new Option(COPY,
|
new Option(COPY,
|
||||||
new Label(new GlobalizedMessage(
|
new Label(new GlobalizedMessage(
|
||||||
"cms.ui.folder.copy.action",
|
"cms.ui.folder.copy.action",
|
||||||
CmsConstants.CMS_FOLDER_BUNDLE))));
|
CmsConstants.CMS_FOLDER_BUNDLE))));
|
||||||
actionSelect.addOption(
|
actionSelect.addOption(
|
||||||
new Option(MOVE,
|
new Option(MOVE,
|
||||||
new Label(new GlobalizedMessage(
|
new Label(new GlobalizedMessage(
|
||||||
"cms.ui.folder.move.action",
|
"cms.ui.folder.move.action",
|
||||||
CmsConstants.CMS_FOLDER_BUNDLE))));
|
CmsConstants.CMS_FOLDER_BUNDLE))));
|
||||||
//Publishing in the folder browser only works if threaded publishing is active
|
//Publishing in the folder browser only works if threaded publishing is active
|
||||||
// if (CMSConfig.getInstanceOf().getThreadedPublishing()) {
|
// if (CMSConfig.getInstanceOf().getThreadedPublishing()) {
|
||||||
// actionSelect.addOption(new Option(PUBLISH,
|
// actionSelect.addOption(new Option(PUBLISH,
|
||||||
|
|
@ -909,8 +911,8 @@ public class FolderManipulator extends SimpleContainer implements
|
||||||
container.add(actionSelect);
|
container.add(actionSelect);
|
||||||
submit = new Submit("Go",
|
submit = new Submit("Go",
|
||||||
new GlobalizedMessage(
|
new GlobalizedMessage(
|
||||||
"cms.ui.folder.go",
|
"cms.ui.folder.go",
|
||||||
CmsConstants.CMS_FOLDER_BUNDLE));
|
CmsConstants.CMS_FOLDER_BUNDLE));
|
||||||
container.add(submit);
|
container.add(submit);
|
||||||
|
|
||||||
// Add a new first column to the table
|
// Add a new first column to the table
|
||||||
|
|
@ -988,8 +990,8 @@ public class FolderManipulator extends SimpleContainer implements
|
||||||
panel = new BoxPanel(BoxPanel.HORIZONTAL);
|
panel = new BoxPanel(BoxPanel.HORIZONTAL);
|
||||||
|
|
||||||
final ActionLink allLink = new ActionLink(
|
final ActionLink allLink = new ActionLink(
|
||||||
new GlobalizedMessage("cms.ui.folder.filter.all",
|
new GlobalizedMessage("cms.ui.folder.filter.all",
|
||||||
CmsConstants.CMS_FOLDER_BUNDLE));
|
CmsConstants.CMS_FOLDER_BUNDLE));
|
||||||
allLink.addActionListener(new ActionListener() {
|
allLink.addActionListener(new ActionListener() {
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
|
|
@ -1015,14 +1017,14 @@ public class FolderManipulator extends SimpleContainer implements
|
||||||
// panel.add(link);
|
// panel.add(link);
|
||||||
// }
|
// }
|
||||||
panel.add(new Label(new GlobalizedMessage(
|
panel.add(new Label(new GlobalizedMessage(
|
||||||
"cms.ui.folder.filter",
|
"cms.ui.folder.filter",
|
||||||
CmsConstants.CMS_FOLDER_BUNDLE)));
|
CmsConstants.CMS_FOLDER_BUNDLE)));
|
||||||
filterField = new TextField(filterParam);
|
filterField = new TextField(filterParam);
|
||||||
panel.add(filterField);
|
panel.add(filterField);
|
||||||
panel.add(new Submit("filterFolderSubmit",
|
panel.add(new Submit("filterFolderSubmit",
|
||||||
new GlobalizedMessage(
|
new GlobalizedMessage(
|
||||||
"cms.ui.folder.filter_do",
|
"cms.ui.folder.filter_do",
|
||||||
CmsConstants.CMS_FOLDER_BUNDLE)));
|
CmsConstants.CMS_FOLDER_BUNDLE)));
|
||||||
|
|
||||||
add(panel);
|
add(panel);
|
||||||
|
|
||||||
|
|
@ -1034,28 +1036,28 @@ public class FolderManipulator extends SimpleContainer implements
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public void process(final FormSectionEvent event) throws
|
public void process(final FormSectionEvent event) throws
|
||||||
FormProcessException {
|
FormProcessException {
|
||||||
//Nothing
|
//Nothing
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public void init(final FormSectionEvent event) throws
|
public void init(final FormSectionEvent event) throws
|
||||||
FormProcessException {
|
FormProcessException {
|
||||||
//fse.getPageState().setValue(FolderManipulator.this.m_filter, null);
|
//fse.getPageState().setValue(FolderManipulator.this.m_filter, null);
|
||||||
//filterField.setValue(fse.getPageState(), null);
|
//filterField.setValue(fse.getPageState(), null);
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public void submitted(final FormSectionEvent event) throws
|
public void submitted(final FormSectionEvent event) throws
|
||||||
FormProcessException {
|
FormProcessException {
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public boolean isVisible(PageState state) {
|
public boolean isVisible(PageState state) {
|
||||||
if (super.isVisible(state)
|
if (super.isVisible(state)
|
||||||
&& (modelBuilder.getFolderSize(state)
|
&& (modelBuilder.getFolderSize(state)
|
||||||
>= CMSConfig.getConfig().
|
>= CMSConfig.getConfig().
|
||||||
getFolderAtoZShowLimit())) {
|
getFolderAtoZShowLimit())) {
|
||||||
return true;
|
return true;
|
||||||
} else {
|
} else {
|
||||||
return false;
|
return false;
|
||||||
|
|
@ -1086,7 +1088,8 @@ public class FolderManipulator extends SimpleContainer implements
|
||||||
// }
|
// }
|
||||||
private class FolderTreeCellRenderer implements TreeCellRenderer {
|
private class FolderTreeCellRenderer implements TreeCellRenderer {
|
||||||
|
|
||||||
private RequestLocal m_invalidFolders = new RequestLocal();
|
private final RequestLocal invalidFoldersRequestLocal
|
||||||
|
= new RequestLocal();
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Render the folders appropriately. The selected folder is a bold
|
* Render the folders appropriately. The selected folder is a bold
|
||||||
|
|
@ -1104,72 +1107,19 @@ public class FolderManipulator extends SimpleContainer implements
|
||||||
final Object key) {
|
final Object key) {
|
||||||
|
|
||||||
// Get the list of invalid folders once per request.
|
// Get the list of invalid folders once per request.
|
||||||
@SuppressWarnings("unchecked")
|
final List<String> invalidFolders;
|
||||||
ArrayList<String> invalidFolders
|
if (invalidFoldersRequestLocal.get(state) == null) {
|
||||||
= (ArrayList<String>) m_invalidFolders.get(state);
|
final CdiUtil cdiUtil = CdiUtil.createCdiUtil();
|
||||||
|
final FolderBrowserController controller = cdiUtil.findBean(
|
||||||
if (invalidFolders == null) {
|
FolderBrowserController.class);
|
||||||
// The list of invalid folders has not been set for this
|
invalidFolders = controller.createInvalidTargetsList(
|
||||||
// request. Setting now.
|
Arrays.asList(getSources(state)));
|
||||||
invalidFolders = new ArrayList<>();
|
invalidFoldersRequestLocal.set(state, invalidFolders);
|
||||||
final String[] sources = getSources(state);
|
} else {
|
||||||
|
invalidFolders = (List<String>) invalidFoldersRequestLocal
|
||||||
for (final String source : sources) {
|
.get(state);
|
||||||
if (source.startsWith("folder--")) {
|
|
||||||
invalidFolders.addAll(source);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
// if (invalidFolders == null) {
|
|
||||||
// // The list of invalid folders has not been set for this
|
|
||||||
// // request. Setting now.
|
|
||||||
// invalidFolders = new ArrayList();
|
|
||||||
//
|
|
||||||
// final DataCollection collection = SessionManager.getSession().
|
|
||||||
// retrieve(
|
|
||||||
// ContentItem.BASE_DATA_OBJECT_TYPE);
|
|
||||||
// CompoundFilter filter = collection.getFilterFactory().or();
|
|
||||||
// // The sources themselves are not valid.
|
|
||||||
// final Long[] sources = getSources(state);
|
|
||||||
//
|
|
||||||
// for (int i = 0; i < sources.length; i++) {
|
|
||||||
// invalidFolders.add(sources[i].toString());
|
|
||||||
//
|
|
||||||
// final Filter temp = filter.addFilter("id = :id" + i);
|
|
||||||
// temp.set("id" + i, sources[i]);
|
|
||||||
// }
|
|
||||||
// collection.addFilter(filter);
|
|
||||||
//
|
|
||||||
// final DataCollection folders = SessionManager.getSession().
|
|
||||||
// retrieve(
|
|
||||||
// Folder.BASE_DATA_OBJECT_TYPE);
|
|
||||||
// folders.addEqualsFilter(Folder.IS_DELETED, Boolean.FALSE);
|
|
||||||
//
|
|
||||||
// filter = collection.getFilterFactory().or();
|
|
||||||
// int count = 0;
|
|
||||||
// while (collection.next()) {
|
|
||||||
// filter.addFilter(Folder.ANCESTORS + " like :ancestors"
|
|
||||||
// + count + " || '%'");
|
|
||||||
// filter.set("ancestors" + count,
|
|
||||||
// collection.get(ContentItem.ANCESTORS));
|
|
||||||
// count++;
|
|
||||||
// }
|
|
||||||
// folders.addFilter(filter);
|
|
||||||
//
|
|
||||||
// while (folders.next()) {
|
|
||||||
// invalidFolders.add(folders.get(Folder.ID).toString());
|
|
||||||
// }
|
|
||||||
//
|
|
||||||
// invalidFolders.add(sourceFolderModel.getSelectedKey(state).
|
|
||||||
// toString());
|
|
||||||
//
|
|
||||||
// // Save the invalid folder list
|
|
||||||
// m_invalidFolders.set(state, invalidFolders);
|
|
||||||
// }
|
|
||||||
final Label label = new Label(value.toString());
|
final Label label = new Label(value.toString());
|
||||||
|
|
||||||
if (invalidFolders.contains(key.toString())) {
|
if (invalidFolders.contains(key.toString())) {
|
||||||
|
|
|
||||||
|
|
@ -26,7 +26,6 @@ import org.librecms.contentsection.Folder;
|
||||||
import org.librecms.contentsection.FolderRepository;
|
import org.librecms.contentsection.FolderRepository;
|
||||||
|
|
||||||
import java.util.ArrayList;
|
import java.util.ArrayList;
|
||||||
import java.util.Iterator;
|
|
||||||
import java.util.List;
|
import java.util.List;
|
||||||
import java.util.Objects;
|
import java.util.Objects;
|
||||||
import java.util.Optional;
|
import java.util.Optional;
|
||||||
|
|
|
||||||
|
|
@ -54,6 +54,9 @@ public class CmsConstants {
|
||||||
|
|
||||||
public static final String CATEGORIZATION_TYPE_FOLDER = "folder";
|
public static final String CATEGORIZATION_TYPE_FOLDER = "folder";
|
||||||
|
|
||||||
|
public static final String FOLDER_BROWSER_KEY_PREFIX_FOLDER = "folder-";
|
||||||
|
public static final String FOLDER_BROWSER_KEY_PREFIX_ITEM = "item-";
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Constant string used as key for creating service package as a legacy
|
* Constant string used as key for creating service package as a legacy
|
||||||
* application.
|
* application.
|
||||||
|
|
|
||||||
Loading…
Reference in New Issue