1 /* 2 * Copyright (c) 2007, Fraunhofer-Gesellschaft 3 * All rights reserved. 4 * 5 * Redistribution and use in source and binary forms, with or without 6 * modification, are permitted provided that the following conditions are 7 * met: 8 * 9 * (1) Redistributions of source code must retain the above copyright 10 * notice, this list of conditions and the disclaimer at the end. 11 * Redistributions in binary form must reproduce the above copyright 12 * notice, this list of conditions and the following disclaimer in 13 * the documentation and/or other materials provided with the 14 * distribution. 15 * 16 * (2) Neither the name of Fraunhofer nor the names of its 17 * contributors may be used to endorse or promote products derived 18 * from this software without specific prior written permission. 19 * 20 * DISCLAIMER 21 * 22 * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS 23 * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT 24 * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR 25 * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT 26 * OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, 27 * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT 28 * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, 29 * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY 30 * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT 31 * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE 32 * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. 33 * 34 */ 35 package org.ogf.graap.wsag.server.persistence.impl; 36 37 import java.text.MessageFormat; 38 import java.util.HashMap; 39 import java.util.Map; 40 import java.util.Vector; 41 42 import org.apache.log4j.Logger; 43 import org.ogf.graap.wsag.server.api.EngineComponent; 44 import org.ogf.graap.wsag.server.persistence.IAgreementFactoryHome; 45 import org.ogf.graap.wsag.server.persistence.PersistedResourceException; 46 import org.ogf.graap.wsag.server.persistence.PersistentAgreementFactory; 47 48 /** 49 * <p> 50 * Abstract implementation of an agreement factory home. This implementation provides global 51 * configuration-related functions as well as it is responsible to find and load the agreement factory 52 * prototype (based on the configuration). 53 * </p> 54 * 55 * <p> 56 * All implementations of the {@link IAgreementFactoryHome} interface should extend this abstract 57 * implementation. 58 * </p> 59 * 60 * @author Oliver Waeldrich 61 * 62 */ 63 public abstract class AbstractWSAG4JPersistence extends EngineComponent 64 implements IAgreementFactoryHome 65 { 66 67 // ////////////////////////////////////////////////////////////////////////////////// 68 // ////// variable definition section //////// 69 // ////////////////////////////////////////////////////////////////////////////////// 70 71 private static final Logger LOG = Logger.getLogger( AbstractWSAG4JPersistence.class ); 72 73 /** 74 * indicates that the persistence layer has changed and a reload is required. 75 */ 76 private boolean changed = false; 77 78 /** 79 * stores the persistent factories of this layer 80 */ 81 private final Vector<PersistentAgreementFactory> persistentFactories = 82 new Vector<PersistentAgreementFactory>(); 83 84 /** 85 * stores the known factories by their ids for fast factory lookup 86 */ 87 private final Map<String, PersistentAgreementFactory> factoriesById = 88 new HashMap<String, PersistentAgreementFactory>(); 89 90 // ////////////////////////////////////////////////////////////////////////////////// 91 // ////// abstract method declaration //////// 92 // ////////////////////////////////////////////////////////////////////////////////// 93 94 /** 95 * Loads the agreement factories for this persistence layer. The load method is invoked during the 96 * initialization process of the persistence layer (see {@link #initialize()}) or during a 97 * {@link #find(String)}, {@link #list()} or {@link #remove(String)} operation 98 * 99 * 100 * @return the loaded factories 101 * 102 * @throws PersistedResourceException 103 * indicates an error while loading the persistent factories 104 */ 105 protected abstract PersistentAgreementFactory[] doLoad() throws PersistedResourceException; 106 107 /** 108 * Removes a persistent factory from the persistence layer. 109 * 110 * @param factory 111 * the factory to remove 112 * 113 * @return <code>true</code> if the factory was removed, otherwise <code>false</code> 114 * 115 * @throws PersistedResourceException 116 * indicates an error while removing the factory 117 */ 118 protected abstract boolean doRemove( PersistentAgreementFactory factory ) 119 throws PersistedResourceException; 120 121 // ////////////////////////////////////////////////////////////////////////////////// 122 // ////// getter/setter methods //////// 123 // ////////////////////////////////////////////////////////////////////////////////// 124 125 /** 126 * Indicates that the persistence layer has changed and needs to be re-initialized (see 127 * {@link #initialize()}). 128 * 129 * @return <code>true</code> if the persistence layer needs to be reloaded, otherwise <code>false</code>. 130 */ 131 public boolean hasChanged() 132 { 133 return changed; 134 } 135 136 /** 137 * Sets the flag to indicate that the persistence layer has changed and needs to be re-initialized (see 138 * {@link #initialize()}). 139 * 140 * @param changed 141 * <code>true</code> if the persistence layer needs to be reloaded, otherwise 142 * <code>false</code> 143 */ 144 public void setChanged( boolean changed ) 145 { 146 this.changed = changed; 147 } 148 149 // ////////////////////////////////////////////////////////////////////////////////// 150 // ////// method implementations //////// 151 // ////////////////////////////////////////////////////////////////////////////////// 152 153 /** 154 * {@inheritDoc} 155 */ 156 @Override 157 protected void doInitialize() throws Exception 158 { 159 synchronized ( this ) 160 { 161 162 try 163 { 164 persistentFactories.clear(); 165 factoriesById.clear(); 166 167 PersistentAgreementFactory[] factories = doLoad(); 168 169 for ( int i = 0; i < factories.length; i++ ) 170 { 171 persistentFactories.add( factories[i] ); 172 factoriesById.put( factories[i].getResourceId(), factories[i] ); 173 } 174 175 setChanged( false ); 176 } 177 catch ( Exception e ) 178 { 179 String message = 180 MessageFormat.format( 181 "Could not load WSAG4J factory instance. Ignoring this instance. Error: {0}", 182 e.getMessage() ); 183 LOG.error( message, e ); 184 } 185 186 } 187 } 188 189 /** 190 * Lists the agreement for the factory with the given id. 191 * 192 * @param agreementFactoryId 193 * the id of the factory for which the agreements are listed 194 * 195 * @return the factory with the given id 196 * 197 * @throws Exception 198 * indicates an error while looking up the factory at the persistence layer 199 */ 200 @Override 201 public PersistentAgreementFactory find( String agreementFactoryId ) throws Exception 202 { 203 if ( hasChanged() ) 204 { 205 doInitialize(); 206 } 207 208 PersistentAgreementFactory persistentAgreementFactory = null; 209 210 // check if the factory is known/available 211 if ( factoriesById.containsKey( agreementFactoryId ) ) 212 { 213 persistentAgreementFactory = factoriesById.get( agreementFactoryId ); 214 } 215 else 216 { 217 throw new Exception( MessageFormat.format( "No agreement factory with id ''{0}'' found.", 218 agreementFactoryId ) ); 219 } 220 221 return persistentAgreementFactory; 222 } 223 224 /** 225 * {@inheritDoc} 226 */ 227 @Override 228 public PersistentAgreementFactory[] list() throws Exception 229 { 230 231 if ( hasChanged() ) 232 { 233 doInitialize(); 234 } 235 236 return persistentFactories.toArray( new PersistentAgreementFactory[persistentFactories.size()] ); 237 } 238 239 /** 240 * {@inheritDoc} 241 */ 242 @Override 243 public void remove( String factoryId ) throws Exception 244 { 245 246 if ( hasChanged() ) 247 { 248 doInitialize(); 249 } 250 251 if ( factoriesById.containsKey( factoryId ) ) 252 { 253 PersistentAgreementFactory factory = factoriesById.get( factoryId ); 254 255 if ( doRemove( factory ) ) 256 { 257 persistentFactories.remove( factory ); 258 factoriesById.remove( factoryId ); 259 } 260 } 261 } 262 }