- New filter for ObjectLists which operates on a category system (either the

one used for the navigation or a secondary one). The filter can also be used 
  for implementing a search for tags (which are in fact categories).
- Some formating


git-svn-id: https://svn.libreccm.org/ccm/trunk@2325 8810af33-2d31-482b-a856-94f89814c4df
master
jensp 2013-09-28 17:05:01 +00:00
parent e209bd4b5e
commit bf25dc8dd2
5 changed files with 360 additions and 217 deletions

View File

@ -649,6 +649,7 @@ public class AuthoringKitWizard extends LayoutPanel implements Resettable {
private final Object m_key;
private Object m_nextKey;
public StepComponent(Object key) {
m_key = key;
}

View File

@ -0,0 +1,144 @@
package com.arsdigita.navigation.ui.object;
import com.arsdigita.categorization.Category;
import com.arsdigita.categorization.CategoryCollection;
import com.arsdigita.domain.DomainObjectFactory;
import com.arsdigita.persistence.CompoundFilter;
import com.arsdigita.persistence.DataCollection;
import com.arsdigita.persistence.FilterFactory;
import com.arsdigita.persistence.SessionManager;
import com.arsdigita.xml.Element;
import java.util.ArrayList;
import java.util.List;
/**
*
* @author Jens Pelzetter <jens@jp-digital.de>
* @version $Id$
*/
public class CategoryFilter {
private final String label;
private final Category filterRootCat;
// private boolean descendCategories = true;
//private String value;
private final List<String> values = new ArrayList<String>();
public static CategoryFilter createCategoryFilter(final String label, final String categoryName) {
final DataCollection collection = SessionManager.getSession().retrieve(
Category.BASE_DATA_OBJECT_TYPE);
collection.addEqualsFilter(Category.NAME, categoryName);
if (collection.next()) {
final Category category = (Category) DomainObjectFactory.newInstance(
collection.getDataObject());
return new CategoryFilter(label, category);
} else {
throw new IllegalArgumentException(String.format(
"A category with the provided name '%s' does not exist", categoryName));
}
}
public CategoryFilter(final String label, final Category filterRootCat) {
this.label = label;
this.filterRootCat = filterRootCat;
}
// public boolean getDescendCategories() {
// return descendCategories;
// }
//
// public void setDescendCategories(final boolean descendCategories) {
// this.descendCategories = descendCategories;
// }
public void applyFilter(final DataCollection objects) {
// for(String value : values) {
// if ((value != null) && !value.isEmpty()) {
// if(descendCategories) {
// com.arsdigita.persistence.Filter filter = objects.addInSubqueryFilter("parent.id",
// "com.arsdigita.categorization.objectIDsInSubtree");
// filter.set("categoryID", value);
// objects.addFilter(filter);
// } else {
// objects.addEqualsFilter("parent.categories.id", value);
// }
// }
// }
if (!values.isEmpty()) {
// if (descendCategories) {
final FilterFactory filterFactory = objects.getFilterFactory();
final CompoundFilter compoundFilter = filterFactory.and();
for (String value : values) {
final com.arsdigita.persistence.Filter filter = filterFactory.in("parent.id",
"com.arsdigita.categorization.objectIDsInSubtree");
filter.set("categoryID", value);
compoundFilter.addFilter(filter);
}
objects.addFilter(compoundFilter);
// com.arsdigita.persistence.Filter filter = objects.addInSubqueryFilter("parent.id",
// "com.arsdigita.categorization.objectIDsInSubtree");
// filter.set("categoryID", values.get(0));
// } else {
// final com.arsdigita.persistence.Filter filter = objects.addFilter(
// "parent.categories.id IN :categories");
// filter.set("categories", values);
//objects.addEqualsFilter("parent.categories.id", values.get(0));
// final FilterFactory filterFactory = objects.getFilterFactory();
// final CompoundFilter compoundFilter = filterFactory.or();
// for (String value : values) {
// final com.arsdigita.persistence.Filter filter = filterFactory.equals(
// "parent.categories.id", value);
// compoundFilter.addFilter(filter);
// }
//
// objects.addFilter(compoundFilter);
// }
}
}
public Element getXml() {
final Element filter = new Element("filter");
filter.addAttribute("name", "categoryFilter");
filter.addAttribute("label", label);
final CategoryCollection categories = filterRootCat.getChildren();
categories.addOrder("name");
Category category;
while (categories.next()) {
category = categories.getCategory();
addCategoryToFilter(filter, category);
}
return filter;
}
private void addCategoryToFilter(final Element parent, final Category category) {
final Element elem = new Element("category");
elem.addAttribute("id", category.getID().toString());
//if ((value != null) && !value.isEmpty() && value.equals(category.getID().toString())) {
if ((values != null) && !values.isEmpty() && values.contains(category.getID().toString())) {
elem.addAttribute("selected", "selected");
}
elem.setText(category.getName());
parent.addContent(elem);
}
public void setValue(final String value) {
if ((value != null) && !value.isEmpty()) {
final String[] tokens = value.split(" ");
for (String token : tokens) {
values.add(token.trim());
}
}
}
}

View File

@ -90,15 +90,15 @@ public class CustomizableObjectList extends ComplexObjectList {
*
*/
private final Map<String, Filter> filters =
new LinkedHashMap<String, Filter>();
//private CategoryFilter categoryFilter;
new LinkedHashMap<String, Filter>();
private CategoryFilter categoryFilter;
/**
* The available sort fields. We use an {@link LinkedHashMap} here to
* preserve the insertation order.
*
*/
private final Map<String, String> sortFields =
new LinkedHashMap<String, String>();
new LinkedHashMap<String, String>();
/**
* Adds a new text filter to the list.
@ -132,17 +132,17 @@ public class CustomizableObjectList extends ComplexObjectList {
*
*/
public CompareFilter addCompareFilter(final String property,
final String label,
final boolean allOption,
final boolean allOptionIsDefault,
final boolean propertyIsNumeric) {
final String label,
final boolean allOption,
final boolean allOptionIsDefault,
final boolean propertyIsNumeric) {
CompareFilter filter;
filter = new CompareFilter(property,
label,
allOption,
allOptionIsDefault,
propertyIsNumeric);
label,
allOption,
allOptionIsDefault,
propertyIsNumeric);
filters.put(label, filter);
return filter;
@ -162,29 +162,30 @@ public class CustomizableObjectList extends ComplexObjectList {
* boolean, boolean, boolean)
*/
public void addSelectFilter(final String property,
final String label,
final boolean reverseOptions,
final boolean allOption,
final boolean allOptionIsDefault,
final boolean propertyIsNumeric) {
final String label,
final boolean reverseOptions,
final boolean allOption,
final boolean allOptionIsDefault,
final boolean propertyIsNumeric) {
SelectFilter filter;
filter = new SelectFilter(property,
label,
this,
reverseOptions,
allOption,
allOptionIsDefault,
propertyIsNumeric);
label,
this,
reverseOptions,
allOption,
allOptionIsDefault,
propertyIsNumeric);
filters.put(label, filter);
}
// public CategoryFilter addCategoryFilter(final String label,
// final String rootCategory) {
// categoryFilter = CategoryFilter.createCategoryFilter(label, rootCategory);
//
// return categoryFilter;
// }
public CategoryFilter addCategoryFilter(final String label,
final String rootCategory) {
categoryFilter = CategoryFilter.createCategoryFilter(label, rootCategory);
return categoryFilter;
}
/**
* Add a sort field option.
*
@ -221,7 +222,7 @@ public class CustomizableObjectList extends ComplexObjectList {
*/
@Override
protected DataCollection getObjects(final HttpServletRequest request,
final HttpServletResponse response) {
final HttpServletResponse response) {
//Set filters (using the SQL)
// final StringBuilder sqlFilters = new StringBuilder();
// for (Map.Entry<String, Filter> filterEntry : filters.entrySet()) {
@ -248,9 +249,9 @@ public class CustomizableObjectList extends ComplexObjectList {
final DataCollection objects = super.getObjects(request, response);
// if ((objects != null) && (categoryFilter != null)) {
// categoryFilter.applyFilter(objects);
// }
if ((objects != null) && (categoryFilter != null)) {
categoryFilter.applyFilter(objects);
}
return objects;
}
@ -259,7 +260,7 @@ public class CustomizableObjectList extends ComplexObjectList {
final StringBuilder sqlFilters = new StringBuilder();
for (Map.Entry<String, Filter> filterEntry : filters.entrySet()) {
if ((filterEntry.getValue().getFilter() == null)
|| (filterEntry.getValue().getFilter().isEmpty())) {
|| (filterEntry.getValue().getFilter().isEmpty())) {
continue;
}
@ -291,7 +292,7 @@ public class CustomizableObjectList extends ComplexObjectList {
*/
@Override
public Element generateXML(final HttpServletRequest request,
final HttpServletResponse response) {
final HttpServletResponse response) {
//Some stuff for the list (copied from ComplexObjectList)
final Element content = Navigation.newElement("customizableObjectList");
@ -327,15 +328,15 @@ public class CustomizableObjectList extends ComplexObjectList {
filterEntry.getValue().setValue(value);
}
}
// if (categoryFilter != null) {
// final String value = Globalization.decodeParameter(request, "categoryFilter");
//
// if ((value != null) && !value.isEmpty()) {
// categoryFilter.setValue(value);
// }
// }
if (categoryFilter != null) {
final String value = Globalization.decodeParameter(request, "categoryFilter");
if (!filters.isEmpty()) {
if ((value != null) && !value.isEmpty()) {
categoryFilter.setValue(value);
}
}
if (!filters.isEmpty() || (categoryFilter != null)) {
final Element controls = content.newChildElement("filterControls");
controls.addAttribute("customName", m_customName);
@ -344,9 +345,9 @@ public class CustomizableObjectList extends ComplexObjectList {
for (Map.Entry<String, Filter> filterEntry : filters.entrySet()) {
filterElems.addContent(filterEntry.getValue().getXml());
}
// if (categoryFilter != null) {
// filterElems.addContent(categoryFilter.getXml());
// }
if (categoryFilter != null) {
filterElems.addContent(categoryFilter.getXml());
}
if (!sortFields.isEmpty()) {
//Look for a sort parameter. If one is found, use one to sort the data
@ -371,4 +372,5 @@ public class CustomizableObjectList extends ComplexObjectList {
return content;
}
}

View File

@ -12,7 +12,6 @@
* rights and limitations under the License.
*
*/
package com.arsdigita.portalworkspace.ui.admin;
import com.arsdigita.bebop.Form;
@ -27,8 +26,6 @@ import com.arsdigita.portalworkspace.WorkspacePage;
import org.apache.log4j.Logger;
/**
* Entry page for PortalWorkspace administration.
*
@ -41,95 +38,97 @@ import org.apache.log4j.Logger;
*/
public class AdminPane extends SimpleContainer {
private static final Logger s_log = Logger.getLogger(AdminPane.class);
private static final Logger s_log = Logger.getLogger(AdminPane.class);
private ApplicationSelectionModel m_app;
private ApplicationSelectionModel m_app;
private CategoryComponent m_catComponent;
private DeleteApplicationComponent m_deleteApplicationComponent;
private CategoryComponent m_catComponent;
private DeleteApplicationComponent m_deleteApplicationComponent;
/**
/**
*
*/
public AdminPane() {
setTag("portal:admin");
setNamespace(WorkspacePage.PORTAL_XML_NS);
m_app = new ApplicationSelectionModel("application", true);
setNamespace(WorkspacePage.PORTAL_XML_NS);
m_app = new ApplicationSelectionModel("application", true);
/* Add component to select a Navigation Category for this portal */
m_catComponent = new CategoryComponent(m_app);
m_catComponent.setIdAttr("categoryComponent");
add(m_catComponent);
m_catComponent.setIdAttr("categoryComponent");
add(m_catComponent);
/* Add component "Extrem Action": Delete this portal */
m_deleteApplicationComponent = new DeleteApplicationComponent(m_app,
m_app.getDefaultApplication().getApplicationType());
m_deleteApplicationComponent.setIdAttr("deleteComponent");
add(m_deleteApplicationComponent);
m_deleteApplicationComponent = new DeleteApplicationComponent(m_app,
m_app.getDefaultApplication().
getApplicationType());
m_deleteApplicationComponent.setIdAttr("deleteComponent");
add(m_deleteApplicationComponent);
/* Add component to manage Members group members for this portal */
GroupMemberDisplay members = new GroupMemberDisplay() {
public Group getGroup(PageState state) {
Workspace workspace = (Workspace) Kernel.getContext()
.getResource();
return (Group) workspace.getParty();
}
};
members.setIdAttr("memberDisplay");
add(members);
GroupMemberDisplay members = new GroupMemberDisplay() {
public Group getGroup(PageState state) {
Workspace workspace = (Workspace) Kernel.getContext()
.getResource();
return (Group) workspace.getParty();
}
Form form = new Form("userPicker", new SimpleContainer(
"portal:memberPicker", WorkspacePage.PORTAL_XML_NS));
form.add(new GroupMemberPicker() {
public Group getGroup(PageState state) {
Workspace workspace = (Workspace) Kernel.getContext()
.getResource();
return (Group) workspace.getParty();
}
});
form.setIdAttr("memberUserPicker");
add(form);
};
members.setIdAttr("memberDisplay");
add(members);
Form form = new Form("userPicker", new SimpleContainer(
"portal:memberPicker", WorkspacePage.PORTAL_XML_NS));
form.add(new GroupMemberPicker() {
public Group getGroup(PageState state) {
Workspace workspace = (Workspace) Kernel.getContext()
.getResource();
return (Group) workspace.getParty();
}
});
form.setIdAttr("memberUserPicker");
add(form);
/* Add component to manage Admins group members for this portal */
GroupMemberDisplay admins = new GroupMemberDisplay() {
public Group getGroup(PageState state) {
Workspace workspace = (Workspace) Kernel.getContext()
.getResource();
Group members = ((Group) workspace.getParty());
Role admins = members.getRole("Administrators");
if (admins == null) {
admins = members.createRole("Administrators");
admins.save();
}
return admins.getGroup();
}
};
admins.setIdAttr("adminDisplay");
add(admins);
GroupMemberDisplay admins = new GroupMemberDisplay() {
public Group getGroup(PageState state) {
Workspace workspace = (Workspace) Kernel.getContext()
.getResource();
Group members = ((Group) workspace.getParty());
Role admins = members.getRole("Administrators");
if (admins == null) {
admins = members.createRole("Administrators");
admins.save();
}
return admins.getGroup();
}
};
admins.setIdAttr("adminDisplay");
add(admins);
Form adminForm = new Form("adminPicker", new SimpleContainer(
"portal:adminPicker", WorkspacePage.PORTAL_XML_NS));
adminForm.add(new GroupMemberPicker() {
public Group getGroup(PageState state) {
Workspace workspace = (Workspace) Kernel.getContext()
.getResource();
Group members = ((Group) workspace.getParty());
Role admins = members.getRole("Administrators");
if (admins == null) {
admins = members.createRole("Administrators");
admins.save();
}
return admins.getGroup();
}
});
adminForm.setIdAttr("adminUserPicker");
add(adminForm);
}
Form adminForm = new Form("adminPicker", new SimpleContainer(
"portal:adminPicker", WorkspacePage.PORTAL_XML_NS));
adminForm.add(new GroupMemberPicker() {
public Group getGroup(PageState state) {
Workspace workspace = (Workspace) Kernel.getContext()
.getResource();
Group members = ((Group) workspace.getParty());
Role admins = members.getRole("Administrators");
if (admins == null) {
admins = members.createRole("Administrators");
admins.save();
}
return admins.getGroup();
}
});
adminForm.setIdAttr("adminUserPicker");
add(adminForm);
}
}

View File

@ -15,7 +15,6 @@
* License along with this library; if not, write to the Free Software
* Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
*/
package com.arsdigita.portalworkspace.ui.admin;
import com.arsdigita.portalworkspace.ui.sitemap.ApplicationSelectionModel;
@ -50,126 +49,124 @@ import com.arsdigita.web.Web;
*/
public class CategoryComponent extends SimpleContainer {
private static final Logger s_log = Logger
.getLogger(CategoryComponent.class);
private static final Logger s_log = Logger
.getLogger(CategoryComponent.class);
private ACSObjectSelectionModel m_catModel;
private CategoryTree m_tree;
private ApplicationSelectionModel m_appModel;
private Label m_error;
private static final Application m_app = Web.getContext().getApplication();
private static final Category m_root = Category.getRootForObject(m_app);
private ACSObjectSelectionModel m_catModel;
private CategoryTree m_tree;
private ApplicationSelectionModel m_appModel;
private Label m_error;
private static final Application m_app = Web.getContext().getApplication();
private static final Category m_root = Category.getRootForObject(m_app);
/**
/**
*
* @param appModel
*/
public CategoryComponent(ApplicationSelectionModel appModel) {
// this model means that the server needs a restart
// if you want to map a category to this personal portal
// AND vice versa - if you remove a domain mapping you need to
// restart the server otherwise you will get an exception next time
// this Component is viewed.
if (m_root != null) {
setNamespace(WorkspacePage.PORTAL_XML_NS);
setTag("portal:categoryPanel");
// this model means that the server needs a restart
// if you want to map a category to this personal portal
// AND vice versa - if you remove a domain mapping you need to
// restart the server otherwise you will get an exception next time
// this Component is viewed.
if (m_root != null) {
setNamespace(WorkspacePage.PORTAL_XML_NS);
setTag("portal:categoryPanel");
m_appModel = appModel;
m_appModel = appModel;
m_catModel = new ACSObjectSelectionModel("category");
m_tree = new CategoryTree(m_catModel);
m_catModel = new ACSObjectSelectionModel("category");
m_tree = new CategoryTree(m_catModel);
add(m_tree);
add(new CategoryTable(appModel, m_catModel));
add(m_tree);
add(new CategoryTable(appModel, m_catModel));
m_error = new Label("");
add(m_error);
}
}
m_error = new Label("");
add(m_error);
}
}
/**
/**
*
*/
private class CategoryTree extends Tree {
public CategoryTree(ACSObjectSelectionModel categoryModel) {
super(new SectionTreeModelBuilder());
setSelectionModel(categoryModel);
addActionListener(new CategoryTreeActionListener(categoryModel));
}
}
public CategoryTree(ACSObjectSelectionModel categoryModel) {
super(new SectionTreeModelBuilder());
setSelectionModel(categoryModel);
addActionListener(new CategoryTreeActionListener(categoryModel));
}
/**
}
/**
*
*/
private class CategoryTreeActionListener implements ActionListener {
private ACSObjectSelectionModel m_catModel;
public CategoryTreeActionListener(ACSObjectSelectionModel catModel) {
m_catModel = catModel;
}
private ACSObjectSelectionModel m_catModel;
public void actionPerformed(ActionEvent event) {
PageState state = event.getPageState();
// categorize the Application
s_log.debug("action performed");
if (m_catModel.isSelected(state)) {
Category category = (Category) m_catModel
.getSelectedObject(state);
public CategoryTreeActionListener(ACSObjectSelectionModel catModel) {
m_catModel = catModel;
}
// Make sure that other workspaces aren't already categorized
DataCollection workspaces = SessionManager.getSession()
.retrieve(Workspace.BASE_DATA_OBJECT_TYPE);
public void actionPerformed(ActionEvent event) {
PageState state = event.getPageState();
// categorize the Application
s_log.debug("action performed");
if (m_catModel.isSelected(state)) {
Category category = (Category) m_catModel
.getSelectedObject(state);
Filter f = workspaces.addInSubqueryFilter("id",
"com.arsdigita.categorization.immediateChildObjectIDs");
f.set("categoryID", category.getID().toString());
// Make sure that other workspaces aren't already categorized
DataCollection workspaces = SessionManager.getSession()
.retrieve(Workspace.BASE_DATA_OBJECT_TYPE);
if (workspaces.isEmpty()) {
s_log.debug("About to categorize");
Filter f = workspaces.addInSubqueryFilter("id",
"com.arsdigita.categorization.immediateChildObjectIDs");
f.set("categoryID", category.getID().toString());
Workspace workspace = (Workspace) m_appModel
.getSelectedObject(state);
category.addChild(workspace);
category.save();
} else {
// print an error
while (workspaces.next()) {
Workspace wk = (Workspace) DomainObjectFactory
.newInstance(workspaces.getDataObject());
m_error.setLabel(
"This category already has a workspace "
+ wk.getTitle(), state);
}
}
}
}
}
if (workspaces.isEmpty()) {
s_log.debug("About to categorize");
/**
* A TreeModelBuilder that loads the tree from the current category
*/
private static class SectionTreeModelBuilder extends LockableImpl implements
TreeModelBuilder {
Workspace workspace = (Workspace) m_appModel
.getSelectedObject(state);
category.addChild(workspace);
category.save();
} else {
// print an error
while (workspaces.next()) {
Workspace wk = (Workspace) DomainObjectFactory
.newInstance(workspaces.getDataObject());
m_error.setLabel(
"This category already has a workspace "
+ wk.getTitle(), state);
}
}
}
}
public SectionTreeModelBuilder() {
super();
}
}
public TreeModel makeModel(Tree t, PageState s) {
Application app = Web.getContext().getApplication();
Category root = null;
while (app != null && root == null) {
root = Category.getRootForObject(app);
app = (Application) app.getParentResource();
}
Assert.exists(root, Category.class);
return new CategoryTreeModelLite(root);
}
}
/**
* A TreeModelBuilder that loads the tree from the current category
*/
private static class SectionTreeModelBuilder extends LockableImpl implements
TreeModelBuilder {
public SectionTreeModelBuilder() {
super();
}
public TreeModel makeModel(Tree t, PageState s) {
Application app = Web.getContext().getApplication();
Category root = null;
while (app != null && root == null) {
root = Category.getRootForObject(app);
app = (Application) app.getParentResource();
}
Assert.exists(root, Category.class);
return new CategoryTreeModelLite(root);
}
}
}