Author: pcl
Date: Wed Aug 29 15:07:44 2007
New Revision: 570948
URL: http://svn.apache.org/viewvc?rev=570948&view=rev
Log:
OPENJPA-344. Enable serialization of metadata and query compilation caches. This implementation requires that the user run a tool to build the cache, and set a configuration property to tell OpenJPA where the serialized data is stored.
Added:
openjpa/trunk/openjpa-kernel/src/main/java/org/apache/openjpa/conf/CacheMarshaller.java
openjpa/trunk/openjpa-kernel/src/main/java/org/apache/openjpa/conf/CacheMarshallerImpl.java
openjpa/trunk/openjpa-kernel/src/main/java/org/apache/openjpa/conf/CacheMarshallersValue.java
openjpa/trunk/openjpa-kernel/src/main/java/org/apache/openjpa/conf/MetaDataCacheMaintenance.java
openjpa/trunk/openjpa-kernel/src/main/java/org/apache/openjpa/conf/MetaDataRepositoryValue.java
openjpa/trunk/openjpa-kernel/src/main/java/org/apache/openjpa/conf/NoOpCacheMarshaller.java
openjpa/trunk/openjpa-kernel/src/main/java/org/apache/openjpa/conf/OpenJPAVersionAndConfigurationTypeValidationPolicy.java
openjpa/trunk/openjpa-kernel/src/test/java/org/apache/openjpa/conf/
openjpa/trunk/openjpa-kernel/src/test/java/org/apache/openjpa/meta/
openjpa/trunk/openjpa-kernel/src/test/java/org/apache/openjpa/meta/TestMemberProvider.java
openjpa/trunk/openjpa-lib/src/main/java/org/apache/openjpa/conf/
openjpa/trunk/openjpa-persistence-jdbc/src/test/java/org/apache/openjpa/conf/TestCacheMarshaller.java
openjpa/trunk/openjpa-persistence-jdbc/src/test/java/org/apache/openjpa/conf/TestCacheMarshallerEndToEnd.java
openjpa/trunk/openjpa-persistence-jdbc/src/test/java/org/apache/openjpa/persistence/query/NamedQueryEntity.java
Modified:
openjpa/trunk/openjpa-jdbc/src/main/java/org/apache/openjpa/jdbc/kernel/exps/JDBCExpressionFactory.java
openjpa/trunk/openjpa-jdbc/src/main/java/org/apache/openjpa/jdbc/kernel/exps/PCPath.java
openjpa/trunk/openjpa-jdbc/src/main/java/org/apache/openjpa/jdbc/kernel/exps/SelectConstructor.java
openjpa/trunk/openjpa-kernel/src/main/java/org/apache/openjpa/conf/OpenJPAConfiguration.java
openjpa/trunk/openjpa-kernel/src/main/java/org/apache/openjpa/conf/OpenJPAConfigurationImpl.java
openjpa/trunk/openjpa-kernel/src/main/java/org/apache/openjpa/conf/QueryCompilationCacheValue.java
openjpa/trunk/openjpa-kernel/src/main/java/org/apache/openjpa/enhance/ReflectingPersistenceCapable.java
openjpa/trunk/openjpa-kernel/src/main/java/org/apache/openjpa/kernel/ExpressionStoreQuery.java
openjpa/trunk/openjpa-kernel/src/main/java/org/apache/openjpa/kernel/QueryImpl.java
openjpa/trunk/openjpa-kernel/src/main/java/org/apache/openjpa/kernel/exps/Expression.java
openjpa/trunk/openjpa-kernel/src/main/java/org/apache/openjpa/kernel/exps/QueryExpressions.java
openjpa/trunk/openjpa-kernel/src/main/java/org/apache/openjpa/kernel/exps/Value.java
openjpa/trunk/openjpa-kernel/src/main/java/org/apache/openjpa/kernel/jpql/JPQLExpressionBuilder.java
openjpa/trunk/openjpa-kernel/src/main/java/org/apache/openjpa/meta/FieldMetaData.java
openjpa/trunk/openjpa-kernel/src/main/java/org/apache/openjpa/meta/MetaDataRepository.java
openjpa/trunk/openjpa-kernel/src/main/resources/org/apache/openjpa/conf/localizer.properties
Modified: openjpa/trunk/openjpa-jdbc/src/main/java/org/apache/openjpa/jdbc/kernel/exps/JDBCExpressionFactory.java
URL: http://svn.apache.org/viewvc/openjpa/trunk/openjpa-jdbc/src/main/java/org/apache/openjpa/jdbc/kernel/exps/JDBCExpressionFactory.java?rev=570948&r1=570947&r2=570948&view=diff
==============================================================================
--- openjpa/trunk/openjpa-jdbc/src/main/java/org/apache/openjpa/jdbc/kernel/exps/JDBCExpressionFactory.java (original)
+++ openjpa/trunk/openjpa-jdbc/src/main/java/org/apache/openjpa/jdbc/kernel/exps/JDBCExpressionFactory.java Wed Aug 29 15:07:44 2007
@@ -18,6 +18,8 @@
*/
package org.apache.openjpa.jdbc.kernel.exps;
+import java.io.Serializable;
+
import org.apache.openjpa.jdbc.meta.ClassMapping;
import org.apache.openjpa.jdbc.meta.JavaSQLTypes;
import org.apache.openjpa.jdbc.sql.DBDictionary;
@@ -43,7 +45,7 @@
* @nojavadoc
*/
public class JDBCExpressionFactory
- implements ExpressionFactory {
+ implements ExpressionFactory, Serializable {
private static final Val NULL = new Null();
private static final Val CURRENT_DATE = new CurrentDate(JavaSQLTypes.DATE);
Modified: openjpa/trunk/openjpa-jdbc/src/main/java/org/apache/openjpa/jdbc/kernel/exps/PCPath.java
URL: http://svn.apache.org/viewvc/openjpa/trunk/openjpa-jdbc/src/main/java/org/apache/openjpa/jdbc/kernel/exps/PCPath.java?rev=570948&r1=570947&r2=570948&view=diff
==============================================================================
--- openjpa/trunk/openjpa-jdbc/src/main/java/org/apache/openjpa/jdbc/kernel/exps/PCPath.java (original)
+++ openjpa/trunk/openjpa-jdbc/src/main/java/org/apache/openjpa/jdbc/kernel/exps/PCPath.java Wed Aug 29 15:07:44 2007
@@ -18,6 +18,7 @@
*/
package org.apache.openjpa.jdbc.kernel.exps;
+import java.io.Serializable;
import java.sql.SQLException;
import java.util.Iterator;
import java.util.LinkedList;
@@ -319,7 +320,7 @@
action.data = meta;
_actions.add(action);
_cast = null;
- _key = false;;
+ _key = false;
_type = XPATH;
_xmlfield = fmd;
}
@@ -330,7 +331,7 @@
action.data = meta.getFieldMapping(name);
_actions.add(action);
_cast = null;
- _key = false;;
+ _key = false;
_type = XPATH;
}
@@ -789,7 +790,8 @@
/**
* Helper class representing an action.
*/
- private static class Action {
+ private static class Action
+ implements Serializable {
public static final int GET = 0;
public static final int GET_OUTER = 1;
Modified: openjpa/trunk/openjpa-jdbc/src/main/java/org/apache/openjpa/jdbc/kernel/exps/SelectConstructor.java
URL: http://svn.apache.org/viewvc/openjpa/trunk/openjpa-jdbc/src/main/java/org/apache/openjpa/jdbc/kernel/exps/SelectConstructor.java?rev=570948&r1=570947&r2=570948&view=diff
==============================================================================
--- openjpa/trunk/openjpa-jdbc/src/main/java/org/apache/openjpa/jdbc/kernel/exps/SelectConstructor.java (original)
+++ openjpa/trunk/openjpa-jdbc/src/main/java/org/apache/openjpa/jdbc/kernel/exps/SelectConstructor.java Wed Aug 29 15:07:44 2007
@@ -18,6 +18,7 @@
*/
package org.apache.openjpa.jdbc.kernel.exps;
+import java.io.Serializable;
import java.util.HashMap;
import java.util.Map;
@@ -38,7 +39,8 @@
* @author Abe White
* @nojavadoc
*/
-public class SelectConstructor {
+public class SelectConstructor
+ implements Serializable {
private boolean _extent = false;
Added: openjpa/trunk/openjpa-kernel/src/main/java/org/apache/openjpa/conf/CacheMarshaller.java
URL: http://svn.apache.org/viewvc/openjpa/trunk/openjpa-kernel/src/main/java/org/apache/openjpa/conf/CacheMarshaller.java?rev=570948&view=auto
==============================================================================
--- openjpa/trunk/openjpa-kernel/src/main/java/org/apache/openjpa/conf/CacheMarshaller.java (added)
+++ openjpa/trunk/openjpa-kernel/src/main/java/org/apache/openjpa/conf/CacheMarshaller.java Wed Aug 29 15:07:44 2007
@@ -0,0 +1,92 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied. See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ */
+package org.apache.openjpa.conf;
+
+
+import org.apache.openjpa.lib.conf.Configurable;
+import org.apache.openjpa.lib.conf.Configuration;
+
+/**
+ * Responsible for marshalling and unmarshalling objects between memory and
+ * durable cache.
+ *
+ * @since 1.1.0
+ */
+public interface CacheMarshaller {
+
+ /**
+ * Load and return an instance of the type handled by this marshaller.
+ * If the type implements {@link Configurable}, then this method will invoke
+ * {@link Configurable#setConfiguration},
+ * {@link Configurable#startConfiguration()}, and
+ * {@link Configurable#endConfiguration()} on the instance before returning.
+ */
+ public Object load();
+
+ /**
+ * Store <code>o</code> into the cache.
+ */
+ public void store(Object o);
+
+ /**
+ * The id that this marshaller is responsible for.
+ * A value for this parameter is required.
+ */
+ public void setId(String id);
+
+ /**
+ * The id that this marshaller is responsible for.
+ */
+ public String getId();
+
+ /**
+ * The {@link ValidationPolicy} that this marshaller should use.
+ * A value for this parameter is required. The class will be instantiated
+ * via the {@link org.apache.openjpa.lib.conf.Configurations} mechanism, ensuring that if the class
+ * implements {@link Configurable} or {@link org.apache.openjpa.lib.conf.GenericConfigurable}, it will
+ * be taken through the appropriate lifecycle.
+ */
+ public void setValidationPolicy(String policy)
+ throws InstantiationException, IllegalAccessException;
+
+ /**
+ * Validation policies are responsible for computing whether or not a
+ * cached data structure is valid for the current context.
+ * <p/>
+ * <code>getValidCachedData(getCacheableData(o), conf)</code> should
+ * return an object equivalent to <code>o</code> in the expected case.
+ * <p/>
+ * Implementations of this class will often also implement
+ * {@link Configurable} in order to receive the current
+ * {@link Configuration}.
+ */
+ public interface ValidationPolicy {
+ /**
+ * Returns an object that this policy considers to be valid, based
+ * on <code>o</code>. If <code>o</code> is not valid, this method
+ * will return <code>null</code>.
+ */
+ public Object getValidData(Object o);
+
+ /**
+ * Return an object that the {@link CacheMarshaller} should store.
+ */
+ public Object getCacheableData(Object o);
+ }
+}
\ No newline at end of file
Added: openjpa/trunk/openjpa-kernel/src/main/java/org/apache/openjpa/conf/CacheMarshallerImpl.java
URL: http://svn.apache.org/viewvc/openjpa/trunk/openjpa-kernel/src/main/java/org/apache/openjpa/conf/CacheMarshallerImpl.java?rev=570948&view=auto
==============================================================================
--- openjpa/trunk/openjpa-kernel/src/main/java/org/apache/openjpa/conf/CacheMarshallerImpl.java (added)
+++ openjpa/trunk/openjpa-kernel/src/main/java/org/apache/openjpa/conf/CacheMarshallerImpl.java Wed Aug 29 15:07:44 2007
@@ -0,0 +1,237 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied. See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ */
+package org.apache.openjpa.conf;
+
+import java.io.BufferedInputStream;
+import java.io.BufferedOutputStream;
+import java.io.File;
+import java.io.FileOutputStream;
+import java.io.IOException;
+import java.io.ObjectInputStream;
+import java.io.ObjectOutputStream;
+import java.io.OutputStream;
+import java.net.URL;
+import java.util.Enumeration;
+
+import org.apache.openjpa.lib.conf.Configurable;
+import org.apache.openjpa.lib.conf.Configuration;
+import org.apache.openjpa.lib.conf.Configurations;
+import org.apache.openjpa.lib.log.Log;
+import org.apache.openjpa.lib.util.Localizer;
+import org.apache.openjpa.util.InternalException;
+
+/**
+ * Default {@link CacheMarshaller} implementation that writes data
+ * to a specified file and reads data from a specified file or URL.
+ *
+ * @since 1.1.0
+ */
+public class CacheMarshallerImpl
+ implements CacheMarshaller, Configurable {
+
+ private static final Localizer _loc =
+ Localizer.forPackage(CacheMarshallerImpl.class);
+
+ private String _id;
+ private ValidationPolicy _validationPolicy;
+ private OpenJPAConfiguration _conf;
+ private Log _log;
+ private File _outputFile;
+ private URL _inputURL;
+
+ // temporary storage for resource location specification
+ private String _inputResourceLocation;
+
+ private boolean _consumeErrors = true;
+
+ public Object load() {
+ if (_inputURL == null) {
+ _log.trace(_loc.get("cache-marshaller-no-inputs", getId()));
+ return null;
+ }
+
+ Object o = null;
+ ObjectInputStream in = null;
+ try {
+ in = new ObjectInputStream(new BufferedInputStream(
+ _inputURL.openStream()));
+
+ o = in.readObject();
+ o = _validationPolicy.getValidData(o);
+
+ if (o != null && o.getClass().isArray()) {
+ Object[] array = (Object[]) o;
+ for (int i = 0; i < array.length; i++)
+ configure(array[i]);
+ } else {
+ configure(o);
+ }
+
+ if (_log.isTraceEnabled())
+ _log.trace(_loc.get("cache-marshaller-loaded",
+ o == null ? null : o.getClass().getName(), _inputURL));
+ } catch (Exception e) {
+ if (_consumeErrors) {
+ if (_log.isWarnEnabled())
+ _log.warn(_loc.get("cache-marshaller-load-exception",
+ _inputURL), e);
+ } else {
+ throw new InternalException(
+ _loc.get("cache-marshaller-load-exception",
+ _inputURL),
+ e);
+ }
+ } finally {
+ if (in != null)
+ try { in.close(); } catch (IOException e) { }
+ }
+
+ return o;
+ }
+
+ private void configure(Object o) {
+ if (o instanceof Configurable) {
+ ((Configurable) o).setConfiguration(_conf);
+ ((Configurable) o).startConfiguration();
+ ((Configurable) o).endConfiguration();
+ }
+ }
+
+ public void store(Object o) {
+ if (_outputFile == null) {
+ _log.trace(_loc.get("cache-marshaller-no-output-file", getId()));
+ return;
+ }
+ OutputStream out = null;
+ try {
+ out = new FileOutputStream(_outputFile);
+ ObjectOutputStream oos =
+ new ObjectOutputStream(new BufferedOutputStream(out));
+ Object toStore = _validationPolicy.getCacheableData(o);
+ oos.writeObject(toStore);
+ oos.flush();
+ out.flush();
+ if (_log.isTraceEnabled())
+ _log.trace(_loc.get("cache-marshaller-stored",
+ o.getClass().getName(), _outputFile));
+ } catch (Exception e) {
+ if (_consumeErrors) {
+ if (_log.isWarnEnabled())
+ _log.warn(_loc.get("cache-marshaller-store-exception",
+ o.getClass().getName(), _outputFile), e);
+ } else {
+ throw new InternalException(
+ _loc.get("cache-marshaller-store-exception",
+ o.getClass().getName(), _outputFile),
+ e);
+ }
+ } finally {
+ if (out != null) {
+ try { out.close(); } catch (IOException ioe) { }
+ }
+ }
+ }
+
+ public void setOutputFile(File file) {
+ _outputFile = file;
+ }
+
+ public File getOutputFile() {
+ return _outputFile;
+ }
+
+ public void setInputURL(URL url) {
+ _inputURL = url;
+ }
+
+ public void setInputResource(String resource) {
+ _inputResourceLocation = resource;
+ }
+
+ public void setConsumeSerializationErrors(boolean consume) {
+ _consumeErrors = consume;
+ }
+
+ public String getId() {
+ return _id;
+ }
+
+ public void setId(String id) {
+ _id = id;
+ }
+
+ public void setValidationPolicy(String policy)
+ throws InstantiationException, IllegalAccessException {
+ String name = Configurations.getClassName(policy);
+ String props = Configurations.getProperties(policy);
+ _validationPolicy = (ValidationPolicy)
+ Configurations.newInstance(name, _conf, props, null);
+ }
+
+ public ValidationPolicy getValidationPolicy() {
+ return _validationPolicy;
+ }
+
+ public void setConfiguration(Configuration conf) {
+ _conf = (OpenJPAConfiguration) conf;
+ _log = conf.getConfigurationLog();
+ }
+
+ public void startConfiguration() {
+ }
+
+ public void endConfiguration() {
+ if (_inputResourceLocation != null && _inputURL != null)
+ throw new IllegalStateException(
+ _loc.get("cache-marshaller-input-url-and-resource-specified")
+ .getMessage());
+ if (_inputResourceLocation != null)
+ setInputUrlFromResourceLocation();
+
+ if (_validationPolicy == null)
+ throw new IllegalStateException(
+ _loc.get("cache-marshaller-null-validation-policy",
+ getClass().getName()).getMessage());
+ if (_id == null)
+ throw new IllegalStateException(
+ _loc.get("cache-marshaller-null-id",
+ getClass().getName()).getMessage());
+ }
+
+ private void setInputUrlFromResourceLocation() {
+ try {
+ ClassLoader cl = _conf.getClassResolverInstance()
+ .getClassLoader(getClass(), null);
+ for (Enumeration e = cl.getResources(_inputResourceLocation);
+ e.hasMoreElements(); ) {
+ if (_inputURL == null)
+ _inputURL = (URL) e.nextElement();
+ else
+ throw new IllegalStateException(
+ _loc.get("cache-marshaller-multiple-resources",
+ getId(), _inputResourceLocation).getMessage());
+ }
+ } catch (IOException ioe) {
+ throw new IllegalStateException(
+ _loc.get("cache-marshaller-bad-url", getId(),
+ _inputResourceLocation)
+ .getMessage(), ioe);
+ }
+ }
+}
Added: openjpa/trunk/openjpa-kernel/src/main/java/org/apache/openjpa/conf/CacheMarshallersValue.java
URL: http://svn.apache.org/viewvc/openjpa/trunk/openjpa-kernel/src/main/java/org/apache/openjpa/conf/CacheMarshallersValue.java?rev=570948&view=auto
==============================================================================
--- openjpa/trunk/openjpa-kernel/src/main/java/org/apache/openjpa/conf/CacheMarshallersValue.java (added)
+++ openjpa/trunk/openjpa-kernel/src/main/java/org/apache/openjpa/conf/CacheMarshallersValue.java Wed Aug 29 15:07:44 2007
@@ -0,0 +1,121 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied. See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ */
+package org.apache.openjpa.conf;
+
+import java.util.HashMap;
+import java.util.Map;
+
+import org.apache.openjpa.lib.log.Log;
+import org.apache.openjpa.lib.util.Localizer;
+import org.apache.openjpa.lib.conf.PluginListValue;
+import org.apache.openjpa.conf.NoOpCacheMarshaller;
+import org.apache.openjpa.lib.conf.Configuration;
+
+/**
+ * A configuration value for handling and accessing cache marshallers.
+ *
+ * @since 1.1.0
+ */
+public class CacheMarshallersValue
+ extends PluginListValue {
+
+ private static final String KEY = "CacheMarshallers";
+ private static final CacheMarshaller NO_OP_CACHE_MARSHALLER
+ = new NoOpCacheMarshaller();
+ private static final Localizer _loc =
+ Localizer.forPackage(CacheMarshallersValue.class);
+
+ private Configuration _conf;
+ private Map _marshallers;
+ private boolean _initialized;
+
+ public CacheMarshallersValue(Configuration conf) {
+ super(KEY);
+ _conf = conf;
+ setAlias("default", CacheMarshallerImpl.class.getName());
+ setAlias("none", null);
+ setDefault("none");
+ setString("none");
+ setScope(getClass());
+ }
+
+ public Object instantiate(Class elemType, Configuration conf,
+ boolean fatal) {
+ CacheMarshaller[] ms = (CacheMarshaller[])
+ super.instantiate(elemType, conf, fatal);
+ if (ms != null) {
+ _marshallers = new HashMap();
+ for (int i = 0; i < ms.length; i++) {
+ String mid = ms[i].getId();
+ if (mid != null)
+ _marshallers.put(mid, ms[i]);
+ }
+ } else {
+ _marshallers = null;
+ }
+ return ms;
+ }
+
+ /**
+ * Return the {@link CacheMarshaller} to use for caching metadata of id
+ * <code>id</code>. If no marshaller exists for the id, returns
+ * {@link NoOpCacheMarshaller}.
+ */
+ public CacheMarshaller getMarshallerById(String id) {
+ initialize();
+
+ CacheMarshaller cm = (CacheMarshaller) _marshallers.get(id);
+ if (cm == null) {
+ if (getLog().isTraceEnabled())
+ getLog().trace(_loc.get("cache-marshaller-not-found", id));
+ return NO_OP_CACHE_MARSHALLER;
+ } else {
+ if (getLog().isTraceEnabled())
+ getLog().trace(_loc.get("cache-marshaller-found", id,
+ cm.getClass().getName()));
+ return cm;
+ }
+ }
+
+ private Log getLog() {
+ return _conf.getConfigurationLog();
+ }
+
+ /**
+ * Return the {@link CacheMarshaller} to use for caching metadata of id
+ * <code>id</code>. If no marshaller exists for the id, returns
+ * {@link NoOpCacheMarshaller}.
+ */
+ public static CacheMarshaller getMarshallerById(Configuration c, String id){
+ CacheMarshallersValue v =
+ ((OpenJPAConfigurationImpl) c).cacheMarshallerPlugins;
+ return v.getMarshallerById(id);
+ }
+
+ public Map getInstancesAsMap() {
+ return _marshallers;
+ }
+
+ protected synchronized void initialize() {
+ if (!_initialized) {
+ instantiate(CacheMarshaller.class, _conf);
+ _initialized = true;
+ }
+ }
+}
Added: openjpa/trunk/openjpa-kernel/src/main/java/org/apache/openjpa/conf/MetaDataCacheMaintenance.java
URL: http://svn.apache.org/viewvc/openjpa/trunk/openjpa-kernel/src/main/java/org/apache/openjpa/conf/MetaDataCacheMaintenance.java?rev=570948&view=auto
==============================================================================
--- openjpa/trunk/openjpa-kernel/src/main/java/org/apache/openjpa/conf/MetaDataCacheMaintenance.java (added)
+++ openjpa/trunk/openjpa-kernel/src/main/java/org/apache/openjpa/conf/MetaDataCacheMaintenance.java Wed Aug 29 15:07:44 2007
@@ -0,0 +1,183 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied. See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ */
+package org.apache.openjpa.conf;
+
+import java.io.PrintStream;
+import java.util.Collection;
+import java.util.Iterator;
+import java.util.Map;
+
+import org.apache.openjpa.kernel.Bootstrap;
+import org.apache.openjpa.kernel.Broker;
+import org.apache.openjpa.kernel.BrokerFactory;
+import org.apache.openjpa.kernel.Query;
+import org.apache.openjpa.conf.CacheMarshallersValue;
+import org.apache.openjpa.lib.util.Options;
+import org.apache.openjpa.meta.ClassMetaData;
+import org.apache.openjpa.meta.MetaDataRepository;
+import org.apache.openjpa.meta.QueryMetaData;
+import org.apache.openjpa.meta.SequenceMetaData;
+
+/**
+ * Performs maintenance tasks on the metadata caches accessible via the
+ * {@link CacheMarshaller} architecture.
+ *
+ * @since 1.1.0
+ */
+public class MetaDataCacheMaintenance {
+
+ private final BrokerFactory factory;
+ private final OpenJPAConfiguration conf;
+ private final boolean devpath;
+ private final boolean verbose;
+ private PrintStream out = System.out;
+
+ public MetaDataCacheMaintenance(BrokerFactory factory, boolean devpath,
+ boolean verbose) {
+ this.factory = factory;
+ this.conf = factory.getConfiguration();
+ this.devpath = devpath;
+ this.verbose = verbose;
+ }
+
+ public void setOutputStream(PrintStream out) {
+ this.out = out;
+ }
+
+ public static void main(String[] args) {
+ Options opts = new Options();
+ args = opts.setFromCmdLine(args);
+ boolean devpath = opts.getBooleanProperty("scanDevPath", "ScanDevPath",
+ true);
+ boolean verbose = opts.getBooleanProperty("verbose", "verbose",
+ false);
+
+ BrokerFactory factory = Bootstrap.newBrokerFactory();
+ try {
+ MetaDataCacheMaintenance maint = new MetaDataCacheMaintenance(
+ factory, devpath, verbose);
+
+ if (args.length != 1)
+ usage();
+
+ if ("store".equals(args[0]))
+ maint.store();
+ else if ("dump".equals(args[0]))
+ maint.dump();
+ else
+ usage();
+ } finally {
+ factory.close();
+ }
+ }
+
+ private static int usage() {
+ System.err.println("Usage: java MetaDataCacheMaintenance "
+ + "[-scanDevPath t|f] [-verbose t|f] store | dump");
+ return -1;
+ }
+
+ public void store() {
+ MetaDataRepository repos = conf.getMetaDataRepositoryInstance();
+ repos.setSourceMode(MetaDataRepository.MODE_META
+ | MetaDataRepository.MODE_MAPPING
+ | MetaDataRepository.MODE_QUERY);
+ Collection types = repos.loadPersistentTypes(devpath, null);
+ for (Iterator iter = types.iterator(); iter.hasNext(); )
+ repos.getMetaData((Class) iter.next(), null, true);
+
+ loadQueries();
+
+ out.println("The following data will be stored: ");
+ log(repos, conf.getQueryCompilationCacheInstance(), verbose, out);
+
+ CacheMarshallersValue.getMarshallerById(conf, getClass().getName())
+ .store(new Object[] {
+ repos, conf.getQueryCompilationCacheInstance()
+ });
+ }
+
+ private void loadQueries() {
+ Broker broker = factory.newBroker();
+ try {
+ QueryMetaData[] qmds =
+ conf.getMetaDataRepositoryInstance().getQueryMetaDatas();
+ for (int i = 0; i < qmds.length; i++)
+ loadQuery(broker, qmds[i]);
+ } finally {
+ broker.close();
+ }
+ }
+
+ private void loadQuery(Broker broker, QueryMetaData qmd) {
+ try {
+ Query q = broker.newQuery(qmd.getLanguage(), null);
+ qmd.setInto(q);
+ q.compile();
+ } catch (Exception e) {
+ out.println("Skipping named query " + qmd.getName() + ": "
+ + e.getMessage());
+ if (verbose)
+ e.printStackTrace(out);
+ }
+ }
+
+ public void dump() {
+ Object[] os = (Object[])
+ CacheMarshallersValue.getMarshallerById(conf, getClass().getName())
+ .load();
+ if (os == null) {
+ out.println("No cached data was found");
+ return;
+ }
+ MetaDataRepository repos = (MetaDataRepository) os[0];
+ Map qcc = (Map) os[1];
+
+ out.println("The following data was found: ");
+ log(repos, qcc, verbose, out);
+ }
+
+ private static void log(MetaDataRepository repos, Map qcc,
+ boolean verbose, PrintStream out) {
+ ClassMetaData[] metas = repos.getMetaDatas();
+ out.println(" Types: " + metas.length);
+ if (verbose)
+ for (int i = 0; i < metas.length; i++)
+ out.println(" " + metas[i].getDescribedType().getName());
+
+ QueryMetaData[] qmds = repos.getQueryMetaDatas();
+ out.println(" Queries: " + qmds.length);
+ if (verbose)
+ for (int i = 0; i < qmds.length; i++)
+ out.println(" " + qmds[i].getName() + ": "
+ + qmds[i].getQueryString());
+
+ SequenceMetaData[] smds = repos.getSequenceMetaDatas();
+ out.println(" Sequences: " + smds.length);
+ if (verbose)
+ for (int i = 0; i < smds.length; i++)
+ out.println(" " + smds[i].getName());
+
+ out.println(" Compiled queries: "
+ + (qcc == null ? "0" : "" + qcc.size()));
+ if (verbose && qcc != null)
+ for (Iterator iter = qcc.keySet().iterator(); iter.hasNext(); )
+ out.println(" " + iter.next());
+ }
+}
Added: openjpa/trunk/openjpa-kernel/src/main/java/org/apache/openjpa/conf/MetaDataRepositoryValue.java
URL: http://svn.apache.org/viewvc/openjpa/trunk/openjpa-kernel/src/main/java/org/apache/openjpa/conf/MetaDataRepositoryValue.java?rev=570948&view=auto
==============================================================================
--- openjpa/trunk/openjpa-kernel/src/main/java/org/apache/openjpa/conf/MetaDataRepositoryValue.java (added)
+++ openjpa/trunk/openjpa-kernel/src/main/java/org/apache/openjpa/conf/MetaDataRepositoryValue.java Wed Aug 29 15:07:44 2007
@@ -0,0 +1,74 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied. See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ */
+package org.apache.openjpa.conf;
+
+import java.util.Map;
+
+import org.apache.openjpa.lib.conf.Configuration;
+import org.apache.openjpa.lib.conf.PluginValue;
+import org.apache.openjpa.conf.CacheMarshallersValue;
+import org.apache.openjpa.meta.MetaDataRepository;
+
+/**
+ * A {@link PluginValue} that interacts with the {@link CacheMarshaller}
+ * to cache the metadata repository between executions.
+ *
+ * @since 1.1.0
+ */
+public class MetaDataRepositoryValue
+ extends PluginValue {
+
+ private static final String KEY = "MetaDataRepository";
+
+ public MetaDataRepositoryValue() {
+ super(KEY, false);
+ String[] aliases = new String[] {
+ "default",
+ MetaDataRepository.class.getName()
+ };
+ setAliases(aliases);
+ setDefault(aliases[0]);
+ setString(aliases[0]);
+ }
+
+ public Object instantiate(Class type, Configuration c, boolean fatal) {
+ MetaDataRepository repos = null;
+ OpenJPAConfiguration conf = (OpenJPAConfiguration) c;
+
+ Object[] os = (Object[]) CacheMarshallersValue.getMarshallerById(
+ conf, MetaDataCacheMaintenance.class.getName())
+ .load();
+ if (os != null) {
+ repos = (MetaDataRepository) os[0];
+ if (os[1] != null)
+ // It's a bit odd that we do this in MetaDataRepositoryValue.
+ // We need to serialize all the various bits of configuration
+ // together; maybe we can move the caching logic somewhere
+ // else?
+ conf.getQueryCompilationCacheInstance().putAll((Map) os[1]);
+ }
+
+ if (repos == null)
+ return super.instantiate(type, c, fatal);
+ else
+ return repos;
+ }
+
+
+}
Added: openjpa/trunk/openjpa-kernel/src/main/java/org/apache/openjpa/conf/NoOpCacheMarshaller.java
URL: http://svn.apache.org/viewvc/openjpa/trunk/openjpa-kernel/src/main/java/org/apache/openjpa/conf/NoOpCacheMarshaller.java?rev=570948&view=auto
==============================================================================
--- openjpa/trunk/openjpa-kernel/src/main/java/org/apache/openjpa/conf/NoOpCacheMarshaller.java (added)
+++ openjpa/trunk/openjpa-kernel/src/main/java/org/apache/openjpa/conf/NoOpCacheMarshaller.java Wed Aug 29 15:07:44 2007
@@ -0,0 +1,48 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied. See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ */
+package org.apache.openjpa.conf;
+
+/**
+ * Implementation of {@link CacheMarshaller} that does nothing.
+ *
+ * @since 1.1.0
+ */
+public class NoOpCacheMarshaller
+ implements CacheMarshaller {
+
+ private String id;
+
+ public Object load() {
+ return null;
+ }
+
+ public void setId(String id) {
+ this.id = id;
+ }
+
+ public String getId() {
+ return id;
+ }
+
+ public void setValidationPolicy(String policy) {
+ }
+
+ public void store(Object o) {
+ }
+}
Modified: openjpa/trunk/openjpa-kernel/src/main/java/org/apache/openjpa/conf/OpenJPAConfiguration.java
URL: http://svn.apache.org/viewvc/openjpa/trunk/openjpa-kernel/src/main/java/org/apache/openjpa/conf/OpenJPAConfiguration.java?rev=570948&r1=570947&r2=570948&view=diff
==============================================================================
--- openjpa/trunk/openjpa-kernel/src/main/java/org/apache/openjpa/conf/OpenJPAConfiguration.java (original)
+++ openjpa/trunk/openjpa-kernel/src/main/java/org/apache/openjpa/conf/OpenJPAConfiguration.java Wed Aug 29 15:07:44 2007
@@ -1448,4 +1448,27 @@
* @since 1.0.0
*/
public void setRuntimeUnenhancedClasses(int mode);
+
+ /**
+ * A comma-separted list of the plugin strings specifying the
+ * {@link CacheMarshaller}s to use.
+ *
+ * @since 1.1.0
+ */
+ public String getCacheMarshallers();
+
+ /**
+ * A comma-separted list of the plugin strings specifying the
+ * {@link CacheMarshaller}s to use.
+ *
+ * @since 1.1.0
+ */
+ public void setCacheMarshallers(String marshallers);
+
+ /**
+ * Return the cache marshaller listeners.
+ *
+ * @since 1.1.0
+ */
+ public Map getCacheMarshallerInstances();
}
Modified: openjpa/trunk/openjpa-kernel/src/main/java/org/apache/openjpa/conf/OpenJPAConfigurationImpl.java
URL: http://svn.apache.org/viewvc/openjpa/trunk/openjpa-kernel/src/main/java/org/apache/openjpa/conf/OpenJPAConfigurationImpl.java?rev=570948&r1=570947&r2=570948&view=diff
==============================================================================
--- openjpa/trunk/openjpa-kernel/src/main/java/org/apache/openjpa/conf/OpenJPAConfigurationImpl.java (original)
+++ openjpa/trunk/openjpa-kernel/src/main/java/org/apache/openjpa/conf/OpenJPAConfigurationImpl.java Wed Aug 29 15:07:44 2007
@@ -133,6 +133,7 @@
public ObjectValue compatibilityPlugin;
public QueryCompilationCacheValue queryCompilationCachePlugin;
public IntValue runtimeUnenhancedClasses;
+ public CacheMarshallersValue cacheMarshallerPlugins;
// custom values
public BrokerFactoryValue brokerFactoryPlugin;
@@ -295,13 +296,8 @@
mapping = addString("Mapping");
metaFactoryPlugin = addPlugin("MetaDataFactory", false);
- metaRepositoryPlugin = addPlugin("MetaDataRepository", false);
- aliases =
- new String[] { "default",
- "org.apache.openjpa.meta.MetaDataRepository" };
- metaRepositoryPlugin.setAliases(aliases);
- metaRepositoryPlugin.setDefault(aliases[0]);
- metaRepositoryPlugin.setString(aliases[0]);
+ metaRepositoryPlugin = (ObjectValue)
+ addValue(new MetaDataRepositoryValue());
connectionFactory = addObject("ConnectionFactory");
connectionFactory.setInstantiatingGetter("getConnectionFactory");
@@ -494,6 +490,9 @@
runtimeUnenhancedClasses.setString("supported");
runtimeUnenhancedClasses.setAliasListComprehensive(true);
+ cacheMarshallerPlugins = (CacheMarshallersValue)
+ addValue(new CacheMarshallersValue(this));
+
// initialize supported options that some runtimes may not support
supportedOptions.add(OPTION_NONTRANS_READ);
supportedOptions.add(OPTION_OPTIMISTIC);
@@ -1450,6 +1449,19 @@
runtimeUnenhancedClasses.set(mode);
}
+ public String getCacheMarshallers() {
+ return cacheMarshallerPlugins.getString();
+ }
+
+ public void setCacheMarshallers(String marshallers) {
+ assertNotReadOnly();
+ cacheMarshallerPlugins.setString(marshallers);
+ }
+
+ public Map getCacheMarshallerInstances() {
+ return cacheMarshallerPlugins.getInstancesAsMap();
+ }
+
public void setRuntimeUnenhancedClasses(String mode) {
assertNotReadOnly();
runtimeUnenhancedClasses.setString(mode);
@@ -1459,6 +1471,7 @@
super.instantiateAll();
getMetaDataRepositoryInstance();
getRemoteCommitEventManager();
+ cacheMarshallerPlugins.initialize();
}
protected void preClose() {
Added: openjpa/trunk/openjpa-kernel/src/main/java/org/apache/openjpa/conf/OpenJPAVersionAndConfigurationTypeValidationPolicy.java
URL: http://svn.apache.org/viewvc/openjpa/trunk/openjpa-kernel/src/main/java/org/apache/openjpa/conf/OpenJPAVersionAndConfigurationTypeValidationPolicy.java?rev=570948&view=auto
==============================================================================
--- openjpa/trunk/openjpa-kernel/src/main/java/org/apache/openjpa/conf/OpenJPAVersionAndConfigurationTypeValidationPolicy.java (added)
+++ openjpa/trunk/openjpa-kernel/src/main/java/org/apache/openjpa/conf/OpenJPAVersionAndConfigurationTypeValidationPolicy.java Wed Aug 29 15:07:44 2007
@@ -0,0 +1,66 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied. See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ */
+package org.apache.openjpa.conf;
+
+import org.apache.openjpa.conf.CacheMarshaller.ValidationPolicy;
+import org.apache.openjpa.lib.conf.Configurable;
+import org.apache.openjpa.lib.conf.Configuration;
+
+/**
+ * Compute validity based on whether or not the cached data is from the same
+ * version of Kodo as the current install. This also checks OpenJPA version
+ * information in case the OpenJPA jars were independently updated.
+ *
+ * @since 1.1.0
+ */
+public class OpenJPAVersionAndConfigurationTypeValidationPolicy
+ implements ValidationPolicy, Configurable {
+
+ private String confClassName;
+
+ public Object getCacheableData(Object o) {
+ return new Object[] {
+ OpenJPAVersion.VERSION_ID,
+ confClassName,
+ o,
+ };
+ }
+
+ public Object getValidData(Object o) {
+ Object[] array = (Object[]) o;
+ if (array.length != 3)
+ return null;
+
+ if (OpenJPAVersion.VERSION_ID.equals(array[0])
+ && confClassName.equals(array[1]))
+ return array[2];
+ else
+ return null;
+ }
+
+ public void setConfiguration(Configuration conf) {
+ confClassName = conf.getClass().getName();
+ }
+
+ public void startConfiguration() {
+ }
+
+ public void endConfiguration() {
+ }
+}
Modified: openjpa/trunk/openjpa-kernel/src/main/java/org/apache/openjpa/conf/QueryCompilationCacheValue.java
URL: http://svn.apache.org/viewvc/openjpa/trunk/openjpa-kernel/src/main/java/org/apache/openjpa/conf/QueryCompilationCacheValue.java?rev=570948&r1=570947&r2=570948&view=diff
==============================================================================
--- openjpa/trunk/openjpa-kernel/src/main/java/org/apache/openjpa/conf/QueryCompilationCacheValue.java (original)
+++ openjpa/trunk/openjpa-kernel/src/main/java/org/apache/openjpa/conf/QueryCompilationCacheValue.java Wed Aug 29 15:07:44 2007
@@ -87,7 +87,8 @@
if (map != null && !(map instanceof Hashtable)
&& !(map instanceof CacheMap)
- && !(map instanceof ConcurrentMap))
+ && !(map instanceof ConcurrentMap)
+ && !(map.getClass().getName().startsWith("java.util.concurrent")))
map = Collections.synchronizedMap(map);
return map;
}
Modified: openjpa/trunk/openjpa-kernel/src/main/java/org/apache/openjpa/enhance/ReflectingPersistenceCapable.java
URL: http://svn.apache.org/viewvc/openjpa/trunk/openjpa-kernel/src/main/java/org/apache/openjpa/enhance/ReflectingPersistenceCapable.java?rev=570948&r1=570947&r2=570948&view=diff
==============================================================================
--- openjpa/trunk/openjpa-kernel/src/main/java/org/apache/openjpa/enhance/ReflectingPersistenceCapable.java (original)
+++ openjpa/trunk/openjpa-kernel/src/main/java/org/apache/openjpa/enhance/ReflectingPersistenceCapable.java Wed Aug 29 15:07:44 2007
@@ -73,45 +73,45 @@
}
public void pcProvideField(int i) {
+ Object value = getValue(i, o);
switch (meta.getField(i).getTypeCode()) {
case JavaTypes.BOOLEAN:
- sm.providedBooleanField(this, i,
- ((Boolean) getValue(i, o)).booleanValue());
+ sm.providedBooleanField(this, i, value == null ? false :
+ ((Boolean) value).booleanValue());
break;
case JavaTypes.BYTE:
- sm.providedByteField(this, i,
- ((Byte) getValue(i, o)).byteValue());
+ sm.providedByteField(this, i, value == null ? 0 :
+ ((Byte) value).byteValue());
break;
case JavaTypes.CHAR:
- sm.providedCharField(this, i,
- ((Character) getValue(i, o)).charValue());
+ sm.providedCharField(this, i, value == null ? 0 :
+ ((Character) value).charValue());
break;
case JavaTypes.DOUBLE:
- sm.providedDoubleField(this, i,
- ((Double) getValue(i, o)).doubleValue());
+ sm.providedDoubleField(this, i, value == null ? 0 :
+ ((Double) value).doubleValue());
break;
case JavaTypes.FLOAT:
- sm.providedFloatField(this, i,
- ((Float) getValue(i, o)).floatValue());
+ sm.providedFloatField(this, i, value == null ? 0 :
+ ((Float) value).floatValue());
break;
case JavaTypes.INT:
- sm.providedIntField(this, i,
- ((Integer) getValue(i, o)).intValue());
+ sm.providedIntField(this, i, value == null ? 0 :
+ ((Integer) value).intValue());
break;
case JavaTypes.LONG:
- sm.providedLongField(this, i,
- ((Long) getValue(i, o)).longValue());
+ sm.providedLongField(this, i, value == null ? 0 :
+ ((Long) value).longValue());
break;
case JavaTypes.SHORT:
- sm.providedShortField(this, i,
- ((Short) getValue(i, o)).shortValue());
+ sm.providedShortField(this, i, value == null ? 0 :
+ ((Short) value).shortValue());
break;
case JavaTypes.STRING:
- sm.providedStringField(this, i,
- (String) getValue(i, o));
+ sm.providedStringField(this, i, (String) value);
break;
default:
- sm.providedObjectField(this, i, getValue(i, o));
+ sm.providedObjectField(this, i, value);
break;
}
}
Modified: openjpa/trunk/openjpa-kernel/src/main/java/org/apache/openjpa/kernel/ExpressionStoreQuery.java
URL: http://svn.apache.org/viewvc/openjpa/trunk/openjpa-kernel/src/main/java/org/apache/openjpa/kernel/ExpressionStoreQuery.java?rev=570948&r1=570947&r2=570948&view=diff
==============================================================================
--- openjpa/trunk/openjpa-kernel/src/main/java/org/apache/openjpa/kernel/ExpressionStoreQuery.java (original)
+++ openjpa/trunk/openjpa-kernel/src/main/java/org/apache/openjpa/kernel/ExpressionStoreQuery.java Wed Aug 29 15:07:44 2007
@@ -18,6 +18,7 @@
*/
package org.apache.openjpa.kernel;
+import java.io.Serializable;
import java.util.ArrayList;
import java.util.Collection;
import java.util.HashSet;
@@ -277,7 +278,7 @@
*
* @author Marc Prud'hommeaux
*/
- private static abstract class AbstractExpressionExecutor
+ public static abstract class AbstractExpressionExecutor
extends AbstractExecutor
implements Executor {
@@ -471,7 +472,7 @@
*/
private static class InMemoryExecutor
extends AbstractExpressionExecutor
- implements Executor {
+ implements Executor, Serializable {
private final ClassMetaData _meta;
private final boolean _subs;
@@ -624,17 +625,17 @@
*
* @author Marc Prud'hommeaux
*/
- private static class DataStoreExecutor
+ public static class DataStoreExecutor
extends AbstractExpressionExecutor
- implements Executor {
+ implements Executor, Serializable {
- private final ClassMetaData _meta;
- private final ClassMetaData[] _metas;
- private final boolean _subs;
- private final ExpressionParser _parser;
- private final ExpressionFactory[] _facts;
- private final QueryExpressions[] _exps;
- private final Class[] _projTypes;
+ private ClassMetaData _meta;
+ private ClassMetaData[] _metas;
+ private boolean _subs;
+ private ExpressionParser _parser;
+ private ExpressionFactory[] _facts;
+ private QueryExpressions[] _exps;
+ private Class[] _projTypes;
private Value[] _inMemOrdering;
public DataStoreExecutor(ExpressionStoreQuery q,
Modified: openjpa/trunk/openjpa-kernel/src/main/java/org/apache/openjpa/kernel/QueryImpl.java
URL: http://svn.apache.org/viewvc/openjpa/trunk/openjpa-kernel/src/main/java/org/apache/openjpa/kernel/QueryImpl.java?rev=570948&r1=570947&r2=570948&view=diff
==============================================================================
--- openjpa/trunk/openjpa-kernel/src/main/java/org/apache/openjpa/kernel/QueryImpl.java (original)
+++ openjpa/trunk/openjpa-kernel/src/main/java/org/apache/openjpa/kernel/QueryImpl.java Wed Aug 29 15:07:44 2007
@@ -74,7 +74,7 @@
public class QueryImpl
implements Query {
- private static Localizer _loc = Localizer.forPackage(QueryImpl.class);
+ private static final Localizer _loc = Localizer.forPackage(QueryImpl.class);
private final String _language;
private final StoreQuery _storeQuery;
@@ -1693,7 +1693,8 @@
/**
* Struct of compiled query properties.
*/
- protected static class Compilation {
+ protected static class Compilation
+ implements Serializable {
public StoreQuery.Executor memory = null;
public StoreQuery.Executor datastore = null;
Modified: openjpa/trunk/openjpa-kernel/src/main/java/org/apache/openjpa/kernel/exps/Expression.java
URL: http://svn.apache.org/viewvc/openjpa/trunk/openjpa-kernel/src/main/java/org/apache/openjpa/kernel/exps/Expression.java?rev=570948&r1=570947&r2=570948&view=diff
==============================================================================
--- openjpa/trunk/openjpa-kernel/src/main/java/org/apache/openjpa/kernel/exps/Expression.java (original)
+++ openjpa/trunk/openjpa-kernel/src/main/java/org/apache/openjpa/kernel/exps/Expression.java Wed Aug 29 15:07:44 2007
@@ -18,13 +18,16 @@
*/
package org.apache.openjpa.kernel.exps;
+import java.io.Serializable;
+
/**
* Interface for a set of conditions that must be met for the query
* to be true.
*
* @author Abe White
*/
-public interface Expression {
+public interface Expression
+ extends Serializable {
/**
* Accept a visit from a tree visitor.
Modified: openjpa/trunk/openjpa-kernel/src/main/java/org/apache/openjpa/kernel/exps/QueryExpressions.java
URL: http://svn.apache.org/viewvc/openjpa/trunk/openjpa-kernel/src/main/java/org/apache/openjpa/kernel/exps/QueryExpressions.java?rev=570948&r1=570947&r2=570948&view=diff
==============================================================================
--- openjpa/trunk/openjpa-kernel/src/main/java/org/apache/openjpa/kernel/exps/QueryExpressions.java (original)
+++ openjpa/trunk/openjpa-kernel/src/main/java/org/apache/openjpa/kernel/exps/QueryExpressions.java Wed Aug 29 15:07:44 2007
@@ -18,6 +18,7 @@
*/
package org.apache.openjpa.kernel.exps;
+import java.io.Serializable;
import java.util.Collections;
import java.util.HashMap;
import java.util.Map;
@@ -35,7 +36,8 @@
* @since 0.3.2
* @nojavadoc
*/
-public class QueryExpressions {
+public class QueryExpressions
+ implements Serializable {
public static final int DISTINCT_AUTO = 2 << 0;
public static final int DISTINCT_TRUE = 2 << 1;
Modified: openjpa/trunk/openjpa-kernel/src/main/java/org/apache/openjpa/kernel/exps/Value.java
URL: http://svn.apache.org/viewvc/openjpa/trunk/openjpa-kernel/src/main/java/org/apache/openjpa/kernel/exps/Value.java?rev=570948&r1=570947&r2=570948&view=diff
==============================================================================
--- openjpa/trunk/openjpa-kernel/src/main/java/org/apache/openjpa/kernel/exps/Value.java (original)
+++ openjpa/trunk/openjpa-kernel/src/main/java/org/apache/openjpa/kernel/exps/Value.java Wed Aug 29 15:07:44 2007
@@ -18,6 +18,8 @@
*/
package org.apache.openjpa.kernel.exps;
+import java.io.Serializable;
+
import org.apache.openjpa.meta.ClassMetaData;
/**
@@ -26,7 +28,8 @@
*
* @author Abe White
*/
-public interface Value {
+public interface Value
+ extends Serializable {
/**
* Return the expected type for this value, or <code>Object</code> if
Modified: openjpa/trunk/openjpa-kernel/src/main/java/org/apache/openjpa/kernel/jpql/JPQLExpressionBuilder.java
URL: http://svn.apache.org/viewvc/openjpa/trunk/openjpa-kernel/src/main/java/org/apache/openjpa/kernel/jpql/JPQLExpressionBuilder.java?rev=570948&r1=570947&r2=570948&view=diff
==============================================================================
--- openjpa/trunk/openjpa-kernel/src/main/java/org/apache/openjpa/kernel/jpql/JPQLExpressionBuilder.java (original)
+++ openjpa/trunk/openjpa-kernel/src/main/java/org/apache/openjpa/kernel/jpql/JPQLExpressionBuilder.java Wed Aug 29 15:07:44 2007
@@ -22,7 +22,6 @@
import java.io.Serializable;
import java.lang.reflect.Field;
import java.math.BigDecimal;
-import java.security.AccessController;
import java.util.Arrays;
import java.util.Collection;
import java.util.HashSet;
@@ -44,7 +43,6 @@
import org.apache.openjpa.kernel.exps.QueryExpressions;
import org.apache.openjpa.kernel.exps.Subquery;
import org.apache.openjpa.kernel.exps.Value;
-import org.apache.openjpa.lib.util.J2DoPrivHelper;
import org.apache.openjpa.lib.util.Localizer;
import org.apache.openjpa.meta.ClassMetaData;
import org.apache.openjpa.meta.FieldMetaData;
@@ -70,7 +68,7 @@
private static final int VAR_PATH = 1;
private static final int VAR_ERROR = 2;
- private static Localizer _loc = Localizer.forPackage
+ private static final Localizer _loc = Localizer.forPackage
(JPQLExpressionBuilder.class);
private final Stack contexts = new Stack();
@@ -261,7 +259,7 @@
Expression filter = null;
filter = and(evalFromClause(root().id == JJTSELECT), filter);
- filter = and(evalWhereClause(exps), filter);
+ filter = and(evalWhereClause(), filter);
filter = and(evalSelectClause(exps), filter);
exps.filter = filter == null ? factory.emptyExpression() : filter;
@@ -469,7 +467,7 @@
}
}
- private Expression evalWhereClause(QueryExpressions exps) {
+ private Expression evalWhereClause() {
// evaluate the WHERE clause
JPQLNode whereNode = root().findChildByID(JJTWHERE, false);
if (whereNode == null)
@@ -529,10 +527,10 @@
exp = and(exp, factory.equal(path, subpath));
}
- return addJoin(path, alias, inner, exp);
+ return addJoin(path, alias, exp);
}
- private Expression addJoin(Path path, JPQLNode aliasNode, boolean inner,
+ private Expression addJoin(Path path, JPQLNode aliasNode,
Expression exp) {
FieldMetaData fmd = path.last();
@@ -1634,8 +1632,11 @@
public static class ParsedJPQL
implements Serializable {
- protected final JPQLNode root;
- protected final String query;
+ // This is only ever used during parse; when ParsedJPQL instances
+ // are serialized, they will have already been parsed.
+ private final transient JPQLNode root;
+
+ private final String query;
// cache of candidate type data. This is stored here in case this
// parse tree is reused in a context that does not know what the
@@ -1651,7 +1652,7 @@
this.query = query;
}
- private static final JPQLNode parse(String jpql) {
+ private static JPQLNode parse(String jpql) {
if (jpql == null)
jpql = "";
Modified: openjpa/trunk/openjpa-kernel/src/main/java/org/apache/openjpa/meta/FieldMetaData.java
URL: http://svn.apache.org/viewvc/openjpa/trunk/openjpa-kernel/src/main/java/org/apache/openjpa/meta/FieldMetaData.java?rev=570948&r1=570947&r2=570948&view=diff
==============================================================================
--- openjpa/trunk/openjpa-kernel/src/main/java/org/apache/openjpa/meta/FieldMetaData.java (original)
+++ openjpa/trunk/openjpa-kernel/src/main/java/org/apache/openjpa/meta/FieldMetaData.java Wed Aug 29 15:07:44 2007
@@ -178,9 +178,8 @@
// Members aren't serializable. Use a proxy that can provide a Member
// to avoid writing the full Externalizable implementation.
- private transient MemberProvider _backingMember = null;
- private String _backingFieldName = null;
-
+ private MemberProvider _backingMember = null;
+
// Members aren't serializable. Initializing _extMethod and _factMethod to
// DEFAULT_METHOD is sufficient to trigger lazy population of these fields.
private transient Method _extMethod = DEFAULT_METHOD;
@@ -1996,18 +1995,22 @@
* Serializable wrapper around a {@link Method} or {@link Field}. For
* space considerations, this does not support {@link Constructor}s.
*/
- private static class MemberProvider
+ public static class MemberProvider
implements Externalizable {
private transient Member _member;
-
- private MemberProvider(Member member) {
+
+ public MemberProvider() {
+ // for externalization
+ }
+
+ MemberProvider(Member member) {
if (member instanceof Constructor)
throw new IllegalArgumentException();
_member = member;
}
-
+
public Member getMember() {
return _member;
}
@@ -2015,13 +2018,13 @@
public void readExternal(ObjectInput in)
throws IOException, ClassNotFoundException {
boolean isField = in.readBoolean();
- Class cls = _member.getDeclaringClass();
+ Class cls = (Class) in.readObject();
String memberName = (String) in.readObject();
try {
if (isField)
_member = (Field) AccessController.doPrivileged(
J2DoPrivHelper.getDeclaredFieldAction(
- cls,memberName));
+ cls, memberName));
else {
Class[] parameterTypes = (Class[]) in.readObject();
_member = (Method) AccessController.doPrivileged(
Modified: openjpa/trunk/openjpa-kernel/src/main/java/org/apache/openjpa/meta/MetaDataRepository.java
URL: http://svn.apache.org/viewvc/openjpa/trunk/openjpa-kernel/src/main/java/org/apache/openjpa/meta/MetaDataRepository.java?rev=570948&r1=570947&r2=570948&view=diff
==============================================================================
--- openjpa/trunk/openjpa-kernel/src/main/java/org/apache/openjpa/meta/MetaDataRepository.java (original)
+++ openjpa/trunk/openjpa-kernel/src/main/java/org/apache/openjpa/meta/MetaDataRepository.java Wed Aug 29 15:07:44 2007
@@ -25,6 +25,7 @@
import java.util.Collection;
import java.util.Collections;
import java.util.HashMap;
+import java.util.HashSet;
import java.util.Iterator;
import java.util.LinkedList;
import java.util.List;
@@ -35,10 +36,10 @@
import org.apache.commons.lang.StringUtils;
import org.apache.openjpa.conf.OpenJPAConfiguration;
+import org.apache.openjpa.enhance.DynamicPersistenceCapable;
import org.apache.openjpa.enhance.PCRegistry;
import org.apache.openjpa.enhance.PCRegistry.RegisterClassListener;
import org.apache.openjpa.enhance.PersistenceCapable;
-import org.apache.openjpa.enhance.DynamicPersistenceCapable;
import org.apache.openjpa.event.LifecycleEventManager;
import org.apache.openjpa.lib.conf.Configurable;
import org.apache.openjpa.lib.conf.Configuration;
@@ -46,10 +47,10 @@
import org.apache.openjpa.lib.util.Closeable;
import org.apache.openjpa.lib.util.J2DoPrivHelper;
import org.apache.openjpa.lib.util.Localizer;
+import org.apache.openjpa.util.ImplHelper;
import org.apache.openjpa.util.InternalException;
import org.apache.openjpa.util.MetaDataException;
import org.apache.openjpa.util.OpenJPAId;
-import org.apache.openjpa.util.ImplHelper;
import serp.util.Strings;
/**
@@ -132,7 +133,7 @@
// we buffer up any classes that register themselves to prevent
// reentrancy errors if classes register during a current parse (common)
- private final Collection _registered = new ArrayList();
+ private final Collection _registered = new HashSet();
// set of metadatas we're in the process of resolving
private final SortedSet _resolving = new TreeSet
Modified: openjpa/trunk/openjpa-kernel/src/main/resources/org/apache/openjpa/conf/localizer.properties
URL: http://svn.apache.org/viewvc/openjpa/trunk/openjpa-kernel/src/main/resources/org/apache/openjpa/conf/localizer.properties?rev=570948&r1=570947&r2=570948&view=diff
==============================================================================
--- openjpa/trunk/openjpa-kernel/src/main/resources/org/apache/openjpa/conf/localizer.properties (original)
+++ openjpa/trunk/openjpa-kernel/src/main/resources/org/apache/openjpa/conf/localizer.properties Wed Aug 29 15:07:44 2007
@@ -552,3 +552,30 @@
diff-specs: Attempt to configure for multiple specifications. Was configured \
for "{0}". Attempt to now configure for "{1}". This attempt will be \
ignored.
+
+cache-marshaller-loaded: Loaded cached data of type {0} from file {1}.
+cache-marshaller-no-inputs: No InputURL or InputResource was specified for \
+ CacheMarshaller {0}. Cannot load data if no input was specified.
+cache-marshaller-load-exception: An error occurred while loading cached data \
+ from {0}. The exception is logged with this message; it will be consumed \
+ and ignored.
+cache-marshaller-stored: Stored data of type {0} to file {1}.
+cache-marshaller-no-output-file: No OutputFile was specified for \
+ CacheMarshaller {0}. Cannot store data if no output was specified.
+cache-marshaller-store-exception: An error occurred while storing data \
+ to cache in {0}. The exception is logged with this message; it will be \
+ consumed and ignored.
+cache-marshaller-input-url-and-resource-specified: An InputURL and an \
+ InputResource were specified for CacheMarshaller {0}. At most one of these \
+ can be specified.
+cache-marshaller-multiple-resources: Multiple resources exist for resource \
+ location {1} for CacheMarshaller {0}.
+cache-marshaller-bad-url: An error occurred while loading resource location \
+ {1} for CacheMarshaller {0}.
+cache-marshaller-null-validation-policy: No ValidationPolicy was set for \
+ cache marshaller of type {0}.
+cache-marshaller-null-id: No id was set for cache marshaller of type {0}. The \
+ id value is used by the subsystems within Kodo that use marshallers to \
+ find the right marshaller to use to load and store cached data.
+cache-marshaller-not-found: No cache marshaller found for id {0}.
+cache-marshaller-found: Cache marshaller of type {1} found for id {0}.
Added: openjpa/trunk/openjpa-kernel/src/test/java/org/apache/openjpa/meta/TestMemberProvider.java
URL: http://svn.apache.org/viewvc/openjpa/trunk/openjpa-kernel/src/test/java/org/apache/openjpa/meta/TestMemberProvider.java?rev=570948&view=auto
==============================================================================
--- openjpa/trunk/openjpa-kernel/src/test/java/org/apache/openjpa/meta/TestMemberProvider.java (added)
+++ openjpa/trunk/openjpa-kernel/src/test/java/org/apache/openjpa/meta/TestMemberProvider.java Wed Aug 29 15:07:44 2007
@@ -0,0 +1,62 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied. See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ */
+package org.apache.openjpa.meta;
+
+import java.io.ByteArrayInputStream;
+import java.io.ByteArrayOutputStream;
+import java.io.ObjectInputStream;
+import java.io.ObjectOutputStream;
+import java.io.IOException;
+
+import junit.framework.TestCase;
+import org.apache.openjpa.meta.FieldMetaData.MemberProvider;
+
+public class TestMemberProvider
+ extends TestCase {
+
+ private String field;
+
+ public void testField()
+ throws NoSuchFieldException, IOException, ClassNotFoundException {
+ MemberProvider b = new MemberProvider(
+ getClass().getDeclaredField("field"));
+ MemberProvider b2 = roundtrip(b);
+ assertEquals(b.getMember(), b2.getMember());
+ }
+
+ public void testMethod()
+ throws NoSuchMethodException, IOException, ClassNotFoundException {
+ MemberProvider b = new MemberProvider(
+ getClass().getDeclaredMethod("testMethod", null));
+ MemberProvider b2 = roundtrip(b);
+ assertEquals(b.getMember(), b2.getMember());
+ }
+
+ private MemberProvider roundtrip(MemberProvider other)
+ throws IOException, ClassNotFoundException {
+ ByteArrayOutputStream out = new ByteArrayOutputStream();
+ new ObjectOutputStream(out).writeObject(other);
+ out.flush();
+ byte[] bytes = out.toByteArray();
+ out.close();
+
+ ByteArrayInputStream in = new ByteArrayInputStream(bytes);
+ return (MemberProvider) new ObjectInputStream(in).readObject();
+ }
+}
Added: openjpa/trunk/openjpa-persistence-jdbc/src/test/java/org/apache/openjpa/conf/TestCacheMarshaller.java
URL: http://svn.apache.org/viewvc/openjpa/trunk/openjpa-persistence-jdbc/src/test/java/org/apache/openjpa/conf/TestCacheMarshaller.java?rev=570948&view=auto
==============================================================================
--- openjpa/trunk/openjpa-persistence-jdbc/src/test/java/org/apache/openjpa/conf/TestCacheMarshaller.java (added)
+++ openjpa/trunk/openjpa-persistence-jdbc/src/test/java/org/apache/openjpa/conf/TestCacheMarshaller.java Wed Aug 29 15:07:44 2007
@@ -0,0 +1,69 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied. See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ */
+package org.apache.openjpa.conf;
+
+import org.apache.openjpa.conf.CacheMarshaller.ValidationPolicy;
+import org.apache.openjpa.persistence.test.SingleEMFTestCase;
+
+public class TestCacheMarshaller
+ extends SingleEMFTestCase {
+
+ private CacheMarshaller cm;
+
+ public void setUp() {
+ setUp(new Object[] { "openjpa.CacheMarshallers",
+ "default(Id=" + getClass().getName() + ", ValidationPolicy="
+ + OpenJPAVersionAndConfigurationTypeValidationPolicy.class
+ .getName()
+ + ", InputURL=file:" + getClass().getName() + ".ser, OutputFile="
+ + getClass().getName() + ".ser)"
+ });
+ emf.createEntityManager().close();
+ cm = CacheMarshallersValue.getMarshallerById(emf.getConfiguration(),
+ getClass().getName());
+ }
+
+ public void testCacheMarshallerType() {
+ assertEquals(CacheMarshallerImpl.class, cm.getClass());
+ }
+
+ public void testConfiguration() {
+ assertEquals(getClass().getName(), cm.getId());
+ }
+
+ public void testValidation() {
+ ValidationPolicy vp = ((CacheMarshallerImpl) cm).getValidationPolicy();
+ assertEquals(OpenJPAVersionAndConfigurationTypeValidationPolicy.class,
+ vp.getClass());
+ Object[] cached = (Object[]) vp.getCacheableData(this);
+
+ assertEquals(3, cached.length);
+ assertEquals(OpenJPAVersion.VERSION_ID, cached[0]);
+ assertEquals(emf.getConfiguration().getClass().getName(), cached[1]);
+ assertEquals(this, cached[2]);
+
+ assertEquals(this, vp.getValidData(cached));
+ }
+
+ public void testRoundTrip() {
+ Object o = "foo";
+ cm.store(o);
+ assertEquals(o, cm.load());
+ }
+}
Added: openjpa/trunk/openjpa-persistence-jdbc/src/test/java/org/apache/openjpa/conf/TestCacheMarshallerEndToEnd.java
URL: http://svn.apache.org/viewvc/openjpa/trunk/openjpa-persistence-jdbc/src/test/java/org/apache/openjpa/conf/TestCacheMarshallerEndToEnd.java?rev=570948&view=auto
==============================================================================
--- openjpa/trunk/openjpa-persistence-jdbc/src/test/java/org/apache/openjpa/conf/TestCacheMarshallerEndToEnd.java (added)
+++ openjpa/trunk/openjpa-persistence-jdbc/src/test/java/org/apache/openjpa/conf/TestCacheMarshallerEndToEnd.java Wed Aug 29 15:07:44 2007
@@ -0,0 +1,114 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied. See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ */
+package org.apache.openjpa.conf;
+
+import java.io.ByteArrayOutputStream;
+import java.io.IOException;
+import java.io.PrintStream;
+import java.util.ArrayList;
+import java.util.List;
+import javax.persistence.EntityManager;
+import javax.persistence.Query;
+
+import org.apache.openjpa.persistence.JPAFacadeHelper;
+import org.apache.openjpa.persistence.OpenJPAEntityManagerFactorySPI;
+import org.apache.openjpa.persistence.query.NamedQueryEntity;
+import org.apache.openjpa.persistence.simple.AllFieldTypes;
+import org.apache.openjpa.persistence.test.PersistenceTestCase;
+
+public class TestCacheMarshallerEndToEnd
+ extends PersistenceTestCase {
+
+ private static final Object[] STORE_PROPS = new Object[] {
+ "openjpa.CacheMarshallers",
+ "default(Id=" + MetaDataCacheMaintenance.class.getName()
+ + ", OutputFile=" + MetaDataCacheMaintenance.class.getName() +".ser"
+ + ", ConsumeSerializationErrors=false"
+ + ", ValidationPolicy="
+ + OpenJPAVersionAndConfigurationTypeValidationPolicy.class.getName()
+ + ")",
+ "openjpa.QueryCompilationCache",
+ "java.util.concurrent.ConcurrentHashMap",
+ AllFieldTypes.class,
+ NamedQueryEntity.class,
+ CLEAR_TABLES
+ };
+
+ private static final Object[] LOAD_PROPS = new Object[] {
+ "openjpa.CacheMarshallers",
+ "default(Id=" + MetaDataCacheMaintenance.class.getName()
+ + ", InputURL=file:" + MetaDataCacheMaintenance.class.getName()
+ + ".ser"
+ + ", ConsumeSerializationErrors=false"
+ + ", ValidationPolicy="
+ + OpenJPAVersionAndConfigurationTypeValidationPolicy.class.getName()
+ + ")",
+ "openjpa.QueryCompilationCache",
+ "java.util.concurrent.ConcurrentHashMap",
+ AllFieldTypes.class,
+ NamedQueryEntity.class
+ };
+
+
+ public void testCacheMarshallerEndToEnd()
+ throws IOException {
+ OpenJPAEntityManagerFactorySPI emf = createEMF(STORE_PROPS);
+ CacheMarshallerImpl cm = (CacheMarshallerImpl)
+ CacheMarshallersValue.getMarshallerById(
+ emf.getConfiguration(), MetaDataCacheMaintenance.class.getName());
+ cm.getOutputFile().delete();
+ MetaDataCacheMaintenance maint = new MetaDataCacheMaintenance(
+ JPAFacadeHelper.toBrokerFactory(emf), false, true);
+ final List<String> lines = new ArrayList<String>();
+ PrintStream out = new PrintStream(new ByteArrayOutputStream()) {
+ public void println(String line) {
+ lines.add(line);
+ }
+
+ public void println(Object line) {
+ println(line.toString());
+ }
+ };
+ maint.setOutputStream(out);
+ maint.store();
+ assertContains(lines, " " + AllFieldTypes.class.getName());
+ assertContains(lines, " " + NamedQueryEntity.class.getName());
+ assertContains(lines, " NamedQueryEntity.namedQuery");
+ emf.close();
+
+ emf = createEMF(LOAD_PROPS);
+ EntityManager em = emf.createEntityManager();
+ em.getTransaction().begin();
+ em.persist(new NamedQueryEntity("foo"));
+ em.flush();
+ Query q = em.createNamedQuery("NamedQueryEntity.namedQuery");
+ assertEquals(1, q.getResultList().size());
+ em.getTransaction().rollback();
+ em.close();
+ emf.close();
+ }
+
+ private void assertContains(List<String> lines, String prefix) {
+ for (String line : lines)
+ if (line.startsWith(prefix))
+ return;
+ fail("should contain a line starting with " + prefix
+ + ": " + lines);
+ }
+}
Added: openjpa/trunk/openjpa-persistence-jdbc/src/test/java/org/apache/openjpa/persistence/query/NamedQueryEntity.java
URL: http://svn.apache.org/viewvc/openjpa/trunk/openjpa-persistence-jdbc/src/test/java/org/apache/openjpa/persistence/query/NamedQueryEntity.java?rev=570948&view=auto
==============================================================================
--- openjpa/trunk/openjpa-persistence-jdbc/src/test/java/org/apache/openjpa/persistence/query/NamedQueryEntity.java (added)
+++ openjpa/trunk/openjpa-persistence-jdbc/src/test/java/org/apache/openjpa/persistence/query/NamedQueryEntity.java Wed Aug 29 15:07:44 2007
@@ -0,0 +1,42 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied. See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ */
+package org.apache.openjpa.persistence.query;
+
+import javax.persistence.Entity;
+import javax.persistence.GeneratedValue;
+import javax.persistence.Id;
+import javax.persistence.NamedQuery;
+
+@Entity
+@NamedQuery(name="NamedQueryEntity.namedQuery",
+ query="select o from NamedQueryEntity o where o.stringField = 'foo'")
+public class NamedQueryEntity {
+ @Id @GeneratedValue
+ private Integer id;
+
+ private String stringField;
+
+ public NamedQueryEntity(String stringField) {
+ this.stringField = stringField;
+ }
+
+ public NamedQueryEntity() {
+ // for JPA
+ }
+}
|