View Javadoc

1   /*
2   	Copyright (c) 2009 Olivier Chafik, All Rights Reserved
3   	
4   	This file is part of JNAerator (http://jnaerator.googlecode.com/).
5   	
6   	JNAerator is free software: you can redistribute it and/or modify
7   	it under the terms of the GNU General Public License as published by
8   	the Free Software Foundation, either version 3 of the License, or
9   	(at your option) any later version.
10  	
11  	JNAerator is distributed in the hope that it will be useful,
12  	but WITHOUT ANY WARRANTY; without even the implied warranty of
13  	MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
14  	GNU General Public License for more details.
15  	
16  	You should have received a copy of the GNU General Public License
17  	along with JNAerator.  If not, see <http://www.gnu.org/licenses/>.
18  */
19  package com.ochafik.lang;
20  
21  import java.io.File;
22  import java.lang.reflect.Constructor;
23  import java.lang.reflect.Method;
24  import java.lang.reflect.Modifier;
25  import java.net.MalformedURLException;
26  import java.net.URI;
27  import java.net.URL;
28  import java.text.DateFormat;
29  import java.text.ParseException;
30  import java.util.Collections;
31  import java.util.Date;
32  import java.util.HashMap;
33  import java.util.Iterator;
34  import java.util.LinkedHashMap;
35  import java.util.Map;
36  import java.util.NoSuchElementException;
37  
38  import org.w3c.dom.Node;
39  import org.w3c.dom.NodeList;
40  
41  
42  public class SyntaxUtils {
43  	public static <T> T[] array(T... elements) {
44  		return elements;
45  	}
46  	
47  	public static <T> boolean equal(T a, T b) {
48  		if (a == null)
49  			return b == null;
50  		if (b == null)
51  			return false;
52  		return a.equals(b);
53  	}
54  
55  	public static <T> T as(Object value, Class<T> c) {
56  		if (value == null)
57  			return null;
58  		if (c.isAssignableFrom(value.getClass()))
59  			return c.cast(value);
60  		return null;
61  	}
62  	
63  	interface Converter<T> {
64  		public T convert(Object value) throws Exception;
65  	}
66  	
67  	public static <T> void registerConverter(Class<T> c, Converter<T> converter) {
68  		converters.put(c, converter);
69  	}
70  	
71  	static Map<Class<?>, Converter<?>> converters = new HashMap<Class<?>, Converter<?>>();
72  	static {
73  		registerConverter(Date.class, new Converter<Date>() {
74  			public Date convert(Object value) throws ParseException {
75  				String s = value.toString();
76  				Date date = DateFormat.getDateTimeInstance().parse(s);
77  				if (date == null)
78  					date = DateFormat.getDateInstance().parse(s);
79  				return date;
80  			}
81  		});
82  		
83  		registerConverter(Double.class, new Converter<Double>() {
84  			public Double convert(Object value) throws ParseException {
85  				if (value instanceof Number)
86  					return ((Number)value).doubleValue();
87  				String s = value.toString();
88  				if (s.length() == 0)
89  					return 0.0;
90  				
91  				return Double.parseDouble(s);
92  			}
93  		});
94  		registerConverter(Float.class, new Converter<Float>() {
95  			public Float convert(Object value) throws ParseException {
96  				if (value instanceof Number)
97  					return ((Number)value).floatValue();
98  				String s = value.toString();
99  				if (s.length() == 0)
100 					return 0f;
101 				
102 				return Float.parseFloat(s);
103 			}
104 		});
105 		registerConverter(Long.class, new Converter<Long>() {
106 			public Long convert(Object value) throws ParseException {
107 				if (value instanceof Number)
108 					return ((Number)value).longValue();
109 				String s = value.toString();
110 				if (s.length() == 0)
111 					return 0l;
112 				
113 				return Long.parseLong(s);
114 			}
115 		});
116 		registerConverter(Integer.class, new Converter<Integer>() {
117 			public Integer convert(Object value) throws ParseException {
118 				if (value instanceof Number)
119 					return ((Number)value).intValue();
120 				String s = value.toString();
121 				if (s.length() == 0)
122 					return 0;
123 				
124 				return Integer.parseInt(s);
125 			}
126 		});
127 		registerConverter(Short.class, new Converter<Short>() {
128 			public Short convert(Object value) throws ParseException {
129 				if (value instanceof Number)
130 					return ((Number)value).shortValue();
131 				String s = value.toString();
132 				if (s.length() == 0)
133 					return 0;
134 				
135 				return Short.parseShort(s);
136 			}
137 		});
138 		registerConverter(String.class, new Converter<String>() {
139 			public String convert(Object value) throws ParseException {
140 				if (value instanceof Date)
141 					return DateFormat.getDateInstance().format((Date)value);
142 				return value.toString();
143 			}
144 		});
145 		registerConverter(File.class, new Converter<File>() {
146 			public File convert(Object value) throws ParseException {
147 				if (value instanceof URI)
148 					try {
149 						value = ((URI)value).toURL();
150 					} catch (MalformedURLException e1) {}
151 				
152 				if (value instanceof String) {
153 					try {
154 						value = new URL((String)value);
155 					} catch (MalformedURLException e) {}
156 				}
157 				if (value instanceof URL)
158 					return new File(((URL)value).getFile());
159 				
160 				String s = value.toString();
161 				if (s.length() == 0)
162 					return null;
163 				
164 				return new File(s);
165 			}
166 		});
167 		registerConverter(URL.class, new Converter<URL>() {
168 			public URL convert(Object value) {
169 				if (value instanceof URI)
170 					try {
171 						return ((URI)value).toURL();
172 					} catch (MalformedURLException e1) {}
173 				
174 				if (value instanceof File)
175 					try {
176 						return ((File)value).toURI().toURL();
177 					} catch (MalformedURLException e1) {}
178 				
179 				String s = value.toString();
180 				if (s.length() == 0)
181 					return null;
182 				
183 				try {
184 					return new URL(s);
185 				} catch (MalformedURLException e) {}
186 				
187 				try {
188 					return new File(s).toURI().toURL();
189 				} catch (MalformedURLException e) {}
190 				
191 				return null;
192 			}
193 		});
194 	}
195 	
196 	@SuppressWarnings("unchecked")
197 	public static <T> T convert(Object value, Class<T> c) {
198 		if (value == null)
199 			return null;
200 		
201 		Class<?> type = value.getClass();
202 		if (c.isAssignableFrom(type))
203 			return c.cast(value);
204 		
205 		Converter<T> converter = (Converter<T>)converters.get(c);
206 		if (converter != null)
207 			try {
208 				return converter.convert(value);
209 			} catch (Exception e) {
210 				e.printStackTrace();
211 			}
212 			
213 		for (Constructor<?> cons : c.getConstructors()) {
214 			Class<?>[] parameterTypes = cons.getParameterTypes();
215 			if (parameterTypes.length == 1 && parameterTypes[0].isAssignableFrom(type)) {
216 				try {
217 					return (T)cons.newInstance(value);
218 				} catch (Exception e) {
219 					e.printStackTrace();
220 				}
221 			}
222 		}
223 		
224 		for (Method meth : c.getMethods()) {
225 			String name = meth.getName();
226 			if ((meth.getModifiers() & Modifier.STATIC) == 0)
227 				continue;
228 			
229 			if (!" parse createInstance newInstance ".contains(" " + name + " "))
230 				continue;
231 			
232 			Class<?>[] parameterTypes = meth.getParameterTypes();
233 			if (parameterTypes.length == 1 && parameterTypes[0].isAssignableFrom(type)) {
234 				try {
235 					return (T)meth.invoke(null, value);
236 				} catch (Exception e) {
237 					e.printStackTrace();
238 				}
239 			}
240 		}
241 		return null;
242 	}
243 	
244 	public static class EasyMap<K, V> extends LinkedHashMap<K, V> {
245 		private static final long serialVersionUID = -3087972422440202407L;
246 
247 		public EasyMap<K, V> add(K key, V value) {
248 			put(key, value);
249 			return this;
250 		}
251 	}
252 	public static <K, V> EasyMap<K, V> map(K key, V value) {
253 		return new EasyMap<K, V>().add(key, value);
254 	}
255 
256 	@SuppressWarnings("unchecked")
257 	public static Iterable<Node> iterable(final NodeList list) {
258 		if (list == null)
259 			return Collections.EMPTY_LIST;
260 		
261 		return new Iterable<Node>() {
262 			int nextPos = 0;
263 			public Iterator<Node> iterator() {
264 				return new Iterator<Node>() {
265 					public Node next() {
266 						if (nextPos >= list.getLength())
267 							throw new NoSuchElementException();
268 						return list.item(nextPos++);
269 					}
270 					public boolean hasNext() {
271 						return nextPos < list.getLength();
272 					}
273 					public void remove() {
274 						throw new UnsupportedOperationException();
275 					}
276 				};
277 			}
278 		};
279 	}
280 }