001/*
002 * (C) Copyright 2006-2007 Nuxeo SAS <http://nuxeo.com> and others
003 *
004 * All rights reserved. This program and the accompanying materials
005 * are made available under the terms of the Eclipse Public License v1.0
006 * which accompanies this distribution, and is available at
007 * http://www.eclipse.org/legal/epl-v10.html
008 *
009 * Contributors:
010 *     Jean-Marc Orliaguet, Chalmers
011 *
012 * $Id$
013 */
014
015package org.nuxeo.theme.types;
016
017import java.util.ArrayList;
018import java.util.List;
019import java.util.Map;
020import java.util.concurrent.ConcurrentHashMap;
021
022import org.apache.commons.logging.Log;
023import org.apache.commons.logging.LogFactory;
024import org.nuxeo.theme.Registrable;
025
026public final class TypeRegistry implements Registrable {
027
028    private static final Log log = LogFactory.getLog(TypeRegistry.class);
029
030    private final Map<String, Type> registry = new ConcurrentHashMap<String, Type>();
031
032    private final Map<TypeFamily, List<String>> typeNames = new ConcurrentHashMap<TypeFamily, List<String>>();
033
034    public synchronized void register(final Type type) {
035        String typeName = type.getTypeName();
036        TypeFamily typeFamily = type.getTypeFamily();
037        String key = computeKey(typeFamily, typeName);
038        if (registry.containsKey(key)) {
039            log.debug("Overriding theme " + typeFamily + ": " + typeName);
040        }
041        registry.put(key, type);
042        if (!typeNames.containsKey(typeFamily)) {
043            typeNames.put(typeFamily, new ArrayList<String>());
044        }
045        List<String> typeNamesByFamily = typeNames.get(typeFamily);
046        if (!typeNamesByFamily.contains(typeName)) {
047            typeNamesByFamily.add(typeName);
048        }
049        log.debug("Registered theme " + typeFamily + ": " + typeName);
050    }
051
052    public synchronized void unregister(final Type type) {
053        String typeName = type.getTypeName();
054        TypeFamily typeFamily = type.getTypeFamily();
055        String key = computeKey(typeFamily, typeName);
056        registry.remove(key);
057        if (typeNames.containsKey(typeFamily)) {
058            typeNames.get(typeFamily).remove(typeName);
059        }
060        log.debug("Unregistered theme " + typeFamily + ": " + typeName);
061    }
062
063    public Type lookup(final TypeFamily typeFamily, final String name) {
064        String key = computeKey(typeFamily, name);
065        return registry.get(key);
066    }
067
068    public Type lookup(final TypeFamily typeFamily, final String... names) {
069        for (String name : names) {
070            if (name == null) {
071                continue;
072            }
073            String key = computeKey(typeFamily, name);
074            Type type = registry.get(key);
075            if (type != null) {
076                return type;
077            }
078        }
079        return null;
080
081    }
082
083    public List<String> getTypeNames(final TypeFamily typeFamily) {
084        if (!typeNames.containsKey(typeFamily)) {
085            return new ArrayList<String>();
086        }
087        return typeNames.get(typeFamily);
088    }
089
090    public List<Type> getTypes(final TypeFamily typeFamily) {
091        List<Type> types = new ArrayList<Type>();
092        if (typeNames.containsKey(typeFamily)) {
093            for (String typeName : typeNames.get(typeFamily)) {
094                types.add(lookup(typeFamily, typeName));
095            }
096        }
097        return types;
098    }
099
100    private static String computeKey(final TypeFamily family, final String name) {
101        return String.format("%s/%s", family, name);
102    }
103
104    @Override
105    public synchronized void clear() {
106        registry.clear();
107        typeNames.clear();
108    }
109
110}