. First cut of User Settings page

- will contain useful things like User Info (which can be changed e.g. name and email), Change Password, View Settings etc.
 - Added Change Password page implementation

. Preferences Service for web-client
 - handles and hides away the retrieving and storing properties from the configurable aspect on the current Person
 - simple use case such as: PreferencesService.getPreferences().setValue(name, value);

. Moved Admin Console to title area in main UI page

. Fixed various Admin Console actions to use dialog framework navigation

git-svn-id: https://svn.alfresco.com/repos/alfresco-enterprise/alfresco/HEAD/root@3315 c4b6b30b-aa2e-2d43-bbcb-ca4b014f7261
This commit is contained in:
Kevin Roast
2006-07-13 07:21:02 +00:00
parent 08f4586da7
commit 3f63e8b83b
21 changed files with 737 additions and 104 deletions

View File

@@ -34,10 +34,9 @@ import org.alfresco.service.cmr.repository.NodeRef;
import org.alfresco.service.cmr.repository.NodeService;
import org.alfresco.service.cmr.security.AccessStatus;
import org.alfresco.service.cmr.security.PermissionService;
import org.alfresco.service.namespace.NamespaceService;
import org.alfresco.service.namespace.QName;
import org.alfresco.web.app.Application;
import org.alfresco.web.bean.repository.Node;
import org.alfresco.web.bean.repository.PreferencesService;
import org.alfresco.web.bean.repository.Repository;
import org.alfresco.web.ui.common.Utils;
import org.alfresco.web.ui.common.component.UIActionLink;
@@ -65,7 +64,7 @@ public class UserShortcutsBean
/** List of shortcut nodes */
private List<Node> shortcuts = null;
private QName QNAME_SHORTCUTS = QName.createQName(NamespaceService.APP_MODEL_1_0_URI, "shortcuts");
private String PREF_SHORTCUTS = "shortcuts";
// ------------------------------------------------------------------------------
@@ -113,8 +112,7 @@ public class UserShortcutsBean
tx.begin();
// get the shortcuts from the preferences for this user
prefRef = getShortcutsNodeRef();
shortcuts = (List<String>)this.nodeService.getProperty(prefRef, QNAME_SHORTCUTS);
shortcuts = (List<String>)PreferencesService.getPreferences(context).getValue(PREF_SHORTCUTS);
if (shortcuts != null)
{
// each shortcut node ID is persisted as a list item in a well known property
@@ -184,7 +182,7 @@ public class UserShortcutsBean
{
shortcuts.add(this.shortcuts.get(i).getId());
}
this.nodeService.setProperty(prefRef, QNAME_SHORTCUTS, (Serializable)shortcuts);
PreferencesService.getPreferences().setValue(PREF_SHORTCUTS, (Serializable)shortcuts);
}
catch (Exception err)
{
@@ -246,14 +244,13 @@ public class UserShortcutsBean
tx = Repository.getUserTransaction(context);
tx.begin();
NodeRef prefRef = getShortcutsNodeRef();
List<String> shortcuts = (List<String>)this.nodeService.getProperty(prefRef, QNAME_SHORTCUTS);
List<String> shortcuts = (List<String>)PreferencesService.getPreferences(context).getValue(PREF_SHORTCUTS);
if (shortcuts == null)
{
shortcuts = new ArrayList<String>(1);
}
shortcuts.add(node.getNodeRef().getId());
this.nodeService.setProperty(prefRef, QNAME_SHORTCUTS, (Serializable)shortcuts);
PreferencesService.getPreferences(context).setValue(PREF_SHORTCUTS, (Serializable)shortcuts);
// commit the transaction
tx.commit();
@@ -280,14 +277,6 @@ public class UserShortcutsBean
}
}
/**
* Get the node we need to store our user preferences
*/
private NodeRef getShortcutsNodeRef()
{
return Application.getCurrentUser(FacesContext.getCurrentInstance()).getUserPreferencesRef();
}
/**
* Action handler bound to the user shortcuts Shelf component called when a node is removed
*/
@@ -303,13 +292,12 @@ public class UserShortcutsBean
tx = Repository.getUserTransaction(context);
tx.begin();
NodeRef prefRef = getShortcutsNodeRef();
List<String> shortcuts = (List<String>)this.nodeService.getProperty(prefRef, QNAME_SHORTCUTS);
List<String> shortcuts = (List<String>)PreferencesService.getPreferences(context).getValue(PREF_SHORTCUTS);
if (shortcuts != null && shortcuts.size() > shortcutEvent.Index)
{
// remove the shortcut from the saved list and persist back
shortcuts.remove(shortcutEvent.Index);
this.nodeService.setProperty(prefRef, QNAME_SHORTCUTS, (Serializable)shortcuts);
PreferencesService.getPreferences(context).setValue(PREF_SHORTCUTS, (Serializable)shortcuts);
// commit the transaction
tx.commit();
@@ -380,13 +368,12 @@ public class UserShortcutsBean
tx = Repository.getUserTransaction(context);
tx.begin();
NodeRef prefRef = getShortcutsNodeRef();
List<String> shortcuts = (List<String>)this.nodeService.getProperty(prefRef, QNAME_SHORTCUTS);
List<String> shortcuts = (List<String>)PreferencesService.getPreferences(context).getValue(PREF_SHORTCUTS);
if (shortcuts != null && shortcuts.size() > shortcutEvent.Index)
{
// remove the shortcut from the saved list and persist back
shortcuts.remove(shortcutEvent.Index);
this.nodeService.setProperty(prefRef, QNAME_SHORTCUTS, (Serializable)shortcuts);
PreferencesService.getPreferences(context).setValue(PREF_SHORTCUTS, (Serializable)shortcuts);
// commit the transaction
tx.commit();

View File

@@ -0,0 +1,99 @@
/*
* Copyright (C) 2005 Alfresco, Inc.
*
* Licensed under the Mozilla Public License version 1.1
* with a permitted attribution clause. You may obtain a
* copy of the License at
*
* http://www.alfresco.org/legal/license.txt
*
* Unless required by applicable law or agreed to in writing,
* software distributed under the License is distributed on an
* "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND,
* either express or implied. See the License for the specific
* language governing permissions and limitations under the
* License.
*/
package org.alfresco.web.bean.repository;
import java.io.Serializable;
import java.util.HashMap;
import java.util.Map;
import javax.faces.context.FacesContext;
import org.alfresco.service.cmr.repository.NodeRef;
import org.alfresco.service.cmr.repository.NodeService;
import org.alfresco.service.namespace.NamespaceService;
import org.alfresco.service.namespace.QName;
/**
* Wraps the notion of preferences and settings for a User.
* Caches values until they are overwritten with a new value.
*
* @author Kevin Roast
*/
public final class Preferences
{
private NodeRef preferencesRef;
private NodeService nodeService;
private Map<String, Serializable> cache = new HashMap<String, Serializable>(16, 1.0f);
/**
* Package level constructor
*/
Preferences(NodeRef prefRef)
{
if (prefRef == null)
{
throw new IllegalArgumentException("Preferences NodeRef cannot be null.");
}
this.preferencesRef = prefRef;
}
/**
* Get a serialized preferences value.
*
* @param name Name of the value to retrieve.
*
* @return The value or null if not found/set.
*/
public Serializable getValue(String name)
{
Serializable value = this.cache.get(name);
if (value == null)
{
QName qname = QName.createQName(NamespaceService.APP_MODEL_1_0_URI, name);
value = getNodeService().getProperty(this.preferencesRef, qname);
this.cache.put(name, value);
}
return value;
}
/**
* Set a serialized preference value.
*
* @param name Name of the value to set.
* @param value Value to set.
*/
public void setValue(String name, Serializable value)
{
QName qname = QName.createQName(NamespaceService.APP_MODEL_1_0_URI, name);
// persist the property to the repo
getNodeService().setProperty(this.preferencesRef, qname, value);
// update the cache
this.cache.put(name, value);
}
/**
* @return the NodeService instance.
*/
private NodeService getNodeService()
{
if (this.nodeService == null)
{
this.nodeService = Repository.getServiceRegistry(FacesContext.getCurrentInstance()).getNodeService();
}
return this.nodeService;
}
}

View File

@@ -0,0 +1,63 @@
/*
* Copyright (C) 2005 Alfresco, Inc.
*
* Licensed under the Mozilla Public License version 1.1
* with a permitted attribution clause. You may obtain a
* copy of the License at
*
* http://www.alfresco.org/legal/license.txt
*
* Unless required by applicable law or agreed to in writing,
* software distributed under the License is distributed on an
* "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND,
* either express or implied. See the License for the specific
* language governing permissions and limitations under the
* License.
*/
package org.alfresco.web.bean.repository;
import javax.faces.context.FacesContext;
import org.alfresco.web.app.Application;
/**
* Simple client service to retrieve the Preferences object for the current User.
*
* @author Kevin Roast
*/
public final class PreferencesService
{
/**
* Private constructor
*/
private PreferencesService()
{
}
/**
* @return The Preferences for the current User instance.
*/
public static Preferences getPreferences()
{
return getPreferences(FacesContext.getCurrentInstance());
}
/**
* @param fc FacesContext
* @return The Preferences for the current User instance.
*/
public static Preferences getPreferences(FacesContext fc)
{
User user = Application.getCurrentUser(fc);
return getPreferences(user);
}
/**
* @param user User instance
* @return The Preferences for the current User instance.
*/
public static Preferences getPreferences(User user)
{
return user.getPreferences();
}
}

View File

@@ -45,8 +45,7 @@ public final class User
private String fullName = null;
private Boolean administrator = null;
/** cached ref to our user preferences node */
private NodeRef preferencesFolderRef = null;
private Preferences preferences = null;
/**
* Constructor
@@ -139,63 +138,70 @@ public final class User
return administrator;
}
/**
* @return The Preferences for the User
*/
Preferences getPreferences()
{
if (this.preferences == null)
{
this.preferences = new Preferences(getUserPreferencesRef());
}
return this.preferences;
}
/**
* Get or create the node used to store user preferences.
* Utilises the 'configurable' aspect on the Person linked to this user.
*/
public synchronized NodeRef getUserPreferencesRef()
synchronized NodeRef getUserPreferencesRef()
{
if (this.preferencesFolderRef == null)
FacesContext fc = FacesContext.getCurrentInstance();
ServiceRegistry registry = Repository.getServiceRegistry(fc);
NodeService nodeService = registry.getNodeService();
SearchService searchService = registry.getSearchService();
NamespaceService namespaceService = registry.getNamespaceService();
ConfigurableService configurableService = Repository.getConfigurableService(fc);
NodeRef person = Application.getCurrentUser(fc).getPerson();
if (nodeService.hasAspect(person, ContentModel.ASPECT_CONFIGURABLE) == false)
{
FacesContext fc = FacesContext.getCurrentInstance();
ServiceRegistry registry = Repository.getServiceRegistry(fc);
NodeService nodeService = registry.getNodeService();
SearchService searchService = registry.getSearchService();
NamespaceService namespaceService = registry.getNamespaceService();
ConfigurableService configurableService = Repository.getConfigurableService(fc);
NodeRef person = Application.getCurrentUser(fc).getPerson();
if (nodeService.hasAspect(person, ContentModel.ASPECT_CONFIGURABLE) == false)
{
// create the configuration folder for this Person node
configurableService.makeConfigurable(person);
}
// target of the assoc is the configurations folder ref
NodeRef configRef = configurableService.getConfigurationFolder(person);
if (configRef == null)
{
throw new IllegalStateException("Unable to find associated 'configurations' folder for node: " + person);
}
String xpath = NamespaceService.APP_MODEL_PREFIX + ":" + "preferences";
List<NodeRef> nodes = searchService.selectNodes(
configRef,
xpath,
null,
namespaceService,
false);
NodeRef prefRef;
if (nodes.size() == 1)
{
prefRef = nodes.get(0);
}
else
{
// create the preferences Node for this user
ChildAssociationRef childRef = nodeService.createNode(
configRef,
ContentModel.ASSOC_CONTAINS,
QName.createQName(NamespaceService.APP_MODEL_1_0_URI, "preferences"),
ContentModel.TYPE_CMOBJECT);
prefRef = childRef.getChildRef();
}
this.preferencesFolderRef = prefRef;
// create the configuration folder for this Person node
configurableService.makeConfigurable(person);
}
return this.preferencesFolderRef;
// target of the assoc is the configurations folder ref
NodeRef configRef = configurableService.getConfigurationFolder(person);
if (configRef == null)
{
throw new IllegalStateException("Unable to find associated 'configurations' folder for node: " + person);
}
String xpath = NamespaceService.APP_MODEL_PREFIX + ":" + "preferences";
List<NodeRef> nodes = searchService.selectNodes(
configRef,
xpath,
null,
namespaceService,
false);
NodeRef prefRef;
if (nodes.size() == 1)
{
prefRef = nodes.get(0);
}
else
{
// create the preferences Node for this user
ChildAssociationRef childRef = nodeService.createNode(
configRef,
ContentModel.ASSOC_CONTAINS,
QName.createQName(NamespaceService.APP_MODEL_1_0_URI, "preferences"),
ContentModel.TYPE_CMOBJECT);
prefRef = childRef.getChildRef();
}
return prefRef;
}
}

View File

@@ -59,6 +59,7 @@ public class UsersBean implements IContextListener
private static final String ERROR_USER_DELETE = "error_delete_user_object";
private static final String DEFAULT_OUTCOME = "manageUsers";
private static final String DIALOG_CLOSE = "dialog:close";
/** NodeService bean reference */
protected NodeService nodeService;
@@ -81,6 +82,7 @@ public class UsersBean implements IContextListener
private List<Node> users = Collections.<Node>emptyList();
private String password = null;
private String oldPassword = null;
private String confirm = null;
private String searchCriteria = null;
@@ -208,6 +210,22 @@ public class UsersBean implements IContextListener
{
this.password = password;
}
/**
* @return Returns the old password.
*/
public String getOldPassword()
{
return this.oldPassword;
}
/**
* @param oldPassword The old password to set.
*/
public void setOldPassword(String oldPassword)
{
this.oldPassword = oldPassword;
}
/**
* @return Returns the person context.
@@ -313,7 +331,7 @@ public class UsersBean implements IContextListener
.getCurrentInstance(), ERROR_DELETE), e.getMessage()), e);
}
return DEFAULT_OUTCOME;
return DIALOG_CLOSE;
}
/**
@@ -321,7 +339,7 @@ public class UsersBean implements IContextListener
*/
public String changePasswordOK()
{
String outcome = DEFAULT_OUTCOME;
String outcome = DIALOG_CLOSE;
if (this.password != null && this.confirm != null && this.password.equals(this.confirm))
{
@@ -346,6 +364,39 @@ public class UsersBean implements IContextListener
return outcome;
}
/**
* Action handler called for OK button press on Change My Password screen
* For this screen the user is required to enter their old password - effectively login.
*/
public String changeMyPasswordOK()
{
String outcome = DIALOG_CLOSE;
if (this.password != null && this.confirm != null && this.password.equals(this.confirm))
{
try
{
String userName = (String)this.person.getProperties().get(ContentModel.PROP_USERNAME);
this.authenticationService.updateAuthentication(userName, this.oldPassword.toCharArray(), this.password.toCharArray());
}
catch (Exception e)
{
outcome = null;
Utils.addErrorMessage(MessageFormat.format(Application.getMessage(FacesContext
.getCurrentInstance(), Repository.ERROR_GENERIC), e.getMessage()), e);
}
}
else
{
outcome = null;
Utils.addErrorMessage(Application.getMessage(FacesContext.getCurrentInstance(),
ERROR_PASSWORD_MATCH));
}
return outcome;
}
/**
* Event handler called when the user wishes to search for a user