blob: 5e383f926978e92cd39f7ddfd403f683f30ceab5 [file] [log] [blame]
/*******************************************************************************
* Copyright (c) 2011, 2015 EclipseSource and others.
* All rights reserved. This program and the accompanying materials
* are made available under the terms of the Eclipse Public License v1.0
* which accompanies this distribution, and is available at
* http://www.eclipse.org/legal/epl-v10.html
*
* Contributors:
* EclipseSource - initial API and implementation
******************************************************************************/
package org.eclipse.rap.rwt.internal;
import java.util.concurrent.atomic.AtomicReference;
import org.eclipse.rap.rwt.internal.util.ClassUtil;
import org.eclipse.rap.rwt.internal.util.SharedInstanceBuffer;
import org.eclipse.rap.rwt.internal.util.SharedInstanceBuffer.InstanceCreator;
import org.eclipse.rap.rwt.service.ApplicationContext;
import org.eclipse.rap.rwt.service.UISession;
import org.eclipse.swt.internal.SerializableCompatibility;
public class SingletonManager implements SerializableCompatibility {
private static final String ATTR_SINGLETON_MANAGER
= SingletonManager.class.getName() + "#instance";
private final SharedInstanceBuffer<Class<?>, AtomicReference<Object>> singletonHolders;
private InstanceCreator<Class<?>, AtomicReference<Object>> instanceCreator;
SingletonManager() {
singletonHolders = new SharedInstanceBuffer<>();
instanceCreator = new InstanceCreator<Class<?>, AtomicReference<Object>>() {
@Override
public AtomicReference<Object> createInstance( Class<?> key ) {
return new AtomicReference<>();
}
};
}
public <T> T getSingleton( Class<T> type ) {
AtomicReference<T> singletonHolder = getSingletonHolder( type );
synchronized( singletonHolder ) {
T singleton = singletonHolder.get();
if( singleton == null ) {
singleton = ClassUtil.newInstance( type );
singletonHolder.set( singleton );
}
return singleton;
}
}
@SuppressWarnings( "unchecked" )
private <T> AtomicReference<T> getSingletonHolder( Class<T> type ) {
Object result = singletonHolders.get( type, instanceCreator );
return ( AtomicReference<T> )result;
}
public static void install( UISession uiSession ) {
checkNotInstalled( uiSession );
uiSession.setAttribute( ATTR_SINGLETON_MANAGER, new SingletonManager() );
}
public static void install( ApplicationContext applicationContext ) {
checkNotInstalled( applicationContext );
applicationContext.setAttribute( ATTR_SINGLETON_MANAGER, new SingletonManager() );
}
public static SingletonManager getInstance( UISession uiSession ) {
return ( SingletonManager )uiSession.getAttribute( ATTR_SINGLETON_MANAGER );
}
public static SingletonManager getInstance( ApplicationContext applicationContext ) {
return ( SingletonManager )applicationContext.getAttribute( ATTR_SINGLETON_MANAGER );
}
private static void checkNotInstalled( UISession uiSession ) {
if( getInstance( uiSession ) != null ) {
String msg = "SingletonManager already installed for UI session: " + uiSession.getId();
throw new IllegalStateException( msg );
}
}
private static void checkNotInstalled( ApplicationContext applicationContext ) {
if( getInstance( applicationContext ) != null ) {
String msg = "SingletonManager already installed for application context";
throw new IllegalStateException( msg );
}
}
}