2 * This document is a part of the source code and related artifacts
3 * for CollectionSpace, an open source collections management system
4 * for museums and related institutions:
6 * http://www.collectionspace.org
7 * http://wiki.collectionspace.org
9 * Copyright 2009 University of California at Berkeley
11 * Licensed under the Educational Community License (ECL), Version 2.0.
12 * You may not use this file except in compliance with this License.
14 * You may obtain a copy of the ECL 2.0 License at
16 * https://source.collectionspace.org/collection-space/LICENSE.txt
18 * Unless required by applicable law or agreed to in writing, software
19 * distributed under the License is distributed on an "AS IS" BASIS,
20 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
21 * See the License for the specific language governing permissions and
22 * limitations under the License.
24 package org.collectionspace.services.common.config;
27 import java.io.IOException;
28 import java.util.ArrayList;
29 import java.util.Hashtable;
30 import java.util.List;
32 import org.collectionspace.services.common.service.ServiceBindingType;
33 import org.collectionspace.services.common.tenant.RepositoryDomainType;
34 import org.collectionspace.services.common.tenant.TenantBindingType;
35 import org.collectionspace.services.common.tenant.TenantBindingConfig;
36 import org.collectionspace.services.common.types.PropertyItemType;
37 import org.slf4j.Logger;
38 import org.slf4j.LoggerFactory;
41 * ServicesConfigReader reads service layer specific configuration
43 * $LastChangedRevision: $
46 public class TenantBindingConfigReaderImpl
47 extends AbstractConfigReaderImpl<List<TenantBindingType>> {
48 final private static String TENANT_BINDINGS_ERROR = "Tenant bindings error: ";
49 final private static String TENANT_BINDINGS_FILENAME = "tenant-bindings.xml";
50 final private static String TENANT_BINDINGS_ROOTDIRNAME = "tenants";
52 final Logger logger = LoggerFactory.getLogger(TenantBindingConfigReaderImpl.class);
53 private List<TenantBindingType> tenantBindingTypeList;
54 //tenant id, tenant binding
55 private Hashtable<String, TenantBindingType> tenantBindings =
56 new Hashtable<String, TenantBindingType>();
58 private Hashtable<String, RepositoryDomainType> domains =
59 new Hashtable<String, RepositoryDomainType>();
60 //tenant-qualified servicename, service binding
61 private Hashtable<String, ServiceBindingType> serviceBindings =
62 new Hashtable<String, ServiceBindingType>();
64 public TenantBindingConfigReaderImpl(String serverRootDir) {
69 public String getFileName() {
70 return TENANT_BINDINGS_FILENAME;
73 protected File getTenantsRootDir() {
75 String tenantsRootPath = getConfigRootDir() + File.separator + TENANT_BINDINGS_ROOTDIRNAME;
76 File tenantsRootDir = new File(tenantsRootPath);
77 if (tenantsRootDir.exists() == true) {
78 result = tenantsRootDir;
79 logger.debug("Tenants home directory is: " + tenantsRootDir.getAbsolutePath()); //FIXME: REM - Add proper if (logger.isDebug() == true) check
81 logger.error("Tenants home directory is missing. Can't find: " + tenantsRootDir.getAbsolutePath()); //FIXME: REM - Add proper if (logger.isError() == true) check
87 public void read() throws Exception {
88 String tenantsRootPath = getTenantsRootDir().getAbsolutePath();
89 read(tenantsRootPath);
93 public void read(String tenantRootDirPath) throws Exception {
94 File tenantsRootDir = new File(tenantRootDirPath);
95 if (tenantsRootDir.exists() == false) {
96 throw new Exception("Cound not find tenant bindings root directory: " +
99 List<File> tenantDirs = getDirectories(tenantsRootDir);
100 tenantBindingTypeList = readTenantConfigs(tenantDirs);
102 for (TenantBindingType tenantBinding : tenantBindingTypeList) {
103 tenantBindings.put(tenantBinding.getId(), tenantBinding);
104 readDomains(tenantBinding);
105 readServiceBindings(tenantBinding);
106 if (logger.isDebugEnabled()) {
107 logger.debug("read() added tenant id=" + tenantBinding.getId()
108 + " name=" + tenantBinding.getName());
113 List<TenantBindingType> readTenantConfigs(List<File> tenantDirList) throws IOException {
114 List<TenantBindingType> result = new ArrayList<TenantBindingType>();
116 // Iterate through a list of directories.
118 for (File tenantDir : tenantDirList) {
119 boolean found = false;
120 String errMessage = null;
121 File configFile = new File(tenantDir.getAbsoluteFile() + File.separator + TENANT_BINDINGS_FILENAME);
122 if (configFile.exists() == true) {
123 TenantBindingConfig tenantBindingConfig = (TenantBindingConfig) parse(
124 configFile, TenantBindingConfig.class);
125 if (tenantBindingConfig != null) {
126 TenantBindingType binding = tenantBindingConfig.getTenantBinding();
127 if (binding != null) {
130 if (logger.isInfoEnabled() == true) {
131 logger.info("Parsed tenant configureation for: " + binding.getDisplayName());
134 errMessage = "Cound not parse the tentant bindings in: ";
137 errMessage = "Could not parse the tenant bindings file: ";
140 errMessage = "Cound not find a tenant configuration file: ";
142 if (found == false) {
143 if (logger.isErrorEnabled() == true) {
144 errMessage = errMessage != null ? errMessage : TENANT_BINDINGS_ERROR;
145 logger.error(errMessage + configFile.getAbsolutePath());
153 private void readDomains(TenantBindingType tenantBinding) throws Exception {
154 for (RepositoryDomainType domain : tenantBinding.getRepositoryDomain()) {
155 domains.put(domain.getName(), domain);
159 private void readServiceBindings(TenantBindingType tenantBinding) throws Exception {
160 for (ServiceBindingType serviceBinding : tenantBinding.getServiceBindings()) {
161 String key = getTenantQualifiedServiceName(tenantBinding.getId(),
162 serviceBinding.getName());
163 serviceBindings.put(key, serviceBinding);
164 if (logger.isDebugEnabled()) {
165 logger.debug("readServiceBindings() added service "
167 + " workspace=" + serviceBinding.getName());
173 public List<TenantBindingType> getConfiguration() {
174 return tenantBindingTypeList;
178 * getTenantBindings returns all the tenant bindings read from configuration
181 public Hashtable<String, TenantBindingType> getTenantBindings() {
182 return tenantBindings;
186 * getTenantBinding gets tenant binding for given tenant
190 public TenantBindingType getTenantBinding(
192 return tenantBindings.get(tenantId);
196 * getRepositoryDomain gets repository domain configuration for the given name
200 public RepositoryDomainType getRepositoryDomain(String domainName) {
201 return domains.get(domainName.trim());
205 * getRepositoryDomain gets repository domain configuration for the given service
206 * and given tenant id
211 public RepositoryDomainType getRepositoryDomain(String tenantId, String serviceName) {
212 ServiceBindingType serviceBinding = getServiceBinding(tenantId, serviceName);
213 if (serviceBinding == null) {
214 throw new IllegalArgumentException("no service binding found for " + serviceName
215 + " of tenant with id=" + tenantId);
217 String repoDomain = serviceBinding.getRepositoryDomain();
218 if (repoDomain == null) {
219 /* This is excessive - every call to a JPA based service dumps this msg.
220 if (logger.isDebugEnabled()) {
221 logger.debug("No repository domain configured for " + serviceName
222 + " of tenant with id=" + tenantId);
227 return domains.get(repoDomain.trim());
231 * getServiceBinding gets service binding for given tenant for a given service
236 public ServiceBindingType getServiceBinding(
237 String tenantId, String serviceName) {
238 String key = getTenantQualifiedServiceName(tenantId, serviceName);
239 return serviceBindings.get(key);
243 * getServiceBinding gets service binding for given tenant for a given service
248 public List<ServiceBindingType> getServiceBindingsByType(
249 String tenantId, String serviceType) {
250 ArrayList<ServiceBindingType> list = null;
251 TenantBindingType tenant = tenantBindings.get(tenantId);
252 if (tenant != null) {
253 for (ServiceBindingType sb : tenant.getServiceBindings()) {
254 if (serviceType.equals(sb.getType())) {
256 list = new ArrayList<ServiceBindingType>();
268 * @return the properly qualified service name
270 public static String getTenantQualifiedServiceName(
271 String tenantId, String serviceName) {
272 return tenantId + "." + serviceName.toLowerCase();
276 * Sets properties in the passed list on the local properties for this TenantBinding.
277 * Note: will only set properties not already set on the TenantBinding.
280 * @param propagateToServices If true, recurses to set set properties
281 * on the associated services.
283 public void setDefaultPropertiesOnTenants(List<PropertyItemType> propList,
284 boolean propagateToServices) {
285 // For each tenant, set properties in list that are not already set
286 if (propList == null || propList.isEmpty()) {
289 for (TenantBindingType tenant : tenantBindings.values()) {
290 for (PropertyItemType prop : propList) {
291 TenantBindingUtils.setPropertyValue(tenant,
292 prop, TenantBindingUtils.SET_PROP_IF_MISSING);
294 if (propagateToServices) {
295 TenantBindingUtils.propagatePropertiesToServices(tenant,
296 TenantBindingUtils.SET_PROP_IF_MISSING);