mirror of https://github.com/apache/openjpa.git
Validate product derivations before caching them so we don't end up with runtime
errors when clients use JPA without jdo.jar or JDO without jpa.jar. Give a more succinct warning when some product derivations are uninstantiable, with more detailed information available via the ProductDerivations class's main(). git-svn-id: https://svn.apache.org/repos/asf/incubator/openjpa/trunk@463829 13f79535-47bb-0310-9956-ffa450edef68
This commit is contained in:
parent
72594b2ac8
commit
c8b5b2746e
|
@ -625,44 +625,6 @@ public class SchemaTool {
|
|||
}
|
||||
}
|
||||
|
||||
// indexes
|
||||
/*
|
||||
if (_indexes)
|
||||
{
|
||||
Index[] idxs;
|
||||
Index idx;
|
||||
for (int i = 0; i < schemas.length; i++)
|
||||
{
|
||||
tabs = schemas[i].getTables ();
|
||||
for (int j = 0; j < tabs.length; j++)
|
||||
{
|
||||
if (!isDroppable (tabs[j]))
|
||||
continue;
|
||||
idxs = tabs[j].getIndexes ();
|
||||
reposTable = repos.findTable (tabs[j]);
|
||||
if (!tables && reposTable == null)
|
||||
continue;
|
||||
|
||||
for (int k = 0; k < idxs.length; k++)
|
||||
{
|
||||
idx = null;
|
||||
if (reposTable != null)
|
||||
idx = reposTable.getIndex (idxs[k].getName ());
|
||||
if (reposTable == null || idx == null
|
||||
|| !idxs[k].equalsIndex (idx))
|
||||
{
|
||||
if (dropIndex (idxs[k]))
|
||||
tabs[j].removeIndex (idxs[k]);
|
||||
else
|
||||
_log.warn (_loc.get ("drop-index", idxs[k],
|
||||
tabs[j]));
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
*/
|
||||
|
||||
// primary keys
|
||||
if (_pks) {
|
||||
PrimaryKey pk;
|
||||
|
@ -830,41 +792,6 @@ public class SchemaTool {
|
|||
}
|
||||
}
|
||||
|
||||
// indexes
|
||||
/*
|
||||
if (_indexes)
|
||||
{
|
||||
Index[] idxs;
|
||||
Index idx;
|
||||
for (int i = 0; i < schemas.length; i++)
|
||||
{
|
||||
tabs = schemas[i].getTables ();
|
||||
for (int j = 0; j < tabs.length; j++)
|
||||
{
|
||||
if (!isDroppable (tabs[j]))
|
||||
continue;
|
||||
idxs = tabs[j].getIndexes ();
|
||||
dbTable = db.findTable (tabs[j]);
|
||||
for (int k = 0; k < idxs.length; k++)
|
||||
{
|
||||
idx = null;
|
||||
if (dbTable != null)
|
||||
idx = dbTable.getIndex (idxs[k].getName ());
|
||||
if (dbTable == null || idx == null)
|
||||
continue;
|
||||
|
||||
if (dropIndex (idxs[k]))
|
||||
if (dbTable != null)
|
||||
dbTable.removeIndex (idx);
|
||||
else
|
||||
_log.warn (_loc.get ("drop-index", idxs[k],
|
||||
tabs[j]));
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
*/
|
||||
|
||||
// drop the tables we calculated above
|
||||
dropTables(drops, db);
|
||||
|
||||
|
@ -885,11 +812,12 @@ public class SchemaTool {
|
|||
if (dbTable == null || col == null)
|
||||
continue;
|
||||
|
||||
if (dropColumn(cols[k]))
|
||||
if (dropColumn(cols[k])) {
|
||||
if (dbTable != null)
|
||||
dbTable.removeColumn(col);
|
||||
else
|
||||
_log.warn(_loc.get("drop-col", cols[k], tabs[j]));
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
@ -948,11 +876,9 @@ public class SchemaTool {
|
|||
if (tables.isEmpty())
|
||||
return;
|
||||
|
||||
Collection nodes = tables;
|
||||
|
||||
Table table;
|
||||
Table changeTable;
|
||||
for (Iterator itr = nodes.iterator(); itr.hasNext();) {
|
||||
for (Iterator itr = tables.iterator(); itr.hasNext();) {
|
||||
table = (Table) itr.next();
|
||||
if (dropTable(table)) {
|
||||
changeTable = change.findTable(table);
|
||||
|
@ -1338,11 +1264,14 @@ public class SchemaTool {
|
|||
* <ul>
|
||||
* <li>Write a script to stdout to re-create the current database
|
||||
* schema:<br />
|
||||
* <code>java org.apache.openjpa.jdbc.schema.SchemaTool -f stdout -a createDB</code>
|
||||
* <code>java org.apache.openjpa.jdbc.schema.SchemaTool -f stdout
|
||||
* -a createDB</code></li>
|
||||
* <li>Drop the current database schema:<br />
|
||||
* <code>java org.apache.openjpa.jdbc.schema.SchemaTool -a dropDB</code></li>
|
||||
* <code>java org.apache.openjpa.jdbc.schema.SchemaTool
|
||||
* -a dropDB</code></li>
|
||||
* <li>Create a schema based on an XML schema definition file:<br />
|
||||
* <code>java org.apache.openjpa.jdbc.schema.SchemaTool myschema.xml</code></li>
|
||||
* <code>java org.apache.openjpa.jdbc.schema.SchemaTool
|
||||
* myschema.xml</code></li>
|
||||
* </ul>
|
||||
*/
|
||||
public static void main(String[] args)
|
||||
|
|
|
@ -3561,14 +3561,8 @@ public class DBDictionary
|
|||
return key;
|
||||
} finally {
|
||||
if (rs != null)
|
||||
try {
|
||||
rs.close();
|
||||
} catch (SQLException se) {
|
||||
}
|
||||
try {
|
||||
stmnt.close();
|
||||
} catch (SQLException se) {
|
||||
}
|
||||
try { rs.close(); } catch (SQLException se) {}
|
||||
try { stmnt.close(); } catch (SQLException se) {}
|
||||
}
|
||||
}
|
||||
|
||||
|
|
|
@ -31,6 +31,10 @@ public abstract class AbstractProductDerivation
|
|||
return null;
|
||||
}
|
||||
|
||||
public void validate()
|
||||
throws Exception {
|
||||
}
|
||||
|
||||
public ConfigurationProvider loadGlobals(ClassLoader loader)
|
||||
throws Exception {
|
||||
return null;
|
||||
|
|
|
@ -45,6 +45,15 @@ public interface ProductDerivation {
|
|||
*/
|
||||
public String getConfigurationPrefix();
|
||||
|
||||
/**
|
||||
* Ensure that this derivation is valid. This action might consist of
|
||||
* loading classes for the product this derivation represents to be sure
|
||||
* they exist. Throw any throwable to indicate an invalid derivation.
|
||||
* Invalid derivations will not be used.
|
||||
*/
|
||||
public void validate()
|
||||
throws Exception;
|
||||
|
||||
/**
|
||||
* Load globals into the returned ConfigurationProvider, or return null if
|
||||
* no globals are found.
|
||||
|
|
|
@ -38,31 +38,41 @@ public class ProductDerivations {
|
|||
(ProductDerivations.class);
|
||||
|
||||
private static final ProductDerivation[] _derivations;
|
||||
private static final String[] _derivationNames;
|
||||
private static final Throwable[] _derivationErrors;
|
||||
private static final String[] _prefixes;
|
||||
static {
|
||||
ClassLoader cl = ProductDerivation.class.getClassLoader();
|
||||
String[] pds = Services.getImplementors(ProductDerivation.class, cl);
|
||||
List derivations = new ArrayList(pds.length);
|
||||
for (int i = 0; i < pds.length; i++) {
|
||||
ClassLoader l = ProductDerivation.class.getClassLoader();
|
||||
_derivationNames = Services.getImplementors(ProductDerivation.class, l);
|
||||
_derivationErrors = new Throwable[_derivationNames.length];
|
||||
List derivations = new ArrayList(_derivationNames.length);
|
||||
for (int i = 0; i < _derivationNames.length; i++) {
|
||||
try {
|
||||
Class cls = Class.forName(pds[i], true, cl);
|
||||
derivations.add(cls.newInstance());
|
||||
} catch (UnsupportedClassVersionError ucve) {
|
||||
// ignore so that < 1.5 users don't get errors about
|
||||
// 1.5 products they aren't using
|
||||
ProductDerivation d = (ProductDerivation) Class.
|
||||
forName(_derivationNames[i], true, l).newInstance();
|
||||
d.validate();
|
||||
derivations.add(d);
|
||||
} catch (Throwable t) {
|
||||
System.err.println(_loc.get("bad-product-derivation", pds[i],
|
||||
t));
|
||||
_derivationErrors[i] = t;
|
||||
}
|
||||
}
|
||||
|
||||
// must be at least one product derivation to define metadata factories,
|
||||
// etc.
|
||||
if (derivations.isEmpty()) {
|
||||
Localizer loc = Localizer.forPackage(ProductDerivations.class);
|
||||
throw new MissingResourceException(loc.get("no-product-derivations",
|
||||
ProductDerivation.class.getName()).getMessage(),
|
||||
ProductDerivations.class.getName(), "derivations");
|
||||
throw new MissingResourceException(_loc.get
|
||||
("no-product-derivations", ProductDerivation.class.getName(),
|
||||
derivationErrorsToString()).getMessage(),
|
||||
ProductDerivations.class.getName(),"derivations");
|
||||
}
|
||||
|
||||
// if some derivations weren't instantiable, warn
|
||||
for (int i = 0; i < _derivationErrors.length; i++) {
|
||||
if (_derivationErrors[i] == null)
|
||||
continue;
|
||||
System.err.println(_loc.get("bad-product-derivations",
|
||||
ProductDerivations.class.getName()));
|
||||
break;
|
||||
}
|
||||
|
||||
Collections.sort(derivations, new ProductDerivationComparator());
|
||||
|
@ -269,5 +279,29 @@ public class ProductDerivations {
|
|||
getName());
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Prints product derivation information.
|
||||
*/
|
||||
public static void main(String[] args) {
|
||||
System.err.println(derivationErrorsToString());
|
||||
}
|
||||
|
||||
/**
|
||||
* Return a message about the status of each product derivation.
|
||||
*/
|
||||
private static String derivationErrorsToString() {
|
||||
StringBuffer buf = new StringBuffer();
|
||||
buf.append("ProductDerivations: ").append(_derivationNames.length);
|
||||
for (int i = 0; i < _derivationNames.length; i++) {
|
||||
buf.append("\n").append(i + 1).append(". ").
|
||||
append(_derivationNames[i]).append(": ");
|
||||
if (_derivationErrors[i] == null)
|
||||
buf.append("OK");
|
||||
else
|
||||
buf.append(_derivationErrors[i].toString());
|
||||
}
|
||||
return buf.toString();
|
||||
}
|
||||
}
|
||||
|
||||
|
|
|
@ -67,10 +67,9 @@ no-product-derivations: Your system is missing product derivations. Product \
|
|||
If you are using ant, a common solution to this problem is to place \
|
||||
the jar libraries of the OpenJPA distribution in the \
|
||||
$'{user.home}/.ant/lib directory. Another common cause of this problem \
|
||||
is an overly-restrictive security manager.
|
||||
bad-product-derivation: An error occurred while attempting to load {0}. This \
|
||||
may indicate a corrupt system configuration, or may just be the result \
|
||||
of the inclusion of unused OpenJPA modules in your classpath. Error: {1}
|
||||
is an overly-restrictive security manager.\n{1}
|
||||
bad-product-derivations: Some product derivations are being skipped. For \
|
||||
information about product derivation status, run:\njava {0}
|
||||
|
||||
Log-name: Log factory
|
||||
Log-desc: LogFactory and configuration
|
||||
|
|
|
@ -43,6 +43,13 @@ public class JDBCPersistenceProductDerivation
|
|||
return TYPE_SPEC_STORE;
|
||||
}
|
||||
|
||||
@Override
|
||||
public void validate()
|
||||
throws Exception {
|
||||
// make sure JPA is available
|
||||
javax.persistence.EntityManagerFactory.class.getClassLoader();
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean beforeConfigurationLoad(Configuration c) {
|
||||
if (c instanceof OpenJPAConfiguration) {
|
||||
|
|
|
@ -76,6 +76,13 @@ public class PersistenceProductDerivation
|
|||
public int getType() {
|
||||
return TYPE_SPEC;
|
||||
}
|
||||
|
||||
@Override
|
||||
public void validate()
|
||||
throws Exception {
|
||||
// make sure JPA is available
|
||||
javax.persistence.EntityManagerFactory.class.getClassLoader();
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean beforeConfigurationLoad(Configuration c) {
|
||||
|
|
Loading…
Reference in New Issue