View Javadoc
1   /**
2    *    Copyright 2015 the original author or authors.
3    *
4    *    Licensed under the Apache License, Version 2.0 (the "License");
5    *    you may not use this file except in compliance with the License.
6    *    You may obtain a copy of the License at
7    *
8    *       http://www.apache.org/licenses/LICENSE-2.0
9    *
10   *    Unless required by applicable law or agreed to in writing, software
11   *    distributed under the License is distributed on an "AS IS" BASIS,
12   *    WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13   *    See the License for the specific language governing permissions and
14   *    limitations under the License.
15   */
16  package org.mybatis.caches.redis;
17  
18  import java.io.IOException;
19  import java.io.InputStream;
20  import java.util.Map;
21  import java.util.Properties;
22  
23  import org.apache.ibatis.cache.CacheException;
24  import org.apache.ibatis.reflection.MetaObject;
25  import org.apache.ibatis.reflection.SystemMetaObject;
26  
27  /**
28   * Converter from the Config to a proper {@link RedisConfig}.
29   *
30   * @author Eduardo Macarron
31   */
32  final class RedisConfigurationBuilder {
33  
34  	/**
35  	 * This class instance.
36  	 */
37  	private static final RedisConfigurationBuilder INSTANCE = new RedisConfigurationBuilder();
38  
39  	private static final String SYSTEM_PROPERTY_REDIS_PROPERTIES_FILENAME = "redis.properties.filename";
40  
41  	private static final String REDIS_RESOURCE = "redis.properties";
42  
43  	private final String redisPropertiesFilename;
44  
45  	/**
46  	 * Hidden constructor, this class can't be instantiated.
47  	 */
48  	private RedisConfigurationBuilder() {
49  		redisPropertiesFilename = System.getProperty(SYSTEM_PROPERTY_REDIS_PROPERTIES_FILENAME, REDIS_RESOURCE);
50  	}
51  
52  	/**
53  	 * Return this class instance.
54  	 *
55  	 * @return this class instance.
56  	 */
57  	public static RedisConfigurationBuilder getInstance() {
58  		return INSTANCE;
59  	}
60  
61  	/**
62  	 * Parses the Config and builds a new {@link RedisConfig}.
63  	 *
64  	 * @return the converted {@link RedisConfig}.
65  	 */
66  	public RedisConfig parseConfiguration() {
67  		return parseConfiguration(getClass().getClassLoader());
68  	}
69  
70  	/**
71  	 * Parses the Config and builds a new {@link RedisConfig}.
72  	 *
73  	 * @param the
74  	 *            {@link ClassLoader} used to load the
75  	 *            {@code memcached.properties} file in classpath.
76  	 * @return the converted {@link RedisConfig}.
77  	 */
78  	public RedisConfig parseConfiguration(ClassLoader classLoader) {
79  		Properties config = new Properties();
80  
81  		InputStream input = classLoader.getResourceAsStream(redisPropertiesFilename);
82  		if (input != null) {
83  			try {
84  				config.load(input);
85  			} catch (IOException e) {
86  				throw new RuntimeException(
87  						"An error occurred while reading classpath property '"
88  								+ redisPropertiesFilename
89  								+ "', see nested exceptions", e);
90  			} finally {
91  				try {
92  					input.close();
93  				} catch (IOException e) {
94  					// close quietly
95  				}
96  			}
97  		}
98  
99  		RedisConfig jedisConfig = new RedisConfig();
100 		setConfigProperties(config, jedisConfig);
101 		return jedisConfig;
102 	}
103 
104 	private void setConfigProperties(Properties properties,
105 			RedisConfig jedisConfig) {
106 		if (properties != null) {
107 			MetaObject metaCache = SystemMetaObject.forObject(jedisConfig);
108 			for (Map.Entry<Object, Object> entry : properties.entrySet()) {
109 				String name = (String) entry.getKey();
110 				String value = (String) entry.getValue();
111 				if (metaCache.hasSetter(name)) {
112 					Class<?> type = metaCache.getSetterType(name);
113 					if (String.class == type) {
114 						metaCache.setValue(name, value);
115 					} else if (int.class == type || Integer.class == type) {
116 						metaCache.setValue(name, Integer.valueOf(value));
117 					} else if (long.class == type || Long.class == type) {
118 						metaCache.setValue(name, Long.valueOf(value));
119 					} else if (short.class == type || Short.class == type) {
120 						metaCache.setValue(name, Short.valueOf(value));
121 					} else if (byte.class == type || Byte.class == type) {
122 						metaCache.setValue(name, Byte.valueOf(value));
123 					} else if (float.class == type || Float.class == type) {
124 						metaCache.setValue(name, Float.valueOf(value));
125 					} else if (boolean.class == type || Boolean.class == type) {
126 						metaCache.setValue(name, Boolean.valueOf(value));
127 					} else if (double.class == type || Double.class == type) {
128 						metaCache.setValue(name, Double.valueOf(value));
129 					} else {
130 						throw new CacheException("Unsupported property type: '"
131 								+ name + "' of type " + type);
132 					}
133 				}
134 			}
135 		}
136 	}
137 
138 }