Commit 966bf167 authored by shake's avatar shake
Browse files

Added support for extending some settings and created access control for the system settings

git-svn-id: https://subversion.umiacs.umd.edu/ace/trunk@157 f1b3a171-7291-4a19-a512-95ad0ad9394a
parent 3917ea05
......@@ -93,13 +93,11 @@ public class QueryThrottle implements ServletContextListener {
@Override
public void contextInitialized( ServletContextEvent sce ) {
System.out.println("[QUERY]");
EntityManager em = PersistUtil.getEntityManager();
Query q = em.createNamedQuery("SettingsParameter.getAttr");
q.setParameter("attr", PARAM_TIME);
SettingsParameter s = (SettingsParameter) q.getSingleResult();
String time = s.getValue();
System.out.println("[QUERY] RESULT " + s.getName() + " " + s.getValue());
if ( Strings.isValidInt(time) ) {
setMinWait(Integer.parseInt(time));
......
......@@ -89,7 +89,6 @@ public final class AuditConfigurationContext implements ServletContextListener {
s = (SettingsParameter) q.getSingleResult();
if ( !Strings.isEmpty(s.getValue()) ) {
String tokenClass = s.getValue();
System.out.println("IMS TOKEN CLASS: " + tokenClass);
AuditThreadFactory.setTokenClass(tokenClass);
}
......@@ -98,7 +97,6 @@ public final class AuditConfigurationContext implements ServletContextListener {
s = (SettingsParameter) q.getSingleResult();
if ( Strings.isValidInt(s.getValue()) ) {
int port = Integer.parseInt(s.getValue());
System.out.println("IMS PORT: " + port);
if ( port > 1 && port < 32768 ) {
AuditThreadFactory.setImsPort(port);
} else {
......
/*
* To change this template, choose Tools | Templates
* and open the template in the editor.
*/
package edu.umiacs.ace.monitor.settings;
import edu.umiacs.ace.util.EntityManagerServlet;
import java.io.IOException;
import java.io.InputStream;
import java.util.HashMap;
import javax.persistence.EntityManager;
import javax.servlet.RequestDispatcher;
import javax.servlet.ServletException;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import org.apache.commons.fileupload.FileItemIterator;
import org.apache.commons.fileupload.FileItemStream;
import org.apache.commons.fileupload.FileUploadException;
import org.apache.commons.fileupload.servlet.ServletFileUpload;
import org.apache.commons.fileupload.util.Streams;
/**
*
* @author shake
*/
public class AddSettingServlet extends EntityManagerServlet{
@Override
protected void processRequest(HttpServletRequest request, HttpServletResponse response, EntityManager em) throws ServletException, IOException {
HashMap <String, String> customSettings = new HashMap<String, String>();
ServletFileUpload su = new ServletFileUpload();
try {
FileItemIterator iter = su.getItemIterator(request);
while ( iter.hasNext() ) {
FileItemStream name = iter.next();
InputStream nameStream = name.openStream();
String paramName = Streams.asString(nameStream);
FileItemStream value = null;
if ( iter.hasNext() ) {
value = iter.next();
InputStream valueStream = value.openStream();
if ( name.isFormField() && value.isFormField()) {
String paramValue = Streams.asString(valueStream);
customSettings.put(paramName, paramValue);
}
}
}
} catch (FileUploadException ex) {
// Logger.getLogger(SettingsServlet.class.getName()).log(Level.SEVERE, null, ex);
}
SettingsUtil.updateSettings(customSettings, true);
RequestDispatcher dispatcher = request.getRequestDispatcher("UpdateSettings");
dispatcher.forward(request, response);
}
}
......@@ -34,7 +34,7 @@ public class SettingsMigrationContextListener implements ServletContextListener{
//System.out.println("[MIGRATION] " + migrated);
if ( !migrated ) {
//System.out.println("[MIGRATION] Inserting tables");
SettingsUtil.updateSettings(SettingsUtil.getDefaultMap());
SettingsUtil.updateSettings(SettingsUtil.getDefaultMap(), false);
}
} catch (SQLException ex) {
Logger.getLogger(SettingsMigrationContextListener.class.getName())
......
......@@ -21,7 +21,10 @@ import javax.persistence.Table;
@NamedQuery(name = "SettingsParameter.getAttrList", query =
"SELECT p FROM SettingsParameter p WHERE p.attr LIKE :attr"),
@NamedQuery(name = "SettingsParameter.getCurrentSettings", query =
"SELECT p FROM SettingsParameter p")
"SELECT p FROM SettingsParameter p"),
@NamedQuery(name = "SettingsParameter.getCustomSettings", query =
"SELECT p FROM SettingsParameter p WHERE p.custom = TRUE")
})
public class SettingsParameter implements Serializable {
@Id
......@@ -29,15 +32,17 @@ public class SettingsParameter implements Serializable {
private Long id;
private String attr;
private String value;
private boolean custom;
public SettingsParameter() {
this.attr = null;
this.value = null;
}
public SettingsParameter(String attr, String value) {
public SettingsParameter(String attr, String value, boolean custom) {
this.attr = attr;
this.value = value;
this.custom = custom;
}
public Long getId() {
......@@ -52,6 +57,10 @@ public class SettingsParameter implements Serializable {
return attr;
}
public boolean getCustom() {
return custom;
}
public String getValue() {
return value;
}
......@@ -64,6 +73,10 @@ public class SettingsParameter implements Serializable {
this.value = value;
}
public void setCustom(boolean custom) {
this.custom = custom;
}
@Override
public String toString() {
return "edu.umiacs.ace.monitor.settings.settingsParameter[id=" + id + "]";
......
......@@ -6,6 +6,7 @@ import java.io.IOException;
import java.io.InputStream;
import java.util.HashMap;
import java.util.List;
import java.util.Map;
import java.util.Set;
import java.util.logging.Level;
import java.util.logging.Logger;
......@@ -61,20 +62,19 @@ public class SettingsServlet extends EntityManagerServlet {
}
if ( update ) {
SettingsUtil.updateSettings(settings);
SettingsUtil.updateSettings(settings, false);
} else {
SettingsUtil.updateSettings(SettingsUtil.getDefaultMap());
SettingsUtil.updateSettings(SettingsUtil.getDefaultMap(), false);
}
}
List<SettingsParameter> currentSettings = SettingsUtil.getCurrentSettings();
HashMap<String, String> settingsMap = new HashMap<String, String>();
for ( SettingsParameter s : currentSettings ) {
settingsMap.put(s.getName(), s.getValue());
}
Map<String, String> settingsMap =
settingsToMap(SettingsUtil.getCurrentSettings());
Map<String, String> customMap =
settingsToMap(SettingsUtil.getCustomSettings());
request.setAttribute("currSettings", settingsMap);
request.setAttribute("customSettings", customMap);
if ( settingsMap.get(SettingsConstants.PARAM_4J_APPENDER).equals(LOG_CLASS)) {
request.setAttribute("fileAppender", true);
......@@ -87,4 +87,14 @@ public class SettingsServlet extends EntityManagerServlet {
dispatcher.forward(request, response);
}
private Map<String, String> settingsToMap( List<SettingsParameter> settings) {
HashMap<String, String> settingsMap = new HashMap<String, String>();
for ( SettingsParameter s : settings ) {
settingsMap.put(s.getName(), s.getValue());
}
return settingsMap;
}
}
......@@ -31,6 +31,13 @@ public class SettingsUtil {
return null;
}
public static List<SettingsParameter> getCustomSettings() {
EntityManager em = PersistUtil.getEntityManager();
Query q = em.createNamedQuery("SettingsParameter.getCustomSettings");
return q.getResultList();
}
public static List<SettingsParameter> getCurrentSettings() {
EntityManager em = PersistUtil.getEntityManager();
Query q = em.createNamedQuery("SettingsParameter.getCurrentSettings");
......@@ -38,15 +45,21 @@ public class SettingsUtil {
return q.getResultList();
}
public static void updateSettings(Map<String, String> settings) {
public static void updateSettings(Map<String, String> settings, boolean isCustom) {
EntityManager em = PersistUtil.getEntityManager();
EntityTransaction trans = em.getTransaction();
trans.begin();
for ( String name : settings.keySet() ) {
// Skip any empty strings
if (name.trim().isEmpty() || settings.get(name).trim().isEmpty() ) {
continue;
}
SettingsParameter item = getItemByAttr(name);
if ( item == null ) {
em.persist(new SettingsParameter(name, settings.get(name)));
em.persist(new SettingsParameter(name, settings.get(name), isCustom));
} else {
item.setValue(settings.get(name));
em.merge(item);
......
......@@ -147,7 +147,7 @@ public class DefaultAccountContextListener implements ServletContextListener {
UserRoles updateSysSettings = new UserRoles();
updateSysSettings.setRolename("Modify System Settings");
updateSysSettings.setUsername("system");
updateSysSettings.setUsername("admin");
EntityTransaction et = em.getTransaction();
......
......@@ -11,6 +11,7 @@ CREATE TABLE `system_settings` (
`ID` bigint(20) NOT NULL auto_increment,
`ATTR` varchar(255) default NULL,
`VALUE` varchar(255) default NULL,
`CUSTOM` BOOLEAN default FALSE,
PRIMARY KEY (`ID`),
UNIQUE (`ATTR`)
) ENGINE=MyISAM DEFAULT CHARSET=utf8;
......
......@@ -214,6 +214,7 @@ CREATE TABLE `system_settings` (
`ID` bigint(20) NOT NULL auto_increment,
`ATTR` varchar(255) default NULL,
`VALUE` varchar(255) default NULL,
`CUSTOM` BOOLEAN default FALSE,
PRIMARY KEY (`ID`),
UNIQUE (`ATTR`)
) ENGINE=MyISAM DEFAULT CHARSET=utf8;
\ No newline at end of file
......@@ -187,6 +187,10 @@
<servlet-name>SettingsServlet</servlet-name>
<servlet-class>edu.umiacs.ace.monitor.settings.SettingsServlet</servlet-class>
</servlet>
<servlet>
<servlet-name>AddSettingServlet</servlet-name>
<servlet-class>edu.umiacs.ace.monitor.settings.AddSettingServlet</servlet-class>
</servlet>
<servlet-mapping>
<servlet-name>ServletAdaptor</servlet-name>
<url-pattern>/rest/*</url-pattern>
......@@ -300,6 +304,10 @@
<servlet-name>SettingsServlet</servlet-name>
<url-pattern>/UpdateSettings</url-pattern>
</servlet-mapping>
<servlet-mapping>
<servlet-name>AddSettingServlet</servlet-name>
<url-pattern>/AddSettings</url-pattern>
</servlet-mapping>
<session-config>
<session-timeout>
30
......@@ -677,6 +685,24 @@
<role-name>Compare</role-name>
</auth-constraint>
</security-constraint>
<security-constraint>
<display-name>System Settings</display-name>
<web-resource-collection>
<web-resource-name>System</web-resource-name>
<description/>
<url-pattern>/UpdateSettings</url-pattern>
<http-method>PUT</http-method>
<http-method>HEAD</http-method>
<http-method>POST</http-method>
<http-method>OPTIONS</http-method>
<http-method>TRACE</http-method>
<http-method>DELETE</http-method>
</web-resource-collection>
<auth-constraint>
<description/>
<role-name>Modify System Settings</role-name>
</auth-constraint>
</security-constraint>
<login-config>
<auth-method>BASIC</auth-method>
<realm-name>Audit Manager</realm-name>
......@@ -745,4 +771,8 @@
<description>Add/edit/remove stuff in /PartnerSite</description>
<role-name>Modify Partner Sites</role-name>
</security-role> --&gt;
<security-role>
<description>Role used to modify system settings</description>
<role-name>Modify System Settings</role-name>
</security-role>
</web-app>
<%--
Document : addsetting
Created on : Aug 6, 2012, 2:41:40 PM
Author : shake
--%>
<%@page contentType="text/html" pageEncoding="UTF-8"%>
<%@taglib uri="http://java.sun.com/jsp/jstl/core" prefix="c"%>
<!DOCTYPE HTML PUBLIC "-//W3C//DTD HTML 4.01 Transitional//EN"
"http://www.w3.org/TR/html4/loose.dtd">
<html>
<head>
<meta http-equiv="Content-Type" content="text/html; charset=UTF-8">
<title>System Settings</title>
<link rel="stylesheet" type="text/css" href="style.css" />
<script type="text/javascript">
var counter = 0;
function addNewSetting() {
counter++;
var newFields = document.getElementById('customSetting').cloneNode(true);
newFields.id = '';
newFields.style.display = 'block';
var newField = newFields.childNodes;
for (var i=0;i<newField.length;i++) {
var theName = newField[i].name
if (theName)
newField[i].name = theName + counter;
}
var insertHere = document.getElementById('writeSetting');
insertHere.parentNode.insertBefore(newFields,insertHere);
}
window.onload = addNewSetting;
</script>
</head>
<body>
<jsp:include page="header.jsp"/>
<fieldset id="customSetting" style="display: none">
<div class="settingsRow">
<div class="settingsName">Setting Name:</div>
<div class="settingsVal"><input type=text name="custom-name"></div>
</div>
<div class="settingsRow">
<div class="settingsName">Setting Val:</div>
<div class="settingsVal"><input type=text name="custom-val"></div>
</div>
</fieldset>
<FORM name="settingsform" METHOD="POST" ENCTYPE="multipart/form-data" ACTION="AddSettings">
<fieldset id="settingsTable">
<legend>
<h2>Add Settings</h2>
</legend>
<span id="writeSetting"></span>
<input type="button" value="+" onClick="addNewSetting()"/>
</fieldset>
<br>
<input type=submit value="Submit" name="addSettings" class="submitLink" style="margin-left: 5%"/>
<a href="UpdateSettings" style="font-size: medium; text-decoration: underline;">Cancel</a>
</FORM>
<jsp:include page="footer.jsp"/>
</body>
</html>
......@@ -17,76 +17,78 @@
</head>
<body>
<jsp:include page="header.jsp"/>
<h1>System Settings</h1>
<FORM name="settingsform" METHOD="POST" ENCTYPE="multipart/form-data" ACTION="UpdateSettings">
<div id="settingsTable">
<fieldset id="settingsTable">
<legend>
<h2>System Settings</h2>
</legend>
<div class="settingsRow">
<div class="settingsName">Mail Server:</div>
<div class="settingsVal"><input type=text name="mail.server" value="${currSettings['mail.server']}"></div>
<div class="settingsVal"><input type=text name="mail.server" value="${currSettings['mail.server']}"/></div>
<div class="settingsHelp"><img src="images/help.png" title="Mail server to use when mailing reports. You will need to set this if you want reports to be mailed properly."></div>
</div>
<div class="settingsRow">
<div class="settingsName">Mail From:</div>
<div class="settingsVal"><input type=text name="mail.from" value="${currSettings['mail.from']}"></div>
<div class="settingsVal"><input type=text name="mail.from" value="${currSettings['mail.from']}"/></div>
<div class="settingsHelp"><img src="images/help.png" title="Set this e-mail address to an address e-mail should originate from"></div>
</div>
<div class="settingsRow">
<div class="settingsName">Max Audit:</div>
<div class="settingsVal"><input type=text name="throttle.maxaudit" value="${currSettings['throttle.maxaudit']}"></div>
<div class="settingsVal"><input type=text name="throttle.maxaudit" value="${currSettings['throttle.maxaudit']}"/></div>
<div class="settingsHelp"><img src="images/help.png" title="Max number of running audits"></div>
</div>
<div class="settingsRow">
<div class="settingsName">Audit Wait Time:</div>
<div class="settingsVal"><input type=text name="throttle.wait" value="${currSettings['throttle.wait']}"></div>
<div class="settingsVal"><input type=text name="throttle.wait" value="${currSettings['throttle.wait']}"/></div>
<div class="settingsHelp"><img src="images/help.png" title="Minimum time between srb file reads in milliseconds"></div>
</div>
<div class="settingsRow">
<div class="settingsName">Audit BPS:</div>
<div class="settingsVal"><input type=text name="throttle.bps" value="${currSettings['throttle.bps']}"></div>
<div class="settingsVal"><input type=text name="throttle.bps" value="${currSettings['throttle.bps']}"/></div>
<div class="settingsHelp"><img src="images/help.png" title="Maximum bytes per second per running audit, default = 0 = unlimited"></div>
</div>
<div class="settingsRow">
<div class="settingsName">Auto Audit:</div>
<div class="settingsVal"><input type=text name="auto.audit.disable" value="${currSettings['auto.audit.disable']}"></div>
<div class="settingsVal"><input type=text name="auto.audit.disable" value="${currSettings['auto.audit.disable']}"/></div>
<div class="settingsHelp"><img src="images/help.png" title="Start automated auditing"></div>
</div>
<div class="settingsRow">
<div class="settingsName">IMS Host:</div>
<div class="settingsVal"><input type=text name="ims" value="${currSettings['ims']}"></div>
<div class="settingsVal"><input type=text name="ims" value="${currSettings['ims']}"/></div>
<div class="settingsHelp"><img src="images/help.png" title="IMS hostname to use. Unless you deployed your own IMS, this should probably not be changed"></div>
</div>
<div class="settingsRow">
<div class="settingsName">User Management:</div>
<div class="settingsVal"><input type=text name="auth.management" value="${currSettings['auth.management']}"></div>
<div class="settingsVal"><input type=text name="auth.management" value="${currSettings['auth.management']}"/></div>
<div class="settingsHelp"><img src="images/help.png" title="Set this to true to disable internal user management. This should only be used in conjunction with changes to the Authentication realm listed above."></div>
</div>
<div class="settingsRow">
<div class="settingsName">Log Location:</div>
<div class="settingsVal"><input type=text name="log4j.appender.A1.File" value="${currSettings['log4j.appender.A1.File']}"></div>
<div class="settingsVal"><input type=text name="log4j.appender.A1.File" value="${currSettings['log4j.appender.A1.File']}"/></div>
<div class="settingsHelp"><img src="images/help.png" title="The location of your logfile"></div>
</div>
<c:choose>
<c:when test="${fileAppender}">
<div class="settingsRow">
<div class="settingsName">Log Type:</div>
<div class="settingsVal"><input type=text name="log4j.appender.A1" value="${currSettings['log4j.appender.A1']}"></div>
<div class="settingsVal"><input type=text name="log4j.appender.A1" value="${currSettings['log4j.appender.A1']}"/></div>
<div class="settingsHelp"><img src="images/help.png" title="Log everything to one file, will grow to infinity"></div>
</div>
</c:when>
<c:otherwise>
<div class="settingsRow">
<div class="settingsName">Log Type:</div>
<div class="settingsVal"><input type=text name="log4j.appender.A1" value="${currSettings['log4j.appender.A1']}"></div>
<div class="settingsVal"><input type=text name="log4j.appender.A1" value="${currSettings['log4j.appender.A1']}"/></div>
<div class="settingsHelp"><img src="images/help.png" title="Rolling log file"></div>
</div>
<div class="settingsRow">
<div class="settingsName">Log File Size:</div>
<div class="settingsVal"><input type=text name="log4j.appender.A1.maxFileSize" value="${currSettings['log4j.appender.A1.maxFileSize']}"></div>
<div class="settingsVal"><input type=text name="log4j.appender.A1.maxFileSize" value="${currSettings['log4j.appender.A1.maxFileSize']}"/></div>
<div class="settingsHelp"><img src="images/help.png" title="File size of your log"></div>
</div>
<div class="settingsRow">
<div class="settingsName">Log Backup Index:</div>
<div class="settingsVal"><input type=text name="log4j.appender.A1.maxBackupIndex" value="${currSettings['log4j.appender.A1.maxBackupIndex']}"></div>
<div class="settingsVal"><input type=text name="log4j.appender.A1.maxBackupIndex" value="${currSettings['log4j.appender.A1.maxBackupIndex']}"/></div>
<div class="settingsHelp"><img src="images/help.png" title="Maximum backup index"></div>
</div>
</c:otherwise>
......@@ -98,30 +100,42 @@
</div>
<div class="settingsRow">
<div class="settingsName">Root Logger:</div>
<div class="settingsVal"><input type=text name="log4j.rootLogger" value="${currSettings['log4j.rootLogger']}"></div>
<div class="settingsVal"><input type=text name="log4j.rootLogger" value="${currSettings['log4j.rootLogger']}"/></div>
</div>
<div class="settingsRow">
<div class="settingsName">Pattern Layout:</div>
<div class="settingsVal"><input type=text name="log4j.appender.A1.layout" value="${currSettings['log4j.appender.A1.layout']}"></div>
<div class="settingsVal"><input type=text name="log4j.appender.A1.layout" value="${currSettings['log4j.appender.A1.layout']}"/></div>
</div>
<div class="settingsRow">
<div class="settingsName">Conversion Pattern:</div>
<div class="settingsVal"><input type=text name="log4j.appender.A1.layout.ConversionPattern" value="${currSettings['log4j.appender.A1.layout.ConversionPattern']}"></div>
<div class="settingsVal"><input type=text name="log4j.appender.A1.layout.ConversionPattern" value="${currSettings['log4j.appender.A1.layout.ConversionPattern']}"/></div>
</div>
<div class="settingsRow">
<div class="settingsName">IRods:</div>
<div class="settingsVal"><input type=text name="log4j.logger.edu.umiacs.irods" value="${currSettings['log4j.logger.edu.umiacs.irods']}"></div>
<div class="settingsVal"><input type=text name="log4j.logger.edu.umiacs.irods" value="${currSettings['log4j.logger.edu.umiacs.irods']}"/></div>
</div>
<div class="settingsRow">
<div class="settingsName">UMIACS Connection:</div>
<div class="settingsVal"><input type=text name="log4j.logger.edu.umiacs" value="${currSettings['log4j.logger.edu.umiacs']}"></div>
<div class="settingsVal"><input type=text name="log4j.logger.edu.umiacs" value="${currSettings['log4j.logger.edu.umiacs']}"/></div>
</div>
<div class="settingsRow">
<div class="settingsName">IRods Connection:</div>
<div class="settingsVal"><input type=text name="irods.connection" value="${currSettings['irods.connection']}"></div>
<div class="settingsVal"><input type=text name="irods.connection" value="${currSettings['irods.connection']}"/></div>
</div>
</div>
<br>
<div class="settingsRow">
<div>Custom Settings: </div>
</div>
<c:forEach var="item" items="${customSettings}">
<div class="settingsRow">
<div class="settingsName">${item.key}</div>
<div class="settingsVal"><input type="text" name="${item.key}" value="${item.value}"/></div>
</div>
</c:forEach>
<div class="settingsRow">
<div class="settingsName"><a href="addsetting.jsp">Add setting</a></div>
</div>
</fieldset>
<br>
<input type=submit value="Submit" name="update" class="submitLink" style="margin-left: 5%">
<input type=submit value="Default" name="default" class="submitLink">
......
......@@ -167,7 +167,6 @@ vertical-align: top;
border: 1px solid #000000;
margin-left: 5%;
margin-right: 5%;
width: 90%;
}
.settingsRow {
......@@ -182,7 +181,6 @@ vertical-align: top;
width: 200px;
float: left;
margin-left: 2px;
margin-top: 5px;
}
.settingsVal {
......
......@@ -150,6 +150,12 @@ Author : toaster
<input type="checkbox" name="role" value="Download Item" ${roles['Download Item']} />Retrieve items from collections
</td>
</tr>
<tr>
<td>
<input type="checkbox" name="role" value="Modify System Settings" ${roles['Modify System Settings']} />Modify System Settings
</td>
</tr>
</table>
<input type="submit" name="commit" value="Save" class="submitLink" />
......
Markdown is supported
0% or .
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment