CCM NG/ccm-cms: Deleting items from FolderBrowser

git-svn-id: https://svn.libreccm.org/ccm/ccm_ng@4591 8810af33-2d31-482b-a856-94f89814c4df
jensp 2017-02-22 12:37:17 +00:00
parent d0f46755e9
commit 0f5f728ffe
10 changed files with 148 additions and 286 deletions

View File

@ -349,6 +349,7 @@ public class FolderBrowser extends Table {
final boolean isFolder = ((FolderBrowserTableModel) table final boolean isFolder = ((FolderBrowserTableModel) table
.getTableModel(state)).isFolder(); .getTableModel(state)).isFolder();
final long objectId = getObjectId(key);
if (isFolder) { if (isFolder) {
//return new ControlLink(new Text(name)); //return new ControlLink(new Text(name));
@ -356,13 +357,13 @@ public class FolderBrowser extends Table {
state, state,
value, value,
isSelected, isSelected,
key, objectId,
row, row,
column); column);
} else { } else {
return new Link(new Text(name), return new Link(new Text(name),
itemResolver.generateItemURL(state, itemResolver.generateItemURL(state,
(long) key, objectId,
name, name,
section, section,
"DRAFT")); "DRAFT"));
@ -392,48 +393,21 @@ public class FolderBrowser extends Table {
final int row, final int row,
final int column) { final int column) {
// final ContentItem item = (ContentItem) value;
// final String name = item.getDisplayName();
final SimpleContainer container = new SimpleContainer(); final SimpleContainer container = new SimpleContainer();
final ContentSection section = CMS.getContext().getContentSection(); final ContentSection section = CMS.getContext().getContentSection();
final CdiUtil cdiUtil = CdiUtil.createCdiUtil(); final CdiUtil cdiUtil = CdiUtil.createCdiUtil();
// final ContentItemManager itemManager = cdiUtil.findBean(
// ContentItemManager.class);
final ContentSectionManager sectionManager = cdiUtil.findBean( final ContentSectionManager sectionManager = cdiUtil.findBean(
ContentSectionManager.class); ContentSectionManager.class);
final ItemResolver itemResolver = sectionManager.getItemResolver( final ItemResolver itemResolver = sectionManager.getItemResolver(
section); section);
// item.getName().getAvailableLocales().stream()
// .map((locale) -> locale.toString())
// .map((lang) -> {
// final StringBuilder fontWeight = new StringBuilder(2);
// final StringBuilder styleClasses = new StringBuilder(20);
// if (itemManager.isLive(item)) {
// fontWeight.append(Label.BOLD);
// styleClasses.append("live ");
// }
// final Label langLabel = new Label(lang);
// langLabel.setFontWeight(fontWeight.toString().trim());
// langLabel.setClassAttr(styleClasses.toString().trim());
// return langLabel;
// })
// .forEach((langLabel) -> {
// container.add(new Link(
// langLabel,
// itemResolver.generateItemURL(state,
// item.getObjectId(),
// name,
// section,
// item.getVersion().name())));
// });
@SuppressWarnings("unchecked") @SuppressWarnings("unchecked")
final List<Locale> availableLocales = (List<Locale>) value; final List<Locale> availableLocales = (List<Locale>) value;
availableLocales.forEach(locale -> container.add(new Link( availableLocales.forEach(locale -> container.add(new Link(
new Text(locale.toString()), new Text(locale.toString()),
itemResolver.generateItemURL( itemResolver.generateItemURL(
state, state,
(long) key, getObjectId(key),
locale.toString(), locale.toString(),
section, section,
"DRAFT")))); "DRAFT"))));
@ -516,188 +490,17 @@ public class FolderBrowser extends Table {
} }
final PageState state = event.getPageState(); final PageState state = event.getPageState();
final long itemId = Long.parseLong(event.getRowKey().toString());
final CdiUtil cdiUtil = CdiUtil.createCdiUtil(); final CdiUtil cdiUtil = CdiUtil.createCdiUtil();
final FolderBrowserController controller = cdiUtil.findBean( final FolderBrowserController controller = cdiUtil.findBean(
FolderBrowserController.class); FolderBrowserController.class);
controller.deleteObject(itemId); controller.deleteObject((String) event.getRowKey());
((Table) event.getSource()).clearSelection(state); ((Table) event.getSource()).clearSelection(state);
} }
} }
// /**
// * Table model around ItemCollection
// */
// private static class FolderTableModel implements TableModel {
//
// private static final int NAME = 0;
// private static final int LANGUAGES = 1;
// private static final int TITLE = 2;
// private static final int ADDITIONAL_INFO = 3;
// private static final int TYPE = 4;
// private static final int CREATION_DATE = 5;
// private static final int LAST_MODIFIED = 6;
// private static final int DELETABLE = 7;
// private static final int IS_INDEX = 8;
// private PageState m_state;
// private FolderBrowser m_table;
// private List<ContentItem> m_itemColl;
// private Category m_fol;
// private Long m_folIndexID;
// private final ContentItemRepository itemRepo;
// private final ContentItemManager itemManager;
// private final CategoryManager categoryManager;
// private int index = -1;
//
// //old constructor before using paginator
// //public FolderTableModel(Folder folder) {
// //m_itemColl = folder.getItems();
// //}
// public FolderTableModel(FolderBrowser table,
// PageState state,
// List<ContentItem> itemColl) {
// m_state = state;
// m_table = table;
// m_itemColl = itemColl;
//
// m_fol = (Category) table.getFolderSelectionModel()
// .getSelectedObject(state);
//
// final CdiUtil cdiUtil = CdiUtil.createCdiUtil();
// itemRepo = cdiUtil.findBean(ContentItemRepository.class);
// itemManager = cdiUtil.findBean(ContentItemManager.class);
// categoryManager = cdiUtil.findBean(CategoryManager.class);
//
// if (!hideIndexColumn()) {
// final Optional<CcmObject> indexItem = categoryManager
// .getIndexObject(m_fol);
// if (indexItem.isPresent()) {
// m_folIndexID = indexItem.get().getObjectId();
// } else {
// m_folIndexID = null;
// }
// }
// }
//
// @Override
// public int getColumnCount() {
// return 7;
// }
//
// @Override
// public boolean nextRow() {
// index++;
// return index < m_itemColl.size();
// }
//
// @Override
// public Object getElementAt(int columnIndex) {
// switch (columnIndex) {
// case NAME:
// return m_itemColl.get(index);
// case LANGUAGES:
// return m_itemColl.get(index);
// case TITLE:
// return m_itemColl.get(index).getDisplayName();
// case ADDITIONAL_INFO:
// return "";
// case TYPE:
// return m_itemColl.get(index).getContentType().getLabel()
// .getValue();
// case CREATION_DATE: {
// final CcmRevision firstRevision = itemRepo
// .retrieveFirstRevision(
// m_itemColl.get(index), m_itemColl.get(index)
// .getObjectId());
// if (firstRevision == null) {
// return "--";
// } else {
// return FormatStandards.formatDate(new Date(firstRevision
// .getTimestamp()));
// }
// }
// case LAST_MODIFIED: {
// final CcmRevision currentRevision = itemRepo
// .retrieveCurrentRevision(
// m_itemColl.get(index),
// m_itemColl.get(index).getObjectId());
// if (currentRevision == null) {
// return "--";
// } else {
// return FormatStandards.formatDate(new Date(
// currentRevision.getTimestamp()));
// }
// }
// case DELETABLE:
// return isDeletable();
// case IS_INDEX: {
// if (hideIndexColumn()) {
// throw new IndexOutOfBoundsException(
// "Column index " + columnIndex
// + " not in table model.");
// }
// if (m_folIndexID == null) {
// return false;
// }
// return m_folIndexID.compareTo(
// m_itemColl.get(index).getObjectId()) == 0;
// }
// default:
// throw new IndexOutOfBoundsException("Column index "
// + columnIndex
// + " not in table model.");
// }
// }
//
// public boolean isDeletable() {
// if (LOGGER.isDebugEnabled()) {
// LOGGER.debug("Checking to see if " + this + " is deletable");
// }
//
//// if (m_itemColl.isFolder()) {
////
//// if (!m_itemColl.hasChildren()) {
//// if (s_log.isDebugEnabled()) {
//// s_log.debug(
//// "The item is an empty folder; it may be deleted");
//// }
//// return true;
////
//// } else {
////
//// if (s_log.isDebugEnabled()) {
//// s_log.debug(
//// "The folder is not empty; it cannot be deleted");
//// }
//// return false;
////
//// }
//// } else
// if (itemManager.isLive(m_itemColl.get(index))) {
//
// if (LOGGER.isDebugEnabled()) {
// LOGGER.debug(
// "This item has a live instance; it cannot be deleted");
// }
// return false;
// }
//
// if (LOGGER.isDebugEnabled()) {
// LOGGER.debug(
// "The item is not a folder and doesn't have a live instance; it may be deleted");
// }
// return true;
// }
//
// public Object getKeyAt(int columnIndex) {
// // Note: Folders were marked by negative IDs
// return m_itemColl.get(index).getObjectId();
// }
//
// }
private class FolderChanger extends TableActionAdapter { private class FolderChanger extends TableActionAdapter {
@Override @Override
@ -708,54 +511,14 @@ public class FolderBrowser extends Table {
if (nameColumn != getColumn(col)) { if (nameColumn != getColumn(col)) {
return; return;
} }
final String key = (String) event.getRowKey();
clearSelection(state); clearSelection(state);
getFolderSelectionModel().setSelectedKey(state, Long.parseLong(key)); getFolderSelectionModel().setSelectedKey(
state,
getObjectId(event.getRowKey()));
} }
} }
// private class IndexChanger extends TableActionAdapter {
//
// private FolderSelectionModel m_fol;
//
// public IndexChanger(FolderSelectionModel fol) {
// super();
// m_fol = fol;
// }
//
// @Override
// public void cellSelected(TableActionEvent e) {
// PageState state = e.getPageState();
//
// BigDecimal rowkey = new BigDecimal((String) e.getRowKey());
// if (rowkey == null) {
// return;
// }
//
// try {
// ContentBundle contentItem = new ContentBundle(rowkey);
//
// Folder folder = (Folder) m_fol.getSelectedObject(state);
//
// ContentBundle currentIndexItem = (ContentBundle) folder.
// getIndexItem();
// if (currentIndexItem == null || (currentIndexItem.getID().
// compareTo(contentItem.getID())
// != 0)) {
// folder.setIndexItem(contentItem);
// } else {
// folder.removeIndexItem();
// }
// folder.save();
// } catch (DataObjectNotFoundException donfe) {
// // Do nothing
// }
// }
//
// }
/** /**
* Getting the GlobalizedMessage using a CMS Class targetBundle. * Getting the GlobalizedMessage using a CMS Class targetBundle.
* *
@ -766,4 +529,18 @@ public class FolderBrowser extends Table {
} }
private long getObjectId(final Object key) {
final String keyStr = (String) key;
if (keyStr.startsWith("folder-")) {
return Long.parseLong(keyStr.substring("folder-".length()));
} else if (keyStr.startsWith("item-")) {
return Long.parseLong(keyStr.substring("item-".length()));
} else {
return Long.parseLong(keyStr);
}
}
} }

View File

@ -30,9 +30,11 @@ import org.librecms.CmsConstants;
import org.librecms.contentsection.ContentItem; import org.librecms.contentsection.ContentItem;
import org.librecms.contentsection.ContentItemL10NManager; import org.librecms.contentsection.ContentItemL10NManager;
import org.librecms.contentsection.ContentItemManager; import org.librecms.contentsection.ContentItemManager;
import org.librecms.contentsection.ContentItemRepository;
import org.librecms.contentsection.ContentItemVersion; import org.librecms.contentsection.ContentItemVersion;
import org.librecms.contentsection.ContentType; import org.librecms.contentsection.ContentType;
import org.librecms.contentsection.Folder; import org.librecms.contentsection.Folder;
import org.librecms.contentsection.FolderRepository;
import org.librecms.contenttypes.ContentTypeInfo; import org.librecms.contenttypes.ContentTypeInfo;
import org.librecms.contenttypes.ContentTypesManager; import org.librecms.contenttypes.ContentTypesManager;
@ -91,6 +93,12 @@ public class FolderBrowserController {
@Inject @Inject
private ContentTypesManager typesManager; private ContentTypesManager typesManager;
@Inject
private FolderRepository folderRepo;
@Inject
private ContentItemRepository itemRepo;
@Inject @Inject
private ContentItemManager itemManager; private ContentItemManager itemManager;
@ -335,7 +343,7 @@ public class FolderBrowserController {
} }
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;
} }
@ -391,11 +399,27 @@ public class FolderBrowserController {
* @param objectId * @param objectId
*/ */
@Transactional(Transactional.TxType.REQUIRED) @Transactional(Transactional.TxType.REQUIRED)
protected void deleteObject(final long objectId) { protected void deleteObject(final String objectId) {
final Optional<CcmObject> object = objectRepo.findById(objectId);
if (object.isPresent()) { Objects.requireNonNull(objectId);
objectRepo.delete(object.get());
if (objectId.startsWith("folder-")) {
final long folderId = Long.parseLong(
objectId.substring("folder-".length()));
folderRepo
.findById(folderId)
.ifPresent(folderRepo::delete);
} else if (objectId.startsWith("item-")) {
final long itemId = Long.parseLong(
objectId.substring("item-".length()));
itemRepo
.findById(itemId)
.ifPresent(itemRepo::delete);
} else {
throw new IllegalArgumentException(
"The objectId is expected to start with 'folder-' or 'item.'.");
} }
} }

View File

@ -98,12 +98,14 @@ class FolderBrowserTableModel implements TableModel {
@Override @Override
public Object getKeyAt(final int columnIndex) { public Object getKeyAt(final int columnIndex) {
// if (currentRow.isFolder()) { if (currentRow.isFolder()) {
// return String.format("folder-%d", currentRow.getObjectId()); return String.format("folder-%d", currentRow.getObjectId());
// } else { } else {
// return String.format("item-%d", currentRow.getObjectId()); return String.format("item-%d", currentRow.getObjectId());
// } }
return currentRow.getObjectId();
// return currentRow.getObjectId();
} }
public boolean isFolder() { public boolean isFolder() {

View File

@ -23,9 +23,13 @@ import org.apache.shiro.subject.Subject;
import java.util.Date; import java.util.Date;
import org.libreccm.auditing.AbstractAuditedEntityRepository; import org.libreccm.auditing.AbstractAuditedEntityRepository;
import org.libreccm.categorization.Categorization;
import org.libreccm.categorization.Category; import org.libreccm.categorization.Category;
import org.libreccm.categorization.CategoryManager;
import org.libreccm.categorization.ObjectNotAssignedToCategoryException;
import org.libreccm.core.CcmObject; import org.libreccm.core.CcmObject;
import org.libreccm.core.CcmObjectRepository; import org.libreccm.core.CcmObjectRepository;
import org.libreccm.core.UnexpectedErrorException;
import java.util.List; import java.util.List;
import java.util.Optional; import java.util.Optional;
@ -39,6 +43,8 @@ import javax.persistence.TypedQuery;
import org.libreccm.security.Shiro; import org.libreccm.security.Shiro;
import org.libreccm.workflow.Workflow; import org.libreccm.workflow.Workflow;
import javax.transaction.Transactional;
/** /**
* Repository for content items. * Repository for content items.
* *
@ -54,6 +60,12 @@ public class ContentItemRepository
@Inject @Inject
private FolderRepository folderRepo; private FolderRepository folderRepo;
@Inject
private ContentItemManager itemManager;
@Inject
private CategoryManager categoryManager;
@Inject @Inject
private Shiro shiro; private Shiro shiro;
@ -372,4 +384,38 @@ public class ContentItemRepository
super.save(item); super.save(item);
} }
@Transactional(Transactional.TxType.REQUIRED)
@Override
public void delete(final ContentItem item) {
if (itemManager.isLive(item)) {
throw new IllegalArgumentException(String.format(
"The provided content item %s can't be deleted because it "
+ "is live.",
item.getItemUuid()));
}
final ContentItem draft = itemManager.getDraftVersion(item,
ContentItem.class);
// draft.getCategories().stream()
// .map(categorization -> categorization.getCategory())
// .forEach(category -> removeCategoryFromItem(item, category));
for(final Categorization categorization : draft.getCategories()) {
final Category category = categorization.getCategory();
removeCategoryFromItem(item, category);
}
super.delete(draft);
}
private void removeCategoryFromItem(final ContentItem item,
final Category category) {
try {
categoryManager.removeObjectFromCategory(item, category);
} catch(ObjectNotAssignedToCategoryException ex) {
throw new UnexpectedErrorException(ex);
}
}
} }

View File

@ -0,0 +1,2 @@
ALTER TABLE ccm_cms.content_items_aud
ALTER COLUMN item_uuid set null;

View File

@ -0,0 +1,2 @@
ALTER TABLE ccm_cms.content_items_aud
ALTER COLUMN item_uuid drop not null;

View File

@ -296,7 +296,6 @@ create schema CCM_CORE;
WORKFLOW_ID bigint, WORKFLOW_ID bigint,
primary key (OBJECT_ID, REV) primary key (OBJECT_ID, REV)
); );
create table CCM_CMS.CONTENT_SECTION_LIFECYCLE_DEFINITIONS ( create table CCM_CMS.CONTENT_SECTION_LIFECYCLE_DEFINITIONS (
CONTENT_SECTION_ID bigint not null, CONTENT_SECTION_ID bigint not null,
LIFECYCLE_DEFINITION_ID bigint not null LIFECYCLE_DEFINITION_ID bigint not null

View File

@ -290,25 +290,27 @@ public class CategoryManager {
return; return;
} }
shiro.getSystemUser().execute(() -> { entityManager.remove(categorization);
object.removeCategory(categorization);
category.removeObject(categorization);
entityManager.remove(categorization);
categoryRepo.save(category);
ccmObjectRepo.save(object);
final List<Categorization> categories = object.getCategories(); // shiro.getSystemUser().execute(() -> {
for (int i = 0; i < categories.size(); i++) { // object.removeCategory(categorization);
categories.get(i).setCategoryOrder(i); // category.removeObject(categorization);
entityManager.merge(categories.get(i)); // entityManager.remove(categorization);
} // categoryRepo.save(category);
// ccmObjectRepo.save(object);
final List<Categorization> objects = category.getObjects(); //
for (int i = 0; i < objects.size(); i++) { // final List<Categorization> categories = object.getCategories();
objects.get(i).setObjectOrder(i); // for (int i = 0; i < categories.size(); i++) {
entityManager.merge(objects.get(i)); // categories.get(i).setCategoryOrder(i);
} // entityManager.merge(categories.get(i));
}); // }
//
// final List<Categorization> objects = category.getObjects();
// for (int i = 0; i < objects.size(); i++) {
// objects.get(i).setObjectOrder(i);
// entityManager.merge(objects.get(i));
// }
// });
} }
/** /**

View File

@ -24,6 +24,7 @@ import org.apache.logging.log4j.Logger;
import java.util.HashMap; import java.util.HashMap;
import java.util.List; import java.util.List;
import java.util.Map; import java.util.Map;
import java.util.Objects;
import java.util.Optional; import java.util.Optional;
import javax.inject.Inject; import javax.inject.Inject;
@ -266,9 +267,9 @@ public abstract class AbstractEntityRepository<K, E> {
*/ */
@Transactional(Transactional.TxType.REQUIRED) @Transactional(Transactional.TxType.REQUIRED)
public void delete(final E entity) { public void delete(final E entity) {
if (entity == null) {
throw new IllegalArgumentException("Can't delete a null entity."); Objects.requireNonNull(entity,
} "Can't delete a null entity.");
//We need to make sure we use a none detached entity, therefore the merge //We need to make sure we use a none detached entity, therefore the merge
entityManager.remove(entityManager.merge(entity)); entityManager.remove(entityManager.merge(entity));

View File

@ -27,6 +27,7 @@ import java.util.UUID;
import javax.enterprise.context.RequestScoped; import javax.enterprise.context.RequestScoped;
import javax.persistence.NoResultException; import javax.persistence.NoResultException;
import javax.persistence.TypedQuery; import javax.persistence.TypedQuery;
import javax.transaction.Transactional;
/** /**
* A repository class for {@link CcmObject}. * A repository class for {@link CcmObject}.
@ -90,4 +91,10 @@ public class CcmObjectRepository extends AbstractEntityRepository<Long, CcmObjec
} }
} }
@Transactional(Transactional.TxType.REQUIRED)
@Override
public void delete(final CcmObject object) {
super.delete(object);
}
} }