Changeset 2116
- Timestamp:
- 07/31/07 16:00:08 (1 year ago)
- Files:
-
- openmrs-modules/logicws/metadata/config.xml (modified) (2 diffs)
- openmrs-modules/logicws/src/org/openmrs/module/logicws/LogicWSUtil.java (moved) (moved from openmrs-modules/logicws/src/org/openmrs/module/logicws/RestUtil.java) (1 diff)
- openmrs-modules/logicws/src/org/openmrs/module/logicws/advice/LogicWSAdministrationAdvisor.java (modified) (2 diffs)
- openmrs-modules/logicws/web/src/org/openmrs/module/logicws/web/RestServlet.java (modified) (3 diffs)
Legend:
- Unmodified
- Added
- Removed
- Modified
- Copied
- Moved
openmrs-modules/logicws/metadata/config.xml
r2101 r2116 24 24 25 25 26 <!-- Extensions 26 <!-- Extensions 27 27 <extension> 28 28 <point>org.openmrs.admin.list</point> 29 <class> org.openmrs.module.formEntry.extension.html.RestAdminExt</class>29 <class>@MODULE_PACKAGE@.extension.html.AdminList</class> 30 30 </extension> 31 /Extensions -->31 /Extensions --> 32 32 33 33 … … 43 43 <!-- Required Privileges --> 44 44 <privilege> 45 <name>Access RESTAPI</name>46 <description>Allows user to access REST API functions</description>45 <name>Access Logic Web Service API</name> 46 <description>Allows user to access the API of the Logic Web Service</description> 47 47 </privilege> 48 48 <!-- /Required Privileges --> openmrs-modules/logicws/src/org/openmrs/module/logicws/LogicWSUtil.java
r2095 r2116 11 11 * Utility class for miscellaneous convenience functions used by the REST API 12 12 */ 13 public class RestUtil {13 public class LogicWSUtil { 14 14 15 /**16 * Identifier for the REST module17 */18 public final static String MODULE_ID = "logicws";15 /** 16 * Identifier for the REST module 17 */ 18 public final static String MODULE_ID = "logicws"; 19 19 20 /**21 * Name of global property containing list of valid client IP addresses22 */23 public final static String GP_ALLOWED_IP_LIST = MODULE_ID24 + ".allowed_ip_list";20 /** 21 * Name of global property containing list of valid client IP addresses 22 */ 23 public final static String GP_ALLOWED_IP_LIST = MODULE_ID 24 + ".allowed_ip_list"; 25 25 26 /**27 * Maximum number of results to return for any single call (0 for unlimited)28 */29 public final static String GP_MAX_RESULTS = MODULE_ID + ".max_results";26 /** 27 * Maximum number of results to return for any single call (0 for unlimited) 28 */ 29 public final static String GP_MAX_RESULTS = MODULE_ID + ".max_results"; 30 30 31 /** 32 * Length of time (in milliseconds) before refreshing global properties 33 */ 34 public final static long PROPERTY_REFRESH_INTERVAL = 600000; 35 36 /** 37 * Privilege required to access any REST API calls 38 */ 39 public static final String REST_API_PRIVILEGE = "Access REST API"; 31 /** 32 * Length of time (in milliseconds) before refreshing global properties 33 */ 34 public final static long PROPERTY_REFRESH_INTERVAL = 600000; 40 35 41 private static Object lock = new Object(); // used for synchronizing 42 private static List<String[]> allowedIpList = null; 43 private static long propertiesUpdatedTime = 0; 44 private static int maxResults = 0;36 /** 37 * Privilege required to access any Logic Web Service API calls 38 */ 39 public static final String LOGIC_WS_PRIVILEGE = "Access Logic Web Service API"; 45 40 46 /** 47 * Validate credentials 48 * 49 * @param auth 50 * BASIC Authentication credentials -- i.e., "username:password" 51 * encoded with Base64 52 * @return <code>true</code> if credentials are valid for the API 53 */ 54 public static boolean allowUser(String auth) { 55 if (auth == null) 56 return false; // only BASIC authentication 41 private static Object lock = new Object(); // used for synchronizing 57 42 58 if (!auth.toUpperCase().startsWith("BASIC ")) 59 return false; // only BASIC authentication 43 private static List<String[]> allowedIpList = null; 60 44 61 // Get encoded user and password following "BASIC " 62 String userpassEncoded = auth.substring(6); 45 private static long propertiesUpdatedTime = 0; 63 46 64 String[] userpassDecoded = new String(Base64.decode(userpassEncoded)) 65 .split(":"); 66 String username = userpassDecoded[0]; 67 String password = userpassDecoded[1]; 68 try { 69 Context.authenticate(username, password); 70 } catch (ContextAuthenticationException e) { 71 } 72 return Context.isAuthenticated() && Context.hasPrivilege(REST_API_PRIVILEGE); 73 } 47 private static int maxResults = 0; 74 48 75 /** 76 * Tests whether or not a client's IP address is allowed to have access to 77 * the REST API (based on a global property) 78 * 79 * @param remoteAddress 80 * address of the remote client 81 * @return <code>true</code> if client should be allowed access 82 */ 83 public static boolean allowRemoteAddress(String remoteAddress) { 84 String[] remoteIp = remoteAddress.split("\\."); 85 List<String[]> allowed = getAllowedIpList(); 86 for (String[] addr : allowed) { 87 boolean match = true; 88 for (int i = 0; i < addr.length; i++) { 89 if (!addr[i].equals(remoteIp[i]) && !addr[i].equals("*")) { 90 match = false; 91 break; 92 } 93 } 94 if (match) 95 return true; 96 } 97 return false; 98 } 49 /** 50 * Validate credentials 51 * 52 * @param auth BASIC Authentication credentials -- i.e., "username:password" 53 * encoded with Base64 54 * @return <code>true</code> if credentials are valid for the API 55 */ 56 public static boolean allowUser(String auth) { 57 if (auth == null) 58 return false; // only BASIC authentication 99 59 100 /** 101 * Return the maximum number of results that should be returned by any call 102 * 103 * @return maximum number of results to return (0 for unlimited) 104 */ 105 public static int getMaxResults() { 106 if (globalPropertiesDirty()) 107 updateGlobalProperties(); 108 return maxResults; 109 } 60 if (!auth.toUpperCase().startsWith("BASIC ")) 61 return false; // only BASIC authentication 110 62 111 /** 112 * Fetch the list of allowed IP addresses 113 * 114 * @return allowed IP addresses 115 */ 116 private static List<String[]> getAllowedIpList() { 117 if (globalPropertiesDirty()) 118 updateGlobalProperties(); 119 return allowedIpList; 120 } 63 // Get encoded user and password following "BASIC " 64 String userpassEncoded = auth.substring(6); 121 65 122 /** 123 * Check if global properties have either not been loaded or have grown 124 * stale 125 * 126 * @return <code>true</code> if global properties need to be fetched from 127 * the database 128 */ 129 private static boolean globalPropertiesDirty() { 130 boolean dirty = false; 131 synchronized (lock) { 132 dirty = (allowedIpList == null || (new Date().getTime() - propertiesUpdatedTime) > PROPERTY_REFRESH_INTERVAL); 133 } 134 return dirty; 135 } 66 String[] userpassDecoded = new String(Base64.decode(userpassEncoded)) 67 .split(":"); 68 if (userpassDecoded.length < 2) 69 return false; 70 String username = userpassDecoded[0]; 71 String password = userpassDecoded[1]; 72 try { 73 Context.authenticate(username, password); 74 } catch (ContextAuthenticationException e) { 75 } 76 return Context.isAuthenticated() 77 && Context.hasPrivilege(LOGIC_WS_PRIVILEGE); 78 } 136 79 137 /** 138 * Update global property settings from the database 139 */ 140 public static void updateGlobalProperties() { 141 synchronized (lock) { 142 // Update allowed IP list 143 String allowedIpListProperty = Context.getAdministrationService() 144 .getGlobalProperty(GP_ALLOWED_IP_LIST, ""); 145 String[] propList = allowedIpListProperty.split("[\\s,]+"); 146 allowedIpList = new Vector<String[]>(); 147 for (String allowedAddress : propList) { 148 allowedIpList.add(allowedAddress.split("\\.")); 149 } 150 // Update max results 151 String maxResultProperty = Context.getAdministrationService() 152 .getGlobalProperty(GP_MAX_RESULTS, "0"); 153 try { 154 maxResults = Integer.parseInt(maxResultProperty); 155 } catch (NumberFormatException e) { 156 maxResults = 0; 157 } 158 propertiesUpdatedTime = new Date().getTime(); 159 } 160 } 80 /** 81 * Tests whether or not a client's IP address is allowed to have access to 82 * the REST API (based on a global property) 83 * 84 * @param remoteAddress address of the remote client 85 * @return <code>true</code> if client should be allowed access 86 */ 87 public static boolean allowRemoteAddress(String remoteAddress) { 88 String[] remoteIp = remoteAddress.split("\\."); 89 List<String[]> allowed = getAllowedIpList(); 90 for (String[] addr : allowed) { 91 boolean match = true; 92 for (int i = 0; i < addr.length; i++) { 93 if (!addr[i].equals(remoteIp[i]) && !addr[i].equals("*")) { 94 match = false; 95 break; 96 } 97 } 98 if (match) 99 return true; 100 } 101 return false; 102 } 103 104 /** 105 * Return the maximum number of results that should be returned by any call 106 * 107 * @return maximum number of results to return (0 for unlimited) 108 */ 109 public static int getMaxResults() { 110 if (globalPropertiesDirty()) 111 updateGlobalProperties(); 112 return maxResults; 113 } 114 115 /** 116 * Fetch the list of allowed IP addresses 117 * 118 * @return allowed IP addresses 119 */ 120 private static List<String[]> getAllowedIpList() { 121 if (globalPropertiesDirty()) 122 updateGlobalProperties(); 123 return allowedIpList; 124 } 125 126 /** 127 * Check if global properties have either not been loaded or have grown 128 * stale 129 * 130 * @return <code>true</code> if global properties need to be fetched from 131 * the database 132 */ 133 private static boolean globalPropertiesDirty() { 134 boolean dirty = false; 135 synchronized (lock) { 136 dirty = (allowedIpList == null || (new Date().getTime() - propertiesUpdatedTime) > PROPERTY_REFRESH_INTERVAL); 137 } 138 return dirty; 139 } 140 141 /** 142 * Update global property settings from the database 143 */ 144 public static void updateGlobalProperties() { 145 synchronized (lock) { 146 // Update allowed IP list 147 String allowedIpListProperty = Context.getAdministrationService() 148 .getGlobalProperty(GP_ALLOWED_IP_LIST, ""); 149 String[] propList = allowedIpListProperty.split("[\\s,]+"); 150 allowedIpList = new Vector<String[]>(); 151 for (String allowedAddress : propList) { 152 allowedIpList.add(allowedAddress.split("\\.")); 153 } 154 // Update max results 155 String maxResultProperty = Context.getAdministrationService() 156 .getGlobalProperty(GP_MAX_RESULTS, "0"); 157 try { 158 maxResults = Integer.parseInt(maxResultProperty); 159 } catch (NumberFormatException e) { 160 maxResults = 0; 161 } 162 propertiesUpdatedTime = new Date().getTime(); 163 } 164 } 161 165 162 166 } openmrs-modules/logicws/src/org/openmrs/module/logicws/advice/LogicWSAdministrationAdvisor.java
r2101 r2116 3 3 import java.lang.reflect.Method; 4 4 5 import org.openmrs.module.logicws. RestUtil;5 import org.openmrs.module.logicws.LogicWSUtil; 6 6 import org.springframework.aop.AfterReturningAdvice; 7 7 … … 21 21 if (!methodName.startsWith("get") && methodName.contains("GlobalPropert")) { 22 22 try { 23 RestUtil.updateGlobalProperties();23 LogicWSUtil.updateGlobalProperties(); 24 24 } 25 25 catch (Throwable t) { openmrs-modules/logicws/web/src/org/openmrs/module/logicws/web/RestServlet.java
r2095 r2116 10 10 11 11 import org.openmrs.api.APIAuthenticationException; 12 import org.openmrs.module.logicws. RestUtil;12 import org.openmrs.module.logicws.LogicWSUtil; 13 13 14 14 /** … … 93 93 94 94 // Parse the request URL to access the api request 95 String servletString = RestUtil.MODULE_ID + "/" + SERVLET_NAME + "/";95 String servletString = LogicWSUtil.MODULE_ID + "/" + SERVLET_NAME + "/"; 96 96 String apiRequest = request.getRequestURI(); 97 97 if (apiRequest.contains(servletString)) … … 124 124 String authHeader = request.getHeader("Authorization"); 125 125 String remoteAddress = request.getRemoteAddr(); 126 return ( RestUtil.allowUser(authHeader) && RestUtil126 return (LogicWSUtil.allowUser(authHeader) && LogicWSUtil 127 127 .allowRemoteAddress(remoteAddress)); 128 128 }