Mercurial > dive4elements > river
comparison flys-artifacts/src/main/java/de/intevation/flys/artifacts/datacage/templating/CompiledStatement.java @ 998:b81626b10cb7
Datacage: Moved templating in a better suited package.
flys-artifacts/trunk@2434 c6561f87-3c4e-4783-a992-168aeb5c3f6f
author | Sascha L. Teichmann <sascha.teichmann@intevation.de> |
---|---|
date | Mon, 01 Aug 2011 08:31:09 +0000 |
parents | |
children | aca3b46160cb |
comparison
equal
deleted
inserted
replaced
997:4c82609824c8 | 998:b81626b10cb7 |
---|---|
1 package de.intevation.flys.artifacts.datacage.templating; | |
2 | |
3 import java.util.regex.Pattern; | |
4 import java.util.regex.Matcher; | |
5 | |
6 import java.util.List; | |
7 import java.util.Map; | |
8 import java.util.TreeMap; | |
9 import java.util.ArrayList; | |
10 | |
11 import java.sql.PreparedStatement; | |
12 import java.sql.SQLException; | |
13 import java.sql.Connection; | |
14 import java.sql.ResultSet; | |
15 | |
16 import net.sf.ehcache.Cache; | |
17 import net.sf.ehcache.Element; | |
18 | |
19 import de.intevation.flys.artifacts.cache.CacheFactory; | |
20 | |
21 public class CompiledStatement | |
22 { | |
23 public static final String DATACAGE_DB_CACHE = | |
24 "datacage.db"; | |
25 | |
26 public static final Pattern VAR = | |
27 Pattern.compile("\\$\\{([a-zA-Z0-9_-]+)\\}"); | |
28 | |
29 protected String original; | |
30 protected String statement; | |
31 | |
32 protected Map<String, List<Integer>> positions; | |
33 | |
34 protected int numVars; | |
35 | |
36 public class Instance { | |
37 | |
38 protected PreparedStatement preparedStatement; | |
39 | |
40 public Instance() { | |
41 } | |
42 | |
43 protected ResultData executeCached( | |
44 Cache cache, | |
45 Connection connection, | |
46 StackFrames frames | |
47 ) | |
48 throws SQLException | |
49 { | |
50 Object [] values = new Object[numVars]; | |
51 | |
52 StringBuilder sb = new StringBuilder(original); | |
53 | |
54 for (Map.Entry<String, List<Integer>> entry: positions.entrySet()) { | |
55 String key = entry.getKey(); | |
56 Object value = frames.get(key); | |
57 sb.append(';').append(key).append(':').append(value); | |
58 for (Integer index: entry.getValue()) { | |
59 values[index] = value; | |
60 } | |
61 } | |
62 | |
63 // XXX: Maybe too many collisions? | |
64 // String key = original + Arrays.hashCode(values); | |
65 String key = sb.toString(); | |
66 | |
67 Element element = cache.get(key); | |
68 | |
69 if (element != null) { | |
70 return (ResultData)element.getValue(); | |
71 } | |
72 | |
73 if (preparedStatement == null) { | |
74 preparedStatement = connection.prepareStatement(statement); | |
75 } | |
76 | |
77 for (int i = 0; i < values.length; ++i) { | |
78 preparedStatement.setObject(i+1, values[i]); | |
79 } | |
80 | |
81 ResultData data; | |
82 | |
83 ResultSet result = preparedStatement.executeQuery(); | |
84 try { | |
85 data = new ResultData(preparedStatement.getMetaData()) | |
86 .addAll(result); | |
87 } | |
88 finally { | |
89 result.close(); | |
90 } | |
91 | |
92 element = new Element(key, data); | |
93 cache.put(element); | |
94 | |
95 return data; | |
96 } | |
97 | |
98 protected ResultData executeUncached( | |
99 Connection connection, | |
100 StackFrames frames | |
101 ) | |
102 throws SQLException | |
103 { | |
104 if (preparedStatement == null) { | |
105 preparedStatement = connection.prepareStatement(statement); | |
106 } | |
107 | |
108 for (Map.Entry<String, List<Integer>> entry: positions.entrySet()) { | |
109 Object value = frames.get(entry.getKey()); | |
110 for (Integer index: entry.getValue()) { | |
111 preparedStatement.setObject(index+1, value); | |
112 } | |
113 } | |
114 | |
115 ResultSet result = preparedStatement.executeQuery(); | |
116 try { | |
117 return new ResultData(preparedStatement.getMetaData()) | |
118 .addAll(result); | |
119 } | |
120 finally { | |
121 result.close(); | |
122 } | |
123 } | |
124 | |
125 public ResultData execute(Connection connection, StackFrames frames) | |
126 throws SQLException | |
127 { | |
128 Cache cache = CacheFactory.getCache(DATACAGE_DB_CACHE); | |
129 | |
130 return cache != null | |
131 ? executeCached(cache, connection, frames) | |
132 : executeUncached(connection, frames); | |
133 } | |
134 | |
135 public void close() { | |
136 if (preparedStatement != null) { | |
137 try { | |
138 preparedStatement.close(); | |
139 } | |
140 catch (SQLException sqle) { | |
141 } | |
142 preparedStatement = null; | |
143 } | |
144 } | |
145 } // class Instance | |
146 | |
147 public CompiledStatement() { | |
148 } | |
149 | |
150 public CompiledStatement(String original) { | |
151 this.original = original; | |
152 // TreeMap to ensure order | |
153 positions = new TreeMap<String, List<Integer>>(); | |
154 compile(); | |
155 } | |
156 | |
157 protected void compile() { | |
158 | |
159 StringBuffer sb = new StringBuffer(); | |
160 | |
161 Matcher m = VAR.matcher(original); | |
162 | |
163 int index = 0; | |
164 | |
165 while (m.find()) { | |
166 String key = m.group(1); | |
167 List<Integer> indices = positions.get(key); | |
168 if (indices == null) { | |
169 indices = new ArrayList<Integer>(); | |
170 positions.put(key, indices); | |
171 } | |
172 indices.add(index); | |
173 m.appendReplacement(sb, "?"); | |
174 ++index; | |
175 } | |
176 | |
177 m.appendTail(sb); | |
178 | |
179 numVars = index; | |
180 | |
181 statement = sb.toString(); | |
182 } | |
183 | |
184 public String getStatement() { | |
185 return statement; | |
186 } | |
187 } | |
188 // vim:set ts=4 sw=4 si et sta sts=4 fenc=utf8 : |