databasepsmlmanagerservice.java
来自「jetspeed源代码」· Java 代码 · 共 1,277 行 · 第 1/3 页
JAVA
1,277 行
/*
* Copyright 2000-2001,2004 The Apache Software Foundation.
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* 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.apache.jetspeed.services.psmlmanager.db;
import java.sql.Connection;
// PSML Manager Service interface
import org.apache.jetspeed.services.psmlmanager.PsmlManagerService;
// Jetspeed Security service
import org.apache.jetspeed.services.JetspeedSecurity;
// Profile and ProfileLocator interface
import org.apache.jetspeed.om.profile.Profile;
import org.apache.jetspeed.om.profile.ProfileLocator;
import org.apache.jetspeed.om.profile.QueryLocator;
import org.apache.jetspeed.services.Profiler;
import org.apache.jetspeed.services.logging.JetspeedLogFactoryService;
import org.apache.jetspeed.services.logging.JetspeedLogger;
//Castor defined API
import org.apache.jetspeed.om.profile.Portlets;
import org.apache.jetspeed.om.profile.PSMLDocument;
import org.apache.jetspeed.om.profile.BasePSMLDocument;
//turbine stuff
import org.apache.turbine.services.TurbineBaseService;
import org.apache.turbine.services.InitializationException;
import org.apache.turbine.services.TurbineServices;
import org.apache.turbine.services.resources.ResourceService;
import org.apache.turbine.services.servlet.TurbineServlet;
import org.apache.turbine.services.servlet.ServletService;
// torque
import org.apache.torque.Torque;
// jetspeed security
import org.apache.jetspeed.om.security.JetspeedUser;
import org.apache.jetspeed.om.security.JetspeedUserFactory;
import org.apache.jetspeed.om.security.Role;
import org.apache.jetspeed.om.security.JetspeedRoleFactory;
import org.apache.jetspeed.om.security.Group;
import org.apache.jetspeed.om.security.JetspeedGroupFactory;
import org.apache.jetspeed.services.security.JetspeedSecurityException;
//Servlet API
import javax.servlet.ServletConfig;
// Torque generated classes
import org.apache.jetspeed.om.dbpsml.JetspeedUserProfile;
import org.apache.jetspeed.om.dbpsml.JetspeedUserProfilePeer;
import org.apache.jetspeed.om.dbpsml.JetspeedRoleProfile;
import org.apache.jetspeed.om.dbpsml.JetspeedRoleProfilePeer;
import org.apache.jetspeed.om.dbpsml.JetspeedGroupProfile;
import org.apache.jetspeed.om.dbpsml.JetspeedGroupProfilePeer;
//standard java stuff
import java.lang.Thread;
import java.util.List;
import java.util.Iterator;
import java.util.StringTokenizer;
import java.util.ArrayList;
import java.util.Map;
import java.util.HashMap;
import java.io.FileReader;
import java.io.File;
import org.exolab.castor.mapping.Mapping;
import org.xml.sax.InputSource;
/**
* This service is responsible for loading and saving PSML documents. It uses
* database to persist the PSML documents.
*
* @author <a href="mailto:adambalk@cisco.com">Atul Dambalkar</a>
* @author <a href="mailto:mvaidya@cisco.com">Medha Vaidya</a>
* @author <a href="mailto:taylor@apache.org">David Sean Taylor</a>
* @version $Id: DatabasePsmlManagerService.java,v 1.35 2004/02/23 03:32:19 jford Exp $
*/
public class DatabasePsmlManagerService extends TurbineBaseService
implements DatabasePsmlManager
{
/**
* Static initialization of the logger for this class
*/
private static final JetspeedLogger logger = JetspeedLogFactoryService.getLogger(DatabasePsmlManagerService.class.getName());
private Map psmlCache = new HashMap();
/** The watcher for the document locations */
private CacheRefresher refresher = null;
/** the base refresh rate for documents */
private long refreshRate; // default will be 8 hours
private final static String REFRESH_RATE = "refresh-rate";
private final static long DEFAULT_REFRESH_RATE = 60 * 60 * 8 * 1000; //8hrs
/** whether caching is allowed */
private boolean cachingOn; // default will be false
private final static String CACHING_ON = "caching-on";
private final static boolean DEFAULT_CACHING_ON = false;
private final static String POOL_NAME = "database";
/** the import/export consumer service **/
private PsmlManagerService consumer = null;
// castor mapping
public static final String DEFAULT_MAPPING = "${webappRoot}/WEB-INF/conf/psml-mapping.xml";
String mapFile = null;
/** the Castor mapping file name */
private Mapping mapping = null;
/** The pool name to use for database requests. */
private String poolName = null;
/**
* This is the early initialization method called by the
* Turbine <code>Service</code> framework
*/
public void init(ServletConfig conf) throws InitializationException
{
if (getInit())
{
return;
}
logger.info("Initializing DatabasePsmlManagerService...");
initConfiguration(conf);
logger.info("Done initializing DatabasePsmlManagerService.");
}
/**
* Loads the configuration parameters for this service from the
* JetspeedResources.properties file.
*
* @exception throws a <code>InitializationException</code> if the service
* fails to initialize
*/
private void initConfiguration(ServletConfig conf)
throws InitializationException
{
//Ensure that the servlet service is initialized
TurbineServices.getInstance().initService(ServletService.SERVICE_NAME, conf);
ResourceService serviceConf =
((TurbineServices)TurbineServices.getInstance())
.getResources(PsmlManagerService.SERVICE_NAME);
try
{
// get configuration parameters from Turbine Resources
// we'll use only string accessors so the values can be multiply
// specified in the properties files (the first one wins).
String value = serviceConf.getString(REFRESH_RATE);
refreshRate = DEFAULT_REFRESH_RATE;
try
{
refreshRate = Long.parseLong(value);
}
catch (Exception e)
{
logger.warn("DatabasePsmlManagerService: error in refresh-rate configuration: using default");
}
// get the name of the torque database pool to use
poolName = serviceConf.getString(POOL_NAME);
//find out if caching allowed
value = serviceConf.getString(CACHING_ON);
cachingOn = DEFAULT_CACHING_ON;
try
{
cachingOn = value.equals("true");
}
catch (Exception e)
{
logger.warn("DatabasePsmlManagerService: error in caching-on configuration: using default");
}
// psml castor mapping file
mapFile = serviceConf.getString("mapping",DEFAULT_MAPPING);
mapFile = TurbineServlet.getRealPath( mapFile );
loadMapping();
}
catch (Throwable t)
{
logger.error(this + ".init:" , t);
throw new InitializationException("Exception initializing DatabasePsmlManagerService" + t);
}
if (cachingOn)
{
this.refresher = new CacheRefresher();
refresher.start();
}
}
/** Late init method from Turbine Service model */
public void init() throws InitializationException
{
//Mark that we are done
setInit(true);
/*
try
{
PsmlImporter importer = new PsmlImporter();
importer.run(null);
}
catch (Exception e)
{
logger.warn("DatabasePsmlManagerService.init: exception while importing:" , e);
}
*/
}
protected void loadMapping()
throws InitializationException
{
// test the mapping file and create the mapping object
if (mapFile != null)
{
File map = new File(mapFile);
if (logger.isDebugEnabled())
logger.debug("Loading psml mapping file " + mapFile);
if (map.exists() && map.isFile() && map.canRead())
{
try
{
mapping = new Mapping();
InputSource is = new InputSource( new FileReader(map) );
is.setSystemId( mapFile );
mapping.loadMapping( is );
}
catch (Exception e)
{
logger.error("Error in psml mapping creation",e);
throw new InitializationException("Error in mapping",e);
}
}
else
{
throw new InitializationException("PSML Mapping not found or not a file or unreadable: "+mapFile);
}
}
}
/**
* This is the shutdown method called by the
* Turbine <code>Service</code> framework
*/
public void shutdown()
{
if (this.refresher != null)
{
this.refresher.setDone(true);
}
}
/**
* A thread implementation of cache refreshing mechanism for database
* persisted PSMLs. We have to refresh the cache after specific intervals
* if someone manually updates the PSML database.
*
* @author <a href="mailto:adambalk@cisco.com">Atul Dambalkar</a>
*/
class CacheRefresher extends Thread
{
private boolean done = false;
/**
* Constructor to to set the priority.
*/
CacheRefresher()
{
setDaemon(true);
setPriority(Thread.MIN_PRIORITY+1);
}
/**
* We are all done, system is shutting down.
*/
void setDone(boolean done)
{
this.done = done;
}
/**
* Method as needed for a Thread to run
*/
public void run()
{
try
{
while (!done)
{
if (logger.isDebugEnabled())
logger.debug("Cache Refresher thread sleeping now!");
sleep (refreshRate);
if (logger.isDebugEnabled())
logger.debug("Cache Refresher thread working now!");
try
{
synchronized (this)
{
Iterator i = psmlCache.keySet().iterator();
while(i.hasNext())
{
String locator = (String)i.next();
// do refresh for the locator
PSMLDocument doc =
refresh(stringToLocator(locator));
// over write the existing document in cache
psmlCache.put(locator, doc);
}
}
}
catch (Exception e)
{
logger.warn("DatabasePsmlManagerService.CacheRefresher: Error in cache refresher...", e);
}
}
}
catch (InterruptedException e)
{
if (logger.isDebugEnabled())
logger.debug("DatabasePsmlManagerService.CacheRefresher: recieved interruption, aborting.");
}
}
}
/**
* Return a unique string identifying this object.
*/
private String locatorToString(ProfileLocator locator)
{
StringBuffer keybuf = new StringBuffer();
JetspeedUser user = locator.getUser();
Role role = locator.getRole();
Group group = locator.getGroup();
String name = locator.getName();
String mediaType = locator.getMediaType();
String country = locator.getCountry();
String language = locator.getLanguage();
synchronized (this)
{
if (user != null)
{
keybuf.append("User:").append(user.getUserName());
}
else if (group != null)
{
keybuf.append("Group:").append(group.getName());
}
else if (role != null)
{
keybuf.append("Role:").append(role.getName());
}
if (name != null)
{
keybuf.append('$').append("Page:").append(name);
}
if (mediaType != null)
{
keybuf.append('$').append("MediaType:").append(mediaType);
}
if (country != null && (! country.equals("-1")))
{
keybuf.append('$').append("Country:").append(country);
}
if (language != null && (! language.equals("-1")))
{
keybuf.append('$').append("Language:").append(language);
}
}
if (logger.isDebugEnabled())
logger.debug("DatabasePsmlManagerService: Returning locator string: " + keybuf.toString());
return keybuf.toString();
}
private ProfileLocator stringToLocator(String locstr) throws Exception
{
ProfileLocator locator = Profiler.createLocator();
String entity = null;
if (logger.isDebugEnabled())
logger.debug("DatabasePsmlManagerService: Creating locator for string: " + locstr);
StringTokenizer dollarTokens = new StringTokenizer(locstr, "$");
while (dollarTokens.hasMoreTokens())
{
String dollarToken = dollarTokens.nextToken().trim();
StringTokenizer colonTokens = new StringTokenizer(dollarToken, ":");
String colonToken = colonTokens.nextToken();
⌨️ 快捷键说明
复制代码Ctrl + C
搜索代码Ctrl + F
全屏模式F11
增大字号Ctrl + =
减小字号Ctrl + -
显示快捷键?