1 package org.apache.torque.engine.database.model;
2
3 /* ====================================================================
4 * The Apache Software License, Version 1.1
5 *
6 * Copyright (c) 2001-2003 The Apache Software Foundation. All rights
7 * reserved.
8 *
9 * Redistribution and use in source and binary forms, with or without
10 * modification, are permitted provided that the following conditions
11 * are met:
12 *
13 * 1. Redistributions of source code must retain the above copyright
14 * notice, this list of conditions and the following disclaimer.
15 *
16 * 2. Redistributions in binary form must reproduce the above copyright
17 * notice, this list of conditions and the following disclaimer in
18 * the documentation and/or other materials provided with the
19 * distribution.
20 *
21 * 3. The end-user documentation included with the redistribution,
22 * if any, must include the following acknowledgment:
23 * "This product includes software developed by the
24 * Apache Software Foundation (http://www.apache.org/)."
25 * Alternately, this acknowledgment may appear in the software itself,
26 * if and wherever such third-party acknowledgments normally appear.
27 *
28 * 4. The names "Apache" and "Apache Software Foundation" and
29 * "Apache Turbine" must not be used to endorse or promote products
30 * derived from this software without prior written permission. For
31 * written permission, please contact apache@apache.org.
32 *
33 * 5. Products derived from this software may not be called "Apache",
34 * "Apache Turbine", nor may "Apache" appear in their name, without
35 * prior written permission of the Apache Software Foundation.
36 *
37 * THIS SOFTWARE IS PROVIDED ``AS IS'' AND ANY EXPRESSED OR IMPLIED
38 * WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES
39 * OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
40 * DISCLAIMED. IN NO EVENT SHALL THE APACHE SOFTWARE FOUNDATION OR
41 * ITS CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
42 * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
43 * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF
44 * USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
45 * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY,
46 * OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT
47 * OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
48 * SUCH DAMAGE.
49 * ====================================================================
50 *
51 * This software consists of voluntary contributions made by many
52 * individuals on behalf of the Apache Software Foundation. For more
53 * information on the Apache Software Foundation, please see
54 * <http://www.apache.org/>.
55 */
56
57 import java.io.File;
58 import java.io.FileInputStream;
59 import java.util.ArrayList;
60 import java.util.HashMap;
61 import java.util.Iterator;
62 import java.util.List;
63 import java.util.Map;
64 import java.util.Properties;
65
66 import org.apache.commons.lang.StringUtils;
67
68 import org.apache.commons.logging.Log;
69 import org.apache.commons.logging.LogFactory;
70
71 import org.apache.torque.engine.EngineException;
72 import org.apache.torque.engine.database.transform.DTDResolver;
73
74 import org.xml.sax.Attributes;
75
76 /***
77 * A class for holding application data structures.
78 *
79 * @author <a href="mailto:leon@opticode.co.za>Leon Messerschmidt</a>
80 * @author <a href="mailto:jmcnally@collab.net>John McNally</a>
81 * @author <a href="mailto:dlr@finemaltcoding.com>Daniel Rall</a>
82 * @version $Id: AppData.java,v 1.4 2003/07/25 16:40:30 henning Exp $
83 */
84 public class AppData
85 {
86 /*** Logging class from commons.logging */
87 private static Log log = LogFactory.getLog(AppData.class);
88
89 /***
90 * The list of databases for this application.
91 */
92 private List dbList = new ArrayList(5);
93
94 /***
95 * The table of idiosyncrasies for various database types.
96 */
97 private Map idiosyncrasyTable = new HashMap(8);
98
99 /***
100 * The type for our databases.
101 */
102 private String databaseType;
103
104 /***
105 * The base of the path to the properties file, including trailing slash.
106 */
107 private String basePropsFilePath;
108
109 /***
110 * Name of the database. Only one database definition
111 * is allowed in one XML descriptor.
112 */
113 private String name;
114
115 // flag to complete initialization only once.
116 boolean isInitialized;
117
118 /***
119 * Creates a new instance for the specified database type.
120 *
121 * @param databaseType The default type for any databases added to
122 * this application model.
123 * @param basePropsFilePath The base of the path to the properties
124 * file, including trailing slash.
125 */
126 public AppData(String databaseType, String basePropsFilePath)
127 {
128 this.basePropsFilePath = basePropsFilePath;
129 this.databaseType = databaseType;
130 }
131
132 /***
133 * Each database has its own list of idiosyncrasies which can be
134 * configured by editting its <code>db.props</code> file.
135 *
136 * @param databaseType The type of database to retrieve the
137 * properties of.
138 * @return The idiosyncrasies of <code>databaseType</code>.
139 * @exception EngineException Couldn't locate properties file.
140 */
141 protected Properties getIdiosyncrasies(String databaseType)
142 throws EngineException
143 {
144 Properties idiosyncrasies
145 = (Properties) idiosyncrasyTable.get(databaseType);
146
147 // If we haven't yet loaded the properties and we have the
148 // information to do so, proceed with loading.
149 if (idiosyncrasies == null && basePropsFilePath != null
150 && databaseType != null)
151 {
152 idiosyncrasies = new Properties();
153 File propsFile = new File(basePropsFilePath + databaseType,
154 "db.props");
155 if (propsFile.exists())
156 {
157 try
158 {
159 idiosyncrasies.load(new FileInputStream(propsFile));
160 }
161 catch (Exception e)
162 {
163 log.error(e, e);
164 }
165 idiosyncrasyTable.put(databaseType, idiosyncrasies);
166 }
167 else
168 {
169 try
170 {
171 String path = '/' + basePropsFilePath + databaseType
172 + "/db.props";
173 idiosyncrasies.load(getClass().getResourceAsStream(path));
174 }
175 catch (Exception e)
176 {
177 log.error(e, e);
178 }
179 }
180
181 if (idiosyncrasies.isEmpty())
182 {
183 throw new EngineException("Database-specific properties "
184 + "file does not exist: "
185 + propsFile.getAbsolutePath());
186 }
187 }
188 return idiosyncrasies;
189 }
190
191 /***
192 * Set the name of the database.
193 *
194 * @param name of the database.
195 */
196 public void setName(String name)
197 {
198 this.name = name;
199 }
200
201 /***
202 * Get the name of the database.
203 *
204 * @return String name
205 */
206 public String getName()
207 {
208 return name;
209 }
210
211 /***
212 * Get the short name of the database (without the '-schema' postfix).
213 *
214 * @return String name
215 */
216 public String getShortName()
217 {
218 return StringUtils.replace(name, "-schema", "");
219 }
220
221 /***
222 * Get database object.
223 *
224 * @return Database database
225 */
226 public Database getDatabase()
227 throws EngineException
228 {
229 doFinalInitialization();
230 return (Database) dbList.get(0);
231 }
232
233 /***
234 * Return an array of all databases
235 *
236 * @return Array of Database objects
237 */
238 public Database[] getDatabases()
239 throws EngineException
240 {
241 doFinalInitialization();
242 int size = dbList.size();
243 Database[] dbs = new Database[size];
244 for (int i = 0; i < size; i++)
245 {
246 dbs[i] = (Database) dbList.get(i);
247 }
248 return dbs;
249 }
250
251 /***
252 * Returns whether this application has multiple databases.
253 *
254 * @return true if the application has multiple databases
255 */
256 public boolean hasMultipleDatabases()
257 {
258 return (dbList.size() > 1);
259 }
260
261 /***
262 * Return the database with the specified name.
263 *
264 * @param name database name
265 * @return A Database object. If it does not exist it returns null
266 */
267 public Database getDatabase (String name)
268 throws EngineException
269 {
270 doFinalInitialization();
271 for (Iterator i = dbList.iterator(); i.hasNext();)
272 {
273 Database db = (Database) i.next();
274 if (db.getName().equals(name))
275 {
276 return db;
277 }
278 }
279 return null;
280 }
281
282 /***
283 * An utility method to add a new database from an xml attribute.
284 *
285 * @param attrib the xml attributes
286 * @return the database
287 */
288 public Database addDatabase(Attributes attrib)
289 {
290 Database db = new Database();
291 db.loadFromXML (attrib);
292 addDatabase (db);
293 return db;
294 }
295
296 /***
297 * Add a database to the list and sets the AppData property to this
298 * AppData
299 *
300 * @param db the database to add
301 */
302 public void addDatabase(Database db)
303 {
304 db.setAppData (this);
305 if (db.getName() == null)
306 {
307 /*** @task check this */
308 db.setName("default"); // Torque.getDefaultDB());
309 }
310 if (db.getDatabaseType() == null)
311 {
312 db.setDatabaseType(databaseType);
313 }
314 dbList.add(db);
315 }
316
317 private void doFinalInitialization()
318 throws EngineException
319 {
320 if (!isInitialized)
321 {
322 Iterator dbs = dbList.iterator();
323 while (dbs.hasNext())
324 {
325 ((Database) dbs.next()).doFinalInitialization();
326 }
327 isInitialized = true;
328 }
329 }
330
331 /***
332 * Creats a string representation of this AppData.
333 * The representation is given in xml format.
334 *
335 * @return representation in xml format
336 */
337 public String toString()
338 {
339 StringBuffer result = new StringBuffer();
340
341 result.append ("<?xml version=\"1.0\"?>\n");
342 result.append ("<!DOCTYPE database SYSTEM \""
343 + DTDResolver.WEB_SITE_DTD + "\">\n");
344 result.append("<!-- Autogenerated by SQLToXMLSchema! -->\n");
345 for (Iterator i = dbList.iterator(); i.hasNext();)
346 {
347 result.append (i.next());
348 }
349 return result.toString();
350 }
351 }
This page was automatically generated by Maven