From 727a852dcd2a6e80b11ae71ca37f50d202baae5c Mon Sep 17 00:00:00 2001 From: Mathieu Baudier Date: Fri, 18 Sep 2009 11:36:21 +0000 Subject: [PATCH] Role DAO git-svn-id: https://svn.argeo.org/commons/trunk@2965 4cfe0d0a-d680-48aa-b62c-e0a02a3f76cc --- .../log4j.properties | 2 + .../META-INF/spring/dao.xml | 4 ++ .../META-INF/spring/ldap.xml | 3 +- .../META-INF/spring/osgi.xml | 1 + .../META-INF/MANIFEST.MF | 7 +- .../WEB-INF/osgi.xml | 1 + .../WEB-INF/security-servlet.xml | 9 ++- .../java/org/argeo/security/dao/RoleDao.java | 7 +- .../java/org/argeo/security/dao/UserDao.java | 10 ++- .../ldap/ArgeoLdapAuthoritiesPopulator.java | 57 ++++++++++++++++ .../org/argeo/security/ldap/RoleDaoLdap.java | 62 +++++++++++++++++ .../org/argeo/security/ldap/UserDaoLdap.java | 67 ++++++++----------- .../security/mvc/UsersRolesController.java | 39 ++++++++--- .../org/argeo/server/ServerDeserializer.java | 7 ++ .../org/argeo/server/ServerSerializer.java | 9 +++ .../mvc/DefaultHandlerExceptionResolver.java | 20 ++++++ .../org/argeo/server/mvc/MvcConstants.java | 5 ++ .../org/argeo/server/mvc/SerializingView.java | 54 +++++++++++++++ .../server/mvc/SerializingViewResolver.java | 24 +++++++ .../argeo/server/json/JsonServerMapper.java | 53 +++++++++++++++ .../org/argeo/server/json/mvc/JsonView.java | 57 ---------------- .../server/json/mvc/JsonViewResolver.java | 18 ----- 22 files changed, 381 insertions(+), 135 deletions(-) create mode 100644 security/runtime/org.argeo.security.core/src/main/java/org/argeo/security/ldap/ArgeoLdapAuthoritiesPopulator.java create mode 100644 security/runtime/org.argeo.security.core/src/main/java/org/argeo/security/ldap/RoleDaoLdap.java create mode 100644 server/runtime/org.argeo.server.core/src/main/java/org/argeo/server/ServerDeserializer.java create mode 100644 server/runtime/org.argeo.server.core/src/main/java/org/argeo/server/ServerSerializer.java create mode 100644 server/runtime/org.argeo.server.core/src/main/java/org/argeo/server/mvc/DefaultHandlerExceptionResolver.java create mode 100644 server/runtime/org.argeo.server.core/src/main/java/org/argeo/server/mvc/MvcConstants.java create mode 100644 server/runtime/org.argeo.server.core/src/main/java/org/argeo/server/mvc/SerializingView.java create mode 100644 server/runtime/org.argeo.server.core/src/main/java/org/argeo/server/mvc/SerializingViewResolver.java create mode 100644 server/runtime/org.argeo.server.json/src/main/java/org/argeo/server/json/JsonServerMapper.java delete mode 100644 server/runtime/org.argeo.server.json/src/main/java/org/argeo/server/json/mvc/JsonView.java delete mode 100644 server/runtime/org.argeo.server.json/src/main/java/org/argeo/server/json/mvc/JsonViewResolver.java diff --git a/security/demo/org.argeo.security.demo.log4j/log4j.properties b/security/demo/org.argeo.security.demo.log4j/log4j.properties index 75aa47799..c9d2a9118 100644 --- a/security/demo/org.argeo.security.demo.log4j/log4j.properties +++ b/security/demo/org.argeo.security.demo.log4j/log4j.properties @@ -10,6 +10,8 @@ log4j.logger.org.springframework=WARN #log4j.logger.org.springframework.jms=WARN log4j.logger.org.springframework.security=DEBUG +log4j.org.apache.directory=ERROR + log4j.logger.org.apache.catalina=INFO log4j.logger.org.apache.coyote=INFO log4j.logger.org.apache.tomcat=INFO diff --git a/security/modules/org.argeo.security.manager.ldap/META-INF/spring/dao.xml b/security/modules/org.argeo.security.manager.ldap/META-INF/spring/dao.xml index a1c99f6fd..6d50a5537 100644 --- a/security/modules/org.argeo.security.manager.ldap/META-INF/spring/dao.xml +++ b/security/modules/org.argeo.security.manager.ldap/META-INF/spring/dao.xml @@ -8,6 +8,10 @@ + + + + diff --git a/security/modules/org.argeo.security.manager.ldap/META-INF/spring/ldap.xml b/security/modules/org.argeo.security.manager.ldap/META-INF/spring/ldap.xml index 22fd5baff..2867ad2c2 100644 --- a/security/modules/org.argeo.security.manager.ldap/META-INF/spring/ldap.xml +++ b/security/modules/org.argeo.security.manager.ldap/META-INF/spring/ldap.xml @@ -52,8 +52,7 @@ - + diff --git a/security/modules/org.argeo.security.manager.ldap/META-INF/spring/osgi.xml b/security/modules/org.argeo.security.manager.ldap/META-INF/spring/osgi.xml index 9b7f38bef..76d63766c 100644 --- a/security/modules/org.argeo.security.manager.ldap/META-INF/spring/osgi.xml +++ b/security/modules/org.argeo.security.manager.ldap/META-INF/spring/osgi.xml @@ -10,4 +10,5 @@ interface="org.springframework.security.AuthenticationManager" /> + \ No newline at end of file diff --git a/security/modules/org.argeo.security.webapp/META-INF/MANIFEST.MF b/security/modules/org.argeo.security.webapp/META-INF/MANIFEST.MF index c7d3bc804..35682dd8e 100644 --- a/security/modules/org.argeo.security.webapp/META-INF/MANIFEST.MF +++ b/security/modules/org.argeo.security.webapp/META-INF/MANIFEST.MF @@ -3,14 +3,15 @@ Bundle-Version: 0.1.1.SNAPSHOT Import-Package: javax.servlet, javax.servlet.http, javax.servlet.resources, + org.argeo.security.dao, org.argeo.security.mvc, - org.argeo.server.json.mvc, + org.argeo.server.json, + org.argeo.server.mvc, org.springframework.ldap.core.support, org.springframework.osgi.web.context.support, org.springframework.security, org.springframework.web.context, org.springframework.web.context.support, org.springframework.web.filter, - org.springframework.web.servlet, - org.argeo.security.dao + org.springframework.web.servlet Web-ContextPath: org.argeo.security.webapp diff --git a/security/modules/org.argeo.security.webapp/WEB-INF/osgi.xml b/security/modules/org.argeo.security.webapp/WEB-INF/osgi.xml index d7152f8cc..22cec14a5 100644 --- a/security/modules/org.argeo.security.webapp/WEB-INF/osgi.xml +++ b/security/modules/org.argeo.security.webapp/WEB-INF/osgi.xml @@ -10,5 +10,6 @@ interface="org.springframework.security.AuthenticationManager" /> + \ No newline at end of file diff --git a/security/modules/org.argeo.security.webapp/WEB-INF/security-servlet.xml b/security/modules/org.argeo.security.webapp/WEB-INF/security-servlet.xml index 875113d74..b2938510a 100644 --- a/security/modules/org.argeo.security.webapp/WEB-INF/security-servlet.xml +++ b/security/modules/org.argeo.security.webapp/WEB-INF/security-servlet.xml @@ -11,9 +11,16 @@ + - + + + + + + + \ No newline at end of file diff --git a/security/runtime/org.argeo.security.core/src/main/java/org/argeo/security/dao/RoleDao.java b/security/runtime/org.argeo.security.core/src/main/java/org/argeo/security/dao/RoleDao.java index 3b0b7ef7e..dc6f3a6ab 100644 --- a/security/runtime/org.argeo.security.core/src/main/java/org/argeo/security/dao/RoleDao.java +++ b/security/runtime/org.argeo.security.core/src/main/java/org/argeo/security/dao/RoleDao.java @@ -2,13 +2,12 @@ package org.argeo.security.dao; import java.util.List; -import org.argeo.security.ArgeoUser; - public interface RoleDao { - public List listRoles(); + public List listEditableRoles(); public void create(String role); - public List listUserRoles(ArgeoUser user); + public void delete(String role); + } diff --git a/security/runtime/org.argeo.security.core/src/main/java/org/argeo/security/dao/UserDao.java b/security/runtime/org.argeo.security.core/src/main/java/org/argeo/security/dao/UserDao.java index 7227bd860..859da1b72 100644 --- a/security/runtime/org.argeo.security.core/src/main/java/org/argeo/security/dao/UserDao.java +++ b/security/runtime/org.argeo.security.core/src/main/java/org/argeo/security/dao/UserDao.java @@ -12,11 +12,15 @@ public interface UserDao { public void update(ArgeoUser user); public void delete(String username); - + public void updatePassword(String oldPassword, String newPassword); - + public Boolean userExists(String username); - public ArgeoUser getUser(String uname); + public ArgeoUser getUser(String username); + + public void addRoles(String username, List roles); + + public void removeRoles(String username, List roles); } diff --git a/security/runtime/org.argeo.security.core/src/main/java/org/argeo/security/ldap/ArgeoLdapAuthoritiesPopulator.java b/security/runtime/org.argeo.security.core/src/main/java/org/argeo/security/ldap/ArgeoLdapAuthoritiesPopulator.java new file mode 100644 index 000000000..9df6ed4a7 --- /dev/null +++ b/security/runtime/org.argeo.security.core/src/main/java/org/argeo/security/ldap/ArgeoLdapAuthoritiesPopulator.java @@ -0,0 +1,57 @@ +package org.argeo.security.ldap; + +import org.springframework.ldap.core.ContextSource; +import org.springframework.security.ldap.populator.DefaultLdapAuthoritiesPopulator; + +/** TODO: notify Spring Security to open this class more. */ +public class ArgeoLdapAuthoritiesPopulator extends + DefaultLdapAuthoritiesPopulator { + + /* Hacked from parent class */ + private String groupRoleAttribute = "cn"; + private final String groupSearchBase; + private String rolePrefix = "ROLE_"; + private boolean convertToUpperCase = true; + + public ArgeoLdapAuthoritiesPopulator(ContextSource contextSource, + String groupSearchBase) { + super(contextSource, groupSearchBase); + this.groupSearchBase = groupSearchBase; + } + + @Override + public void setConvertToUpperCase(boolean convertToUpperCase) { + super.setConvertToUpperCase(convertToUpperCase); + this.convertToUpperCase = convertToUpperCase; + } + + @Override + public void setGroupRoleAttribute(String groupRoleAttribute) { + super.setGroupRoleAttribute(groupRoleAttribute); + this.groupRoleAttribute = groupRoleAttribute; + } + + @Override + public void setRolePrefix(String rolePrefix) { + super.setRolePrefix(rolePrefix); + this.rolePrefix = rolePrefix; + } + + /** Hacked from parent class. */ + public String convertGroupToRole(String groupName) { + if (convertToUpperCase) { + groupName = groupName.toUpperCase(); + } + + return rolePrefix + groupName; + } + + public String getGroupRoleAttribute() { + return groupRoleAttribute; + } + + public String getGroupSearchBase() { + return groupSearchBase; + } + +} diff --git a/security/runtime/org.argeo.security.core/src/main/java/org/argeo/security/ldap/RoleDaoLdap.java b/security/runtime/org.argeo.security.core/src/main/java/org/argeo/security/ldap/RoleDaoLdap.java new file mode 100644 index 000000000..7a40a3faa --- /dev/null +++ b/security/runtime/org.argeo.security.core/src/main/java/org/argeo/security/ldap/RoleDaoLdap.java @@ -0,0 +1,62 @@ +package org.argeo.security.ldap; + +import java.util.List; + +import javax.naming.Name; + +import org.argeo.security.dao.RoleDao; +import org.springframework.ldap.core.ContextMapper; +import org.springframework.ldap.core.ContextSource; +import org.springframework.ldap.core.DirContextAdapter; +import org.springframework.ldap.core.DistinguishedName; +import org.springframework.ldap.core.LdapTemplate; + +public class RoleDaoLdap implements RoleDao { + + private ArgeoLdapAuthoritiesPopulator authoritiesPopulator; + private final LdapTemplate ldapTemplate; + + public RoleDaoLdap(ContextSource contextSource) { + ldapTemplate = new LdapTemplate(contextSource); + } + + public void create(String role) { + Name dn = buildDn(role); + DirContextAdapter context = new DirContextAdapter(); + context.setAttributeValues("objectClass", new String[] { "top", + "groupOfUniqueNames" }); + context.setAttributeValue("cn", role); + ldapTemplate.bind(dn, context, null); + } + + @SuppressWarnings("unchecked") + public List listEditableRoles() { + return (List) ldapTemplate.listBindings(authoritiesPopulator + .getGroupSearchBase(), new ContextMapper() { + public Object mapFromContext(Object ctxArg) { + String groupName = ((DirContextAdapter) ctxArg) + .getStringAttribute(authoritiesPopulator + .getGroupRoleAttribute()); + String roleName = authoritiesPopulator + .convertGroupToRole(groupName); + return roleName; + } + }); + } + + public void delete(String role) { + // TODO Auto-generated method stub + + } + + public void setAuthoritiesPopulator( + ArgeoLdapAuthoritiesPopulator ldapAuthoritiesPopulator) { + this.authoritiesPopulator = ldapAuthoritiesPopulator; + } + + protected Name buildDn(String name) { + return new DistinguishedName("cn=" + name + "," + + authoritiesPopulator.getGroupSearchBase()); + } + +} diff --git a/security/runtime/org.argeo.security.core/src/main/java/org/argeo/security/ldap/UserDaoLdap.java b/security/runtime/org.argeo.security.core/src/main/java/org/argeo/security/ldap/UserDaoLdap.java index 18b47cf6a..110d1e650 100644 --- a/security/runtime/org.argeo.security.core/src/main/java/org/argeo/security/ldap/UserDaoLdap.java +++ b/security/runtime/org.argeo.security.core/src/main/java/org/argeo/security/ldap/UserDaoLdap.java @@ -2,14 +2,8 @@ package org.argeo.security.ldap; import java.util.ArrayList; import java.util.List; -import java.util.Set; -import javax.naming.NamingException; - -import org.apache.commons.logging.Log; -import org.apache.commons.logging.LogFactory; import org.argeo.security.ArgeoUser; -import org.argeo.security.BasicArgeoUser; import org.argeo.security.core.ArgeoUserDetails; import org.argeo.security.dao.UserDao; import org.springframework.ldap.core.ContextMapper; @@ -17,16 +11,17 @@ import org.springframework.ldap.core.ContextSource; import org.springframework.ldap.core.DirContextAdapter; import org.springframework.ldap.core.DistinguishedName; import org.springframework.ldap.core.LdapTemplate; -import org.springframework.security.ldap.populator.DefaultLdapAuthoritiesPopulator; +import org.springframework.security.GrantedAuthority; +import org.springframework.security.GrantedAuthorityImpl; import org.springframework.security.userdetails.UserDetails; import org.springframework.security.userdetails.UserDetailsManager; public class UserDaoLdap implements UserDao { - private final static Log log = LogFactory.getLog(UserDaoLdap.class); + // private final static Log log = LogFactory.getLog(UserDaoLdap.class); private UserDetailsManager userDetailsManager; - private DefaultLdapAuthoritiesPopulator authoritiesPopulator; private String userBase = "ou=users"; + private String usernameAttribute = "uid"; private final LdapTemplate ldapTemplate; @@ -35,7 +30,7 @@ public class UserDaoLdap implements UserDao { } public void create(ArgeoUser user) { - userDetailsManager.createUser((UserDetails) user); + userDetailsManager.createUser(new ArgeoUserDetails(user)); } public ArgeoUser getUser(String uname) { @@ -45,7 +40,13 @@ public class UserDaoLdap implements UserDao { @SuppressWarnings("unchecked") public List listUsers() { List usernames = (List) ldapTemplate.listBindings( - new DistinguishedName(userBase), new UserContextMapper()); + new DistinguishedName(userBase), new ContextMapper() { + public Object mapFromContext(Object ctxArg) { + DirContextAdapter ctx = (DirContextAdapter) ctxArg; + return ctx.getStringAttribute(usernameAttribute); + } + }); + List lst = new ArrayList(); for (String username : usernames) { UserDetails userDetails = userDetailsManager @@ -71,41 +72,29 @@ public class UserDaoLdap implements UserDao { return userDetailsManager.userExists(username); } - public void setUserDetailsManager(UserDetailsManager userDetailsManager) { - this.userDetailsManager = userDetailsManager; + public void addRoles(String username, List roles) { + GrantedAuthority[] auths = new GrantedAuthority[roles.size()]; + for (int i = 0; i < roles.size(); i++) + auths[i] = new GrantedAuthorityImpl(roles.get(i)); + ArgeoUserDetails user = (ArgeoUserDetails) userDetailsManager + .loadUserByUsername(username); + throw new UnsupportedOperationException(); + //userDetailsManager. + } + + public void removeRoles(String username, List roles) { + throw new UnsupportedOperationException(); } - public void setAuthoritiesPopulator( - DefaultLdapAuthoritiesPopulator authoritiesPopulator) { - this.authoritiesPopulator = authoritiesPopulator; + public void setUserDetailsManager(UserDetailsManager userDetailsManager) { + this.userDetailsManager = userDetailsManager; } public void setUserBase(String userBase) { this.userBase = userBase; } - class UserContextMapper implements ContextMapper { - public Object mapFromContext(Object ctxArg) { - DirContextAdapter ctx = (DirContextAdapter) ctxArg; - // BasicArgeoUser user = new BasicArgeoUser(); - return ctx.getStringAttribute("uid"); - - // log.debug("dn# " + ctx.getDn()); - // log.debug("NameInNamespace# " + ctx.getNameInNamespace()); - // log.debug("toString# " + ctx.toString()); - - // Set roles = authoritiesPopulator.getGroupMembershipRoles( - // ctx.composeName(user.getUsername(), userBase), user - // .getUsername()); - // user.setRoles(new ArrayList(roles)); - // GrantedAuthority[] auths = authoritiesPopulator - // .getGrantedAuthorities(ldapTemplate., - // user.getUsername()); - // for (GrantedAuthority auth : auths) { - // user.getRoles().add(auth.getAuthority()); - // } - // return user; - } + public void setUsernameAttribute(String usernameAttribute) { + this.usernameAttribute = usernameAttribute; } - } diff --git a/security/runtime/org.argeo.security.mvc/src/main/java/org/argeo/security/mvc/UsersRolesController.java b/security/runtime/org.argeo.security.mvc/src/main/java/org/argeo/security/mvc/UsersRolesController.java index 505f0094f..4b91075ce 100644 --- a/security/runtime/org.argeo.security.mvc/src/main/java/org/argeo/security/mvc/UsersRolesController.java +++ b/security/runtime/org.argeo.security.mvc/src/main/java/org/argeo/security/mvc/UsersRolesController.java @@ -8,6 +8,7 @@ import org.argeo.security.dao.RoleDao; import org.argeo.security.dao.UserDao; import org.argeo.server.BooleanAnswer; import org.argeo.server.ServerAnswer; +import org.argeo.server.mvc.MvcConstants; import org.springframework.security.Authentication; import org.springframework.security.context.SecurityContextHolder; import org.springframework.stereotype.Controller; @@ -16,44 +17,66 @@ import org.springframework.web.bind.annotation.RequestMapping; import org.springframework.web.bind.annotation.RequestParam; @Controller -public class UsersRolesController { +public class UsersRolesController implements MvcConstants { private UserDao userDao; private RoleDao roleDao; + /* USER */ + @RequestMapping("/getCredentials.security") - @ModelAttribute("getCredentials") + @ModelAttribute(ANSWER_MODEL_KEY) public ArgeoUser getCredentials() { Authentication authentication = SecurityContextHolder.getContext() .getAuthentication(); - return ArgeoUserDetails.asArgeoUser(authentication); } @RequestMapping("/getUsersList.security") - @ModelAttribute("getUsersList") + @ModelAttribute(ANSWER_MODEL_KEY) public List getUsersList() { return userDao.listUsers(); } @RequestMapping("/userExists.security") - @ModelAttribute("userExists") + @ModelAttribute(ANSWER_MODEL_KEY) public BooleanAnswer userExists(@RequestParam("username") String username) { return new BooleanAnswer(userDao.userExists(username)); } @RequestMapping("/deleteUser.security") - @ModelAttribute("deleteUser") + @ModelAttribute(ANSWER_MODEL_KEY) public ServerAnswer deleteUser(@RequestParam("username") String username) { userDao.delete(username); - return ServerAnswer.ok(username + " deleted"); + return ServerAnswer.ok("User " + username + " deleted"); } @RequestMapping("/getUserDetails.security") - @ModelAttribute("getUserDetails") + @ModelAttribute(ANSWER_MODEL_KEY) public ArgeoUser getUserDetails(@RequestParam("username") String username) { return userDao.getUser(username); } + /* ROLE */ + @RequestMapping("/getRolesList.security") + @ModelAttribute(ANSWER_MODEL_KEY) + public List getEditableRolesList() { + return roleDao.listEditableRoles(); + } + + @RequestMapping("/createRole.security") + @ModelAttribute(ANSWER_MODEL_KEY) + public ServerAnswer createRole(@RequestParam("role") String role) { + roleDao.create(role); + return ServerAnswer.ok("Role " + role + " created"); + } + + @RequestMapping("/deleteRole.security") + @ModelAttribute(ANSWER_MODEL_KEY) + public ServerAnswer deleteRole(@RequestParam("role") String role) { + roleDao.delete(role); + return ServerAnswer.ok("Role " + role + " created"); + } + public void setUserDao(UserDao userDao) { this.userDao = userDao; } diff --git a/server/runtime/org.argeo.server.core/src/main/java/org/argeo/server/ServerDeserializer.java b/server/runtime/org.argeo.server.core/src/main/java/org/argeo/server/ServerDeserializer.java new file mode 100644 index 000000000..98b7f71eb --- /dev/null +++ b/server/runtime/org.argeo.server.core/src/main/java/org/argeo/server/ServerDeserializer.java @@ -0,0 +1,7 @@ +package org.argeo.server; + +import javax.servlet.http.HttpServletRequest; + +public interface ServerDeserializer { + public Object deserialize(Object obj, HttpServletRequest request); +} diff --git a/server/runtime/org.argeo.server.core/src/main/java/org/argeo/server/ServerSerializer.java b/server/runtime/org.argeo.server.core/src/main/java/org/argeo/server/ServerSerializer.java new file mode 100644 index 000000000..550fa75cc --- /dev/null +++ b/server/runtime/org.argeo.server.core/src/main/java/org/argeo/server/ServerSerializer.java @@ -0,0 +1,9 @@ +package org.argeo.server; + +import javax.servlet.http.HttpServletRequest; +import javax.servlet.http.HttpServletResponse; + +public interface ServerSerializer { + public void serialize(Object obj, HttpServletRequest request, + HttpServletResponse response); +} diff --git a/server/runtime/org.argeo.server.core/src/main/java/org/argeo/server/mvc/DefaultHandlerExceptionResolver.java b/server/runtime/org.argeo.server.core/src/main/java/org/argeo/server/mvc/DefaultHandlerExceptionResolver.java new file mode 100644 index 000000000..d075d3205 --- /dev/null +++ b/server/runtime/org.argeo.server.core/src/main/java/org/argeo/server/mvc/DefaultHandlerExceptionResolver.java @@ -0,0 +1,20 @@ +package org.argeo.server.mvc; + +import javax.servlet.http.HttpServletRequest; +import javax.servlet.http.HttpServletResponse; + +import org.argeo.server.ServerAnswer; +import org.springframework.web.servlet.HandlerExceptionResolver; +import org.springframework.web.servlet.ModelAndView; + +public class DefaultHandlerExceptionResolver implements + HandlerExceptionResolver { + + public ModelAndView resolveException(HttpServletRequest request, + HttpServletResponse response, Object handler, Exception ex) { + ModelAndView mv = new ModelAndView(); + mv.addObject(ServerAnswer.error(ex)); + return mv; + } + +} diff --git a/server/runtime/org.argeo.server.core/src/main/java/org/argeo/server/mvc/MvcConstants.java b/server/runtime/org.argeo.server.core/src/main/java/org/argeo/server/mvc/MvcConstants.java new file mode 100644 index 000000000..78846b0e4 --- /dev/null +++ b/server/runtime/org.argeo.server.core/src/main/java/org/argeo/server/mvc/MvcConstants.java @@ -0,0 +1,5 @@ +package org.argeo.server.mvc; + +public interface MvcConstants { + public final static String ANSWER_MODEL_KEY = "org.argeo.server.mvc.ANSWER"; +} diff --git a/server/runtime/org.argeo.server.core/src/main/java/org/argeo/server/mvc/SerializingView.java b/server/runtime/org.argeo.server.core/src/main/java/org/argeo/server/mvc/SerializingView.java new file mode 100644 index 000000000..6acecf000 --- /dev/null +++ b/server/runtime/org.argeo.server.core/src/main/java/org/argeo/server/mvc/SerializingView.java @@ -0,0 +1,54 @@ +package org.argeo.server.mvc; + +import java.util.Locale; +import java.util.Map; + +import javax.servlet.http.HttpServletRequest; +import javax.servlet.http.HttpServletResponse; + +import org.argeo.server.ArgeoServerException; +import org.argeo.server.ServerSerializer; +import org.springframework.web.servlet.view.AbstractView; + +public class SerializingView extends AbstractView implements MvcConstants { + private final String viewName; + private final Locale locale; + + private final ServerSerializer serializer; + + public SerializingView(String viewName, Locale locale, + ServerSerializer serializer) { + this.viewName = viewName; + this.locale = locale; + this.serializer = serializer; + } + + @SuppressWarnings("unchecked") + @Override + protected void renderMergedOutputModel(Map model, + HttpServletRequest request, HttpServletResponse response) + throws Exception { + final Object answer; + if (model.size() == 1) { + answer = model.values().iterator().next(); + } else if (model.containsKey(ANSWER_MODEL_KEY)) { + answer = model.get(ANSWER_MODEL_KEY); + } else if (model.containsKey(viewName)) { + answer = model.get(viewName); + } else { + throw new ArgeoServerException( + "Model has a size different from 1. Specify a modelKey."); + } + + serializer.serialize(answer, request, response); + } + + public String getViewName() { + return viewName; + } + + public Locale getLocale() { + return locale; + } + +} diff --git a/server/runtime/org.argeo.server.core/src/main/java/org/argeo/server/mvc/SerializingViewResolver.java b/server/runtime/org.argeo.server.core/src/main/java/org/argeo/server/mvc/SerializingViewResolver.java new file mode 100644 index 000000000..26eab418a --- /dev/null +++ b/server/runtime/org.argeo.server.core/src/main/java/org/argeo/server/mvc/SerializingViewResolver.java @@ -0,0 +1,24 @@ +package org.argeo.server.mvc; + +import java.util.Locale; + +import org.argeo.server.ServerSerializer; +import org.springframework.web.servlet.View; +import org.springframework.web.servlet.view.AbstractCachingViewResolver; + +/** + * Returns a {@link SerializingView} based on the underlying. + */ +public class SerializingViewResolver extends AbstractCachingViewResolver { + private ServerSerializer serializer; + + @Override + protected View loadView(String viewName, Locale locale) throws Exception { + return new SerializingView(viewName, locale, serializer); + } + + public void setSerializer(ServerSerializer serializer) { + this.serializer = serializer; + } + +} diff --git a/server/runtime/org.argeo.server.json/src/main/java/org/argeo/server/json/JsonServerMapper.java b/server/runtime/org.argeo.server.json/src/main/java/org/argeo/server/json/JsonServerMapper.java new file mode 100644 index 000000000..4ab128e0b --- /dev/null +++ b/server/runtime/org.argeo.server.json/src/main/java/org/argeo/server/json/JsonServerMapper.java @@ -0,0 +1,53 @@ +package org.argeo.server.json; + +import java.io.BufferedReader; + +import javax.servlet.http.HttpServletRequest; +import javax.servlet.http.HttpServletResponse; + +import org.argeo.server.ArgeoServerException; +import org.argeo.server.ServerDeserializer; +import org.argeo.server.ServerSerializer; +import org.codehaus.jackson.JsonFactory; +import org.codehaus.jackson.JsonGenerator; +import org.codehaus.jackson.map.ObjectMapper; + +public class JsonServerMapper implements ServerSerializer, ServerDeserializer { + private JsonFactory jsonFactory = new JsonFactory(); + private ObjectMapper objectMapper = new ObjectMapper(); + + public void serialize(Object obj, HttpServletRequest request, + HttpServletResponse response) { + try { + response.setContentType("application/json"); + + JsonGenerator jsonGenerator = jsonFactory + .createJsonGenerator(response.getWriter()); + jsonGenerator.useDefaultPrettyPrinter(); + + objectMapper.writeValue(jsonGenerator, obj); + } catch (Exception e) { + throw new ArgeoServerException("Cannot serialize " + obj, e); + } + } + + public Object deserialize(Object obj, HttpServletRequest request) { + try { + String body = request.getParameter("body"); + if (body == null) { + // lets read the message body instead + BufferedReader reader = request.getReader(); + StringBuffer buffer = new StringBuffer(); + String line = null; + while (((line = reader.readLine()) != null)) { + buffer.append(line); + } + body = buffer.toString(); + } + return objectMapper.readValue(body, Object.class); + } catch (Exception e) { + throw new ArgeoServerException("Cannot deserialize " + request, e); + } + } + +} diff --git a/server/runtime/org.argeo.server.json/src/main/java/org/argeo/server/json/mvc/JsonView.java b/server/runtime/org.argeo.server.json/src/main/java/org/argeo/server/json/mvc/JsonView.java deleted file mode 100644 index 2d342e9b3..000000000 --- a/server/runtime/org.argeo.server.json/src/main/java/org/argeo/server/json/mvc/JsonView.java +++ /dev/null @@ -1,57 +0,0 @@ -package org.argeo.server.json.mvc; - -import java.util.Map; - -import javax.servlet.http.HttpServletRequest; -import javax.servlet.http.HttpServletResponse; - -import org.argeo.server.ArgeoServerException; -import org.codehaus.jackson.JsonFactory; -import org.codehaus.jackson.JsonGenerator; -import org.codehaus.jackson.map.ObjectMapper; -import org.springframework.web.servlet.view.AbstractView; - -/** Marshal one of the object of the map to the output. */ -public class JsonView extends AbstractView { - private JsonFactory jsonFactory = new JsonFactory(); - private ObjectMapper objectMapper = new ObjectMapper(); - - private String modelKey = null; - - public JsonView(String modelKey) { - this.modelKey = modelKey; - } - - @Override - @SuppressWarnings(value = { "unchecked" }) - protected void renderMergedOutputModel(Map model, - HttpServletRequest request, HttpServletResponse response) - throws Exception { - final Object answer; - if (model.size() == 1) - answer = model.values().iterator().next(); - else if (modelKey != null) { - if (!model.containsKey(modelKey)) - throw new ArgeoServerException("Key " + modelKey - + " not found in model."); - answer = model.get(modelKey); - } else {// models.size!=1 and no modelKey - throw new ArgeoServerException( - "Model has a size different from 1. Specify a modelKey."); - } - - response.setContentType("application/json"); - - JsonGenerator jsonGenerator = jsonFactory.createJsonGenerator(response - .getWriter()); - jsonGenerator.useDefaultPrettyPrinter(); - - objectMapper.writeValue(jsonGenerator, answer); - - } - - public void setModelKey(String modelKey) { - this.modelKey = modelKey; - } - -} diff --git a/server/runtime/org.argeo.server.json/src/main/java/org/argeo/server/json/mvc/JsonViewResolver.java b/server/runtime/org.argeo.server.json/src/main/java/org/argeo/server/json/mvc/JsonViewResolver.java deleted file mode 100644 index a3b5e0ddb..000000000 --- a/server/runtime/org.argeo.server.json/src/main/java/org/argeo/server/json/mvc/JsonViewResolver.java +++ /dev/null @@ -1,18 +0,0 @@ -package org.argeo.server.json.mvc; - -import java.util.Locale; - -import org.springframework.web.servlet.View; -import org.springframework.web.servlet.view.AbstractCachingViewResolver; - -/** - * Returns a {@link JsonView} based on the underlying. View name is the model - * key of the JSON view. - */ -public class JsonViewResolver extends AbstractCachingViewResolver { - @Override - protected View loadView(String viewName, Locale locale) throws Exception { - return new JsonView(viewName); - } - -} -- 2.30.2