001/*
002 *  Copyright 2018 Anyware Services
003 *
004 *  Licensed under the Apache License, Version 2.0 (the "License");
005 *  you may not use this file except in compliance with the License.
006 *  You may obtain a copy of the License at
007 *
008 *      http://www.apache.org/licenses/LICENSE-2.0
009 *
010 *  Unless required by applicable law or agreed to in writing, software
011 *  distributed under the License is distributed on an "AS IS" BASIS,
012 *  WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
013 *  See the License for the specific language governing permissions and
014 *  limitations under the License.
015 */
016package org.ametys.web.frontoffice.search.instance;
017
018import java.util.HashMap;
019import java.util.Map;
020
021import org.apache.avalon.framework.activity.Disposable;
022import org.apache.avalon.framework.component.Component;
023import org.apache.avalon.framework.service.ServiceException;
024import org.apache.avalon.framework.service.ServiceManager;
025import org.apache.avalon.framework.service.Serviceable;
026
027import org.ametys.plugins.repository.AmetysObjectResolver;
028import org.ametys.plugins.repository.AmetysRepositoryException;
029import org.ametys.web.frontoffice.search.SearchService;
030import org.ametys.web.repository.page.ZoneItem;
031import org.ametys.web.repository.page.ZoneItem.ZoneType;
032
033/**
034 * The component managing all {@link SearchServiceInstance}s.
035 */
036public class SearchServiceInstanceManager implements Component, Serviceable, Disposable
037{
038    /** Avalon Role */
039    public static final String ROLE = SearchServiceInstanceManager.class.getName();
040    
041    private AmetysObjectResolver _resolver;
042    private SearchServiceInstanceFactory _factory;
043    private Map<String, SearchServiceInstance> _instances = new HashMap<>();
044
045    @Override
046    public void service(ServiceManager manager) throws ServiceException
047    {
048        _resolver = (AmetysObjectResolver) manager.lookup(AmetysObjectResolver.ROLE);
049        _factory = (SearchServiceInstanceFactory) manager.lookup(SearchServiceInstanceFactory.ROLE);
050    }
051    
052    @Override
053    public void dispose()
054    {
055        _clearCache();
056    }
057    
058    private void _clearCache()
059    {
060        _instances.clear();
061    }
062    
063    /**
064     * Returns <code>true</code> if the given id of a {@link ZoneItem} is an instance of a {@link SearchService}
065     * @param zoneItemId the id of the {@link ZoneItem}
066     * @return <code>true</code> if the given id of a {@link ZoneItem} is an instance of a {@link SearchService}
067     */
068    public boolean isSearchServiceInstance(String zoneItemId)
069    {
070        ZoneItem zoneItem;
071        try
072        {
073            zoneItem = _resolver.resolveById(zoneItemId);
074        }
075        catch (AmetysRepositoryException e)
076        {
077            return false;
078        }
079        return zoneItem != null && zoneItem.getType() == ZoneType.SERVICE && SearchService.ROLE.equals(zoneItem.getServiceId());
080    }
081    
082    /**
083     * Gets, or creates if it does not exist yet, the {@link SearchServiceInstance} which is placed at the given {@link ZoneItem}.
084     * <br>You must call {@link SearchServiceInstanceManager#isSearchServiceInstance(String) isSearchServiceInstance} before to ensure that the given id is an instance of {@link SearchService}
085     * (this check is not done in this method)
086     * @param zoneItemId the id of the {@link ZoneItem}
087     * @return the {@link SearchServiceInstance} which is placed at the given {@link ZoneItem}
088     */
089    public synchronized SearchServiceInstance get(String zoneItemId)
090    {
091        if (_instances.containsKey(zoneItemId))
092        {
093            return _instances.get(zoneItemId);
094        }
095        else
096        {
097            SearchServiceInstance instance = _factory.createSearchServiceInstance(zoneItemId);
098            _instances.put(zoneItemId, instance);
099            return instance;
100        }
101    }
102    
103    /**
104     * Removes the {@link SearchServiceInstance} which is placed at the given {@link ZoneItem}.
105     * @param zoneItemId the id of the {@link ZoneItem}
106     */
107    public synchronized void remove(String zoneItemId)
108    {
109        _instances.remove(zoneItemId);
110    }
111}